more features
This commit is contained in:
parent
e1c99e2647
commit
0df5a9e194
13 changed files with 127 additions and 82 deletions
|
|
@ -3,8 +3,9 @@ plugins {
|
|||
id 'com.google.android.libraries.mapsplatform.secrets-gradle-plugin' version '2.0.1'
|
||||
id 'org.jetbrains.kotlin.android'
|
||||
id 'com.google.devtools.ksp'
|
||||
id "org.jetbrains.kotlin.plugin.serialization" version "1.8.10"
|
||||
id "org.jetbrains.kotlin.plugin.parcelize" version "1.8.10"
|
||||
id "org.jetbrains.kotlin.plugin.serialization" version "2.0.21"
|
||||
id "org.jetbrains.kotlin.plugin.parcelize" version "2.0.21"
|
||||
id "org.jetbrains.kotlin.plugin.compose" version "2.0.21"
|
||||
}
|
||||
|
||||
def properties = new Properties()
|
||||
|
|
@ -101,6 +102,7 @@ android {
|
|||
|
||||
buildFeatures {
|
||||
viewBinding true
|
||||
buildConfig true
|
||||
compose true
|
||||
}
|
||||
|
||||
|
|
@ -195,7 +197,7 @@ dependencies {
|
|||
implementation 'org.jetbrains.kotlinx:kotlinx-serialization-json:1.5.0'
|
||||
implementation 'it.xabaras.android:recyclerview-swipedecorator:1.4'
|
||||
implementation "androidx.lifecycle:lifecycle-livedata-ktx:2.8.6"
|
||||
implementation "com.github.Irineu333:Highlight-KT:1.0.4"
|
||||
implementation "com.neoutils.highlight:highlight-view:2.2.0"
|
||||
|
||||
// For media playback using ExoPlayer
|
||||
implementation("androidx.media3:media3-exoplayer:$media3_version")
|
||||
|
|
|
|||
|
|
@ -228,6 +228,9 @@ interface DownloadDao {
|
|||
@Query("UPDATE downloads set status=:status where id=:id")
|
||||
suspend fun setStatus(id: Long, status: String)
|
||||
|
||||
@Query("UPDATE downloads set status=:status where id IN (:ids)")
|
||||
suspend fun setStatusMultiple(ids: List<Long>, status: String)
|
||||
|
||||
@Update
|
||||
suspend fun updateWithoutUpsert(item: DownloadItem)
|
||||
|
||||
|
|
|
|||
|
|
@ -123,6 +123,10 @@ class DownloadRepository(private val downloadDao: DownloadDao) {
|
|||
downloadDao.setStatus(id, status.toString())
|
||||
}
|
||||
|
||||
suspend fun setDownloadStatusMultiple(ids: List<Long>, status: Status) {
|
||||
downloadDao.setStatusMultiple(ids, status.toString())
|
||||
}
|
||||
|
||||
fun getItemByID(id: Long) : DownloadItem {
|
||||
return downloadDao.getDownloadById(id)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1268,9 +1268,7 @@ class DownloadViewModel(private val application: Application) : AndroidViewModel
|
|||
}
|
||||
delay(1000)
|
||||
isPausingResuming = false
|
||||
activeDownloadsList.forEach {
|
||||
repository.setDownloadStatus(it.id, DownloadRepository.Status.Paused)
|
||||
}
|
||||
repository.setDownloadStatusMultiple(activeDownloadsList.map { it.id }, DownloadRepository.Status.Paused)
|
||||
pausedAllDownloads.value = PausedAllDownloadsState.RESUME
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -71,6 +71,10 @@ class TemplatesAdapter(onItemClickListener: OnItemClickListener, activity: Activ
|
|||
text = finalText
|
||||
}
|
||||
|
||||
card.findViewById<TextView>(R.id.dataFetchingExtraCommands).apply {
|
||||
isVisible = item.useAsExtraCommandDataFetching
|
||||
}
|
||||
|
||||
card.findViewById<TextView>(R.id.preferredTemplate).apply {
|
||||
val preferred = sharedPreferences.getString("preferred_command_template", "")
|
||||
isVisible = preferred == item.content
|
||||
|
|
@ -165,7 +169,8 @@ class TemplatesAdapter(onItemClickListener: OnItemClickListener, activity: Activ
|
|||
oldItem.content == newItem.content &&
|
||||
oldItem.useAsExtraCommand == newItem.useAsExtraCommand &&
|
||||
oldItem.useAsExtraCommandAudio == newItem.useAsExtraCommandAudio &&
|
||||
oldItem.useAsExtraCommandVideo == newItem.useAsExtraCommandVideo
|
||||
oldItem.useAsExtraCommandVideo == newItem.useAsExtraCommandVideo &&
|
||||
oldItem.useAsExtraCommandDataFetching == newItem.useAsExtraCommandDataFetching
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -46,11 +46,12 @@ import com.deniscerri.ytdl.database.repository.ObserveSourcesRepository.EveryCat
|
|||
import com.google.android.material.bottomsheet.BottomSheetBehavior
|
||||
import com.google.android.material.bottomsheet.BottomSheetDialog
|
||||
import com.google.android.material.tabs.TabLayout
|
||||
import com.google.gson.Gson
|
||||
import com.google.gson.JsonArray
|
||||
import com.neo.highlight.core.Highlight
|
||||
import com.neo.highlight.util.listener.HighlightTextWatcher
|
||||
import com.neo.highlight.util.scheme.ColorScheme
|
||||
import com.neoutils.highlight.core.Highlight
|
||||
import com.neoutils.highlight.core.scheme.TextColorScheme
|
||||
import com.neoutils.highlight.core.util.Match
|
||||
import com.neoutils.highlight.core.util.UiColor
|
||||
import com.neoutils.highlight.view.extension.toSpannedString
|
||||
import com.neoutils.highlight.view.text.HighlightTextWatcher
|
||||
import com.squareup.picasso.Picasso
|
||||
import kotlinx.coroutines.flow.Flow
|
||||
import kotlinx.coroutines.flow.combine
|
||||
|
|
@ -72,28 +73,27 @@ object Extensions {
|
|||
return (metrics.density * px).toInt()
|
||||
}
|
||||
|
||||
private var textHighLightSchemes = listOf(
|
||||
ColorScheme(Pattern.compile("([\"'])(?:\\\\1|.)*?\\1"), Color.parseColor("#FC8500")),
|
||||
ColorScheme(Pattern.compile("yt-dlp"), Color.parseColor("#77eb09")),
|
||||
ColorScheme(Pattern.compile("(https?://(?:www\\.|(?!www))[a-zA-Z0-9][a-zA-Z0-9-]+[a-zA-Z0-9]\\.[^\\s]{2,}|www\\.[a-zA-Z0-9][a-zA-Z0-9-]+[a-zA-Z0-9]\\.[^\\s]{2,}|https?://(?:www\\.|(?!www))[a-zA-Z0-9]+\\.[^\\s]{2,}|www\\.[a-zA-Z0-9]+\\.[^\\s]{2,})"), Color.parseColor("#b5942f")),
|
||||
ColorScheme(Pattern.compile("\\d+(\\.\\d)?%"), Color.parseColor("#43a564"))
|
||||
private var textHighlightSchemes = listOf(
|
||||
TextColorScheme(regex = "([\"'])(?:\\\\1|.)*?\\1".toRegex(), match = Match.fully(UiColor.Hex("#FC8500"))),
|
||||
TextColorScheme(regex = "yt-dlp".toRegex(), match = Match.fully(UiColor.Hex("#77eb09"))),
|
||||
TextColorScheme(regex = "(https?://(?:www\\.|(?!www))[a-zA-Z0-9][a-zA-Z0-9-]+[a-zA-Z0-9]\\.[^\\s]{2,}|www\\.[a-zA-Z0-9][a-zA-Z0-9-]+[a-zA-Z0-9]\\.[^\\s]{2,}|https?://(?:www\\.|(?!www))[a-zA-Z0-9]+\\.[^\\s]{2,}|www\\.[a-zA-Z0-9]+\\.[^\\s]{2,})".toRegex(), match = Match.fully(UiColor.Hex("#b5942f"))),
|
||||
TextColorScheme(regex = "\\d+(\\.\\d)?%".toRegex(), match = Match.fully(UiColor.Hex("#43a564"))),
|
||||
)
|
||||
|
||||
|
||||
fun View.enableTextHighlight(){
|
||||
if (this is EditText || this is TextView){
|
||||
//init syntax highlighter
|
||||
val highlight = Highlight()
|
||||
val highlightWatcher = HighlightTextWatcher()
|
||||
val highlight = Highlight(textHighlightSchemes)
|
||||
val highlightWatcher = HighlightTextWatcher(highlight)
|
||||
|
||||
highlight.addScheme(
|
||||
*textHighLightSchemes.map { it }.toTypedArray()
|
||||
)
|
||||
highlightWatcher.addScheme(
|
||||
*textHighLightSchemes.map { it }.toTypedArray()
|
||||
)
|
||||
|
||||
highlight.setSpan(this as TextView)
|
||||
this.addTextChangedListener(highlightWatcher)
|
||||
if (this is EditText) {
|
||||
this.addTextChangedListener(highlightWatcher)
|
||||
this.setText(highlight.toSpannedString(this.text.toString()))
|
||||
}else if (this is TextView) {
|
||||
this.addTextChangedListener(highlightWatcher)
|
||||
this.text = highlight.toSpannedString(this.text.toString())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -108,7 +108,7 @@ object FileUtil {
|
|||
if (it.isDirectory && it.absolutePath == originDir.absolutePath) return@forEach
|
||||
var destFile: DocumentFile
|
||||
try {
|
||||
if (it.name.matches("(^config.*.\\.txt\$)|(rList)|(.*.part-Frag.*)|(.*.live_chat)|(.*.ytdl)".toRegex())){
|
||||
if (it.name.matches("(^config.*.\\.txt\$)|(rList)|(.*.part-Frag.*)|(.*.live_chat)|(.*.ytdl)|(.*.info.json)".toRegex())){
|
||||
return@forEach
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -725,6 +725,18 @@ class YTDLPUtil(private val context: Context) {
|
|||
request.addOption("--download-archive", FileUtil.getDownloadArchivePath(context))
|
||||
}
|
||||
|
||||
if (!sharedPreferences.getBoolean("disable_write_info_json", false)) {
|
||||
val infoJsonFile = downDir.walkTopDown().firstOrNull { it.name == "${downloadItem.id}.info.json" }
|
||||
//ignore info file if its older than 5 hours. puny measure to prevent expired formats in some cases
|
||||
if (infoJsonFile == null || System.currentTimeMillis() - infoJsonFile.lastModified() > (1000 * 60 * 60 * 5)) {
|
||||
request.addOption("--write-info-json")
|
||||
request.addOption("--no-clean-info-json")
|
||||
request.addOption("-o", "infojson:${downloadItem.id}")
|
||||
}else {
|
||||
request.addOption("--load-info-json", infoJsonFile.absolutePath)
|
||||
}
|
||||
}
|
||||
|
||||
val preferredAudioCodec = sharedPreferences.getString("audio_codec", "")!!
|
||||
val aCodecPrefIndex = context.getStringArray(R.array.audio_codec_values).indexOf(preferredAudioCodec)
|
||||
val aCodecPref = runCatching { context.getStringArray(R.array.audio_codec_values_ytdlp)[aCodecPrefIndex] }.getOrElse { "" }
|
||||
|
|
|
|||
|
|
@ -41,64 +41,75 @@
|
|||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@+id/title" />
|
||||
|
||||
<HorizontalScrollView
|
||||
android:layout_width="wrap_content"
|
||||
android:scrollbars="none"
|
||||
<com.google.android.material.chip.ChipGroup
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/content"
|
||||
app:layout_constraintHorizontal_bias="0.0"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content">
|
||||
|
||||
<LinearLayout
|
||||
<TextView
|
||||
android:id="@+id/preferredTemplate"
|
||||
style="@style/Widget.Material3.FloatingActionButton.Large.Primary"
|
||||
android:visibility="gone"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="match_parent">
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@drawable/rounded_corner"
|
||||
android:backgroundTint="?attr/colorPrimaryContainer"
|
||||
android:clickable="false"
|
||||
android:gravity="center"
|
||||
android:minWidth="30dp"
|
||||
android:paddingHorizontal="5dp"
|
||||
android:textSize="12sp"
|
||||
android:textStyle="bold"
|
||||
app:cornerRadius="10dp"
|
||||
android:text="@string/preferred_command_template"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent"/>
|
||||
|
||||
<TextView
|
||||
android:id="@+id/preferredTemplate"
|
||||
style="@style/Widget.Material3.FloatingActionButton.Large.Primary"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="5dp"
|
||||
android:background="@drawable/rounded_corner"
|
||||
android:backgroundTint="?attr/colorPrimaryContainer"
|
||||
android:clickable="false"
|
||||
android:gravity="center"
|
||||
android:visibility="gone"
|
||||
android:minWidth="30dp"
|
||||
android:paddingHorizontal="5dp"
|
||||
android:textSize="12sp"
|
||||
android:textStyle="bold"
|
||||
app:cornerRadius="10dp"
|
||||
android:text="@string/preferred_command_template"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent"/>
|
||||
<TextView
|
||||
android:id="@+id/useInExtraCommands"
|
||||
style="@style/Widget.Material3.FloatingActionButton.Large.Secondary"
|
||||
android:visibility="gone"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="@string/extra_command"
|
||||
android:background="@drawable/rounded_corner"
|
||||
android:backgroundTint="?attr/colorSecondaryContainer"
|
||||
android:clickable="false"
|
||||
android:gravity="center"
|
||||
android:minWidth="30dp"
|
||||
android:paddingHorizontal="5dp"
|
||||
android:textSize="12sp"
|
||||
android:textStyle="bold"
|
||||
app:cornerRadius="10dp"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/useInExtraCommands"
|
||||
style="@style/Widget.Material3.FloatingActionButton.Large.Secondary"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:visibility="gone"
|
||||
android:layout_marginEnd="5dp"
|
||||
android:text="@string/extra_command"
|
||||
android:background="@drawable/rounded_corner"
|
||||
android:backgroundTint="?attr/colorSecondaryContainer"
|
||||
android:clickable="false"
|
||||
android:gravity="center"
|
||||
android:minWidth="30dp"
|
||||
android:paddingHorizontal="5dp"
|
||||
android:textSize="12sp"
|
||||
android:textStyle="bold"
|
||||
app:cornerRadius="10dp"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
<TextView
|
||||
android:id="@+id/dataFetchingExtraCommands"
|
||||
style="@style/Widget.Material3.FloatingActionButton.Large.Tertiary"
|
||||
android:visibility="gone"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="@string/data_fetching_extra_command"
|
||||
android:background="@drawable/rounded_corner"
|
||||
android:backgroundTint="?attr/colorTertiaryContainer"
|
||||
android:clickable="false"
|
||||
android:gravity="center"
|
||||
android:minWidth="30dp"
|
||||
android:paddingHorizontal="5dp"
|
||||
android:textSize="12sp"
|
||||
android:textStyle="bold"
|
||||
app:cornerRadius="10dp"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
</HorizontalScrollView>
|
||||
</com.google.android.material.chip.ChipGroup>
|
||||
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -437,4 +437,6 @@
|
|||
<string name="data_fetching_extra_command">Data Fetching Extra Command</string>
|
||||
<string name="thumbnail">Thumbnail</string>
|
||||
<string name="data_fetching_extra_command_summary">Enable command templates to be used for data fetching as extra commands</string>
|
||||
<string name="disable_write_info_json">Disable Write Info Json</string>
|
||||
<string name="disable_write_info_json_summary">(Not Recommended) Every time you restart / resume the download, yt-dlp will re-download json data from the servers.</string>
|
||||
</resources>
|
||||
|
|
@ -33,4 +33,12 @@
|
|||
android:title="@string/data_fetching_extra_command" />
|
||||
</PreferenceCategory>
|
||||
|
||||
<PreferenceCategory android:title="@string/downloading">
|
||||
<SwitchPreferenceCompat
|
||||
android:icon="@drawable/if_file_rename"
|
||||
android:key="disable_write_info_json"
|
||||
android:summary="@string/disable_write_info_json_summary"
|
||||
android:title="@string/disable_write_info_json" />
|
||||
</PreferenceCategory>
|
||||
|
||||
</PreferenceScreen>
|
||||
|
|
@ -41,11 +41,11 @@ buildscript {
|
|||
plugins {
|
||||
id 'com.android.application' version '8.5.2' apply false
|
||||
id 'com.android.library' version '8.5.2' apply false
|
||||
id 'org.jetbrains.kotlin.android' version '1.8.10' apply false
|
||||
id "org.jetbrains.kotlin.plugin.serialization" version "1.8.10" apply false
|
||||
id "org.jetbrains.kotlin.plugin.parcelize" version "1.8.10" apply false
|
||||
id 'org.jetbrains.kotlin.android' version '2.0.21' apply false
|
||||
id "org.jetbrains.kotlin.plugin.serialization" version "2.0.21" apply false
|
||||
id "org.jetbrains.kotlin.plugin.parcelize" version "2.0.21" apply false
|
||||
id 'com.android.test' version '8.5.2' apply false
|
||||
id 'com.google.devtools.ksp' version '1.8.10-1.0.9' apply false
|
||||
id 'com.google.devtools.ksp' version '2.0.21-1.0.28' apply false
|
||||
}
|
||||
|
||||
tasks.register('clean', Delete) {
|
||||
|
|
|
|||
|
|
@ -11,9 +11,9 @@
|
|||
# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
|
||||
# org.gradle.parallel=true
|
||||
#Sun Oct 08 20:53:48 CEST 2023
|
||||
android.defaults.buildfeatures.buildconfig=true
|
||||
android.enableJetifier=true
|
||||
android.nonFinalResIds=false
|
||||
android.nonTransitiveRClass=false
|
||||
android.suppressUnsupportedCompileSdk=35
|
||||
android.useAndroidX=true
|
||||
org.gradle.jvmargs=-Xmx1536M -Dkotlin.daemon.jvm.options\="-Xmx1024M" -Dfile.encoding\=UTF-8
|
||||
|
|
|
|||
Loading…
Reference in a new issue