mirror of
https://github.com/szkolny-eu/szkolny-android.git
synced 2025-06-13 22:20:17 +02:00
Compare commits
5 Commits
Author | SHA1 | Date | |
---|---|---|---|
99afa77a63 | |||
a5d0f4212d | |||
a85f935eb4 | |||
bb44fa066c | |||
54a61c6254 |
@ -82,9 +82,6 @@ android {
|
||||
defaultConfig {
|
||||
vectorDrawables.useSupportLibrary = true
|
||||
}
|
||||
lintOptions {
|
||||
checkReleaseBuilds = false
|
||||
}
|
||||
buildFeatures {
|
||||
dataBinding = true
|
||||
viewBinding = true
|
||||
@ -98,7 +95,9 @@ android {
|
||||
jvmTarget = "1.8"
|
||||
}
|
||||
packagingOptions {
|
||||
exclude 'META-INF/library-core_release.kotlin_module'
|
||||
resources {
|
||||
excludes += ['META-INF/library-core_release.kotlin_module']
|
||||
}
|
||||
}
|
||||
externalNativeBuild {
|
||||
cmake {
|
||||
@ -106,6 +105,9 @@ android {
|
||||
version "3.10.2"
|
||||
}
|
||||
}
|
||||
lint {
|
||||
checkReleaseBuilds false
|
||||
}
|
||||
}
|
||||
|
||||
tasks.whenTaskAdded { task ->
|
||||
@ -140,28 +142,29 @@ dependencies {
|
||||
|
||||
// Language cores
|
||||
implementation "org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version"
|
||||
implementation "androidx.multidex:multidex:2.0.1"
|
||||
coreLibraryDesugaring "com.android.tools:desugar_jdk_libs:1.1.5"
|
||||
|
||||
// Android Jetpack
|
||||
implementation "androidx.appcompat:appcompat:1.3.1"
|
||||
implementation "androidx.appcompat:appcompat:1.5.1"
|
||||
implementation "androidx.cardview:cardview:1.0.0"
|
||||
implementation "androidx.constraintlayout:constraintlayout:2.1.1"
|
||||
implementation "androidx.core:core-ktx:1.6.0"
|
||||
implementation "androidx.lifecycle:lifecycle-livedata-ktx:2.3.1"
|
||||
implementation "androidx.navigation:navigation-fragment-ktx:2.3.5"
|
||||
implementation "androidx.constraintlayout:constraintlayout:2.1.4"
|
||||
implementation "androidx.core:core-ktx:1.9.0"
|
||||
implementation "androidx.lifecycle:lifecycle-livedata-ktx:2.5.1"
|
||||
implementation "androidx.navigation:navigation-fragment-ktx:2.5.2"
|
||||
implementation "androidx.recyclerview:recyclerview:1.2.1"
|
||||
implementation "androidx.room:room-runtime:2.3.0"
|
||||
implementation "androidx.work:work-runtime-ktx:2.6.0"
|
||||
kapt "androidx.room:room-compiler:2.3.0"
|
||||
implementation "androidx.room:room-runtime:2.4.3"
|
||||
implementation "androidx.work:work-runtime-ktx:2.7.1"
|
||||
kapt "androidx.room:room-compiler:2.4.3"
|
||||
|
||||
// Google design libs
|
||||
implementation "com.google.android.material:material:1.4.0"
|
||||
implementation "com.google.android.material:material:1.6.1"
|
||||
implementation "com.google.android.flexbox:flexbox:3.0.0"
|
||||
|
||||
// Play Services/Firebase
|
||||
implementation "com.google.android.gms:play-services-wearable:17.1.0"
|
||||
implementation "com.google.firebase:firebase-core:19.0.2"
|
||||
implementation "com.google.firebase:firebase-crashlytics:18.2.3"
|
||||
implementation("com.google.firebase:firebase-core") { version { strictly "19.0.2" } }
|
||||
implementation "com.google.firebase:firebase-crashlytics:18.2.13"
|
||||
implementation("com.google.firebase:firebase-messaging") { version { strictly "20.1.3" } }
|
||||
|
||||
// OkHttp, Retrofit, Gson, Jsoup
|
||||
|
@ -43,6 +43,7 @@
|
||||
android:configChanges="orientation|screenSize"
|
||||
android:label="@string/app_name"
|
||||
android:launchMode="singleTop"
|
||||
android:exported="true"
|
||||
android:theme="@style/SplashTheme">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.MAIN" />
|
||||
@ -66,6 +67,7 @@
|
||||
android:configChanges="orientation|keyboardHidden"
|
||||
android:excludeFromRecents="true"
|
||||
android:noHistory="true"
|
||||
android:exported="true"
|
||||
android:theme="@style/AppTheme.Dark.NoDisplay">
|
||||
<intent-filter>
|
||||
<action android:name="android.appwidget.action.APPWIDGET_CONFIGURE" />
|
||||
@ -73,7 +75,8 @@
|
||||
</activity>
|
||||
<!-- TIMETABLE -->
|
||||
<receiver android:name=".ui.widgets.timetable.WidgetTimetableProvider"
|
||||
android:label="@string/widget_timetable_title">
|
||||
android:label="@string/widget_timetable_title"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||
</intent-filter>
|
||||
@ -88,10 +91,12 @@
|
||||
android:configChanges="orientation|keyboardHidden"
|
||||
android:excludeFromRecents="true"
|
||||
android:noHistory="true"
|
||||
android:exported="true"
|
||||
android:theme="@style/AppTheme.Dark.NoDisplay" />
|
||||
<!-- NOTIFICATIONS -->
|
||||
<receiver android:name=".ui.widgets.notifications.WidgetNotificationsProvider"
|
||||
android:label="@string/widget_notifications_title">
|
||||
android:label="@string/widget_notifications_title"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||
</intent-filter>
|
||||
@ -104,7 +109,8 @@
|
||||
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
||||
<!-- LUCKY NUMBER -->
|
||||
<receiver android:name=".ui.widgets.luckynumber.WidgetLuckyNumberProvider"
|
||||
android:label="@string/widget_lucky_number_title">
|
||||
android:label="@string/widget_lucky_number_title"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||
</intent-filter>
|
||||
@ -124,29 +130,36 @@
|
||||
<activity android:name=".ui.base.CrashActivity"
|
||||
android:configChanges="orientation|screenSize|keyboardHidden"
|
||||
android:process=":error_activity"
|
||||
android:exported="false"
|
||||
android:theme="@style/DeadTheme" />
|
||||
<activity android:name=".ui.intro.ChangelogIntroActivity"
|
||||
android:configChanges="orientation|keyboardHidden"
|
||||
android:label="@string/app_name"
|
||||
android:exported="false"
|
||||
android:theme="@style/Theme.Intro" />
|
||||
<activity android:name=".ui.login.LoginActivity"
|
||||
android:configChanges="orientation|screenSize"
|
||||
android:launchMode="singleTop"
|
||||
android:exported="false"
|
||||
android:theme="@style/AppTheme.Light" />
|
||||
<activity android:name=".ui.home.CounterActivity"
|
||||
android:exported="false"
|
||||
android:theme="@style/AppTheme.Black" />
|
||||
<activity android:name=".ui.feedback.FeedbackActivity"
|
||||
android:configChanges="orientation|screenSize|keyboardHidden"
|
||||
android:label="@string/app_name"
|
||||
android:exported="false"
|
||||
android:theme="@style/AppTheme" />
|
||||
<activity android:name=".ui.settings.SettingsLicenseActivity"
|
||||
android:configChanges="orientation|keyboardHidden"
|
||||
android:exported="false"
|
||||
android:theme="@style/AppTheme" />
|
||||
<activity android:name="com.canhub.cropper.CropImageActivity"
|
||||
android:configChanges="orientation|keyboardHidden"
|
||||
android:exported="false"
|
||||
android:theme="@style/Base.Theme.AppCompat" />
|
||||
<activity android:name=".ui.base.BuildInvalidActivity" />
|
||||
<activity android:name=".ui.settings.contributors.ContributorsActivity" />
|
||||
<activity android:name=".ui.base.BuildInvalidActivity" android:exported="false" />
|
||||
<activity android:name=".ui.settings.contributors.ContributorsActivity" android:exported="false" />
|
||||
|
||||
<!-- _____ _
|
||||
| __ \ (_)
|
||||
@ -156,12 +169,14 @@
|
||||
|_| \_\___|\___\___|_| \_/ \___|_| |___/
|
||||
-->
|
||||
<receiver android:name=".receivers.UserPresentReceiver"
|
||||
android:enabled="true">
|
||||
android:enabled="true"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.USER_PRESENT" />
|
||||
</intent-filter>
|
||||
</receiver>
|
||||
<receiver android:name=".sync.UpdateDownloaderService$DownloadProgressReceiver">
|
||||
<receiver android:name=".sync.UpdateDownloaderService$DownloadProgressReceiver"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.DOWNLOAD_COMPLETE" />
|
||||
</intent-filter>
|
||||
|
@ -1,6 +1,8 @@
|
||||
<h3>Wersja 4.11.6, 2022-05-27</h3>
|
||||
<h3>Wersja 4.11.7, 2022-09-17</h3>
|
||||
<ul>
|
||||
<li>Poprawiono błędy formatowania wiadomości. @BxOxSxS</li>
|
||||
<li>Vulcan UONET+: naprawiono działanie systemu wiadomości. @Antoni-Czaplicki</li>
|
||||
<li>Poprawiono wyświetlanie lekcji odwołanych na stronie głównej.</li>
|
||||
<li>Dodano dostęp do Laboratorium na ekranie logowania.</li>
|
||||
</ul>
|
||||
<br>
|
||||
<br>
|
||||
|
@ -9,7 +9,7 @@
|
||||
|
||||
/*secret password - removed for source code publication*/
|
||||
static toys AES_IV[16] = {
|
||||
0xeb, 0x3c, 0x93, 0xf5, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
|
||||
0x59, 0x01, 0xcc, 0x81, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
|
||||
|
||||
unsigned char *agony(unsigned int laugh, unsigned char *box, unsigned char *heat);
|
||||
|
||||
|
@ -92,7 +92,7 @@ val MOBIDZIENNIK_USER_AGENT = SYSTEM_USER_AGENT
|
||||
|
||||
const val VULCAN_HEBE_USER_AGENT = "Dart/2.10 (dart:io)"
|
||||
const val VULCAN_HEBE_APP_NAME = "DzienniczekPlus 2.0"
|
||||
const val VULCAN_HEBE_APP_VERSION = "21.02.09 (G)"
|
||||
const val VULCAN_HEBE_APP_VERSION = "22.09.02 (G)"
|
||||
private const val VULCAN_API_DEVICE_NAME_PREFIX = "Szkolny.eu "
|
||||
private const val VULCAN_API_DEVICE_NAME_SUFFIX = " - nie usuwać"
|
||||
val VULCAN_API_DEVICE_NAME by lazy {
|
||||
@ -116,9 +116,11 @@ const val VULCAN_HEBE_ENDPOINT_GRADE_SUMMARY = "api/mobile/grade/summary"
|
||||
const val VULCAN_HEBE_ENDPOINT_HOMEWORK = "api/mobile/homework"
|
||||
const val VULCAN_HEBE_ENDPOINT_NOTICES = "api/mobile/note"
|
||||
const val VULCAN_HEBE_ENDPOINT_ATTENDANCE = "api/mobile/lesson"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGES = "api/mobile/message"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGES_STATUS = "api/mobile/message/status"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGES_SEND = "api/mobile/message"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGEBOX = "api/mobile/messagebox"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGEBOX_ADDRESSBOOK = "api/mobile/messagebox/addressbook"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGEBOX_MESSAGES = "api/mobile/messagebox/message"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGEBOX_STATUS = "api/mobile/messagebox/message/status"
|
||||
const val VULCAN_HEBE_ENDPOINT_MESSAGEBOX_SEND = "api/mobile/messagebox/message"
|
||||
const val VULCAN_HEBE_ENDPOINT_LUCKY_NUMBER = "api/mobile/school/lucky"
|
||||
|
||||
const val EDUDZIENNIK_USER_AGENT = "Szkolny.eu/${BuildConfig.VERSION_NAME}"
|
||||
|
@ -20,6 +20,10 @@ object Regexes {
|
||||
"""<br\s?/?>""".toRegex()
|
||||
}
|
||||
|
||||
val MESSAGE_META by lazy {
|
||||
"""^\[META:([A-z0-9-&=]+)]""".toRegex()
|
||||
}
|
||||
|
||||
|
||||
|
||||
val MOBIDZIENNIK_GRADES_SUBJECT_NAME by lazy {
|
||||
|
@ -222,15 +222,15 @@ class DataVulcan(app: App, profile: Profile?, loginStore: LoginStore) : Data(app
|
||||
get() { mHebeContext = mHebeContext ?: profile?.getStudentData("hebeContext", null); return mHebeContext }
|
||||
set(value) { profile?.putStudentData("hebeContext", value) ?: return; mHebeContext = value }
|
||||
|
||||
private var mSenderAddressHash: String? = null
|
||||
var senderAddressHash: String?
|
||||
get() { mSenderAddressHash = mSenderAddressHash ?: profile?.getStudentData("senderAddressHash", null); return mSenderAddressHash }
|
||||
set(value) { profile?.putStudentData("senderAddressHash", value) ?: return; mSenderAddressHash = value }
|
||||
private var mMessageBoxKey: String? = null
|
||||
var messageBoxKey: String?
|
||||
get() { mMessageBoxKey = mMessageBoxKey ?: profile?.getStudentData("messageBoxKey", null); return mMessageBoxKey }
|
||||
set(value) { profile?.putStudentData("messageBoxKey", value) ?: return; mMessageBoxKey = value }
|
||||
|
||||
private var mSenderAddressName: String? = null
|
||||
var senderAddressName: String?
|
||||
get() { mSenderAddressName = mSenderAddressName ?: profile?.getStudentData("senderAddressName", null); return mSenderAddressName }
|
||||
set(value) { profile?.putStudentData("senderAddressName", value) ?: return; mSenderAddressName = value }
|
||||
private var mMessageBoxName: String? = null
|
||||
var messageBoxName: String?
|
||||
get() { mMessageBoxName = mMessageBoxName ?: profile?.getStudentData("messageBoxName", null); return mMessageBoxName }
|
||||
set(value) { profile?.putStudentData("messageBoxName", value) ?: return; mMessageBoxName = value }
|
||||
|
||||
val apiUrl: String?
|
||||
get() {
|
||||
|
@ -12,6 +12,7 @@ const val ENDPOINT_VULCAN_WEB_LUCKY_NUMBERS = 2010
|
||||
const val ENDPOINT_VULCAN_HEBE_MAIN = 3000
|
||||
const val ENDPOINT_VULCAN_HEBE_PUSH_CONFIG = 3005
|
||||
const val ENDPOINT_VULCAN_HEBE_ADDRESSBOOK = 3010
|
||||
const val ENDPOINT_VULCAN_HEBE_ADDRESSBOOK_2 = 3011
|
||||
const val ENDPOINT_VULCAN_HEBE_TIMETABLE = 3020
|
||||
const val ENDPOINT_VULCAN_HEBE_EXAMS = 3030
|
||||
const val ENDPOINT_VULCAN_HEBE_GRADES = 3040
|
||||
@ -19,10 +20,11 @@ const val ENDPOINT_VULCAN_HEBE_GRADE_SUMMARY = 3050
|
||||
const val ENDPOINT_VULCAN_HEBE_HOMEWORK = 3060
|
||||
const val ENDPOINT_VULCAN_HEBE_NOTICES = 3070
|
||||
const val ENDPOINT_VULCAN_HEBE_ATTENDANCE = 3080
|
||||
const val ENDPOINT_VULCAN_HEBE_MESSAGES_INBOX = 3090
|
||||
const val ENDPOINT_VULCAN_HEBE_MESSAGES_SENT = 3100
|
||||
const val ENDPOINT_VULCAN_HEBE_TEACHERS = 3110
|
||||
const val ENDPOINT_VULCAN_HEBE_LUCKY_NUMBER = 3200
|
||||
const val ENDPOINT_VULCAN_HEBE_MESSAGE_BOXES = 3500
|
||||
const val ENDPOINT_VULCAN_HEBE_MESSAGES_INBOX = 3510
|
||||
const val ENDPOINT_VULCAN_HEBE_MESSAGES_SENT = 3520
|
||||
|
||||
val VulcanFeatures = listOf(
|
||||
// timetable
|
||||
@ -85,6 +87,8 @@ val VulcanFeatures = listOf(
|
||||
Feature(LOGIN_TYPE_VULCAN, FEATURE_ALWAYS_NEEDED, listOf(
|
||||
ENDPOINT_VULCAN_HEBE_MAIN to LOGIN_METHOD_VULCAN_HEBE,
|
||||
ENDPOINT_VULCAN_HEBE_ADDRESSBOOK to LOGIN_METHOD_VULCAN_HEBE,
|
||||
ENDPOINT_VULCAN_HEBE_TEACHERS to LOGIN_METHOD_VULCAN_HEBE
|
||||
ENDPOINT_VULCAN_HEBE_ADDRESSBOOK_2 to LOGIN_METHOD_VULCAN_HEBE,
|
||||
ENDPOINT_VULCAN_HEBE_TEACHERS to LOGIN_METHOD_VULCAN_HEBE,
|
||||
ENDPOINT_VULCAN_HEBE_MESSAGE_BOXES to LOGIN_METHOD_VULCAN_HEBE,
|
||||
), listOf(LOGIN_METHOD_VULCAN_HEBE))
|
||||
)
|
||||
|
@ -21,10 +21,12 @@ class VulcanData(val data: DataVulcan, val onSuccess: () -> Unit) {
|
||||
ENDPOINT_VULCAN_HEBE_MAIN,
|
||||
ENDPOINT_VULCAN_HEBE_PUSH_CONFIG,
|
||||
ENDPOINT_VULCAN_HEBE_ADDRESSBOOK,
|
||||
ENDPOINT_VULCAN_HEBE_ADDRESSBOOK_2,
|
||||
ENDPOINT_VULCAN_HEBE_TIMETABLE,
|
||||
ENDPOINT_VULCAN_HEBE_EXAMS,
|
||||
ENDPOINT_VULCAN_HEBE_HOMEWORK,
|
||||
ENDPOINT_VULCAN_HEBE_NOTICES,
|
||||
ENDPOINT_VULCAN_HEBE_MESSAGE_BOXES,
|
||||
ENDPOINT_VULCAN_HEBE_MESSAGES_INBOX,
|
||||
ENDPOINT_VULCAN_HEBE_MESSAGES_SENT,
|
||||
ENDPOINT_VULCAN_HEBE_TEACHERS,
|
||||
@ -107,6 +109,10 @@ class VulcanData(val data: DataVulcan, val onSuccess: () -> Unit) {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_addressbook)
|
||||
VulcanHebeAddressbook(data, lastSync, onSuccess)
|
||||
}
|
||||
ENDPOINT_VULCAN_HEBE_ADDRESSBOOK_2 -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_addressbook)
|
||||
VulcanHebeAddressbook2(data, lastSync, onSuccess)
|
||||
}
|
||||
ENDPOINT_VULCAN_HEBE_TEACHERS -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_teachers)
|
||||
VulcanHebeTeachers(data, lastSync, onSuccess)
|
||||
@ -139,6 +145,10 @@ class VulcanData(val data: DataVulcan, val onSuccess: () -> Unit) {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_attendance)
|
||||
VulcanHebeAttendance(data, lastSync, onSuccess)
|
||||
}
|
||||
ENDPOINT_VULCAN_HEBE_MESSAGE_BOXES -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages)
|
||||
VulcanHebeMessageBoxes(data, lastSync, onSuccess)
|
||||
}
|
||||
ENDPOINT_VULCAN_HEBE_MESSAGES_INBOX -> {
|
||||
data.startProgress(R.string.edziennik_progress_endpoint_messages_inbox)
|
||||
VulcanHebeMessages(data, lastSync, onSuccess).getMessages(Message.TYPE_RECEIVED)
|
||||
|
@ -14,7 +14,6 @@ import im.wangchao.mhttp.Response
|
||||
import im.wangchao.mhttp.body.MediaTypeUtils
|
||||
import im.wangchao.mhttp.callback.JsonCallbackHandler
|
||||
import io.github.wulkanowy.signer.hebe.getSignatureHeaders
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.data.api.*
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe.HebeFilterType
|
||||
@ -55,6 +54,15 @@ open class VulcanHebe(open val data: DataVulcan, open val lastSync: Long?) {
|
||||
return date.getLong("Timestamp") ?: return default
|
||||
}
|
||||
|
||||
fun buildDateTime(): JsonObject {
|
||||
return JsonObject(
|
||||
"Timestamp" to System.currentTimeMillis(),
|
||||
"Date" to Date.getToday().stringY_m_d,
|
||||
"DateDisplay" to Date.getToday().stringDmy,
|
||||
"Time" to Time.getNow().stringHMS,
|
||||
)
|
||||
}
|
||||
|
||||
fun getDate(json: JsonObject?, key: String): Date? {
|
||||
val date = json.getJsonObject(key)
|
||||
return date.getString("Date")?.let { Date.fromY_m_d(it) }
|
||||
@ -74,6 +82,22 @@ open class VulcanHebe(open val data: DataVulcan, open val lastSync: Long?) {
|
||||
return teacherId
|
||||
}
|
||||
|
||||
fun getTeacherRecipient(json: JsonObject): Teacher? {
|
||||
val globalKey = json.getString("GlobalKey") ?: return null
|
||||
if (globalKey == data.messageBoxKey)
|
||||
return null
|
||||
var name = json.getString("Name") ?: return null
|
||||
val group = json.getString("Group", "P")
|
||||
val loginId = "${globalKey};${group};${name}"
|
||||
val pattern = " - $group - (${data.schoolShort})"
|
||||
if (name.endsWith(pattern))
|
||||
name = name.substringBefore(pattern)
|
||||
val teacher = data.getTeacherByFirstLast(name, loginId)
|
||||
if (teacher.type == 0)
|
||||
teacher.type = Teacher.TYPE_OTHER
|
||||
return teacher
|
||||
}
|
||||
|
||||
fun getSubjectId(json: JsonObject?, key: String): Long? {
|
||||
val subject = json.getJsonObject(key)
|
||||
val subjectId = subject.getLong("Id") ?: return null
|
||||
@ -89,7 +113,7 @@ open class VulcanHebe(open val data: DataVulcan, open val lastSync: Long?) {
|
||||
}
|
||||
|
||||
fun getTeamId(json: JsonObject?, key: String): Long? {
|
||||
val team = json.getJsonObject(key)
|
||||
val team = json.getJsonObject(key) ?: return null
|
||||
val teamId = team.getLong("Id")
|
||||
var teamName = team.getString("Shortcut")
|
||||
?: team.getString("Name")
|
||||
@ -104,7 +128,7 @@ open class VulcanHebe(open val data: DataVulcan, open val lastSync: Long?) {
|
||||
}
|
||||
|
||||
fun getClassId(json: JsonObject?, key: String): Long? {
|
||||
val team = json.getJsonObject(key)
|
||||
val team = json.getJsonObject(key) ?: return null
|
||||
val teamId = team.getLong("Id")
|
||||
val teamName = data.profile?.studentClassName
|
||||
?: team.getString("Name")
|
||||
@ -148,7 +172,7 @@ open class VulcanHebe(open val data: DataVulcan, open val lastSync: Long?) {
|
||||
|
||||
fun isCurrentYear(dateTime: Long): Boolean {
|
||||
return profile?.let { profile ->
|
||||
return@let dateTime >= profile.dateSemester1Start.inMillis
|
||||
return@let dateTime >= profile.dateSemester1Start.inMillis - WEEK * MS
|
||||
} ?: false
|
||||
}
|
||||
|
||||
@ -355,6 +379,7 @@ open class VulcanHebe(open val data: DataVulcan, open val lastSync: Long?) {
|
||||
dateTo: Date? = null,
|
||||
lastSync: Long? = null,
|
||||
folder: Int? = null,
|
||||
messageBox: String? = null,
|
||||
params: Map<String, String> = mapOf(),
|
||||
includeFilterType: Boolean = true,
|
||||
onSuccess: (data: List<JsonObject>, response: Response?) -> Unit
|
||||
@ -378,6 +403,9 @@ open class VulcanHebe(open val data: DataVulcan, open val lastSync: Long?) {
|
||||
query["periodId"] = data.studentSemesterId.toString()
|
||||
query["pupilId"] = data.studentId.toString()
|
||||
}
|
||||
HebeFilterType.BY_MESSAGEBOX -> {
|
||||
query["box"] = messageBox ?: data.messageBoxKey ?: ""
|
||||
}
|
||||
}
|
||||
|
||||
if (dateFrom != null)
|
||||
|
@ -5,6 +5,7 @@
|
||||
package pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe
|
||||
|
||||
enum class HebeFilterType(val endpoint: String) {
|
||||
BY_MESSAGEBOX("byBox"),
|
||||
BY_PUPIL("byPupil"),
|
||||
BY_PERSON("byPerson"),
|
||||
BY_PERIOD("byPeriod")
|
||||
|
@ -5,6 +5,7 @@
|
||||
package pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe
|
||||
|
||||
import androidx.core.util.set
|
||||
import androidx.room.OnConflictStrategy
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_ADDRESSBOOK
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.DataVulcan
|
||||
@ -44,7 +45,6 @@ class VulcanHebeAddressbook(
|
||||
) { list, _ ->
|
||||
list.forEach { person ->
|
||||
val id = person.getString("Id") ?: return@forEach
|
||||
val loginId = person.getString("LoginId") ?: return@forEach
|
||||
|
||||
val idType = id.split("-")
|
||||
.getOrNull(0)
|
||||
@ -69,7 +69,7 @@ class VulcanHebeAddressbook(
|
||||
idLong,
|
||||
name,
|
||||
surname,
|
||||
loginId
|
||||
null
|
||||
).also {
|
||||
data.teacherList[idLong] = it
|
||||
}
|
||||
@ -108,13 +108,14 @@ class VulcanHebeAddressbook(
|
||||
}
|
||||
|
||||
teacher.setTeacherType(personType)
|
||||
teacher.typeDescription = roleText
|
||||
if (roleText != null)
|
||||
teacher.typeDescription = roleText
|
||||
}
|
||||
|
||||
if (teacher.type == 0)
|
||||
teacher.setTeacherType(typeBase)
|
||||
}
|
||||
|
||||
data.teacherOnConflictStrategy = OnConflictStrategy.REPLACE
|
||||
data.setSyncNext(ENDPOINT_VULCAN_HEBE_ADDRESSBOOK, 2 * DAY)
|
||||
onSuccess(ENDPOINT_VULCAN_HEBE_ADDRESSBOOK)
|
||||
}
|
||||
|
@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright (c) Kuba Szczodrzyński 2021-2-21.
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe
|
||||
|
||||
import androidx.room.OnConflictStrategy
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGEBOX_ADDRESSBOOK
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.ENDPOINT_VULCAN_HEBE_ADDRESSBOOK_2
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.VulcanHebe
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Teacher.Companion.TYPE_OTHER
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Teacher.Companion.TYPE_PARENT
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Teacher.Companion.TYPE_STUDENT
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Teacher.Companion.TYPE_TEACHER
|
||||
import pl.szczodrzynski.edziennik.ext.DAY
|
||||
import pl.szczodrzynski.edziennik.ext.getString
|
||||
|
||||
class VulcanHebeAddressbook2(
|
||||
override val data: DataVulcan,
|
||||
override val lastSync: Long?,
|
||||
val onSuccess: (endpointId: Int) -> Unit
|
||||
) : VulcanHebe(data, lastSync) {
|
||||
companion object {
|
||||
const val TAG = "VulcanHebeAddressbook2"
|
||||
}
|
||||
|
||||
init {
|
||||
apiGetList(
|
||||
TAG,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGEBOX_ADDRESSBOOK,
|
||||
HebeFilterType.BY_MESSAGEBOX,
|
||||
messageBox = data.messageBoxKey,
|
||||
lastSync = lastSync,
|
||||
includeFilterType = false
|
||||
) { list, _ ->
|
||||
list.forEach { person ->
|
||||
val teacher = getTeacherRecipient(person) ?: return@forEach
|
||||
val group = person.getString("Group", "P")
|
||||
if (teacher.type == TYPE_OTHER) {
|
||||
teacher.type = when (group) {
|
||||
"P" -> TYPE_TEACHER // Pracownik
|
||||
"O" -> TYPE_PARENT // Opiekun
|
||||
"U" -> TYPE_STUDENT // Uczeń
|
||||
else -> TYPE_OTHER
|
||||
}
|
||||
}
|
||||
}
|
||||
data.teacherOnConflictStrategy = OnConflictStrategy.REPLACE
|
||||
data.setSyncNext(ENDPOINT_VULCAN_HEBE_ADDRESSBOOK_2, 2 * DAY)
|
||||
onSuccess(ENDPOINT_VULCAN_HEBE_ADDRESSBOOK_2)
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,43 @@
|
||||
/*
|
||||
* Copyright (c) Kuba Szczodrzyński 2022-9-16.
|
||||
*/
|
||||
|
||||
package pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe
|
||||
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGEBOX
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.ENDPOINT_VULCAN_HEBE_MESSAGE_BOXES
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.VulcanHebe
|
||||
import pl.szczodrzynski.edziennik.ext.DAY
|
||||
import pl.szczodrzynski.edziennik.ext.getString
|
||||
|
||||
class VulcanHebeMessageBoxes(
|
||||
override val data: DataVulcan,
|
||||
override val lastSync: Long?,
|
||||
val onSuccess: (endpointId: Int) -> Unit
|
||||
) : VulcanHebe(data, lastSync) {
|
||||
companion object {
|
||||
const val TAG = "VulcanHebeMessageBoxes"
|
||||
}
|
||||
|
||||
init {
|
||||
apiGetList(
|
||||
TAG,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGEBOX,
|
||||
lastSync = lastSync
|
||||
) { list, _ ->
|
||||
for (messageBox in list) {
|
||||
val name = messageBox.getString("Name") ?: continue
|
||||
val studentName = profile?.studentNameLong ?: continue
|
||||
if (!name.startsWith(studentName))
|
||||
continue
|
||||
|
||||
data.messageBoxKey = messageBox.getString("GlobalKey")
|
||||
data.messageBoxName = name
|
||||
break
|
||||
}
|
||||
data.setSyncNext(ENDPOINT_VULCAN_HEBE_MESSAGE_BOXES, 7 * DAY)
|
||||
onSuccess(ENDPOINT_VULCAN_HEBE_MESSAGE_BOXES)
|
||||
}
|
||||
}
|
||||
}
|
@ -4,22 +4,21 @@
|
||||
|
||||
package pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe
|
||||
|
||||
import androidx.core.util.set
|
||||
import com.google.gson.JsonObject
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.MainActivity.Companion.DRAWER_ITEM_MESSAGES
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGES
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGEBOX_MESSAGES
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.ENDPOINT_VULCAN_HEBE_MESSAGES_INBOX
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.ENDPOINT_VULCAN_HEBE_MESSAGES_SENT
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.VulcanHebe
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.*
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Message
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Message.Companion.TYPE_DELETED
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Message.Companion.TYPE_RECEIVED
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Message.Companion.TYPE_SENT
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.MessageRecipient
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Metadata
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.SYNC_ALWAYS
|
||||
import pl.szczodrzynski.edziennik.ext.*
|
||||
import pl.szczodrzynski.edziennik.utils.Utils
|
||||
import pl.szczodrzynski.navlib.crc16
|
||||
|
||||
class VulcanHebeMessages(
|
||||
override val data: DataVulcan,
|
||||
@ -27,29 +26,7 @@ class VulcanHebeMessages(
|
||||
val onSuccess: (endpointId: Int) -> Unit
|
||||
) : VulcanHebe(data, lastSync) {
|
||||
companion object {
|
||||
const val TAG = "VulcanHebeMessagesInbox"
|
||||
}
|
||||
|
||||
private fun getPersonId(json: JsonObject): Long {
|
||||
val senderLoginId = json.getInt("LoginId") ?: return -1
|
||||
/*if (senderLoginId == data.studentLoginId)
|
||||
return -1*/
|
||||
|
||||
val senderName = json.getString("Address") ?: return -1
|
||||
val senderNameSplit = senderName.splitName()
|
||||
val senderLoginIdStr = senderLoginId.toString()
|
||||
val teacher = data.teacherList.singleOrNull { it.loginId == senderLoginIdStr }
|
||||
?: Teacher(
|
||||
profileId,
|
||||
-1 * crc16(senderName).toLong(),
|
||||
senderNameSplit?.second ?: "",
|
||||
senderNameSplit?.first ?: "",
|
||||
senderLoginIdStr
|
||||
).also {
|
||||
it.setTeacherType(Teacher.TYPE_OTHER)
|
||||
data.teacherList[it.id] = it
|
||||
}
|
||||
return teacher.id
|
||||
const val TAG = "VulcanHebeMessages"
|
||||
}
|
||||
|
||||
fun getMessages(messageType: Int) {
|
||||
@ -64,17 +41,28 @@ class VulcanHebeMessages(
|
||||
TYPE_SENT -> ENDPOINT_VULCAN_HEBE_MESSAGES_SENT
|
||||
else -> ENDPOINT_VULCAN_HEBE_MESSAGES_INBOX
|
||||
}
|
||||
|
||||
val messageBox = data.messageBoxKey
|
||||
if (messageBox == null) {
|
||||
onSuccess(endpointId)
|
||||
return
|
||||
}
|
||||
|
||||
apiGetList(
|
||||
TAG,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGES,
|
||||
HebeFilterType.BY_PERSON,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGEBOX_MESSAGES,
|
||||
HebeFilterType.BY_MESSAGEBOX,
|
||||
messageBox = data.messageBoxKey,
|
||||
folder = folder,
|
||||
lastSync = lastSync
|
||||
) { list, _ ->
|
||||
list.forEach { message ->
|
||||
val id = message.getLong("Id") ?: return@forEach
|
||||
val uuid = message.getString("Id") ?: return@forEach
|
||||
val id = Utils.crc32(uuid.toByteArray())
|
||||
val globalKey = message.getString("GlobalKey", "")
|
||||
val threadKey = message.getString("ThreadKey", "")
|
||||
val subject = message.getString("Subject") ?: return@forEach
|
||||
val body = message.getString("Content") ?: return@forEach
|
||||
var body = message.getString("Content") ?: return@forEach
|
||||
|
||||
val sender = message.getJsonObject("Sender") ?: return@forEach
|
||||
|
||||
@ -83,13 +71,27 @@ class VulcanHebeMessages(
|
||||
|
||||
if (!isCurrentYear(sentDate)) return@forEach
|
||||
|
||||
val senderId = if (messageType == TYPE_RECEIVED)
|
||||
getTeacherRecipient(sender)?.id
|
||||
else
|
||||
null
|
||||
|
||||
val meta = mutableMapOf(
|
||||
"uuid" to uuid,
|
||||
"globalKey" to globalKey,
|
||||
"threadKey" to threadKey,
|
||||
)
|
||||
val metaString = meta.map { "${it.key}=${it.value}" }.join("&")
|
||||
body = "[META:${metaString}]" + body
|
||||
body = body.replace("\n", "<br>")
|
||||
|
||||
val messageObject = Message(
|
||||
profileId = profileId,
|
||||
id = id,
|
||||
type = messageType,
|
||||
subject = subject,
|
||||
body = body.replace("\n", "<br>"),
|
||||
senderId = if (messageType == TYPE_RECEIVED) getPersonId(sender) else null,
|
||||
body = body,
|
||||
senderId = senderId,
|
||||
addedDate = sentDate
|
||||
)
|
||||
|
||||
@ -101,9 +103,14 @@ class VulcanHebeMessages(
|
||||
else -1
|
||||
|
||||
for (receiver in receivers) {
|
||||
val recipientId = if (messageType == TYPE_SENT)
|
||||
getTeacherRecipient(receiver)?.id ?: -1
|
||||
else
|
||||
-1
|
||||
|
||||
val messageRecipientObject = MessageRecipient(
|
||||
profileId,
|
||||
if (messageType == TYPE_SENT) getPersonId(receiver) else -1,
|
||||
recipientId,
|
||||
-1,
|
||||
receiverReadDate,
|
||||
id
|
||||
@ -115,6 +122,9 @@ class VulcanHebeMessages(
|
||||
?.asJsonObjectList()
|
||||
?: return@forEach
|
||||
|
||||
messageObject.attachmentIds = mutableListOf()
|
||||
messageObject.attachmentNames = mutableListOf()
|
||||
messageObject.attachmentSizes = mutableListOf()
|
||||
for (attachment in attachments) {
|
||||
val fileName = attachment.getString("Name") ?: continue
|
||||
val url = attachment.getString("Link") ?: continue
|
||||
|
@ -5,7 +5,7 @@
|
||||
package pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe
|
||||
|
||||
import org.greenrobot.eventbus.EventBus
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGES_STATUS
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGEBOX_STATUS
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.VulcanHebe
|
||||
import pl.szczodrzynski.edziennik.data.api.events.MessageGetEvent
|
||||
@ -23,13 +23,19 @@ class VulcanHebeMessagesChangeStatus(
|
||||
const val TAG = "VulcanHebeMessagesChangeStatus"
|
||||
}
|
||||
|
||||
init {
|
||||
init { let {
|
||||
val messageKey = messageObject.body?.let { data.parseMessageMeta(it) }?.get("globalKey") ?: run {
|
||||
EventBus.getDefault().postSticky(MessageGetEvent(messageObject))
|
||||
onSuccess()
|
||||
return@let
|
||||
}
|
||||
|
||||
apiPost(
|
||||
TAG,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGES_STATUS,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGEBOX_STATUS,
|
||||
payload = JsonObject(
|
||||
"MessageId" to messageObject.id,
|
||||
"LoginId" to data.studentLoginId,
|
||||
"BoxKey" to data.messageBoxKey,
|
||||
"MessageKey" to messageKey,
|
||||
"Status" to 1
|
||||
)
|
||||
) { _: Boolean, _ ->
|
||||
@ -61,5 +67,5 @@ class VulcanHebeMessagesChangeStatus(
|
||||
EventBus.getDefault().postSticky(MessageGetEvent(messageObject))
|
||||
onSuccess()
|
||||
}
|
||||
}
|
||||
}}
|
||||
}
|
||||
|
@ -4,17 +4,20 @@
|
||||
|
||||
package pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.hebe
|
||||
|
||||
import com.google.gson.JsonArray
|
||||
import com.google.gson.JsonObject
|
||||
import org.greenrobot.eventbus.EventBus
|
||||
import pl.szczodrzynski.edziennik.*
|
||||
import pl.szczodrzynski.edziennik.data.api.ERROR_MESSAGE_NOT_SENT
|
||||
import pl.szczodrzynski.edziennik.data.api.ERROR_VULCAN_HEBE_MISSING_SENDER_ENTRY
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGES_SEND
|
||||
import pl.szczodrzynski.edziennik.data.api.VULCAN_HEBE_ENDPOINT_MESSAGEBOX_SEND
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.DataVulcan
|
||||
import pl.szczodrzynski.edziennik.data.api.edziennik.vulcan.data.VulcanHebe
|
||||
import pl.szczodrzynski.edziennik.data.api.events.MessageSentEvent
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Message
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.Teacher
|
||||
import pl.szczodrzynski.edziennik.ext.*
|
||||
import java.util.UUID
|
||||
|
||||
class VulcanHebeSendMessage(
|
||||
override val data: DataVulcan,
|
||||
@ -28,9 +31,9 @@ class VulcanHebeSendMessage(
|
||||
}
|
||||
|
||||
init {
|
||||
if (data.senderAddressName == null || data.senderAddressHash == null) {
|
||||
VulcanHebeMain(data).getStudents(data.profile, null) {
|
||||
if (data.senderAddressName == null || data.senderAddressHash == null) {
|
||||
if (data.messageBoxKey == null || data.messageBoxName == null) {
|
||||
VulcanHebeMessageBoxes(data, 0) {
|
||||
if (data.messageBoxKey == null || data.messageBoxName == null) {
|
||||
data.error(TAG, ERROR_VULCAN_HEBE_MISSING_SENDER_ENTRY)
|
||||
}
|
||||
else {
|
||||
@ -44,47 +47,64 @@ class VulcanHebeSendMessage(
|
||||
}
|
||||
|
||||
private fun sendMessage() {
|
||||
val uuid = UUID.randomUUID().toString()
|
||||
val globalKey = UUID.randomUUID().toString()
|
||||
val partition = "${data.symbol}-${data.schoolSymbol}"
|
||||
|
||||
val recipientsArray = JsonArray()
|
||||
recipients.forEach { teacher ->
|
||||
val loginId = teacher.loginId?.split(";", limit = 3) ?: return@forEach
|
||||
val key = loginId.getOrNull(0) ?: teacher.loginId
|
||||
val group = loginId.getOrNull(1)
|
||||
val name = loginId.getOrNull(2)
|
||||
if (key?.toIntOrNull() != null) {
|
||||
// raise error for old-format (non-UUID) login IDs
|
||||
data.error(TAG, ERROR_MESSAGE_NOT_SENT)
|
||||
return
|
||||
}
|
||||
recipientsArray += JsonObject(
|
||||
"Address" to teacher.fullNameLastFirst,
|
||||
"LoginId" to (teacher.loginId?.toIntOrNull() ?: return@forEach),
|
||||
"Initials" to teacher.initialsLastFirst,
|
||||
"AddressHash" to teacher.fullNameLastFirst.sha1Hex()
|
||||
"Id" to "${data.messageBoxKey}-${key}",
|
||||
"Partition" to partition,
|
||||
"Owner" to data.messageBoxKey,
|
||||
"GlobalKey" to key,
|
||||
"Name" to name,
|
||||
"Group" to group,
|
||||
"Initials" to "",
|
||||
"HasRead" to 0,
|
||||
)
|
||||
}
|
||||
|
||||
val senderName = (profile?.accountName ?: profile?.studentNameLong)
|
||||
?.swapFirstLastName() ?: ""
|
||||
val sender = JsonObject(
|
||||
"Address" to data.senderAddressName,
|
||||
"LoginId" to data.studentLoginId.toString(),
|
||||
"Initials" to senderName.getNameInitials(),
|
||||
"AddressHash" to data.senderAddressHash
|
||||
"Id" to "0",
|
||||
"Partition" to partition,
|
||||
"Owner" to data.messageBoxKey,
|
||||
"GlobalKey" to data.messageBoxKey,
|
||||
"Name" to data.messageBoxName,
|
||||
"Group" to "",
|
||||
"Initials" to "",
|
||||
"HasRead" to 0,
|
||||
)
|
||||
|
||||
apiPost(
|
||||
TAG,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGES_SEND,
|
||||
VULCAN_HEBE_ENDPOINT_MESSAGEBOX_SEND,
|
||||
payload = JsonObject(
|
||||
"Status" to 1,
|
||||
"Sender" to sender,
|
||||
"DateSent" to null,
|
||||
"DateRead" to null,
|
||||
"Content" to text,
|
||||
"Receiver" to recipientsArray,
|
||||
"Id" to 0,
|
||||
"Id" to uuid,
|
||||
"GlobalKey" to globalKey,
|
||||
"Partition" to partition,
|
||||
"ThreadKey" to globalKey, // TODO correct threadKey for reply messages
|
||||
"Subject" to subject,
|
||||
"Attachments" to null,
|
||||
"Self" to null
|
||||
"Content" to text,
|
||||
"Status" to 1,
|
||||
"Owner" to data.messageBoxKey,
|
||||
"DateSent" to buildDateTime(),
|
||||
"DateRead" to null,
|
||||
"Sender" to sender,
|
||||
"Receiver" to recipientsArray,
|
||||
"Attachments" to JsonArray(),
|
||||
)
|
||||
) { json: JsonObject, _ ->
|
||||
val messageId = json.getLong("Id")
|
||||
|
||||
if (messageId == null) {
|
||||
// TODO error
|
||||
return@apiPost
|
||||
}
|
||||
) { _: JsonObject, _ ->
|
||||
// TODO handle errors
|
||||
|
||||
VulcanHebeMessages(data, null) {
|
||||
val message = data.messageList.firstOrNull { it.isSent && it.subject == subject }
|
||||
|
@ -45,6 +45,7 @@ class VulcanHebeTeachers(
|
||||
|
||||
when (subjectName) {
|
||||
"Pedagog" -> teacher.setTeacherType(Teacher.TYPE_PEDAGOGUE)
|
||||
"Dyrektor" -> teacher.setTeacherType(Teacher.TYPE_PRINCIPAL)
|
||||
else -> {
|
||||
val subjectId = data.getSubject(null, subjectName).id
|
||||
if (!teacher.subjects.contains(subjectId))
|
||||
|
@ -11,6 +11,7 @@ import pl.szczodrzynski.edziennik.App
|
||||
import pl.szczodrzynski.edziennik.BuildConfig
|
||||
import pl.szczodrzynski.edziennik.R
|
||||
import pl.szczodrzynski.edziennik.data.api.ERROR_REQUEST_FAILURE
|
||||
import pl.szczodrzynski.edziennik.data.api.Regexes.MESSAGE_META
|
||||
import pl.szczodrzynski.edziennik.data.api.interfaces.EndpointCallback
|
||||
import pl.szczodrzynski.edziennik.data.db.AppDb
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.*
|
||||
@ -489,11 +490,19 @@ abstract class Data(val app: App, val profile: Profile?, val loginStore: LoginSt
|
||||
teacherList[id] = this
|
||||
}
|
||||
return obj.also {
|
||||
if (loginId != null && it.loginId != null)
|
||||
if (loginId != null)
|
||||
it.loginId = loginId
|
||||
if (firstName.length > 1)
|
||||
it.name = firstName
|
||||
it.surname = lastName
|
||||
}
|
||||
}
|
||||
|
||||
fun parseMessageMeta(body: String): Map<String, String>? {
|
||||
val match = MESSAGE_META.find(body) ?: return null
|
||||
return match[1].split("&").associateBy(
|
||||
{ it.substringBefore("=") },
|
||||
{ it.substringAfter("=") },
|
||||
)
|
||||
}
|
||||
}
|
||||
|
@ -46,6 +46,6 @@ object Signing {
|
||||
|
||||
/*fun provideKey(param1: String, param2: Long): ByteArray {*/
|
||||
fun pleaseStopRightNow(param1: String, param2: Long): ByteArray {
|
||||
return "$param1.MTIzNDU2Nzg5MDocQtfDuE===.$param2".sha256()
|
||||
return "$param1.MTIzNDU2Nzg5MDgEKON2ua===.$param2".sha256()
|
||||
}
|
||||
}
|
||||
|
@ -109,7 +109,7 @@ abstract class EventDao : BaseDao<Event, EventFull> {
|
||||
abstract fun removeNotManual(profileId: Int)*/
|
||||
|
||||
@RawQuery
|
||||
abstract fun dontKeepFuture(query: SupportSQLiteQuery?): Long
|
||||
abstract fun dontKeepFuture(query: SupportSQLiteQuery): Long
|
||||
|
||||
@Transaction
|
||||
open fun dontKeepFuture(profileId: Int, todayDate: Date, filter: String) {
|
||||
|
@ -8,6 +8,7 @@ import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.fragment.app.Fragment
|
||||
import kotlinx.coroutines.CoroutineScope
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
@ -17,6 +18,8 @@ import pl.szczodrzynski.edziennik.MainActivity
|
||||
import pl.szczodrzynski.edziennik.databinding.TemplateFragmentBinding
|
||||
import pl.szczodrzynski.edziennik.ext.addOnPageSelectedListener
|
||||
import pl.szczodrzynski.edziennik.ui.base.lazypager.FragmentLazyPagerAdapter
|
||||
import pl.szczodrzynski.edziennik.ui.login.LoginActivity
|
||||
import pl.szczodrzynski.edziennik.utils.SwipeRefreshLayoutNoTouch
|
||||
import kotlin.coroutines.CoroutineContext
|
||||
|
||||
class LabFragment : Fragment(), CoroutineScope {
|
||||
@ -26,7 +29,7 @@ class LabFragment : Fragment(), CoroutineScope {
|
||||
}
|
||||
|
||||
private lateinit var app: App
|
||||
private lateinit var activity: MainActivity
|
||||
private lateinit var activity: AppCompatActivity
|
||||
private lateinit var b: TemplateFragmentBinding
|
||||
|
||||
private val job: Job = Job()
|
||||
@ -36,11 +39,14 @@ class LabFragment : Fragment(), CoroutineScope {
|
||||
// local/private variables go here
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
||||
activity = (getActivity() as MainActivity?) ?: return null
|
||||
activity = (getActivity() as AppCompatActivity?) ?: return null
|
||||
context ?: return null
|
||||
app = activity.application as App
|
||||
b = TemplateFragmentBinding.inflate(inflater)
|
||||
b.refreshLayout.setParent(activity.swipeRefreshLayout)
|
||||
when (activity) {
|
||||
is MainActivity -> b.refreshLayout.setParent((activity as MainActivity).swipeRefreshLayout)
|
||||
is LoginActivity -> b.refreshLayout.setParent((activity as LoginActivity).swipeRefreshLayout)
|
||||
}
|
||||
b.refreshLayout.isEnabled = false
|
||||
return b.root
|
||||
}
|
||||
|
@ -9,6 +9,7 @@ import android.os.Process
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.sqlite.db.SimpleSQLiteQuery
|
||||
import com.chuckerteam.chucker.api.Chucker
|
||||
@ -35,7 +36,7 @@ class LabPageFragment : LazyFragment(), CoroutineScope {
|
||||
}
|
||||
|
||||
private lateinit var app: App
|
||||
private lateinit var activity: MainActivity
|
||||
private lateinit var activity: AppCompatActivity
|
||||
private lateinit var b: LabFragmentBinding
|
||||
|
||||
private val job: Job = Job()
|
||||
@ -45,7 +46,7 @@ class LabPageFragment : LazyFragment(), CoroutineScope {
|
||||
// local/private variables go here
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
||||
activity = (getActivity() as MainActivity?) ?: return null
|
||||
activity = (getActivity() as AppCompatActivity?) ?: return null
|
||||
context ?: return null
|
||||
app = activity.application as App
|
||||
b = LabFragmentBinding.inflate(inflater)
|
||||
@ -55,6 +56,16 @@ class LabPageFragment : LazyFragment(), CoroutineScope {
|
||||
override fun onPageCreated(): Boolean {
|
||||
b.app = app
|
||||
|
||||
if (app.profile.id == 0) {
|
||||
b.last10unseen.isVisible = false
|
||||
b.fullSync.isVisible = false
|
||||
b.clearProfile.isVisible = false
|
||||
b.rodo.isVisible = false
|
||||
b.removeHomework.isVisible = false
|
||||
b.unarchive.isVisible = false
|
||||
b.profile.isVisible = false
|
||||
}
|
||||
|
||||
b.last10unseen.onClick {
|
||||
launch(Dispatchers.Default) {
|
||||
val events = app.db.eventDao().getAllNow(App.profileId)
|
||||
@ -139,7 +150,8 @@ class LabPageFragment : LazyFragment(), CoroutineScope {
|
||||
b.profile += profiles.map { TextInputDropDown.Item(it.id.toLong(), "${it.id} ${it.name} archived ${it.archived}", tag = it) }
|
||||
b.profile.select(app.profileId.toLong())
|
||||
b.profile.setOnChangeListener {
|
||||
activity.loadProfile(it.id.toInt())
|
||||
if (activity is MainActivity)
|
||||
(activity as MainActivity).loadProfile(it.id.toInt())
|
||||
return@setOnChangeListener true
|
||||
}
|
||||
|
||||
|
@ -8,6 +8,7 @@ import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.appcompat.app.AppCompatActivity
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||
@ -22,6 +23,7 @@ import pl.szczodrzynski.edziennik.ext.input
|
||||
import pl.szczodrzynski.edziennik.ext.set
|
||||
import pl.szczodrzynski.edziennik.ext.startCoroutineTimer
|
||||
import pl.szczodrzynski.edziennik.ui.base.lazypager.LazyFragment
|
||||
import pl.szczodrzynski.edziennik.ui.login.LoginActivity
|
||||
import pl.szczodrzynski.edziennik.utils.SimpleDividerItemDecoration
|
||||
import kotlin.coroutines.CoroutineContext
|
||||
|
||||
@ -31,7 +33,7 @@ class LabProfileFragment : LazyFragment(), CoroutineScope {
|
||||
}
|
||||
|
||||
private lateinit var app: App
|
||||
private lateinit var activity: MainActivity
|
||||
private lateinit var activity: AppCompatActivity
|
||||
private lateinit var b: TemplateListPageFragmentBinding
|
||||
|
||||
private val job: Job = Job()
|
||||
@ -45,7 +47,7 @@ class LabProfileFragment : LazyFragment(), CoroutineScope {
|
||||
}
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
|
||||
activity = (getActivity() as MainActivity?) ?: return null
|
||||
activity = (getActivity() as AppCompatActivity?) ?: return null
|
||||
context ?: return null
|
||||
app = activity.application as App
|
||||
b = TemplateListPageFragmentBinding.inflate(inflater)
|
||||
@ -142,7 +144,10 @@ class LabProfileFragment : LazyFragment(), CoroutineScope {
|
||||
.show()
|
||||
}
|
||||
catch (e: Exception) {
|
||||
activity.error(ApiError.fromThrowable(TAG, e))
|
||||
if (activity is MainActivity)
|
||||
(activity as MainActivity).error(ApiError.fromThrowable(TAG, e))
|
||||
if (activity is LoginActivity)
|
||||
(activity as LoginActivity).error(ApiError.fromThrowable(TAG, e))
|
||||
}
|
||||
})
|
||||
|
||||
|
@ -198,7 +198,7 @@ class HomeFragment : Fragment(), CoroutineScope {
|
||||
}
|
||||
}
|
||||
|
||||
override fun performAccessibilityAction(host: View, action: Int, args: Bundle): Boolean {
|
||||
override fun performAccessibilityAction(host: View, action: Int, args: Bundle?): Boolean {
|
||||
val fromPosition: Int = b.list.getChildLayoutPosition(host)
|
||||
if (action == R.id.move_card_down_action) {
|
||||
swapCards(fromPosition, fromPosition + 1, adapter)
|
||||
|
@ -75,7 +75,7 @@ class HomeTimetableCard(
|
||||
private var counterEnd: Time? = null
|
||||
private var subjectSpannable: CharSequence? = null
|
||||
|
||||
private val ignoreCancelled = true
|
||||
private val ignoreCancelled = false
|
||||
|
||||
private val countInSeconds: Boolean
|
||||
get() = app.config.timetable.countInSeconds
|
||||
@ -160,6 +160,9 @@ class HomeTimetableCard(
|
||||
&& it.displayEndTime > now
|
||||
&& !(it.isCancelled && ignoreCancelled)
|
||||
}
|
||||
if (!ignoreCancelled && lessons.all { it.isCancelled })
|
||||
// skip current day if all lessons are cancelled
|
||||
lessons = listOf()
|
||||
while ((lessons.isEmpty() || lessons.none {
|
||||
it.type != Lesson.TYPE_NO_LESSONS
|
||||
&& (it.displayDate != today
|
||||
@ -174,6 +177,7 @@ class HomeTimetableCard(
|
||||
it.profileId == profile.id
|
||||
&& it.displayDate == timetableDate
|
||||
}
|
||||
lessons = lessons.dropWhile { it.isCancelled }
|
||||
|
||||
if (lessons.isEmpty())
|
||||
break
|
||||
@ -238,15 +242,18 @@ class HomeTimetableCard(
|
||||
b.counter.visibility = View.GONE
|
||||
|
||||
val now = syncedNow
|
||||
val firstLesson = lessons.firstOrNull()
|
||||
val lastLesson = lessons.lastOrNull()
|
||||
val firstLesson = lessons.firstOrNull { !it.isCancelled }
|
||||
val lastLesson = lessons.lastOrNull { !it.isCancelled }
|
||||
val skipFirst = if (firstLesson == null) 0 else lessons.indexOf(firstLesson)
|
||||
val skipLast = if (lastLesson == null) 0 else lessons.size - 1 - lessons.indexOf(lastLesson)
|
||||
val lessonCount = lessons.size - skipFirst - skipLast
|
||||
|
||||
if (isToday) {
|
||||
// today
|
||||
b.dayInfo.setText(R.string.home_timetable_today)
|
||||
b.lessonInfo.setText(
|
||||
R.string.home_timetable_lessons_remaining,
|
||||
lessons.size,
|
||||
lessonCount,
|
||||
lastLesson?.displayEndTime?.stringHM ?: "?"
|
||||
)
|
||||
counterStart = firstLesson?.displayStartTime
|
||||
@ -291,12 +298,14 @@ class HomeTimetableCard(
|
||||
b.dayInfo.setText(dayInfoRes, Week.getFullDayName(timetableDate.weekDay), timetableDate.formattedString)
|
||||
b.lessonInfo.setText(
|
||||
R.string.home_timetable_lessons_info,
|
||||
lessons.size,
|
||||
lessonCount,
|
||||
firstLesson?.displayStartTime?.stringHM ?: "?",
|
||||
lastLesson?.displayEndTime?.stringHM ?: "?"
|
||||
)
|
||||
|
||||
b.lessonBig.setText(R.string.home_timetable_lesson_first, firstLesson.subjectSpannable)
|
||||
b.counter.visibility = View.VISIBLE
|
||||
b.counter.text = firstLesson?.displayStartTime?.stringHM
|
||||
firstLesson?.displayClassroom?.let {
|
||||
b.classroom.visibility = View.VISIBLE
|
||||
b.classroom.text = it
|
||||
@ -308,9 +317,8 @@ class HomeTimetableCard(
|
||||
val text = mutableListOf<CharSequence>(
|
||||
activity.getString(R.string.home_timetable_later)
|
||||
)
|
||||
var first = true
|
||||
for (lesson in lessons) {
|
||||
if (first) { first = false; continue }
|
||||
val nextLessons = lessons.drop(skipFirst + 1)
|
||||
for (lesson in nextLessons) {
|
||||
text += listOf(
|
||||
lesson.displayStartTime?.stringHM,
|
||||
lesson.subjectSpannable
|
||||
@ -363,7 +371,10 @@ class HomeTimetableCard(
|
||||
b.progress.visibility = View.GONE
|
||||
b.counter.visibility = View.VISIBLE
|
||||
val diff = counterStart - now
|
||||
b.counter.text = activity.timeTill(diff.toInt(), "\n", countInSeconds)
|
||||
if (diff >= 60 * MINUTE)
|
||||
b.counter.text = counterStart.stringHM
|
||||
else
|
||||
b.counter.text = activity.timeTill(diff.toInt(), "\n", countInSeconds)
|
||||
}
|
||||
else {
|
||||
// the lesson is right now
|
||||
|
@ -20,6 +20,7 @@ import pl.szczodrzynski.edziennik.data.api.models.ApiError
|
||||
import pl.szczodrzynski.edziennik.data.db.entity.LoginStore
|
||||
import pl.szczodrzynski.edziennik.databinding.LoginActivityBinding
|
||||
import pl.szczodrzynski.edziennik.ui.error.ErrorSnackbar
|
||||
import pl.szczodrzynski.edziennik.utils.SwipeRefreshLayoutNoTouch
|
||||
import kotlin.coroutines.CoroutineContext
|
||||
|
||||
class LoginActivity : AppCompatActivity(), CoroutineScope {
|
||||
@ -32,6 +33,7 @@ class LoginActivity : AppCompatActivity(), CoroutineScope {
|
||||
lateinit var navOptions: NavOptions
|
||||
val nav by lazy { Navigation.findNavController(this, R.id.nav_host_fragment) }
|
||||
val errorSnackbar: ErrorSnackbar by lazy { ErrorSnackbar(this) }
|
||||
val swipeRefreshLayout: SwipeRefreshLayoutNoTouch by lazy { b.swipeRefreshLayout }
|
||||
|
||||
private val job: Job = Job()
|
||||
override val coroutineContext: CoroutineContext
|
||||
|
@ -66,6 +66,8 @@ class LoginChooserFragment : Fragment(), CoroutineScope {
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
if (!isAdded) return
|
||||
|
||||
val adapter = LoginChooserAdapter(activity, this::onLoginModeClicked)
|
||||
|
||||
b.versionText.setText(
|
||||
R.string.login_chooser_version_format,
|
||||
app.buildManager.versionName,
|
||||
@ -73,10 +75,33 @@ class LoginChooserFragment : Fragment(), CoroutineScope {
|
||||
)
|
||||
b.versionText.onClick {
|
||||
app.buildManager.showVersionDialog(activity)
|
||||
if (!App.devMode)
|
||||
return@onClick
|
||||
if (adapter.items.firstOrNull { it is LoginInfo.Register && it.internalName == "lab" } != null)
|
||||
return@onClick
|
||||
adapter.items.add(
|
||||
index = 0,
|
||||
element = LoginInfo.Register(
|
||||
loginType = 999999,
|
||||
internalName = "lab",
|
||||
registerName = R.string.menu_lab,
|
||||
registerLogo = R.drawable.face_2,
|
||||
loginModes = listOf(
|
||||
LoginInfo.Mode(
|
||||
loginMode = 0,
|
||||
name = 0,
|
||||
icon = 0,
|
||||
guideText = 0,
|
||||
credentials = listOf(),
|
||||
errorCodes = mapOf()
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
adapter.notifyItemInserted(0)
|
||||
b.list.smoothScrollToPosition(0)
|
||||
}
|
||||
|
||||
val adapter = LoginChooserAdapter(activity, this::onLoginModeClicked)
|
||||
|
||||
LoginInfo.chooserList = LoginInfo.chooserList
|
||||
?: LoginInfo.list.toMutableList()
|
||||
|
||||
@ -164,7 +189,7 @@ class LoginChooserFragment : Fragment(), CoroutineScope {
|
||||
anim.fillAfter = true
|
||||
activity.getRootView().startAnimation(anim)
|
||||
|
||||
b.list.smoothScrollToPosition(0)
|
||||
adapter.items.removeAll { it !is LoginInfo.Register }
|
||||
adapter.items.add(
|
||||
LoginInfo.Register(
|
||||
loginType = 74,
|
||||
@ -183,7 +208,8 @@ class LoginChooserFragment : Fragment(), CoroutineScope {
|
||||
)
|
||||
)
|
||||
)
|
||||
adapter.notifyItemInserted(adapter.items.size - 1)
|
||||
adapter.notifyDataSetChanged()
|
||||
b.list.smoothScrollToPosition(adapter.items.size - 1)
|
||||
}
|
||||
|
||||
when {
|
||||
@ -216,6 +242,11 @@ class LoginChooserFragment : Fragment(), CoroutineScope {
|
||||
return
|
||||
}
|
||||
|
||||
if (loginType.internalName == "lab") {
|
||||
nav.navigate(R.id.labFragment, null, activity.navOptions)
|
||||
return
|
||||
}
|
||||
|
||||
if (!app.config.privacyPolicyAccepted) {
|
||||
MaterialAlertDialogBuilder(activity)
|
||||
.setTitle(R.string.privacy_policy)
|
||||
|
@ -77,7 +77,7 @@ class MessagesComposeFragment : Fragment(), CoroutineScope {
|
||||
private lateinit var stylingConfig: StylingConfig
|
||||
private lateinit var uiConfig: UIConfig
|
||||
private val enableTextStyling
|
||||
get() = app.profile.loginStoreType != LoginStore.LOGIN_TYPE_VULCAN && app.profile.loginStoreType != LoginStore.LOGIN_TYPE_LIBRUS
|
||||
get() = app.profile.loginStoreType != LoginStore.LOGIN_TYPE_LIBRUS
|
||||
private var changedRecipients = false
|
||||
private var changedSubject = false
|
||||
private var changedBody = false
|
||||
|
@ -15,6 +15,7 @@ import android.text.style.*
|
||||
import androidx.appcompat.widget.AppCompatEditText
|
||||
import androidx.core.graphics.ColorUtils
|
||||
import androidx.core.text.HtmlCompat
|
||||
import pl.szczodrzynski.edziennik.data.api.Regexes.MESSAGE_META
|
||||
import pl.szczodrzynski.edziennik.ext.dp
|
||||
import pl.szczodrzynski.edziennik.ext.getWordBounds
|
||||
import pl.szczodrzynski.edziennik.ext.resolveAttr
|
||||
@ -45,7 +46,7 @@ object BetterHtml {
|
||||
.toRegex(RegexOption.IGNORE_CASE)
|
||||
|
||||
var text = html
|
||||
.replace("\\[META:[A-z0-9]+;[0-9-]+]".toRegex(), "")
|
||||
.replace(MESSAGE_META, "")
|
||||
.replace("background-color: ?$hexPattern;".toRegex(), "")
|
||||
// treat paragraphs as if they had no margin
|
||||
.replace("<p", "<span")
|
||||
|
BIN
app/src/main/res/drawable/face_2.png
Normal file
BIN
app/src/main/res/drawable/face_2.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 13 KiB |
@ -19,13 +19,19 @@
|
||||
android:orientation="vertical"
|
||||
android:visibility="visible">
|
||||
|
||||
<fragment
|
||||
android:id="@+id/nav_host_fragment"
|
||||
android:name="androidx.navigation.fragment.NavHostFragment"
|
||||
<pl.szczodrzynski.edziennik.utils.SwipeRefreshLayoutNoTouch
|
||||
android:id="@+id/swipeRefreshLayout"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
app:defaultNavHost="false"
|
||||
app:navGraph="@navigation/nav_login" />
|
||||
android:layout_height="match_parent">
|
||||
|
||||
<fragment
|
||||
android:id="@+id/nav_host_fragment"
|
||||
android:name="androidx.navigation.fragment.NavHostFragment"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
app:defaultNavHost="false"
|
||||
app:navGraph="@navigation/nav_login" />
|
||||
</pl.szczodrzynski.edziennik.utils.SwipeRefreshLayoutNoTouch>
|
||||
</androidx.coordinatorlayout.widget.CoordinatorLayout>
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
|
@ -22,6 +22,9 @@
|
||||
<action
|
||||
android:id="@+id/action_loginChooserFragment_to_loginEggsFragment"
|
||||
app:destination="@id/loginEggsFragment" />
|
||||
<action
|
||||
android:id="@+id/action_loginChooserFragment_to_labFragment"
|
||||
app:destination="@id/labFragment" />
|
||||
</fragment>
|
||||
<!-- eggs -->
|
||||
<fragment
|
||||
@ -95,4 +98,8 @@
|
||||
android:id="@+id/loginFinishFragment"
|
||||
android:name="pl.szczodrzynski.edziennik.ui.login.LoginFinishFragment"
|
||||
android:label="LoginFinishFragment" />
|
||||
<fragment
|
||||
android:id="@+id/labFragment"
|
||||
android:name="pl.szczodrzynski.edziennik.ui.debug.LabFragment"
|
||||
android:label="LabFragment" />
|
||||
</navigation>
|
||||
|
@ -859,7 +859,7 @@
|
||||
<string name="settings_about_licenses_text">Open-source licenses</string>
|
||||
<string name="settings_about_privacy_policy_text">Privacy policy</string>
|
||||
<string name="settings_card_register_title">E-register</string>
|
||||
<string name="settings_about_title_subtext">© Kuba Szczodrzyński && Kacper Ziubryniewicz\nSeptember 2018 - 2022</string>
|
||||
<string name="settings_about_title_subtext">© Kuba Szczodrzyński && Kacper Ziubryniewicz\nSeptember 2018 – 2022</string>
|
||||
<string name="settings_about_update_subtext">Click to check for updates</string>
|
||||
<string name="settings_about_update_text">Update</string>
|
||||
<string name="settings_about_version_text">Version</string>
|
||||
|
16
build.gradle
16
build.gradle
@ -2,17 +2,17 @@
|
||||
|
||||
buildscript {
|
||||
ext {
|
||||
kotlin_version = '1.5.30'
|
||||
kotlin_version = '1.6.10'
|
||||
|
||||
release = [
|
||||
versionName: "4.11.6",
|
||||
versionCode: 4110699
|
||||
versionName: "4.11.7",
|
||||
versionCode: 4110799
|
||||
]
|
||||
|
||||
setup = [
|
||||
compileSdk: 30,
|
||||
compileSdk: 33,
|
||||
minSdk : 16,
|
||||
targetSdk : 30
|
||||
targetSdk : 33
|
||||
]
|
||||
}
|
||||
|
||||
@ -21,10 +21,10 @@ buildscript {
|
||||
mavenCentral()
|
||||
}
|
||||
dependencies {
|
||||
classpath 'com.android.tools.build:gradle:7.0.3'
|
||||
classpath 'com.android.tools.build:gradle:7.2.2'
|
||||
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
|
||||
classpath 'com.google.gms:google-services:4.3.10'
|
||||
classpath 'com.google.firebase:firebase-crashlytics-gradle:2.7.1'
|
||||
classpath 'com.google.gms:google-services:4.3.14'
|
||||
classpath 'com.google.firebase:firebase-crashlytics-gradle:2.9.2'
|
||||
}
|
||||
}
|
||||
|
||||
|
2
gradle/wrapper/gradle-wrapper.properties
vendored
2
gradle/wrapper/gradle-wrapper.properties
vendored
@ -1,6 +1,6 @@
|
||||
#Wed Feb 17 14:04:38 CET 2021
|
||||
distributionBase=GRADLE_USER_HOME
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-7.0.2-bin.zip
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.3-bin.zip
|
||||
distributionPath=wrapper/dists
|
||||
zipStorePath=wrapper/dists
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
|
Reference in New Issue
Block a user