forked from github/szkolny
[Widgets] Implement new Notifications widget.
This commit is contained in:
parent
7b97ef316d
commit
878de34546
@ -25,10 +25,10 @@
|
|||||||
-keep class pl.szczodrzynski.edziennik.data.db.entity.Event { *; }
|
-keep class pl.szczodrzynski.edziennik.data.db.entity.Event { *; }
|
||||||
-keep class pl.szczodrzynski.edziennik.data.db.full.EventFull { *; }
|
-keep class pl.szczodrzynski.edziennik.data.db.full.EventFull { *; }
|
||||||
-keep class pl.szczodrzynski.edziennik.ui.modules.home.HomeCardModel { *; }
|
-keep class pl.szczodrzynski.edziennik.ui.modules.home.HomeCardModel { *; }
|
||||||
-keepclassmembers class pl.szczodrzynski.edziennik.widgets.WidgetConfig { public *; }
|
-keepclassmembers class pl.szczodrzynski.edziennik.ui.widgets.WidgetConfig { public *; }
|
||||||
-keepnames class pl.szczodrzynski.edziennik.WidgetTimetable
|
-keepnames class pl.szczodrzynski.edziennik.ui.widgets.timetable.WidgetTimetableProvider
|
||||||
-keepnames class pl.szczodrzynski.edziennik.notifications.WidgetNotifications
|
-keepnames class pl.szczodrzynski.edziennik.ui.widgets.notifications.WidgetNotificationsProvider
|
||||||
-keepnames class pl.szczodrzynski.edziennik.luckynumber.WidgetLuckyNumber
|
-keepnames class pl.szczodrzynski.edziennik.widgets.luckynumber.WidgetLuckyNumber
|
||||||
|
|
||||||
-keep class .R
|
-keep class .R
|
||||||
-keep class **.R$* {
|
-keep class **.R$* {
|
||||||
|
@ -3,6 +3,17 @@
|
|||||||
xmlns:tools="http://schemas.android.com/tools"
|
xmlns:tools="http://schemas.android.com/tools"
|
||||||
package="pl.szczodrzynski.edziennik">
|
package="pl.szczodrzynski.edziennik">
|
||||||
|
|
||||||
|
<uses-permission android:name="android.permission.REQUEST_INSTALL_PACKAGES" />
|
||||||
|
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
|
||||||
|
<uses-permission android:name="android.permission.INTERNET" />
|
||||||
|
<uses-permission android:name="android.permission.WAKE_LOCK" />
|
||||||
|
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
|
||||||
|
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
|
||||||
|
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
|
||||||
|
<uses-permission android:name="android.permission.VIBRATE" />
|
||||||
|
<uses-permission android:name="android.permission.CAMERA" />
|
||||||
|
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
|
||||||
|
|
||||||
<application
|
<application
|
||||||
android:name=".App"
|
android:name=".App"
|
||||||
android:allowBackup="true"
|
android:allowBackup="true"
|
||||||
@ -15,12 +26,16 @@
|
|||||||
android:theme="@style/AppTheme.Dark"
|
android:theme="@style/AppTheme.Dark"
|
||||||
android:usesCleartextTraffic="true"
|
android:usesCleartextTraffic="true"
|
||||||
tools:ignore="UnusedAttribute">
|
tools:ignore="UnusedAttribute">
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.login.LoginLibrusCaptchaActivity"
|
<!-- __ __ _ _ _ _ _
|
||||||
android:theme="@android:style/Theme.Dialog"
|
| \/ | (_) /\ | | (_) (_) |
|
||||||
android:excludeFromRecents="true"/>
|
| \ / | __ _ _ _ __ / \ ___| |_ ___ ___| |_ _ _
|
||||||
<activity
|
| |\/| |/ _` | | '_ \ / /\ \ / __| __| \ \ / / | __| | | |
|
||||||
android:name=".MainActivity"
|
| | | | (_| | | | | | / ____ \ (__| |_| |\ V /| | |_| |_| |
|
||||||
|
|_| |_|\__,_|_|_| |_| /_/ \_\___|\__|_| \_/ |_|\__|\__, |
|
||||||
|
__/ |
|
||||||
|
|___/ -->
|
||||||
|
<activity android:name=".MainActivity"
|
||||||
android:configChanges="orientation|screenSize"
|
android:configChanges="orientation|screenSize"
|
||||||
android:label="@string/app_name"
|
android:label="@string/app_name"
|
||||||
android:launchMode="singleTop"
|
android:launchMode="singleTop"
|
||||||
@ -32,58 +47,7 @@
|
|||||||
<category android:name="android.intent.category.LAUNCHER" />
|
<category android:name="android.intent.category.LAUNCHER" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</activity>
|
</activity>
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.feedback.FeedbackActivity"
|
|
||||||
android:configChanges="orientation|screenSize|keyboardHidden"
|
|
||||||
android:label="@string/app_name"
|
|
||||||
android:theme="@style/AppTheme" />
|
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.login.LoginActivity"
|
|
||||||
android:configChanges="orientation|screenSize"
|
|
||||||
android:launchMode="singleTop"
|
|
||||||
android:theme="@style/AppTheme.Light" />
|
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.intro.ChangelogIntroActivity"
|
|
||||||
android:configChanges="orientation|keyboardHidden"
|
|
||||||
android:label="@string/app_name"
|
|
||||||
android:theme="@style/Theme.Intro" />
|
|
||||||
<!--
|
|
||||||
______ _ _
|
|
||||||
| ____(_) | |
|
|
||||||
| |__ _ _ __ ___| |__ __ _ ___ ___
|
|
||||||
| __| | | '__/ _ \ '_ \ / _` / __|/ _ \
|
|
||||||
| | | | | | __/ |_) | (_| \__ \ __/
|
|
||||||
|_| |_|_| \___|_.__/ \__,_|___/\___/
|
|
||||||
-->
|
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.base.CrashActivity"
|
|
||||||
android:configChanges="orientation|screenSize|keyboardHidden"
|
|
||||||
android:process=":error_activity"
|
|
||||||
android:theme="@style/DeadTheme" />
|
|
||||||
<!--
|
|
||||||
_____ _ _ _ _ _
|
|
||||||
/ ____| | | | | (_) (_) |
|
|
||||||
| | _ __ __ _ ___| |__ __ _ ___| |_ ___ ___| |_ _ _
|
|
||||||
| | | '__/ _` / __| '_ \ / _` |/ __| __| \ \ / / | __| | | |
|
|
||||||
| |____| | | (_| \__ \ | | | | (_| | (__| |_| |\ V /| | |_| |_| |
|
|
||||||
\_____|_| \__,_|___/_| |_| \__,_|\___|\__|_| \_/ |_|\__|\__, |
|
|
||||||
__/ |
|
|
||||||
|___/
|
|
||||||
-->
|
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.base.CrashGtfoActivity"
|
|
||||||
android:configChanges="orientation|screenSize|keyboardHidden"
|
|
||||||
android:theme="@style/DeadTheme" />
|
|
||||||
<activity
|
|
||||||
android:name=".widgets.WidgetConfigActivity"
|
|
||||||
android:configChanges="orientation|keyboardHidden"
|
|
||||||
android:excludeFromRecents="true"
|
|
||||||
android:noHistory="true"
|
|
||||||
android:theme="@style/AppTheme.NoDisplay">
|
|
||||||
<intent-filter>
|
|
||||||
<action android:name="android.appwidget.action.APPWIDGET_CONFIGURE" />
|
|
||||||
</intent-filter>
|
|
||||||
</activity>
|
|
||||||
<!--
|
<!--
|
||||||
__ ___ _ _
|
__ ___ _ _
|
||||||
\ \ / (_) | | | |
|
\ \ / (_) | | | |
|
||||||
@ -92,68 +56,36 @@
|
|||||||
\ /\ / | | (_| | (_| | __/ |_ \__ \
|
\ /\ / | | (_| | (_| | __/ |_ \__ \
|
||||||
\/ \/ |_|\__,_|\__, |\___|\__||___/
|
\/ \/ |_|\__,_|\__, |\___|\__||___/
|
||||||
__/ |
|
__/ |
|
||||||
|_
|
|___/
|
||||||
-->
|
-->
|
||||||
<activity android:name=".widgets.timetable.LessonDialogActivity"
|
<activity android:name=".ui.widgets.WidgetConfigActivity"
|
||||||
android:configChanges="orientation|keyboardHidden"
|
android:configChanges="orientation|keyboardHidden"
|
||||||
android:excludeFromRecents="true"
|
android:excludeFromRecents="true"
|
||||||
android:noHistory="true"
|
android:noHistory="true"
|
||||||
android:theme="@style/AppTheme.NoDisplay" />
|
android:theme="@style/AppTheme.NoDisplay">
|
||||||
<activity
|
<intent-filter>
|
||||||
android:name=".ui.modules.settings.SettingsLicenseActivity"
|
<action android:name="android.appwidget.action.APPWIDGET_CONFIGURE" />
|
||||||
android:configChanges="orientation|keyboardHidden"
|
</intent-filter>
|
||||||
android:theme="@style/AppTheme" />
|
</activity>
|
||||||
<activity
|
<!-- TIMETABLE -->
|
||||||
android:name="com.theartofdev.edmodo.cropper.CropImageActivity"
|
<receiver android:name=".ui.widgets.timetable.WidgetTimetableProvider"
|
||||||
android:configChanges="orientation|keyboardHidden"
|
|
||||||
android:theme="@style/Base.Theme.AppCompat" />
|
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.webpush.WebPushConfigActivity"
|
|
||||||
android:configChanges="orientation|keyboardHidden"
|
|
||||||
android:theme="@style/AppTheme.Dark" />
|
|
||||||
<activity
|
|
||||||
android:name=".ui.modules.home.CounterActivity"
|
|
||||||
android:theme="@style/AppTheme.Black" />
|
|
||||||
<activity android:name=".ui.modules.webpush.QrScannerActivity" />
|
|
||||||
|
|
||||||
<provider
|
|
||||||
android:name="androidx.core.content.FileProvider"
|
|
||||||
android:authorities="${applicationId}.provider"
|
|
||||||
android:exported="false"
|
|
||||||
android:grantUriPermissions="true">
|
|
||||||
<meta-data
|
|
||||||
android:name="android.support.FILE_PROVIDER_PATHS"
|
|
||||||
android:resource="@xml/provider_paths" />
|
|
||||||
</provider>
|
|
||||||
<!--
|
|
||||||
_____ _ _
|
|
||||||
| __ \ (_) | |
|
|
||||||
| |__) | __ _____ ___ __| | ___ _ __ ___
|
|
||||||
| ___/ '__/ _ \ \ / / |/ _` |/ _ \ '__/ __|
|
|
||||||
| | | | | (_) \ V /| | (_| | __/ | \__ \
|
|
||||||
|_| |_| \___/ \_/ |_|\__,_|\___|_| |___/
|
|
||||||
-->
|
|
||||||
<receiver
|
|
||||||
android:name=".WidgetTimetable"
|
|
||||||
android:label="@string/widget_timetable_title">
|
android:label="@string/widget_timetable_title">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
|
|
||||||
<meta-data
|
<meta-data
|
||||||
android:name="android.appwidget.provider"
|
android:name="android.appwidget.provider"
|
||||||
android:resource="@xml/widget_timetable_info" />
|
android:resource="@xml/widget_timetable_info" />
|
||||||
</receiver>
|
</receiver>
|
||||||
<!--
|
<service android:name=".ui.widgets.timetable.WidgetTimetableService"
|
||||||
____ _ _
|
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
||||||
| _ \ | | (_)
|
<activity android:name=".ui.widgets.LessonDialogActivity"
|
||||||
| |_) | ___ ___ | |_ _ __ ___ ___ ___ ___ _____ _ __
|
android:configChanges="orientation|keyboardHidden"
|
||||||
| _ < / _ \ / _ \| __| | '__/ _ \/ __/ _ \ \ \ / / _ \ '__|
|
android:excludeFromRecents="true"
|
||||||
| |_) | (_) | (_) | |_ | | | __/ (_| __/ |\ V / __/ |
|
android:noHistory="true"
|
||||||
|____/ \___/ \___/ \__| |_| \___|\___\___|_| \_/ \_____|
|
android:theme="@style/AppTheme.NoDisplay" />
|
||||||
-->
|
<!-- NOTIFICATIONS -->
|
||||||
<receiver
|
<receiver android:name=".ui.widgets.notifications.WidgetNotificationsProvider"
|
||||||
android:name=".widgets.notifications.WidgetNotifications"
|
|
||||||
android:label="@string/widget_notifications_title">
|
android:label="@string/widget_notifications_title">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||||
@ -163,8 +95,10 @@
|
|||||||
android:name="android.appwidget.provider"
|
android:name="android.appwidget.provider"
|
||||||
android:resource="@xml/widget_notifications_info" />
|
android:resource="@xml/widget_notifications_info" />
|
||||||
</receiver>
|
</receiver>
|
||||||
<receiver
|
<service android:name=".ui.widgets.notifications.WidgetNotificationsService"
|
||||||
android:name=".widgets.luckynumber.WidgetLuckyNumber"
|
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
||||||
|
<!-- LUCKY NUMBER -->
|
||||||
|
<receiver android:name=".widgets.luckynumber.WidgetLuckyNumber"
|
||||||
android:label="@string/widget_lucky_number_title">
|
android:label="@string/widget_lucky_number_title">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||||
@ -174,8 +108,58 @@
|
|||||||
android:name="android.appwidget.provider"
|
android:name="android.appwidget.provider"
|
||||||
android:resource="@xml/widget_lucky_number_info" />
|
android:resource="@xml/widget_lucky_number_info" />
|
||||||
</receiver>
|
</receiver>
|
||||||
<receiver
|
|
||||||
android:name=".receivers.UserPresentReceiver"
|
<!-- _ _ _ _ _
|
||||||
|
/\ | | (_) (_) | (_)
|
||||||
|
/ \ ___| |_ ___ ___| |_ _ ___ ___
|
||||||
|
/ /\ \ / __| __| \ \ / / | __| |/ _ \/ __|
|
||||||
|
/ ____ \ (__| |_| |\ V /| | |_| | __/\__ \
|
||||||
|
/_/ \_\___|\__|_| \_/ |_|\__|_|\___||___/
|
||||||
|
-->
|
||||||
|
<activity android:name=".ui.modules.base.CrashActivity"
|
||||||
|
android:configChanges="orientation|screenSize|keyboardHidden"
|
||||||
|
android:process=":error_activity"
|
||||||
|
android:theme="@style/DeadTheme" />
|
||||||
|
<activity android:name=".ui.modules.base.CrashGtfoActivity"
|
||||||
|
android:configChanges="orientation|screenSize|keyboardHidden"
|
||||||
|
android:theme="@style/DeadTheme" />
|
||||||
|
<activity android:name=".ui.modules.intro.ChangelogIntroActivity"
|
||||||
|
android:configChanges="orientation|keyboardHidden"
|
||||||
|
android:label="@string/app_name"
|
||||||
|
android:theme="@style/Theme.Intro" />
|
||||||
|
<activity android:name=".ui.modules.login.LoginActivity"
|
||||||
|
android:configChanges="orientation|screenSize"
|
||||||
|
android:launchMode="singleTop"
|
||||||
|
android:theme="@style/AppTheme.Light" />
|
||||||
|
<activity android:name=".ui.modules.login.LoginLibrusCaptchaActivity"
|
||||||
|
android:theme="@android:style/Theme.Dialog"
|
||||||
|
android:excludeFromRecents="true"/>
|
||||||
|
<activity android:name=".ui.modules.home.CounterActivity"
|
||||||
|
android:theme="@style/AppTheme.Black" />
|
||||||
|
<activity android:name=".ui.modules.feedback.FeedbackActivity"
|
||||||
|
android:configChanges="orientation|screenSize|keyboardHidden"
|
||||||
|
android:label="@string/app_name"
|
||||||
|
android:theme="@style/AppTheme" />
|
||||||
|
<activity android:name=".ui.modules.settings.SettingsLicenseActivity"
|
||||||
|
|
||||||
|
android:configChanges="orientation|keyboardHidden"
|
||||||
|
android:theme="@style/AppTheme" />
|
||||||
|
<activity android:name=".ui.modules.webpush.WebPushConfigActivity"
|
||||||
|
android:configChanges="orientation|keyboardHidden"
|
||||||
|
android:theme="@style/AppTheme.Dark" />
|
||||||
|
<activity android:name=".ui.modules.webpush.QrScannerActivity" />
|
||||||
|
<activity android:name="com.theartofdev.edmodo.cropper.CropImageActivity"
|
||||||
|
android:configChanges="orientation|keyboardHidden"
|
||||||
|
android:theme="@style/Base.Theme.AppCompat" />
|
||||||
|
|
||||||
|
<!-- _____ _
|
||||||
|
| __ \ (_)
|
||||||
|
| |__) |___ ___ ___ ___ _____ _ __ ___
|
||||||
|
| _ // _ \/ __/ _ \ \ \ / / _ \ '__/ __|
|
||||||
|
| | \ \ __/ (_| __/ |\ V / __/ | \__ \
|
||||||
|
|_| \_\___|\___\___|_| \_/ \___|_| |___/
|
||||||
|
-->
|
||||||
|
<receiver android:name=".receivers.UserPresentReceiver"
|
||||||
android:enabled="true">
|
android:enabled="true">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.intent.action.USER_PRESENT" />
|
<action android:name="android.intent.action.USER_PRESENT" />
|
||||||
@ -188,54 +172,53 @@
|
|||||||
<action android:name="android.intent.action.QUICKBOOT_POWERON" />
|
<action android:name="android.intent.action.QUICKBOOT_POWERON" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</receiver>
|
</receiver>
|
||||||
|
<receiver android:name=".sync.FirebaseBroadcastReceiver"
|
||||||
<receiver
|
|
||||||
android:name=".sync.FirebaseBroadcastReceiver"
|
|
||||||
android:exported="true"
|
android:exported="true"
|
||||||
android:permission="com.google.android.c2dm.permission.SEND">
|
android:permission="com.google.android.c2dm.permission.SEND">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="com.google.android.c2dm.intent.RECEIVE" />
|
<action android:name="com.google.android.c2dm.intent.RECEIVE" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</receiver>
|
</receiver>
|
||||||
|
<receiver android:name=".receivers.SzkolnyReceiver"
|
||||||
<receiver
|
|
||||||
android:name=".receivers.SzkolnyReceiver"
|
|
||||||
android:exported="true">
|
android:exported="true">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="pl.szczodrzynski.edziennik.SZKOLNY_MAIN" />
|
<action android:name="pl.szczodrzynski.edziennik.SZKOLNY_MAIN" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</receiver>
|
</receiver>
|
||||||
|
|
||||||
<service
|
<!-- _____ _
|
||||||
android:name=".sync.MyFirebaseMessagingService"
|
/ ____| (_)
|
||||||
|
| (___ ___ _ ____ ___ ___ ___ ___
|
||||||
|
\___ \ / _ \ '__\ \ / / |/ __/ _ \/ __|
|
||||||
|
____) | __/ | \ V /| | (_| __/\__ \
|
||||||
|
|_____/ \___|_| \_/ |_|\___\___||___/
|
||||||
|
-->
|
||||||
|
<service android:name=".sync.MyFirebaseMessagingService"
|
||||||
android:exported="false">
|
android:exported="false">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="com.google.firebase.INSTANCE_ID_EVENT" />
|
<action android:name="com.google.firebase.INSTANCE_ID_EVENT" />
|
||||||
<action android:name="com.google.firebase.MESSAGING_EVENT" />
|
<action android:name="com.google.firebase.MESSAGING_EVENT" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</service>
|
</service>
|
||||||
<service
|
|
||||||
android:name=".widgets.timetable.WidgetTimetableService"
|
|
||||||
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
|
||||||
<service
|
|
||||||
android:name=".widgets.notifications.WidgetNotificationsService"
|
|
||||||
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
|
||||||
<service android:name=".receivers.BootReceiver$NotificationActionService" />
|
<service android:name=".receivers.BootReceiver$NotificationActionService" />
|
||||||
|
|
||||||
<service android:name=".Notifier$GetDataRetryService" />
|
<service android:name=".Notifier$GetDataRetryService" />
|
||||||
|
<service android:name=".data.api.ApiService" />
|
||||||
|
|
||||||
<service android:name="pl.szczodrzynski.edziennik.data.api.ApiService" />
|
<!--
|
||||||
|
_____ _ _
|
||||||
|
| __ \ (_) | |
|
||||||
|
| |__) | __ _____ ___ __| | ___ _ __ ___
|
||||||
|
| ___/ '__/ _ \ \ / / |/ _` |/ _ \ '__/ __|
|
||||||
|
| | | | | (_) \ V /| | (_| | __/ | \__ \
|
||||||
|
|_| |_| \___/ \_/ |_|\__,_|\___|_| |___/
|
||||||
|
-->
|
||||||
|
<provider android:name="androidx.core.content.FileProvider"
|
||||||
|
android:authorities="${applicationId}.provider"
|
||||||
|
android:exported="false"
|
||||||
|
android:grantUriPermissions="true">
|
||||||
|
<meta-data
|
||||||
|
android:name="android.support.FILE_PROVIDER_PATHS"
|
||||||
|
android:resource="@xml/provider_paths" />
|
||||||
|
</provider>
|
||||||
</application>
|
</application>
|
||||||
<uses-permission android:name="android.permission.REQUEST_INSTALL_PACKAGES" />
|
|
||||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
|
|
||||||
<uses-permission android:name="android.permission.INTERNET" />
|
|
||||||
<uses-permission android:name="android.permission.WAKE_LOCK" />
|
|
||||||
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
|
|
||||||
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
|
|
||||||
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
|
|
||||||
<uses-permission android:name="android.permission.VIBRATE" />
|
|
||||||
<uses-permission android:name="android.permission.CAMERA" />
|
|
||||||
|
|
||||||
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
|
|
||||||
|
|
||||||
</manifest>
|
</manifest>
|
||||||
|
@ -6,6 +6,7 @@ import android.content.Context
|
|||||||
import android.content.pm.PackageManager
|
import android.content.pm.PackageManager
|
||||||
import android.content.res.ColorStateList
|
import android.content.res.ColorStateList
|
||||||
import android.content.res.Resources
|
import android.content.res.Resources
|
||||||
|
import android.database.Cursor
|
||||||
import android.graphics.PorterDuff
|
import android.graphics.PorterDuff
|
||||||
import android.graphics.PorterDuffColorFilter
|
import android.graphics.PorterDuffColorFilter
|
||||||
import android.graphics.Typeface
|
import android.graphics.Typeface
|
||||||
@ -26,6 +27,9 @@ import android.widget.CompoundButton
|
|||||||
import android.widget.TextView
|
import android.widget.TextView
|
||||||
import androidx.annotation.*
|
import androidx.annotation.*
|
||||||
import androidx.core.app.ActivityCompat
|
import androidx.core.app.ActivityCompat
|
||||||
|
import androidx.core.database.getIntOrNull
|
||||||
|
import androidx.core.database.getLongOrNull
|
||||||
|
import androidx.core.database.getStringOrNull
|
||||||
import androidx.core.util.forEach
|
import androidx.core.util.forEach
|
||||||
import androidx.lifecycle.LifecycleOwner
|
import androidx.lifecycle.LifecycleOwner
|
||||||
import androidx.lifecycle.LiveData
|
import androidx.lifecycle.LiveData
|
||||||
@ -938,3 +942,7 @@ fun Context.getNotificationTitle(type: Int): String {
|
|||||||
else -> R.string.notification_type_general
|
else -> R.string.notification_type_general
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun Cursor?.getString(columnName: String) = this?.getStringOrNull(getColumnIndex(columnName))
|
||||||
|
fun Cursor?.getInt(columnName: String) = this?.getIntOrNull(getColumnIndex(columnName))
|
||||||
|
fun Cursor?.getLong(columnName: String) = this?.getLongOrNull(getColumnIndex(columnName))
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
|
|
||||||
package pl.szczodrzynski.edziennik.config
|
package pl.szczodrzynski.edziennik.config
|
||||||
|
|
||||||
|
import com.google.gson.JsonObject
|
||||||
import kotlinx.coroutines.CoroutineScope
|
import kotlinx.coroutines.CoroutineScope
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.Job
|
import kotlinx.coroutines.Job
|
||||||
@ -74,6 +75,11 @@ class Config(val db: AppDb) : CoroutineScope, AbstractConfig {
|
|||||||
get() { mRunSync = mRunSync ?: values.get("runSync", false); return mRunSync ?: false }
|
get() { mRunSync = mRunSync ?: values.get("runSync", false); return mRunSync ?: false }
|
||||||
set(value) { set("runSync", value); mRunSync = value }
|
set(value) { set("runSync", value); mRunSync = value }
|
||||||
|
|
||||||
|
private var mWidgetConfigs: JsonObject? = null
|
||||||
|
var widgetConfigs: JsonObject
|
||||||
|
get() { mWidgetConfigs = mWidgetConfigs ?: values.get("widgetConfigs", JsonObject()); return mWidgetConfigs ?: JsonObject() }
|
||||||
|
set(value) { set("widgetConfigs", value); mWidgetConfigs = value }
|
||||||
|
|
||||||
private var rawEntries: List<ConfigEntry> = db.configDao().getAllNow()
|
private var rawEntries: List<ConfigEntry> = db.configDao().getAllNow()
|
||||||
private val profileConfigs: HashMap<Int, ProfileConfig> = hashMapOf()
|
private val profileConfigs: HashMap<Int, ProfileConfig> = hashMapOf()
|
||||||
init {
|
init {
|
||||||
|
@ -10,38 +10,14 @@ import pl.szczodrzynski.edziennik.App
|
|||||||
import pl.szczodrzynski.edziennik.data.api.*
|
import pl.szczodrzynski.edziennik.data.api.*
|
||||||
import pl.szczodrzynski.edziennik.data.api.interfaces.EndpointCallback
|
import pl.szczodrzynski.edziennik.data.api.interfaces.EndpointCallback
|
||||||
import pl.szczodrzynski.edziennik.data.db.AppDb
|
import pl.szczodrzynski.edziennik.data.db.AppDb
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Announcement
|
import pl.szczodrzynski.edziennik.data.db.entity.*
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.EndpointTimer
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Attendance
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.AttendanceType
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Classroom
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Event
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.EventType
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Grade
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.GradeCategory
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.LessonRange
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.LoginStore
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.LuckyNumber
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Message
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.MessageRecipient
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Metadata
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Notice
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.NoticeType
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Notification
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Profile
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Subject
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Teacher
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.TeacherAbsence
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.TeacherAbsenceType
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Team
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Lesson
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.LibrusLesson
|
|
||||||
import pl.szczodrzynski.edziennik.singleOrNull
|
import pl.szczodrzynski.edziennik.singleOrNull
|
||||||
import pl.szczodrzynski.edziennik.toSparseArray
|
import pl.szczodrzynski.edziennik.toSparseArray
|
||||||
import pl.szczodrzynski.edziennik.utils.Utils.d
|
import pl.szczodrzynski.edziennik.utils.Utils.d
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||||
import pl.szczodrzynski.edziennik.values
|
import pl.szczodrzynski.edziennik.values
|
||||||
import java.io.InterruptedIOException
|
import java.io.InterruptedIOException
|
||||||
|
import java.net.ConnectException
|
||||||
import java.net.SocketTimeoutException
|
import java.net.SocketTimeoutException
|
||||||
import java.net.UnknownHostException
|
import java.net.UnknownHostException
|
||||||
import javax.net.ssl.SSLException
|
import javax.net.ssl.SSLException
|
||||||
@ -390,7 +366,7 @@ abstract class Data(val app: App, val profile: Profile?, val loginStore: LoginSt
|
|||||||
apiError.errorCode = when (apiError.throwable) {
|
apiError.errorCode = when (apiError.throwable) {
|
||||||
is UnknownHostException -> ERROR_REQUEST_FAILURE_HOSTNAME_NOT_FOUND
|
is UnknownHostException -> ERROR_REQUEST_FAILURE_HOSTNAME_NOT_FOUND
|
||||||
is SSLException -> ERROR_REQUEST_FAILURE_SSL_ERROR
|
is SSLException -> ERROR_REQUEST_FAILURE_SSL_ERROR
|
||||||
is InterruptedIOException -> ERROR_REQUEST_FAILURE_NO_INTERNET
|
is InterruptedIOException, is ConnectException -> ERROR_REQUEST_FAILURE_NO_INTERNET
|
||||||
is SocketTimeoutException -> ERROR_REQUEST_FAILURE_TIMEOUT
|
is SocketTimeoutException -> ERROR_REQUEST_FAILURE_TIMEOUT
|
||||||
else ->
|
else ->
|
||||||
if (apiError.errorCode == ERROR_REQUEST_FAILURE)
|
if (apiError.errorCode == ERROR_REQUEST_FAILURE)
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
|
|
||||||
package pl.szczodrzynski.edziennik.data.db.dao
|
package pl.szczodrzynski.edziennik.data.db.dao
|
||||||
|
|
||||||
|
import android.database.Cursor
|
||||||
import androidx.lifecycle.LiveData
|
import androidx.lifecycle.LiveData
|
||||||
import androidx.room.Dao
|
import androidx.room.Dao
|
||||||
import androidx.room.Insert
|
import androidx.room.Insert
|
||||||
@ -36,4 +37,7 @@ interface NotificationDao {
|
|||||||
|
|
||||||
@Query("UPDATE notifications SET posted = 1 WHERE posted = 0")
|
@Query("UPDATE notifications SET posted = 1 WHERE posted = 0")
|
||||||
fun setAllPosted()
|
fun setAllPosted()
|
||||||
|
|
||||||
|
@Query("SELECT * FROM notifications ORDER BY addedDate DESC")
|
||||||
|
fun getAllCursor(): Cursor
|
||||||
}
|
}
|
||||||
|
@ -13,6 +13,10 @@ import pl.szczodrzynski.edziennik.data.api.events.requests.TaskCancelRequest
|
|||||||
import pl.szczodrzynski.edziennik.data.api.task.EdziennikTask
|
import pl.szczodrzynski.edziennik.data.api.task.EdziennikTask
|
||||||
|
|
||||||
class SzkolnyReceiver : BroadcastReceiver() {
|
class SzkolnyReceiver : BroadcastReceiver() {
|
||||||
|
companion object {
|
||||||
|
const val ACTION = "pl.szczodrzynski.edziennik.SZKOLNY_MAIN"
|
||||||
|
}
|
||||||
|
|
||||||
override fun onReceive(context: Context?, intent: Intent?) {
|
override fun onReceive(context: Context?, intent: Intent?) {
|
||||||
context ?: return
|
context ?: return
|
||||||
when (intent?.extras?.getString("task", null)) {
|
when (intent?.extras?.getString("task", null)) {
|
||||||
|
@ -6,7 +6,7 @@ import android.content.ComponentName;
|
|||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
|
|
||||||
import pl.szczodrzynski.edziennik.WidgetTimetable;
|
import pl.szczodrzynski.edziennik.ui.widgets.timetable.WidgetTimetableProvider;
|
||||||
|
|
||||||
public class UserPresentReceiver extends BroadcastReceiver {
|
public class UserPresentReceiver extends BroadcastReceiver {
|
||||||
@Override
|
@Override
|
||||||
@ -14,12 +14,12 @@ public class UserPresentReceiver extends BroadcastReceiver {
|
|||||||
if (intent.getAction() != null) {
|
if (intent.getAction() != null) {
|
||||||
if (intent.getAction().equals(Intent.ACTION_USER_PRESENT)) {
|
if (intent.getAction().equals(Intent.ACTION_USER_PRESENT)) {
|
||||||
//Toast.makeText(context, "User is present", Toast.LENGTH_SHORT).show();
|
//Toast.makeText(context, "User is present", Toast.LENGTH_SHORT).show();
|
||||||
Intent widgetIntent = new Intent(context, WidgetTimetable.class);
|
Intent widgetIntent = new Intent(context, WidgetTimetableProvider.class);
|
||||||
widgetIntent.setAction(AppWidgetManager.ACTION_APPWIDGET_UPDATE);
|
widgetIntent.setAction(AppWidgetManager.ACTION_APPWIDGET_UPDATE);
|
||||||
// Use an array and EXTRA_APPWIDGET_IDS instead of AppWidgetManager.EXTRA_APPWIDGET_ID,
|
// Use an array and EXTRA_APPWIDGET_IDS instead of AppWidgetManager.EXTRA_APPWIDGET_ID,
|
||||||
// since it seems the onUpdate() is only fired on that:
|
// since it seems the onUpdate() is only fired on that:
|
||||||
int[] ids = AppWidgetManager.getInstance(context)
|
int[] ids = AppWidgetManager.getInstance(context)
|
||||||
.getAppWidgetIds(new ComponentName(context, WidgetTimetable.class));
|
.getAppWidgetIds(new ComponentName(context, WidgetTimetableProvider.class));
|
||||||
widgetIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, ids);
|
widgetIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, ids);
|
||||||
context.sendBroadcast(widgetIntent);
|
context.sendBroadcast(widgetIntent);
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
* Copyright (c) Kuba Szczodrzyński 2019-11-14.
|
* Copyright (c) Kuba Szczodrzyński 2019-11-14.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package pl.szczodrzynski.edziennik.widgets.timetable
|
package pl.szczodrzynski.edziennik.ui.widgets
|
||||||
|
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
import android.content.Intent.FLAG_ACTIVITY_REORDER_TO_FRONT
|
import android.content.Intent.FLAG_ACTIVITY_REORDER_TO_FRONT
|
@ -1,4 +1,8 @@
|
|||||||
package pl.szczodrzynski.edziennik.widgets;
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets;
|
||||||
|
|
||||||
public class WidgetConfig {
|
public class WidgetConfig {
|
||||||
public int profileId = -1;
|
public int profileId = -1;
|
@ -1,4 +1,8 @@
|
|||||||
package pl.szczodrzynski.edziennik.widgets;
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets;
|
||||||
|
|
||||||
import android.app.Activity;
|
import android.app.Activity;
|
||||||
import android.app.WallpaperManager;
|
import android.app.WallpaperManager;
|
||||||
@ -15,16 +19,17 @@ import android.widget.SeekBar;
|
|||||||
import com.afollestad.materialdialogs.MaterialDialog;
|
import com.afollestad.materialdialogs.MaterialDialog;
|
||||||
import com.afollestad.materialdialogs.simplelist.MaterialSimpleListAdapter;
|
import com.afollestad.materialdialogs.simplelist.MaterialSimpleListAdapter;
|
||||||
import com.afollestad.materialdialogs.simplelist.MaterialSimpleListItem;
|
import com.afollestad.materialdialogs.simplelist.MaterialSimpleListItem;
|
||||||
|
import com.google.gson.JsonObject;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import pl.szczodrzynski.edziennik.App;
|
import pl.szczodrzynski.edziennik.App;
|
||||||
import pl.szczodrzynski.edziennik.R;
|
import pl.szczodrzynski.edziennik.R;
|
||||||
import pl.szczodrzynski.edziennik.WidgetTimetable;
|
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Profile;
|
import pl.szczodrzynski.edziennik.data.db.entity.Profile;
|
||||||
import pl.szczodrzynski.edziennik.databinding.DialogWidgetConfigBinding;
|
import pl.szczodrzynski.edziennik.databinding.DialogWidgetConfigBinding;
|
||||||
|
import pl.szczodrzynski.edziennik.ui.widgets.notifications.WidgetNotificationsProvider;
|
||||||
|
import pl.szczodrzynski.edziennik.ui.widgets.timetable.WidgetTimetableProvider;
|
||||||
import pl.szczodrzynski.edziennik.widgets.luckynumber.WidgetLuckyNumber;
|
import pl.szczodrzynski.edziennik.widgets.luckynumber.WidgetLuckyNumber;
|
||||||
import pl.szczodrzynski.edziennik.widgets.notifications.WidgetNotifications;
|
|
||||||
|
|
||||||
import static pl.szczodrzynski.edziennik.ExtensionsKt.filterOutArchived;
|
import static pl.szczodrzynski.edziennik.ExtensionsKt.filterOutArchived;
|
||||||
|
|
||||||
@ -130,17 +135,19 @@ public class WidgetConfigActivity extends Activity {
|
|||||||
.positiveText(R.string.ok)
|
.positiveText(R.string.ok)
|
||||||
.negativeText(R.string.cancel)
|
.negativeText(R.string.cancel)
|
||||||
.onPositive(((dialog1, which) -> {
|
.onPositive(((dialog1, which) -> {
|
||||||
app.appConfig.widgetTimetableConfigs.put(mAppWidgetId, new WidgetConfig(profileId, bigStyle, darkTheme, opacity));
|
WidgetConfig config = new WidgetConfig(profileId, bigStyle, darkTheme, opacity);
|
||||||
app.saveConfig("widgetTimetableConfigs");
|
JsonObject configs = app.config.getWidgetConfigs();
|
||||||
|
configs.add(Integer.toString(mAppWidgetId), app.gson.toJsonTree(config));
|
||||||
|
app.config.setWidgetConfigs(configs);
|
||||||
|
|
||||||
Intent refreshIntent;
|
Intent refreshIntent;
|
||||||
switch (widgetType) {
|
switch (widgetType) {
|
||||||
default:
|
default:
|
||||||
case WIDGET_TIMETABLE:
|
case WIDGET_TIMETABLE:
|
||||||
refreshIntent = new Intent(app.getContext(), WidgetTimetable.class);
|
refreshIntent = new Intent(app.getContext(), WidgetTimetableProvider.class);
|
||||||
break;
|
break;
|
||||||
case WIDGET_NOTIFICATIONS:
|
case WIDGET_NOTIFICATIONS:
|
||||||
refreshIntent = new Intent(app.getContext(), WidgetNotifications.class);
|
refreshIntent = new Intent(app.getContext(), WidgetNotificationsProvider.class);
|
||||||
break;
|
break;
|
||||||
case WIDGET_LUCKY_NUMBER:
|
case WIDGET_LUCKY_NUMBER:
|
||||||
refreshIntent = new Intent(app.getContext(), WidgetLuckyNumber.class);
|
refreshIntent = new Intent(app.getContext(), WidgetLuckyNumber.class);
|
@ -0,0 +1,77 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets.notifications
|
||||||
|
|
||||||
|
import android.content.Intent
|
||||||
|
import android.database.Cursor
|
||||||
|
import android.os.Binder
|
||||||
|
import android.widget.AdapterView
|
||||||
|
import android.widget.RemoteViews
|
||||||
|
import android.widget.RemoteViewsService
|
||||||
|
import com.google.gson.JsonParser
|
||||||
|
import pl.szczodrzynski.edziennik.*
|
||||||
|
import pl.szczodrzynski.edziennik.data.db.entity.Notification
|
||||||
|
import pl.szczodrzynski.edziennik.ui.widgets.WidgetConfig
|
||||||
|
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||||
|
|
||||||
|
class WidgetNotificationsFactory(val app: App, val config: WidgetConfig) : RemoteViewsService.RemoteViewsFactory {
|
||||||
|
companion object {
|
||||||
|
private const val TAG = "WidgetNotificationsFactory"
|
||||||
|
}
|
||||||
|
private var cursor: Cursor? = null
|
||||||
|
|
||||||
|
override fun onDataSetChanged() {
|
||||||
|
cursor?.close()
|
||||||
|
Binder.clearCallingIdentity().let {
|
||||||
|
cursor = app.db.notificationDao().getAllCursor()
|
||||||
|
Binder.restoreCallingIdentity(it)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun getViewAt(position: Int): RemoteViews? {
|
||||||
|
if (position == AdapterView.INVALID_POSITION || cursor?.moveToPosition(position) != true)
|
||||||
|
return null
|
||||||
|
|
||||||
|
val views: RemoteViews = if (config.bigStyle) {
|
||||||
|
RemoteViews(app.packageName, if (config.darkTheme) R.layout.row_widget_notifications_dark_big_item else R.layout.row_widget_notifications_big_item)
|
||||||
|
} else {
|
||||||
|
RemoteViews(app.packageName, if (config.darkTheme) R.layout.row_widget_notifications_dark_item else R.layout.row_widget_notifications_item)
|
||||||
|
}
|
||||||
|
|
||||||
|
val notification = cursor?.run {
|
||||||
|
Notification(
|
||||||
|
getInt("id") ?: 0,
|
||||||
|
getString("title") ?: "",
|
||||||
|
getString("text") ?: "",
|
||||||
|
getInt("type") ?: 0,
|
||||||
|
getInt("profileId"),
|
||||||
|
getString("profileName"),
|
||||||
|
getInt("posted") == 1,
|
||||||
|
getInt("viewId"),
|
||||||
|
getString("extras")?.let { JsonParser().parse(it).asJsonObject },
|
||||||
|
getLong("addedDate") ?: System.currentTimeMillis()
|
||||||
|
)
|
||||||
|
} ?: return views
|
||||||
|
|
||||||
|
views.apply {
|
||||||
|
setTextViewText(R.id.widgetNotificationsTitle,
|
||||||
|
app.getString(R.string.widget_notifications_title_format, notification.title, app.getNotificationTitle(notification.type)))
|
||||||
|
setTextViewText(R.id.widgetNotificationsText, notification.text)
|
||||||
|
setTextViewText(R.id.widgetNotificationsDate, Date.fromMillis(notification.addedDate).formattedString)
|
||||||
|
setOnClickFillInIntent(R.id.widgetNotificationsRoot, Intent().also { notification.fillIntent(it) })
|
||||||
|
}
|
||||||
|
|
||||||
|
return views
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun getItemId(position: Int): Long = if (cursor?.moveToPosition(position) == true)
|
||||||
|
cursor?.getLong("id") ?: position.toLong() else position.toLong()
|
||||||
|
override fun getCount() = cursor?.count ?: 0
|
||||||
|
override fun onCreate() {}
|
||||||
|
override fun getLoadingView() = null
|
||||||
|
override fun hasStableIds() = true
|
||||||
|
override fun getViewTypeCount() = 1
|
||||||
|
override fun onDestroy() = cursor?.close() ?: Unit
|
||||||
|
}
|
@ -0,0 +1,91 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets.notifications
|
||||||
|
|
||||||
|
import android.app.PendingIntent
|
||||||
|
import android.appwidget.AppWidgetManager
|
||||||
|
import android.appwidget.AppWidgetProvider
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.Intent
|
||||||
|
import android.graphics.Color
|
||||||
|
import android.net.Uri
|
||||||
|
import android.view.View
|
||||||
|
import android.widget.RemoteViews
|
||||||
|
import com.mikepenz.iconics.IconicsDrawable
|
||||||
|
import com.mikepenz.iconics.typeface.library.community.material.CommunityMaterial
|
||||||
|
import com.mikepenz.iconics.utils.colorInt
|
||||||
|
import com.mikepenz.iconics.utils.sizeDp
|
||||||
|
import pl.szczodrzynski.edziennik.App
|
||||||
|
import pl.szczodrzynski.edziennik.MainActivity
|
||||||
|
import pl.szczodrzynski.edziennik.R
|
||||||
|
import pl.szczodrzynski.edziennik.getJsonObject
|
||||||
|
import pl.szczodrzynski.edziennik.receivers.SzkolnyReceiver
|
||||||
|
import pl.szczodrzynski.edziennik.ui.widgets.WidgetConfig
|
||||||
|
|
||||||
|
class WidgetNotificationsProvider : AppWidgetProvider() {
|
||||||
|
companion object {
|
||||||
|
private const val TAG = "WidgetNotificationsProvider"
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onUpdate(context: Context, appWidgetManager: AppWidgetManager, appWidgetIds: IntArray) {
|
||||||
|
val app = context.applicationContext as App
|
||||||
|
val widgetConfigs = app.config.widgetConfigs
|
||||||
|
for (appWidgetId in appWidgetIds) {
|
||||||
|
val config = widgetConfigs.getJsonObject(appWidgetId.toString())?.let { app.gson.fromJson(it, WidgetConfig::class.java) } ?: continue
|
||||||
|
|
||||||
|
val iconSize = if (config.bigStyle) 24 else 16
|
||||||
|
|
||||||
|
val views: RemoteViews = if (config.bigStyle) {
|
||||||
|
RemoteViews(app.packageName, if (config.darkTheme) R.layout.widget_notifications_dark_big else R.layout.widget_notifications_big)
|
||||||
|
} else {
|
||||||
|
RemoteViews(app.packageName, if (config.darkTheme) R.layout.widget_notifications_dark else R.layout.widget_notifications)
|
||||||
|
}
|
||||||
|
|
||||||
|
val syncIntent = Intent(SzkolnyReceiver.ACTION)
|
||||||
|
syncIntent.putExtra("task", "SyncRequest")
|
||||||
|
val syncPendingIntent = PendingIntent.getBroadcast(context, 0, syncIntent, 0)
|
||||||
|
views.setOnClickPendingIntent(R.id.widgetNotificationsSync, syncPendingIntent)
|
||||||
|
|
||||||
|
views.setImageViewBitmap(
|
||||||
|
R.id.widgetNotificationsSync,
|
||||||
|
IconicsDrawable(context, CommunityMaterial.Icon.cmd_download_outline)
|
||||||
|
.colorInt(Color.WHITE)
|
||||||
|
.sizeDp(iconSize)
|
||||||
|
.toBitmap()
|
||||||
|
)
|
||||||
|
|
||||||
|
views.setViewVisibility(R.id.widgetNotificationsLoading, View.GONE)
|
||||||
|
|
||||||
|
val listIntent = Intent(context, WidgetNotificationsService::class.java)
|
||||||
|
listIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetId)
|
||||||
|
listIntent.putExtra("config", app.gson.toJson(config))
|
||||||
|
listIntent.data = Uri.parse(listIntent.toUri(Intent.URI_INTENT_SCHEME))
|
||||||
|
views.setRemoteAdapter(R.id.widgetNotificationsListView, listIntent)
|
||||||
|
|
||||||
|
val itemIntent = Intent(context, MainActivity::class.java)
|
||||||
|
itemIntent.action = Intent.ACTION_MAIN
|
||||||
|
val itemPendingIntent = PendingIntent.getActivity(context, 0, itemIntent, 0)
|
||||||
|
views.setPendingIntentTemplate(R.id.widgetNotificationsListView, itemPendingIntent)
|
||||||
|
|
||||||
|
val headerIntent = Intent(context, MainActivity::class.java)
|
||||||
|
headerIntent.action = Intent.ACTION_MAIN
|
||||||
|
headerIntent.putExtra("fragmentId", MainActivity.DRAWER_ITEM_NOTIFICATIONS)
|
||||||
|
val headerPendingIntent = PendingIntent.getActivity(context, 0, headerIntent, 0)
|
||||||
|
views.setOnClickPendingIntent(R.id.widgetNotificationsHeader, headerPendingIntent)
|
||||||
|
|
||||||
|
appWidgetManager.updateAppWidget(appWidgetId, views)
|
||||||
|
appWidgetManager.notifyAppWidgetViewDataChanged(appWidgetId, R.id.widgetNotificationsListView)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onDeleted(context: Context, appWidgetIds: IntArray) {
|
||||||
|
val app = context.applicationContext as App
|
||||||
|
val widgetConfigs = app.config.widgetConfigs
|
||||||
|
appWidgetIds.forEach {
|
||||||
|
widgetConfigs.remove(it.toString())
|
||||||
|
}
|
||||||
|
app.config.widgetConfigs = widgetConfigs
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets.notifications
|
||||||
|
|
||||||
|
import android.content.Intent
|
||||||
|
import android.widget.RemoteViewsService
|
||||||
|
import pl.szczodrzynski.edziennik.App
|
||||||
|
import pl.szczodrzynski.edziennik.ui.widgets.WidgetConfig
|
||||||
|
|
||||||
|
class WidgetNotificationsService : RemoteViewsService() {
|
||||||
|
override fun onGetViewFactory(intent: Intent): RemoteViewsFactory {
|
||||||
|
val app = application as App
|
||||||
|
val config = intent.getStringExtra("config")?.let { app.gson.fromJson(it, WidgetConfig::class.java) }
|
||||||
|
return WidgetNotificationsFactory(app, config ?: WidgetConfig(-1))
|
||||||
|
}
|
||||||
|
}
|
@ -1,4 +1,8 @@
|
|||||||
package pl.szczodrzynski.edziennik.widgets.timetable;
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets.timetable;
|
||||||
|
|
||||||
import android.appwidget.AppWidgetManager;
|
import android.appwidget.AppWidgetManager;
|
||||||
import android.content.ComponentName;
|
import android.content.ComponentName;
|
||||||
@ -28,14 +32,13 @@ import com.mikepenz.iconics.typeface.library.community.material.CommunityMateria
|
|||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import pl.szczodrzynski.edziennik.R;
|
import pl.szczodrzynski.edziennik.R;
|
||||||
import pl.szczodrzynski.edziennik.WidgetTimetable;
|
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Date;
|
import pl.szczodrzynski.edziennik.utils.models.Date;
|
||||||
import pl.szczodrzynski.edziennik.utils.models.ItemWidgetTimetableModel;
|
import pl.szczodrzynski.edziennik.utils.models.ItemWidgetTimetableModel;
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Time;
|
import pl.szczodrzynski.edziennik.utils.models.Time;
|
||||||
|
|
||||||
import static android.util.TypedValue.COMPLEX_UNIT_SP;
|
import static android.util.TypedValue.COMPLEX_UNIT_SP;
|
||||||
|
|
||||||
public class WidgetTimetableListProvider implements RemoteViewsService.RemoteViewsFactory {
|
public class WidgetTimetableFactory implements RemoteViewsService.RemoteViewsFactory {
|
||||||
|
|
||||||
private static final String TAG = "WidgetTimetableProvider";
|
private static final String TAG = "WidgetTimetableProvider";
|
||||||
private Context context;
|
private Context context;
|
||||||
@ -44,7 +47,7 @@ public class WidgetTimetableListProvider implements RemoteViewsService.RemoteVie
|
|||||||
private static boolean triedToReload = false;
|
private static boolean triedToReload = false;
|
||||||
|
|
||||||
//For obtaining the activity's context and intent
|
//For obtaining the activity's context and intent
|
||||||
public WidgetTimetableListProvider(Context context, Intent intent) {
|
public WidgetTimetableFactory(Context context, Intent intent) {
|
||||||
this.context = context;
|
this.context = context;
|
||||||
this.appWidgetId = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, 0);
|
this.appWidgetId = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, 0);
|
||||||
// executed only ONCE
|
// executed only ONCE
|
||||||
@ -65,7 +68,7 @@ public class WidgetTimetableListProvider implements RemoteViewsService.RemoteVie
|
|||||||
public void onDataSetChanged() {
|
public void onDataSetChanged() {
|
||||||
// executed EVERY TIME
|
// executed EVERY TIME
|
||||||
Log.d(TAG, "onDataSetChanged for appWidgetId: "+appWidgetId);
|
Log.d(TAG, "onDataSetChanged for appWidgetId: "+appWidgetId);
|
||||||
lessons = WidgetTimetable.Companion.getTimetables() == null ? null : WidgetTimetable.Companion.getTimetables().get(appWidgetId);
|
lessons = WidgetTimetableProvider.Companion.getTimetables() == null ? null : WidgetTimetableProvider.Companion.getTimetables().get(appWidgetId);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -306,11 +309,11 @@ public class WidgetTimetableListProvider implements RemoteViewsService.RemoteVie
|
|||||||
// try to reload the widget
|
// try to reload the widget
|
||||||
// only once
|
// only once
|
||||||
triedToReload = true;
|
triedToReload = true;
|
||||||
Intent intent = new Intent(context, WidgetTimetable.class);
|
Intent intent = new Intent(context, WidgetTimetableProvider.class);
|
||||||
intent.setAction(AppWidgetManager.ACTION_APPWIDGET_UPDATE);
|
intent.setAction(AppWidgetManager.ACTION_APPWIDGET_UPDATE);
|
||||||
// Use an array and EXTRA_APPWIDGET_IDS instead of AppWidgetManager.EXTRA_APPWIDGET_ID,
|
// Use an array and EXTRA_APPWIDGET_IDS instead of AppWidgetManager.EXTRA_APPWIDGET_ID,
|
||||||
// since it seems the onUpdate() is only fired on that:
|
// since it seems the onUpdate() is only fired on that:
|
||||||
int[] ids = AppWidgetManager.getInstance(context).getAppWidgetIds(new ComponentName(context, WidgetTimetable.class));
|
int[] ids = AppWidgetManager.getInstance(context).getAppWidgetIds(new ComponentName(context, WidgetTimetableProvider.class));
|
||||||
intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, ids);
|
intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, ids);
|
||||||
context.sendBroadcast(intent);
|
context.sendBroadcast(intent);
|
||||||
}
|
}
|
@ -1,4 +1,8 @@
|
|||||||
package pl.szczodrzynski.edziennik
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets.timetable
|
||||||
|
|
||||||
import android.app.PendingIntent
|
import android.app.PendingIntent
|
||||||
import android.appwidget.AppWidgetManager
|
import android.appwidget.AppWidgetManager
|
||||||
@ -21,20 +25,50 @@ import com.mikepenz.iconics.IconicsDrawable
|
|||||||
import com.mikepenz.iconics.typeface.library.community.material.CommunityMaterial
|
import com.mikepenz.iconics.typeface.library.community.material.CommunityMaterial
|
||||||
import com.mikepenz.iconics.utils.colorInt
|
import com.mikepenz.iconics.utils.colorInt
|
||||||
import com.mikepenz.iconics.utils.sizeDp
|
import com.mikepenz.iconics.utils.sizeDp
|
||||||
|
import pl.szczodrzynski.edziennik.*
|
||||||
import pl.szczodrzynski.edziennik.data.api.task.EdziennikTask
|
import pl.szczodrzynski.edziennik.data.api.task.EdziennikTask
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Event.TYPE_HOMEWORK
|
import pl.szczodrzynski.edziennik.data.db.entity.Event.TYPE_HOMEWORK
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Lesson
|
import pl.szczodrzynski.edziennik.data.db.entity.Lesson
|
||||||
|
import pl.szczodrzynski.edziennik.ui.widgets.LessonDialogActivity
|
||||||
|
import pl.szczodrzynski.edziennik.ui.widgets.WidgetConfig
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||||
import pl.szczodrzynski.edziennik.utils.models.ItemWidgetTimetableModel
|
import pl.szczodrzynski.edziennik.utils.models.ItemWidgetTimetableModel
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Time
|
import pl.szczodrzynski.edziennik.utils.models.Time
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Week
|
import pl.szczodrzynski.edziennik.utils.models.Week
|
||||||
import pl.szczodrzynski.edziennik.widgets.WidgetConfig
|
|
||||||
import pl.szczodrzynski.edziennik.widgets.timetable.LessonDialogActivity
|
|
||||||
import pl.szczodrzynski.edziennik.widgets.timetable.WidgetTimetableService
|
|
||||||
import java.lang.reflect.InvocationTargetException
|
import java.lang.reflect.InvocationTargetException
|
||||||
|
|
||||||
|
|
||||||
class WidgetTimetable : AppWidgetProvider() {
|
class WidgetTimetableProvider : AppWidgetProvider() {
|
||||||
|
companion object {
|
||||||
|
const val ACTION_SYNC_DATA = "ACTION_SYNC_DATA"
|
||||||
|
private const val TAG = "WidgetTimetable"
|
||||||
|
|
||||||
|
var timetables: SparseArray<List<ItemWidgetTimetableModel>>? = null
|
||||||
|
|
||||||
|
fun getPendingSelfIntent(context: Context, action: String): PendingIntent {
|
||||||
|
val intent = Intent(context, WidgetTimetableProvider::class.java)
|
||||||
|
intent.action = action
|
||||||
|
return getPendingSelfIntent(context, intent)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getPendingSelfIntent(context: Context, intent: Intent): PendingIntent {
|
||||||
|
return PendingIntent.getBroadcast(context, 0, intent, 0)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun drawableToBitmap(drawable: Drawable): Bitmap {
|
||||||
|
|
||||||
|
if (drawable is BitmapDrawable) {
|
||||||
|
return drawable.bitmap
|
||||||
|
}
|
||||||
|
|
||||||
|
val bitmap = Bitmap.createBitmap(drawable.intrinsicWidth, drawable.intrinsicHeight, Bitmap.Config.ARGB_8888)
|
||||||
|
val canvas = Canvas(bitmap)
|
||||||
|
drawable.setBounds(0, 0, canvas.width, canvas.height)
|
||||||
|
drawable.draw(canvas)
|
||||||
|
|
||||||
|
return bitmap
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
override fun onReceive(context: Context, intent: Intent) {
|
override fun onReceive(context: Context, intent: Intent) {
|
||||||
if (ACTION_SYNC_DATA == intent.action) {
|
if (ACTION_SYNC_DATA == intent.action) {
|
||||||
@ -46,12 +80,12 @@ class WidgetTimetable : AppWidgetProvider() {
|
|||||||
private val ignoreCancelled = true
|
private val ignoreCancelled = true
|
||||||
|
|
||||||
override fun onUpdate(context: Context, appWidgetManager: AppWidgetManager, appWidgetIds: IntArray) {
|
override fun onUpdate(context: Context, appWidgetManager: AppWidgetManager, appWidgetIds: IntArray) {
|
||||||
val thisWidget = ComponentName(context, WidgetTimetable::class.java)
|
val thisWidget = ComponentName(context, WidgetTimetableProvider::class.java)
|
||||||
|
|
||||||
timetables = SparseArray()
|
timetables = SparseArray()
|
||||||
//timetables.clear();
|
|
||||||
|
|
||||||
val app = context.applicationContext as App
|
val app = context.applicationContext as App
|
||||||
|
val widgetConfigs = app.config.widgetConfigs
|
||||||
|
|
||||||
var bellSyncDiffMillis: Long = 0
|
var bellSyncDiffMillis: Long = 0
|
||||||
app.config.timetable.bellSyncDiff?.let {
|
app.config.timetable.bellSyncDiff?.let {
|
||||||
@ -63,37 +97,32 @@ class WidgetTimetable : AppWidgetProvider() {
|
|||||||
val allWidgetIds = appWidgetManager.getAppWidgetIds(thisWidget)
|
val allWidgetIds = appWidgetManager.getAppWidgetIds(thisWidget)
|
||||||
|
|
||||||
allWidgetIds?.forEach { appWidgetId ->
|
allWidgetIds?.forEach { appWidgetId ->
|
||||||
var widgetConfig = app.appConfig.widgetTimetableConfigs[appWidgetId]
|
val config = widgetConfigs.getJsonObject(appWidgetId.toString())?.let { app.gson.fromJson(it, WidgetConfig::class.java) } ?: return@forEach
|
||||||
if (widgetConfig == null) {
|
|
||||||
widgetConfig = WidgetConfig(app.profileFirstId())
|
|
||||||
app.appConfig.widgetTimetableConfigs[appWidgetId] = widgetConfig
|
|
||||||
app.appConfig.savePending = true
|
|
||||||
}
|
|
||||||
|
|
||||||
val views = if (widgetConfig.bigStyle) {
|
val views = if (config.bigStyle) {
|
||||||
RemoteViews(context.packageName, if (widgetConfig.darkTheme) R.layout.widget_timetable_dark_big else R.layout.widget_timetable_big)
|
RemoteViews(context.packageName, if (config.darkTheme) R.layout.widget_timetable_dark_big else R.layout.widget_timetable_big)
|
||||||
} else {
|
} else {
|
||||||
RemoteViews(context.packageName, if (widgetConfig.darkTheme) R.layout.widget_timetable_dark else R.layout.widget_timetable)
|
RemoteViews(context.packageName, if (config.darkTheme) R.layout.widget_timetable_dark else R.layout.widget_timetable)
|
||||||
}
|
}
|
||||||
|
|
||||||
val refreshIntent = Intent(app, WidgetTimetable::class.java)
|
val refreshIntent = Intent(app, WidgetTimetableProvider::class.java)
|
||||||
refreshIntent.action = AppWidgetManager.ACTION_APPWIDGET_UPDATE
|
refreshIntent.action = AppWidgetManager.ACTION_APPWIDGET_UPDATE
|
||||||
refreshIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, appWidgetIds)
|
refreshIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, appWidgetIds)
|
||||||
val pendingRefreshIntent = PendingIntent.getBroadcast(context,
|
val refreshPendingIntent = PendingIntent.getBroadcast(context,
|
||||||
0, refreshIntent, PendingIntent.FLAG_UPDATE_CURRENT)
|
0, refreshIntent, PendingIntent.FLAG_UPDATE_CURRENT)
|
||||||
views.setOnClickPendingIntent(R.id.widgetTimetableRefresh, pendingRefreshIntent)
|
views.setOnClickPendingIntent(R.id.widgetTimetableRefresh, refreshPendingIntent)
|
||||||
|
|
||||||
views.setOnClickPendingIntent(R.id.widgetTimetableSync, getPendingSelfIntent(context, ACTION_SYNC_DATA))
|
views.setOnClickPendingIntent(R.id.widgetTimetableSync, getPendingSelfIntent(context, ACTION_SYNC_DATA))
|
||||||
|
|
||||||
views.setImageViewBitmap(R.id.widgetTimetableRefresh, IconicsDrawable(context, CommunityMaterial.Icon2.cmd_refresh)
|
views.setImageViewBitmap(R.id.widgetTimetableRefresh, IconicsDrawable(context, CommunityMaterial.Icon2.cmd_refresh)
|
||||||
.colorInt(Color.WHITE)
|
.colorInt(Color.WHITE)
|
||||||
.sizeDp(if (widgetConfig.bigStyle) 24 else 16).toBitmap())
|
.sizeDp(if (config.bigStyle) 24 else 16).toBitmap())
|
||||||
|
|
||||||
views.setImageViewBitmap(R.id.widgetTimetableSync, IconicsDrawable(context, CommunityMaterial.Icon.cmd_download_outline)
|
views.setImageViewBitmap(R.id.widgetTimetableSync, IconicsDrawable(context, CommunityMaterial.Icon.cmd_download_outline)
|
||||||
.colorInt(Color.WHITE)
|
.colorInt(Color.WHITE)
|
||||||
.sizeDp(if (widgetConfig.bigStyle) 24 else 16).toBitmap())
|
.sizeDp(if (config.bigStyle) 24 else 16).toBitmap())
|
||||||
|
|
||||||
prepareAppWidget(app, appWidgetId, views, widgetConfig, bellSyncDiffMillis)
|
prepareAppWidget(app, appWidgetId, views, config, bellSyncDiffMillis)
|
||||||
|
|
||||||
appWidgetManager.updateAppWidget(appWidgetId, views)
|
appWidgetManager.updateAppWidget(appWidgetId, views)
|
||||||
appWidgetManager.notifyAppWidgetViewDataChanged(appWidgetId, R.id.widgetTimetableListView)
|
appWidgetManager.notifyAppWidgetViewDataChanged(appWidgetId, R.id.widgetTimetableListView)
|
||||||
@ -329,20 +358,20 @@ class WidgetTimetable : AppWidgetProvider() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// intent running when the header is clicked
|
// intent running when the header is clicked
|
||||||
val openIntent = Intent(app, MainActivity::class.java)
|
val headerIntent = Intent(app, MainActivity::class.java)
|
||||||
openIntent.action = "android.intent.action.MAIN"
|
headerIntent.action = "android.intent.action.MAIN"
|
||||||
if (!unified) {
|
if (!unified) {
|
||||||
// per-profile widget should redirect to it + correct day
|
// per-profile widget should redirect to it + correct day
|
||||||
profileId?.let {
|
profileId?.let {
|
||||||
openIntent.putExtra("profileId", it)
|
headerIntent.putExtra("profileId", it)
|
||||||
}
|
}
|
||||||
displayingDate?.let {
|
displayingDate?.let {
|
||||||
openIntent.putExtra("timetableDate", it.value)
|
headerIntent.putExtra("timetableDate", it.value)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
openIntent.putExtra("fragmentId", MainActivity.DRAWER_ITEM_TIMETABLE)
|
headerIntent.putExtra("fragmentId", MainActivity.DRAWER_ITEM_TIMETABLE)
|
||||||
val pendingOpenIntent = PendingIntent.getActivity(app, appWidgetId, openIntent, 0)
|
val headerPendingIntent = PendingIntent.getActivity(app, appWidgetId, headerIntent, 0)
|
||||||
views.setOnClickPendingIntent(R.id.widgetTimetableHeader, pendingOpenIntent)
|
views.setOnClickPendingIntent(R.id.widgetTimetableHeader, headerPendingIntent)
|
||||||
|
|
||||||
timetables!!.put(appWidgetId, models)
|
timetables!!.put(appWidgetId, models)
|
||||||
|
|
||||||
@ -353,55 +382,21 @@ class WidgetTimetable : AppWidgetProvider() {
|
|||||||
views.setRemoteAdapter(R.id.widgetTimetableListView, listIntent)
|
views.setRemoteAdapter(R.id.widgetTimetableListView, listIntent)
|
||||||
|
|
||||||
// create an intent used to display the lesson details dialog
|
// create an intent used to display the lesson details dialog
|
||||||
val intentTemplate = Intent(app, LessonDialogActivity::class.java)
|
val itemIntent = Intent(app, LessonDialogActivity::class.java)
|
||||||
intentTemplate.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK /*or Intent.FLAG_ACTIVITY_CLEAR_TASK*/)
|
itemIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK /*or Intent.FLAG_ACTIVITY_CLEAR_TASK*/)
|
||||||
val pendingIntentTimetable = PendingIntent.getActivity(app, appWidgetId, intentTemplate, 0)
|
val itemPendingIntent = PendingIntent.getActivity(app, appWidgetId, itemIntent, 0)
|
||||||
views.setPendingIntentTemplate(R.id.widgetTimetableListView, pendingIntentTimetable)
|
views.setPendingIntentTemplate(R.id.widgetTimetableListView, itemPendingIntent)
|
||||||
|
|
||||||
if (!unified)
|
if (!unified)
|
||||||
views.setScrollPosition(R.id.widgetTimetableListView, scrollPos)
|
views.setScrollPosition(R.id.widgetTimetableListView, scrollPos)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onEnabled(context: Context) {
|
|
||||||
// Enter relevant functionality for when the first widget is created
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun onDeleted(context: Context, appWidgetIds: IntArray) {
|
override fun onDeleted(context: Context, appWidgetIds: IntArray) {
|
||||||
val app = context.applicationContext as App
|
val app = context.applicationContext as App
|
||||||
for (appWidgetId in appWidgetIds) {
|
val widgetConfigs = app.config.widgetConfigs
|
||||||
app.appConfig.widgetTimetableConfigs.remove(appWidgetId)
|
appWidgetIds.forEach {
|
||||||
}
|
widgetConfigs.remove(it.toString())
|
||||||
app.saveConfig("widgetTimetableConfigs")
|
|
||||||
}
|
|
||||||
|
|
||||||
companion object {
|
|
||||||
const val ACTION_SYNC_DATA = "ACTION_SYNC_DATA"
|
|
||||||
private const val TAG = "WidgetTimetable"
|
|
||||||
|
|
||||||
var timetables: SparseArray<List<ItemWidgetTimetableModel>>? = null
|
|
||||||
|
|
||||||
fun getPendingSelfIntent(context: Context, action: String): PendingIntent {
|
|
||||||
val intent = Intent(context, WidgetTimetable::class.java)
|
|
||||||
intent.action = action
|
|
||||||
return getPendingSelfIntent(context, intent)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getPendingSelfIntent(context: Context, intent: Intent): PendingIntent {
|
|
||||||
return PendingIntent.getBroadcast(context, 0, intent, 0)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun drawableToBitmap(drawable: Drawable): Bitmap {
|
|
||||||
|
|
||||||
if (drawable is BitmapDrawable) {
|
|
||||||
return drawable.bitmap
|
|
||||||
}
|
|
||||||
|
|
||||||
val bitmap = Bitmap.createBitmap(drawable.intrinsicWidth, drawable.intrinsicHeight, Bitmap.Config.ARGB_8888)
|
|
||||||
val canvas = Canvas(bitmap)
|
|
||||||
drawable.setBounds(0, 0, canvas.width, canvas.height)
|
|
||||||
drawable.draw(canvas)
|
|
||||||
|
|
||||||
return bitmap
|
|
||||||
}
|
}
|
||||||
|
app.config.widgetConfigs = widgetConfigs
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -0,0 +1,15 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) Kuba Szczodrzyński 2020-1-6.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package pl.szczodrzynski.edziennik.ui.widgets.timetable;
|
||||||
|
|
||||||
|
import android.content.Intent;
|
||||||
|
import android.widget.RemoteViewsService;
|
||||||
|
|
||||||
|
public class WidgetTimetableService extends RemoteViewsService {
|
||||||
|
@Override
|
||||||
|
public RemoteViewsFactory onGetViewFactory(Intent intent) {
|
||||||
|
return (new WidgetTimetableFactory(this.getApplicationContext(), intent));
|
||||||
|
}
|
||||||
|
}
|
@ -8,7 +8,7 @@ import java.util.Map;
|
|||||||
import java.util.TreeMap;
|
import java.util.TreeMap;
|
||||||
|
|
||||||
import pl.szczodrzynski.edziennik.App;
|
import pl.szczodrzynski.edziennik.App;
|
||||||
import pl.szczodrzynski.edziennik.widgets.WidgetConfig;
|
import pl.szczodrzynski.edziennik.ui.widgets.WidgetConfig;
|
||||||
|
|
||||||
public class AppConfig {
|
public class AppConfig {
|
||||||
|
|
||||||
|
@ -26,7 +26,7 @@ import pl.szczodrzynski.edziennik.MainActivity;
|
|||||||
import pl.szczodrzynski.edziennik.R;
|
import pl.szczodrzynski.edziennik.R;
|
||||||
import pl.szczodrzynski.edziennik.data.api.task.EdziennikTask;
|
import pl.szczodrzynski.edziennik.data.api.task.EdziennikTask;
|
||||||
import pl.szczodrzynski.edziennik.data.db.entity.Profile;
|
import pl.szczodrzynski.edziennik.data.db.entity.Profile;
|
||||||
import pl.szczodrzynski.edziennik.widgets.WidgetConfig;
|
import pl.szczodrzynski.edziennik.ui.widgets.WidgetConfig;
|
||||||
|
|
||||||
import static pl.szczodrzynski.edziennik.utils.Utils.getCellsForSize;
|
import static pl.szczodrzynski.edziennik.utils.Utils.getCellsForSize;
|
||||||
|
|
||||||
|
@ -1,171 +0,0 @@
|
|||||||
package pl.szczodrzynski.edziennik.widgets.notifications;
|
|
||||||
|
|
||||||
import android.app.PendingIntent;
|
|
||||||
import android.appwidget.AppWidgetManager;
|
|
||||||
import android.appwidget.AppWidgetProvider;
|
|
||||||
import android.content.ComponentName;
|
|
||||||
import android.content.Context;
|
|
||||||
import android.content.Intent;
|
|
||||||
import android.graphics.Color;
|
|
||||||
import android.graphics.PorterDuff;
|
|
||||||
import android.net.Uri;
|
|
||||||
import android.os.Build;
|
|
||||||
import android.view.View;
|
|
||||||
import android.widget.RemoteViews;
|
|
||||||
|
|
||||||
import com.mikepenz.iconics.IconicsColor;
|
|
||||||
import com.mikepenz.iconics.IconicsDrawable;
|
|
||||||
import com.mikepenz.iconics.IconicsSize;
|
|
||||||
import com.mikepenz.iconics.typeface.library.community.material.CommunityMaterial;
|
|
||||||
|
|
||||||
import java.lang.reflect.InvocationTargetException;
|
|
||||||
import java.lang.reflect.Method;
|
|
||||||
|
|
||||||
import pl.szczodrzynski.edziennik.App;
|
|
||||||
import pl.szczodrzynski.edziennik.MainActivity;
|
|
||||||
import pl.szczodrzynski.edziennik.R;
|
|
||||||
import pl.szczodrzynski.edziennik.data.api.task.EdziennikTask;
|
|
||||||
import pl.szczodrzynski.edziennik.widgets.WidgetConfig;
|
|
||||||
|
|
||||||
public class WidgetNotifications extends AppWidgetProvider {
|
|
||||||
|
|
||||||
public static final String ACTION_SYNC_DATA = "ACTION_SYNC_DATA";
|
|
||||||
private static final String TAG = "WidgetNotifications";
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onReceive(Context context, Intent intent) {
|
|
||||||
if (ACTION_SYNC_DATA.equals(intent.getAction())){
|
|
||||||
EdziennikTask.Companion.sync().enqueue(context);
|
|
||||||
}
|
|
||||||
super.onReceive(context, intent);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static PendingIntent getPendingSelfIntent(Context context, String action) {
|
|
||||||
Intent intent = new Intent(context, WidgetNotifications.class);
|
|
||||||
intent.setAction(action);
|
|
||||||
return getPendingSelfIntent(context, intent);
|
|
||||||
}
|
|
||||||
public static PendingIntent getPendingSelfIntent(Context context, Intent intent) {
|
|
||||||
return PendingIntent.getBroadcast(context, 0, intent, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onUpdate(Context context, AppWidgetManager appWidgetManager, int[] appWidgetIds) {
|
|
||||||
ComponentName thisWidget = new ComponentName(context, WidgetNotifications.class);
|
|
||||||
|
|
||||||
App app = (App)context.getApplicationContext();
|
|
||||||
|
|
||||||
int[] allWidgetIds = appWidgetManager.getAppWidgetIds(thisWidget);
|
|
||||||
// There may be multiple widgets active, so update all of them
|
|
||||||
for (int appWidgetId : allWidgetIds) {
|
|
||||||
|
|
||||||
WidgetConfig widgetConfig = app.appConfig.widgetTimetableConfigs.get(appWidgetId);
|
|
||||||
if (widgetConfig == null) {
|
|
||||||
widgetConfig = new WidgetConfig(-1);
|
|
||||||
app.appConfig.widgetTimetableConfigs.put(appWidgetId, widgetConfig);
|
|
||||||
app.appConfig.savePending = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
RemoteViews views;
|
|
||||||
if (widgetConfig.bigStyle) {
|
|
||||||
views = new RemoteViews(context.getPackageName(), widgetConfig.darkTheme ? R.layout.widget_notifications_dark_big : R.layout.widget_notifications_big);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
views = new RemoteViews(context.getPackageName(), widgetConfig.darkTheme ? R.layout.widget_notifications_dark : R.layout.widget_notifications);
|
|
||||||
}
|
|
||||||
|
|
||||||
PorterDuff.Mode mode = PorterDuff.Mode.DST_IN;
|
|
||||||
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.P) {
|
|
||||||
// this code seems to crash the launcher on >= P
|
|
||||||
float transparency = widgetConfig.opacity; //0...1
|
|
||||||
long colorFilter = 0x01000000L * (long) (255f * transparency);
|
|
||||||
try {
|
|
||||||
final Method[] declaredMethods = Class.forName("android.widget.RemoteViews").getDeclaredMethods();
|
|
||||||
final int len = declaredMethods.length;
|
|
||||||
if (len > 0) {
|
|
||||||
for (int m = 0; m < len; m++) {
|
|
||||||
final Method method = declaredMethods[m];
|
|
||||||
if (method.getName().equals("setDrawableParameters")) {
|
|
||||||
method.setAccessible(true);
|
|
||||||
method.invoke(views, R.id.widgetNotificationsListView, true, -1, (int) colorFilter, mode, -1);
|
|
||||||
method.invoke(views, R.id.widgetNotificationsHeader, true, -1, (int) colorFilter, mode, -1);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (ClassNotFoundException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} catch (InvocationTargetException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} catch (IllegalAccessException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} catch (IllegalArgumentException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Intent refreshIntent = new Intent(context, WidgetNotifications.class);
|
|
||||||
refreshIntent.setAction(AppWidgetManager.ACTION_APPWIDGET_UPDATE);
|
|
||||||
refreshIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, appWidgetIds);
|
|
||||||
PendingIntent pendingRefreshIntent = PendingIntent.getBroadcast(context,
|
|
||||||
0, refreshIntent, PendingIntent.FLAG_UPDATE_CURRENT);
|
|
||||||
views.setOnClickPendingIntent(R.id.widgetNotificationsRefresh, pendingRefreshIntent);
|
|
||||||
|
|
||||||
views.setOnClickPendingIntent(R.id.widgetNotificationsSync, getPendingSelfIntent(context, ACTION_SYNC_DATA));
|
|
||||||
|
|
||||||
views.setImageViewBitmap(R.id.widgetNotificationsRefresh, new IconicsDrawable(context, CommunityMaterial.Icon2.cmd_refresh)
|
|
||||||
.color(IconicsColor.colorInt(Color.WHITE))
|
|
||||||
.size(IconicsSize.dp(widgetConfig.bigStyle ? 24 : 16)).toBitmap());
|
|
||||||
|
|
||||||
views.setImageViewBitmap(R.id.widgetNotificationsSync, new IconicsDrawable(context, CommunityMaterial.Icon.cmd_download_outline)
|
|
||||||
.color(IconicsColor.colorInt(Color.WHITE))
|
|
||||||
.size(IconicsSize.dp(widgetConfig.bigStyle ? 24 : 16)).toBitmap());
|
|
||||||
|
|
||||||
//d(TAG, "Profiles: "+ Arrays.toString(profileList.toArray()));
|
|
||||||
|
|
||||||
if (app.appConfig.notifications.size() == 0) {
|
|
||||||
views.setViewVisibility(R.id.widgetNotificationsLoading, View.VISIBLE);
|
|
||||||
views.setRemoteAdapter(R.id.widgetNotificationsListView, new Intent());
|
|
||||||
views.setTextViewText(R.id.widgetNotificationsLoading, app.getString(R.string.widget_notifications_no_data));
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
views.setViewVisibility(R.id.widgetNotificationsLoading, View.GONE);
|
|
||||||
|
|
||||||
Intent listIntent = new Intent(context, WidgetNotificationsService.class);
|
|
||||||
listIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetId);
|
|
||||||
listIntent.putExtra("bigStyle", widgetConfig.bigStyle);
|
|
||||||
listIntent.putExtra("darkTheme", widgetConfig.darkTheme);
|
|
||||||
listIntent.setData(Uri.parse(listIntent.toUri(Intent.URI_INTENT_SCHEME)));
|
|
||||||
views.setRemoteAdapter(R.id.widgetNotificationsListView, listIntent);
|
|
||||||
|
|
||||||
// template to handle the click listener for each item
|
|
||||||
Intent intentTemplate = new Intent(context, MainActivity.class);
|
|
||||||
intentTemplate.setAction("android.intent.action.MAIN");
|
|
||||||
PendingIntent pendingIntentNotifications = PendingIntent.getActivity(context, 0, intentTemplate, 0);
|
|
||||||
views.setPendingIntentTemplate(R.id.widgetNotificationsListView, pendingIntentNotifications);
|
|
||||||
}
|
|
||||||
|
|
||||||
Intent openIntent = new Intent(context, MainActivity.class);
|
|
||||||
openIntent.setAction("android.intent.action.MAIN");
|
|
||||||
openIntent.putExtra("fragmentId", MainActivity.DRAWER_ITEM_NOTIFICATIONS);
|
|
||||||
PendingIntent pendingOpenIntent = PendingIntent.getActivity(context,
|
|
||||||
appWidgetId, openIntent, PendingIntent.FLAG_UPDATE_CURRENT);
|
|
||||||
views.setOnClickPendingIntent(R.id.widgetNotificationsHeader, pendingOpenIntent);
|
|
||||||
|
|
||||||
appWidgetManager.updateAppWidget(appWidgetId, views);
|
|
||||||
appWidgetManager.notifyAppWidgetViewDataChanged(appWidgetId, R.id.widgetNotificationsListView);
|
|
||||||
}
|
|
||||||
//modeInt++;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onDeleted(Context context, int[] appWidgetIds) {
|
|
||||||
App app = (App) context.getApplicationContext();
|
|
||||||
for (int appWidgetId: appWidgetIds) {
|
|
||||||
app.appConfig.widgetTimetableConfigs.remove(appWidgetId);
|
|
||||||
}
|
|
||||||
app.saveConfig("widgetTimetableConfigs");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
@ -1,98 +0,0 @@
|
|||||||
package pl.szczodrzynski.edziennik.widgets.notifications;
|
|
||||||
|
|
||||||
import android.appwidget.AppWidgetManager;
|
|
||||||
import android.content.Context;
|
|
||||||
import android.content.Intent;
|
|
||||||
import android.util.Log;
|
|
||||||
import android.widget.RemoteViews;
|
|
||||||
import android.widget.RemoteViewsService;
|
|
||||||
|
|
||||||
import pl.szczodrzynski.edziennik.App;
|
|
||||||
import pl.szczodrzynski.edziennik.R;
|
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Date;
|
|
||||||
import pl.szczodrzynski.edziennik.utils.models.Notification;
|
|
||||||
|
|
||||||
public class WidgetNotificationsListProvider implements RemoteViewsService.RemoteViewsFactory {
|
|
||||||
|
|
||||||
private static final String TAG = "WidgetNotificationsProv";
|
|
||||||
private App app;
|
|
||||||
private Context context;
|
|
||||||
private int appWidgetId;
|
|
||||||
private boolean bigStyle;
|
|
||||||
private boolean darkTheme;
|
|
||||||
|
|
||||||
//For obtaining the activity's context and intent
|
|
||||||
public WidgetNotificationsListProvider(Context context, Intent intent) {
|
|
||||||
this.app = (App) context.getApplicationContext();
|
|
||||||
this.context = context;
|
|
||||||
this.appWidgetId = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, 0);
|
|
||||||
this.bigStyle = intent.getBooleanExtra("bigStyle", false);
|
|
||||||
this.darkTheme = intent.getBooleanExtra("darkTheme", false);
|
|
||||||
// executed only ONCE
|
|
||||||
Log.d(TAG, "appWidgetId: "+appWidgetId);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onCreate() {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onDataSetChanged() {
|
|
||||||
// executed EVERY TIME
|
|
||||||
Log.d(TAG, "onDataSetChanged for appWidgetId: "+appWidgetId);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onDestroy() {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int getCount() {
|
|
||||||
return (app.appConfig.notifications == null ? 0 : app.appConfig.notifications.size());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public RemoteViews getViewAt(int i) {
|
|
||||||
RemoteViews views = new RemoteViews(context.getPackageName(), R.layout.row_widget_notifications_item);
|
|
||||||
if (i > app.appConfig.notifications.size()-1)
|
|
||||||
return views;
|
|
||||||
Notification notification = app.appConfig.notifications.get(i);
|
|
||||||
|
|
||||||
if (bigStyle) {
|
|
||||||
views = new RemoteViews(context.getPackageName(), darkTheme ? R.layout.row_widget_notifications_dark_big_item : R.layout.row_widget_notifications_big_item);
|
|
||||||
}
|
|
||||||
else if (darkTheme) {
|
|
||||||
views = new RemoteViews(context.getPackageName(), R.layout.row_widget_notifications_dark_item);
|
|
||||||
}
|
|
||||||
|
|
||||||
Intent intent = new Intent();
|
|
||||||
notification.fillIntent(intent);
|
|
||||||
views.setOnClickFillInIntent(R.id.widgetNotificationsRoot, intent);
|
|
||||||
|
|
||||||
views.setTextViewText(R.id.widgetNotificationsTitle, app.getString(R.string.widget_notifications_title_format, notification.title, Notification.stringType(context, notification.type)));
|
|
||||||
views.setTextViewText(R.id.widgetNotificationsText, notification.text);
|
|
||||||
views.setTextViewText(R.id.widgetNotificationsDate, Date.fromMillis(notification.addedDate).getFormattedString());
|
|
||||||
|
|
||||||
return views;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public RemoteViews getLoadingView() {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int getViewTypeCount() {
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public long getItemId(int i) {
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean hasStableIds() {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,11 +0,0 @@
|
|||||||
package pl.szczodrzynski.edziennik.widgets.notifications;
|
|
||||||
|
|
||||||
import android.content.Intent;
|
|
||||||
import android.widget.RemoteViewsService;
|
|
||||||
|
|
||||||
public class WidgetNotificationsService extends RemoteViewsService {
|
|
||||||
@Override
|
|
||||||
public RemoteViewsFactory onGetViewFactory(Intent intent) {
|
|
||||||
return (new WidgetNotificationsListProvider(this.getApplicationContext(), intent));
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,17 +0,0 @@
|
|||||||
package pl.szczodrzynski.edziennik.widgets.timetable;
|
|
||||||
|
|
||||||
import android.content.Intent;
|
|
||||||
import android.widget.RemoteViewsService;
|
|
||||||
|
|
||||||
public class WidgetTimetableService extends RemoteViewsService {
|
|
||||||
/*
|
|
||||||
* So pretty simple just defining the Adapter of the listview
|
|
||||||
* here Adapter is ListProvider
|
|
||||||
* */
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public RemoteViewsFactory onGetViewFactory(Intent intent) {
|
|
||||||
return (new WidgetTimetableListProvider(this.getApplicationContext(), intent));
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,6 +1,4 @@
|
|||||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
|
||||||
android:id="@+id/root"
|
android:id="@+id/root"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
android:layout_height="match_parent"
|
android:layout_height="match_parent"
|
||||||
@ -36,14 +34,6 @@
|
|||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|
||||||
<ImageButton
|
|
||||||
android:id="@+id/widgetNotificationsRefresh"
|
|
||||||
android:layout_width="45.0dip"
|
|
||||||
android:layout_height="45.0dip"
|
|
||||||
android:layout_gravity="end|center"
|
|
||||||
android:background="?android:selectableItemBackground"
|
|
||||||
android:contentDescription="@string/widget_refresh" />
|
|
||||||
|
|
||||||
<ImageButton
|
<ImageButton
|
||||||
android:id="@+id/widgetNotificationsSync"
|
android:id="@+id/widgetNotificationsSync"
|
||||||
android:layout_width="45.0dip"
|
android:layout_width="45.0dip"
|
||||||
|
@ -1,6 +1,4 @@
|
|||||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
|
||||||
android:id="@+id/root"
|
android:id="@+id/root"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
android:layout_height="match_parent"
|
android:layout_height="match_parent"
|
||||||
@ -36,14 +34,6 @@
|
|||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|
||||||
<ImageButton
|
|
||||||
android:id="@+id/widgetNotificationsRefresh"
|
|
||||||
android:layout_width="60dip"
|
|
||||||
android:layout_height="60dip"
|
|
||||||
android:layout_gravity="end|center"
|
|
||||||
android:background="?android:selectableItemBackground"
|
|
||||||
android:contentDescription="@string/widget_refresh" />
|
|
||||||
|
|
||||||
<ImageButton
|
<ImageButton
|
||||||
android:id="@+id/widgetNotificationsSync"
|
android:id="@+id/widgetNotificationsSync"
|
||||||
android:layout_width="60dip"
|
android:layout_width="60dip"
|
||||||
|
@ -1,6 +1,4 @@
|
|||||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
|
||||||
android:id="@+id/root"
|
android:id="@+id/root"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
android:layout_height="match_parent"
|
android:layout_height="match_parent"
|
||||||
@ -36,14 +34,6 @@
|
|||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|
||||||
<ImageButton
|
|
||||||
android:id="@+id/widgetNotificationsRefresh"
|
|
||||||
android:layout_width="45.0dip"
|
|
||||||
android:layout_height="45.0dip"
|
|
||||||
android:layout_gravity="end|center"
|
|
||||||
android:background="?android:selectableItemBackground"
|
|
||||||
android:contentDescription="@string/widget_refresh" />
|
|
||||||
|
|
||||||
<ImageButton
|
<ImageButton
|
||||||
android:id="@+id/widgetNotificationsSync"
|
android:id="@+id/widgetNotificationsSync"
|
||||||
android:layout_width="45.0dip"
|
android:layout_width="45.0dip"
|
||||||
|
@ -1,6 +1,4 @@
|
|||||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
|
||||||
xmlns:tools="http://schemas.android.com/tools"
|
|
||||||
android:id="@+id/root"
|
android:id="@+id/root"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
android:layout_height="match_parent"
|
android:layout_height="match_parent"
|
||||||
@ -36,14 +34,6 @@
|
|||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|
||||||
<ImageButton
|
|
||||||
android:id="@+id/widgetNotificationsRefresh"
|
|
||||||
android:layout_width="60dip"
|
|
||||||
android:layout_height="60dip"
|
|
||||||
android:layout_gravity="end|center"
|
|
||||||
android:background="?android:selectableItemBackground"
|
|
||||||
android:contentDescription="@string/widget_refresh" />
|
|
||||||
|
|
||||||
<ImageButton
|
<ImageButton
|
||||||
android:id="@+id/widgetNotificationsSync"
|
android:id="@+id/widgetNotificationsSync"
|
||||||
android:layout_width="60dip"
|
android:layout_width="60dip"
|
||||||
|
@ -11,5 +11,5 @@
|
|||||||
android:resizeMode="horizontal|vertical"
|
android:resizeMode="horizontal|vertical"
|
||||||
android:updatePeriodMillis="1800000"
|
android:updatePeriodMillis="1800000"
|
||||||
android:widgetCategory="home_screen"
|
android:widgetCategory="home_screen"
|
||||||
android:configure="pl.szczodrzynski.edziennik.widgets.WidgetConfigActivity"
|
android:configure="pl.szczodrzynski.edziennik.ui.widgets.WidgetConfigActivity"
|
||||||
tools:ignore="UnusedAttribute" />
|
tools:ignore="UnusedAttribute" />
|
||||||
|
@ -11,5 +11,5 @@
|
|||||||
android:resizeMode="horizontal|vertical"
|
android:resizeMode="horizontal|vertical"
|
||||||
android:updatePeriodMillis="5400000"
|
android:updatePeriodMillis="5400000"
|
||||||
android:widgetCategory="home_screen"
|
android:widgetCategory="home_screen"
|
||||||
android:configure="pl.szczodrzynski.edziennik.widgets.WidgetConfigActivity"
|
android:configure="pl.szczodrzynski.edziennik.ui.widgets.WidgetConfigActivity"
|
||||||
tools:ignore="UnusedAttribute" />
|
tools:ignore="UnusedAttribute" />
|
||||||
|
@ -11,5 +11,5 @@
|
|||||||
android:resizeMode="horizontal|vertical"
|
android:resizeMode="horizontal|vertical"
|
||||||
android:updatePeriodMillis="1800000"
|
android:updatePeriodMillis="1800000"
|
||||||
android:widgetCategory="home_screen"
|
android:widgetCategory="home_screen"
|
||||||
android:configure="pl.szczodrzynski.edziennik.widgets.WidgetConfigActivity"
|
android:configure="pl.szczodrzynski.edziennik.ui.widgets.WidgetConfigActivity"
|
||||||
tools:ignore="UnusedAttribute" />
|
tools:ignore="UnusedAttribute" />
|
||||||
|
Loading…
x
Reference in New Issue
Block a user