diff --git a/.gitignore b/.gitignore
index 6a3815d..8347dfb 100644
--- a/.gitignore
+++ b/.gitignore
@@ -11,4 +11,5 @@ build/
.idea/
key.properties
+premium_features_manager.class.dart
pubspec.lock
\ No newline at end of file
diff --git a/android/app/src/main/AndroidManifest.xml b/android/app/src/main/AndroidManifest.xml
index 57c694b..59be133 100644
--- a/android/app/src/main/AndroidManifest.xml
+++ b/android/app/src/main/AndroidManifest.xml
@@ -7,6 +7,7 @@
-->
+
@@ -46,5 +47,12 @@
+
+
+
+
+
+
diff --git a/android/app/src/main/java/com/keyboardcrumbs/hassclient/Application.java b/android/app/src/main/java/com/keyboardcrumbs/hassclient/Application.java
new file mode 100644
index 0000000..d77e627
--- /dev/null
+++ b/android/app/src/main/java/com/keyboardcrumbs/hassclient/Application.java
@@ -0,0 +1,20 @@
+package com.keyboardcrumbs.hassclient;
+
+import io.flutter.app.FlutterApplication;
+import io.flutter.plugin.common.PluginRegistry;
+import io.flutter.plugin.common.PluginRegistry.PluginRegistrantCallback;
+import io.flutter.plugins.GeneratedPluginRegistrant;
+import com.lyokone.location.LocationPlugin;
+
+public class Application extends FlutterApplication implements PluginRegistrantCallback {
+ @Override
+ public void onCreate() {
+ super.onCreate();
+ LocationPlugin.setPluginRegistrant(this);
+ }
+
+ @Override
+ public void registerWith(PluginRegistry registry) {
+ GeneratedPluginRegistrant.registerWith(registry);
+ }
+}
\ No newline at end of file
diff --git a/flutter_01.log b/flutter_01.log
new file mode 100644
index 0000000..b4dfb04
--- /dev/null
+++ b/flutter_01.log
@@ -0,0 +1,41 @@
+Flutter crash report; please file at https://github.com/flutter/flutter/issues.
+
+## command
+
+flutter --no-color run --machine --track-widget-creation --device-id=89AY052S4 lib/main.dart
+
+## exception
+
+_InternalLinkedHashMap: {code: 105, message: Isolate must be runnable, data: {request: {method: _reloadSources, params: {pause: true, rootLibUri: file:///data/user/0/com.keyboardcrumbs.haclient/code_cache/ha_clientSYJJZI/ha_client/lib/main.dart.incremental.dill, packagesUri: file:///data/user/0/com.keyboardcrumbs.haclient/code_cache/ha_clientSYJJZI/ha_client/.packages, isolateId: isolates/68989666}}, details: Isolate must be runnable before this request is made.}}
+
+```
+null```
+
+## flutter doctor
+
+```
+[✓] Flutter (Channel stable, v1.7.8+hotfix.4, on Linux, locale en_US.UTF-8)
+ • Flutter version 1.7.8+hotfix.4 at /home/estevez/sdk/flutter
+ • Framework revision 20e59316b8 (6 weeks ago), 2019-07-18 20:04:33 -0700
+ • Engine revision fee001c93f
+ • Dart version 2.4.0
+
+[✓] Android toolchain - develop for Android devices (Android SDK version 29.0.2)
+ • Android SDK at /home/estevez/Android/Sdk
+ • Android NDK location not configured (optional; useful for native profiling support)
+ • Platform android-29, build-tools 29.0.2
+ • Java binary at: /home/estevez/bin/android-studio/jre/bin/java
+ • Java version OpenJDK Runtime Environment (build 1.8.0_202-release-1483-b49-5587405)
+ • All Android licenses accepted.
+
+[✓] Android Studio (version 3.5)
+ • Android Studio at /home/estevez/bin/android-studio
+ • Flutter plugin version 38.2.3
+ • Dart plugin version 191.8423
+ • Java version OpenJDK Runtime Environment (build 1.8.0_202-release-1483-b49-5587405)
+
+[✓] Connected device (1 available)
+ • Pixel 3 XL • 89AY052S4 • android-arm64 • Android 9 (API 28)
+
+• No issues found!
+```
diff --git a/lib/main.dart b/lib/main.dart
index 2d311a7..ccdc68b 100644
--- a/lib/main.dart
+++ b/lib/main.dart
@@ -15,7 +15,6 @@ import 'package:http/http.dart' as http;
import 'package:charts_flutter/flutter.dart' as charts;
import 'package:progress_indicators/progress_indicators.dart';
import 'package:flutter_markdown/flutter_markdown.dart';
-//import 'package:flutter_svg/flutter_svg.dart';
import 'package:flutter_custom_tabs/flutter_custom_tabs.dart';
import 'package:firebase_messaging/firebase_messaging.dart';
import 'package:flutter_webview_plugin/flutter_webview_plugin.dart';
@@ -23,8 +22,10 @@ import 'package:flutter_secure_storage/flutter_secure_storage.dart';
import 'package:device_info/device_info.dart';
import 'package:flutter_local_notifications/flutter_local_notifications.dart';
import 'package:in_app_purchase/in_app_purchase.dart';
+import 'package:location/location.dart';
part 'const.dart';
+part 'premium_features_manager.class.dart';
part 'entities/entity.class.dart';
part 'entities/entity_wrapper.class.dart';
part 'entities/timer/timer_entity.class.dart';
@@ -118,7 +119,7 @@ FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin = new FlutterLoc
const String appName = "HA Client";
const appVersion = "0.6.4";
-void main() {
+void main() async {
FlutterError.onError = (errorDetails) {
Logger.e( "${errorDetails.exception}");
if (Logger.isInDebugMode) {
@@ -127,7 +128,9 @@ void main() {
};
runZoned(() {
+
runApp(new HAClientApp());
+
}, onError: (error, stack) {
Logger.e("$error");
Logger.e("$stack");
@@ -239,6 +242,8 @@ class _MainPageState extends State with WidgetsBindingObserver, Ticker
flutterLocalNotificationsPlugin.initialize(initializationSettings,
onSelectNotification: onSelectNotification);
+
+
_settingsSubscription = eventBus.on().listen((event) {
Logger.d("Settings change event: reconnect=${event.reconnect}");
if (event.reconnect) {
@@ -247,6 +252,8 @@ class _MainPageState extends State with WidgetsBindingObserver, Ticker
});
_fullLoad();
+
+
}
Future onSelectNotification(String payload) async {
@@ -274,6 +281,7 @@ class _MainPageState extends State with WidgetsBindingObserver, Ticker
_showInfoBottomBar(progress: true,);
_subscribe().then((_) {
Connection().init(loadSettings: true, forceReconnect: true).then((__){
+ PremiumFeaturesManager();
_fetchData();
}, onError: (e) {
_setErrorState(e);
@@ -321,6 +329,7 @@ class _MainPageState extends State with WidgetsBindingObserver, Ticker
void _handlePurchaseUpdates(purchase) {
if (purchase is List) {
if (purchase[0].status == PurchaseStatus.purchased) {
+ PremiumFeaturesManager().updatePurchases(purchase[0]);
eventBus.fire(ShowPopupMessageEvent(
title: "Thanks a lot!",
body: "Thank you for supporting HA Client development!",
@@ -752,6 +761,7 @@ class _MainPageState extends State with WidgetsBindingObserver, Ticker
Widget _buildScaffoldBody(bool empty) {
List> popupMenuItems = [];
+
popupMenuItems.add(PopupMenuItem(
child: new Text("Reload"),
value: "reload",
diff --git a/lib/pages/purchase.page.dart b/lib/pages/purchase.page.dart
index ef4c733..8b0d7d1 100644
--- a/lib/pages/purchase.page.dart
+++ b/lib/pages/purchase.page.dart
@@ -10,66 +10,29 @@ class PurchasePage extends StatefulWidget {
}
class _PurchasePageState extends State {
-
+
bool _loaded = false;
String _error = "";
- List _products;
- List _purchases;
+
@override
void initState() {
super.initState();
- _loadProducts();
- }
-
- _loadProducts() async {
- final bool available = await InAppPurchaseConnection.instance.isAvailable();
- if (!available) {
- setState(() {
- _error = "Error connecting to store";
- });
+ if (PremiumFeaturesManager().products.isEmpty) {
+ _error = "Subscription is not loaded";
} else {
- const Set _kIds = {'just_few_bucks_per_year', 'app_fan_support_per_year', 'grateful_user_support_per_year'};
- final ProductDetailsResponse response = await InAppPurchaseConnection.instance.queryProductDetails(_kIds);
- if (!response.notFoundIDs.isEmpty) {
- Logger.d("Products not found: ${response.notFoundIDs}");
- }
- _products = response.productDetails;
- _loadPreviousPurchases();
+ _loaded = true;
}
}
- _loadPreviousPurchases() async {
- final QueryPurchaseDetailsResponse response = await InAppPurchaseConnection.instance.queryPastPurchases();
- if (response.error != null) {
- setState(() {
- _error = "Error loading previous purchases";
- });
- } else {
- _purchases = response.pastPurchases;
- for (PurchaseDetails purchase in _purchases) {
- Logger.d("Previous purchase: ${purchase.status}");
- }
- if (_products.isEmpty) {
- setState(() {
- _error = "No data found in store";
- });
- } else {
- setState(() {
- _loaded = true;
- });
- }
- }
- }
-
Widget _buildProducts() {
List productWidgets = [];
- for (ProductDetails product in _products) {
+ for (ProductDetails product in PremiumFeaturesManager().products) {
productWidgets.add(
ProductPurchase(
product: product,
onBuy: (product) => _buyProduct(product),
- purchased: _purchases.any((purchase) { return purchase.productID == product.id;}),)
+ purchased: PremiumFeaturesManager().purchases.any((purchase) { return purchase.productID == product.id;}),)
);
}
return ListView(
diff --git a/pubspec.lock b/pubspec.lock
index 0dc0c35..c51d396 100644
--- a/pubspec.lock
+++ b/pubspec.lock
@@ -49,14 +49,14 @@ packages:
name: charts_common
url: "https://pub.dartlang.org"
source: hosted
- version: "0.6.0"
+ version: "0.7.0"
charts_flutter:
dependency: "direct main"
description:
name: charts_flutter
url: "https://pub.dartlang.org"
source: hosted
- version: "0.6.0"
+ version: "0.7.0"
collection:
dependency: transitive
description:
@@ -77,7 +77,7 @@ packages:
name: crypto
url: "https://pub.dartlang.org"
source: hosted
- version: "2.1.1+1"
+ version: "2.1.2"
date_format:
dependency: "direct main"
description:
@@ -207,6 +207,15 @@ packages:
url: "https://pub.dartlang.org"
source: hosted
version: "2.4.0"
+ location:
+ dependency: "direct main"
+ description:
+ path: "."
+ ref: background_location
+ resolved-ref: "7c089fad38acbb7be7c46f207f601ac8e6b21caf"
+ url: "git://github.com/Lyokone/flutterlocation.git"
+ source: git
+ version: "2.3.5"
logging:
dependency: transitive
description:
@@ -309,7 +318,7 @@ packages:
name: sqflite
url: "https://pub.dartlang.org"
source: hosted
- version: "1.1.6+3"
+ version: "1.1.6+4"
stack_trace:
dependency: transitive
description:
diff --git a/pubspec.yaml b/pubspec.yaml
index 26fe385..a2cdb7e 100644
--- a/pubspec.yaml
+++ b/pubspec.yaml
@@ -26,6 +26,11 @@ dependencies:
flutter_secure_storage: ^3.2.1+1
device_info: ^0.4.0+2
flutter_local_notifications: ^0.8.2
+ location:
+ git:
+ url: git://github.com/Lyokone/flutterlocation.git
+ ref: background_location
+
dev_dependencies:
flutter_test: