mirror of
https://github.com/szkolny-eu/szkolny-android.git
synced 2025-06-15 15:10:17 +02:00
Compare commits
3 Commits
v3.9.1-dev
...
code-refor
Author | SHA1 | Date | |
---|---|---|---|
8f80bc70ed | |||
e1d902ceb5 | |||
eb1984c6b5 |
@ -1,6 +1,7 @@
|
||||
apply plugin: 'com.android.application'
|
||||
apply plugin: 'kotlin-android-extensions'
|
||||
apply plugin: 'kotlin-android'
|
||||
apply plugin: 'kotlin-kapt'
|
||||
apply plugin: 'com.google.gms.google-services'
|
||||
apply plugin: 'io.fabric'
|
||||
|
||||
@ -91,7 +92,7 @@ tasks.whenTaskAdded { task ->
|
||||
dependencies {
|
||||
implementation fileTree(include: ['*.jar'], dir: 'libs')
|
||||
|
||||
annotationProcessor "androidx.room:room-compiler:${versions.room}"
|
||||
kapt "androidx.room:room-compiler:${versions.room}"
|
||||
debugImplementation "com.amitshekhar.android:debug-db:1.0.5"
|
||||
|
||||
implementation "android.arch.navigation:navigation-fragment-ktx:${versions.navigationFragment}"
|
||||
@ -159,11 +160,16 @@ dependencies {
|
||||
//implementation 'com.github.wulkanowy:uonet-request-signer:master-SNAPSHOT'
|
||||
//implementation 'com.github.kuba2k2.uonet-request-signer:android:master-63f094b14a-1'
|
||||
|
||||
//implementation "org.redundent:kotlin-xml-builder:1.5.3"
|
||||
implementation "org.redundent:kotlin-xml-builder:1.5.3"
|
||||
|
||||
implementation "io.github.wulkanowy:signer-android:0.1.1"
|
||||
|
||||
implementation "androidx.work:work-runtime-ktx:${versions.work}"
|
||||
|
||||
api "com.google.dagger:dagger:${versions.dagger}"
|
||||
api "com.google.dagger:dagger-android-support:${versions.dagger}"
|
||||
kapt "com.google.dagger:dagger-compiler:${versions.dagger}"
|
||||
kapt "com.google.dagger:dagger-android-processor:${versions.dagger}"
|
||||
}
|
||||
repositories {
|
||||
mavenCentral()
|
||||
|
@ -15,14 +15,10 @@
|
||||
android:theme="@style/SplashTheme"
|
||||
android:usesCleartextTraffic="true"
|
||||
tools:ignore="UnusedAttribute">
|
||||
<activity
|
||||
android:name=".ui.modules.login.LoginLibrusCaptchaActivity"
|
||||
android:theme="@android:style/Theme.Dialog"
|
||||
android:excludeFromRecents="true"/>
|
||||
<activity
|
||||
android:name=".MainActivity"
|
||||
android:configChanges="orientation|screenSize"
|
||||
android:label="@string/app_name"
|
||||
android:configChanges="orientation|screenSize"
|
||||
android:launchMode="singleTop"
|
||||
android:theme="@style/SplashTheme">
|
||||
<intent-filter>
|
||||
@ -33,7 +29,7 @@
|
||||
</intent-filter>
|
||||
</activity>
|
||||
<activity
|
||||
android:name=".ui.modules.messages.MessagesComposeActivity"
|
||||
android:name="pl.szczodrzynski.edziennik.ui.modules.messages.MessagesComposeActivity"
|
||||
android:configChanges="orientation|screenSize"
|
||||
android:label="@string/messages_compose_title"
|
||||
android:theme="@style/AppTheme.Black" />
|
||||
@ -43,7 +39,7 @@
|
||||
android:label="@string/app_name"
|
||||
android:theme="@style/AppTheme" />
|
||||
<activity
|
||||
android:name=".ui.modules.login.LoginActivity"
|
||||
android:name="pl.szczodrzynski.edziennik.ui.modules.login.LoginActivity"
|
||||
android:configChanges="orientation|screenSize"
|
||||
android:launchMode="singleTop"
|
||||
android:theme="@style/AppTheme.Light" />
|
||||
@ -105,18 +101,22 @@
|
||||
android:excludeFromRecents="true"
|
||||
android:noHistory="true"
|
||||
android:theme="@style/AppTheme.NoDisplay" />
|
||||
|
||||
<activity
|
||||
android:name=".ui.modules.settings.SettingsLicenseActivity"
|
||||
android:configChanges="orientation|keyboardHidden"
|
||||
android:theme="@style/AppTheme" />
|
||||
|
||||
<activity
|
||||
android:name="com.theartofdev.edmodo.cropper.CropImageActivity"
|
||||
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" />
|
||||
@ -169,6 +169,7 @@
|
||||
android:name="android.appwidget.provider"
|
||||
android:resource="@xml/widget_notifications_info" />
|
||||
</receiver>
|
||||
|
||||
<receiver
|
||||
android:name=".widgets.luckynumber.WidgetLuckyNumber"
|
||||
android:label="@string/widget_lucky_number_title">
|
||||
@ -187,6 +188,7 @@
|
||||
<action android:name="android.intent.action.USER_PRESENT" />
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
|
||||
<receiver android:name=".receivers.BootReceiver">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.BOOT_COMPLETED" />
|
||||
@ -194,24 +196,6 @@
|
||||
<action android:name="android.intent.action.QUICKBOOT_POWERON" />
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
|
||||
<receiver
|
||||
android:name=".sync.FirebaseBroadcastReceiver"
|
||||
android:exported="true"
|
||||
android:permission="com.google.android.c2dm.permission.SEND">
|
||||
<intent-filter>
|
||||
<action android:name="com.google.android.c2dm.intent.RECEIVE" />
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
|
||||
<receiver
|
||||
android:name=".receivers.SzkolnyReceiver"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="pl.szczodrzynski.edziennik.SZKOLNY_MAIN" />
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
|
||||
<service
|
||||
android:name=".sync.MyFirebaseMessagingService"
|
||||
android:exported="false">
|
||||
@ -220,6 +204,14 @@
|
||||
<action android:name="com.google.firebase.MESSAGING_EVENT" />
|
||||
</intent-filter>
|
||||
</service>
|
||||
<receiver
|
||||
android:name=".sync.FirebaseBroadcastReceiver"
|
||||
android:exported="true"
|
||||
android:permission="com.google.android.c2dm.permission.SEND">
|
||||
<intent-filter>
|
||||
<action android:name="com.google.android.c2dm.intent.RECEIVE" />
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
<service
|
||||
android:name=".widgets.timetable.WidgetTimetableService"
|
||||
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
||||
@ -230,6 +222,14 @@
|
||||
|
||||
<service android:name=".Notifier$GetDataRetryService" />
|
||||
|
||||
<receiver
|
||||
android:name=".receivers.SzkolnyReceiver"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="pl.szczodrzynski.edziennik.SZKOLNY_MAIN" />
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
|
||||
<service android:name=".api.v2.ApiService" />
|
||||
</application>
|
||||
<uses-permission android:name="android.permission.REQUEST_INSTALL_PACKAGES" />
|
||||
@ -244,4 +244,4 @@
|
||||
|
||||
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
|
||||
|
||||
</manifest>
|
||||
</manifest>
|
||||
|
@ -31,11 +31,57 @@
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<h3>Wersja 4.0, 2019-jeszcze-nie-wiem-kiedy</h3>
|
||||
<h3>Wersja 3.1.1, 2019-10-09</h3>
|
||||
<ul>
|
||||
<li>UWAGA. To jest wersja in-development. Wiele funkcji może nie działać prawidłowo (lub wcale), co oznacza tylko że nie zostały jeszcze przeniesione
|
||||
z wersji 3.x. Proszę o cierpliwość oraz <b>nie udostępnianie</b> tej wersji <u>nikomu</u>.</li>
|
||||
<li>Bardzo dużo zmian</li>
|
||||
<li>Librus: poprawiona synchronizacja kategorii i kolorów ocen.</li>
|
||||
<li>Zmieniony kolor dolnego paska w ciemnym motywie.</li>
|
||||
<li>Zaktualizowany licznik czasu lekcji.</li>
|
||||
</ul>
|
||||
|
||||
<h3>Wersja 3.1, 2019-09-29</h3>
|
||||
<ul>
|
||||
<li>Poprawiony interfejs zadań domowych.</li>
|
||||
<li>Librus: wyświetlanie komentarzy ocen.</li>
|
||||
<li>Librus: wyświetlanie nieobecności nauczycieli w Terminarzu.</li>
|
||||
<li>Librus: usprawniona synchronizacja ocen.</li>
|
||||
<li>Poprawki angielskiego tłumaczenia.</li>
|
||||
</ul>
|
||||
|
||||
<h3>Wersja 3.0.3, 2019-09-26</h3>
|
||||
<ul>
|
||||
<li>Librus: poprawka kilku błędów synchronizacji.</li>
|
||||
<li>Vulcan: prawidłowe oznaczanie wiadomości jako przeczytana.</li>
|
||||
<li>Vulcan: poprawiona synchronizacja wiadomości i frekwencji.</li>
|
||||
<li>Vulcan: poprawka błędów logowania.</li>
|
||||
</ul>
|
||||
|
||||
<h3>Wersja 3.0.2, 2019-09-24</h3>
|
||||
<ul>
|
||||
<li>Librus: pobieranie Bieżących ocen opisowych.</li>
|
||||
<li>Poprawki UI: kolor ikon paska statusu w jasnym motywie.</li>
|
||||
<li>Poprawka braku skanera QR do przekazywania powiadomień.</li>
|
||||
<li>Poprawka wyboru koloru i daty własnego wydarzenia, które crashowały aplikację.</li>
|
||||
</ul>
|
||||
|
||||
<h3>Wersja 3.0.1, 2019-09-19</h3>
|
||||
<ul>
|
||||
<li>Librus: Poprawa błędu synchronizacji.</li>
|
||||
<li>Poprawki UI związane z paskiem nawigacji.</li>
|
||||
<li>Mobidziennik: Pobieranie ocen w niektórych przedmiotach.</li>
|
||||
</ul>
|
||||
|
||||
<h3>Wersja 3.0, 2019-09-13</h3>
|
||||
<ul>
|
||||
<li><b>Nowy wygląd i sposób nawigacji</b> w całej aplikacji.</li>
|
||||
<li>Menu nawigacji można teraz otworzyć przyciskiem na <b>dolnym pasku</b>. Pociągnięcie w górę tego paska wyświetla <b>menu kontekstowe</b> dotyczące danego widoku.</li>
|
||||
<li>Założyliśmy serwer Discord! <a href="https://discord.gg/n9e8pWr">https://discord.gg/n9e8pWr</a></li>
|
||||
<br>
|
||||
<li>Librus: poprawka powielonych ogłoszeń szkolnych.</li>
|
||||
<li>Naprawiłem błąd nieskończonej synchronizacji w Vulcanie.</li>
|
||||
<li>Naprawiłem crash launchera przy dodaniu widgetu.</li>
|
||||
<li>Naprawiłem częste crashe związane z widokiem kalendarza.</li>
|
||||
<li>Nowe, ładniejsze (choć trochę) motywy kolorów.</li>
|
||||
<li>Dużo drobnych poprawek UI i działania aplikacji.</li>
|
||||
</ul>
|
||||
|
||||
<!--<i>
|
||||
|
@ -22,6 +22,7 @@ import android.util.Pair;
|
||||
|
||||
import androidx.annotation.RequiresApi;
|
||||
import androidx.appcompat.app.AppCompatDelegate;
|
||||
import androidx.multidex.MultiDex;
|
||||
import androidx.work.Configuration;
|
||||
|
||||
import com.chuckerteam.chucker.api.ChuckerCollector;
|
||||
@ -59,6 +60,8 @@ import javax.net.ssl.TrustManagerFactory;
|
||||
import javax.net.ssl.X509TrustManager;
|
||||
|
||||
import cat.ereza.customactivityoncrash.config.CaocConfig;
|
||||
import dagger.android.AndroidInjector;
|
||||
import dagger.android.support.DaggerApplication;
|
||||
import im.wangchao.mhttp.MHttp;
|
||||
import im.wangchao.mhttp.internal.cookie.PersistentCookieJar;
|
||||
import im.wangchao.mhttp.internal.cookie.cache.SetCookieCache;
|
||||
@ -77,6 +80,7 @@ import pl.szczodrzynski.edziennik.data.db.modules.debuglog.DebugLog;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.login.LoginStore;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.profiles.Profile;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.profiles.ProfileFull;
|
||||
import pl.szczodrzynski.edziennik.di.DaggerAppComponent;
|
||||
import pl.szczodrzynski.edziennik.network.NetworkUtils;
|
||||
import pl.szczodrzynski.edziennik.network.TLSSocketFactory;
|
||||
import pl.szczodrzynski.edziennik.sync.SyncWorker;
|
||||
@ -90,7 +94,7 @@ import static pl.szczodrzynski.edziennik.data.db.modules.login.LoginStore.LOGIN_
|
||||
import static pl.szczodrzynski.edziennik.data.db.modules.login.LoginStore.LOGIN_TYPE_MOBIDZIENNIK;
|
||||
import static pl.szczodrzynski.edziennik.data.db.modules.login.LoginStore.LOGIN_TYPE_VULCAN;
|
||||
|
||||
public class App extends androidx.multidex.MultiDexApplication implements Configuration.Provider {
|
||||
public class App extends DaggerApplication implements Configuration.Provider {
|
||||
private static final String TAG = "App";
|
||||
public static int profileId = -1;
|
||||
private Context mContext;
|
||||
@ -181,6 +185,17 @@ public class App extends androidx.multidex.MultiDexApplication implements Config
|
||||
return Icon.createWithBitmap(bitmap);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void attachBaseContext(Context base) {
|
||||
super.attachBaseContext(base);
|
||||
MultiDex.install(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected AndroidInjector<? extends DaggerApplication> applicationInjector() {
|
||||
return DaggerAppComponent.factory().create(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCreate() {
|
||||
super.onCreate();
|
||||
@ -543,6 +558,7 @@ public class App extends androidx.multidex.MultiDexApplication implements Config
|
||||
appConfig = new AppConfig(this);
|
||||
}
|
||||
}
|
||||
|
||||
public void saveConfig()
|
||||
{
|
||||
try {
|
||||
@ -724,5 +740,4 @@ public class App extends androidx.multidex.MultiDexApplication implements Config
|
||||
devMode = false;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -2,19 +2,13 @@ package pl.szczodrzynski.edziennik
|
||||
|
||||
import android.app.Activity
|
||||
import android.app.ActivityManager
|
||||
import android.content.BroadcastReceiver
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.content.IntentFilter
|
||||
import android.content.pm.PackageManager
|
||||
import android.content.*
|
||||
import android.graphics.BitmapFactory
|
||||
import android.graphics.drawable.BitmapDrawable
|
||||
import android.os.*
|
||||
import android.provider.Settings
|
||||
import android.view.Gravity
|
||||
import android.view.View
|
||||
import android.widget.Toast
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.appcompat.widget.PopupMenu
|
||||
import androidx.core.graphics.ColorUtils
|
||||
import androidx.lifecycle.Observer
|
||||
@ -31,6 +25,7 @@ import com.mikepenz.materialdrawer.model.ProfileDrawerItem
|
||||
import com.mikepenz.materialdrawer.model.ProfileSettingDrawerItem
|
||||
import com.mikepenz.materialdrawer.model.interfaces.IDrawerItem
|
||||
import com.mikepenz.materialdrawer.model.interfaces.IProfile
|
||||
import dagger.android.support.DaggerAppCompatActivity
|
||||
import org.greenrobot.eventbus.EventBus
|
||||
import org.greenrobot.eventbus.Subscribe
|
||||
import org.greenrobot.eventbus.ThreadMode
|
||||
@ -69,7 +64,6 @@ import pl.szczodrzynski.edziennik.utils.Themes
|
||||
import pl.szczodrzynski.edziennik.utils.Utils
|
||||
import pl.szczodrzynski.edziennik.utils.Utils.d
|
||||
import pl.szczodrzynski.edziennik.utils.Utils.dpToPx
|
||||
import pl.szczodrzynski.edziennik.utils.appManagerIntentList
|
||||
import pl.szczodrzynski.edziennik.utils.models.NavTarget
|
||||
import pl.szczodrzynski.navlib.*
|
||||
import pl.szczodrzynski.navlib.SystemBarsUtil.Companion.COLOR_HALF_TRANSPARENT
|
||||
@ -84,7 +78,7 @@ import java.io.IOException
|
||||
import java.util.*
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
class MainActivity : AppCompatActivity() {
|
||||
class MainActivity : DaggerAppCompatActivity() {
|
||||
companion object {
|
||||
|
||||
var useOldMessages = false
|
||||
@ -346,7 +340,7 @@ class MainActivity : AppCompatActivity() {
|
||||
if (!profileListEmpty) {
|
||||
handleIntent(intent?.extras)
|
||||
}
|
||||
app.db.profileDao().getAllFull().observe(this, Observer { profiles ->
|
||||
app.db.profileDao().allFull.observe(this, Observer { profiles ->
|
||||
// TODO fix weird -1 profiles ???
|
||||
profiles.removeAll { it.id < 0 }
|
||||
drawer.setProfileList(profiles)
|
||||
@ -363,7 +357,7 @@ class MainActivity : AppCompatActivity() {
|
||||
if (app.profile != null)
|
||||
setDrawerItems()
|
||||
|
||||
app.db.metadataDao().getUnreadCounts().observe(this, Observer { unreadCounters ->
|
||||
app.db.metadataDao().unreadCounts.observe(this, Observer { unreadCounters ->
|
||||
unreadCounters.map {
|
||||
it.type = it.thingType
|
||||
}
|
||||
@ -588,17 +582,28 @@ class MainActivity : AppCompatActivity() {
|
||||
.setMessage(R.string.app_manager_dialog_text)
|
||||
.setPositiveButton(R.string.ok) { dialog, which ->
|
||||
try {
|
||||
for (intent in appManagerIntentList) {
|
||||
if (packageManager.resolveActivity(intent, PackageManager.MATCH_DEFAULT_ONLY) != null) {
|
||||
startActivity(intent)
|
||||
}
|
||||
}
|
||||
val intent = Intent()
|
||||
intent.component = ComponentName(
|
||||
"com.huawei.systemmanager",
|
||||
"com.huawei.systemmanager.appcontrol.activity.StartupAppControlActivity"
|
||||
)
|
||||
startActivity(intent)
|
||||
} catch (e: Exception) {
|
||||
e.printStackTrace()
|
||||
try {
|
||||
startActivity(Intent(Settings.ACTION_SETTINGS))
|
||||
val intent = Intent()
|
||||
intent.component = ComponentName(
|
||||
"com.asus.mobilemanager",
|
||||
"com.asus.mobilemanager.MainActivity"
|
||||
)
|
||||
startActivity(intent)
|
||||
} catch (e: Exception) {
|
||||
e.printStackTrace()
|
||||
Toast.makeText(this, R.string.app_manager_open_failed, Toast.LENGTH_SHORT).show()
|
||||
try {
|
||||
startActivity(Intent(android.provider.Settings.ACTION_SETTINGS))
|
||||
} catch (e: Exception) {
|
||||
e.printStackTrace()
|
||||
Toast.makeText(this, R.string.app_manager_open_failed, Toast.LENGTH_SHORT).show()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -90,7 +90,6 @@ class ApiService : Service() {
|
||||
errorList.add(apiError)
|
||||
apiError.throwable?.printStackTrace()
|
||||
if (apiError.isCritical) {
|
||||
taskRunning?.cancel()
|
||||
notification.setCriticalError().post()
|
||||
taskRunning = null
|
||||
taskIsRunning = false
|
||||
@ -155,14 +154,10 @@ class ApiService : Service() {
|
||||
// post an event
|
||||
EventBus.getDefault().post(ApiTaskStartedEvent(taskProfileId, task.profile))
|
||||
|
||||
try {
|
||||
when (task) {
|
||||
is EdziennikTask -> task.run(app, taskCallback)
|
||||
is NotifyTask -> task.run(app, taskCallback)
|
||||
is ErrorReportTask -> task.run(app, taskCallback, notification, errorList)
|
||||
}
|
||||
} catch (e: Exception) {
|
||||
taskCallback.onError(ApiError(TAG, EXCEPTION_API_TASK).withThrowable(e))
|
||||
when (task) {
|
||||
is EdziennikTask -> task.run(app, taskCallback)
|
||||
is NotifyTask -> task.run(app, taskCallback)
|
||||
is ErrorReportTask -> task.run(app, taskCallback, notification, errorList)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -150,7 +150,6 @@ const val ERROR_IDZIENNIK_API_OTHER = 451
|
||||
|
||||
const val ERROR_TEMPLATE_WEB_OTHER = 801
|
||||
|
||||
const val EXCEPTION_API_TASK = 900
|
||||
const val EXCEPTION_LOGIN_LIBRUS_API_TOKEN = 901
|
||||
const val EXCEPTION_LOGIN_LIBRUS_PORTAL_TOKEN = 902
|
||||
const val EXCEPTION_LIBRUS_PORTAL_SYNERGIA_TOKEN = 903
|
||||
|
@ -41,43 +41,43 @@ class IdziennikData(val data: DataIdziennik, val onSuccess: () -> Unit) {
|
||||
when (endpointId) {
|
||||
ENDPOINT_IDZIENNIK_WEB_TIMETABLE -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_timetable)
|
||||
IdziennikWebTimetable(data, onSuccess)
|
||||
IdziennikWebTimetable(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_WEB_GRADES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_grades)
|
||||
IdziennikWebGrades(data, onSuccess)
|
||||
IdziennikWebGrades(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_WEB_PROPOSED_GRADES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_proposed_grades)
|
||||
IdziennikWebProposedGrades(data, onSuccess)
|
||||
IdziennikWebProposedGrades(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_WEB_EXAMS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_exams)
|
||||
IdziennikWebExams(data, onSuccess)
|
||||
IdziennikWebExams(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_WEB_NOTICES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_notices)
|
||||
IdziennikWebNotices(data, onSuccess)
|
||||
IdziennikWebNotices(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_WEB_ANNOUNCEMENTS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_announcements)
|
||||
IdziennikWebAnnouncements(data, onSuccess)
|
||||
IdziennikWebAnnouncements(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_WEB_ATTENDANCE -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_attendance)
|
||||
IdziennikWebAttendance(data, onSuccess)
|
||||
IdziennikWebAttendance(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_API_CURRENT_REGISTER -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_lucky_number)
|
||||
IdziennikApiCurrentRegister(data, onSuccess)
|
||||
IdziennikApiCurrentRegister(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_API_MESSAGES_INBOX -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_inbox)
|
||||
IdziennikApiMessagesInbox(data, onSuccess)
|
||||
IdziennikApiMessagesInbox(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_IDZIENNIK_API_MESSAGES_SENT -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_outbox)
|
||||
IdziennikApiMessagesSent(data, onSuccess)
|
||||
IdziennikApiMessagesSent(data) { onSuccess() }
|
||||
}
|
||||
else -> onSuccess()
|
||||
}
|
||||
|
@ -5,7 +5,7 @@
|
||||
package pl.szczodrzynski.edziennik.api.v2.librus
|
||||
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.api.v2.*
|
||||
import pl.szczodrzynski.edziennik.api.v2.CODE_INTERNAL_LIBRUS_ACCOUNT_410
|
||||
import pl.szczodrzynski.edziennik.api.v2.interfaces.EdziennikCallback
|
||||
import pl.szczodrzynski.edziennik.api.v2.interfaces.EdziennikInterface
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.data.LibrusData
|
||||
@ -14,7 +14,9 @@ import pl.szczodrzynski.edziennik.api.v2.librus.firstlogin.LibrusFirstLogin
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.login.LibrusLogin
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.login.LibrusLoginApi
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.login.LibrusLoginSynergia
|
||||
import pl.szczodrzynski.edziennik.api.v2.librusLoginMethods
|
||||
import pl.szczodrzynski.edziennik.api.v2.models.ApiError
|
||||
import pl.szczodrzynski.edziennik.api.v2.prepare
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.login.LoginStore
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.profiles.Profile
|
||||
import pl.szczodrzynski.edziennik.utils.Utils.d
|
||||
@ -51,28 +53,12 @@ class Librus(val app: App, val profile: Profile?, val loginStore: LoginStore, va
|
||||
|__*/
|
||||
override fun sync(featureIds: List<Int>, viewId: Int?) {
|
||||
data.prepare(librusLoginMethods, LibrusFeatures, featureIds, viewId)
|
||||
login()
|
||||
}
|
||||
|
||||
private fun login() {
|
||||
d(TAG, "Trying to login with ${data.targetLoginMethodIds}")
|
||||
if (internalErrorList.isNotEmpty()) {
|
||||
d(TAG, " - Internal errors:")
|
||||
internalErrorList.forEach { d(TAG, " - code $it") }
|
||||
}
|
||||
LibrusLogin(data) {
|
||||
data()
|
||||
}
|
||||
}
|
||||
|
||||
private fun data() {
|
||||
d(TAG, "LoginMethod IDs: ${data.targetLoginMethodIds}")
|
||||
d(TAG, "Endpoint IDs: ${data.targetEndpointIds}")
|
||||
if (internalErrorList.isNotEmpty()) {
|
||||
d(TAG, " - Internal errors:")
|
||||
internalErrorList.forEach { d(TAG, " - code $it") }
|
||||
}
|
||||
LibrusData(data) {
|
||||
completed()
|
||||
LibrusLogin(data) {
|
||||
LibrusData(data) {
|
||||
completed()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -116,67 +102,15 @@ class Librus(val app: App, val profile: Profile?, val loginStore: LoginStore, va
|
||||
}
|
||||
|
||||
override fun onError(apiError: ApiError) {
|
||||
if (apiError.errorCode in internalErrorList) {
|
||||
// finish immediately if the same error occurs twice during the same sync
|
||||
callback.onError(apiError)
|
||||
return
|
||||
}
|
||||
internalErrorList.add(apiError.errorCode)
|
||||
when (apiError.errorCode) {
|
||||
ERROR_LIBRUS_PORTAL_ACCESS_DENIED -> {
|
||||
data.loginMethods.remove(LOGIN_METHOD_LIBRUS_PORTAL)
|
||||
data.targetLoginMethodIds.add(LOGIN_METHOD_LIBRUS_PORTAL)
|
||||
data.targetLoginMethodIds.sort()
|
||||
data.portalTokenExpiryTime = 0
|
||||
login()
|
||||
in internalErrorList -> {
|
||||
// finish immediately if the same error occurs twice during the same sync
|
||||
callback.onError(apiError)
|
||||
}
|
||||
ERROR_LIBRUS_API_ACCESS_DENIED,
|
||||
ERROR_LIBRUS_API_TOKEN_EXPIRED -> {
|
||||
data.loginMethods.remove(LOGIN_METHOD_LIBRUS_API)
|
||||
data.targetLoginMethodIds.add(LOGIN_METHOD_LIBRUS_API)
|
||||
data.targetLoginMethodIds.sort()
|
||||
data.apiTokenExpiryTime = 0
|
||||
login()
|
||||
}
|
||||
ERROR_LIBRUS_SYNERGIA_ACCESS_DENIED -> {
|
||||
data.loginMethods.remove(LOGIN_METHOD_LIBRUS_SYNERGIA)
|
||||
data.targetLoginMethodIds.add(LOGIN_METHOD_LIBRUS_SYNERGIA)
|
||||
data.targetLoginMethodIds.sort()
|
||||
data.synergiaSessionIdExpiryTime = 0
|
||||
login()
|
||||
}
|
||||
ERROR_LIBRUS_MESSAGES_ACCESS_DENIED -> {
|
||||
data.loginMethods.remove(LOGIN_METHOD_LIBRUS_MESSAGES)
|
||||
data.targetLoginMethodIds.add(LOGIN_METHOD_LIBRUS_MESSAGES)
|
||||
data.targetLoginMethodIds.sort()
|
||||
data.messagesSessionIdExpiryTime = 0
|
||||
login()
|
||||
}
|
||||
ERROR_LOGIN_LIBRUS_PORTAL_NO_CODE,
|
||||
ERROR_LOGIN_LIBRUS_PORTAL_CSRF_MISSING,
|
||||
ERROR_LOGIN_LIBRUS_PORTAL_CODE_REVOKED,
|
||||
ERROR_LOGIN_LIBRUS_PORTAL_CODE_EXPIRED -> {
|
||||
login()
|
||||
}
|
||||
ERROR_LOGIN_LIBRUS_PORTAL_NO_REFRESH,
|
||||
ERROR_LOGIN_LIBRUS_PORTAL_REFRESH_REVOKED,
|
||||
ERROR_LOGIN_LIBRUS_PORTAL_REFRESH_INVALID -> {
|
||||
data.portalRefreshToken = null
|
||||
login()
|
||||
}
|
||||
ERROR_LOGIN_LIBRUS_SYNERGIA_TOKEN_INVALID,
|
||||
ERROR_LOGIN_LIBRUS_SYNERGIA_NO_TOKEN,
|
||||
ERROR_LOGIN_LIBRUS_SYNERGIA_NO_SESSION_ID -> {
|
||||
login()
|
||||
}
|
||||
ERROR_LOGIN_LIBRUS_MESSAGES_NO_SESSION_ID -> {
|
||||
login()
|
||||
}
|
||||
// TODO PORTAL CAPTCHA
|
||||
ERROR_LIBRUS_API_TIMETABLE_NOT_PUBLIC,
|
||||
ERROR_LIBRUS_API_LUCKY_NUMBER_NOT_ACTIVE,
|
||||
ERROR_LIBRUS_API_NOTES_NOT_ACTIVE -> {
|
||||
data()
|
||||
CODE_INTERNAL_LIBRUS_ACCOUNT_410 -> {
|
||||
internalErrorList.add(apiError.errorCode)
|
||||
loginStore.removeLoginData("refreshToken") // force a clean login
|
||||
//loginLibrus()
|
||||
}
|
||||
else -> callback.onError(apiError)
|
||||
}
|
||||
|
@ -45,96 +45,92 @@ class LibrusData(val data: DataLibrus, val onSuccess: () -> Unit) {
|
||||
*/
|
||||
ENDPOINT_LIBRUS_API_ME -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_student_info)
|
||||
LibrusApiMe(data, onSuccess)
|
||||
LibrusApiMe(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_SCHOOLS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_school_info)
|
||||
LibrusApiSchools(data, onSuccess)
|
||||
LibrusApiSchools(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_CLASSES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_classes)
|
||||
LibrusApiClasses(data, onSuccess)
|
||||
LibrusApiClasses(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_VIRTUAL_CLASSES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_teams)
|
||||
LibrusApiVirtualClasses(data, onSuccess)
|
||||
LibrusApiVirtualClasses(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_UNITS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_units)
|
||||
LibrusApiUnits(data, onSuccess)
|
||||
LibrusApiUnits(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_USERS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_teachers)
|
||||
LibrusApiUsers(data, onSuccess)
|
||||
LibrusApiUsers(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_SUBJECTS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_subjects)
|
||||
LibrusApiSubjects(data, onSuccess)
|
||||
LibrusApiSubjects(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_CLASSROOMS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_classrooms)
|
||||
LibrusApiClassrooms(data, onSuccess)
|
||||
LibrusApiClassrooms(data) { onSuccess() }
|
||||
}
|
||||
// TODO push config
|
||||
// TODO timetable
|
||||
|
||||
ENDPOINT_LIBRUS_API_NORMAL_GRADES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_grades)
|
||||
LibrusApiGrades(data, onSuccess)
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_NORMAL_GC -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_grade_categories)
|
||||
LibrusApiGradeCategories(data, onSuccess)
|
||||
LibrusApiGrades(data) { onSuccess() }
|
||||
}
|
||||
// TODO grades
|
||||
|
||||
ENDPOINT_LIBRUS_API_EVENT_TYPES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_event_types)
|
||||
LibrusApiEventTypes(data, onSuccess)
|
||||
LibrusApiEventTypes(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_EVENTS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_events)
|
||||
LibrusApiEvents(data, onSuccess)
|
||||
LibrusApiEvents(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_HOMEWORK -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_homework)
|
||||
LibrusApiHomework(data, onSuccess)
|
||||
LibrusApiHomework(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_LUCKY_NUMBER -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_lucky_number)
|
||||
LibrusApiLuckyNumber(data, onSuccess)
|
||||
LibrusApiLuckyNumber(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_NOTICE_TYPES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_notice_types)
|
||||
LibrusApiNoticeTypes(data, onSuccess)
|
||||
LibrusApiNoticeTypes(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_NOTICES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_notices)
|
||||
LibrusApiNotices(data, onSuccess)
|
||||
LibrusApiNotices(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_ATTENDANCE_TYPES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_attendance_types)
|
||||
LibrusApiAttendanceTypes(data, onSuccess)
|
||||
LibrusApiAttendanceTypes(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_ATTENDANCES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_attendance)
|
||||
LibrusApiAttendances(data, onSuccess)
|
||||
LibrusApiAttendances(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_ANNOUNCEMENTS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_announcements)
|
||||
LibrusApiAnnouncements(data, onSuccess)
|
||||
LibrusApiAnnouncements(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_PT_MEETINGS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_pt_meetings)
|
||||
LibrusApiPtMeetings(data, onSuccess)
|
||||
LibrusApiPtMeetings(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_TEACHER_FREE_DAY_TYPES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_teacher_free_day_types)
|
||||
LibrusApiTeacherFreeDayTypes(data, onSuccess)
|
||||
LibrusApiTeacherFreeDayTypes(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_API_TEACHER_FREE_DAYS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_teacher_free_days)
|
||||
LibrusApiTeacherFreeDays(data, onSuccess)
|
||||
LibrusApiTeacherFreeDays(data) { onSuccess() }
|
||||
}
|
||||
|
||||
/**
|
||||
@ -142,11 +138,11 @@ class LibrusData(val data: DataLibrus, val onSuccess: () -> Unit) {
|
||||
*/
|
||||
ENDPOINT_LIBRUS_SYNERGIA_HOMEWORK -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_homework)
|
||||
LibrusSynergiaHomework(data, onSuccess)
|
||||
LibrusSynergiaHomework(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_SYNERGIA_INFO -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_student_info)
|
||||
LibrusSynergiaInfo(data, onSuccess)
|
||||
LibrusSynergiaInfo(data) { onSuccess() }
|
||||
}
|
||||
|
||||
/**
|
||||
@ -154,11 +150,11 @@ class LibrusData(val data: DataLibrus, val onSuccess: () -> Unit) {
|
||||
*/
|
||||
ENDPOINT_LIBRUS_MESSAGES_RECEIVED -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_inbox)
|
||||
LibrusMessagesGetList(data, type = Message.TYPE_RECEIVED, onSuccess = onSuccess)
|
||||
LibrusMessagesGetList(data, type = Message.TYPE_RECEIVED) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_LIBRUS_MESSAGES_SENT -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_outbox)
|
||||
LibrusMessagesGetList(data, type = Message.TYPE_SENT, onSuccess = onSuccess)
|
||||
LibrusMessagesGetList(data, type = Message.TYPE_SENT) { onSuccess() }
|
||||
}
|
||||
|
||||
else -> onSuccess()
|
||||
|
@ -12,17 +12,13 @@ import okhttp3.Cookie
|
||||
import org.jsoup.Jsoup
|
||||
import org.jsoup.nodes.Document
|
||||
import org.jsoup.parser.Parser
|
||||
import org.redundent.kotlin.xml.PrintOptions
|
||||
import org.redundent.kotlin.xml.xml
|
||||
import pl.szczodrzynski.edziennik.api.v2.*
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.DataLibrus
|
||||
import pl.szczodrzynski.edziennik.api.v2.models.ApiError
|
||||
import pl.szczodrzynski.edziennik.get
|
||||
import pl.szczodrzynski.edziennik.utils.Utils.d
|
||||
import java.io.StringWriter
|
||||
import javax.xml.parsers.DocumentBuilderFactory
|
||||
import javax.xml.transform.OutputKeys
|
||||
import javax.xml.transform.TransformerFactory
|
||||
import javax.xml.transform.dom.DOMSource
|
||||
import javax.xml.transform.stream.StreamResult
|
||||
|
||||
open class LibrusMessages(open val data: DataLibrus) {
|
||||
companion object {
|
||||
@ -84,27 +80,7 @@ open class LibrusMessages(open val data: DataLibrus) {
|
||||
.secure().httpOnly().build()
|
||||
))
|
||||
|
||||
|
||||
val docBuilder = DocumentBuilderFactory.newInstance().newDocumentBuilder()
|
||||
val doc = docBuilder.newDocument()
|
||||
val serviceElement = doc.createElement("service")
|
||||
val headerElement = doc.createElement("header")
|
||||
val dataElement = doc.createElement("data")
|
||||
for ((key, value) in parameters.orEmpty()) {
|
||||
val element = doc.createElement(key)
|
||||
element.appendChild(doc.createTextNode(value.toString()))
|
||||
dataElement.appendChild(element)
|
||||
}
|
||||
serviceElement.appendChild(headerElement)
|
||||
serviceElement.appendChild(dataElement)
|
||||
doc.appendChild(serviceElement)
|
||||
val transformer = TransformerFactory.newInstance().newTransformer()
|
||||
transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes")
|
||||
val stringWriter = StringWriter()
|
||||
transformer.transform(DOMSource(doc), StreamResult(stringWriter))
|
||||
val requestXml = stringWriter.toString()
|
||||
|
||||
/*val requestXml = xml("service") {
|
||||
val requestXml = xml("service") {
|
||||
"header" { }
|
||||
"data" {
|
||||
for ((key, value) in parameters.orEmpty()) {
|
||||
@ -116,7 +92,7 @@ open class LibrusMessages(open val data: DataLibrus) {
|
||||
}.toString(PrintOptions(
|
||||
singleLineTextElements = true,
|
||||
useSelfClosingTags = true
|
||||
))*/
|
||||
))
|
||||
|
||||
Request.builder()
|
||||
.url("$LIBRUS_MESSAGES_URL/$endpoint")
|
||||
|
@ -44,10 +44,7 @@ open class LibrusPortal(open val data: DataLibrus) {
|
||||
"Access token is invalid" -> ERROR_LIBRUS_PORTAL_ACCESS_DENIED
|
||||
"ApiDisabled" -> ERROR_LIBRUS_PORTAL_API_DISABLED
|
||||
"Account not found" -> ERROR_LIBRUS_PORTAL_SYNERGIA_NOT_FOUND
|
||||
else -> when (json.getString("hint")) {
|
||||
"Error while decoding to JSON" -> ERROR_LIBRUS_PORTAL_ACCESS_DENIED
|
||||
else -> ERROR_LIBRUS_PORTAL_OTHER
|
||||
}
|
||||
else -> ERROR_LIBRUS_PORTAL_OTHER
|
||||
}.let { errorCode ->
|
||||
data.error(ApiError(tag, errorCode)
|
||||
.withApiResponse(json)
|
||||
|
@ -1,48 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-5
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.api.v2.librus.data.api
|
||||
|
||||
import android.graphics.Color
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.DataLibrus
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.ENDPOINT_LIBRUS_API_NORMAL_GC
|
||||
import pl.szczodrzynski.edziennik.api.v2.librus.data.LibrusApi
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.api.SYNC_ALWAYS
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.grades.GradeCategory
|
||||
|
||||
class LibrusApiGradeCategories(override val data: DataLibrus,
|
||||
val onSuccess: () -> Unit) : LibrusApi(data) {
|
||||
companion object {
|
||||
const val TAG = "LibrusApiGradeCategories"
|
||||
}
|
||||
|
||||
init {
|
||||
apiGet(TAG, "Grades/Categories") { json ->
|
||||
json.getJsonArray("Categories")?.asJsonObjectList()?.forEach { category ->
|
||||
val id = category.getLong("Id") ?: return@forEach
|
||||
val name = category.getString("Name") ?: ""
|
||||
val weight = when (category.getBoolean("CountToTheAverage")) {
|
||||
true -> category.getFloat("Weight") ?: 0f
|
||||
else -> 0f
|
||||
}
|
||||
val color = category.getJsonObject("Color")?.getInt("Id")
|
||||
?.let { data.getColor(it) } ?: Color.BLUE
|
||||
|
||||
val gradeCategoryObject = GradeCategory(
|
||||
profileId,
|
||||
id,
|
||||
weight,
|
||||
color,
|
||||
name
|
||||
)
|
||||
|
||||
data.gradeCategories.put(id, gradeCategoryObject)
|
||||
}
|
||||
|
||||
data.setSyncNext(ENDPOINT_LIBRUS_API_NORMAL_GC, SYNC_ALWAYS)
|
||||
onSuccess()
|
||||
}
|
||||
}
|
||||
}
|
@ -42,7 +42,7 @@ class MobidziennikData(val data: DataMobidziennik, val onSuccess: () -> Unit) {
|
||||
when (endpointId) {
|
||||
ENDPOINT_MOBIDZIENNIK_API_MAIN -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_data)
|
||||
MobidziennikApi(data, onSuccess)
|
||||
MobidziennikApi(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_MOBIDZIENNIK_WEB_MESSAGES_INBOX -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_inbox)
|
||||
@ -75,4 +75,4 @@ class MobidziennikData(val data: DataMobidziennik, val onSuccess: () -> Unit) {
|
||||
else -> onSuccess()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -390,6 +390,8 @@ open class Data(val app: App, val profile: Profile?, val loginStore: LoginStore)
|
||||
}
|
||||
|
||||
fun error(apiError: ApiError) {
|
||||
if (apiError.isCritical)
|
||||
cancel()
|
||||
callback.onError(apiError)
|
||||
}
|
||||
|
||||
|
@ -38,39 +38,35 @@ class VulcanData(val data: DataVulcan, val onSuccess: () -> Unit) {
|
||||
when (endpointId) {
|
||||
ENDPOINT_VULCAN_API_DICTIONARIES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_dictionaries)
|
||||
VulcanApiDictionaries(data, onSuccess)
|
||||
VulcanApiDictionaries(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_VULCAN_API_GRADES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_grades)
|
||||
VulcanApiGrades(data, onSuccess)
|
||||
VulcanApiGrades(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_VULCAN_API_GRADES_SUMMARY -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_proposed_grades)
|
||||
VulcanApiProposedGrades(data, onSuccess)
|
||||
VulcanApiProposedGrades(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_VULCAN_API_EVENTS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_events)
|
||||
VulcanApiEvents(data, isHomework = false, onSuccess = onSuccess)
|
||||
VulcanApiEvents(data, isHomework = false) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_VULCAN_API_HOMEWORK -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_homework)
|
||||
VulcanApiEvents(data, isHomework = true, onSuccess = onSuccess)
|
||||
VulcanApiEvents(data, isHomework = true) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_VULCAN_API_NOTICES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_notices)
|
||||
VulcanApiNotices(data, onSuccess)
|
||||
VulcanApiNotices(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_VULCAN_API_ATTENDANCE -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_attendance)
|
||||
VulcanApiAttendance(data, onSuccess)
|
||||
VulcanApiAttendance(data) { onSuccess() }
|
||||
}
|
||||
ENDPOINT_VULCAN_API_MESSAGES_INBOX -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_inbox)
|
||||
VulcanApiMessagesInbox(data, onSuccess)
|
||||
}
|
||||
ENDPOINT_VULCAN_API_MESSAGES_SENT -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_outbox)
|
||||
VulcanApiMessagesSent(data, onSuccess)
|
||||
VulcanApiMessagesInbox(data) { onSuccess() }
|
||||
}
|
||||
else -> onSuccess()
|
||||
}
|
||||
|
@ -11,7 +11,6 @@ import pl.szczodrzynski.edziennik.api.v2.vulcan.ENDPOINT_VULCAN_API_MESSAGES_INB
|
||||
import pl.szczodrzynski.edziennik.api.v2.vulcan.data.VulcanApi
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.api.SYNC_ALWAYS
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.messages.Message
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.messages.Message.TYPE_RECEIVED
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.messages.MessageRecipient
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
@ -21,68 +20,64 @@ class VulcanApiMessagesInbox(override val data: DataVulcan, val onSuccess: () ->
|
||||
const val TAG = "VulcanApiMessagesInbox"
|
||||
}
|
||||
|
||||
init {
|
||||
data.profile?.also { profile ->
|
||||
init { data.profile?.also { profile ->
|
||||
|
||||
val startDate: String = when (profile.empty) {
|
||||
true -> profile.getSemesterStart(profile.currentSemester).stringY_m_d
|
||||
else -> Date.getToday().stepForward(0, -1, 0).stringY_m_d
|
||||
val startDate: String = when (profile.empty) {
|
||||
true -> profile.getSemesterStart(profile.currentSemester).stringY_m_d
|
||||
else -> Date.getToday().stepForward(0, -1, 0).stringY_m_d
|
||||
}
|
||||
val endDate: String = profile.getSemesterEnd(profile.currentSemester).stringY_m_d
|
||||
|
||||
apiGet(TAG, VULCAN_API_ENDPOINT_MESSAGES_RECEIVED, parameters = mapOf(
|
||||
"DataPoczatkowa" to startDate,
|
||||
"DataKoncowa" to endDate,
|
||||
"LoginId" to data.studentLoginId,
|
||||
"IdUczen" to data.studentId
|
||||
)) { json, _ ->
|
||||
json.getJsonArray("Data").asJsonObjectList()?.forEach { message ->
|
||||
val id = message.getLong("WiadomoscId") ?: return@forEach
|
||||
val subject = message.getString("Tytul") ?: ""
|
||||
val body = message.getString("Tresc") ?: ""
|
||||
|
||||
val senderLoginId = message.getString("NadawcaId") ?: return@forEach
|
||||
val senderId = data.teacherList
|
||||
.singleOrNull { it.loginId == senderLoginId }?.id ?: return@forEach
|
||||
|
||||
val addedDate = message.getLong("DataWyslaniaUnixEpoch")?.let { it * 1000 } ?: -1
|
||||
val readDate = message.getLong("DataPrzeczytaniaUnixEpoch")?.let { it * 1000 } ?: -1
|
||||
|
||||
val messageObject = Message(
|
||||
profileId,
|
||||
id,
|
||||
subject,
|
||||
body,
|
||||
Message.TYPE_RECEIVED,
|
||||
senderId,
|
||||
-1
|
||||
)
|
||||
|
||||
val messageRecipientObject = MessageRecipient(
|
||||
profileId,
|
||||
-1,
|
||||
-1,
|
||||
readDate,
|
||||
id
|
||||
)
|
||||
|
||||
data.messageList.add(messageObject)
|
||||
data.messageRecipientList.add(messageRecipientObject)
|
||||
data.metadataList.add(Metadata(
|
||||
profileId,
|
||||
Metadata.TYPE_MESSAGE,
|
||||
id,
|
||||
readDate > 0,
|
||||
readDate > 0,
|
||||
addedDate
|
||||
))
|
||||
}
|
||||
val endDate: String = profile.getSemesterEnd(profile.currentSemester).stringY_m_d
|
||||
|
||||
apiGet(TAG, VULCAN_API_ENDPOINT_MESSAGES_RECEIVED, parameters = mapOf(
|
||||
"DataPoczatkowa" to startDate,
|
||||
"DataKoncowa" to endDate,
|
||||
"LoginId" to data.studentLoginId,
|
||||
"IdUczen" to data.studentId
|
||||
)) { json, _ ->
|
||||
json.getJsonArray("Data").asJsonObjectList()?.forEach { message ->
|
||||
val id = message.getLong("WiadomoscId") ?: return@forEach
|
||||
val subject = message.getString("Tytul") ?: ""
|
||||
val body = message.getString("Tresc") ?: ""
|
||||
|
||||
val senderLoginId = message.getString("NadawcaId") ?: return@forEach
|
||||
val senderId = data.teacherList
|
||||
.singleOrNull { it.loginId == senderLoginId }?.id ?: return@forEach
|
||||
|
||||
val sentDate = message.getLong("DataWyslaniaUnixEpoch")?.let { it * 1000 }
|
||||
?: -1
|
||||
val readDate = message.getLong("DataPrzeczytaniaUnixEpoch")?.let { it * 1000 }
|
||||
?: -1
|
||||
|
||||
val messageObject = Message(
|
||||
profileId,
|
||||
id,
|
||||
subject,
|
||||
body,
|
||||
TYPE_RECEIVED,
|
||||
senderId,
|
||||
-1
|
||||
)
|
||||
|
||||
val messageRecipientObject = MessageRecipient(
|
||||
profileId,
|
||||
-1,
|
||||
-1,
|
||||
readDate,
|
||||
id
|
||||
)
|
||||
|
||||
data.messageList.add(messageObject)
|
||||
data.messageRecipientList.add(messageRecipientObject)
|
||||
data.metadataList.add(Metadata(
|
||||
profileId,
|
||||
Metadata.TYPE_MESSAGE,
|
||||
id,
|
||||
readDate > 0,
|
||||
readDate > 0,
|
||||
sentDate
|
||||
))
|
||||
}
|
||||
|
||||
data.setSyncNext(ENDPOINT_VULCAN_API_MESSAGES_INBOX, SYNC_ALWAYS)
|
||||
onSuccess()
|
||||
}
|
||||
} ?: onSuccess()
|
||||
}
|
||||
data.setSyncNext(ENDPOINT_VULCAN_API_MESSAGES_INBOX, SYNC_ALWAYS)
|
||||
onSuccess()
|
||||
}
|
||||
} ?: onSuccess()}
|
||||
}
|
||||
|
@ -1,99 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-5
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.api.v2.vulcan.data.api
|
||||
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.MainActivity.Companion.DRAWER_ITEM_MESSAGES
|
||||
import pl.szczodrzynski.edziennik.api.v2.VULCAN_API_ENDPOINT_MESSAGES_SENT
|
||||
import pl.szczodrzynski.edziennik.api.v2.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.api.v2.vulcan.ENDPOINT_VULCAN_API_MESSAGES_SENT
|
||||
import pl.szczodrzynski.edziennik.api.v2.vulcan.data.VulcanApi
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.messages.Message
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.messages.Message.TYPE_SENT
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.messages.MessageRecipient
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
|
||||
class VulcanApiMessagesSent(override val data: DataVulcan, val onSuccess: () -> Unit) : VulcanApi(data) {
|
||||
companion object {
|
||||
const val TAG = "VulcanApiMessagesSent"
|
||||
}
|
||||
|
||||
init {
|
||||
data.profile?.also { profile ->
|
||||
val startDate: String = when (profile.empty) {
|
||||
true -> profile.getSemesterStart(profile.currentSemester).stringY_m_d
|
||||
else -> Date.getToday().stepForward(0, -1, 0).stringY_m_d
|
||||
}
|
||||
val endDate: String = profile.getSemesterEnd(profile.currentSemester).stringY_m_d
|
||||
|
||||
apiGet(TAG, VULCAN_API_ENDPOINT_MESSAGES_SENT, parameters = mapOf(
|
||||
"DataPoczatkowa" to startDate,
|
||||
"DataKoncowa" to endDate,
|
||||
"LoginId" to data.studentLoginId,
|
||||
"IdUczen" to data.studentId
|
||||
)) { json, _ ->
|
||||
json.getJsonArray("Data")?.asJsonObjectList()?.forEach { message ->
|
||||
val id = message.getLong("WiadomoscId") ?: return@forEach
|
||||
val subject = message.getString("Tytul") ?: ""
|
||||
val body = message.getString("Tresc") ?: ""
|
||||
val readBy = message.getInt("Przeczytane") ?: 0
|
||||
val unreadBy = message.getInt("Nieprzeczytane") ?: 0
|
||||
val sentDate = message.getLong("DataWyslaniaUnixEpoch")?.let { it * 1000 } ?: -1
|
||||
|
||||
val messageObject = Message(
|
||||
profileId,
|
||||
id,
|
||||
subject,
|
||||
body,
|
||||
TYPE_SENT,
|
||||
-1,
|
||||
-1
|
||||
)
|
||||
|
||||
message.getJsonArray("Adresaci")?.asJsonObjectList()
|
||||
?.forEachIndexed { _, recipient ->
|
||||
|
||||
val recipientLoginId = recipient.getString("LoginId")
|
||||
?: return@forEachIndexed
|
||||
val recipientId = data.teacherList.singleOrNull { it.loginId == recipientLoginId }?.id
|
||||
?: return@forEachIndexed
|
||||
|
||||
val readDate: Long = when (readBy) {
|
||||
0 -> 0
|
||||
else -> when (unreadBy) {
|
||||
0 -> 1
|
||||
else -> -1
|
||||
}
|
||||
}
|
||||
|
||||
val messageRecipientObject = MessageRecipient(
|
||||
profileId,
|
||||
recipientId,
|
||||
-1,
|
||||
readDate,
|
||||
id
|
||||
)
|
||||
|
||||
data.messageRecipientList.add(messageRecipientObject)
|
||||
}
|
||||
|
||||
data.messageList.add(messageObject)
|
||||
data.metadataList.add(Metadata(
|
||||
profileId,
|
||||
Metadata.TYPE_MESSAGE,
|
||||
id,
|
||||
true,
|
||||
true,
|
||||
sentDate
|
||||
))
|
||||
}
|
||||
|
||||
data.setSyncNext(ENDPOINT_VULCAN_API_MESSAGES_SENT, 1 * DAY, DRAWER_ITEM_MESSAGES)
|
||||
onSuccess()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -6,6 +6,8 @@ package pl.szczodrzynski.edziennik.api.v2.vulcan.data.api
|
||||
|
||||
import pl.szczodrzynski.edziennik.api.v2.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.api.v2.vulcan.data.VulcanApi
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.api.SYNC_ALWAYS
|
||||
import pl.szczodrzynski.edziennik.getJsonArray
|
||||
|
||||
class VulcanApiTemplate(override val data: DataVulcan, val onSuccess: () -> Unit) : VulcanApi(data) {
|
||||
companion object {
|
||||
@ -13,12 +15,10 @@ class VulcanApiTemplate(override val data: DataVulcan, val onSuccess: () -> Unit
|
||||
}
|
||||
|
||||
init {
|
||||
/* data.profile?.also { profile ->
|
||||
apiGet(TAG, VULCAN_API_ENDPOINT_) { json, _ ->
|
||||
/* apiGet(TAG, VULCAN_API_ENDPOINT_) { json, _ ->
|
||||
|
||||
data.setSyncNext(ENDPOINT_VULCAN_API_, SYNC_ALWAYS)
|
||||
onSuccess()
|
||||
}
|
||||
data.setSyncNext(ENDPOINT_VULCAN_API_, SYNC_ALWAYS)
|
||||
onSuccess()
|
||||
} */
|
||||
}
|
||||
}
|
||||
|
@ -10,6 +10,8 @@ import androidx.room.TypeConverters;
|
||||
import androidx.room.migration.Migration;
|
||||
import androidx.sqlite.db.SupportSQLiteDatabase;
|
||||
|
||||
import javax.inject.Singleton;
|
||||
|
||||
import pl.szczodrzynski.edziennik.data.db.converters.ConverterDate;
|
||||
import pl.szczodrzynski.edziennik.data.db.converters.ConverterDateInt;
|
||||
import pl.szczodrzynski.edziennik.data.db.converters.ConverterJsonObject;
|
||||
@ -74,6 +76,7 @@ import pl.szczodrzynski.edziennik.data.db.modules.teams.Team;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.teams.TeamDao;
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date;
|
||||
|
||||
@Singleton
|
||||
@Database(entities = {
|
||||
Grade.class,
|
||||
//GradeCategory.class,
|
||||
@ -114,33 +117,60 @@ import pl.szczodrzynski.edziennik.utils.models.Date;
|
||||
public abstract class AppDb extends RoomDatabase {
|
||||
|
||||
public abstract GradeDao gradeDao();
|
||||
|
||||
//public abstract GradeCategoryDao gradeCategoryDao();
|
||||
public abstract TeacherDao teacherDao();
|
||||
|
||||
public abstract TeacherAbsenceDao teacherAbsenceDao();
|
||||
|
||||
public abstract TeacherAbsenceTypeDao teacherAbsenceTypeDao();
|
||||
|
||||
public abstract SubjectDao subjectDao();
|
||||
|
||||
public abstract NoticeDao noticeDao();
|
||||
|
||||
public abstract LessonDao lessonDao();
|
||||
|
||||
public abstract LessonChangeDao lessonChangeDao();
|
||||
|
||||
public abstract TeamDao teamDao();
|
||||
|
||||
public abstract AttendanceDao attendanceDao();
|
||||
|
||||
public abstract EventDao eventDao();
|
||||
|
||||
public abstract EventTypeDao eventTypeDao();
|
||||
|
||||
public abstract LoginStoreDao loginStoreDao();
|
||||
|
||||
public abstract ProfileDao profileDao();
|
||||
|
||||
public abstract LuckyNumberDao luckyNumberDao();
|
||||
|
||||
public abstract AnnouncementDao announcementDao();
|
||||
|
||||
public abstract GradeCategoryDao gradeCategoryDao();
|
||||
|
||||
public abstract FeedbackMessageDao feedbackMessageDao();
|
||||
|
||||
public abstract MessageDao messageDao();
|
||||
|
||||
public abstract MessageRecipientDao messageRecipientDao();
|
||||
|
||||
public abstract DebugLogDao debugLogDao();
|
||||
|
||||
public abstract EndpointTimerDao endpointTimerDao();
|
||||
|
||||
public abstract LessonRangeDao lessonRangeDao();
|
||||
|
||||
public abstract NotificationDao notificationDao();
|
||||
|
||||
public abstract ClassroomDao classroomDao();
|
||||
|
||||
public abstract NoticeTypeDao noticeTypeDao();
|
||||
|
||||
public abstract AttendanceTypeDao attendanceTypeDao();
|
||||
|
||||
public abstract MetadataDao metadataDao();
|
||||
|
||||
private static volatile AppDb INSTANCE;
|
||||
|
@ -0,0 +1,26 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.data.db
|
||||
|
||||
import android.content.Context
|
||||
import dagger.Module
|
||||
import dagger.Provides
|
||||
import javax.inject.Singleton
|
||||
|
||||
@Module
|
||||
internal class DatabaseModule {
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
fun provideDatabase(context: Context) = AppDb.getDatabase(context)
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
fun provideEventDao(database: AppDb) = database.eventDao()
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
fun provideMetadataDao(database: AppDb) = database.metadataDao()
|
||||
}
|
@ -1,19 +1,22 @@
|
||||
package pl.szczodrzynski.edziennik.data.db.modules.events;
|
||||
|
||||
import android.util.Log;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.lifecycle.LiveData;
|
||||
import androidx.sqlite.db.SimpleSQLiteQuery;
|
||||
import androidx.sqlite.db.SupportSQLiteQuery;
|
||||
import androidx.room.Dao;
|
||||
import androidx.room.Insert;
|
||||
import androidx.room.OnConflictStrategy;
|
||||
import androidx.room.Query;
|
||||
import androidx.room.RawQuery;
|
||||
import androidx.room.Transaction;
|
||||
import androidx.annotation.NonNull;
|
||||
import android.util.Log;
|
||||
import androidx.sqlite.db.SimpleSQLiteQuery;
|
||||
import androidx.sqlite.db.SupportSQLiteQuery;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import javax.inject.Singleton;
|
||||
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date;
|
||||
import pl.szczodrzynski.edziennik.utils.models.Time;
|
||||
|
||||
@ -21,6 +24,7 @@ import static pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata.TYPE_
|
||||
import static pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata.TYPE_HOMEWORK;
|
||||
import static pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata.TYPE_LESSON_CHANGE;
|
||||
|
||||
@Singleton
|
||||
@Dao
|
||||
public abstract class EventDao {
|
||||
@Insert(onConflict = OnConflictStrategy.REPLACE)
|
||||
@ -34,26 +38,32 @@ public abstract class EventDao {
|
||||
|
||||
@Query("DELETE FROM events WHERE profileId = :profileId AND eventId = :id")
|
||||
public abstract void remove(int profileId, long id);
|
||||
|
||||
@Query("DELETE FROM metadata WHERE profileId = :profileId AND thingType = :thingType AND thingId = :thingId")
|
||||
public abstract void removeMetadata(int profileId, int thingType, long thingId);
|
||||
|
||||
@Transaction
|
||||
public void remove(int profileId, int type, long id) {
|
||||
remove(profileId, id);
|
||||
removeMetadata(profileId, type == Event.TYPE_HOMEWORK ? TYPE_HOMEWORK : TYPE_EVENT, id);
|
||||
}
|
||||
|
||||
@Transaction
|
||||
public void remove(Event event) {
|
||||
remove(event.profileId, event.type, event.id);
|
||||
}
|
||||
|
||||
@Transaction
|
||||
public void remove(int profileId, Event event) {
|
||||
remove(profileId, event.type, event.id);
|
||||
}
|
||||
|
||||
@Query("DELETE FROM events WHERE teamId = :teamId AND eventId = :id")
|
||||
public abstract void removeByTeamId(long teamId, long id);
|
||||
|
||||
@RawQuery(observedEntities = {Event.class})
|
||||
abstract LiveData<List<EventFull>> getAll(SupportSQLiteQuery query);
|
||||
|
||||
public LiveData<List<EventFull>> getAll(int profileId, String filter) {
|
||||
String query = "SELECT \n" +
|
||||
"*, \n" +
|
||||
@ -71,24 +81,31 @@ public abstract class EventDao {
|
||||
Log.d("DB", query);
|
||||
return getAll(new SimpleSQLiteQuery(query));
|
||||
}
|
||||
|
||||
public LiveData<List<EventFull>> getAll(int profileId) {
|
||||
return getAll(profileId, "1");
|
||||
}
|
||||
|
||||
public List<EventFull> getAllNow(int profileId) {
|
||||
return getAllNow(profileId, "1");
|
||||
}
|
||||
|
||||
public LiveData<List<EventFull>> getAllWhere(int profileId, String filter) {
|
||||
return getAll(profileId, filter);
|
||||
}
|
||||
|
||||
public LiveData<List<EventFull>> getAllByType(int profileId, int type, String filter) {
|
||||
return getAll(profileId, "eventType = "+type+" AND "+filter);
|
||||
}
|
||||
|
||||
public LiveData<List<EventFull>> getAllByDate(int profileId, @NonNull Date date) {
|
||||
return getAll(profileId, "eventDate = '"+date.getStringY_m_d()+"'");
|
||||
}
|
||||
|
||||
public List<EventFull> getAllByDateNow(int profileId, @NonNull Date date) {
|
||||
return getAllNow(profileId, "eventDate = '"+date.getStringY_m_d()+"'");
|
||||
}
|
||||
|
||||
public LiveData<List<EventFull>> getAllByDateTime(int profileId, @NonNull Date date, Time time) {
|
||||
if (time == null)
|
||||
return getAllByDate(profileId, date);
|
||||
@ -97,6 +114,7 @@ public abstract class EventDao {
|
||||
|
||||
@RawQuery
|
||||
abstract List<EventFull> getAllNow(SupportSQLiteQuery query);
|
||||
|
||||
public List<EventFull> getAllNow(int profileId, String filter) {
|
||||
return getAllNow(new SimpleSQLiteQuery("SELECT \n" +
|
||||
"*, \n" +
|
||||
@ -112,6 +130,7 @@ public abstract class EventDao {
|
||||
"WHERE events.profileId = "+profileId+" AND events.eventBlacklisted = 0 AND "+filter+"\n" +
|
||||
"ORDER BY eventStartTime, addedDate ASC"));
|
||||
}
|
||||
|
||||
public List<EventFull> getNotNotifiedNow(int profileId) {
|
||||
return getAllNow(profileId, "notified = 0");
|
||||
}
|
||||
|
@ -8,7 +8,6 @@ import androidx.room.Entity;
|
||||
import androidx.room.Ignore;
|
||||
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonNull;
|
||||
import com.google.gson.JsonObject;
|
||||
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.profiles.ProfileFull;
|
||||
@ -74,7 +73,7 @@ public class LoginStore {
|
||||
if (data == null)
|
||||
return defaultValue;
|
||||
JsonElement element = data.get(key);
|
||||
if (element != null && !(element instanceof JsonNull)) {
|
||||
if (element != null) {
|
||||
return element.getAsString();
|
||||
}
|
||||
return defaultValue;
|
||||
@ -84,7 +83,7 @@ public class LoginStore {
|
||||
if (data == null)
|
||||
return defaultValue;
|
||||
JsonElement element = data.get(key);
|
||||
if (element != null && !(element instanceof JsonNull)) {
|
||||
if (element != null) {
|
||||
return element.getAsInt();
|
||||
}
|
||||
return defaultValue;
|
||||
@ -94,7 +93,7 @@ public class LoginStore {
|
||||
if (data == null)
|
||||
return defaultValue;
|
||||
JsonElement element = data.get(key);
|
||||
if (element != null && !(element instanceof JsonNull)) {
|
||||
if (element != null) {
|
||||
return element.getAsLong();
|
||||
}
|
||||
return defaultValue;
|
||||
@ -104,7 +103,7 @@ public class LoginStore {
|
||||
if (data == null)
|
||||
return defaultValue;
|
||||
JsonElement element = data.get(key);
|
||||
if (element != null && !(element instanceof JsonNull)) {
|
||||
if (element != null) {
|
||||
return element.getAsFloat();
|
||||
}
|
||||
return defaultValue;
|
||||
@ -113,7 +112,7 @@ public class LoginStore {
|
||||
if (data == null)
|
||||
return defaultValue;
|
||||
JsonElement element = data.get(key);
|
||||
if (element != null && !(element instanceof JsonNull)) {
|
||||
if (element != null) {
|
||||
return element.getAsBoolean();
|
||||
}
|
||||
return defaultValue;
|
||||
|
@ -9,7 +9,8 @@ import androidx.room.Transaction;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.notices.Notice;
|
||||
import javax.inject.Singleton;
|
||||
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.announcements.Announcement;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.attendance.Attendance;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.Event;
|
||||
@ -17,6 +18,7 @@ import pl.szczodrzynski.edziennik.data.db.modules.grades.Grade;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.lessons.LessonChange;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.lessons.LessonFull;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.messages.Message;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.notices.Notice;
|
||||
import pl.szczodrzynski.edziennik.utils.models.UnreadCounter;
|
||||
|
||||
import static pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata.TYPE_ANNOUNCEMENT;
|
||||
@ -28,6 +30,7 @@ import static pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata.TYPE_
|
||||
import static pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata.TYPE_MESSAGE;
|
||||
import static pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata.TYPE_NOTICE;
|
||||
|
||||
@Singleton
|
||||
@Dao
|
||||
public abstract class MetadataDao {
|
||||
@Insert(onConflict = OnConflictStrategy.IGNORE)
|
||||
@ -43,7 +46,6 @@ public abstract class MetadataDao {
|
||||
abstract void updateNotified(int profileId, int thingType, long thingId, boolean notified);
|
||||
|
||||
|
||||
|
||||
@Transaction
|
||||
public void setSeen(List<Metadata> metadataList) {
|
||||
for (Metadata metadata: metadataList) {
|
||||
@ -152,7 +154,6 @@ public abstract class MetadataDao {
|
||||
}
|
||||
|
||||
|
||||
|
||||
@Query("UPDATE metadata SET seen = :seen WHERE profileId = :profileId AND thingType = :thingType")
|
||||
public abstract void setAllSeen(int profileId, int thingType, boolean seen);
|
||||
|
||||
@ -166,7 +167,6 @@ public abstract class MetadataDao {
|
||||
public abstract void setAllNotified(int profileId, boolean notified);
|
||||
|
||||
|
||||
|
||||
@Query("SELECT count() FROM metadata WHERE profileId = :profileId AND thingType = :thingType AND seen = 0")
|
||||
public abstract LiveData<Integer> countUnseen(int profileId, int thingType);
|
||||
|
||||
@ -183,7 +183,6 @@ public abstract class MetadataDao {
|
||||
public abstract LiveData<Integer> countUnseen();
|
||||
|
||||
|
||||
|
||||
@Query("DELETE FROM metadata WHERE profileId = :profileId AND thingType = :thingType AND thingId = :thingId")
|
||||
public abstract void delete(int profileId, int thingType, long thingId);
|
||||
|
||||
@ -191,12 +190,10 @@ public abstract class MetadataDao {
|
||||
public abstract void deleteAll(int profileId);
|
||||
|
||||
|
||||
|
||||
@Query("SELECT profileId, thingType, COUNT(thingId) AS count FROM metadata WHERE seen = 0 GROUP BY profileId, thingType")
|
||||
public abstract LiveData<List<UnreadCounter>> getUnreadCounts();
|
||||
|
||||
|
||||
|
||||
@Query("DELETE FROM metadata WHERE profileId = :profileId AND thingType = "+TYPE_GRADE+" AND thingId NOT IN (SELECT gradeId FROM grades WHERE profileId = :profileId);")
|
||||
public abstract void deleteUnusedGrades(int profileId);
|
||||
|
||||
|
@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.di
|
||||
|
||||
import dagger.Component
|
||||
import dagger.android.AndroidInjector
|
||||
import dagger.android.support.AndroidSupportInjectionModule
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.data.db.DatabaseModule
|
||||
import javax.inject.Singleton
|
||||
|
||||
@Singleton
|
||||
@Component(modules = [
|
||||
AndroidSupportInjectionModule::class,
|
||||
BindingModule::class,
|
||||
AppModule::class,
|
||||
DatabaseModule::class
|
||||
])
|
||||
interface AppComponent : AndroidInjector<App> {
|
||||
|
||||
@Component.Factory
|
||||
interface Factory : AndroidInjector.Factory<App>
|
||||
}
|
19
app/src/main/java/pl/szczodrzynski/edziennik/di/AppModule.kt
Normal file
19
app/src/main/java/pl/szczodrzynski/edziennik/di/AppModule.kt
Normal file
@ -0,0 +1,19 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.di
|
||||
|
||||
import android.content.Context
|
||||
import dagger.Module
|
||||
import dagger.Provides
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import javax.inject.Singleton
|
||||
|
||||
@Module
|
||||
internal class AppModule {
|
||||
|
||||
@Singleton
|
||||
@Provides
|
||||
fun provideContext(app: App): Context = app
|
||||
}
|
@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.di
|
||||
|
||||
import dagger.Module
|
||||
import dagger.android.ContributesAndroidInjector
|
||||
import pl.szczodrzynski.edziennik.MainActivity
|
||||
import pl.szczodrzynski.edziennik.di.scopes.PerActivity
|
||||
import pl.szczodrzynski.edziennik.di.scopes.PerFragment
|
||||
import pl.szczodrzynski.edziennik.ui.modules.homework.HomeworkFragment
|
||||
import pl.szczodrzynski.edziennik.ui.modules.homework.list.HomeworkListFragment
|
||||
|
||||
@Module
|
||||
@Suppress("unused")
|
||||
internal abstract class BindingModule {
|
||||
|
||||
/**
|
||||
* ACTIVITIES
|
||||
*/
|
||||
|
||||
@PerActivity
|
||||
@ContributesAndroidInjector
|
||||
abstract fun bindMainActivity(): MainActivity
|
||||
|
||||
/**
|
||||
* FRAGMENTS
|
||||
*/
|
||||
|
||||
@PerFragment
|
||||
@ContributesAndroidInjector
|
||||
abstract fun bindHomeworkFragment(): HomeworkFragment
|
||||
|
||||
@PerFragment
|
||||
@ContributesAndroidInjector
|
||||
abstract fun bindHomeworkListFragment(): HomeworkListFragment
|
||||
}
|
@ -0,0 +1,11 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.di.scopes
|
||||
|
||||
import javax.inject.Scope
|
||||
|
||||
@Scope
|
||||
@Retention(AnnotationRetention.RUNTIME)
|
||||
annotation class PerActivity
|
@ -0,0 +1,11 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.di.scopes
|
||||
|
||||
import javax.inject.Scope
|
||||
|
||||
@Scope
|
||||
@Retention(AnnotationRetention.RUNTIME)
|
||||
annotation class PerFragment
|
@ -0,0 +1,22 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.base
|
||||
|
||||
import android.widget.Toast
|
||||
import dagger.android.support.DaggerFragment
|
||||
|
||||
abstract class BaseFragment<T : BasePresenter<out BaseView>> : DaggerFragment(), BaseView {
|
||||
|
||||
abstract var presenter: T
|
||||
|
||||
override fun showMessage(text: String) {
|
||||
Toast.makeText(activity, text, Toast.LENGTH_SHORT).show()
|
||||
}
|
||||
|
||||
override fun onDestroy() {
|
||||
super.onDestroy()
|
||||
presenter.onDetachView()
|
||||
}
|
||||
}
|
@ -0,0 +1,18 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.base
|
||||
|
||||
open class BasePresenter<T : BaseView> {
|
||||
|
||||
var view: T? = null
|
||||
|
||||
open fun onAttachView(view: T) {
|
||||
this.view = view
|
||||
}
|
||||
|
||||
open fun onDetachView() {
|
||||
view = null
|
||||
}
|
||||
}
|
@ -0,0 +1,10 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.base
|
||||
|
||||
interface BaseView {
|
||||
|
||||
fun showMessage(text: String)
|
||||
}
|
@ -30,7 +30,6 @@ import androidx.fragment.app.Fragment;
|
||||
import androidx.work.WorkManager;
|
||||
|
||||
import com.afollestad.materialdialogs.MaterialDialog;
|
||||
import com.chuckerteam.chucker.api.Chucker;
|
||||
import com.mikepenz.iconics.IconicsColor;
|
||||
import com.mikepenz.iconics.IconicsDrawable;
|
||||
import com.mikepenz.iconics.IconicsSize;
|
||||
@ -51,7 +50,6 @@ import pl.szczodrzynski.edziennik.databinding.CardLuckyNumberBinding;
|
||||
import pl.szczodrzynski.edziennik.databinding.CardUpdateBinding;
|
||||
import pl.szczodrzynski.edziennik.databinding.FragmentHomeBinding;
|
||||
import pl.szczodrzynski.edziennik.receivers.BootReceiver;
|
||||
import pl.szczodrzynski.edziennik.ui.modules.login.LoginLibrusCaptchaActivity;
|
||||
import pl.szczodrzynski.edziennik.ui.modules.messages.MessagesComposeActivity;
|
||||
import pl.szczodrzynski.edziennik.utils.Colors;
|
||||
import pl.szczodrzynski.edziennik.utils.Themes;
|
||||
@ -106,14 +104,6 @@ public class HomeFragment extends Fragment {
|
||||
|
||||
b.pruneWorkButton.setOnClickListener((v -> WorkManager.getInstance(app).pruneWork()));
|
||||
|
||||
b.runChucker.setOnClickListener((v -> {
|
||||
startActivity(Chucker.getLaunchIntent(activity, 1));
|
||||
}));
|
||||
|
||||
b.librusCaptchaButton.setOnClickListener((v -> {
|
||||
startActivity(new Intent(activity, LoginLibrusCaptchaActivity.class));
|
||||
}));
|
||||
|
||||
//((TextView)v.findViewById(R.id.nextSync)).setText(getString(R.string.next_sync_format,Time.fromMillis(app.appJobs.syncJobTime).getStringHMS()));
|
||||
|
||||
|
||||
|
@ -1,132 +0,0 @@
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.PorterDuff;
|
||||
import android.graphics.PorterDuffColorFilter;
|
||||
import android.os.AsyncTask;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.cardview.widget.CardView;
|
||||
import androidx.recyclerview.widget.RecyclerView;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.Button;
|
||||
import android.widget.TextView;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import pl.szczodrzynski.edziennik.App;
|
||||
import pl.szczodrzynski.edziennik.R;
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.EventFull;
|
||||
import pl.szczodrzynski.edziennik.ui.dialogs.event.EventManualDialog;
|
||||
import pl.szczodrzynski.edziennik.ui.modules.home.HomeFragment;
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date;
|
||||
|
||||
import static pl.szczodrzynski.edziennik.utils.Utils.bs;
|
||||
|
||||
public class HomeworkAdapter extends RecyclerView.Adapter<HomeworkAdapter.ViewHolder> {
|
||||
private Context context;
|
||||
private List<EventFull> homeworkList;
|
||||
|
||||
//getting the context and product list with constructor
|
||||
public HomeworkAdapter(Context mCtx, List<EventFull> homeworkList) {
|
||||
this.context = mCtx;
|
||||
this.homeworkList = homeworkList;
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
|
||||
//inflating and returning our view holder
|
||||
LayoutInflater inflater = LayoutInflater.from(context);
|
||||
View view = inflater.inflate(R.layout.row_homework_item, parent, false);
|
||||
return new ViewHolder(view);
|
||||
}
|
||||
|
||||
public static String dayDiffString(Context context, int dayDiff) {
|
||||
if (dayDiff > 0) {
|
||||
if (dayDiff == 1) {
|
||||
return context.getString(R.string.tomorrow);
|
||||
}
|
||||
else if (dayDiff == 2) {
|
||||
return context.getString(R.string.the_day_after);
|
||||
}
|
||||
return HomeFragment.plural(context, R.plurals.time_till_days, Math.abs(dayDiff));
|
||||
}
|
||||
else if (dayDiff < 0) {
|
||||
if (dayDiff == -1) {
|
||||
return context.getString(R.string.yesterday);
|
||||
}
|
||||
else if (dayDiff == -2) {
|
||||
return context.getString(R.string.the_day_before);
|
||||
}
|
||||
return context.getString(R.string.ago_format, HomeFragment.plural(context, R.plurals.time_till_days, Math.abs(dayDiff)));
|
||||
}
|
||||
return context.getString(R.string.today);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
|
||||
App app = (App) context.getApplicationContext();
|
||||
|
||||
EventFull homework = homeworkList.get(position);
|
||||
|
||||
int diffDays = Date.diffDays(homework.eventDate, Date.getToday());
|
||||
|
||||
holder.homeworkItemHomeworkDate.setText(app.getString(R.string.date_relative_format, homework.eventDate.getFormattedString(), dayDiffString(context, diffDays)));
|
||||
holder.homeworkItemTopic.setText(homework.topic);
|
||||
holder.homeworkItemSubjectTeacher.setText(context.getString(R.string.homework_subject_teacher_format, bs(homework.subjectLongName), bs(homework.teacherFullName)));
|
||||
holder.homeworkItemTeamDate.setText(context.getString(R.string.homework_team_date_format, bs(homework.teamName), Date.fromMillis(homework.addedDate).getFormattedStringShort()));
|
||||
|
||||
if (!homework.seen) {
|
||||
holder.homeworkItemTopic.setBackground(context.getResources().getDrawable(R.drawable.bg_rounded_8dp));
|
||||
holder.homeworkItemTopic.getBackground().setColorFilter(new PorterDuffColorFilter(0x692196f3, PorterDuff.Mode.MULTIPLY));
|
||||
homework.seen = true;
|
||||
AsyncTask.execute(() -> {
|
||||
app.db.metadataDao().setSeen(App.profileId, homework, true);
|
||||
});
|
||||
}
|
||||
else {
|
||||
holder.homeworkItemTopic.setBackground(null);
|
||||
}
|
||||
|
||||
holder.homeworkItemEdit.setVisibility((homework.addedManually ? View.VISIBLE : View.GONE));
|
||||
holder.homeworkItemEdit.setOnClickListener(v -> {
|
||||
new EventManualDialog(context).show(app, homework, null, null, EventManualDialog.DIALOG_HOMEWORK);
|
||||
});
|
||||
|
||||
if (homework.sharedBy == null) {
|
||||
holder.homeworkItemSharedBy.setVisibility(View.GONE);
|
||||
}
|
||||
else if (homework.sharedByName != null) {
|
||||
holder.homeworkItemSharedBy.setText(app.getString(R.string.event_shared_by_format, (homework.sharedBy.equals("self") ? app.getString(R.string.event_shared_by_self) : homework.sharedByName)));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getItemCount() {
|
||||
return homeworkList.size();
|
||||
}
|
||||
|
||||
class ViewHolder extends RecyclerView.ViewHolder {
|
||||
|
||||
CardView homeworkItemCard;
|
||||
TextView homeworkItemTopic;
|
||||
TextView homeworkItemHomeworkDate;
|
||||
TextView homeworkItemSharedBy;
|
||||
TextView homeworkItemSubjectTeacher;
|
||||
TextView homeworkItemTeamDate;
|
||||
Button homeworkItemEdit;
|
||||
|
||||
ViewHolder(View itemView) {
|
||||
super(itemView);
|
||||
homeworkItemCard = itemView.findViewById(R.id.homeworkItemCard);
|
||||
homeworkItemTopic = itemView.findViewById(R.id.homeworkItemTopic);
|
||||
homeworkItemHomeworkDate = itemView.findViewById(R.id.homeworkItemHomeworkDate);
|
||||
homeworkItemSharedBy = itemView.findViewById(R.id.homeworkItemSharedBy);
|
||||
homeworkItemSubjectTeacher = itemView.findViewById(R.id.homeworkItemSubjectTeacher);
|
||||
homeworkItemTeamDate = itemView.findViewById(R.id.homeworkItemTeamDate);
|
||||
homeworkItemEdit = itemView.findViewById(R.id.homeworkItemEdit);
|
||||
}
|
||||
}
|
||||
}
|
@ -1,84 +1,77 @@
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework
|
||||
|
||||
import android.os.AsyncTask
|
||||
import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import android.widget.Toast
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.viewpager.widget.ViewPager
|
||||
import com.mikepenz.iconics.typeface.library.community.material.CommunityMaterial
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.MainActivity
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.databinding.FragmentHomeworkBinding
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata
|
||||
import pl.szczodrzynski.edziennik.ui.base.BaseFragment
|
||||
import pl.szczodrzynski.edziennik.ui.dialogs.event.EventManualDialog
|
||||
import pl.szczodrzynski.edziennik.ui.modules.homework.list.HomeworkListFragment
|
||||
import pl.szczodrzynski.edziennik.ui.modules.messages.MessagesFragment
|
||||
import pl.szczodrzynski.edziennik.utils.Themes
|
||||
import pl.szczodrzynski.navlib.bottomsheet.items.BottomSheetPrimaryItem
|
||||
import pl.szczodrzynski.navlib.bottomsheet.items.BottomSheetSeparatorItem
|
||||
import javax.inject.Inject
|
||||
|
||||
class HomeworkFragment : Fragment() {
|
||||
class HomeworkFragment : BaseFragment<HomeworkPresenter>(), HomeworkView {
|
||||
companion object {
|
||||
var pageSelection = 0
|
||||
}
|
||||
|
||||
private lateinit var app: App
|
||||
private lateinit var activity: MainActivity
|
||||
private lateinit var b: FragmentHomeworkBinding
|
||||
|
||||
@Inject
|
||||
override lateinit var presenter: HomeworkPresenter
|
||||
|
||||
@Inject
|
||||
lateinit var app: App
|
||||
|
||||
override val markAsReadSuccessString: String
|
||||
get() = getString(R.string.main_menu_mark_as_read_success)
|
||||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
presenter.onAttachView(this)
|
||||
}
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
||||
activity = (getActivity() as MainActivity?) ?: return null
|
||||
if (context == null)
|
||||
return null
|
||||
app = activity.application as App
|
||||
activity = (getActivity() as MainActivity)
|
||||
context!!.theme.applyStyle(Themes.appTheme, true)
|
||||
if (app.profile == null)
|
||||
return inflater.inflate(R.layout.fragment_loading, container, false)
|
||||
// activity, context and profile is valid
|
||||
b = FragmentHomeworkBinding.inflate(inflater)
|
||||
b.refreshLayout.setParent(activity.swipeRefreshLayout)
|
||||
return b.root
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
override fun initView() {
|
||||
// TODO check if app, activity, b can be null
|
||||
if (app.profile == null || !isAdded)
|
||||
return
|
||||
|
||||
b.refreshLayout.setParent(activity.swipeRefreshLayout)
|
||||
|
||||
activity.bottomSheet.prependItems(
|
||||
BottomSheetPrimaryItem(true)
|
||||
.withTitle(R.string.menu_add_event)
|
||||
.withDescription(R.string.menu_add_event_desc)
|
||||
.withIcon(CommunityMaterial.Icon.cmd_calendar_plus)
|
||||
.withOnClickListener(View.OnClickListener {
|
||||
activity.bottomSheet.close()
|
||||
EventManualDialog(activity).show(app, null, null, null, EventManualDialog.DIALOG_HOMEWORK)
|
||||
}),
|
||||
BottomSheetSeparatorItem(true),
|
||||
BottomSheetPrimaryItem(true)
|
||||
.withTitle(R.string.menu_mark_as_read)
|
||||
.withIcon(CommunityMaterial.Icon.cmd_eye_check)
|
||||
.withOnClickListener(View.OnClickListener {
|
||||
activity.bottomSheet.close()
|
||||
AsyncTask.execute { app.db.metadataDao().setAllSeen(App.profileId, Metadata.TYPE_HOMEWORK, true) }
|
||||
Toast.makeText(activity, R.string.main_menu_mark_as_read_success, Toast.LENGTH_SHORT).show()
|
||||
}))
|
||||
.withTitle(R.string.menu_add_event)
|
||||
.withDescription(R.string.menu_add_event_desc)
|
||||
.withIcon(CommunityMaterial.Icon.cmd_calendar_plus)
|
||||
.withOnClickListener(View.OnClickListener { presenter.onAddEventClick() }),
|
||||
BottomSheetSeparatorItem(true),
|
||||
BottomSheetPrimaryItem(true)
|
||||
.withTitle(R.string.menu_mark_as_read)
|
||||
.withIcon(CommunityMaterial.Icon.cmd_eye_check)
|
||||
.withOnClickListener(View.OnClickListener { presenter.onMarkAsReadClick() }))
|
||||
|
||||
b.viewPager.adapter = MessagesFragment.Adapter(childFragmentManager).also { adapter ->
|
||||
adapter.addFragment(HomeworkListFragment().also { fragment ->
|
||||
fragment.arguments = Bundle().also { args ->
|
||||
args.putInt("homeworkDate", HomeworkDate.CURRENT)
|
||||
}
|
||||
}, getString(R.string.homework_tab_current))
|
||||
|
||||
adapter.addFragment(HomeworkListFragment().also { fragment ->
|
||||
fragment.arguments = Bundle().also { args ->
|
||||
args.putInt("homeworkDate", HomeworkDate.PAST)
|
||||
}
|
||||
}, getString(R.string.homework_tab_past))
|
||||
adapter.addFragment(HomeworkListFragment.newInstance(HomeworkDate.CURRENT), getString(R.string.homework_tab_current))
|
||||
adapter.addFragment(HomeworkListFragment.newInstance(HomeworkDate.PAST), getString(R.string.homework_tab_past))
|
||||
}
|
||||
|
||||
b.viewPager.currentItem = pageSelection
|
||||
@ -86,9 +79,7 @@ class HomeworkFragment : Fragment() {
|
||||
b.viewPager.addOnPageChangeListener(object : ViewPager.OnPageChangeListener {
|
||||
override fun onPageScrollStateChanged(state: Int) {}
|
||||
override fun onPageScrolled(position: Int, positionOffset: Float, positionOffsetPixels: Int) {}
|
||||
override fun onPageSelected(position: Int) {
|
||||
pageSelection = position
|
||||
}
|
||||
override fun onPageSelected(position: Int) = presenter.onPageSelected(position)
|
||||
})
|
||||
|
||||
b.tabLayout.setupWithViewPager(b.viewPager)
|
||||
@ -96,11 +87,21 @@ class HomeworkFragment : Fragment() {
|
||||
activity.navView.bottomBar.fabEnable = true
|
||||
activity.navView.bottomBar.fabExtendedText = getString(R.string.add)
|
||||
activity.navView.bottomBar.fabIcon = CommunityMaterial.Icon2.cmd_plus
|
||||
activity.navView.setFabOnClickListener(View.OnClickListener {
|
||||
EventManualDialog(activity).show(app, null, null, null, EventManualDialog.DIALOG_HOMEWORK)
|
||||
})
|
||||
activity.navView.setFabOnClickListener(View.OnClickListener { presenter.onHomeworkAddFabClick() })
|
||||
|
||||
activity.gainAttention()
|
||||
activity.gainAttentionFAB()
|
||||
}
|
||||
|
||||
override fun setPageSelection(position: Int) {
|
||||
pageSelection = position
|
||||
}
|
||||
|
||||
override fun closeBottomSheet() {
|
||||
activity.bottomSheet.close()
|
||||
}
|
||||
|
||||
override fun showAddHomeworkDialog() {
|
||||
EventManualDialog(activity).show(app, null, null, null, EventManualDialog.DIALOG_HOMEWORK)
|
||||
}
|
||||
}
|
||||
|
@ -1,77 +0,0 @@
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.lifecycle.Observer
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.MainActivity
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.databinding.HomeworkListBinding
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.Event
|
||||
import pl.szczodrzynski.edziennik.getInt
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
import pl.szczodrzynski.edziennik.utils.Themes
|
||||
|
||||
class HomeworkListFragment : Fragment() {
|
||||
|
||||
private lateinit var app: App
|
||||
private lateinit var activity: MainActivity
|
||||
private lateinit var b: HomeworkListBinding
|
||||
|
||||
private var homeworkDate = HomeworkDate.CURRENT
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
||||
activity = (getActivity() as MainActivity?) ?: return null
|
||||
if (context == null)
|
||||
return null
|
||||
app = activity.application as App
|
||||
context!!.theme.applyStyle(Themes.appTheme, true)
|
||||
if (app.profile == null)
|
||||
return inflater.inflate(R.layout.fragment_loading, container, false)
|
||||
// activity, context and profile is valid
|
||||
b = HomeworkListBinding.inflate(inflater)
|
||||
return b.root
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
// TODO check if app, activity, b can be null
|
||||
if (app.profile == null || !isAdded)
|
||||
return
|
||||
|
||||
if (arguments != null) {
|
||||
homeworkDate = arguments.getInt("homeworkDate", HomeworkDate.CURRENT)
|
||||
}
|
||||
|
||||
val layoutManager = LinearLayoutManager(context)
|
||||
layoutManager.reverseLayout = true
|
||||
layoutManager.stackFromEnd = true
|
||||
|
||||
b.homeworkView.setHasFixedSize(true)
|
||||
b.homeworkView.layoutManager = layoutManager
|
||||
|
||||
val filter = when(homeworkDate) {
|
||||
HomeworkDate.CURRENT -> "eventDate > '" + Date.getToday().stringY_m_d + "'"
|
||||
else -> "eventDate <= '" + Date.getToday().stringY_m_d + "'"
|
||||
}
|
||||
|
||||
app.db.eventDao()
|
||||
.getAllByType(App.profileId, Event.TYPE_HOMEWORK, filter)
|
||||
.observe(this, Observer { homeworkList ->
|
||||
if (app.profile == null || !isAdded) return@Observer
|
||||
|
||||
if (homeworkList != null && homeworkList.size > 0) {
|
||||
val adapter = HomeworkAdapter(context, homeworkList)
|
||||
b.homeworkView.adapter = adapter
|
||||
b.homeworkView.visibility = View.VISIBLE
|
||||
b.homeworkNoData.visibility = View.GONE
|
||||
} else {
|
||||
b.homeworkView.visibility = View.GONE
|
||||
b.homeworkNoData.visibility = View.VISIBLE
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
@ -0,0 +1,47 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework
|
||||
|
||||
import android.os.AsyncTask
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.metadata.Metadata
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.metadata.MetadataDao
|
||||
import pl.szczodrzynski.edziennik.ui.base.BasePresenter
|
||||
import javax.inject.Inject
|
||||
|
||||
class HomeworkPresenter @Inject constructor(
|
||||
private val metadataDao: MetadataDao
|
||||
) : BasePresenter<HomeworkView>() {
|
||||
|
||||
override fun onAttachView(view: HomeworkView) {
|
||||
super.onAttachView(view)
|
||||
view.initView()
|
||||
}
|
||||
|
||||
fun onPageSelected(position: Int) {
|
||||
view?.setPageSelection(position)
|
||||
}
|
||||
|
||||
fun onAddEventClick() {
|
||||
view?.apply {
|
||||
closeBottomSheet()
|
||||
showAddHomeworkDialog()
|
||||
}
|
||||
}
|
||||
|
||||
fun onMarkAsReadClick() {
|
||||
view?.apply {
|
||||
closeBottomSheet()
|
||||
AsyncTask.execute {
|
||||
metadataDao.setAllSeen(App.profileId, Metadata.TYPE_HOMEWORK, true)
|
||||
}
|
||||
showMessage(markAsReadSuccessString)
|
||||
}
|
||||
}
|
||||
|
||||
fun onHomeworkAddFabClick() {
|
||||
view?.showAddHomeworkDialog()
|
||||
}
|
||||
}
|
@ -0,0 +1,20 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework
|
||||
|
||||
import pl.szczodrzynski.edziennik.ui.base.BaseView
|
||||
|
||||
interface HomeworkView : BaseView {
|
||||
|
||||
val markAsReadSuccessString: String
|
||||
|
||||
fun initView()
|
||||
|
||||
fun closeBottomSheet()
|
||||
|
||||
fun showAddHomeworkDialog()
|
||||
|
||||
fun setPageSelection(position: Int)
|
||||
}
|
@ -0,0 +1,111 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework.list
|
||||
|
||||
import android.content.res.Resources
|
||||
import android.graphics.PorterDuff
|
||||
import android.graphics.PorterDuffColorFilter
|
||||
import android.graphics.drawable.Drawable
|
||||
import android.os.AsyncTask
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View.GONE
|
||||
import android.view.View.VISIBLE
|
||||
import android.view.ViewGroup
|
||||
import androidx.core.content.ContextCompat
|
||||
import androidx.databinding.DataBindingUtil
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.EventFull
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.metadata.MetadataDao
|
||||
import pl.szczodrzynski.edziennik.databinding.RowHomeworkItemBinding
|
||||
import pl.szczodrzynski.edziennik.utils.Utils.bs
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
import javax.inject.Inject
|
||||
import kotlin.math.abs
|
||||
|
||||
class HomeworkListAdapter @Inject constructor(
|
||||
private val metadataDao: MetadataDao
|
||||
) : RecyclerView.Adapter<HomeworkListAdapter.ViewHolder>() {
|
||||
|
||||
val homeworkList: MutableList<EventFull> = mutableListOf()
|
||||
lateinit var onItemEditClick: (homework: EventFull) -> Unit
|
||||
|
||||
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
|
||||
val inflater = LayoutInflater.from(parent.context)
|
||||
val b: RowHomeworkItemBinding = DataBindingUtil.inflate(inflater, R.layout.row_homework_item, parent, false)
|
||||
return ViewHolder(b)
|
||||
}
|
||||
|
||||
override fun onBindViewHolder(holder: ViewHolder, position: Int) {
|
||||
val homework = homeworkList[position]
|
||||
|
||||
holder.apply {
|
||||
val diffDaysString = dateDiffString(Date.diffDays(homework.eventDate, Date.getToday()))
|
||||
|
||||
b.homeworkItemHomeworkDate.text = getString(R.string.date_relative_format, homework.eventDate.formattedString, diffDaysString)
|
||||
b.homeworkItemTopic.text = homework.topic
|
||||
b.homeworkItemSubjectTeacher.text = getString(R.string.homework_subject_teacher_format, bs(homework.subjectLongName), bs(homework.teacherFullName))
|
||||
b.homeworkItemTeamDate.text = getString(R.string.homework_team_date_format, bs(homework.teamName), Date.fromMillis(homework.addedDate).formattedStringShort)
|
||||
|
||||
when {
|
||||
!homework.seen -> {
|
||||
b.homeworkItemTopic.apply {
|
||||
background = getDrawable(R.drawable.bg_rounded_8dp)
|
||||
background.colorFilter = PorterDuffColorFilter(0x692196f3, PorterDuff.Mode.MULTIPLY)
|
||||
}
|
||||
|
||||
homework.seen = true
|
||||
AsyncTask.execute {
|
||||
metadataDao.setSeen(App.profileId, homework, true)
|
||||
}
|
||||
}
|
||||
else -> b.homeworkItemTopic.background = null
|
||||
}
|
||||
|
||||
b.homeworkItemEdit.apply {
|
||||
visibility = if (homework.addedManually) VISIBLE else GONE
|
||||
setOnClickListener { onItemEditClick(homework) }
|
||||
}
|
||||
|
||||
b.homeworkItemSharedBy.apply {
|
||||
when {
|
||||
homework.sharedBy == null -> visibility = GONE
|
||||
homework.sharedByName != null -> text = getString(R.string.event_shared_by_format,
|
||||
when (homework.sharedBy == "self") {
|
||||
true -> getString(R.string.event_shared_by_self)
|
||||
else -> homework.sharedByName
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun getItemCount() = homeworkList.size
|
||||
|
||||
class ViewHolder(val b: RowHomeworkItemBinding) : RecyclerView.ViewHolder(b.root) {
|
||||
fun getString(resId: Int): String = itemView.context.getString(resId)
|
||||
fun getString(resId: Int, vararg formatArgs: Any): String = itemView.context.getString(resId, *formatArgs)
|
||||
fun getDrawable(resId: Int): Drawable? = ContextCompat.getDrawable(itemView.context, resId)
|
||||
|
||||
val resources: Resources get() = itemView.context.resources
|
||||
|
||||
fun dateDiffString(diff: Int): String {
|
||||
return when {
|
||||
diff > 0 -> when (diff) {
|
||||
1 -> getString(R.string.tomorrow)
|
||||
2 -> getString(R.string.the_day_after)
|
||||
else -> resources.getQuantityString(R.plurals.time_till_days, abs(diff), abs(diff))
|
||||
}
|
||||
diff < 0 -> when (diff) {
|
||||
-1 -> getString(R.string.yesterday)
|
||||
-2 -> getString(R.string.the_day_before)
|
||||
else -> getString(R.string.ago_format, resources.getQuantityString(R.plurals.time_till_days, abs(diff), abs(diff)))
|
||||
}
|
||||
else -> getString(R.string.today)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,107 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework.list
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.View.GONE
|
||||
import android.view.View.VISIBLE
|
||||
import android.view.ViewGroup
|
||||
import androidx.lifecycle.Lifecycle
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.MainActivity
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.EventFull
|
||||
import pl.szczodrzynski.edziennik.databinding.HomeworkListBinding
|
||||
import pl.szczodrzynski.edziennik.ui.base.BaseFragment
|
||||
import pl.szczodrzynski.edziennik.ui.dialogs.event.EventManualDialog
|
||||
import pl.szczodrzynski.edziennik.utils.Themes
|
||||
import javax.inject.Inject
|
||||
|
||||
class HomeworkListFragment : BaseFragment<HomeworkListPresenter>(), HomeworkListView {
|
||||
|
||||
private lateinit var activity: MainActivity
|
||||
private lateinit var b: HomeworkListBinding
|
||||
|
||||
@Inject
|
||||
override lateinit var presenter: HomeworkListPresenter
|
||||
|
||||
@Inject
|
||||
lateinit var app: App
|
||||
|
||||
@Inject
|
||||
lateinit var homeworkAdapter: HomeworkListAdapter
|
||||
|
||||
override val viewLifecycle: Lifecycle
|
||||
get() = lifecycle
|
||||
|
||||
companion object {
|
||||
private const val ARGUMENT_KEY = "homeworkDate"
|
||||
|
||||
fun newInstance(homeworkDate: Int) = HomeworkListFragment().apply {
|
||||
arguments = Bundle().apply { putInt(ARGUMENT_KEY, homeworkDate) }
|
||||
}
|
||||
}
|
||||
|
||||
override fun onActivityCreated(savedInstanceState: Bundle?) {
|
||||
super.onActivityCreated(savedInstanceState)
|
||||
presenter.onAttachView(this, arguments?.getInt(ARGUMENT_KEY))
|
||||
}
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
||||
activity = (getActivity() as MainActivity?) ?: return null
|
||||
if (context == null)
|
||||
return null
|
||||
context!!.theme.applyStyle(Themes.appTheme, true)
|
||||
if (app.profile == null)
|
||||
return inflater.inflate(R.layout.fragment_loading, container, false)
|
||||
// activity, context and profile is valid
|
||||
b = HomeworkListBinding.inflate(inflater)
|
||||
return b.root
|
||||
}
|
||||
|
||||
override fun initView() {
|
||||
// TODO check if app, activity, b can be null
|
||||
if (app.profile == null || !isAdded)
|
||||
return
|
||||
|
||||
val layoutManager = LinearLayoutManager(context).apply {
|
||||
reverseLayout = true
|
||||
stackFromEnd = true
|
||||
}
|
||||
|
||||
homeworkAdapter.onItemEditClick = presenter::onItemEditClick
|
||||
|
||||
b.homeworkView.apply {
|
||||
setHasFixedSize(true)
|
||||
this.layoutManager = layoutManager
|
||||
adapter = homeworkAdapter
|
||||
}
|
||||
}
|
||||
|
||||
override fun updateData(data: List<EventFull>) {
|
||||
homeworkAdapter.apply {
|
||||
homeworkList.apply {
|
||||
clear()
|
||||
addAll(data)
|
||||
}
|
||||
notifyDataSetChanged()
|
||||
}
|
||||
}
|
||||
|
||||
override fun showContent(show: Boolean) {
|
||||
b.homeworkView.visibility = if (show) VISIBLE else GONE
|
||||
}
|
||||
|
||||
override fun showNoData(show: Boolean) {
|
||||
b.homeworkNoData.visibility = if (show) VISIBLE else GONE
|
||||
}
|
||||
|
||||
override fun showEditHomeworkDialog(homework: EventFull) {
|
||||
EventManualDialog(context).show(app, homework, null, null, EventManualDialog.DIALOG_HOMEWORK)
|
||||
}
|
||||
}
|
@ -0,0 +1,55 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework.list
|
||||
|
||||
import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.Event
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.EventDao
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.EventFull
|
||||
import pl.szczodrzynski.edziennik.ui.base.BasePresenter
|
||||
import pl.szczodrzynski.edziennik.ui.modules.homework.HomeworkDate
|
||||
import pl.szczodrzynski.edziennik.utils.models.Date
|
||||
import javax.inject.Inject
|
||||
|
||||
class HomeworkListPresenter @Inject constructor(
|
||||
private val app: App,
|
||||
private val eventDao: EventDao
|
||||
) : BasePresenter<HomeworkListView>() {
|
||||
|
||||
fun onAttachView(view: HomeworkListView, homeworkDate: Int?) {
|
||||
super.onAttachView(view)
|
||||
view.initView()
|
||||
loadData(homeworkDate ?: HomeworkDate.CURRENT)
|
||||
}
|
||||
|
||||
private fun loadData(homeworkDate: Int) {
|
||||
val today = Date.getToday().stringY_m_d
|
||||
|
||||
val filter = when (homeworkDate) {
|
||||
HomeworkDate.CURRENT -> "eventDate > '$today'"
|
||||
else -> "eventDate <= '$today'"
|
||||
}
|
||||
|
||||
view?.run {
|
||||
eventDao.getAllByType(App.profileId, Event.TYPE_HOMEWORK, filter)
|
||||
.observe({ viewLifecycle }, { homeworkList ->
|
||||
if (app.profile == null) return@observe
|
||||
|
||||
if (homeworkList != null && homeworkList.size > 0) {
|
||||
updateData(homeworkList)
|
||||
showContent(true)
|
||||
showNoData(false)
|
||||
} else {
|
||||
showContent(false)
|
||||
showNoData(true)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
fun onItemEditClick(homework: EventFull) {
|
||||
view?.showEditHomeworkDialog(homework)
|
||||
}
|
||||
}
|
@ -0,0 +1,24 @@
|
||||
/*
|
||||
* Copyright (c) Kacper Ziubryniewicz 2019-11-4
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.ui.modules.homework.list
|
||||
|
||||
import androidx.lifecycle.Lifecycle
|
||||
import pl.szczodrzynski.edziennik.data.db.modules.events.EventFull
|
||||
import pl.szczodrzynski.edziennik.ui.base.BaseView
|
||||
|
||||
interface HomeworkListView : BaseView {
|
||||
|
||||
val viewLifecycle: Lifecycle
|
||||
|
||||
fun initView()
|
||||
|
||||
fun updateData(data: List<EventFull>)
|
||||
|
||||
fun showContent(show: Boolean)
|
||||
|
||||
fun showNoData(show: Boolean)
|
||||
|
||||
fun showEditHomeworkDialog(homework: EventFull)
|
||||
}
|
@ -1,116 +0,0 @@
|
||||
package pl.szczodrzynski.edziennik.ui.modules.login
|
||||
|
||||
import android.annotation.SuppressLint
|
||||
import android.graphics.Color
|
||||
import android.os.Build
|
||||
import android.os.Bundle
|
||||
import android.util.Base64
|
||||
import android.webkit.JavascriptInterface
|
||||
import android.webkit.WebView
|
||||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import com.afollestad.materialdialogs.MaterialDialog
|
||||
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.api.v2.LIBRUS_USER_AGENT
|
||||
import pl.szczodrzynski.edziennik.utils.Themes
|
||||
import pl.szczodrzynski.edziennik.utils.Utils.hexFromColorInt
|
||||
import java.nio.charset.Charset
|
||||
|
||||
class LoginLibrusCaptchaActivity : AppCompatActivity() {
|
||||
companion object {
|
||||
private const val TAG = "LoginLibrusCaptchaActivity"
|
||||
}
|
||||
|
||||
private lateinit var webView: WebView
|
||||
private lateinit var dialog: AlertDialog
|
||||
private lateinit var jsInterface: CaptchaCallbackInterface
|
||||
|
||||
@SuppressLint("AddJavascriptInterface", "SetJavaScriptEnabled")
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
setTheme(Themes.appThemeNoDisplay)
|
||||
setFinishOnTouchOutside(false)
|
||||
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
|
||||
WebView.setWebContentsDebuggingEnabled(true)
|
||||
}
|
||||
|
||||
val base64Content = """
|
||||
PCFET0NUWVBFIGh0bWw+PGh0bWw+PGhlYWQ+PHNjcmlwdCBzcmM9Imh0dHBzOi8vd3d3Lmdvb2ds
|
||||
ZS5jb20vcmVjYXB0Y2hhL2FwaS5qcz9vbmxvYWQ9cmVhZHkmcmVuZGVyPWV4cGxpY2l0Ij48L3Nj
|
||||
cmlwdD48L2hlYWQ+PGJvZHk+PGJyPjxjZW50ZXIgaWQ9ImdyIj48L2NlbnRlcj48YnI+PHNjcmlw
|
||||
dD5mdW5jdGlvbiByZWFkeSgpe2dyZWNhcHRjaGEucmVuZGVyKCdncicse3NpdGVrZXk6JzZMZjQ4
|
||||
bW9VQUFBQUFCOUNsaGR2SHI0NmdSV1ItQ04zMUNYUVBHMlUnLHRoZW1lOidUSEVNRScsY2FsbGJh
|
||||
Y2s6ZnVuY3Rpb24oZSl7d2luZG93LmlmLmNhbGxiYWNrKGUpO30sImV4cGlyZWQtY2FsbGJhY2si
|
||||
OmZ1bmN0aW9uKCl7d2luZG93LmlmLmV4cGlyZWRDYWxsYmFjayhlKTt9LCJlcnJvci1jYWxsYmFj
|
||||
ayI6ZnVuY3Rpb24oKXt3aW5kb3cuaWYuZXJyb3JDYWxsYmFjayhlKTt9fSk7fTwvc2NyaXB0Pjwv
|
||||
Ym9keT48L2h0bWw+"""
|
||||
|
||||
val backgroundColor = if (Themes.isDark) 0x424242 else 0xffffff
|
||||
val backgroundColorString = hexFromColorInt(backgroundColor)
|
||||
|
||||
val htmlContent = Base64.decode(base64Content, Base64.DEFAULT)
|
||||
.toString(Charset.defaultCharset())
|
||||
.replace("COLOR", backgroundColorString, true)
|
||||
.replace("THEME", if (Themes.isDark) "dark" else "light")
|
||||
|
||||
jsInterface = object : CaptchaCallbackInterface {
|
||||
@JavascriptInterface
|
||||
override fun callback(recaptchaResponse: String) {
|
||||
MaterialDialog.Builder(this@LoginLibrusCaptchaActivity)
|
||||
.title("Captcha checked")
|
||||
.content("Response: $recaptchaResponse")
|
||||
.positiveText("OK")
|
||||
.show()
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
override fun expiredCallback() {
|
||||
MaterialDialog.Builder(this@LoginLibrusCaptchaActivity)
|
||||
.title("Captcha expired")
|
||||
.content("Captcha expired")
|
||||
.positiveText("OK")
|
||||
.show()
|
||||
}
|
||||
|
||||
@JavascriptInterface
|
||||
override fun errorCallback() {
|
||||
MaterialDialog.Builder(this@LoginLibrusCaptchaActivity)
|
||||
.title("Captcha error")
|
||||
.content("Captcha error")
|
||||
.positiveText("OK")
|
||||
.show()
|
||||
}
|
||||
}
|
||||
|
||||
webView = WebView(this).apply {
|
||||
//setBackgroundColor((backgroundColor.toLong() or 0xff000000).toInt())
|
||||
setBackgroundColor(Color.TRANSPARENT)
|
||||
settings.javaScriptEnabled = true
|
||||
settings.userAgentString = LIBRUS_USER_AGENT
|
||||
addJavascriptInterface(jsInterface, "if")
|
||||
loadDataWithBaseURL("https://portal.librus.pl/rodzina/login/", htmlContent, "text/html", "UTF-8", null)
|
||||
setLayerType(WebView.LAYER_TYPE_SOFTWARE, null)
|
||||
}
|
||||
|
||||
dialog = MaterialAlertDialogBuilder(this)
|
||||
.setTitle(R.string.login_librus_captcha_title)
|
||||
.setView(webView)
|
||||
.setNegativeButton(R.string.cancel) { dialog, _ ->
|
||||
dialog.dismiss()
|
||||
finish()
|
||||
}
|
||||
.setCancelable(false)
|
||||
.show()
|
||||
}
|
||||
|
||||
interface CaptchaCallbackInterface {
|
||||
@JavascriptInterface
|
||||
fun callback(recaptchaResponse: String)
|
||||
@JavascriptInterface
|
||||
fun expiredCallback()
|
||||
@JavascriptInterface
|
||||
fun errorCallback()
|
||||
}
|
||||
}
|
@ -1,24 +0,0 @@
|
||||
package pl.szczodrzynski.edziennik.utils
|
||||
|
||||
import android.content.ComponentName
|
||||
import android.content.Intent
|
||||
|
||||
val appManagerIntentList = listOf(
|
||||
Intent().setClassName("com.miui.powerkeeper", "com.miui.powerkeeper.ui.HiddenAppsConfigActivity")
|
||||
.putExtra("packageName", "pl.szczodrzynski.edziennik")
|
||||
.putExtra("package_label", "Szkolny.eu"),
|
||||
Intent().setComponent(ComponentName("com.miui.securitycenter", "com.miui.permcenter.autostart.AutoStartManagementActivity")),
|
||||
Intent().setComponent(ComponentName("com.letv.android.letvsafe", "com.letv.android.letvsafe.AutobootManageActivity")),
|
||||
Intent().setComponent(ComponentName("com.huawei.systemmanager", "com.huawei.systemmanager.optimize.process.ProtectActivity")),
|
||||
Intent().setComponent(ComponentName("com.huawei.systemmanager", "com.huawei.systemmanager.appcontrol.activity.StartupAppControlActivity")),
|
||||
Intent().setComponent(ComponentName("com.huawei.systemmanager", "com.huawei.systemmanager.startupmgr.ui.StartupNormalAppListActivity")),
|
||||
Intent().setComponent(ComponentName("com.coloros.safecenter", "com.coloros.safecenter.permission.startup.StartupAppListActivity")),
|
||||
Intent().setComponent(ComponentName("com.coloros.safecenter", "com.coloros.safecenter.startupapp.StartupAppListActivity")),
|
||||
Intent().setComponent(ComponentName("com.oppo.safe", "com.oppo.safe.permission.startup.StartupAppListActivity")),
|
||||
Intent().setComponent(ComponentName("com.iqoo.secure", "com.iqoo.secure.ui.phoneoptimize.AddWhiteListActivity")),
|
||||
Intent().setComponent(ComponentName("com.iqoo.secure", "com.iqoo.secure.ui.phoneoptimize.BgStartUpManager")),
|
||||
Intent().setComponent(ComponentName("com.vivo.permissionmanager", "com.vivo.permissionmanager.activity.BgStartUpManagerActivity")),
|
||||
Intent().setComponent(ComponentName("com.samsung.android.lool", "com.samsung.android.sm.ui.battery.BatteryActivity")),
|
||||
Intent().setComponent(ComponentName("com.htc.pitroad", "com.htc.pitroad.landingpage.activity.LandingPageActivity")),
|
||||
Intent().setComponent(ComponentName("com.asus.mobilemanager", "com.asus.mobilemanager.MainActivity"))
|
||||
)
|
@ -36,46 +36,24 @@
|
||||
android:layout_height="wrap_content"
|
||||
android:visibility="gone"
|
||||
android:orientation="vertical"
|
||||
tools:visibility="visible"
|
||||
tools:ignore="HardcodedText">
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/librusCaptchaButton"
|
||||
style="@style/Widget.MaterialComponents.Button"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_margin="8dp"
|
||||
android:text="Librus Captcha" />
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/runChucker"
|
||||
style="@style/Widget.MaterialComponents.Button"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_margin="8dp"
|
||||
android:text="Launch Chucker" />
|
||||
|
||||
tools:visibility="visible">
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center">
|
||||
|
||||
android:layout_height="wrap_content">
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/mobidziennikMessagesSwitch"
|
||||
style="@style/Widget.MaterialComponents.Button.OutlinedButton"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_margin="8dp"
|
||||
android:layout_weight="1"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="Zmień moduł wiadomości" />
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/composeButton"
|
||||
style="@style/Widget.MaterialComponents.Button"
|
||||
android:layout_width="0dp"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_margin="8dp"
|
||||
android:layout_weight="1"
|
||||
android:text="Compose" />
|
||||
</LinearLayout>
|
||||
|
||||
|
@ -1,113 +1,116 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
<layout 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:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical">
|
||||
xmlns:tools="http://schemas.android.com/tools">
|
||||
|
||||
<com.google.android.material.card.MaterialCardView
|
||||
android:id="@+id/homeworkItemCard"
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_margin="8dp"
|
||||
app:cardElevation="4dp"
|
||||
app:cardCornerRadius="5dp"
|
||||
android:background="?selectableItemBackground"
|
||||
android:paddingLeft="10dp"
|
||||
android:paddingTop="5dp"
|
||||
android:paddingRight="10dp"
|
||||
android:paddingBottom="3dp">
|
||||
android:orientation="vertical">
|
||||
|
||||
<LinearLayout
|
||||
<com.google.android.material.card.MaterialCardView
|
||||
android:id="@+id/homeworkItemCard"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="vertical"
|
||||
android:padding="8dp">
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_margin="8dp"
|
||||
android:background="?selectableItemBackground"
|
||||
android:paddingLeft="10dp"
|
||||
android:paddingTop="5dp"
|
||||
android:paddingRight="10dp"
|
||||
android:paddingBottom="3dp"
|
||||
app:cardCornerRadius="5dp"
|
||||
app:cardElevation="4dp">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="horizontal">
|
||||
android:orientation="vertical"
|
||||
android:padding="8dp">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemHomeworkDate"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginRight="16dp"
|
||||
android:textAppearance="@style/TextAppearance.AppCompat.Small"
|
||||
android:textSize="16sp"
|
||||
tools:text="homeworkDate"
|
||||
android:layout_marginEnd="16dp" />
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="horizontal">
|
||||
|
||||
<com.mikepenz.iconics.view.IconicsTextView
|
||||
android:id="@+id/homeworkItemSharedBy"
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemHomeworkDate"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="16dp"
|
||||
android:layout_marginRight="16dp"
|
||||
android:textAppearance="@style/TextAppearance.AppCompat.Small"
|
||||
android:textSize="16sp"
|
||||
tools:text="homeworkDate" />
|
||||
|
||||
<com.mikepenz.iconics.view.IconicsTextView
|
||||
android:id="@+id/homeworkItemSharedBy"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="8dp"
|
||||
android:layout_marginEnd="8dp"
|
||||
android:ellipsize="end"
|
||||
android:gravity="end"
|
||||
android:maxLines="1"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toEndOf="@+id/constraintLayout"
|
||||
app:layout_constraintTop_toBottomOf="@+id/eventListItemTopic"
|
||||
tools:text="{cmd-share-variant} przez" />
|
||||
</LinearLayout>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="8dp"
|
||||
android:layout_marginEnd="8dp"
|
||||
android:ellipsize="end"
|
||||
android:gravity="end"
|
||||
android:maxLines="1"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toEndOf="@+id/constraintLayout"
|
||||
app:layout_constraintTop_toBottomOf="@+id/eventListItemTopic"
|
||||
tools:text="{cmd-share-variant} przez" />
|
||||
</LinearLayout>
|
||||
android:orientation="horizontal">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemTopic"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:autoLink="all"
|
||||
android:paddingBottom="4dp"
|
||||
android:textIsSelectable="true"
|
||||
android:textSize="18sp"
|
||||
tools:text="topic???" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemTopic"
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/homeworkItemEdit"
|
||||
style="@style/Widget.MaterialComponents.Button.OutlinedButton"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="0"
|
||||
android:minHeight="0dp"
|
||||
android:text="@string/homework_edit"
|
||||
android:visibility="visible" /><!--android:minWidth="0dp"
|
||||
android:minHeight="0dp"-->
|
||||
</LinearLayout>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:paddingBottom="4dp"
|
||||
android:textSize="18sp"
|
||||
android:textIsSelectable="true"
|
||||
android:autoLink="all"
|
||||
tools:text="topic???" />
|
||||
android:orientation="horizontal">
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/homeworkItemEdit"
|
||||
style="@style/Widget.MaterialComponents.Button.OutlinedButton"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="0"
|
||||
android:minHeight="0dp"
|
||||
android:text="@string/homework_edit"
|
||||
android:visibility="visible" /><!--android:minWidth="0dp"
|
||||
android:minHeight="0dp"-->
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemSubjectTeacher"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginRight="8dp"
|
||||
android:layout_weight="1"
|
||||
android:ellipsize="end"
|
||||
android:singleLine="true"
|
||||
android:textAppearance="@style/TextAppearance.AppCompat.Small"
|
||||
tools:text="subjectName, teacherName" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemTeamDate"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:textAppearance="@style/TextAppearance.AppCompat.Small"
|
||||
tools:text="teamName addedDate" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="horizontal">
|
||||
</com.google.android.material.card.MaterialCardView>
|
||||
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemSubjectTeacher"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginRight="8dp"
|
||||
android:layout_weight="1"
|
||||
android:ellipsize="end"
|
||||
android:singleLine="true"
|
||||
android:textAppearance="@style/TextAppearance.AppCompat.Small"
|
||||
tools:text="subjectName, teacherName" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/homeworkItemTeamDate"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:textAppearance="@style/TextAppearance.AppCompat.Small"
|
||||
tools:text="teamName addedDate" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
|
||||
</com.google.android.material.card.MaterialCardView>
|
||||
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
</layout>
|
||||
|
@ -930,7 +930,6 @@
|
||||
<string name="settings_register_show_teacher_absences_text">Pokazuj nieobecności nauczycieli w Terminarzu</string>
|
||||
<string name="edziennik_progress_endpoint_school_info">Pobieram informacje o szkole...</string>
|
||||
<string name="edziennik_progress_endpoint_grades">Pobieranie ocen ucznia...</string>
|
||||
<string name="edziennik_progress_endpoint_grade_categories">Pobieranie kategorii ocen...</string>
|
||||
<string name="edziennik_progress_login_template_web">Logowanie do Template WEB...</string>
|
||||
<string name="edziennik_progress_login_template_api">Logowanie do Template API...</string>
|
||||
<string name="edziennik_progress_login_mobidziennik_web">Logowanie do MobiDziennika...</string>
|
||||
@ -984,5 +983,4 @@
|
||||
<string name="dont_ask_again">Nie pytaj ponownie</string>
|
||||
<string name="app_manager_open_failed">Nie udało się otworzyć ustawień</string>
|
||||
<string name="edziennik_notification_api_notify_title">Tworzenie powiadomień</string>
|
||||
<string name="login_librus_captcha_title">Librus - logowanie</string>
|
||||
</resources>
|
||||
|
@ -5,8 +5,8 @@ buildscript {
|
||||
kotlin_version = '1.3.50'
|
||||
|
||||
release = [
|
||||
versionName: "3.9.1-dev",
|
||||
versionCode: 3090100
|
||||
versionName: "3.1.1",
|
||||
versionCode: 3010199
|
||||
]
|
||||
|
||||
setup = [
|
||||
@ -47,7 +47,8 @@ buildscript {
|
||||
|
||||
navlib : "e4ad01dc87",
|
||||
|
||||
gifdrawable : "1.2.15"
|
||||
gifdrawable : "1.2.15",
|
||||
dagger : "2.24"
|
||||
]
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user