Skip to content

Commit

Permalink
6.15.0 commit
Browse files Browse the repository at this point in the history
  • Loading branch information
XilinJia committed Nov 29, 2024
1 parent 8c13b7e commit 884abb5
Show file tree
Hide file tree
Showing 40 changed files with 1,082 additions and 1,763 deletions.
4 changes: 2 additions & 2 deletions app/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -26,8 +26,8 @@ android {
vectorDrawables.useSupportLibrary false
vectorDrawables.generatedDensities = []

versionCode 3020307
versionName "6.14.8"
versionCode 3020308
versionName "6.15.0"

applicationId "ac.mdiq.podcini.R"
def commit = ""
Expand Down
27 changes: 1 addition & 26 deletions app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -190,32 +190,6 @@
android:resource="@xml/player_widget_info"/>
</receiver>

<activity
android:name=".ui.activity.OpmlImportActivity"
android:configChanges="keyboardHidden|orientation|screenSize"
android:label="@string/opml_import_label"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.VIEW"/>
<action android:name="android.intent.action.SEND"/>

<category android:name="android.intent.category.DEFAULT"/>
<category android:name="android.intent.category.BROWSABLE"/>

<data android:mimeType="text/xml"/>
<data android:mimeType="text/x-opml"/>
<data android:mimeType="application/xml"/>

<data android:scheme="file"/>
<data android:scheme="content"/>
<data android:scheme="http"/>
<data android:scheme="https"/>

<!-- <data android:host="*"/>-->
<data android:pathPattern="/.*\\.xml" />
<data android:pathPattern="/.*\\.opml" />
</intent-filter>
</activity>
<activity
android:name=".ui.activity.BugReportActivity"
android:label="@string/bug_report_title">
Expand Down Expand Up @@ -257,6 +231,7 @@
<category android:name="android.intent.category.BROWSABLE"/>

<data android:scheme="http"/>
<data android:host="*"/>
<data android:scheme="https"/>
<data android:mimeType="text/xml"/>
<data android:mimeType="application/rss+xml"/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -233,16 +233,16 @@ class DownloadServiceInterfaceImpl : DownloadServiceInterface() {
{ ctx: Context -> MainActivityStarter(ctx).withDownloadLogsOpen().start() },
applicationContext.getString(R.string.download_error_details)))
}
private fun getDownloadLogsIntent(context: Context): PendingIntent {
val intent = MainActivityStarter(context).withDownloadLogsOpen().getIntent()
return PendingIntent.getActivity(context, R.id.pending_intent_download_service_report, intent,
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE)
}
private fun getDownloadsIntent(context: Context): PendingIntent {
val intent = MainActivityStarter(context).withFragmentLoaded("DownloadsFragment").getIntent()
return PendingIntent.getActivity(context, R.id.pending_intent_download_service_notification, intent,
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE)
}
// private fun getDownloadLogsIntent(context: Context): PendingIntent {
// val intent = MainActivityStarter(context).withDownloadLogsOpen().getIntent()
// return PendingIntent.getActivity(context, R.id.pending_intent_download_service_report, intent,
// PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE)
// }
// private fun getDownloadsIntent(context: Context): PendingIntent {
// val intent = MainActivityStarter(context).withFragmentLoaded("DownloadsFragment").getIntent()
// return PendingIntent.getActivity(context, R.id.pending_intent_download_service_notification, intent,
// PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE)
// }
private fun sendErrorNotification(title: String) {
// TODO: need to get number of subscribers in SharedFlow
// if (EventBus.getDefault().hasSubscriberForEvent(FlowEvent.MessageEvent::class.java)) {
Expand All @@ -254,7 +254,7 @@ class DownloadServiceInterfaceImpl : DownloadServiceInterface() {
.setContentTitle(applicationContext.getString(R.string.download_report_title))
.setContentText(applicationContext.getString(R.string.download_error_tap_for_details))
.setSmallIcon(R.drawable.ic_notification_sync_error)
.setContentIntent(getDownloadLogsIntent(applicationContext))
// .setContentIntent(getDownloadLogsIntent(applicationContext))
.setAutoCancel(true)
builder.setVisibility(NotificationCompat.VISIBILITY_PUBLIC)
val nm = applicationContext.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
Expand All @@ -277,7 +277,7 @@ class DownloadServiceInterfaceImpl : DownloadServiceInterface() {
.setContentTitle(applicationContext.getString(R.string.download_notification_title_episodes))
.setContentText(contentText)
.setStyle(NotificationCompat.BigTextStyle().bigText(bigText))
.setContentIntent(getDownloadsIntent(applicationContext))
// .setContentIntent(getDownloadsIntent(applicationContext))
.setAutoCancel(false)
.setOngoing(true)
.setWhen(0)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -245,7 +245,7 @@ class WifiSyncService(val context: Context, params: WorkerParameters) : SyncSer
// only push downloaded items
val pausedItems = getEpisodes(0, Int.MAX_VALUE, EpisodeFilter(EpisodeFilter.States.paused.name), EpisodeSortOrder.DATE_NEW_OLD)
val readItems = getEpisodes(0, Int.MAX_VALUE, EpisodeFilter(EpisodeFilter.States.played.name), EpisodeSortOrder.DATE_NEW_OLD)
val favoriteItems = getEpisodes(0, Int.MAX_VALUE, EpisodeFilter(EpisodeFilter.States.favorite.name), EpisodeSortOrder.DATE_NEW_OLD)
val favoriteItems = getEpisodes(0, Int.MAX_VALUE, EpisodeFilter(EpisodeFilter.States.superb.name), EpisodeSortOrder.DATE_NEW_OLD)
val comItems = mutableSetOf<Episode>()
comItems.addAll(pausedItems)
comItems.addAll(readItems)
Expand Down
79 changes: 40 additions & 39 deletions app/src/main/kotlin/ac/mdiq/podcini/preferences/OpmlTransporter.kt
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,10 @@ import android.util.Log
import android.util.Xml
import androidx.core.app.ActivityCompat
import com.google.android.material.dialog.MaterialAlertDialogBuilder
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import org.apache.commons.io.input.BOMInputStream
import org.xmlpull.v1.XmlPullParser
import org.xmlpull.v1.XmlPullParserException
Expand Down Expand Up @@ -164,54 +168,51 @@ class OpmlTransporter {
}

companion object {
fun startImport(context: Context, uri: Uri) {
fun startImport(context: Context, uri: Uri, CB: (List<OpmlElement>)->Unit) {
val TAG = "OpmlTransporter"
// CoroutineScope(Dispatchers.IO).launch {
try {
val opmlFileStream = context.contentResolver.openInputStream(uri)
val bomInputStream = BOMInputStream(opmlFileStream)
val bom = bomInputStream.bom
val charsetName = if (bom == null) "UTF-8" else bom.charsetName
val reader: Reader = InputStreamReader(bomInputStream, charsetName)
val opmlReader = OpmlReader()
val result = opmlReader.readDocument(reader)
reader.close()
// withContext(Dispatchers.Main) {
// binding.progressBar.visibility = View.GONE
Logd(TAG, "Parsing was successful")
// readElements = result
// }
} catch (e: Throwable) {
// withContext(Dispatchers.Main) {
Logd(TAG, Log.getStackTraceString(e))
val message = if (e.message == null) "" else e.message!!
if (message.lowercase().contains("permission")) {
val permission = ActivityCompat.checkSelfPermission(context, Manifest.permission.READ_EXTERNAL_STORAGE)
if (permission != PackageManager.PERMISSION_GRANTED) {
CoroutineScope(Dispatchers.IO).launch {
try {
val opmlFileStream = context.contentResolver.openInputStream(uri)
val bomInputStream = BOMInputStream(opmlFileStream)
val bom = bomInputStream.bom
val charsetName = if (bom == null) "UTF-8" else bom.charsetName
val reader: Reader = InputStreamReader(bomInputStream, charsetName)
val opmlReader = OpmlReader()
val result = opmlReader.readDocument(reader)
reader.close()
withContext(Dispatchers.Main) { CB(result) }
} catch (e: Throwable) {
withContext(Dispatchers.Main) {
Logd(TAG, Log.getStackTraceString(e))
val message = if (e.message == null) "" else e.message!!
if (message.lowercase().contains("permission")) {
val permission = ActivityCompat.checkSelfPermission(context, Manifest.permission.READ_EXTERNAL_STORAGE)
if (permission != PackageManager.PERMISSION_GRANTED) {
// requestPermission()
return
}
}
// binding.progressBar.visibility = View.GONE
val alert = MaterialAlertDialogBuilder(context)
alert.setTitle(R.string.error_label)
val userReadable = context.getString(R.string.opml_reader_error)
val details = e.message
val total = """
CB(listOf())
return@withContext
}
}
val alert = MaterialAlertDialogBuilder(context)
alert.setTitle(R.string.error_label)
val userReadable = context.getString(R.string.opml_reader_error)
val details = e.message
val total = """
$userReadable
$details
""".trimIndent()
val errorMessage = SpannableString(total)
errorMessage.setSpan(ForegroundColorSpan(-0x77777778), userReadable.length, total.length, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
alert.setMessage(errorMessage)
alert.setPositiveButton(android.R.string.ok) { _: DialogInterface?, _: Int ->
val errorMessage = SpannableString(total)
errorMessage.setSpan(ForegroundColorSpan(-0x77777778), userReadable.length, total.length, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
alert.setMessage(errorMessage)
alert.setPositiveButton(android.R.string.ok) { _: DialogInterface?, _: Int ->
// finish()
}
alert.show()
CB(listOf())
}
}
alert.show()
// }
}
// }
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,10 +50,12 @@ object UserPreferences {
val isThemeColorTinted: Boolean
get() = Build.VERSION.SDK_INT >= 31 && appPrefs.getBoolean(Prefs.prefTintedColors.name, false)

// not using this
var hiddenDrawerItems: List<String>
get() {
val hiddenItems = appPrefs.getString(Prefs.prefHiddenDrawerItems.name, "")
return hiddenItems?.split(",") ?: listOf()
return listOf()
// val hiddenItems = appPrefs.getString(Prefs.prefHiddenDrawerItems.name, "")
// return hiddenItems?.split(",") ?: listOf()
}
set(items) {
val str = items.joinToString()
Expand Down
31 changes: 29 additions & 2 deletions app/src/main/kotlin/ac/mdiq/podcini/storage/database/Feeds.kt
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import ac.mdiq.podcini.storage.database.RealmDB.upsert
import ac.mdiq.podcini.storage.database.RealmDB.upsertBlk
import ac.mdiq.podcini.storage.model.*
import ac.mdiq.podcini.storage.model.Feed.Companion.MAX_NATURAL_SYNTHETIC_ID
import ac.mdiq.podcini.storage.model.FeedPreferences.AudioType
import ac.mdiq.podcini.storage.model.FeedPreferences.AutoDeleteAction
import ac.mdiq.podcini.storage.model.FeedPreferences.Companion.TAG_ROOT
import ac.mdiq.podcini.storage.utils.FilesUtils.feedfilePath
Expand Down Expand Up @@ -481,6 +482,13 @@ object Feeds {
return !feed.isLocalFeed || isAutoDeleteLocal
}

fun createYTSyndicates() {
getYoutubeSyndicate(true, false)
getYoutubeSyndicate(false, false)
getYoutubeSyndicate(true, true)
getYoutubeSyndicate(false, true)
}

private fun getYoutubeSyndicate(video: Boolean, music: Boolean): Feed {
var feedId: Long = if (video) 1 else 2
if (music) feedId += 2 // music feed takes ids 3 and 4
Expand All @@ -492,6 +500,7 @@ object Feeds {
feed = createSynthetic(feedId, name)
feed.type = Feed.FeedType.YOUTUBE.name
feed.hasVideoMedia = video
feed.preferences!!.audioTypeSetting = if (music) AudioType.MOVIE else AudioType.SPEECH
feed.preferences!!.videoModePolicy = if (video) VideoMode.WINDOW_VIEW else VideoMode.AUDIO_ONLY
upsertBlk(feed) {}
EventFlow.postEvent(FlowEvent.FeedListEvent(FlowEvent.FeedListEvent.Action.ADDED))
Expand All @@ -509,8 +518,26 @@ object Feeds {
episode.feedId = feed.id
episode.media?.id = episode.id
upsertBlk(episode) {}
feed.episodes.add(episode)
upsertBlk(feed) {}
upsertBlk(feed) {
it.episodes.add(episode)
}
EventFlow.postStickyEvent(FlowEvent.FeedUpdatingEvent(false))
return 1
}

fun addToSyndicate(episode: Episode, feed: Feed) : Int {
Logd(TAG, "addToYoutubeSyndicate: feed: ${feed.title}")
if (searchEpisodeByIdentifyingValue(feed.episodes, episode) != null) return 2

Logd(TAG, "addToSyndicate adding new episode: ${episode.title}")
episode.feed = feed
episode.id = Feed.newId()
episode.feedId = feed.id
episode.media?.id = episode.id
upsertBlk(episode) {}
upsertBlk(feed) {
it.episodes.add(episode)
}
EventFlow.postStickyEvent(FlowEvent.FeedUpdatingEvent(false))
return 1
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ object Queues {
*/
var queueKeepSortedOrder: EpisodeSortOrder?
get() {
val sortOrderStr = appPrefs.getString(UserPreferences.Prefs.prefQueueKeepSortedOrder.name, "use-default")
val sortOrderStr = appPrefs.getString(UserPreferences.Prefs.prefQueueKeepSortedOrder.name, "use-default")!!
return EpisodeSortOrder.parseWithDefault(sortOrderStr, EpisodeSortOrder.DATE_NEW_OLD)
}
set(sortOrder) {
Expand All @@ -61,8 +61,8 @@ object Queues {

var enqueueLocation: EnqueueLocation
get() {
val valStr = appPrefs.getString(UserPreferences.Prefs.prefEnqueueLocation.name, EnqueueLocation.BACK.name)
try { return EnqueueLocation.valueOf(valStr!!)
val valStr = appPrefs.getString(UserPreferences.Prefs.prefEnqueueLocation.name, EnqueueLocation.BACK.name)!!
try { return EnqueueLocation.valueOf(valStr)
} catch (t: Throwable) {
// should never happen but just in case
Log.e(TAG, "getEnqueueLocation: invalid value '$valStr' Use default.", t)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ object RealmDB {
SubscriptionLog::class,
Chapter::class))
.name("Podcini.realm")
.schemaVersion(35)
.schemaVersion(36)
.migration({ mContext ->
val oldRealm = mContext.oldRealm // old realm using the previous schema
val newRealm = mContext.newRealm // new realm using the new schema
Expand Down
5 changes: 5 additions & 0 deletions app/src/main/kotlin/ac/mdiq/podcini/storage/model/Episode.kt
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,11 @@ class Episode : RealmObject {

var feedId: Long? = null

// parent in these refers to the original parent of the content (shared)
var parentTitle: String? = null

var parentURL: String? = null

var podcastIndexChapterUrl: String? = null

var playState: Int
Expand Down
18 changes: 11 additions & 7 deletions app/src/main/kotlin/ac/mdiq/podcini/storage/model/EpisodeFilter.kt
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,17 @@ import java.io.Serializable
class EpisodeFilter(vararg properties_: String) : Serializable {
val properties: HashSet<String> = setOf(*properties_).filter { it.isNotEmpty() }.map {it.trim()}.toHashSet()

val showQueued: Boolean = properties.contains(States.queued.name)
val showNotQueued: Boolean = properties.contains(States.not_queued.name)
// val showQueued: Boolean = properties.contains(States.queued.name)
// val showNotQueued: Boolean = properties.contains(States.not_queued.name)
val showDownloaded: Boolean = properties.contains(States.downloaded.name)
val showNotDownloaded: Boolean = properties.contains(States.not_downloaded.name)

constructor(properties: String) : this(*(properties.split(",").toTypedArray()))

fun add(vararg properties_: String) {
properties.addAll(setOf(*properties_).filter { it.isNotEmpty() }.map {it.trim()})
}

fun queryString(): String {
val statements: MutableList<String> = mutableListOf()
val mediaTypeQuerys = mutableListOf<String>()
Expand All @@ -37,7 +41,7 @@ class EpisodeFilter(vararg properties_: String) : Serializable {
if (properties.contains(States.bad.name)) ratingQuerys.add(" rating == ${Rating.BAD.code} ")
if (properties.contains(States.neutral.name)) ratingQuerys.add(" rating == ${Rating.OK.code} ")
if (properties.contains(States.good.name)) ratingQuerys.add(" rating == ${Rating.GOOD.code} ")
if (properties.contains(States.favorite.name)) ratingQuerys.add(" rating == ${Rating.SUPER.code} ")
if (properties.contains(States.superb.name)) ratingQuerys.add(" rating == ${Rating.SUPER.code} ")
if (ratingQuerys.isNotEmpty()) {
val query = StringBuilder(" (" + ratingQuerys[0])
if (ratingQuerys.size > 1) for (r in ratingQuerys.subList(1, ratingQuerys.size)) {
Expand Down Expand Up @@ -135,8 +139,8 @@ class EpisodeFilter(vararg properties_: String) : Serializable {
no_media,
has_comments,
no_comments,
queued,
not_queued,
// queued,
// not_queued,
downloaded,
not_downloaded,
auto_downloadable,
Expand All @@ -146,7 +150,7 @@ class EpisodeFilter(vararg properties_: String) : Serializable {
bad,
neutral,
good,
favorite,
superb,
}

enum class EpisodesFilterGroup(val nameRes: Int, vararg values_: ItemProperties) {
Expand All @@ -155,7 +159,7 @@ class EpisodeFilter(vararg properties_: String) : Serializable {
ItemProperties(R.string.bad, States.bad.name),
ItemProperties(R.string.OK, States.neutral.name),
ItemProperties(R.string.good, States.good.name),
ItemProperties(R.string.Super, States.favorite.name),
ItemProperties(R.string.Super, States.superb.name),
),
PLAY_STATE(R.string.playstate, ItemProperties(R.string.unspecified, States.unspecified.name),
ItemProperties(R.string.building, States.building.name),
Expand Down
Loading

0 comments on commit 884abb5

Please sign in to comment.