Migrate to MVVM
This commit is contained in:
@@ -84,17 +84,12 @@ dependencies {
|
|||||||
implementation 'androidx.room:room-ktx:2.2.5'
|
implementation 'androidx.room:room-ktx:2.2.5'
|
||||||
kapt 'androidx.room:room-compiler:2.2.5'
|
kapt 'androidx.room:room-compiler:2.2.5'
|
||||||
|
|
||||||
implementation 'com.github.moxy-community:moxy:2.2.0'
|
|
||||||
implementation 'com.github.moxy-community:moxy-androidx:2.2.0'
|
|
||||||
implementation 'com.github.moxy-community:moxy-material:2.2.0'
|
|
||||||
implementation 'com.github.moxy-community:moxy-ktx:2.2.0'
|
|
||||||
kapt 'com.github.moxy-community:moxy-compiler:2.2.0'
|
|
||||||
|
|
||||||
implementation 'com.squareup.okhttp3:okhttp:4.9.0'
|
implementation 'com.squareup.okhttp3:okhttp:4.9.0'
|
||||||
implementation 'com.squareup.okio:okio:2.9.0'
|
implementation 'com.squareup.okio:okio:2.9.0'
|
||||||
implementation 'org.jsoup:jsoup:1.13.1'
|
implementation 'org.jsoup:jsoup:1.13.1'
|
||||||
|
|
||||||
implementation 'org.koin:koin-android:2.2.0'
|
implementation 'org.koin:koin-android:2.2.0'
|
||||||
|
implementation 'org.koin:koin-android-viewmodel:2.2.0'
|
||||||
implementation 'io.coil-kt:coil-base:1.0.0'
|
implementation 'io.coil-kt:coil-base:1.0.0'
|
||||||
implementation 'com.davemorrissey.labs:subsampling-scale-image-view:3.10.0'
|
implementation 'com.davemorrissey.labs:subsampling-scale-image-view:3.10.0'
|
||||||
implementation 'com.tomclaw.cache:cache:1.0'
|
implementation 'com.tomclaw.cache:cache:1.0'
|
||||||
|
|||||||
@@ -23,7 +23,7 @@
|
|||||||
android:theme="@style/AppTheme"
|
android:theme="@style/AppTheme"
|
||||||
android:usesCleartextTraffic="true"
|
android:usesCleartextTraffic="true"
|
||||||
tools:ignore="UnusedAttribute">
|
tools:ignore="UnusedAttribute">
|
||||||
<activity android:name=".ui.list.MainActivity">
|
<activity android:name="org.koitharu.kotatsu.main.ui.MainActivity">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.intent.action.MAIN" />
|
<action android:name="android.intent.action.MAIN" />
|
||||||
<category android:name="android.intent.category.LAUNCHER" />
|
<category android:name="android.intent.category.LAUNCHER" />
|
||||||
@@ -32,62 +32,62 @@
|
|||||||
android:name="android.app.default_searchable"
|
android:name="android.app.default_searchable"
|
||||||
android:value=".ui.search.SearchActivity" />
|
android:value=".ui.search.SearchActivity" />
|
||||||
</activity>
|
</activity>
|
||||||
<activity android:name=".ui.details.MangaDetailsActivity">
|
<activity android:name="org.koitharu.kotatsu.details.ui.DetailsActivity">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="${applicationId}.action.VIEW_MANGA" />
|
<action android:name="${applicationId}.action.VIEW_MANGA" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</activity>
|
</activity>
|
||||||
<activity android:name=".ui.reader.ReaderActivity" />
|
<activity android:name="org.koitharu.kotatsu.reader.ui.ReaderActivity" />
|
||||||
<activity
|
<activity
|
||||||
android:name=".ui.search.SearchActivity"
|
android:name="org.koitharu.kotatsu.search.ui.SearchActivity"
|
||||||
android:label="@string/search" />
|
android:label="@string/search" />
|
||||||
<activity
|
<activity
|
||||||
android:name=".ui.settings.SettingsActivity"
|
android:name="org.koitharu.kotatsu.settings.SettingsActivity"
|
||||||
android:label="@string/settings" />
|
android:label="@string/settings" />
|
||||||
<activity
|
<activity
|
||||||
android:name=".ui.reader.SimpleSettingsActivity"
|
android:name="org.koitharu.kotatsu.reader.ui.SimpleSettingsActivity"
|
||||||
android:label="@string/settings">
|
android:label="@string/settings">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.intent.action.MANAGE_NETWORK_USAGE" />
|
<action android:name="android.intent.action.MANAGE_NETWORK_USAGE" />
|
||||||
<category android:name="android.intent.category.DEFAULT" />
|
<category android:name="android.intent.category.DEFAULT" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</activity>
|
</activity>
|
||||||
<activity android:name=".ui.browser.BrowserActivity" />
|
<activity android:name="org.koitharu.kotatsu.browser.BrowserActivity" />
|
||||||
<activity
|
<activity
|
||||||
android:name=".ui.utils.CrashActivity"
|
android:name="org.koitharu.kotatsu.core.ui.CrashActivity"
|
||||||
android:label="@string/error_occurred"
|
android:label="@string/error_occurred"
|
||||||
android:theme="@android:style/Theme.DeviceDefault"
|
android:theme="@android:style/Theme.DeviceDefault"
|
||||||
android:windowSoftInputMode="stateAlwaysHidden" />
|
android:windowSoftInputMode="stateAlwaysHidden" />
|
||||||
<activity
|
<activity
|
||||||
android:name="org.koitharu.kotatsu.ui.list.favourites.categories.CategoriesActivity"
|
android:name="org.koitharu.kotatsu.favourites.ui.categories.CategoriesActivity"
|
||||||
android:label="@string/favourites_categories"
|
android:label="@string/favourites_categories"
|
||||||
android:windowSoftInputMode="stateAlwaysHidden" />
|
android:windowSoftInputMode="stateAlwaysHidden" />
|
||||||
<activity
|
<activity
|
||||||
android:name=".ui.widget.shelf.ShelfConfigActivity"
|
android:name="org.koitharu.kotatsu.widget.shelf.ShelfConfigActivity"
|
||||||
android:label="@string/manga_shelf">
|
android:label="@string/manga_shelf">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.appwidget.action.APPWIDGET_CONFIGURE" />
|
<action android:name="android.appwidget.action.APPWIDGET_CONFIGURE" />
|
||||||
</intent-filter>
|
</intent-filter>
|
||||||
</activity>
|
</activity>
|
||||||
<activity
|
<activity
|
||||||
android:name=".ui.search.global.GlobalSearchActivity"
|
android:name="org.koitharu.kotatsu.search.ui.global.GlobalSearchActivity"
|
||||||
android:label="@string/search" />
|
android:label="@string/search" />
|
||||||
<activity
|
<activity
|
||||||
android:name=".ui.utils.protect.ProtectActivity"
|
android:name="org.koitharu.kotatsu.main.ui.protect.ProtectActivity"
|
||||||
android:windowSoftInputMode="adjustResize" />
|
android:windowSoftInputMode="adjustResize" />
|
||||||
|
|
||||||
<service
|
<service
|
||||||
android:name=".ui.download.DownloadService"
|
android:name="org.koitharu.kotatsu.download.DownloadService"
|
||||||
android:foregroundServiceType="dataSync" />
|
android:foregroundServiceType="dataSync" />
|
||||||
<service
|
<service
|
||||||
android:name=".ui.widget.shelf.ShelfWidgetService"
|
android:name="org.koitharu.kotatsu.widget.shelf.ShelfWidgetService"
|
||||||
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
||||||
<service
|
<service
|
||||||
android:name=".ui.widget.recent.RecentWidgetService"
|
android:name="org.koitharu.kotatsu.widget.recent.RecentWidgetService"
|
||||||
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
android:permission="android.permission.BIND_REMOTEVIEWS" />
|
||||||
|
|
||||||
<provider
|
<provider
|
||||||
android:name=".ui.search.MangaSuggestionsProvider"
|
android:name="org.koitharu.kotatsu.search.ui.MangaSuggestionsProvider"
|
||||||
android:authorities="${applicationId}.MangaSuggestionsProvider"
|
android:authorities="${applicationId}.MangaSuggestionsProvider"
|
||||||
android:exported="false" />
|
android:exported="false" />
|
||||||
<provider
|
<provider
|
||||||
@@ -101,7 +101,7 @@
|
|||||||
</provider>
|
</provider>
|
||||||
|
|
||||||
<receiver
|
<receiver
|
||||||
android:name=".ui.widget.shelf.ShelfWidgetProvider"
|
android:name="org.koitharu.kotatsu.widget.shelf.ShelfWidgetProvider"
|
||||||
android:label="@string/manga_shelf">
|
android:label="@string/manga_shelf">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||||
@@ -111,7 +111,7 @@
|
|||||||
android:resource="@xml/widget_shelf" />
|
android:resource="@xml/widget_shelf" />
|
||||||
</receiver>
|
</receiver>
|
||||||
<receiver
|
<receiver
|
||||||
android:name=".ui.widget.recent.RecentWidgetProvider"
|
android:name="org.koitharu.kotatsu.widget.recent.RecentWidgetProvider"
|
||||||
android:label="@string/recent_manga">
|
android:label="@string/recent_manga">
|
||||||
<intent-filter>
|
<intent-filter>
|
||||||
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
<action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
|
||||||
|
|||||||
@@ -6,25 +6,29 @@ import androidx.appcompat.app.AppCompatDelegate
|
|||||||
import org.koin.android.ext.android.get
|
import org.koin.android.ext.android.get
|
||||||
import org.koin.android.ext.koin.androidContext
|
import org.koin.android.ext.koin.androidContext
|
||||||
import org.koin.core.context.startKoin
|
import org.koin.core.context.startKoin
|
||||||
import org.koin.dsl.module
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.backup.BackupRepository
|
|
||||||
import org.koitharu.kotatsu.core.backup.RestoreRepository
|
|
||||||
import org.koitharu.kotatsu.core.db.databaseModule
|
import org.koitharu.kotatsu.core.db.databaseModule
|
||||||
import org.koitharu.kotatsu.core.github.githubModule
|
import org.koitharu.kotatsu.core.github.githubModule
|
||||||
import org.koitharu.kotatsu.core.local.PagesCache
|
|
||||||
import org.koitharu.kotatsu.core.network.networkModule
|
import org.koitharu.kotatsu.core.network.networkModule
|
||||||
import org.koitharu.kotatsu.core.parser.LocalMangaRepository
|
|
||||||
import org.koitharu.kotatsu.core.parser.parserModule
|
import org.koitharu.kotatsu.core.parser.parserModule
|
||||||
import org.koitharu.kotatsu.core.prefs.AppSettings
|
import org.koitharu.kotatsu.core.prefs.AppSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaDataRepository
|
import org.koitharu.kotatsu.core.ui.AppCrashHandler
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
import org.koitharu.kotatsu.core.ui.uiModule
|
||||||
import org.koitharu.kotatsu.domain.MangaSearchRepository
|
import org.koitharu.kotatsu.details.detailsModule
|
||||||
import org.koitharu.kotatsu.domain.favourites.FavouritesRepository
|
import org.koitharu.kotatsu.favourites.domain.FavouritesRepository
|
||||||
import org.koitharu.kotatsu.domain.history.HistoryRepository
|
import org.koitharu.kotatsu.favourites.favouritesModule
|
||||||
import org.koitharu.kotatsu.domain.tracking.TrackingRepository
|
import org.koitharu.kotatsu.history.domain.HistoryRepository
|
||||||
import org.koitharu.kotatsu.ui.base.uiModule
|
import org.koitharu.kotatsu.history.historyModule
|
||||||
import org.koitharu.kotatsu.ui.utils.AppCrashHandler
|
import org.koitharu.kotatsu.local.data.PagesCache
|
||||||
import org.koitharu.kotatsu.ui.widget.WidgetUpdater
|
import org.koitharu.kotatsu.local.domain.LocalMangaRepository
|
||||||
|
import org.koitharu.kotatsu.local.localModule
|
||||||
|
import org.koitharu.kotatsu.main.mainModule
|
||||||
|
import org.koitharu.kotatsu.reader.readerModule
|
||||||
|
import org.koitharu.kotatsu.remotelist.remoteListModule
|
||||||
|
import org.koitharu.kotatsu.search.searchModule
|
||||||
|
import org.koitharu.kotatsu.settings.settingsModule
|
||||||
|
import org.koitharu.kotatsu.tracker.trackerModule
|
||||||
|
import org.koitharu.kotatsu.widget.WidgetUpdater
|
||||||
|
|
||||||
class KotatsuApp : Application() {
|
class KotatsuApp : Application() {
|
||||||
|
|
||||||
@@ -62,20 +66,18 @@ class KotatsuApp : Application() {
|
|||||||
networkModule,
|
networkModule,
|
||||||
databaseModule,
|
databaseModule,
|
||||||
githubModule,
|
githubModule,
|
||||||
parserModule,
|
|
||||||
uiModule,
|
uiModule,
|
||||||
module {
|
parserModule,
|
||||||
single { FavouritesRepository(get()) }
|
mainModule,
|
||||||
single { HistoryRepository(get()) }
|
searchModule,
|
||||||
single { TrackingRepository(get(), get()) }
|
localModule,
|
||||||
single { MangaDataRepository(get()) }
|
favouritesModule,
|
||||||
single { BackupRepository(get()) }
|
historyModule,
|
||||||
single { RestoreRepository(get()) }
|
remoteListModule,
|
||||||
single { MangaSearchRepository() }
|
detailsModule,
|
||||||
single { MangaLoaderContext() }
|
trackerModule,
|
||||||
single { AppSettings(get()) }
|
settingsModule,
|
||||||
single { PagesCache(get()) }
|
readerModule
|
||||||
}
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.domain
|
package org.koitharu.kotatsu.base.domain
|
||||||
|
|
||||||
import androidx.room.withTransaction
|
import androidx.room.withTransaction
|
||||||
import org.koitharu.kotatsu.core.db.MangaDatabase
|
import org.koitharu.kotatsu.core.db.MangaDatabase
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.domain
|
package org.koitharu.kotatsu.base.domain
|
||||||
|
|
||||||
import okhttp3.*
|
import okhttp3.*
|
||||||
import org.koin.core.component.KoinComponent
|
import org.koin.core.component.KoinComponent
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.domain
|
package org.koitharu.kotatsu.base.domain
|
||||||
|
|
||||||
import org.koin.core.component.KoinComponent
|
import org.koin.core.component.KoinComponent
|
||||||
import org.koin.core.component.get
|
import org.koin.core.component.get
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.domain
|
package org.koitharu.kotatsu.base.domain
|
||||||
|
|
||||||
import android.graphics.BitmapFactory
|
import android.graphics.BitmapFactory
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
import android.app.Dialog
|
import android.app.Dialog
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
@@ -6,11 +6,11 @@ import android.view.View
|
|||||||
import androidx.annotation.CallSuper
|
import androidx.annotation.CallSuper
|
||||||
import androidx.annotation.LayoutRes
|
import androidx.annotation.LayoutRes
|
||||||
import androidx.appcompat.app.AlertDialog
|
import androidx.appcompat.app.AlertDialog
|
||||||
import moxy.MvpAppCompatDialogFragment
|
import androidx.fragment.app.DialogFragment
|
||||||
|
|
||||||
abstract class AlertDialogFragment(
|
abstract class AlertDialogFragment(
|
||||||
@LayoutRes private val layoutResId: Int
|
@LayoutRes private val layoutResId: Int
|
||||||
) : MvpAppCompatDialogFragment() {
|
) : DialogFragment() {
|
||||||
|
|
||||||
private var rootView: View? = null
|
private var rootView: View? = null
|
||||||
|
|
||||||
@@ -1,15 +1,15 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.view.MenuItem
|
import android.view.MenuItem
|
||||||
import android.view.View
|
import android.view.View
|
||||||
|
import androidx.appcompat.app.AppCompatActivity
|
||||||
import androidx.appcompat.widget.Toolbar
|
import androidx.appcompat.widget.Toolbar
|
||||||
import moxy.MvpAppCompatActivity
|
|
||||||
import org.koin.android.ext.android.get
|
import org.koin.android.ext.android.get
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.core.prefs.AppSettings
|
import org.koitharu.kotatsu.core.prefs.AppSettings
|
||||||
|
|
||||||
abstract class BaseActivity : MvpAppCompatActivity() {
|
abstract class BaseActivity : AppCompatActivity() {
|
||||||
|
|
||||||
override fun onCreate(savedInstanceState: Bundle?) {
|
override fun onCreate(savedInstanceState: Bundle?) {
|
||||||
if (get<AppSettings>().isAmoledTheme) {
|
if (get<AppSettings>().isAmoledTheme) {
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
import android.app.Dialog
|
import android.app.Dialog
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
@@ -7,11 +7,11 @@ import android.view.View
|
|||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.annotation.LayoutRes
|
import androidx.annotation.LayoutRes
|
||||||
import androidx.appcompat.app.AppCompatDialog
|
import androidx.appcompat.app.AppCompatDialog
|
||||||
import moxy.MvpBottomSheetDialogFragment
|
import com.google.android.material.bottomsheet.BottomSheetDialogFragment
|
||||||
import org.koitharu.kotatsu.utils.UiUtils
|
import org.koitharu.kotatsu.utils.UiUtils
|
||||||
|
|
||||||
abstract class BaseBottomSheet(@LayoutRes private val layoutResId: Int) :
|
abstract class BaseBottomSheet(@LayoutRes private val layoutResId: Int) :
|
||||||
MvpBottomSheetDialogFragment() {
|
BottomSheetDialogFragment() {
|
||||||
|
|
||||||
final override fun onCreateView(
|
final override fun onCreateView(
|
||||||
inflater: LayoutInflater,
|
inflater: LayoutInflater,
|
||||||
@@ -1,14 +1,14 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import androidx.annotation.LayoutRes
|
import androidx.annotation.LayoutRes
|
||||||
|
import androidx.fragment.app.Fragment
|
||||||
import coil.ImageLoader
|
import coil.ImageLoader
|
||||||
import moxy.MvpAppCompatFragment
|
|
||||||
import org.koin.android.ext.android.inject
|
import org.koin.android.ext.android.inject
|
||||||
|
|
||||||
abstract class BaseFragment(
|
abstract class BaseFragment(
|
||||||
@LayoutRes contentLayoutId: Int
|
@LayoutRes contentLayoutId: Int
|
||||||
) : MvpAppCompatFragment(contentLayoutId) {
|
) : Fragment(contentLayoutId) {
|
||||||
|
|
||||||
protected val coil by inject<ImageLoader>()
|
protected val coil by inject<ImageLoader>()
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
import android.graphics.Color
|
import android.graphics.Color
|
||||||
import android.os.Build
|
import android.os.Build
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
import androidx.annotation.StringRes
|
import androidx.annotation.StringRes
|
||||||
import androidx.preference.PreferenceFragmentCompat
|
import androidx.preference.PreferenceFragmentCompat
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
|
import androidx.lifecycle.LifecycleService
|
||||||
|
|
||||||
|
abstract class BaseService : LifecycleService()
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
package org.koitharu.kotatsu.base.ui
|
||||||
|
|
||||||
|
import androidx.lifecycle.MutableLiveData
|
||||||
|
import androidx.lifecycle.ViewModel
|
||||||
|
import androidx.lifecycle.viewModelScope
|
||||||
|
import kotlinx.coroutines.*
|
||||||
|
import org.koitharu.kotatsu.BuildConfig
|
||||||
|
import org.koitharu.kotatsu.utils.SingleLiveEvent
|
||||||
|
|
||||||
|
abstract class BaseViewModel : ViewModel() {
|
||||||
|
|
||||||
|
val onError = SingleLiveEvent<Throwable>()
|
||||||
|
val isLoading = MutableLiveData(false)
|
||||||
|
|
||||||
|
protected fun launchJob(
|
||||||
|
start: CoroutineStart = CoroutineStart.DEFAULT,
|
||||||
|
block: suspend CoroutineScope.() -> Unit
|
||||||
|
): Job = viewModelScope.launch(createErrorHandler(), start, block)
|
||||||
|
|
||||||
|
protected fun launchLoadingJob(
|
||||||
|
start: CoroutineStart = CoroutineStart.DEFAULT,
|
||||||
|
block: suspend CoroutineScope.() -> Unit
|
||||||
|
): Job = viewModelScope.launch(createErrorHandler(), start) {
|
||||||
|
isLoading.value = true
|
||||||
|
try {
|
||||||
|
block()
|
||||||
|
} finally {
|
||||||
|
isLoading.value = false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun createErrorHandler() = CoroutineExceptionHandler { _, throwable ->
|
||||||
|
if (BuildConfig.DEBUG) {
|
||||||
|
throwable.printStackTrace()
|
||||||
|
}
|
||||||
|
if (throwable !is CancellationException) {
|
||||||
|
onError.call(throwable)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.dialog
|
package org.koitharu.kotatsu.base.ui.dialog
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.dialog
|
package org.koitharu.kotatsu.base.ui.dialog
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.DialogInterface
|
import android.content.DialogInterface
|
||||||
@@ -10,7 +10,7 @@ import androidx.appcompat.app.AlertDialog
|
|||||||
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||||
import kotlinx.android.synthetic.main.item_storage.view.*
|
import kotlinx.android.synthetic.main.item_storage.view.*
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.core.parser.LocalMangaRepository
|
import org.koitharu.kotatsu.local.domain.LocalMangaRepository
|
||||||
import org.koitharu.kotatsu.utils.ext.getStorageName
|
import org.koitharu.kotatsu.utils.ext.getStorageName
|
||||||
import org.koitharu.kotatsu.utils.ext.inflate
|
import org.koitharu.kotatsu.utils.ext.inflate
|
||||||
import org.koitharu.kotatsu.utils.ext.longHashCode
|
import org.koitharu.kotatsu.utils.ext.longHashCode
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.dialog
|
package org.koitharu.kotatsu.base.ui.dialog
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import androidx.recyclerview.widget.DiffUtil
|
import androidx.recyclerview.widget.DiffUtil
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
import androidx.recyclerview.widget.LinearLayoutManager
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import android.view.View
|
import android.view.View
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list
|
package org.koitharu.kotatsu.base.ui.list
|
||||||
|
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list.decor
|
package org.koitharu.kotatsu.base.ui.list.decor
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.graphics.Canvas
|
import android.graphics.Canvas
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list.decor
|
package org.koitharu.kotatsu.base.ui.list.decor
|
||||||
|
|
||||||
import android.graphics.Canvas
|
import android.graphics.Canvas
|
||||||
import android.graphics.Rect
|
import android.graphics.Rect
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.list.decor
|
package org.koitharu.kotatsu.base.ui.list.decor
|
||||||
|
|
||||||
import android.graphics.Rect
|
import android.graphics.Rect
|
||||||
import android.view.View
|
import android.view.View
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.widgets
|
package org.koitharu.kotatsu.base.ui.widgets
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.util.AttributeSet
|
import android.util.AttributeSet
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.widgets
|
package org.koitharu.kotatsu.base.ui.widgets
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.util.AttributeSet
|
import android.util.AttributeSet
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base.widgets
|
package org.koitharu.kotatsu.base.ui.widgets
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.util.AttributeSet
|
import android.util.AttributeSet
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.browser
|
package org.koitharu.kotatsu.browser
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import android.content.ActivityNotFoundException
|
import android.content.ActivityNotFoundException
|
||||||
@@ -11,7 +11,7 @@ import android.view.MenuItem
|
|||||||
import androidx.core.view.isVisible
|
import androidx.core.view.isVisible
|
||||||
import kotlinx.android.synthetic.main.activity_browser.*
|
import kotlinx.android.synthetic.main.activity_browser.*
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.ui.base.BaseActivity
|
import org.koitharu.kotatsu.base.ui.BaseActivity
|
||||||
|
|
||||||
@SuppressLint("SetJavaScriptEnabled")
|
@SuppressLint("SetJavaScriptEnabled")
|
||||||
class BrowserActivity : BaseActivity(), BrowserCallback {
|
class BrowserActivity : BaseActivity(), BrowserCallback {
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.browser
|
package org.koitharu.kotatsu.browser
|
||||||
|
|
||||||
interface BrowserCallback {
|
interface BrowserCallback {
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.browser
|
package org.koitharu.kotatsu.browser
|
||||||
|
|
||||||
import android.graphics.Bitmap
|
import android.graphics.Bitmap
|
||||||
import android.webkit.WebResourceRequest
|
import android.webkit.WebResourceRequest
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.utils.cloudflare
|
package org.koitharu.kotatsu.browser.cloudflare
|
||||||
|
|
||||||
interface CloudFlareCallback {
|
interface CloudFlareCallback {
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.utils.cloudflare
|
package org.koitharu.kotatsu.browser.cloudflare
|
||||||
|
|
||||||
import android.graphics.Bitmap
|
import android.graphics.Bitmap
|
||||||
import android.webkit.CookieManager
|
import android.webkit.CookieManager
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.utils.cloudflare
|
package org.koitharu.kotatsu.browser.cloudflare
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
@@ -10,8 +10,8 @@ import androidx.core.view.isInvisible
|
|||||||
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout
|
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout
|
||||||
import kotlinx.android.synthetic.main.fragment_cloudflare.*
|
import kotlinx.android.synthetic.main.fragment_cloudflare.*
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.AlertDialogFragment
|
||||||
import org.koitharu.kotatsu.core.network.UserAgentInterceptor
|
import org.koitharu.kotatsu.core.network.UserAgentInterceptor
|
||||||
import org.koitharu.kotatsu.ui.base.AlertDialogFragment
|
|
||||||
import org.koitharu.kotatsu.utils.ext.stringArgument
|
import org.koitharu.kotatsu.utils.ext.stringArgument
|
||||||
import org.koitharu.kotatsu.utils.ext.withArgs
|
import org.koitharu.kotatsu.utils.ext.withArgs
|
||||||
|
|
||||||
@@ -4,7 +4,11 @@ import org.json.JSONArray
|
|||||||
import org.json.JSONObject
|
import org.json.JSONObject
|
||||||
import org.koitharu.kotatsu.BuildConfig
|
import org.koitharu.kotatsu.BuildConfig
|
||||||
import org.koitharu.kotatsu.core.db.MangaDatabase
|
import org.koitharu.kotatsu.core.db.MangaDatabase
|
||||||
import org.koitharu.kotatsu.core.db.entity.*
|
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
||||||
|
import org.koitharu.kotatsu.core.db.entity.TagEntity
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteCategoryEntity
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteEntity
|
||||||
|
import org.koitharu.kotatsu.history.data.HistoryEntity
|
||||||
|
|
||||||
class BackupRepository(private val db: MangaDatabase) {
|
class BackupRepository(private val db: MangaDatabase) {
|
||||||
|
|
||||||
|
|||||||
@@ -3,7 +3,11 @@ package org.koitharu.kotatsu.core.backup
|
|||||||
import androidx.room.withTransaction
|
import androidx.room.withTransaction
|
||||||
import org.json.JSONObject
|
import org.json.JSONObject
|
||||||
import org.koitharu.kotatsu.core.db.MangaDatabase
|
import org.koitharu.kotatsu.core.db.MangaDatabase
|
||||||
import org.koitharu.kotatsu.core.db.entity.*
|
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
||||||
|
import org.koitharu.kotatsu.core.db.entity.TagEntity
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteCategoryEntity
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteEntity
|
||||||
|
import org.koitharu.kotatsu.history.data.HistoryEntity
|
||||||
import org.koitharu.kotatsu.utils.ext.getStringOrNull
|
import org.koitharu.kotatsu.utils.ext.getStringOrNull
|
||||||
import org.koitharu.kotatsu.utils.ext.iterator
|
import org.koitharu.kotatsu.utils.ext.iterator
|
||||||
import org.koitharu.kotatsu.utils.ext.map
|
import org.koitharu.kotatsu.utils.ext.map
|
||||||
|
|||||||
@@ -4,6 +4,12 @@ import androidx.room.Database
|
|||||||
import androidx.room.RoomDatabase
|
import androidx.room.RoomDatabase
|
||||||
import org.koitharu.kotatsu.core.db.dao.*
|
import org.koitharu.kotatsu.core.db.dao.*
|
||||||
import org.koitharu.kotatsu.core.db.entity.*
|
import org.koitharu.kotatsu.core.db.entity.*
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteCategoriesDao
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteCategoryEntity
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteEntity
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouritesDao
|
||||||
|
import org.koitharu.kotatsu.history.data.HistoryDao
|
||||||
|
import org.koitharu.kotatsu.history.data.HistoryEntity
|
||||||
|
|
||||||
@Database(
|
@Database(
|
||||||
entities = [
|
entities = [
|
||||||
|
|||||||
@@ -15,7 +15,7 @@ import androidx.room.PrimaryKey
|
|||||||
)
|
)
|
||||||
]
|
]
|
||||||
)
|
)
|
||||||
data class TrackEntity (
|
data class TrackEntity(
|
||||||
@PrimaryKey(autoGenerate = false)
|
@PrimaryKey(autoGenerate = false)
|
||||||
@ColumnInfo(name = "manga_id") val mangaId: Long,
|
@ColumnInfo(name = "manga_id") val mangaId: Long,
|
||||||
@ColumnInfo(name = "chapters_total") val totalChapters: Int,
|
@ColumnInfo(name = "chapters_total") val totalChapters: Int,
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.core.exceptions
|
package org.koitharu.kotatsu.core.exceptions
|
||||||
|
|
||||||
class ParseException(message: String? = null, cause: Throwable? = null) : RuntimeException(message, cause)
|
class ParseException(message: String? = null, cause: Throwable? = null) :
|
||||||
|
RuntimeException(message, cause)
|
||||||
@@ -4,9 +4,10 @@ import android.os.Parcelable
|
|||||||
import kotlinx.android.parcel.Parcelize
|
import kotlinx.android.parcel.Parcelize
|
||||||
import org.koin.core.context.GlobalContext
|
import org.koin.core.context.GlobalContext
|
||||||
import org.koin.core.error.NoBeanDefFoundException
|
import org.koin.core.error.NoBeanDefFoundException
|
||||||
import org.koitharu.kotatsu.core.parser.LocalMangaRepository
|
import org.koin.core.qualifier.named
|
||||||
import org.koitharu.kotatsu.core.parser.MangaRepository
|
import org.koitharu.kotatsu.core.parser.MangaRepository
|
||||||
import org.koitharu.kotatsu.core.parser.site.*
|
import org.koitharu.kotatsu.core.parser.site.*
|
||||||
|
import org.koitharu.kotatsu.local.domain.LocalMangaRepository
|
||||||
|
|
||||||
@Suppress("SpellCheckingInspection")
|
@Suppress("SpellCheckingInspection")
|
||||||
@Parcelize
|
@Parcelize
|
||||||
@@ -30,6 +31,7 @@ enum class MangaSource(
|
|||||||
// HENTAILIB("HentaiLib", "ru", HentaiLibRepository::class.java)
|
// HENTAILIB("HentaiLib", "ru", HentaiLibRepository::class.java)
|
||||||
|
|
||||||
@get:Throws(NoBeanDefFoundException::class)
|
@get:Throws(NoBeanDefFoundException::class)
|
||||||
|
@Deprecated("")
|
||||||
val repository: MangaRepository
|
val repository: MangaRepository
|
||||||
get() = GlobalContext.get().get(cls.kotlin)
|
get() = GlobalContext.get().get(named(this))
|
||||||
}
|
}
|
||||||
@@ -5,10 +5,10 @@ import kotlinx.android.parcel.Parcelize
|
|||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
@Parcelize
|
@Parcelize
|
||||||
data class MangaTracking (
|
data class MangaTracking(
|
||||||
val manga: Manga,
|
val manga: Manga,
|
||||||
val knownChaptersCount: Int,
|
val knownChaptersCount: Int,
|
||||||
val lastChapterId: Long,
|
val lastChapterId: Long,
|
||||||
val lastNotifiedChapterId: Long,
|
val lastNotifiedChapterId: Long,
|
||||||
val lastCheck: Date?
|
val lastCheck: Date?
|
||||||
): Parcelable
|
) : Parcelable
|
||||||
@@ -5,9 +5,9 @@ import kotlinx.android.parcel.Parcelize
|
|||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
@Parcelize
|
@Parcelize
|
||||||
data class TrackingLogItem (
|
data class TrackingLogItem(
|
||||||
val id: Long,
|
val id: Long,
|
||||||
val manga: Manga,
|
val manga: Manga,
|
||||||
val chapters: List<String>,
|
val chapters: List<String>,
|
||||||
val createdAt: Date
|
val createdAt: Date
|
||||||
): Parcelable
|
) : Parcelable
|
||||||
@@ -6,13 +6,18 @@ interface MangaRepository {
|
|||||||
|
|
||||||
val sortOrders: Set<SortOrder>
|
val sortOrders: Set<SortOrder>
|
||||||
|
|
||||||
suspend fun getList(offset: Int, query: String? = null, sortOrder: SortOrder? = null, tag: MangaTag? = null): List<Manga>
|
suspend fun getList(
|
||||||
|
offset: Int,
|
||||||
|
query: String? = null,
|
||||||
|
sortOrder: SortOrder? = null,
|
||||||
|
tag: MangaTag? = null
|
||||||
|
): List<Manga>
|
||||||
|
|
||||||
suspend fun getDetails(manga: Manga) : Manga
|
suspend fun getDetails(manga: Manga): Manga
|
||||||
|
|
||||||
suspend fun getPages(chapter: MangaChapter) : List<MangaPage>
|
suspend fun getPages(chapter: MangaChapter): List<MangaPage>
|
||||||
|
|
||||||
suspend fun getPageFullUrl(page: MangaPage) : String
|
suspend fun getPageFullUrl(page: MangaPage): String
|
||||||
|
|
||||||
suspend fun getTags(): Set<MangaTag>
|
suspend fun getTags(): Set<MangaTag>
|
||||||
}
|
}
|
||||||
@@ -1,22 +1,25 @@
|
|||||||
package org.koitharu.kotatsu.core.parser
|
package org.koitharu.kotatsu.core.parser
|
||||||
|
|
||||||
import org.koin.dsl.bind
|
import org.koin.core.qualifier.named
|
||||||
import org.koin.dsl.module
|
import org.koin.dsl.module
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.core.parser.site.*
|
import org.koitharu.kotatsu.core.parser.site.*
|
||||||
|
|
||||||
val parserModule
|
val parserModule
|
||||||
get() = module {
|
get() = module {
|
||||||
single { LocalMangaRepository(get()) } bind MangaRepository::class
|
|
||||||
|
|
||||||
factory { ReadmangaRepository(get()) } bind MangaRepository::class
|
single { MangaLoaderContext() }
|
||||||
factory { MintMangaRepository(get()) } bind MangaRepository::class
|
|
||||||
factory { SelfMangaRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.READMANGA_RU)) { ReadmangaRepository(get()) }
|
||||||
factory { MangaChanRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.MINTMANGA)) { MintMangaRepository(get()) }
|
||||||
factory { DesuMeRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.SELFMANGA)) { SelfMangaRepository(get()) }
|
||||||
factory { HenChanRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.MANGACHAN)) { MangaChanRepository(get()) }
|
||||||
factory { YaoiChanRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.DESUME)) { DesuMeRepository(get()) }
|
||||||
factory { MangaTownRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.HENCHAN)) { HenChanRepository(get()) }
|
||||||
factory { MangaLibRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.YAOICHAN)) { YaoiChanRepository(get()) }
|
||||||
factory { NudeMoonRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.MANGATOWN)) { MangaTownRepository(get()) }
|
||||||
factory { MangareadRepository(get()) } bind MangaRepository::class
|
factory<MangaRepository>(named(MangaSource.MANGALIB)) { MangaLibRepository(get()) }
|
||||||
|
factory<MangaRepository>(named(MangaSource.NUDEMOON)) { NudeMoonRepository(get()) }
|
||||||
|
factory<MangaRepository>(named(MangaSource.MANGAREAD)) { MangareadRepository(get()) }
|
||||||
}
|
}
|
||||||
@@ -1,10 +1,10 @@
|
|||||||
package org.koitharu.kotatsu.core.parser
|
package org.koitharu.kotatsu.core.parser
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.model.MangaPage
|
import org.koitharu.kotatsu.core.model.MangaPage
|
||||||
import org.koitharu.kotatsu.core.model.MangaSource
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.core.model.MangaTag
|
import org.koitharu.kotatsu.core.model.MangaTag
|
||||||
import org.koitharu.kotatsu.core.model.SortOrder
|
import org.koitharu.kotatsu.core.model.SortOrder
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
|
|
||||||
abstract class RemoteMangaRepository(
|
abstract class RemoteMangaRepository(
|
||||||
protected val loaderContext: MangaLoaderContext
|
protected val loaderContext: MangaLoaderContext
|
||||||
|
|||||||
@@ -1,11 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
import androidx.collection.arraySetOf
|
import androidx.collection.arraySetOf
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
||||||
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
import androidx.collection.arraySetOf
|
import androidx.collection.arraySetOf
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
||||||
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.util.*
|
import java.util.*
|
||||||
import kotlin.collections.ArrayList
|
import kotlin.collections.ArrayList
|
||||||
|
|||||||
@@ -2,11 +2,11 @@ package org.koitharu.kotatsu.core.parser.site
|
|||||||
|
|
||||||
import androidx.collection.arraySetOf
|
import androidx.collection.arraySetOf
|
||||||
import androidx.core.net.toUri
|
import androidx.core.net.toUri
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
||||||
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.longHashCode
|
import org.koitharu.kotatsu.utils.ext.longHashCode
|
||||||
import org.koitharu.kotatsu.utils.ext.mapToSet
|
import org.koitharu.kotatsu.utils.ext.mapToSet
|
||||||
import org.koitharu.kotatsu.utils.ext.parseHtml
|
import org.koitharu.kotatsu.utils.ext.parseHtml
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.model.MangaSource
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
|
|
||||||
class MangaChanRepository(loaderContext: MangaLoaderContext) : ChanRepository(loaderContext) {
|
class MangaChanRepository(loaderContext: MangaLoaderContext) : ChanRepository(loaderContext) {
|
||||||
|
|
||||||
|
|||||||
@@ -4,11 +4,11 @@ import androidx.collection.ArraySet
|
|||||||
import androidx.collection.arraySetOf
|
import androidx.collection.arraySetOf
|
||||||
import org.json.JSONArray
|
import org.json.JSONArray
|
||||||
import org.json.JSONObject
|
import org.json.JSONObject
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
||||||
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.util.*
|
import java.util.*
|
||||||
import kotlin.collections.ArrayList
|
import kotlin.collections.ArrayList
|
||||||
|
|||||||
@@ -2,11 +2,11 @@ package org.koitharu.kotatsu.core.parser.site
|
|||||||
|
|
||||||
import androidx.collection.arraySetOf
|
import androidx.collection.arraySetOf
|
||||||
import org.intellij.lang.annotations.Language
|
import org.intellij.lang.annotations.Language
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
||||||
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
import androidx.collection.arraySetOf
|
import androidx.collection.arraySetOf
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
||||||
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.model.MangaSource
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
|
|
||||||
class MintMangaRepository(loaderContext: MangaLoaderContext) : GroupleRepository(loaderContext) {
|
class MintMangaRepository(loaderContext: MangaLoaderContext) : GroupleRepository(loaderContext) {
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
import androidx.collection.arraySetOf
|
import androidx.collection.arraySetOf
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.core.model.*
|
||||||
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
import org.koitharu.kotatsu.core.parser.RemoteMangaRepository
|
||||||
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
import org.koitharu.kotatsu.core.prefs.SourceSettings
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.util.*
|
import java.util.*
|
||||||
import java.util.regex.Pattern
|
import java.util.regex.Pattern
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.model.MangaSource
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
|
|
||||||
class ReadmangaRepository(loaderContext: MangaLoaderContext) : GroupleRepository(loaderContext) {
|
class ReadmangaRepository(loaderContext: MangaLoaderContext) : GroupleRepository(loaderContext) {
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.model.MangaSource
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
|
|
||||||
class SelfMangaRepository(loaderContext: MangaLoaderContext) : GroupleRepository(loaderContext) {
|
class SelfMangaRepository(loaderContext: MangaLoaderContext) : GroupleRepository(loaderContext) {
|
||||||
|
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
package org.koitharu.kotatsu.core.parser.site
|
package org.koitharu.kotatsu.core.parser.site
|
||||||
|
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaLoaderContext
|
||||||
import org.koitharu.kotatsu.core.exceptions.ParseException
|
import org.koitharu.kotatsu.core.exceptions.ParseException
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.core.model.MangaChapter
|
import org.koitharu.kotatsu.core.model.MangaChapter
|
||||||
import org.koitharu.kotatsu.core.model.MangaSource
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.domain.MangaLoaderContext
|
|
||||||
import org.koitharu.kotatsu.utils.ext.longHashCode
|
import org.koitharu.kotatsu.utils.ext.longHashCode
|
||||||
import org.koitharu.kotatsu.utils.ext.parseHtml
|
import org.koitharu.kotatsu.utils.ext.parseHtml
|
||||||
import org.koitharu.kotatsu.utils.ext.withDomain
|
import org.koitharu.kotatsu.utils.ext.withDomain
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ import androidx.collection.arraySetOf
|
|||||||
import androidx.core.content.edit
|
import androidx.core.content.edit
|
||||||
import androidx.preference.PreferenceManager
|
import androidx.preference.PreferenceManager
|
||||||
import org.koitharu.kotatsu.core.model.ZoomMode
|
import org.koitharu.kotatsu.core.model.ZoomMode
|
||||||
import org.koitharu.kotatsu.core.parser.LocalMangaRepository
|
import org.koitharu.kotatsu.local.domain.LocalMangaRepository
|
||||||
import org.koitharu.kotatsu.utils.delegates.prefs.*
|
import org.koitharu.kotatsu.utils.delegates.prefs.*
|
||||||
import java.io.File
|
import java.io.File
|
||||||
|
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ import org.koitharu.kotatsu.utils.delegates.prefs.LongPreferenceDelegate
|
|||||||
class AppWidgetConfig private constructor(
|
class AppWidgetConfig private constructor(
|
||||||
private val prefs: SharedPreferences,
|
private val prefs: SharedPreferences,
|
||||||
val widgetId: Int
|
val widgetId: Int
|
||||||
) : SharedPreferences by prefs {
|
) : SharedPreferences by prefs {
|
||||||
|
|
||||||
var categoryId by LongPreferenceDelegate(CATEGORY_ID, 0L)
|
var categoryId by LongPreferenceDelegate(CATEGORY_ID, 0L)
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.utils
|
package org.koitharu.kotatsu.core.ui
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.core.ui
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.view.View
|
import android.view.View
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.utils
|
package org.koitharu.kotatsu.core.ui
|
||||||
|
|
||||||
import android.app.Activity
|
import android.app.Activity
|
||||||
import android.content.ActivityNotFoundException
|
import android.content.ActivityNotFoundException
|
||||||
@@ -10,7 +10,7 @@ import android.view.MenuItem
|
|||||||
import android.view.View
|
import android.view.View
|
||||||
import kotlinx.android.synthetic.main.activity_crash.*
|
import kotlinx.android.synthetic.main.activity_crash.*
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.ui.list.MainActivity
|
import org.koitharu.kotatsu.main.ui.MainActivity
|
||||||
import org.koitharu.kotatsu.utils.ShareHelper
|
import org.koitharu.kotatsu.utils.ShareHelper
|
||||||
|
|
||||||
class CrashActivity : Activity(), View.OnClickListener {
|
class CrashActivity : Activity(), View.OnClickListener {
|
||||||
@@ -1,11 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.ui.base
|
package org.koitharu.kotatsu.core.ui
|
||||||
|
|
||||||
import coil.ComponentRegistry
|
import coil.ComponentRegistry
|
||||||
import coil.ImageLoader
|
import coil.ImageLoader
|
||||||
import okhttp3.OkHttpClient
|
import okhttp3.OkHttpClient
|
||||||
import org.koin.android.ext.koin.androidContext
|
import org.koin.android.ext.koin.androidContext
|
||||||
import org.koin.dsl.module
|
import org.koin.dsl.module
|
||||||
import org.koitharu.kotatsu.core.local.CbzFetcher
|
import org.koitharu.kotatsu.local.data.CbzFetcher
|
||||||
|
|
||||||
val uiModule
|
val uiModule
|
||||||
get() = module {
|
get() = module {
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
package org.koitharu.kotatsu.details
|
||||||
|
|
||||||
|
import org.koin.android.viewmodel.dsl.viewModel
|
||||||
|
import org.koin.dsl.module
|
||||||
|
import org.koitharu.kotatsu.details.ui.DetailsViewModel
|
||||||
|
|
||||||
|
val detailsModule
|
||||||
|
get() = module {
|
||||||
|
|
||||||
|
viewModel { DetailsViewModel(get(), get(), get(), get(), get(), get()) }
|
||||||
|
}
|
||||||
@@ -1,13 +1,13 @@
|
|||||||
package org.koitharu.kotatsu.ui.details
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
import android.graphics.Color
|
import android.graphics.Color
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.core.view.isVisible
|
import androidx.core.view.isVisible
|
||||||
import kotlinx.android.synthetic.main.item_chapter.*
|
import kotlinx.android.synthetic.main.item_chapter.*
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseViewHolder
|
||||||
import org.koitharu.kotatsu.core.model.MangaChapter
|
import org.koitharu.kotatsu.core.model.MangaChapter
|
||||||
import org.koitharu.kotatsu.domain.history.ChapterExtra
|
import org.koitharu.kotatsu.history.domain.ChapterExtra
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseViewHolder
|
|
||||||
import org.koitharu.kotatsu.utils.ext.getThemeColor
|
import org.koitharu.kotatsu.utils.ext.getThemeColor
|
||||||
|
|
||||||
class ChapterHolder(parent: ViewGroup) :
|
class ChapterHolder(parent: ViewGroup) :
|
||||||
@@ -1,11 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.ui.details
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseRecyclerAdapter
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.OnRecyclerItemClickListener
|
||||||
import org.koitharu.kotatsu.core.model.MangaChapter
|
import org.koitharu.kotatsu.core.model.MangaChapter
|
||||||
import org.koitharu.kotatsu.domain.history.ChapterExtra
|
import org.koitharu.kotatsu.history.domain.ChapterExtra
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseRecyclerAdapter
|
|
||||||
import org.koitharu.kotatsu.ui.base.list.OnRecyclerItemClickListener
|
|
||||||
|
|
||||||
class ChaptersAdapter(onItemClickListener: OnRecyclerItemClickListener<MangaChapter>) :
|
class ChaptersAdapter(onItemClickListener: OnRecyclerItemClickListener<MangaChapter>) :
|
||||||
BaseRecyclerAdapter<MangaChapter, ChapterExtra>(onItemClickListener) {
|
BaseRecyclerAdapter<MangaChapter, ChapterExtra>(onItemClickListener) {
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.details
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
import android.app.ActivityOptions
|
import android.app.ActivityOptions
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
@@ -12,22 +12,22 @@ import androidx.recyclerview.widget.DividerItemDecoration
|
|||||||
import androidx.recyclerview.widget.LinearLayoutManager
|
import androidx.recyclerview.widget.LinearLayoutManager
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import kotlinx.android.synthetic.main.fragment_chapters.*
|
import kotlinx.android.synthetic.main.fragment_chapters.*
|
||||||
import moxy.ktx.moxyPresenter
|
import org.koin.android.viewmodel.ext.android.sharedViewModel
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.core.model.*
|
import org.koitharu.kotatsu.base.ui.BaseFragment
|
||||||
import org.koitharu.kotatsu.ui.base.BaseFragment
|
import org.koitharu.kotatsu.base.ui.list.OnRecyclerItemClickListener
|
||||||
import org.koitharu.kotatsu.ui.base.list.OnRecyclerItemClickListener
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.ui.download.DownloadService
|
import org.koitharu.kotatsu.core.model.MangaChapter
|
||||||
import org.koitharu.kotatsu.ui.reader.ReaderActivity
|
import org.koitharu.kotatsu.core.model.MangaHistory
|
||||||
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
|
import org.koitharu.kotatsu.download.DownloadService
|
||||||
|
import org.koitharu.kotatsu.reader.ui.ReaderActivity
|
||||||
import org.koitharu.kotatsu.utils.ext.resolveDp
|
import org.koitharu.kotatsu.utils.ext.resolveDp
|
||||||
|
|
||||||
class ChaptersFragment : BaseFragment(R.layout.fragment_chapters), MangaDetailsView,
|
class ChaptersFragment : BaseFragment(R.layout.fragment_chapters),
|
||||||
OnRecyclerItemClickListener<MangaChapter>, ActionMode.Callback {
|
OnRecyclerItemClickListener<MangaChapter>, ActionMode.Callback {
|
||||||
|
|
||||||
@Suppress("unused")
|
private val viewModel by sharedViewModel<DetailsViewModel>()
|
||||||
private val presenter by moxyPresenter {
|
|
||||||
MangaDetailsPresenter.getInstance(activity.hashCode())
|
|
||||||
}
|
|
||||||
|
|
||||||
private var manga: Manga? = null
|
private var manga: Manga? = null
|
||||||
|
|
||||||
@@ -45,33 +45,32 @@ class ChaptersFragment : BaseFragment(R.layout.fragment_chapters), MangaDetailsV
|
|||||||
)
|
)
|
||||||
recyclerView_chapters.setHasFixedSize(true)
|
recyclerView_chapters.setHasFixedSize(true)
|
||||||
recyclerView_chapters.adapter = adapter
|
recyclerView_chapters.adapter = adapter
|
||||||
|
|
||||||
|
viewModel.mangaData.observe(viewLifecycleOwner, this::onMangaUpdated)
|
||||||
|
viewModel.isLoading.observe(viewLifecycleOwner, this::onLoadingStateChanged)
|
||||||
|
viewModel.history.observe(viewLifecycleOwner, this::onHistoryChanged)
|
||||||
|
viewModel.newChapters.observe(viewLifecycleOwner, this::onNewChaptersChanged)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onMangaUpdated(manga: Manga) {
|
private fun onMangaUpdated(manga: Manga) {
|
||||||
this.manga = manga
|
this.manga = manga
|
||||||
adapter.replaceData(manga.chapters.orEmpty())
|
adapter.replaceData(manga.chapters.orEmpty())
|
||||||
scrollToCurrent()
|
scrollToCurrent()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onLoadingStateChanged(isLoading: Boolean) {
|
private fun onLoadingStateChanged(isLoading: Boolean) {
|
||||||
progressBar.isVisible = isLoading
|
progressBar.isVisible = isLoading
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onError(e: Throwable) = Unit //handled in activity
|
private fun onHistoryChanged(history: MangaHistory?) {
|
||||||
|
|
||||||
override fun onMangaRemoved(manga: Manga) = Unit //handled in activity
|
|
||||||
|
|
||||||
override fun onHistoryChanged(history: MangaHistory?) {
|
|
||||||
adapter.currentChapterId = history?.chapterId
|
adapter.currentChapterId = history?.chapterId
|
||||||
scrollToCurrent()
|
scrollToCurrent()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onNewChaptersChanged(newChapters: Int) {
|
private fun onNewChaptersChanged(newChapters: Int) {
|
||||||
adapter.newChaptersCount = newChapters
|
adapter.newChaptersCount = newChapters
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onFavouriteChanged(categories: List<FavouriteCategory>) = Unit
|
|
||||||
|
|
||||||
override fun onItemClick(item: MangaChapter, position: Int, view: View) {
|
override fun onItemClick(item: MangaChapter, position: Int, view: View) {
|
||||||
if (adapter.checkedItemsCount != 0) {
|
if (adapter.checkedItemsCount != 0) {
|
||||||
adapter.toggleItemChecked(item.id)
|
adapter.toggleItemChecked(item.id)
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.details
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
@@ -18,28 +18,22 @@ import com.google.android.material.tabs.TabLayout
|
|||||||
import com.google.android.material.tabs.TabLayoutMediator
|
import com.google.android.material.tabs.TabLayoutMediator
|
||||||
import kotlinx.android.synthetic.main.activity_details.*
|
import kotlinx.android.synthetic.main.activity_details.*
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import moxy.MvpDelegate
|
import org.koin.android.viewmodel.ext.android.viewModel
|
||||||
import moxy.ktx.moxyPresenter
|
|
||||||
import org.koitharu.kotatsu.BuildConfig
|
import org.koitharu.kotatsu.BuildConfig
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.base.ui.BaseActivity
|
||||||
|
import org.koitharu.kotatsu.browser.BrowserActivity
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.core.model.MangaHistory
|
|
||||||
import org.koitharu.kotatsu.core.model.MangaSource
|
import org.koitharu.kotatsu.core.model.MangaSource
|
||||||
import org.koitharu.kotatsu.ui.base.BaseActivity
|
import org.koitharu.kotatsu.download.DownloadService
|
||||||
import org.koitharu.kotatsu.ui.browser.BrowserActivity
|
|
||||||
import org.koitharu.kotatsu.ui.download.DownloadService
|
|
||||||
import org.koitharu.kotatsu.utils.MangaShortcut
|
import org.koitharu.kotatsu.utils.MangaShortcut
|
||||||
import org.koitharu.kotatsu.utils.ShareHelper
|
import org.koitharu.kotatsu.utils.ShareHelper
|
||||||
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
||||||
import org.koitharu.kotatsu.utils.ext.getThemeColor
|
import org.koitharu.kotatsu.utils.ext.getThemeColor
|
||||||
|
|
||||||
class MangaDetailsActivity : BaseActivity(), MangaDetailsView,
|
class DetailsActivity : BaseActivity(), TabLayoutMediator.TabConfigurationStrategy {
|
||||||
TabLayoutMediator.TabConfigurationStrategy {
|
|
||||||
|
|
||||||
private val presenter by moxyPresenter {
|
private val viewModel by viewModel<DetailsViewModel>()
|
||||||
MangaDetailsPresenter.getInstance(hashCode())
|
|
||||||
}
|
|
||||||
|
|
||||||
private var manga: Manga? = null
|
private var manga: Manga? = null
|
||||||
|
|
||||||
@@ -49,28 +43,27 @@ class MangaDetailsActivity : BaseActivity(), MangaDetailsView,
|
|||||||
supportActionBar?.setDisplayHomeAsUpEnabled(true)
|
supportActionBar?.setDisplayHomeAsUpEnabled(true)
|
||||||
pager.adapter = MangaDetailsAdapter(this)
|
pager.adapter = MangaDetailsAdapter(this)
|
||||||
TabLayoutMediator(tabs, pager, this).attach()
|
TabLayoutMediator(tabs, pager, this).attach()
|
||||||
if (savedInstanceState?.containsKey(MvpDelegate.MOXY_DELEGATE_TAGS_KEY) != true) {
|
if (savedInstanceState == null) {
|
||||||
intent?.getParcelableExtra<Manga>(EXTRA_MANGA)?.let {
|
intent?.getParcelableExtra<Manga>(EXTRA_MANGA)?.let {
|
||||||
presenter.loadDetails(it, true)
|
viewModel.loadDetails(it, true)
|
||||||
} ?: intent?.getLongExtra(EXTRA_MANGA_ID, 0)?.takeUnless { it == 0L }?.let {
|
} ?: intent?.getLongExtra(EXTRA_MANGA_ID, 0)?.takeUnless { it == 0L }?.let {
|
||||||
presenter.findMangaById(it)
|
viewModel.findMangaById(it)
|
||||||
} ?: finishAfterTransition()
|
} ?: finishAfterTransition()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
viewModel.mangaData.observe(this, ::onMangaUpdated)
|
||||||
|
viewModel.onMangaRemoved.observe(this, ::onMangaRemoved)
|
||||||
|
viewModel.onError.observe(this, ::onError)
|
||||||
|
viewModel.newChapters.observe(this, ::onNewChaptersChanged)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onMangaUpdated(manga: Manga) {
|
private fun onMangaUpdated(manga: Manga) {
|
||||||
this.manga = manga
|
this.manga = manga
|
||||||
title = manga.title
|
title = manga.title
|
||||||
invalidateOptionsMenu()
|
invalidateOptionsMenu()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onHistoryChanged(history: MangaHistory?) = Unit
|
private fun onMangaRemoved(manga: Manga) {
|
||||||
|
|
||||||
override fun onFavouriteChanged(categories: List<FavouriteCategory>) = Unit
|
|
||||||
|
|
||||||
override fun onLoadingStateChanged(isLoading: Boolean) = Unit
|
|
||||||
|
|
||||||
override fun onMangaRemoved(manga: Manga) {
|
|
||||||
Toast.makeText(
|
Toast.makeText(
|
||||||
this, getString(R.string._s_deleted_from_local_storage, manga.title),
|
this, getString(R.string._s_deleted_from_local_storage, manga.title),
|
||||||
Toast.LENGTH_SHORT
|
Toast.LENGTH_SHORT
|
||||||
@@ -78,7 +71,7 @@ class MangaDetailsActivity : BaseActivity(), MangaDetailsView,
|
|||||||
finishAfterTransition()
|
finishAfterTransition()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onError(e: Throwable) {
|
private fun onError(e: Throwable) {
|
||||||
if (manga == null) {
|
if (manga == null) {
|
||||||
Toast.makeText(this, e.getDisplayMessage(resources), Toast.LENGTH_LONG).show()
|
Toast.makeText(this, e.getDisplayMessage(resources), Toast.LENGTH_LONG).show()
|
||||||
finishAfterTransition()
|
finishAfterTransition()
|
||||||
@@ -87,7 +80,7 @@ class MangaDetailsActivity : BaseActivity(), MangaDetailsView,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onNewChaptersChanged(newChapters: Int) {
|
private fun onNewChaptersChanged(newChapters: Int) {
|
||||||
val tab = tabs.getTabAt(1) ?: return
|
val tab = tabs.getTabAt(1) ?: return
|
||||||
if (newChapters == 0) {
|
if (newChapters == 0) {
|
||||||
tab.removeBadge()
|
tab.removeBadge()
|
||||||
@@ -132,7 +125,7 @@ class MangaDetailsActivity : BaseActivity(), MangaDetailsView,
|
|||||||
.setTitle(R.string.delete_manga)
|
.setTitle(R.string.delete_manga)
|
||||||
.setMessage(getString(R.string.text_delete_local_manga, m.title))
|
.setMessage(getString(R.string.text_delete_local_manga, m.title))
|
||||||
.setPositiveButton(R.string.delete) { _, _ ->
|
.setPositiveButton(R.string.delete) { _, _ ->
|
||||||
presenter.deleteLocal(m)
|
viewModel.deleteLocal(m)
|
||||||
}
|
}
|
||||||
.setNegativeButton(android.R.string.cancel, null)
|
.setNegativeButton(android.R.string.cancel, null)
|
||||||
.show()
|
.show()
|
||||||
@@ -174,7 +167,7 @@ class MangaDetailsActivity : BaseActivity(), MangaDetailsView,
|
|||||||
R.id.action_shortcut -> {
|
R.id.action_shortcut -> {
|
||||||
manga?.let {
|
manga?.let {
|
||||||
lifecycleScope.launch {
|
lifecycleScope.launch {
|
||||||
if (!MangaShortcut(it).requestPinShortcut(this@MangaDetailsActivity)) {
|
if (!MangaShortcut(it).requestPinShortcut(this@DetailsActivity)) {
|
||||||
Snackbar.make(
|
Snackbar.make(
|
||||||
pager,
|
pager,
|
||||||
R.string.operation_not_supported,
|
R.string.operation_not_supported,
|
||||||
@@ -217,11 +210,11 @@ class MangaDetailsActivity : BaseActivity(), MangaDetailsView,
|
|||||||
const val ACTION_MANGA_VIEW = "${BuildConfig.APPLICATION_ID}.action.VIEW_MANGA"
|
const val ACTION_MANGA_VIEW = "${BuildConfig.APPLICATION_ID}.action.VIEW_MANGA"
|
||||||
|
|
||||||
fun newIntent(context: Context, manga: Manga) =
|
fun newIntent(context: Context, manga: Manga) =
|
||||||
Intent(context, MangaDetailsActivity::class.java)
|
Intent(context, DetailsActivity::class.java)
|
||||||
.putExtra(EXTRA_MANGA, manga)
|
.putExtra(EXTRA_MANGA, manga)
|
||||||
|
|
||||||
fun newIntent(context: Context, mangaId: Long) =
|
fun newIntent(context: Context, mangaId: Long) =
|
||||||
Intent(context, MangaDetailsActivity::class.java)
|
Intent(context, DetailsActivity::class.java)
|
||||||
.putExtra(EXTRA_MANGA_ID, mangaId)
|
.putExtra(EXTRA_MANGA_ID, mangaId)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,5 +1,6 @@
|
|||||||
package org.koitharu.kotatsu.ui.details
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
|
import android.os.Bundle
|
||||||
import android.text.Spanned
|
import android.text.Spanned
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import androidx.core.net.toUri
|
import androidx.core.net.toUri
|
||||||
@@ -10,32 +11,36 @@ import kotlinx.android.synthetic.main.fragment_details.*
|
|||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
import moxy.ktx.moxyPresenter
|
import org.koin.android.viewmodel.ext.android.sharedViewModel
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.BaseFragment
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.core.model.MangaHistory
|
import org.koitharu.kotatsu.core.model.MangaHistory
|
||||||
import org.koitharu.kotatsu.ui.base.BaseFragment
|
import org.koitharu.kotatsu.favourites.ui.categories.select.FavouriteCategoriesDialog
|
||||||
import org.koitharu.kotatsu.ui.list.favourites.categories.select.FavouriteCategoriesDialog
|
import org.koitharu.kotatsu.reader.ui.ReaderActivity
|
||||||
import org.koitharu.kotatsu.ui.reader.ReaderActivity
|
import org.koitharu.kotatsu.search.ui.MangaSearchSheet
|
||||||
import org.koitharu.kotatsu.ui.search.MangaSearchSheet
|
|
||||||
import org.koitharu.kotatsu.utils.FileSizeUtils
|
import org.koitharu.kotatsu.utils.FileSizeUtils
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import kotlin.math.roundToInt
|
import kotlin.math.roundToInt
|
||||||
|
|
||||||
class MangaDetailsFragment : BaseFragment(R.layout.fragment_details), MangaDetailsView,
|
class DetailsFragment : BaseFragment(R.layout.fragment_details), View.OnClickListener,
|
||||||
View.OnClickListener,
|
|
||||||
View.OnLongClickListener {
|
View.OnLongClickListener {
|
||||||
|
|
||||||
@Suppress("unused")
|
private val viewModel by sharedViewModel<DetailsViewModel>()
|
||||||
private val presenter by moxyPresenter {
|
|
||||||
MangaDetailsPresenter.getInstance(activity.hashCode())
|
|
||||||
}
|
|
||||||
|
|
||||||
private var manga: Manga? = null
|
private var manga: Manga? = null
|
||||||
private var history: MangaHistory? = null
|
private var history: MangaHistory? = null
|
||||||
|
|
||||||
override fun onMangaUpdated(manga: Manga) {
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
|
super.onViewCreated(view, savedInstanceState)
|
||||||
|
viewModel.mangaData.observe(viewLifecycleOwner, ::onMangaUpdated)
|
||||||
|
viewModel.isLoading.observe(viewLifecycleOwner, ::onLoadingStateChanged)
|
||||||
|
viewModel.favouriteCategories.observe(viewLifecycleOwner, ::onFavouriteChanged)
|
||||||
|
viewModel.history.observe(viewLifecycleOwner, ::onHistoryChanged)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun onMangaUpdated(manga: Manga) {
|
||||||
this.manga = manga
|
this.manga = manga
|
||||||
imageView_cover.newImageRequest(manga.largeCoverUrl ?: manga.coverUrl)
|
imageView_cover.newImageRequest(manga.largeCoverUrl ?: manga.coverUrl)
|
||||||
.fallback(R.drawable.ic_placeholder)
|
.fallback(R.drawable.ic_placeholder)
|
||||||
@@ -59,7 +64,7 @@ class MangaDetailsFragment : BaseFragment(R.layout.fragment_details), MangaDetai
|
|||||||
text = it,
|
text = it,
|
||||||
iconRes = R.drawable.ic_chip_user,
|
iconRes = R.drawable.ic_chip_user,
|
||||||
tag = it,
|
tag = it,
|
||||||
onClickListener = this@MangaDetailsFragment
|
onClickListener = this@DetailsFragment
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -68,7 +73,7 @@ class MangaDetailsFragment : BaseFragment(R.layout.fragment_details), MangaDetai
|
|||||||
text = it.title,
|
text = it.title,
|
||||||
iconRes = R.drawable.ic_chip_tag,
|
iconRes = R.drawable.ic_chip_tag,
|
||||||
tag = it,
|
tag = it,
|
||||||
onClickListener = this@MangaDetailsFragment
|
onClickListener = this@DetailsFragment
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
manga.url.toUri().toFileOrNull()?.let { f ->
|
manga.url.toUri().toFileOrNull()?.let { f ->
|
||||||
@@ -81,7 +86,7 @@ class MangaDetailsFragment : BaseFragment(R.layout.fragment_details), MangaDetai
|
|||||||
text = FileSizeUtils.formatBytes(context, size),
|
text = FileSizeUtils.formatBytes(context, size),
|
||||||
iconRes = R.drawable.ic_chip_storage,
|
iconRes = R.drawable.ic_chip_storage,
|
||||||
tag = it,
|
tag = it,
|
||||||
onClickListener = this@MangaDetailsFragment
|
onClickListener = this@DetailsFragment
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -92,12 +97,12 @@ class MangaDetailsFragment : BaseFragment(R.layout.fragment_details), MangaDetai
|
|||||||
updateReadButton()
|
updateReadButton()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onHistoryChanged(history: MangaHistory?) {
|
private fun onHistoryChanged(history: MangaHistory?) {
|
||||||
this.history = history
|
this.history = history
|
||||||
updateReadButton()
|
updateReadButton()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onFavouriteChanged(categories: List<FavouriteCategory>) {
|
private fun onFavouriteChanged(categories: List<FavouriteCategory>) {
|
||||||
imageView_favourite.setImageResource(
|
imageView_favourite.setImageResource(
|
||||||
if (categories.isEmpty()) {
|
if (categories.isEmpty()) {
|
||||||
R.drawable.ic_heart_outline
|
R.drawable.ic_heart_outline
|
||||||
@@ -107,16 +112,10 @@ class MangaDetailsFragment : BaseFragment(R.layout.fragment_details), MangaDetai
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onLoadingStateChanged(isLoading: Boolean) {
|
private fun onLoadingStateChanged(isLoading: Boolean) {
|
||||||
progressBar.isVisible = isLoading
|
progressBar.isVisible = isLoading
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onError(e: Throwable) = Unit //handled in activity
|
|
||||||
|
|
||||||
override fun onMangaRemoved(manga: Manga) = Unit //handled in activity
|
|
||||||
|
|
||||||
override fun onNewChaptersChanged(newChapters: Int) = Unit
|
|
||||||
|
|
||||||
override fun onClick(v: View) {
|
override fun onClick(v: View) {
|
||||||
when {
|
when {
|
||||||
v.id == R.id.imageView_favourite -> {
|
v.id == R.id.imageView_favourite -> {
|
||||||
@@ -0,0 +1,135 @@
|
|||||||
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
|
import androidx.lifecycle.MutableLiveData
|
||||||
|
import kotlinx.coroutines.Dispatchers
|
||||||
|
import kotlinx.coroutines.flow.*
|
||||||
|
import kotlinx.coroutines.withContext
|
||||||
|
import org.koitharu.kotatsu.base.domain.MangaDataRepository
|
||||||
|
import org.koitharu.kotatsu.core.exceptions.MangaNotFoundException
|
||||||
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
|
import org.koitharu.kotatsu.core.model.MangaHistory
|
||||||
|
import org.koitharu.kotatsu.favourites.domain.FavouritesRepository
|
||||||
|
import org.koitharu.kotatsu.favourites.domain.OnFavouritesChangeListener
|
||||||
|
import org.koitharu.kotatsu.history.domain.HistoryRepository
|
||||||
|
import org.koitharu.kotatsu.history.domain.OnHistoryChangeListener
|
||||||
|
import org.koitharu.kotatsu.list.ui.MangaListViewModel
|
||||||
|
import org.koitharu.kotatsu.local.domain.LocalMangaRepository
|
||||||
|
import org.koitharu.kotatsu.search.domain.MangaSearchRepository
|
||||||
|
import org.koitharu.kotatsu.tracker.domain.TrackingRepository
|
||||||
|
import org.koitharu.kotatsu.utils.SingleLiveEvent
|
||||||
|
import org.koitharu.kotatsu.utils.ext.onFirst
|
||||||
|
import org.koitharu.kotatsu.utils.ext.safe
|
||||||
|
import java.io.IOException
|
||||||
|
|
||||||
|
class DetailsViewModel(
|
||||||
|
private val historyRepository: HistoryRepository,
|
||||||
|
private val favouritesRepository: FavouritesRepository,
|
||||||
|
private val localMangaRepository: LocalMangaRepository,
|
||||||
|
private val trackingRepository: TrackingRepository,
|
||||||
|
private val searchRepository: MangaSearchRepository,
|
||||||
|
private val mangaDataRepository: MangaDataRepository
|
||||||
|
) : MangaListViewModel(), OnHistoryChangeListener, OnFavouritesChangeListener {
|
||||||
|
|
||||||
|
val mangaData = MutableLiveData<Manga>()
|
||||||
|
val newChapters = MutableLiveData<Int>(0)
|
||||||
|
val onMangaRemoved = SingleLiveEvent<Manga>()
|
||||||
|
val history = MutableLiveData<MangaHistory?>()
|
||||||
|
val favouriteCategories = MutableLiveData<List<FavouriteCategory>>()
|
||||||
|
|
||||||
|
init {
|
||||||
|
HistoryRepository.subscribe(this)
|
||||||
|
FavouritesRepository.subscribe(this)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun findMangaById(id: Long) {
|
||||||
|
launchLoadingJob {
|
||||||
|
val manga = mangaDataRepository.findMangaById(id)
|
||||||
|
?: throw MangaNotFoundException("Cannot find manga by id")
|
||||||
|
mangaData.value = manga
|
||||||
|
loadDetails(manga, true)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun loadDetails(manga: Manga, force: Boolean = false) {
|
||||||
|
if (!force && mangaData.value == manga) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
loadHistory(manga)
|
||||||
|
mangaData.value = manga
|
||||||
|
loadFavourite(manga)
|
||||||
|
launchLoadingJob {
|
||||||
|
val data = withContext(Dispatchers.Default) {
|
||||||
|
manga.source.repository.getDetails(manga)
|
||||||
|
}
|
||||||
|
mangaData.value = data
|
||||||
|
newChapters.value = trackingRepository.getNewChaptersCount(manga.id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun deleteLocal(manga: Manga) {
|
||||||
|
launchLoadingJob {
|
||||||
|
withContext(Dispatchers.Default) {
|
||||||
|
val original = localMangaRepository.getRemoteManga(manga)
|
||||||
|
localMangaRepository.delete(manga) || throw IOException("Unable to delete file")
|
||||||
|
safe {
|
||||||
|
historyRepository.deleteOrSwap(manga, original)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
onMangaRemoved.call(manga)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun loadHistory(manga: Manga) {
|
||||||
|
launchJob {
|
||||||
|
history.value = historyRepository.getOne(manga)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun loadFavourite(manga: Manga) {
|
||||||
|
launchJob {
|
||||||
|
favouriteCategories.value = favouritesRepository.getCategories(manga.id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun loadRelated() {
|
||||||
|
val manga = mangaData.value ?: return
|
||||||
|
searchRepository.globalSearch(manga.title)
|
||||||
|
.map { list ->
|
||||||
|
list.filter { x -> x.id != manga.id }
|
||||||
|
}.filterNot { x -> x.isEmpty() }
|
||||||
|
.flowOn(Dispatchers.IO)
|
||||||
|
.catch { e ->
|
||||||
|
if (e is IOException) {
|
||||||
|
onError.call(e)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.onEmpty {
|
||||||
|
content.value = emptyList()
|
||||||
|
isLoading.value = false
|
||||||
|
}.onCompletion {
|
||||||
|
// TODO
|
||||||
|
}.onFirst {
|
||||||
|
isLoading.value = false
|
||||||
|
}.onEach {
|
||||||
|
content.value = content.value.orEmpty() + it
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onHistoryChanged() {
|
||||||
|
loadHistory(mangaData.value ?: return)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onFavouritesChanged(mangaId: Long) {
|
||||||
|
val manga = mangaData.value ?: return
|
||||||
|
if (mangaId == manga.id) {
|
||||||
|
loadFavourite(manga)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onCleared() {
|
||||||
|
HistoryRepository.unsubscribe(this)
|
||||||
|
FavouritesRepository.unsubscribe(this)
|
||||||
|
super.onCleared()
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.details
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
import androidx.fragment.app.Fragment
|
import androidx.fragment.app.Fragment
|
||||||
import androidx.fragment.app.FragmentActivity
|
import androidx.fragment.app.FragmentActivity
|
||||||
@@ -8,8 +8,8 @@ class MangaDetailsAdapter(activity: FragmentActivity) : FragmentStateAdapter(act
|
|||||||
|
|
||||||
override fun getItemCount() = 3
|
override fun getItemCount() = 3
|
||||||
|
|
||||||
override fun createFragment(position: Int): Fragment = when(position) {
|
override fun createFragment(position: Int): Fragment = when (position) {
|
||||||
0 -> MangaDetailsFragment()
|
0 -> DetailsFragment()
|
||||||
1 -> ChaptersFragment()
|
1 -> ChaptersFragment()
|
||||||
2 -> RelatedMangaFragment()
|
2 -> RelatedMangaFragment()
|
||||||
else -> throw IndexOutOfBoundsException("No fragment for position $position")
|
else -> throw IndexOutOfBoundsException("No fragment for position $position")
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
package org.koitharu.kotatsu.details.ui
|
||||||
|
|
||||||
|
import android.os.Bundle
|
||||||
|
import android.view.View
|
||||||
|
import org.koin.android.viewmodel.ext.android.sharedViewModel
|
||||||
|
import org.koitharu.kotatsu.list.ui.MangaListFragment
|
||||||
|
|
||||||
|
class RelatedMangaFragment : MangaListFragment() {
|
||||||
|
|
||||||
|
override val viewModel by sharedViewModel<DetailsViewModel>()
|
||||||
|
|
||||||
|
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||||
|
super.onViewCreated(view, savedInstanceState)
|
||||||
|
isSwipeRefreshEnabled = false
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onRequestMoreItems(offset: Int) {
|
||||||
|
if (offset == 0) {
|
||||||
|
viewModel.loadRelated()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.download
|
package org.koitharu.kotatsu.download
|
||||||
|
|
||||||
import android.app.Notification
|
import android.app.Notification
|
||||||
import android.app.NotificationChannel
|
import android.app.NotificationChannel
|
||||||
@@ -12,7 +12,7 @@ import androidx.core.content.ContextCompat
|
|||||||
import androidx.core.graphics.drawable.toBitmap
|
import androidx.core.graphics.drawable.toBitmap
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.ui.details.MangaDetailsActivity
|
import org.koitharu.kotatsu.details.ui.DetailsActivity
|
||||||
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
||||||
import kotlin.math.roundToInt
|
import kotlin.math.roundToInt
|
||||||
|
|
||||||
@@ -24,7 +24,8 @@ class DownloadNotification(private val context: Context) {
|
|||||||
|
|
||||||
init {
|
init {
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O
|
||||||
&& manager.getNotificationChannel(CHANNEL_ID) == null) {
|
&& manager.getNotificationChannel(CHANNEL_ID) == null
|
||||||
|
) {
|
||||||
val channel = NotificationChannel(
|
val channel = NotificationChannel(
|
||||||
CHANNEL_ID,
|
CHANNEL_ID,
|
||||||
context.getString(R.string.downloads),
|
context.getString(R.string.downloads),
|
||||||
@@ -145,7 +146,7 @@ class DownloadNotification(private val context: Context) {
|
|||||||
private fun createIntent(context: Context, manga: Manga) = PendingIntent.getActivity(
|
private fun createIntent(context: Context, manga: Manga) = PendingIntent.getActivity(
|
||||||
context,
|
context,
|
||||||
manga.hashCode(),
|
manga.hashCode(),
|
||||||
MangaDetailsActivity.newIntent(context, manga),
|
DetailsActivity.newIntent(context, manga),
|
||||||
PendingIntent.FLAG_CANCEL_CURRENT
|
PendingIntent.FLAG_CANCEL_CURRENT
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.download
|
package org.koitharu.kotatsu.download
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
@@ -7,6 +7,7 @@ import android.os.PowerManager
|
|||||||
import android.webkit.MimeTypeMap
|
import android.webkit.MimeTypeMap
|
||||||
import android.widget.Toast
|
import android.widget.Toast
|
||||||
import androidx.core.content.ContextCompat
|
import androidx.core.content.ContextCompat
|
||||||
|
import androidx.lifecycle.lifecycleScope
|
||||||
import coil.ImageLoader
|
import coil.ImageLoader
|
||||||
import coil.request.ImageRequest
|
import coil.request.ImageRequest
|
||||||
import kotlinx.coroutines.*
|
import kotlinx.coroutines.*
|
||||||
@@ -19,13 +20,13 @@ import org.koin.android.ext.android.inject
|
|||||||
import org.koin.core.context.GlobalContext
|
import org.koin.core.context.GlobalContext
|
||||||
import org.koitharu.kotatsu.BuildConfig
|
import org.koitharu.kotatsu.BuildConfig
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.core.local.PagesCache
|
import org.koitharu.kotatsu.base.ui.BaseService
|
||||||
|
import org.koitharu.kotatsu.base.ui.dialog.CheckBoxAlertDialog
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.core.parser.LocalMangaRepository
|
|
||||||
import org.koitharu.kotatsu.core.prefs.AppSettings
|
import org.koitharu.kotatsu.core.prefs.AppSettings
|
||||||
import org.koitharu.kotatsu.domain.local.MangaZip
|
import org.koitharu.kotatsu.local.data.MangaZip
|
||||||
import org.koitharu.kotatsu.ui.base.BaseService
|
import org.koitharu.kotatsu.local.data.PagesCache
|
||||||
import org.koitharu.kotatsu.ui.base.dialog.CheckBoxAlertDialog
|
import org.koitharu.kotatsu.local.domain.LocalMangaRepository
|
||||||
import org.koitharu.kotatsu.utils.CacheUtils
|
import org.koitharu.kotatsu.utils.CacheUtils
|
||||||
import org.koitharu.kotatsu.utils.ext.*
|
import org.koitharu.kotatsu.utils.ext.*
|
||||||
import java.io.File
|
import java.io.File
|
||||||
@@ -54,8 +55,9 @@ class DownloadService : BaseService() {
|
|||||||
.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "kotatsu:downloading")
|
.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "kotatsu:downloading")
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
|
override fun onStartCommand(intent: Intent, flags: Int, startId: Int): Int {
|
||||||
when (intent?.action) {
|
super.onStartCommand(intent, flags, startId)
|
||||||
|
when (intent.action) {
|
||||||
ACTION_DOWNLOAD_START -> {
|
ACTION_DOWNLOAD_START -> {
|
||||||
val manga = intent.getParcelableExtra<Manga>(EXTRA_MANGA)
|
val manga = intent.getParcelableExtra<Manga>(EXTRA_MANGA)
|
||||||
val chapters = intent.getLongArrayExtra(EXTRA_CHAPTERS_IDS)?.toArraySet()
|
val chapters = intent.getLongArrayExtra(EXTRA_CHAPTERS_IDS)?.toArraySet()
|
||||||
@@ -77,7 +79,7 @@ class DownloadService : BaseService() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun downloadManga(manga: Manga, chaptersIds: Set<Long>?, startId: Int): Job {
|
private fun downloadManga(manga: Manga, chaptersIds: Set<Long>?, startId: Int): Job {
|
||||||
return serviceScope.launch(Dispatchers.Default) {
|
return lifecycleScope.launch(Dispatchers.Default) {
|
||||||
mutex.lock()
|
mutex.lock()
|
||||||
wakeLock.acquire(TimeUnit.HOURS.toMillis(1))
|
wakeLock.acquire(TimeUnit.HOURS.toMillis(1))
|
||||||
notification.fillFrom(manga)
|
notification.fillFrom(manga)
|
||||||
@@ -0,0 +1,18 @@
|
|||||||
|
package org.koitharu.kotatsu.favourites
|
||||||
|
|
||||||
|
import org.koin.android.viewmodel.dsl.viewModel
|
||||||
|
import org.koin.dsl.module
|
||||||
|
import org.koitharu.kotatsu.favourites.domain.FavouritesRepository
|
||||||
|
import org.koitharu.kotatsu.favourites.ui.categories.FavouritesCategoriesViewModel
|
||||||
|
import org.koitharu.kotatsu.favourites.ui.list.FavouritesListViewModel
|
||||||
|
|
||||||
|
val favouritesModule
|
||||||
|
get() = module {
|
||||||
|
|
||||||
|
single { FavouritesRepository(get()) }
|
||||||
|
|
||||||
|
viewModel { (categoryId: Long) ->
|
||||||
|
FavouritesListViewModel(categoryId, get())
|
||||||
|
}
|
||||||
|
viewModel { FavouritesCategoriesViewModel(get()) }
|
||||||
|
}
|
||||||
@@ -1,7 +1,6 @@
|
|||||||
package org.koitharu.kotatsu.core.db.dao
|
package org.koitharu.kotatsu.favourites.data
|
||||||
|
|
||||||
import androidx.room.*
|
import androidx.room.*
|
||||||
import org.koitharu.kotatsu.core.db.entity.FavouriteCategoryEntity
|
|
||||||
|
|
||||||
@Dao
|
@Dao
|
||||||
abstract class FavouriteCategoriesDao {
|
abstract class FavouriteCategoriesDao {
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.core.db.entity
|
package org.koitharu.kotatsu.favourites.data
|
||||||
|
|
||||||
import androidx.room.ColumnInfo
|
import androidx.room.ColumnInfo
|
||||||
import androidx.room.Entity
|
import androidx.room.Entity
|
||||||
@@ -1,8 +1,9 @@
|
|||||||
package org.koitharu.kotatsu.core.db.entity
|
package org.koitharu.kotatsu.favourites.data
|
||||||
|
|
||||||
import androidx.room.ColumnInfo
|
import androidx.room.ColumnInfo
|
||||||
import androidx.room.Entity
|
import androidx.room.Entity
|
||||||
import androidx.room.ForeignKey
|
import androidx.room.ForeignKey
|
||||||
|
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
||||||
|
|
||||||
@Entity(
|
@Entity(
|
||||||
tableName = "favourites", primaryKeys = ["manga_id", "category_id"], foreignKeys = [
|
tableName = "favourites", primaryKeys = ["manga_id", "category_id"], foreignKeys = [
|
||||||
@@ -1,8 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.core.db.entity
|
package org.koitharu.kotatsu.favourites.data
|
||||||
|
|
||||||
import androidx.room.Embedded
|
import androidx.room.Embedded
|
||||||
import androidx.room.Junction
|
import androidx.room.Junction
|
||||||
import androidx.room.Relation
|
import androidx.room.Relation
|
||||||
|
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
||||||
|
import org.koitharu.kotatsu.core.db.entity.MangaTagsEntity
|
||||||
|
import org.koitharu.kotatsu.core.db.entity.TagEntity
|
||||||
|
|
||||||
data class FavouriteManga(
|
data class FavouriteManga(
|
||||||
@Embedded val favourite: FavouriteEntity,
|
@Embedded val favourite: FavouriteEntity,
|
||||||
@@ -1,8 +1,6 @@
|
|||||||
package org.koitharu.kotatsu.core.db.dao
|
package org.koitharu.kotatsu.favourites.data
|
||||||
|
|
||||||
import androidx.room.*
|
import androidx.room.*
|
||||||
import org.koitharu.kotatsu.core.db.entity.FavouriteEntity
|
|
||||||
import org.koitharu.kotatsu.core.db.entity.FavouriteManga
|
|
||||||
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
||||||
|
|
||||||
@Dao
|
@Dao
|
||||||
@@ -1,16 +1,16 @@
|
|||||||
package org.koitharu.kotatsu.domain.favourites
|
package org.koitharu.kotatsu.favourites.domain
|
||||||
|
|
||||||
import androidx.collection.ArraySet
|
import androidx.collection.ArraySet
|
||||||
import androidx.room.withTransaction
|
import androidx.room.withTransaction
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
import org.koitharu.kotatsu.core.db.MangaDatabase
|
import org.koitharu.kotatsu.core.db.MangaDatabase
|
||||||
import org.koitharu.kotatsu.core.db.entity.FavouriteCategoryEntity
|
|
||||||
import org.koitharu.kotatsu.core.db.entity.FavouriteEntity
|
|
||||||
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
import org.koitharu.kotatsu.core.db.entity.MangaEntity
|
||||||
import org.koitharu.kotatsu.core.db.entity.TagEntity
|
import org.koitharu.kotatsu.core.db.entity.TagEntity
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteCategoryEntity
|
||||||
|
import org.koitharu.kotatsu.favourites.data.FavouriteEntity
|
||||||
import org.koitharu.kotatsu.utils.ext.mapToSet
|
import org.koitharu.kotatsu.utils.ext.mapToSet
|
||||||
|
|
||||||
class FavouritesRepository(private val db: MangaDatabase) {
|
class FavouritesRepository(private val db: MangaDatabase) {
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.domain.favourites
|
package org.koitharu.kotatsu.favourites.domain
|
||||||
|
|
||||||
fun interface OnFavouritesChangeListener {
|
fun interface OnFavouritesChangeListener {
|
||||||
|
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites
|
package org.koitharu.kotatsu.favourites.ui
|
||||||
|
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.view.Menu
|
import android.view.Menu
|
||||||
@@ -8,25 +8,25 @@ import android.view.View
|
|||||||
import com.google.android.material.snackbar.Snackbar
|
import com.google.android.material.snackbar.Snackbar
|
||||||
import com.google.android.material.tabs.TabLayoutMediator
|
import com.google.android.material.tabs.TabLayoutMediator
|
||||||
import kotlinx.android.synthetic.main.fragment_favourites.*
|
import kotlinx.android.synthetic.main.fragment_favourites.*
|
||||||
import moxy.ktx.moxyPresenter
|
import org.koin.android.viewmodel.ext.android.viewModel
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.BaseFragment
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.domain.favourites.FavouritesRepository
|
import org.koitharu.kotatsu.favourites.domain.FavouritesRepository
|
||||||
import org.koitharu.kotatsu.domain.favourites.OnFavouritesChangeListener
|
import org.koitharu.kotatsu.favourites.domain.OnFavouritesChangeListener
|
||||||
import org.koitharu.kotatsu.ui.base.BaseFragment
|
import org.koitharu.kotatsu.favourites.ui.categories.CategoriesActivity
|
||||||
import org.koitharu.kotatsu.ui.list.favourites.categories.CategoriesActivity
|
import org.koitharu.kotatsu.favourites.ui.categories.CategoriesEditDelegate
|
||||||
import org.koitharu.kotatsu.ui.list.favourites.categories.CategoriesEditDelegate
|
import org.koitharu.kotatsu.favourites.ui.categories.FavouritesCategoriesViewModel
|
||||||
import org.koitharu.kotatsu.ui.list.favourites.categories.FavouriteCategoriesPresenter
|
|
||||||
import org.koitharu.kotatsu.ui.list.favourites.categories.FavouriteCategoriesView
|
|
||||||
import org.koitharu.kotatsu.utils.ext.showPopupMenu
|
import org.koitharu.kotatsu.utils.ext.showPopupMenu
|
||||||
import java.util.*
|
import java.util.*
|
||||||
import kotlin.collections.ArrayList
|
import kotlin.collections.ArrayList
|
||||||
|
|
||||||
class FavouritesContainerFragment : BaseFragment(R.layout.fragment_favourites),
|
class FavouritesContainerFragment : BaseFragment(R.layout.fragment_favourites),
|
||||||
FavouriteCategoriesView, OnFavouritesChangeListener, FavouritesTabLongClickListener,
|
OnFavouritesChangeListener, FavouritesTabLongClickListener,
|
||||||
CategoriesEditDelegate.CategoriesEditCallback {
|
CategoriesEditDelegate.CategoriesEditCallback {
|
||||||
|
|
||||||
private val presenter by moxyPresenter(factory = ::FavouriteCategoriesPresenter)
|
private val viewModel by viewModel<FavouritesCategoriesViewModel>()
|
||||||
|
|
||||||
private val editDelegate by lazy(LazyThreadSafetyMode.NONE) {
|
private val editDelegate by lazy(LazyThreadSafetyMode.NONE) {
|
||||||
CategoriesEditDelegate(requireContext(), this)
|
CategoriesEditDelegate(requireContext(), this)
|
||||||
}
|
}
|
||||||
@@ -42,6 +42,9 @@ class FavouritesContainerFragment : BaseFragment(R.layout.fragment_favourites),
|
|||||||
pager.adapter = adapter
|
pager.adapter = adapter
|
||||||
TabLayoutMediator(tabs, pager, adapter).attach()
|
TabLayoutMediator(tabs, pager, adapter).attach()
|
||||||
FavouritesRepository.subscribe(this)
|
FavouritesRepository.subscribe(this)
|
||||||
|
|
||||||
|
viewModel.categories.observe(viewLifecycleOwner, ::onCategoriesChanged)
|
||||||
|
viewModel.onError.observe(viewLifecycleOwner, ::onError)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onDestroyView() {
|
override fun onDestroyView() {
|
||||||
@@ -49,7 +52,7 @@ class FavouritesContainerFragment : BaseFragment(R.layout.fragment_favourites),
|
|||||||
super.onDestroyView()
|
super.onDestroyView()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCategoriesChanged(categories: List<FavouriteCategory>) {
|
fun onCategoriesChanged(categories: List<FavouriteCategory>) {
|
||||||
val data = ArrayList<FavouriteCategory>(categories.size + 1)
|
val data = ArrayList<FavouriteCategory>(categories.size + 1)
|
||||||
data += FavouriteCategory(0L, getString(R.string.all_favourites), -1, Date())
|
data += FavouriteCategory(0L, getString(R.string.all_favourites), -1, Date())
|
||||||
data += categories
|
data += categories
|
||||||
@@ -75,16 +78,14 @@ class FavouritesContainerFragment : BaseFragment(R.layout.fragment_favourites),
|
|||||||
return getString(R.string.favourites)
|
return getString(R.string.favourites)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCheckedCategoriesChanged(checkedIds: Set<Int>) = Unit
|
private fun onError(e: Throwable) {
|
||||||
|
|
||||||
override fun onError(e: Throwable) {
|
|
||||||
Snackbar.make(pager, e.message ?: return, Snackbar.LENGTH_LONG).show()
|
Snackbar.make(pager, e.message ?: return, Snackbar.LENGTH_LONG).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onFavouritesChanged(mangaId: Long) = Unit
|
override fun onFavouritesChanged(mangaId: Long) = Unit
|
||||||
|
|
||||||
override fun onCategoriesChanged() {
|
override fun onCategoriesChanged() {
|
||||||
presenter.loadAllCategories()
|
viewModel.loadAllCategories()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onTabLongClick(tabView: View, category: FavouriteCategory): Boolean {
|
override fun onTabLongClick(tabView: View, category: FavouriteCategory): Boolean {
|
||||||
@@ -101,15 +102,15 @@ class FavouritesContainerFragment : BaseFragment(R.layout.fragment_favourites),
|
|||||||
}
|
}
|
||||||
|
|
||||||
override fun onDeleteCategory(category: FavouriteCategory) {
|
override fun onDeleteCategory(category: FavouriteCategory) {
|
||||||
presenter.deleteCategory(category.id)
|
viewModel.deleteCategory(category.id)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onRenameCategory(category: FavouriteCategory, newName: String) {
|
override fun onRenameCategory(category: FavouriteCategory, newName: String) {
|
||||||
presenter.renameCategory(category.id, newName)
|
viewModel.renameCategory(category.id, newName)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCreateCategory(name: String) {
|
override fun onCreateCategory(name: String) {
|
||||||
presenter.createCategory(name)
|
viewModel.createCategory(name)
|
||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
@@ -1,12 +1,13 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites
|
package org.koitharu.kotatsu.favourites.ui
|
||||||
|
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import androidx.fragment.app.Fragment
|
import androidx.fragment.app.Fragment
|
||||||
import androidx.viewpager2.adapter.FragmentStateAdapter
|
import androidx.viewpager2.adapter.FragmentStateAdapter
|
||||||
import com.google.android.material.tabs.TabLayout
|
import com.google.android.material.tabs.TabLayout
|
||||||
import com.google.android.material.tabs.TabLayoutMediator
|
import com.google.android.material.tabs.TabLayoutMediator
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.AdapterUpdater
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.ui.base.list.AdapterUpdater
|
import org.koitharu.kotatsu.favourites.ui.list.FavouritesListFragment
|
||||||
import org.koitharu.kotatsu.utils.ext.replaceWith
|
import org.koitharu.kotatsu.utils.ext.replaceWith
|
||||||
|
|
||||||
class FavouritesPagerAdapter(
|
class FavouritesPagerAdapter(
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites
|
package org.koitharu.kotatsu.favourites.ui
|
||||||
|
|
||||||
import android.view.View
|
import android.view.View
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories
|
package org.koitharu.kotatsu.favourites.ui.categories
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.content.Intent
|
import android.content.Intent
|
||||||
@@ -12,18 +12,18 @@ import androidx.recyclerview.widget.ItemTouchHelper
|
|||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import com.google.android.material.snackbar.Snackbar
|
import com.google.android.material.snackbar.Snackbar
|
||||||
import kotlinx.android.synthetic.main.activity_categories.*
|
import kotlinx.android.synthetic.main.activity_categories.*
|
||||||
import moxy.ktx.moxyPresenter
|
import org.koin.android.viewmodel.ext.android.viewModel
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.BaseActivity
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.OnRecyclerItemClickListener
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.ui.base.BaseActivity
|
|
||||||
import org.koitharu.kotatsu.ui.base.list.OnRecyclerItemClickListener
|
|
||||||
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
||||||
import org.koitharu.kotatsu.utils.ext.showPopupMenu
|
import org.koitharu.kotatsu.utils.ext.showPopupMenu
|
||||||
|
|
||||||
class CategoriesActivity : BaseActivity(), OnRecyclerItemClickListener<FavouriteCategory>,
|
class CategoriesActivity : BaseActivity(), OnRecyclerItemClickListener<FavouriteCategory>,
|
||||||
FavouriteCategoriesView, View.OnClickListener, CategoriesEditDelegate.CategoriesEditCallback {
|
View.OnClickListener, CategoriesEditDelegate.CategoriesEditCallback {
|
||||||
|
|
||||||
private val presenter by moxyPresenter(factory = ::FavouriteCategoriesPresenter)
|
private val viewModel by viewModel<FavouritesCategoriesViewModel>()
|
||||||
|
|
||||||
private lateinit var adapter: CategoriesAdapter
|
private lateinit var adapter: CategoriesAdapter
|
||||||
private lateinit var reorderHelper: ItemTouchHelper
|
private lateinit var reorderHelper: ItemTouchHelper
|
||||||
@@ -41,6 +41,9 @@ class CategoriesActivity : BaseActivity(), OnRecyclerItemClickListener<Favourite
|
|||||||
fab_add.setOnClickListener(this)
|
fab_add.setOnClickListener(this)
|
||||||
reorderHelper = ItemTouchHelper(ReorderHelperCallback())
|
reorderHelper = ItemTouchHelper(ReorderHelperCallback())
|
||||||
reorderHelper.attachToRecyclerView(recyclerView)
|
reorderHelper.attachToRecyclerView(recyclerView)
|
||||||
|
|
||||||
|
viewModel.categories.observe(this, ::onCategoriesChanged)
|
||||||
|
viewModel.onError.observe(this, ::onError)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onClick(v: View) {
|
override fun onClick(v: View) {
|
||||||
@@ -66,28 +69,26 @@ class CategoriesActivity : BaseActivity(), OnRecyclerItemClickListener<Favourite
|
|||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCategoriesChanged(categories: List<FavouriteCategory>) {
|
private fun onCategoriesChanged(categories: List<FavouriteCategory>) {
|
||||||
adapter.replaceData(categories)
|
adapter.replaceData(categories)
|
||||||
textView_holder.isVisible = categories.isEmpty()
|
textView_holder.isVisible = categories.isEmpty()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCheckedCategoriesChanged(checkedIds: Set<Int>) = Unit
|
private fun onError(e: Throwable) {
|
||||||
|
|
||||||
override fun onError(e: Throwable) {
|
|
||||||
Snackbar.make(recyclerView, e.getDisplayMessage(resources), Snackbar.LENGTH_LONG)
|
Snackbar.make(recyclerView, e.getDisplayMessage(resources), Snackbar.LENGTH_LONG)
|
||||||
.show()
|
.show()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onDeleteCategory(category: FavouriteCategory) {
|
override fun onDeleteCategory(category: FavouriteCategory) {
|
||||||
presenter.deleteCategory(category.id)
|
viewModel.deleteCategory(category.id)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onRenameCategory(category: FavouriteCategory, newName: String) {
|
override fun onRenameCategory(category: FavouriteCategory, newName: String) {
|
||||||
presenter.renameCategory(category.id, newName)
|
viewModel.renameCategory(category.id, newName)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCreateCategory(name: String) {
|
override fun onCreateCategory(name: String) {
|
||||||
presenter.createCategory(name)
|
viewModel.createCategory(name)
|
||||||
}
|
}
|
||||||
|
|
||||||
private inner class ReorderHelperCallback : ItemTouchHelper.SimpleCallback(
|
private inner class ReorderHelperCallback : ItemTouchHelper.SimpleCallback(
|
||||||
@@ -102,7 +103,7 @@ class CategoriesActivity : BaseActivity(), OnRecyclerItemClickListener<Favourite
|
|||||||
val oldPos = viewHolder.bindingAdapterPosition
|
val oldPos = viewHolder.bindingAdapterPosition
|
||||||
val newPos = target.bindingAdapterPosition
|
val newPos = target.bindingAdapterPosition
|
||||||
adapter.moveItem(oldPos, newPos)
|
adapter.moveItem(oldPos, newPos)
|
||||||
presenter.storeCategoriesOrder(adapter.items.map { it.id })
|
viewModel.storeCategoriesOrder(adapter.items.map { it.id })
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1,13 +1,13 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories
|
package org.koitharu.kotatsu.favourites.ui.categories
|
||||||
|
|
||||||
import android.annotation.SuppressLint
|
import android.annotation.SuppressLint
|
||||||
import android.view.MotionEvent
|
import android.view.MotionEvent
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import kotlinx.android.synthetic.main.item_category.*
|
import kotlinx.android.synthetic.main.item_category.*
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseRecyclerAdapter
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseViewHolder
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.OnRecyclerItemClickListener
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseRecyclerAdapter
|
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseViewHolder
|
|
||||||
import org.koitharu.kotatsu.ui.base.list.OnRecyclerItemClickListener
|
|
||||||
|
|
||||||
class CategoriesAdapter(private val onItemClickListener: OnRecyclerItemClickListener<FavouriteCategory>) :
|
class CategoriesAdapter(private val onItemClickListener: OnRecyclerItemClickListener<FavouriteCategory>) :
|
||||||
BaseRecyclerAdapter<FavouriteCategory, Unit>() {
|
BaseRecyclerAdapter<FavouriteCategory, Unit>() {
|
||||||
@@ -1,11 +1,11 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories
|
package org.koitharu.kotatsu.favourites.ui.categories
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.text.InputType
|
import android.text.InputType
|
||||||
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.dialog.TextInputDialog
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.ui.base.dialog.TextInputDialog
|
|
||||||
|
|
||||||
class CategoriesEditDelegate(
|
class CategoriesEditDelegate(
|
||||||
private val context: Context,
|
private val context: Context,
|
||||||
@@ -1,10 +1,10 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories
|
package org.koitharu.kotatsu.favourites.ui.categories
|
||||||
|
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import kotlinx.android.synthetic.main.item_category.*
|
import kotlinx.android.synthetic.main.item_category.*
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseViewHolder
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseViewHolder
|
|
||||||
|
|
||||||
class CategoryHolder(parent: ViewGroup) :
|
class CategoryHolder(parent: ViewGroup) :
|
||||||
BaseViewHolder<FavouriteCategory, Unit>(parent, R.layout.item_category) {
|
BaseViewHolder<FavouriteCategory, Unit>(parent, R.layout.item_category) {
|
||||||
@@ -0,0 +1,77 @@
|
|||||||
|
package org.koitharu.kotatsu.favourites.ui.categories
|
||||||
|
|
||||||
|
import androidx.lifecycle.MutableLiveData
|
||||||
|
import kotlinx.coroutines.Job
|
||||||
|
import org.koitharu.kotatsu.base.ui.BaseViewModel
|
||||||
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
|
import org.koitharu.kotatsu.favourites.domain.FavouritesRepository
|
||||||
|
import org.koitharu.kotatsu.utils.ext.mapToSet
|
||||||
|
|
||||||
|
class FavouritesCategoriesViewModel(
|
||||||
|
private val repository: FavouritesRepository
|
||||||
|
) : BaseViewModel() {
|
||||||
|
|
||||||
|
private var reorderJob: Job? = null
|
||||||
|
|
||||||
|
val categories = MutableLiveData<List<FavouriteCategory>>()
|
||||||
|
val mangaCategories = MutableLiveData<Set<Int>>()
|
||||||
|
|
||||||
|
init {
|
||||||
|
loadAllCategories()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun loadAllCategories() {
|
||||||
|
launchJob {
|
||||||
|
categories.value = repository.getAllCategories()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun loadMangaCategories(manga: Manga) {
|
||||||
|
launchJob {
|
||||||
|
val categories = repository.getCategories(manga.id)
|
||||||
|
mangaCategories.value = categories.mapToSet { it.id.toInt() }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun createCategory(name: String) {
|
||||||
|
launchJob {
|
||||||
|
repository.addCategory(name)
|
||||||
|
categories.value = repository.getAllCategories()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun renameCategory(id: Long, name: String) {
|
||||||
|
launchJob {
|
||||||
|
repository.renameCategory(id, name)
|
||||||
|
categories.value = repository.getAllCategories()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun deleteCategory(id: Long) {
|
||||||
|
launchJob {
|
||||||
|
repository.removeCategory(id)
|
||||||
|
categories.value = repository.getAllCategories()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun storeCategoriesOrder(orderedIds: List<Long>) {
|
||||||
|
val prevJob = reorderJob
|
||||||
|
reorderJob = launchJob {
|
||||||
|
prevJob?.join()
|
||||||
|
repository.reorderCategories(orderedIds)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun addToCategory(manga: Manga, categoryId: Long) {
|
||||||
|
launchJob {
|
||||||
|
repository.addToCategory(manga, categoryId)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun removeFromCategory(manga: Manga, categoryId: Long) {
|
||||||
|
launchJob {
|
||||||
|
repository.removeFromCategory(manga, categoryId)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,12 +1,12 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories.select
|
package org.koitharu.kotatsu.favourites.ui.categories.select
|
||||||
|
|
||||||
import android.util.SparseBooleanArray
|
import android.util.SparseBooleanArray
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import android.widget.Checkable
|
import android.widget.Checkable
|
||||||
import androidx.core.util.set
|
import androidx.core.util.set
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseRecyclerAdapter
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseViewHolder
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseRecyclerAdapter
|
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseViewHolder
|
|
||||||
|
|
||||||
class CategoriesSelectAdapter(private val listener: OnCategoryCheckListener) :
|
class CategoriesSelectAdapter(private val listener: OnCategoryCheckListener) :
|
||||||
BaseRecyclerAdapter<FavouriteCategory, Boolean>() {
|
BaseRecyclerAdapter<FavouriteCategory, Boolean>() {
|
||||||
@@ -1,10 +1,10 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories.select
|
package org.koitharu.kotatsu.favourites.ui.categories.select
|
||||||
|
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import kotlinx.android.synthetic.main.item_category_checkable.*
|
import kotlinx.android.synthetic.main.item_category_checkable.*
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.list.BaseViewHolder
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.ui.base.list.BaseViewHolder
|
|
||||||
|
|
||||||
class CategoryCheckableHolder(parent: ViewGroup) :
|
class CategoryCheckableHolder(parent: ViewGroup) :
|
||||||
BaseViewHolder<FavouriteCategory, Boolean>(parent, R.layout.item_category_checkable) {
|
BaseViewHolder<FavouriteCategory, Boolean>(parent, R.layout.item_category_checkable) {
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories.select
|
package org.koitharu.kotatsu.favourites.ui.categories.select
|
||||||
|
|
||||||
import android.os.Bundle
|
import android.os.Bundle
|
||||||
import android.text.InputType
|
import android.text.InputType
|
||||||
@@ -6,22 +6,20 @@ import android.view.View
|
|||||||
import android.widget.Toast
|
import android.widget.Toast
|
||||||
import androidx.fragment.app.FragmentManager
|
import androidx.fragment.app.FragmentManager
|
||||||
import kotlinx.android.synthetic.main.dialog_favorite_categories.*
|
import kotlinx.android.synthetic.main.dialog_favorite_categories.*
|
||||||
import moxy.ktx.moxyPresenter
|
import org.koin.android.viewmodel.ext.android.viewModel
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
|
import org.koitharu.kotatsu.base.ui.BaseBottomSheet
|
||||||
|
import org.koitharu.kotatsu.base.ui.dialog.TextInputDialog
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.ui.base.BaseBottomSheet
|
import org.koitharu.kotatsu.favourites.ui.categories.FavouritesCategoriesViewModel
|
||||||
import org.koitharu.kotatsu.ui.base.dialog.TextInputDialog
|
|
||||||
import org.koitharu.kotatsu.ui.list.favourites.categories.FavouriteCategoriesPresenter
|
|
||||||
import org.koitharu.kotatsu.ui.list.favourites.categories.FavouriteCategoriesView
|
|
||||||
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
import org.koitharu.kotatsu.utils.ext.getDisplayMessage
|
||||||
import org.koitharu.kotatsu.utils.ext.withArgs
|
import org.koitharu.kotatsu.utils.ext.withArgs
|
||||||
|
|
||||||
class FavouriteCategoriesDialog : BaseBottomSheet(R.layout.dialog_favorite_categories),
|
class FavouriteCategoriesDialog : BaseBottomSheet(R.layout.dialog_favorite_categories),
|
||||||
FavouriteCategoriesView,
|
|
||||||
OnCategoryCheckListener {
|
OnCategoryCheckListener {
|
||||||
|
|
||||||
private val presenter by moxyPresenter(factory = ::FavouriteCategoriesPresenter)
|
private val viewModel by viewModel<FavouritesCategoriesViewModel>()
|
||||||
|
|
||||||
private val manga get() = arguments?.getParcelable<Manga>(ARG_MANGA)
|
private val manga get() = arguments?.getParcelable<Manga>(ARG_MANGA)
|
||||||
|
|
||||||
@@ -38,8 +36,12 @@ class FavouriteCategoriesDialog : BaseBottomSheet(R.layout.dialog_favorite_categ
|
|||||||
createCategory()
|
createCategory()
|
||||||
}
|
}
|
||||||
manga?.let {
|
manga?.let {
|
||||||
presenter.loadMangaCategories(it)
|
viewModel.loadMangaCategories(it)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
viewModel.categories.observe(viewLifecycleOwner, ::onCategoriesChanged)
|
||||||
|
viewModel.mangaCategories.observe(viewLifecycleOwner, ::onCheckedCategoriesChanged)
|
||||||
|
viewModel.onError.observe(viewLifecycleOwner, ::onError)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onDestroyView() {
|
override fun onDestroyView() {
|
||||||
@@ -47,23 +49,23 @@ class FavouriteCategoriesDialog : BaseBottomSheet(R.layout.dialog_favorite_categ
|
|||||||
super.onDestroyView()
|
super.onDestroyView()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCategoriesChanged(categories: List<FavouriteCategory>) {
|
private fun onCategoriesChanged(categories: List<FavouriteCategory>) {
|
||||||
adapter?.replaceData(categories)
|
adapter?.replaceData(categories)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCheckedCategoriesChanged(checkedIds: Set<Int>) {
|
private fun onCheckedCategoriesChanged(checkedIds: Set<Int>) {
|
||||||
adapter?.setCheckedIds(checkedIds)
|
adapter?.setCheckedIds(checkedIds)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCategoryChecked(category: FavouriteCategory) {
|
override fun onCategoryChecked(category: FavouriteCategory) {
|
||||||
presenter.addToCategory(manga ?: return, category.id)
|
viewModel.addToCategory(manga ?: return, category.id)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onCategoryUnchecked(category: FavouriteCategory) {
|
override fun onCategoryUnchecked(category: FavouriteCategory) {
|
||||||
presenter.removeFromCategory(manga ?: return, category.id)
|
viewModel.removeFromCategory(manga ?: return, category.id)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onError(e: Throwable) {
|
private fun onError(e: Throwable) {
|
||||||
Toast.makeText(context ?: return, e.getDisplayMessage(resources), Toast.LENGTH_SHORT).show()
|
Toast.makeText(context ?: return, e.getDisplayMessage(resources), Toast.LENGTH_SHORT).show()
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -75,7 +77,7 @@ class FavouriteCategoriesDialog : BaseBottomSheet(R.layout.dialog_favorite_categ
|
|||||||
.setInputType(InputType.TYPE_TEXT_VARIATION_PERSON_NAME or InputType.TYPE_TEXT_FLAG_CAP_SENTENCES)
|
.setInputType(InputType.TYPE_TEXT_VARIATION_PERSON_NAME or InputType.TYPE_TEXT_FLAG_CAP_SENTENCES)
|
||||||
.setNegativeButton(android.R.string.cancel)
|
.setNegativeButton(android.R.string.cancel)
|
||||||
.setPositiveButton(R.string.add) { _, name ->
|
.setPositiveButton(R.string.add) { _, name ->
|
||||||
presenter.createCategory(name)
|
viewModel.createCategory(name)
|
||||||
}.create()
|
}.create()
|
||||||
.show()
|
.show()
|
||||||
}
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites.categories.select
|
package org.koitharu.kotatsu.favourites.ui.categories.select
|
||||||
|
|
||||||
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
import org.koitharu.kotatsu.core.model.FavouriteCategory
|
||||||
|
|
||||||
@@ -1,28 +1,27 @@
|
|||||||
package org.koitharu.kotatsu.ui.list.favourites
|
package org.koitharu.kotatsu.favourites.ui.list
|
||||||
|
|
||||||
import android.view.Menu
|
import android.view.Menu
|
||||||
import android.view.MenuInflater
|
import android.view.MenuInflater
|
||||||
import android.view.MenuItem
|
import android.view.MenuItem
|
||||||
import kotlinx.android.synthetic.main.fragment_list.*
|
import kotlinx.android.synthetic.main.fragment_list.*
|
||||||
import moxy.ktx.moxyPresenter
|
import org.koin.android.viewmodel.ext.android.viewModel
|
||||||
import org.koin.android.ext.android.get
|
import org.koin.core.parameter.parametersOf
|
||||||
import org.koitharu.kotatsu.R
|
import org.koitharu.kotatsu.R
|
||||||
import org.koitharu.kotatsu.core.model.Manga
|
import org.koitharu.kotatsu.core.model.Manga
|
||||||
import org.koitharu.kotatsu.ui.list.MangaListFragment
|
import org.koitharu.kotatsu.list.ui.MangaListFragment
|
||||||
import org.koitharu.kotatsu.ui.list.MangaListView
|
|
||||||
import org.koitharu.kotatsu.utils.ext.withArgs
|
import org.koitharu.kotatsu.utils.ext.withArgs
|
||||||
|
|
||||||
class FavouritesListFragment : MangaListFragment<Unit>(), MangaListView<Unit> {
|
class FavouritesListFragment : MangaListFragment() {
|
||||||
|
|
||||||
private val presenter by moxyPresenter {
|
override val viewModel by viewModel<FavouritesListViewModel> {
|
||||||
FavouritesListPresenter(categoryId, get())
|
parametersOf(categoryId)
|
||||||
}
|
}
|
||||||
|
|
||||||
private val categoryId: Long
|
private val categoryId: Long
|
||||||
get() = arguments?.getLong(ARG_CATEGORY_ID) ?: 0L
|
get() = arguments?.getLong(ARG_CATEGORY_ID) ?: 0L
|
||||||
|
|
||||||
override fun onRequestMoreItems(offset: Int) {
|
override fun onRequestMoreItems(offset: Int) {
|
||||||
presenter.loadList(offset)
|
viewModel.loadList(offset)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun setUpEmptyListHolder() {
|
override fun setUpEmptyListHolder() {
|
||||||
@@ -41,9 +40,9 @@ class FavouritesListFragment : MangaListFragment<Unit>(), MangaListView<Unit> {
|
|||||||
inflater.inflate(R.menu.popup_favourites, menu)
|
inflater.inflate(R.menu.popup_favourites, menu)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onPopupMenuItemSelected(item: MenuItem, data: Manga) = when(item.itemId) {
|
override fun onPopupMenuItemSelected(item: MenuItem, data: Manga) = when (item.itemId) {
|
||||||
R.id.action_remove -> {
|
R.id.action_remove -> {
|
||||||
presenter.removeFromFavourites(data)
|
viewModel.removeFromFavourites(data)
|
||||||
true
|
true
|
||||||
}
|
}
|
||||||
else -> super.onPopupMenuItemSelected(item, data)
|
else -> super.onPopupMenuItemSelected(item, data)
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user