forked from firka/student-legacy
added ad provider
This commit is contained in:
parent
fceb4e050f
commit
a5a43ea0b9
14
filcnaplo/ios/Flutter/Generated 2.xcconfig
Normal file
14
filcnaplo/ios/Flutter/Generated 2.xcconfig
Normal file
@ -0,0 +1,14 @@
|
||||
// This is a generated file; do not edit or check into version control.
|
||||
FLUTTER_ROOT=/Users/kima/src/flutter
|
||||
FLUTTER_APPLICATION_PATH=/Users/kima/Documents/refilc/app/naplo/filcnaplo
|
||||
COCOAPODS_PARALLEL_CODE_SIGN=true
|
||||
FLUTTER_TARGET=lib/main.dart
|
||||
FLUTTER_BUILD_DIR=build
|
||||
FLUTTER_BUILD_NAME=4.2.0
|
||||
FLUTTER_BUILD_NUMBER=220
|
||||
EXCLUDED_ARCHS[sdk=iphonesimulator*]=i386
|
||||
EXCLUDED_ARCHS[sdk=iphoneos*]=armv7
|
||||
DART_OBFUSCATION=false
|
||||
TRACK_WIDGET_CREATION=true
|
||||
TREE_SHAKE_ICONS=false
|
||||
PACKAGE_CONFIG=.dart_tool/package_config.json
|
13
filcnaplo/ios/Flutter/flutter_export_environment 3.sh
Executable file
13
filcnaplo/ios/Flutter/flutter_export_environment 3.sh
Executable file
@ -0,0 +1,13 @@
|
||||
#!/bin/sh
|
||||
# This is a generated file; do not edit or check into version control.
|
||||
export "FLUTTER_ROOT=/Users/kima/src/flutter"
|
||||
export "FLUTTER_APPLICATION_PATH=/Users/kima/Documents/refilc/app/naplo/filcnaplo"
|
||||
export "COCOAPODS_PARALLEL_CODE_SIGN=true"
|
||||
export "FLUTTER_TARGET=lib/main.dart"
|
||||
export "FLUTTER_BUILD_DIR=build"
|
||||
export "FLUTTER_BUILD_NAME=4.2.0"
|
||||
export "FLUTTER_BUILD_NUMBER=220"
|
||||
export "DART_OBFUSCATION=false"
|
||||
export "TRACK_WIDGET_CREATION=true"
|
||||
export "TREE_SHAKE_ICONS=false"
|
||||
export "PACKAGE_CONFIG=.dart_tool/package_config.json"
|
@ -1,6 +1,7 @@
|
||||
import 'dart:convert';
|
||||
import 'dart:developer';
|
||||
|
||||
import 'package:filcnaplo/models/ad.dart';
|
||||
import 'package:filcnaplo/models/config.dart';
|
||||
import 'package:filcnaplo/models/news.dart';
|
||||
import 'package:filcnaplo/models/release.dart';
|
||||
@ -19,6 +20,7 @@ class FilcAPI {
|
||||
|
||||
// Private API
|
||||
static const config = "https://api.refilc.hu/v1/private/config";
|
||||
static const ads = "https://api.refilc.hu/v1/private/ads";
|
||||
static const reportApi = "https://api.refilc.hu/v1/private/crash-report";
|
||||
static const premiumApi = "https://api.filcnaplo.hu/premium/activate";
|
||||
// static const premiumScopesApi = "https://api.filcnaplo.hu/premium/scopes";
|
||||
@ -117,6 +119,24 @@ class FilcAPI {
|
||||
return null;
|
||||
}
|
||||
|
||||
static Future<List<Ad>?> getAds() async {
|
||||
try {
|
||||
http.Response res = await http.get(Uri.parse(ads));
|
||||
|
||||
if (res.statusCode == 200) {
|
||||
return (jsonDecode(res.body) as List)
|
||||
.cast<Map>()
|
||||
.map((e) => Ad.fromJson(e))
|
||||
.toList();
|
||||
} else {
|
||||
throw "HTTP ${res.statusCode}: ${res.body}";
|
||||
}
|
||||
} on Exception catch (error, stacktrace) {
|
||||
log("ERROR: FilcAPI.getAds: $error $stacktrace");
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
static Future<List<Release>?> getReleases() async {
|
||||
try {
|
||||
http.Response res = await http.get(Uri.parse(releases));
|
||||
|
29
filcnaplo/lib/api/providers/ad_provider.dart
Normal file
29
filcnaplo/lib/api/providers/ad_provider.dart
Normal file
@ -0,0 +1,29 @@
|
||||
import 'package:filcnaplo/api/client.dart';
|
||||
import 'package:filcnaplo/models/ad.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class AdProvider extends ChangeNotifier {
|
||||
// private
|
||||
late List<Ad> _ads;
|
||||
bool get available => _ads.isNotEmpty;
|
||||
|
||||
// public
|
||||
List<Ad> get ads => _ads;
|
||||
|
||||
AdProvider({
|
||||
List<Ad> initialAds = const [],
|
||||
required BuildContext context,
|
||||
}) {
|
||||
_ads = List.castFrom(initialAds);
|
||||
}
|
||||
|
||||
Future<void> fetch() async {
|
||||
_ads = await FilcAPI.getAds() ?? [];
|
||||
_ads.sort((a, b) => -a.date.compareTo(b.date));
|
||||
|
||||
// check for new ads
|
||||
if (_ads.isNotEmpty) {
|
||||
notifyListeners();
|
||||
}
|
||||
}
|
||||
}
|
29
filcnaplo/lib/models/ad.dart
Normal file
29
filcnaplo/lib/models/ad.dart
Normal file
@ -0,0 +1,29 @@
|
||||
class Ad {
|
||||
String title;
|
||||
String description;
|
||||
String author;
|
||||
Uri? logoUrl;
|
||||
bool overridePremium;
|
||||
DateTime date;
|
||||
|
||||
Ad({
|
||||
required this.title,
|
||||
required this.description,
|
||||
required this.author,
|
||||
required this.logoUrl,
|
||||
this.overridePremium = false,
|
||||
required this.date,
|
||||
});
|
||||
|
||||
factory Ad.fromJson(Map json) {
|
||||
return Ad(
|
||||
title: json['title'] ?? 'Ad',
|
||||
description: json['description'] ?? '',
|
||||
author: json['author'] ?? 'reFilc',
|
||||
logoUrl: json['logo_url'] != null ? Uri.parse(json['logo_url']) : null,
|
||||
overridePremium: json['override_premium'] ?? false,
|
||||
date:
|
||||
json['date'] != null ? DateTime.parse(json['date']) : DateTime.now(),
|
||||
);
|
||||
}
|
||||
}
|
@ -1,3 +1,4 @@
|
||||
import 'package:filcnaplo/api/providers/ad_provider.dart';
|
||||
import 'package:filcnaplo/api/providers/update_provider.dart';
|
||||
import 'package:filcnaplo/models/settings.dart';
|
||||
import 'package:filcnaplo/ui/date_widget.dart';
|
||||
@ -14,6 +15,7 @@ import 'package:filcnaplo/ui/filter/widgets/lessons.dart' as lesson_filter;
|
||||
import 'package:filcnaplo/ui/filter/widgets/update.dart' as update_filter;
|
||||
import 'package:filcnaplo/ui/filter/widgets/missed_exams.dart'
|
||||
as missed_exam_filter;
|
||||
import 'package:filcnaplo/ui/filter/widgets/ads.dart' as ad_filter;
|
||||
import 'package:filcnaplo_kreta_api/models/week.dart';
|
||||
import 'package:filcnaplo_kreta_api/providers/absence_provider.dart';
|
||||
import 'package:filcnaplo_kreta_api/providers/event_provider.dart';
|
||||
@ -50,7 +52,8 @@ enum FilterType {
|
||||
lessons,
|
||||
updates,
|
||||
certifications,
|
||||
missedExams
|
||||
missedExams,
|
||||
ads,
|
||||
}
|
||||
|
||||
Future<List<DateWidget>> getFilterWidgets(FilterType activeData,
|
||||
@ -65,6 +68,7 @@ Future<List<DateWidget>> getFilterWidgets(FilterType activeData,
|
||||
final eventProvider = Provider.of<EventProvider>(context);
|
||||
final updateProvider = Provider.of<UpdateProvider>(context);
|
||||
final settingsProvider = Provider.of<SettingsProvider>(context);
|
||||
final adProvider = Provider.of<AdProvider>(context);
|
||||
|
||||
List<DateWidget> items = [];
|
||||
|
||||
@ -82,6 +86,7 @@ Future<List<DateWidget>> getFilterWidgets(FilterType activeData,
|
||||
getFilterWidgets(FilterType.updates, context: context),
|
||||
getFilterWidgets(FilterType.certifications, context: context),
|
||||
getFilterWidgets(FilterType.missedExams, context: context),
|
||||
getFilterWidgets(FilterType.ads, context: context),
|
||||
]);
|
||||
items = all.expand((x) => x).toList();
|
||||
|
||||
@ -89,9 +94,9 @@ Future<List<DateWidget>> getFilterWidgets(FilterType activeData,
|
||||
|
||||
// Grades
|
||||
case FilterType.grades:
|
||||
if(!settingsProvider.gradeOpeningFun) {
|
||||
gradeProvider.seenAll();
|
||||
}
|
||||
if (!settingsProvider.gradeOpeningFun) {
|
||||
gradeProvider.seenAll();
|
||||
}
|
||||
items = grade_filter.getWidgets(
|
||||
gradeProvider.grades, gradeProvider.lastSeenDate);
|
||||
if (settingsProvider.gradeOpeningFun) {
|
||||
@ -164,6 +169,13 @@ Future<List<DateWidget>> getFilterWidgets(FilterType activeData,
|
||||
items = missed_exam_filter
|
||||
.getWidgets(timetableProvider.getWeek(Week.current()) ?? []);
|
||||
break;
|
||||
|
||||
// Ads
|
||||
case FilterType.ads:
|
||||
if (adProvider.available) {
|
||||
items = ad_filter.getWidgets(adProvider.ads);
|
||||
}
|
||||
break;
|
||||
}
|
||||
return items;
|
||||
}
|
||||
|
24
filcnaplo/lib/ui/filter/widgets/ads.dart
Normal file
24
filcnaplo/lib/ui/filter/widgets/ads.dart
Normal file
@ -0,0 +1,24 @@
|
||||
import 'package:filcnaplo/models/ad.dart';
|
||||
import 'package:filcnaplo/ui/date_widget.dart';
|
||||
import 'package:filcnaplo_mobile_ui/common/widgets/ad/ad_viewable.dart'
|
||||
as mobile;
|
||||
|
||||
List<DateWidget> getWidgets(List<Ad> providerAds) {
|
||||
List<DateWidget> items = [];
|
||||
|
||||
if (providerAds.isNotEmpty) {
|
||||
for (var ad in providerAds) {
|
||||
if (ad.date.isAfter(DateTime.now())) {
|
||||
providerAds.sort((a, b) => -a.date.compareTo(b.date));
|
||||
|
||||
items.add(DateWidget(
|
||||
key: ad.description,
|
||||
date: ad.date,
|
||||
widget: mobile.AdViewable(ad),
|
||||
));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return items;
|
||||
}
|
@ -24,7 +24,7 @@ class KretaAPI {
|
||||
KretaApiEndpoints.groupAverages +
|
||||
"?oktatasiNevelesiFeladatUid=" +
|
||||
uid;
|
||||
static String averages(String iss, String uid) =>
|
||||
static String averages(String iss, String uid) =>
|
||||
BaseKreta.kreta(iss) +
|
||||
KretaApiEndpoints.averages +
|
||||
"?oktatasiNevelesiFeladatUid=" +
|
||||
@ -95,8 +95,7 @@ class KretaApiEndpoints {
|
||||
static const groups = "/ellenorzo/V3/Sajat/OsztalyCsoportok";
|
||||
static const groupAverages =
|
||||
"/ellenorzo/V3/Sajat/Ertekelesek/Atlagok/OsztalyAtlagok";
|
||||
static const averages =
|
||||
"/ellenorzo/V3/Sajat/Ertekelesek/Atlagok/TantargyiAtlagok";
|
||||
static const averages = "/ellenorzo/V3/idk";
|
||||
static const timetable = "/ellenorzo/V3/Sajat/OrarendElemek";
|
||||
static const exams = "/ellenorzo/V3/Sajat/BejelentettSzamonkeresek";
|
||||
static const homework = "/ellenorzo/V3/Sajat/HaziFeladatok";
|
||||
|
30
filcnaplo_mobile_ui/lib/common/widgets/ad/ad_tile.dart
Normal file
30
filcnaplo_mobile_ui/lib/common/widgets/ad/ad_tile.dart
Normal file
@ -0,0 +1,30 @@
|
||||
import 'package:filcnaplo/models/ad.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:filcnaplo_mobile_ui/common/panel/panel_button.dart';
|
||||
import 'package:flutter_feather_icons/flutter_feather_icons.dart';
|
||||
|
||||
class AdTile extends StatelessWidget {
|
||||
const AdTile(this.ad, {Key? key, this.onTap, this.padding}) : super(key: key);
|
||||
|
||||
final Ad ad;
|
||||
final Function()? onTap;
|
||||
final EdgeInsetsGeometry? padding;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Padding(
|
||||
padding: padding ?? const EdgeInsets.symmetric(horizontal: 8.0),
|
||||
child: PanelButton(
|
||||
onPressed: onTap,
|
||||
title: Column(
|
||||
children: [
|
||||
Text(ad.title),
|
||||
Text(ad.description),
|
||||
],
|
||||
),
|
||||
leading: Image.network(ad.logoUrl.toString()),
|
||||
trailing: const Icon(FeatherIcons.externalLink),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
18
filcnaplo_mobile_ui/lib/common/widgets/ad/ad_viewable.dart
Normal file
18
filcnaplo_mobile_ui/lib/common/widgets/ad/ad_viewable.dart
Normal file
@ -0,0 +1,18 @@
|
||||
import 'package:filcnaplo/models/ad.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
import 'ad_tile.dart';
|
||||
|
||||
class AdViewable extends StatelessWidget {
|
||||
const AdViewable(this.ad, {Key? key}) : super(key: key);
|
||||
|
||||
final Ad ad;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return AdTile(
|
||||
ad,
|
||||
onTap: () => [],
|
||||
);
|
||||
}
|
||||
}
|
@ -5,6 +5,8 @@ import 'package:filcnaplo/api/providers/database_provider.dart';
|
||||
import 'package:filcnaplo/api/providers/user_provider.dart';
|
||||
import 'package:filcnaplo/models/settings.dart';
|
||||
import 'package:filcnaplo/utils/format.dart';
|
||||
// import 'package:filcnaplo_kreta_api/client/api.dart';
|
||||
// import 'package:filcnaplo_kreta_api/client/client.dart';
|
||||
import 'package:filcnaplo_kreta_api/providers/grade_provider.dart';
|
||||
import 'package:filcnaplo/helpers/average_helper.dart';
|
||||
import 'package:filcnaplo/helpers/subject.dart';
|
||||
|
@ -2,6 +2,8 @@ import 'dart:math';
|
||||
|
||||
import 'package:auto_size_text/auto_size_text.dart';
|
||||
import 'package:filcnaplo/api/providers/update_provider.dart';
|
||||
// import 'package:filcnaplo_kreta_api/client/api.dart';
|
||||
// import 'package:filcnaplo_kreta_api/client/client.dart';
|
||||
import 'package:filcnaplo_kreta_api/providers/grade_provider.dart';
|
||||
import 'package:filcnaplo/api/providers/user_provider.dart';
|
||||
import 'package:filcnaplo/theme/colors/colors.dart';
|
||||
@ -112,6 +114,18 @@ class _GradesPageState extends State<GradesPage> {
|
||||
} else {
|
||||
tiles.insert(
|
||||
0,
|
||||
// TextButton(
|
||||
// onPressed: () async {
|
||||
// var url = KretaAPI.averages(
|
||||
// user.instituteCode!,
|
||||
// user.id!,
|
||||
// );
|
||||
// print(url);
|
||||
// var res = await Provider.of<KretaClient>(context, listen: false)
|
||||
// .getAPI(url);
|
||||
// print(res);
|
||||
// },
|
||||
// child: Text('test')),
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(top: 24.0),
|
||||
child: Empty(subtitle: "empty".i18n),
|
||||
|
@ -26,6 +26,7 @@ import 'package:home_widget/home_widget.dart';
|
||||
import 'package:wtf_sliding_sheet/wtf_sliding_sheet.dart';
|
||||
import 'package:background_fetch/background_fetch.dart';
|
||||
import 'package:filcnaplo_premium/providers/goal_provider.dart';
|
||||
import 'package:filcnaplo/api/providers/ad_provider.dart';
|
||||
|
||||
class NavigationScreen extends StatefulWidget {
|
||||
const NavigationScreen({Key? key}) : super(key: key);
|
||||
@ -48,6 +49,7 @@ class NavigationScreenState extends State<NavigationScreen>
|
||||
late GoalProvider goalProvider;
|
||||
late UpdateProvider updateProvider;
|
||||
late GradeProvider gradeProvicer;
|
||||
late AdProvider adProvider;
|
||||
|
||||
NavigatorState? get navigator => _navigatorState.currentState;
|
||||
|
||||
@ -176,6 +178,10 @@ class NavigationScreenState extends State<NavigationScreen>
|
||||
updateProvider = Provider.of<UpdateProvider>(context, listen: false);
|
||||
updateProvider.fetch();
|
||||
|
||||
// get advertisements
|
||||
adProvider = Provider.of<AdProvider>(context, listen: false);
|
||||
adProvider.fetch();
|
||||
|
||||
// initial sync
|
||||
syncAll(context);
|
||||
setupQuickActions();
|
||||
|
Loading…
x
Reference in New Issue
Block a user