(...);
-}
--keep public enum com.bumptech.glide.load.ImageHeaderParser$** {
- **[] $VALUES;
- public *;
-}
--keep class com.bumptech.glide.load.data.ParcelFileDescriptorRewinder$InternalRewinder {
- *** rewind();
+-keep public enum com.bumptech.glide.load.resource.bitmap.ImageHeaderParser$** {
+ **[] $VALUES;
+ public *;
}
-# OkHttp
--keepattributes Signature
--keepattributes *Annotation*
--keep interface com.squareup.okhttp3.** { *; }
--dontwarn com.squareup.okhttp3.**
+-keep class !android.support.v7.internal.view.menu.**,** {*;}
-#-dontwarn
-#-ignorewarnings
+-dontwarn
+-ignorewarnings
-#Jaudiotagger
--dontwarn org.jaudiotagger.**
--dontwarn org.jcodec.**
--keep class org.jaudiotagger.** { *; }
--keep class org.jcodec.** { *; }
+-keep public class android.support.design.widget.BottomNavigationView { *; }
+-keep public class android.support.design.internal.BottomNavigationMenuView { *; }
+-keep public class android.support.design.internal.BottomNavigationPresenter { *; }
+-keep public class android.support.design.internal.BottomNavigationItemView { *; }
--keepclassmembers enum * { *; }
--keepattributes *Annotation*, Signature, Exception
--keepnames class androidx.navigation.fragment.NavHostFragment
--keep class * extends androidx.fragment.app.Fragment{}
--keepnames class * extends android.os.Parcelable
--keepnames class * extends java.io.Serializable
--keep class code.name.monkey.retromusic.network.model.** { *; }
--keep class code.name.monkey.retromusic.model.** { *; }
--keep class com.google.android.material.bottomsheet.** { *; }
\ No newline at end of file
+#-dontwarn android.support.v8.renderscript.*
+#-keepclassmembers class android.support.v8.renderscript.RenderScript {
+# native *** rsn*(...);
+# native *** n*(...);
+#}
+
+#-keep class org.jaudiotagger.** { *; }
+
+
+-obfuscationdictionary build/obfuscation-dictionary.txt
+-classobfuscationdictionary build/class-dictionary.txt
+-packageobfuscationdictionary build/package-dictionary.txt
diff --git a/app/release/output-metadata.json b/app/release/output-metadata.json
new file mode 100644
index 000000000..08c9ac789
--- /dev/null
+++ b/app/release/output-metadata.json
@@ -0,0 +1,20 @@
+{
+ "version": 1,
+ "artifactType": {
+ "type": "APK",
+ "kind": "Directory"
+ },
+ "applicationId": "io.github.muntashirakon.Music",
+ "variantName": "release",
+ "elements": [
+ {
+ "type": "SINGLE",
+ "filters": [],
+ "properties": [],
+ "versionCode": 10443,
+ "versionName": "3.5.10",
+ "enabled": true,
+ "outputFile": "app-release.apk"
+ }
+ ]
+}
\ No newline at end of file
diff --git a/app/release/output.json b/app/release/output.json
new file mode 100644
index 000000000..758f3ea4a
--- /dev/null
+++ b/app/release/output.json
@@ -0,0 +1,20 @@
+{
+ "version": 1,
+ "artifactType": {
+ "type": "APK",
+ "kind": "Directory"
+ },
+ "applicationId": "code.name.monkey.retromusic",
+ "variantName": "release",
+ "elements": [
+ {
+ "type": "SINGLE",
+ "filters": [],
+ "properties": [],
+ "versionCode": 10438,
+ "versionName": "10438",
+ "enabled": true,
+ "outputFile": "app-release.apk"
+ }
+ ]
+}
\ No newline at end of file
diff --git a/app/src/debug/res/font/bold.ttf b/app/src/debug/res/font/bold.ttf
deleted file mode 100644
index 96619df92..000000000
Binary files a/app/src/debug/res/font/bold.ttf and /dev/null differ
diff --git a/app/src/debug/res/font/google_sans_bold.ttf b/app/src/debug/res/font/google_sans_bold.ttf
deleted file mode 100644
index 80497666e..000000000
Binary files a/app/src/debug/res/font/google_sans_bold.ttf and /dev/null differ
diff --git a/app/src/debug/res/font/google_sans_medium.ttf b/app/src/debug/res/font/google_sans_medium.ttf
deleted file mode 100644
index 1543660da..000000000
Binary files a/app/src/debug/res/font/google_sans_medium.ttf and /dev/null differ
diff --git a/app/src/debug/res/font/google_sans_regular.ttf b/app/src/debug/res/font/google_sans_regular.ttf
deleted file mode 100644
index ab605f9e2..000000000
Binary files a/app/src/debug/res/font/google_sans_regular.ttf and /dev/null differ
diff --git a/app/src/debug/res/font/medium.ttf b/app/src/debug/res/font/medium.ttf
deleted file mode 100644
index fd818d6f5..000000000
Binary files a/app/src/debug/res/font/medium.ttf and /dev/null differ
diff --git a/app/src/debug/res/font/regular.ttf b/app/src/debug/res/font/regular.ttf
deleted file mode 100644
index e2c69c3fb..000000000
Binary files a/app/src/debug/res/font/regular.ttf and /dev/null differ
diff --git a/app/src/debug/res/font/sans.xml b/app/src/debug/res/font/sans.xml
deleted file mode 100644
index 7bbc8513b..000000000
--- a/app/src/debug/res/font/sans.xml
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
-
-
-
-
\ No newline at end of file
diff --git a/app/src/debug/res/values/bools.xml b/app/src/debug/res/values/bools.xml
deleted file mode 100644
index 7d3f0ee62..000000000
--- a/app/src/debug/res/values/bools.xml
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
- true
- false
-
\ No newline at end of file
diff --git a/app/src/debug/res/values/donottranslate.xml b/app/src/debug/res/values/donottranslate.xml
deleted file mode 100644
index 79e559838..000000000
--- a/app/src/debug/res/values/donottranslate.xml
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
- Metro Debug
-
\ No newline at end of file
diff --git a/app/src/debug/res/values/styles.xml b/app/src/debug/res/values/styles.xml
deleted file mode 100644
index f3761b219..000000000
--- a/app/src/debug/res/values/styles.xml
+++ /dev/null
@@ -1,105 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 14fbaaab7..30cf2312c 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -1,57 +1,39 @@
-
-
-
-
+
-
-
-
-
+
+
+
+
-
-
+ android:usesCleartextTraffic="false"
+ tools:ignore="AllowBackup,GoogleAppIndexingWarning"
+ tools:targetApi="m">
+ android:label="@string/app_name"
+ android:theme="@style/SplashTheme">
@@ -62,6 +44,7 @@
+
@@ -121,54 +104,30 @@
+
+
+
+
+
+
+
+
+
+
-
+
+
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
+
+
+
-
+
-
+
@@ -216,7 +174,7 @@
@@ -229,7 +187,7 @@
@@ -241,7 +199,7 @@
@@ -253,7 +211,7 @@
@@ -265,7 +223,7 @@
@@ -275,36 +233,13 @@
android:name="android.appwidget.provider"
android:resource="@xml/app_widget_card_info" />
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+ android:label="@string/app_name"
+ tools:ignore="ExportedService">
@@ -318,33 +253,15 @@
android:name="com.lge.support.SPLIT_WINDOW"
android:value="true" />
-
-
-
+ android:name="io.github.muntashirakon.music.glide.RetroMusicGlideModule"
+ android:value="GlideModule" />
-
-
-
-
+
+
-
-
-
-
-
diff --git a/app/src/main/assets/contributors.json b/app/src/main/assets/contributors.json
new file mode 100644
index 000000000..2efd24509
--- /dev/null
+++ b/app/src/main/assets/contributors.json
@@ -0,0 +1,26 @@
+[
+ {
+ "name": "Hemanth Savarala",
+ "summary": "Lead Developer & Designer",
+ "link": "https://github.com/h4h13",
+ "profile_image": "https://i.imgur.com/AoVs9oj.jpg"
+ },
+ {
+ "name": "Lennart Glamann",
+ "summary": "Play Store banner and Images",
+ "link": "https://t.me/FlixbusLennart",
+ "profile_image": "https://i.imgur.com/Q5Nsx1R.jpg"
+ },
+ {
+ "name": "Daksh P. Jain",
+ "summary": "Telegram group maintainer",
+ "link": "https://dakshpjain.eu.org",
+ "profile_image": "https://i.imgur.com/fnYpg65.jpg"
+ },
+ {
+ "name": "Milind Goel",
+ "summary": "Github & Telegram maintainer",
+ "link": "https://t.me/MilindGoel15",
+ "profile_image": "https://i.imgur.com/Bz4De21_d.jpg"
+ }
+]
diff --git a/app/src/main/assets/images/daksh.png b/app/src/main/assets/images/daksh.png
deleted file mode 100644
index 737f9066c..000000000
Binary files a/app/src/main/assets/images/daksh.png and /dev/null differ
diff --git a/app/src/main/assets/images/haythem.jpg b/app/src/main/assets/images/haythem.jpg
deleted file mode 100644
index c74527f1d..000000000
Binary files a/app/src/main/assets/images/haythem.jpg and /dev/null differ
diff --git a/app/src/main/assets/images/hemanth.jpg b/app/src/main/assets/images/hemanth.jpg
deleted file mode 100644
index b8f5e7805..000000000
Binary files a/app/src/main/assets/images/hemanth.jpg and /dev/null differ
diff --git a/app/src/main/assets/images/lenny.jpg b/app/src/main/assets/images/lenny.jpg
deleted file mode 100644
index 7f8025f08..000000000
Binary files a/app/src/main/assets/images/lenny.jpg and /dev/null differ
diff --git a/app/src/main/assets/images/milind.png b/app/src/main/assets/images/milind.png
deleted file mode 100644
index bbf9b8278..000000000
Binary files a/app/src/main/assets/images/milind.png and /dev/null differ
diff --git a/app/src/main/assets/images/pratham.jpg b/app/src/main/assets/images/pratham.jpg
deleted file mode 100644
index 7f05ad9d5..000000000
Binary files a/app/src/main/assets/images/pratham.jpg and /dev/null differ
diff --git a/app/src/main/assets/license.html b/app/src/main/assets/license.html
deleted file mode 100644
index 2fd8ba5ed..000000000
--- a/app/src/main/assets/license.html
+++ /dev/null
@@ -1,76 +0,0 @@
-
-
-
-
-
-
-
-
-
- Phonograph by
- Karim Abou Zeid
-AOSP Support Libraries by AOSP contributors
- Glide by Sam Judd
- Retrofit by Square team
-
- OkHttp by Square team
-Koin by Arnaud Giuliani
- Material Dialogs and Cab
- by Aidan Michael Follestad
-
- Material Contextual Action Bar by Aidan Michael Follestad
- Advanced RecyclerView by Haruki Hasegawa
-Custom Activity on Crash by Eduard Ereza Martínez
-
-NanoHttpd by NanoHttpd Team
-Circular Seekbar by Tankery
-jAudioTagger by Kanedias
-Android Fast Scroll by Zhang Hai
-Image Picker by Dhaval Patel
-Material Intro by Jan Heinrich Reimer
-Slidr by Drew Heavner
-FadingEdgeLayout by bosphere
-KeyboardVisibilityEvent by Yasuhiro SHIMIZU
-android-snowfall by Jetradar Mobile
-Insetter by Chris Banes
- Icons by Austin Andrews
- Material Design City Wallpaper
-
-
-
diff --git a/app/src/main/assets/oldindex.html b/app/src/main/assets/oldindex.html
new file mode 100644
index 000000000..367da632a
--- /dev/null
+++ b/app/src/main/assets/oldindex.html
@@ -0,0 +1,63 @@
+
+
+
+
+
+
+
+
+
+ Phonograph by
+ Karim Abou Zeid
+ Material Dialogs and Cab
+ by Aidan Michael Follestad
+ AOSP Support Libraries by AOSP contributors
+ Glide by Sam Judd
+ Retrofit by Square team
+
+
+ Material Contextual Action Bar by Aidan Michael Follestad
+ OkHttp by Square team
+
+ CircleImageView by Henning Dodenhof
+
+ MaterialProgressBar by Zhang Hai
+ Android In-App Billing v3 Library by
+ Henning Dodenhof
+ Advanced RecyclerView by Haruki Hasegawa
+ Android-ObservableScrollView by Soichiro
+ Kashima
+ Icons by Austin Andrews
+ Material Design City Wallpaper
+
+
+
+
diff --git a/app/src/main/assets/retro-changelog.html b/app/src/main/assets/retro-changelog.html
index b6b1c411a..aa3c01e7f 100644
--- a/app/src/main/assets/retro-changelog.html
+++ b/app/src/main/assets/retro-changelog.html
@@ -6,23 +6,22 @@
word-wrap: break-word;
}
- div {
- margin: 20px 10px;
- padding: 10px;
- border-radius: 10px;
- box-shadow: 0px 0px 10px rgba(0, 0, 0, 0.2);
+ body {
+ padding-left: 1rem;
+ padding-right: 1rem;
}
h2 {
margin-block-end: 0rem;
margin-block-start: 0rem;
- display: inline-block;
- vertical-align: center;
}
li {
font-size: 0.85rem;
- padding: 0.5rem 0;
+ padding-top: 0.5rem;
+ padding-left: 0;
+ padding-right: 0;
+ color: rgba(0, 0, 0, 0.8);
}
ul {
@@ -37,6 +36,7 @@
span {
font-size: 0.7rem;
+ line-height: 0.7rem;
}
h5 {
@@ -44,423 +44,39 @@
margin-block-end: 0.5rem;
}
- h3 {
- margin: 10px 0px;
+ h3 span {
+ border-radius: 0.2rem;
+ padding-left: 0.5rem;
+ padding-right: 0.5rem;
+ padding-top: 0.3rem;
+ padding-bottom: 0.3rem;
font-size: 1rem;
}
-
- .tag {
- border-radius: 5px;
- margin-left: 10px;
- padding: 5px;
- display: inline-block;
- vertical-align: top;
- }
-
{style-placeholder}
+
+
-
-
-
March 30, 2023
-
v6.1.0
-
What's New
-
- App now targets Android 13, support for Granular media permissions, Photo picker, Per-app language preferences & Predictive back gesture
-
-
Fixed
-
- Fixed playlist reordering crash
- Other minor bugs fixes and improvements
-
-
-
-
March 13, 2023
-
v6.0.4
-
What's New
-
- Minor redesign in Playlist details screen
- Updated translations
-
-
Fixed
-
- Fixed file popup menu actions in Folders tab
- Fixed playlist image loading
- Fixed blurry album art in Android 13
- Minor bug fixes and improvements
-
-
-
-
July 10, 2022
-
v6.0.3Beta
-
Fixed
-
- Migrated icons to Material symbols
-
-
-
-
June 21, 2022
-
v6.0.2Beta
-
Fixed
-
- Minor bug fixes and improvements
-
-
-
-
June 13, 2022
-
v6.0.1Beta
-
Fixed
-
- Fixed ChromeCast crash
- Fixed Slider crashes
- Fixed storage related crashes on Android 10
- Fixed CrossFade not working Fade Audio is not working
-
-
-
-
June 7, 2022
-
v6.0.0Beta
-
What's New
-
- Better Cast
- Mini player in settings screen
- Changed Seekbar with Sliders
- Added NavigationRailView for Landscape
- Show remaining time in Sleep timer dialog
-
-
Fixed
-
- Fixed Top/Recent Artists/Albums not updating (Wrong sort order)
- Fixed all Blacklist related crashes
- Fix restart button not working in crash activity
-
-
-
-
May 25, 2022
-
v5.8.5
-
What's New
-
- Display song images along in the artist and album details pages
- Removed the Internet permissions and all the associated features
-
-
Fixed
-
- Fixed crashing occurs during changing screen orientation
-
-
-
-
May 13, 2022
-
v5.8.4
-
What's New
-
- Added a toggle to enable/disable swipe down to dismiss mini player
-
-
Fixed
-
- Fixed Playback speed and pitch not working when CrossFade is enabled
- Fixed crash when adding folders to blacklist
- Fix bugs in MD3 theme
-
-
-
-
May 07, 2022
-
v5.8.3
-
What's New
-
- Added a new MD3 now playing theme
- Swipe down to dismiss Mini player
- Add support for Just Black with Material You
-
-
Fixed
-
- Fixed sharing of files from SD Card
- Fix ChromeCast crash and bugs
- Fix Audio Crossfade
- Tried to fix incorrect song data in notification
-
-
-
-
April 8, 2022
-
v5.8.0
-
What's New
-
-
Fixed
-
- Fixed Classic Notification crash
- Fixed crash when clicking on Playlist in the Search Tab
- Fixed settings change not reflecting immediately
- Fixed shuffle
- Fixed Song duration not visible in Card & Blur card themes
- Fixed some Album skip styles
- Minor bug fixes & UI improvements
-
-
-
-
March 13, 2022
-
v5.7.3
-
What's New
-
- Added adaptive color in Material now playing theme
- Added an option to share crash report
- Added options to clear, pause history
-
-
Fixed
-
- Adapt Wallpaper accent for better readability
- Optimized search
- Made sleep timer precise
-
-
-
-
February 13, 2022
-
v5.7.2Beta
-
What's New
-
- Animated splash screen on Android 12 devices
-
-
Fixed
-
- Fixed crash when removing song from Playing queue
- Fixed lyrics editing crash
- Fixed shuffle button not working
- Fixed crash on song deletion
-
-
-
-
February 1, 2022
-
v5.7.1Beta
-
What's New
-
- Added option to disable changing song by swiping anywhere on the now playing screen
-
-
Fixed
-
- Fixed Playlist save on A11+
- Fixed Just Black theme
- Fixed some UI issues
-
-
Improved
-
- Improvements to search
-
-
-
-
January 25, 2022
-
v5.7.0Beta
-
What's New
-
- Added Android Auto
- Added accent color extraction on Android 8.1+ devices
- Added new Circle widget
- Added Collapsing appbar to library tabs with an option to switch back to simple appbar
-
- Added Search tab
- Added option to use circular play button
- Added lyrics editing on A11+ devices again
- Added Long Press to forward, rewind current song
- Added ability to set Playback speed and pitch
- Added option to show lyrics over Cover
- Added option to keep screen on when showing lyrics
- Added option to switch to Manrope font
-
-
Fixed
-
- Fixed Gapless Playback
- Fixed Shuffle FAB going behind Mini Player
- Fixed crashes on Pre-marshmallow devices
- Blacklisted songs can't be played after opening from outside the app
- Fixed various small bugs and some minor improvements
-
-
-
-
January 1, 2021
-
v5.6.1
-
Fixed
-
- Fixed artist covers not updating and showing album cover images.
- Fixed FAB's not visible (Shuffle, Save, etc.)
- Fixed a crash when a Song is deleted in Artist Details
- Fixed Snowfall effect
- Fixed empty notification when queue is cleared
-
-
-
-
December 25, 2021
-
v5.6.0Beta
-
What's New
-
- Added Artwork editing for songs
- Circle theme has album art now
- Upgraded tag editor library, we should support reading tags of more formats now e.g.
- opus.
-
- Added Snowfall effect
- Crossfade effect for background when Song is changed for Blur, Blur card themes
- Album art is hidden when Show lyrics is enabled
- Added fastscroll in Playlists tab
- Added Chooser to choose what to restore
- Hide BottomNavigation when only one tab is selected in Library Categories(This was
- already there but when changing screens it was getting visible)
-
-
-
Fixed
-
- Fixed Ringtone crash
- Fixed blank album cover bug
- Fixed bottom navigation visible in Playing Queue
- Fixed lockscreen dragging glitch
- Fixed incorrect colors when no cover art is available
- Fixed favorite not updating when song is changed
- Fixed playlist not getting created & playlist creation crash with same name
- Fixed a bug in "Plain" Now playing theme where onClick event is consumed by the views
- behind the bottom sheet
-
-
-
-
-
December 6, 2021
-
v5.4.2Beta
-
Fixed
-
-
-
-
December 1, 2021
-
v5.4.1Beta
-
What's New
-
- Added file selection from system file picker for restore
- Added Grid size selection for Playlists
-
-
Improved
-
- Enable Material You by default on Android 12
- Reworked Grid Style saving
- Improved Playlist preview images
- UI improvements
-
-
Improved
-
- Fixed File deletion on Android 10
- Fixed Sleep Timer crash
- Fixed Bottom Toolbar not clickable in now playing when Shuffle is clicked
- Fixed Album Artist sort order
- Fixed a crash when clicking the "Clear All" button in the Blacklist folder selection
-
- Fixed Continuous crashes on A12 when the song ends
- Fixed New Music Mix multiple clicks crash
-
-
-
-
November 22, 2021
-
v5.4.0Beta
-
What's New
-
- Material You
- Going Edge-to-Edge
- Added Backup & restore
-
-
Improved
-
- Improved Animations
- Improved Crossfade
-
-
-
-
September 06, 2021
-
v5.0.0
-
What's New
-
- Added ability to Remember last tab
- Added Whitelisting songs
- You can now browse SDCard from Folders Tab
-
-
-
-
August 22, 2021
-
v4.4.0Beta
-
What's New
-
- Added Crossfade
- Multi-select in Album and Artist Details
- Albums now show Album Artists instead of artist of first song
-
-
Fixed
-
- Fixed Playlist Preview Images
-
-
-
-
August 11, 2021
-
v4.2.30Beta
-
What's New
-
- Revamped Playlist Tab
- Revamped Genres Tab
- Added support for embedded Synced Lyrics
- Added animated icons
-
-
Fixed
-
- Fixed Language Switching
- Fixed some reported bugs
-
-
-
-
July 18, 2021
-
v4.2.020Beta
-
What's New
-
- Added ChromeCast Support
- Added Lyrics Editor for Normal and Synced Lyrics
- Added Ripple Animation for Color Theme
- Added Drag to seek in Tiny Theme
- Added Playlist Order
- Added Search Filters
- Added Audio Fade
- Synced Lyrics in all Themes
- Swipe anywhere to change song
-
-
Improved
-
- Fixed Navigate by Album Artist
- Changed New Music Mix Actions
- Improved Animations
- And some minor bug fixes and improvements
-
-
-
-
October 12, 2020
-
v4.0.10
-
What's New
-
- Re-built from scratch using MVVM Architecture and JetPack Components
- New Material Design icon
- Implemented a custom database for playlists
- Added new Material Design motions
- Bug fixes & performance improvements
- Revamped Home tab UI
- Android 11 support
- And more!
-
-
-
-
April 30, 2020
-
v3.5.110Beta
-
What's New
-
- Changed profile form image to icon
- New what's new screen
- Added In-App language changer, where you can select language
-
-
Improved
-
- Improved loading of Songs, Albums, Artists, Genres, Playlists
-
-
+April 30, 2020
+v3.5.110
+Beta version
+
+
+ Changed profile form image to icon
+ New what's new screen
+ Added In-App language changer, where you can select language
+
+
+
+ Improved loading of Songs, Albums, Artists, Genres, Playlists
+
+
+*If you face any UI related issues you clear app data and cache, if itsnot working try to
+ uninstall and install
+ again.
\ No newline at end of file
diff --git a/app/src/main/ic_launcher-playstore.png b/app/src/main/ic_launcher-playstore.png
index aa6e4ae9a..991844b5e 100644
Binary files a/app/src/main/ic_launcher-playstore.png and b/app/src/main/ic_launcher-playstore.png differ
diff --git a/app/src/main/ic_launcher-web.png b/app/src/main/ic_launcher-web.png
index 7e7647db5..ff0f8b9ff 100644
Binary files a/app/src/main/ic_launcher-web.png and b/app/src/main/ic_launcher-web.png differ
diff --git a/app/src/main/java/code/name/monkey/retromusic/App.kt b/app/src/main/java/code/name/monkey/retromusic/App.kt
deleted file mode 100644
index 93dfe4d96..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/App.kt
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic
-
-import android.app.Application
-import androidx.preference.PreferenceManager
-import cat.ereza.customactivityoncrash.config.CaocConfig
-import code.name.monkey.appthemehelper.ThemeStore
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.activities.ErrorActivity
-import code.name.monkey.retromusic.activities.MainActivity
-import code.name.monkey.retromusic.appshortcuts.DynamicShortcutManager
-import code.name.monkey.retromusic.helper.WallpaperAccentManager
-import org.koin.android.ext.koin.androidContext
-import org.koin.core.context.startKoin
-
-class App : Application() {
-
- private val wallpaperAccentManager = WallpaperAccentManager(this)
-
- override fun onCreate() {
- super.onCreate()
- instance = this
-
- startKoin {
- androidContext(this@App)
- modules(appModules)
- }
- // default theme
- if (!ThemeStore.isConfigured(this, 3)) {
- ThemeStore.editTheme(this)
- .accentColorRes(code.name.monkey.appthemehelper.R.color.md_deep_purple_A200)
- .coloredNavigationBar(true)
- .commit()
- }
- wallpaperAccentManager.init()
-
- if (VersionUtils.hasNougatMR())
- DynamicShortcutManager(this).initDynamicShortcuts()
-
- // setting Error activity
- CaocConfig.Builder.create().errorActivity(ErrorActivity::class.java)
- .restartActivity(MainActivity::class.java).apply()
-
- // Set Default values for now playing preferences
- // This will reduce startup time for now playing settings fragment as Preference listener of AbsSlidingMusicPanelActivity won't be called
- PreferenceManager.setDefaultValues(this, R.xml.pref_now_playing_screen, false)
- }
-
- override fun onTerminate() {
- super.onTerminate()
- wallpaperAccentManager.release()
- }
-
- companion object {
- private var instance: App? = null
-
- fun getContext(): App {
- return instance!!
- }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/HomeSection.kt b/app/src/main/java/code/name/monkey/retromusic/HomeSection.kt
deleted file mode 100644
index 4f1273a03..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/HomeSection.kt
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic
-
-import androidx.annotation.IntDef
-
-@IntDef(
- RECENT_ALBUMS,
- TOP_ALBUMS,
- RECENT_ARTISTS,
- TOP_ARTISTS,
- SUGGESTIONS,
- FAVOURITES,
- GENRES,
- PLAYLISTS
-)
-@Retention(AnnotationRetention.SOURCE)
-annotation class HomeSection
-
-const val RECENT_ALBUMS = 3
-const val TOP_ALBUMS = 1
-const val RECENT_ARTISTS = 2
-const val TOP_ARTISTS = 0
-const val SUGGESTIONS = 5
-const val FAVOURITES = 4
-const val GENRES = 6
-const val PLAYLISTS = 7
-const val HISTORY_PLAYLIST = 8
-const val LAST_ADDED_PLAYLIST = 9
-const val TOP_PLAYED_PLAYLIST = 10
diff --git a/app/src/main/java/code/name/monkey/retromusic/MainModule.kt b/app/src/main/java/code/name/monkey/retromusic/MainModule.kt
deleted file mode 100644
index d88f8a760..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/MainModule.kt
+++ /dev/null
@@ -1,156 +0,0 @@
-package code.name.monkey.retromusic
-
-import androidx.room.Room
-import code.name.monkey.retromusic.auto.AutoMusicProvider
-import code.name.monkey.retromusic.db.MIGRATION_23_24
-import code.name.monkey.retromusic.db.RetroDatabase
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.fragments.albums.AlbumDetailsViewModel
-import code.name.monkey.retromusic.fragments.artists.ArtistDetailsViewModel
-import code.name.monkey.retromusic.fragments.genres.GenreDetailsViewModel
-import code.name.monkey.retromusic.fragments.playlists.PlaylistDetailsViewModel
-import code.name.monkey.retromusic.model.Genre
-import code.name.monkey.retromusic.repository.*
-import org.koin.android.ext.koin.androidContext
-import org.koin.androidx.viewmodel.dsl.viewModel
-import org.koin.dsl.bind
-import org.koin.dsl.module
-
-private val roomModule = module {
-
- single {
- Room.databaseBuilder(androidContext(), RetroDatabase::class.java, "playlist.db")
- .addMigrations(MIGRATION_23_24)
- .build()
- }
-
- factory {
- get().playlistDao()
- }
-
- factory {
- get().playCountDao()
- }
-
- factory {
- get().historyDao()
- }
-
- single {
- RealRoomRepository(get(), get(), get())
- } bind RoomRepository::class
-}
-private val autoModule = module {
- single {
- AutoMusicProvider(
- androidContext(),
- get(),
- get(),
- get(),
- get(),
- get(),
- get()
- )
- }
-}
-private val mainModule = module {
- single {
- androidContext().contentResolver
- }
-}
-private val dataModule = module {
- single {
- RealRepository(
- get(),
- get(),
- get(),
- get(),
- get(),
- get(),
- get(),
- get(),
- get(),
- get(),
- )
- } bind Repository::class
-
- single {
- RealSongRepository(get())
- } bind SongRepository::class
-
- single {
- RealGenreRepository(get(), get())
- } bind GenreRepository::class
-
- single {
- RealAlbumRepository(get())
- } bind AlbumRepository::class
-
- single {
- RealArtistRepository(get(), get())
- } bind ArtistRepository::class
-
- single {
- RealPlaylistRepository(get())
- } bind PlaylistRepository::class
-
- single {
- RealTopPlayedRepository(get(), get(), get(), get())
- } bind TopPlayedRepository::class
-
- single {
- RealLastAddedRepository(
- get(),
- get(),
- get()
- )
- } bind LastAddedRepository::class
-
- single {
- RealSearchRepository(
- get(),
- get(),
- get(),
- get(),
- get()
- )
- }
-}
-
-private val viewModules = module {
-
- viewModel {
- LibraryViewModel(get())
- }
-
- viewModel { (albumId: Long) ->
- AlbumDetailsViewModel(
- get(),
- albumId
- )
- }
-
- viewModel { (artistId: Long?, artistName: String?) ->
- ArtistDetailsViewModel(
- get(),
- artistId,
- artistName
- )
- }
-
- viewModel { (playlistId: Long) ->
- PlaylistDetailsViewModel(
- get(),
- playlistId
- )
- }
-
- viewModel { (genre: Genre) ->
- GenreDetailsViewModel(
- get(),
- genre
- )
- }
-}
-
-val appModules = listOf(mainModule, dataModule, autoModule, viewModules, roomModule)
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/DriveModeActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/DriveModeActivity.kt
deleted file mode 100644
index af3890d22..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/DriveModeActivity.kt
+++ /dev/null
@@ -1,258 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities
-
-import android.content.Intent
-import android.graphics.Color
-import android.graphics.PorterDuff
-import android.os.Bundle
-import androidx.lifecycle.lifecycleScope
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.base.AbsMusicServiceActivity
-import code.name.monkey.retromusic.databinding.ActivityDriveModeBinding
-import code.name.monkey.retromusic.db.toSongEntity
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.drawAboveSystemBars
-import code.name.monkey.retromusic.glide.BlurTransformation
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.songCoverOptions
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.helper.MusicProgressViewUpdateHelper
-import code.name.monkey.retromusic.helper.MusicProgressViewUpdateHelper.Callback
-import code.name.monkey.retromusic.helper.PlayPauseButtonOnClickHandler
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.repository.RealRepository
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.util.MusicUtil
-import com.bumptech.glide.Glide
-import com.google.android.material.slider.Slider
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.launch
-import kotlinx.coroutines.withContext
-import org.koin.android.ext.android.inject
-
-
-/**
- * Created by hemanths on 2020-02-02.
- */
-
-class DriveModeActivity : AbsMusicServiceActivity(), Callback {
-
- private lateinit var binding: ActivityDriveModeBinding
- private var lastPlaybackControlsColor: Int = Color.GRAY
- private var lastDisabledPlaybackControlsColor: Int = Color.GRAY
- private lateinit var progressViewUpdateHelper: MusicProgressViewUpdateHelper
- private val repository: RealRepository by inject()
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- binding = ActivityDriveModeBinding.inflate(layoutInflater)
- setContentView(binding.root)
- setUpMusicControllers()
-
- progressViewUpdateHelper = MusicProgressViewUpdateHelper(this)
- lastPlaybackControlsColor = accentColor()
- binding.close.setOnClickListener {
- onBackPressedDispatcher.onBackPressed()
- }
- binding.repeatButton.drawAboveSystemBars()
- }
-
- private fun setUpMusicControllers() {
- setUpPlayPauseFab()
- setUpPrevNext()
- setUpRepeatButton()
- setUpShuffleButton()
- setUpProgressSlider()
- setupFavouriteToggle()
- }
-
- private fun setupFavouriteToggle() {
- binding.songFavourite.setOnClickListener {
- toggleFavorite(MusicPlayerRemote.currentSong)
- }
- }
-
- private fun toggleFavorite(song: Song) {
- lifecycleScope.launch(Dispatchers.IO) {
- val playlist = repository.favoritePlaylist()
- val songEntity = song.toSongEntity(playlist.playListId)
- val isFavorite = repository.isSongFavorite(song.id)
- if (isFavorite) {
- repository.removeSongFromPlaylist(songEntity)
- } else {
- repository.insertSongs(listOf(song.toSongEntity(playlist.playListId)))
- }
- sendBroadcast(Intent(MusicService.FAVORITE_STATE_CHANGED))
- }
- }
-
- private fun updateFavorite() {
- lifecycleScope.launch(Dispatchers.IO) {
- val isFavorite: Boolean =
- repository.isSongFavorite(MusicPlayerRemote.currentSong.id)
- withContext(Dispatchers.Main) {
- binding.songFavourite.setImageResource(if (isFavorite) R.drawable.ic_favorite else R.drawable.ic_favorite_border)
- }
- }
- }
-
- private fun setUpProgressSlider() {
- binding.progressSlider.addOnChangeListener { _: Slider, progress: Float, fromUser: Boolean ->
- if (fromUser) {
- MusicPlayerRemote.seekTo(progress.toInt())
- onUpdateProgressViews(
- MusicPlayerRemote.songProgressMillis,
- MusicPlayerRemote.songDurationMillis
- )
- }
- }
- }
-
- override fun onPause() {
- super.onPause()
- progressViewUpdateHelper.stop()
- }
-
- override fun onResume() {
- super.onResume()
- progressViewUpdateHelper.start()
- }
-
- private fun setUpPrevNext() {
- binding.nextButton.setOnClickListener { MusicPlayerRemote.playNextSong() }
- binding.previousButton.setOnClickListener { MusicPlayerRemote.back() }
- }
-
- private fun setUpShuffleButton() {
- binding.shuffleButton.setOnClickListener { MusicPlayerRemote.toggleShuffleMode() }
- }
-
- private fun setUpRepeatButton() {
- binding.repeatButton.setOnClickListener { MusicPlayerRemote.cycleRepeatMode() }
- }
-
- private fun setUpPlayPauseFab() {
- binding.playPauseButton.setOnClickListener(PlayPauseButtonOnClickHandler())
- }
-
- override fun onRepeatModeChanged() {
- super.onRepeatModeChanged()
- updateRepeatState()
- }
-
- override fun onShuffleModeChanged() {
- super.onShuffleModeChanged()
- updateShuffleState()
- }
-
- override fun onPlayStateChanged() {
- super.onPlayStateChanged()
- updatePlayPauseDrawableState()
- }
-
- override fun onServiceConnected() {
- super.onServiceConnected()
- updatePlayPauseDrawableState()
- updateSong()
- updateRepeatState()
- updateShuffleState()
- updateFavorite()
- }
-
- private fun updatePlayPauseDrawableState() {
- if (MusicPlayerRemote.isPlaying) {
- binding.playPauseButton.setImageResource(R.drawable.ic_pause)
- } else {
- binding.playPauseButton.setImageResource(R.drawable.ic_play_arrow)
- }
- }
-
- fun updateShuffleState() {
- when (MusicPlayerRemote.shuffleMode) {
- MusicService.SHUFFLE_MODE_SHUFFLE -> binding.shuffleButton.setColorFilter(
- lastPlaybackControlsColor,
- PorterDuff.Mode.SRC_IN
- )
-
- else -> binding.shuffleButton.setColorFilter(
- lastDisabledPlaybackControlsColor,
- PorterDuff.Mode.SRC_IN
- )
- }
- }
-
- private fun updateRepeatState() {
- when (MusicPlayerRemote.repeatMode) {
- MusicService.REPEAT_MODE_NONE -> {
- binding.repeatButton.setImageResource(R.drawable.ic_repeat)
- binding.repeatButton.setColorFilter(
- lastDisabledPlaybackControlsColor,
- PorterDuff.Mode.SRC_IN
- )
- }
-
- MusicService.REPEAT_MODE_ALL -> {
- binding.repeatButton.setImageResource(R.drawable.ic_repeat)
- binding.repeatButton.setColorFilter(
- lastPlaybackControlsColor,
- PorterDuff.Mode.SRC_IN
- )
- }
-
- MusicService.REPEAT_MODE_THIS -> {
- binding.repeatButton.setImageResource(R.drawable.ic_repeat_one)
- binding.repeatButton.setColorFilter(
- lastPlaybackControlsColor,
- PorterDuff.Mode.SRC_IN
- )
- }
- }
- }
-
- override fun onPlayingMetaChanged() {
- super.onPlayingMetaChanged()
- updateSong()
- updateFavorite()
- }
-
- override fun onFavoriteStateChanged() {
- super.onFavoriteStateChanged()
- updateFavorite()
- }
-
- private fun updateSong() {
- val song = MusicPlayerRemote.currentSong
-
- binding.songTitle.text = song.title
- binding.songText.text = song.artistName
-
- Glide.with(this)
- .load(RetroGlideExtension.getSongModel(song))
- .songCoverOptions(song)
- .transform(BlurTransformation.Builder(this).build())
- .into(binding.image)
- }
-
- override fun onUpdateProgressViews(progress: Int, total: Int) {
- binding.progressSlider.run {
- valueTo = total.toFloat()
- value = progress.toFloat().coerceIn(valueFrom, valueTo)
- }
-
- binding.songTotalTime.text = MusicUtil.getReadableDurationString(total.toLong())
- binding.songCurrentProgress.text = MusicUtil.getReadableDurationString(progress.toLong())
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/ErrorActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/ErrorActivity.kt
deleted file mode 100644
index 6823b80f8..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/ErrorActivity.kt
+++ /dev/null
@@ -1,80 +0,0 @@
-package code.name.monkey.retromusic.activities
-
-import android.os.Bundle
-import android.widget.Button
-import android.widget.ImageView
-import androidx.appcompat.app.AppCompatActivity
-import cat.ereza.customactivityoncrash.CustomActivityOnCrash
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.util.FileUtils.createFile
-import code.name.monkey.retromusic.util.Share.shareFile
-import com.google.android.material.dialog.MaterialAlertDialogBuilder
-import java.text.DateFormat
-import java.text.SimpleDateFormat
-import java.util.*
-
-class ErrorActivity : AppCompatActivity() {
- private val dayFormat: DateFormat = SimpleDateFormat("yyyy-MM-dd", Locale.getDefault())
- private val reportPrefix = "bug_report-"
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- setContentView(cat.ereza.customactivityoncrash.R.layout.customactivityoncrash_default_error_activity)
-
- val restartButton =
- findViewById(cat.ereza.customactivityoncrash.R.id.customactivityoncrash_error_activity_restart_button)
-
- val config = CustomActivityOnCrash.getConfigFromIntent(intent)
- if (config == null) {
- finish()
- return
- }
- restartButton.setText(cat.ereza.customactivityoncrash.R.string.customactivityoncrash_error_activity_restart_app)
- restartButton.setOnClickListener {
- CustomActivityOnCrash.restartApplication(
- this@ErrorActivity,
- config
- )
- }
- val moreInfoButton =
- findViewById(cat.ereza.customactivityoncrash.R.id.customactivityoncrash_error_activity_more_info_button)
-
- moreInfoButton.setOnClickListener { //We retrieve all the error data and show it
- MaterialAlertDialogBuilder(this@ErrorActivity)
- .setTitle(cat.ereza.customactivityoncrash.R.string.customactivityoncrash_error_activity_error_details_title)
- .setMessage(
- CustomActivityOnCrash.getAllErrorDetailsFromIntent(
- this@ErrorActivity,
- intent
- )
- )
- .setPositiveButton(
- cat.ereza.customactivityoncrash.R.string.customactivityoncrash_error_activity_error_details_close,
- null
- )
- .setNeutralButton(
- R.string.customactivityoncrash_error_activity_error_details_share
- ) { _, _ ->
-
- val bugReport = createFile(
- context = this,
- "Bug Report",
- "$reportPrefix${dayFormat.format(Date())}",
- CustomActivityOnCrash.getAllErrorDetailsFromIntent(
- this@ErrorActivity,
- intent
- ), ".txt"
- )
- shareFile(this, bugReport, "text/*")
- }
- .show()
- }
- val errorActivityDrawableId = config.errorDrawable
- val errorImageView =
- findViewById(cat.ereza.customactivityoncrash.R.id.customactivityoncrash_error_activity_image)
- if (errorActivityDrawableId != null) {
- errorImageView.setImageResource(
- errorActivityDrawableId
- )
- }
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/LicenseActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/LicenseActivity.kt
deleted file mode 100644
index e41352dae..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/LicenseActivity.kt
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright (c) 2019 Hemanth Savarala.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it under
- * the terms of the GNU General Public License as published by
- * the Free Software Foundation either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- */
-package code.name.monkey.retromusic.activities
-
-import android.graphics.Color
-import android.os.Bundle
-import android.view.MenuItem
-import code.name.monkey.appthemehelper.util.ATHUtil.isWindowBackgroundDark
-import code.name.monkey.appthemehelper.util.ColorUtil.lightenColor
-import code.name.monkey.appthemehelper.util.ToolbarContentTintHelper
-import code.name.monkey.retromusic.activities.base.AbsThemeActivity
-import code.name.monkey.retromusic.databinding.ActivityLicenseBinding
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.drawAboveSystemBars
-import code.name.monkey.retromusic.extensions.surfaceColor
-import java.io.BufferedReader
-import java.io.InputStreamReader
-import java.nio.charset.StandardCharsets
-
-/** Created by hemanths on 2019-09-27. */
-class LicenseActivity : AbsThemeActivity() {
- private lateinit var binding: ActivityLicenseBinding
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- binding = ActivityLicenseBinding.inflate(layoutInflater)
- setContentView(binding.root)
- setSupportActionBar(binding.toolbar)
- ToolbarContentTintHelper.colorBackButton(binding.toolbar)
- try {
- val buf = StringBuilder()
- val json = assets.open("license.html")
- BufferedReader(InputStreamReader(json, StandardCharsets.UTF_8)).use { br ->
- var str: String?
- while (br.readLine().also { str = it } != null) {
- buf.append(str)
- }
- }
-
- // Inject color values for WebView body background and links
- val isDark = isWindowBackgroundDark(this)
- val backgroundColor = colorToCSS(
- surfaceColor(Color.parseColor(if (isDark) "#424242" else "#ffffff"))
- )
- val contentColor = colorToCSS(Color.parseColor(if (isDark) "#ffffff" else "#000000"))
- val changeLog = buf.toString()
- .replace(
- "{style-placeholder}", String.format(
- "body { background-color: %s; color: %s; }", backgroundColor, contentColor
- )
- )
- .replace("{link-color}", colorToCSS(accentColor()))
- .replace(
- "{link-color-active}",
- colorToCSS(
- lightenColor(accentColor())
- )
- )
- binding.license.loadData(changeLog, "text/html", "UTF-8")
- } catch (e: Throwable) {
- binding.license.loadData(
- "Unable to load " + e.localizedMessage + "
", "text/html", "UTF-8"
- )
- }
- binding.license.drawAboveSystemBars()
- }
-
- override fun onOptionsItemSelected(item: MenuItem): Boolean {
- if (item.itemId == android.R.id.home) {
- onBackPressedDispatcher.onBackPressed()
- return true
- }
- return super.onOptionsItemSelected(item)
- }
-
- private fun colorToCSS(color: Int): String {
- return String.format(
- "rgb(%d, %d, %d)",
- Color.red(color),
- Color.green(color),
- Color.blue(color)
- ) // on API 29, WebView doesn't load with hex colors
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/LockScreenActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/LockScreenActivity.kt
deleted file mode 100644
index 3ac219871..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/LockScreenActivity.kt
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities
-
-import android.app.KeyguardManager
-import android.os.Bundle
-import android.view.WindowManager
-import androidx.core.content.getSystemService
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.base.AbsMusicServiceActivity
-import code.name.monkey.retromusic.databinding.ActivityLockScreenBinding
-import code.name.monkey.retromusic.extensions.hideStatusBar
-import code.name.monkey.retromusic.extensions.setTaskDescriptionColorAuto
-import code.name.monkey.retromusic.extensions.whichFragment
-import code.name.monkey.retromusic.fragments.player.lockscreen.LockScreenControlsFragment
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.RetroGlideExtension.songCoverOptions
-import code.name.monkey.retromusic.glide.RetroMusicColoredTarget
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.util.color.MediaNotificationProcessor
-import com.bumptech.glide.Glide
-import com.r0adkll.slidr.Slidr
-import com.r0adkll.slidr.model.SlidrConfig
-import com.r0adkll.slidr.model.SlidrListener
-import com.r0adkll.slidr.model.SlidrPosition
-
-class LockScreenActivity : AbsMusicServiceActivity() {
- private lateinit var binding: ActivityLockScreenBinding
- private var fragment: LockScreenControlsFragment? = null
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- lockScreenInit()
- binding = ActivityLockScreenBinding.inflate(layoutInflater)
- setContentView(binding.root)
- hideStatusBar()
- setTaskDescriptionColorAuto()
-
- val config = SlidrConfig.Builder().listener(object : SlidrListener {
- override fun onSlideStateChanged(state: Int) {
- }
-
- override fun onSlideChange(percent: Float) {
- }
-
- override fun onSlideOpened() {
- }
-
- override fun onSlideClosed(): Boolean {
- if (VersionUtils.hasOreo()) {
- val keyguardManager =
- getSystemService()
- keyguardManager?.requestDismissKeyguard(this@LockScreenActivity, null)
- }
- finish()
- return true
- }
- }).position(SlidrPosition.BOTTOM).build()
-
- Slidr.attach(this, config)
-
- fragment = whichFragment(R.id.playback_controls_fragment)
-
- binding.slide.apply {
- translationY = 100f
- alpha = 0f
- animate().translationY(0f).alpha(1f).setDuration(1500).start()
- }
- }
-
- @Suppress("Deprecation")
- private fun lockScreenInit() {
- if (VersionUtils.hasOreoMR1()) {
- setShowWhenLocked(true)
- //setTurnScreenOn(true)
- } else {
- window.addFlags(
- WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED
- // or WindowManager.LayoutParams.FLAG_TURN_SCREEN_ON
- )
- }
- }
-
- override fun onPlayingMetaChanged() {
- super.onPlayingMetaChanged()
- updateSongs()
- }
-
- override fun onServiceConnected() {
- super.onServiceConnected()
- updateSongs()
- }
-
- private fun updateSongs() {
- val song = MusicPlayerRemote.currentSong
- Glide.with(this)
- .asBitmapPalette()
- .songCoverOptions(song)
- .load(RetroGlideExtension.getSongModel(song))
- .dontAnimate()
- .into(object : RetroMusicColoredTarget(binding.image) {
- override fun onColorReady(colors: MediaNotificationProcessor) {
- fragment?.setColor(colors)
- }
- })
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/MainActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/MainActivity.kt
deleted file mode 100644
index e9cb29abe..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/MainActivity.kt
+++ /dev/null
@@ -1,214 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities
-
-import android.content.Intent
-import android.net.Uri
-import android.os.Bundle
-import android.provider.MediaStore
-import androidx.lifecycle.lifecycleScope
-import androidx.navigation.contains
-import androidx.navigation.ui.setupWithNavController
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.base.AbsSlidingMusicPanelActivity
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.helper.SearchQueryHelper.getSongs
-import code.name.monkey.retromusic.interfaces.IScrollHelper
-import code.name.monkey.retromusic.model.CategoryInfo
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.repository.PlaylistSongsLoader
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.logE
-import kotlinx.coroutines.Dispatchers.IO
-import kotlinx.coroutines.launch
-import org.koin.android.ext.android.get
-
-class MainActivity : AbsSlidingMusicPanelActivity() {
- companion object {
- const val TAG = "MainActivity"
- const val EXPAND_PANEL = "expand_panel"
- }
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- setTaskDescriptionColorAuto()
- hideStatusBar()
- updateTabs()
-
- setupNavigationController()
-
- WhatsNewFragment.showChangeLog(this)
- }
-
- private fun setupNavigationController() {
- val navController = findNavController(R.id.fragment_container)
- val navInflater = navController.navInflater
- val navGraph = navInflater.inflate(R.navigation.main_graph)
-
- val categoryInfo: CategoryInfo = PreferenceUtil.libraryCategory.first { it.visible }
- if (categoryInfo.visible) {
- if (!navGraph.contains(PreferenceUtil.lastTab)) PreferenceUtil.lastTab =
- categoryInfo.category.id
- navGraph.setStartDestination(
- if (PreferenceUtil.rememberLastTab) {
- PreferenceUtil.lastTab.let {
- if (it == 0) {
- categoryInfo.category.id
- } else {
- it
- }
- }
- } else categoryInfo.category.id
- )
- }
- navController.graph = navGraph
- navigationView.setupWithNavController(navController)
- // Scroll Fragment to top
- navigationView.setOnItemReselectedListener {
- currentFragment(R.id.fragment_container).apply {
- if (this is IScrollHelper) {
- scrollToTop()
- }
- }
- }
- navController.addOnDestinationChangedListener { _, destination, _ ->
- if (destination.id == navGraph.startDestinationId) {
- currentFragment(R.id.fragment_container)?.enterTransition = null
- }
- when (destination.id) {
- R.id.action_home, R.id.action_song, R.id.action_album, R.id.action_artist, R.id.action_folder, R.id.action_playlist, R.id.action_genre, R.id.action_search -> {
- // Save the last tab
- if (PreferenceUtil.rememberLastTab) {
- saveTab(destination.id)
- }
- // Show Bottom Navigation Bar
- setBottomNavVisibility(visible = true, animate = true)
- }
- R.id.playing_queue_fragment -> {
- setBottomNavVisibility(visible = false, hideBottomSheet = true)
- }
- else -> setBottomNavVisibility(
- visible = false,
- animate = true
- ) // Hide Bottom Navigation Bar
- }
- }
- }
-
- private fun saveTab(id: Int) {
- if (PreferenceUtil.libraryCategory.firstOrNull { it.category.id == id }?.visible == true) {
- PreferenceUtil.lastTab = id
- }
- }
-
- override fun onSupportNavigateUp(): Boolean =
- findNavController(R.id.fragment_container).navigateUp()
-
- override fun onNewIntent(intent: Intent?) {
- super.onNewIntent(intent)
- val expand = intent?.extra(EXPAND_PANEL)?.value ?: false
- if (expand && PreferenceUtil.isExpandPanel) {
- fromNotification = true
- slidingPanel.bringToFront()
- expandPanel()
- intent?.removeExtra(EXPAND_PANEL)
- }
- }
-
- override fun onServiceConnected() {
- super.onServiceConnected()
- intent ?: return
- handlePlaybackIntent(intent)
- }
-
- private fun handlePlaybackIntent(intent: Intent) {
- lifecycleScope.launch(IO) {
- val uri: Uri? = intent.data
- val mimeType: String? = intent.type
- var handled = false
- if (intent.action != null &&
- intent.action == MediaStore.INTENT_ACTION_MEDIA_PLAY_FROM_SEARCH
- ) {
- val songs: List = getSongs(intent.extras!!)
- if (MusicPlayerRemote.shuffleMode == MusicService.SHUFFLE_MODE_SHUFFLE) {
- MusicPlayerRemote.openAndShuffleQueue(songs, true)
- } else {
- MusicPlayerRemote.openQueue(songs, 0, true)
- }
- handled = true
- }
- if (uri != null && uri.toString().isNotEmpty()) {
- MusicPlayerRemote.playFromUri(this@MainActivity, uri)
- handled = true
- } else if (MediaStore.Audio.Playlists.CONTENT_TYPE == mimeType) {
- val id = parseLongFromIntent(intent, "playlistId", "playlist")
- if (id >= 0L) {
- val position: Int = intent.getIntExtra("position", 0)
- val songs: List = PlaylistSongsLoader.getPlaylistSongList(get(), id)
- MusicPlayerRemote.openQueue(songs, position, true)
- handled = true
- }
- } else if (MediaStore.Audio.Albums.CONTENT_TYPE == mimeType) {
- val id = parseLongFromIntent(intent, "albumId", "album")
- if (id >= 0L) {
- val position: Int = intent.getIntExtra("position", 0)
- val songs = libraryViewModel.albumById(id).songs
- MusicPlayerRemote.openQueue(
- songs,
- position,
- true
- )
- handled = true
- }
- } else if (MediaStore.Audio.Artists.CONTENT_TYPE == mimeType) {
- val id = parseLongFromIntent(intent, "artistId", "artist")
- if (id >= 0L) {
- val position: Int = intent.getIntExtra("position", 0)
- val songs: List = libraryViewModel.artistById(id).songs
- MusicPlayerRemote.openQueue(
- songs,
- position,
- true
- )
- handled = true
- }
- }
- if (handled) {
- setIntent(Intent())
- }
- }
- }
-
- private fun parseLongFromIntent(
- intent: Intent,
- longKey: String,
- stringKey: String,
- ): Long {
- var id = intent.getLongExtra(longKey, -1)
- if (id < 0) {
- val idString = intent.getStringExtra(stringKey)
- if (idString != null) {
- try {
- id = idString.toLong()
- } catch (e: NumberFormatException) {
- logE(e)
- }
- }
- }
- return id
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/PermissionActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/PermissionActivity.kt
deleted file mode 100644
index 5cb64cf93..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/PermissionActivity.kt
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities
-
-import android.Manifest.permission.BLUETOOTH_CONNECT
-import android.content.Intent
-import android.content.pm.PackageManager
-import android.content.res.ColorStateList
-import android.os.Build
-import android.os.Bundle
-import android.provider.Settings
-import androidx.activity.OnBackPressedCallback
-import androidx.annotation.RequiresApi
-import androidx.core.app.ActivityCompat
-import androidx.core.net.toUri
-import androidx.core.text.parseAsHtml
-import androidx.core.view.isVisible
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.base.AbsMusicServiceActivity
-import code.name.monkey.retromusic.databinding.ActivityPermissionBinding
-import code.name.monkey.retromusic.extensions.*
-
-class PermissionActivity : AbsMusicServiceActivity() {
- private lateinit var binding: ActivityPermissionBinding
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- binding = ActivityPermissionBinding.inflate(layoutInflater)
- setContentView(binding.root)
- setStatusBarColorAuto()
- setTaskDescriptionColorAuto()
- setupTitle()
-
- binding.storagePermission.setButtonClick {
- requestPermissions()
- }
- if (VersionUtils.hasMarshmallow()) {
- binding.audioPermission.show()
- binding.audioPermission.setButtonClick {
- if (!hasAudioPermission()) {
- val intent = Intent(Settings.ACTION_MANAGE_WRITE_SETTINGS)
- intent.data = ("package:" + applicationContext.packageName).toUri()
- startActivity(intent)
- }
- }
- }
-
- if (VersionUtils.hasS()) {
- binding.bluetoothPermission.show()
- binding.bluetoothPermission.setButtonClick {
- ActivityCompat.requestPermissions(
- this,
- arrayOf(BLUETOOTH_CONNECT),
- BLUETOOTH_PERMISSION_REQUEST
- )
- }
- } else {
- binding.audioPermission.setNumber("2")
- }
-
- binding.finish.accentBackgroundColor()
- binding.finish.setOnClickListener {
- if (hasPermissions()) {
- startActivity(
- Intent(this, MainActivity::class.java).addFlags(
- Intent.FLAG_ACTIVITY_NEW_TASK or
- Intent.FLAG_ACTIVITY_CLEAR_TASK
- )
- )
- finish()
- }
- }
- onBackPressedDispatcher.addCallback(object : OnBackPressedCallback(true) {
- override fun handleOnBackPressed() {
- finishAffinity()
- remove()
- }
- })
- }
-
- private fun setupTitle() {
- val appName =
- getString(
- R.string.message_welcome,
- "Metro "
- )
- .parseAsHtml()
- binding.appNameText.text = appName
- }
-
- override fun onResume() {
- super.onResume()
- binding.finish.isEnabled = hasStoragePermission()
- if (hasStoragePermission()) {
- binding.storagePermission.checkImage.isVisible = true
- binding.storagePermission.checkImage.imageTintList =
- ColorStateList.valueOf(accentColor())
- }
- if (VersionUtils.hasMarshmallow()) {
- if (hasAudioPermission()) {
- binding.audioPermission.checkImage.isVisible = true
- binding.audioPermission.checkImage.imageTintList =
- ColorStateList.valueOf(accentColor())
- }
- }
- if (VersionUtils.hasS()) {
- if (hasBluetoothPermission()) {
- binding.bluetoothPermission.checkImage.isVisible = true
- binding.bluetoothPermission.checkImage.imageTintList =
- ColorStateList.valueOf(accentColor())
- }
- }
- }
-
- private fun hasStoragePermission(): Boolean {
- return hasPermissions()
- }
-
- @RequiresApi(Build.VERSION_CODES.S)
- private fun hasBluetoothPermission(): Boolean {
- return ActivityCompat.checkSelfPermission(
- this,
- BLUETOOTH_CONNECT
- ) == PackageManager.PERMISSION_GRANTED
- }
-
- @RequiresApi(Build.VERSION_CODES.M)
- private fun hasAudioPermission(): Boolean {
- return Settings.System.canWrite(this)
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/ShareInstagramStory.kt b/app/src/main/java/code/name/monkey/retromusic/activities/ShareInstagramStory.kt
deleted file mode 100644
index 546c9d794..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/ShareInstagramStory.kt
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities
-
-import android.content.res.ColorStateList
-import android.graphics.Bitmap
-import android.graphics.Color
-import android.graphics.drawable.GradientDrawable
-import android.os.Bundle
-import android.provider.MediaStore.Images.Media
-import android.view.MenuItem
-import androidx.core.net.toUri
-import androidx.core.os.BundleCompat
-import androidx.core.view.drawToBitmap
-import code.name.monkey.appthemehelper.util.ColorUtil
-import code.name.monkey.appthemehelper.util.MaterialValueHelper
-import code.name.monkey.retromusic.activities.base.AbsThemeActivity
-import code.name.monkey.retromusic.databinding.ActivityShareInstagramBinding
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.setStatusBarColor
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.RetroGlideExtension.songCoverOptions
-import code.name.monkey.retromusic.glide.RetroMusicColoredTarget
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.Share
-import code.name.monkey.retromusic.util.color.MediaNotificationProcessor
-import com.bumptech.glide.Glide
-
-/**
- * Created by hemanths on 2020-02-02.
- */
-
-class ShareInstagramStory : AbsThemeActivity() {
-
- private lateinit var binding: ActivityShareInstagramBinding
-
- companion object {
- const val EXTRA_SONG = "extra_song"
- }
-
- override fun onOptionsItemSelected(item: MenuItem): Boolean {
- if (item.itemId == android.R.id.home) {
- onBackPressedDispatcher.onBackPressed()
- return true
- }
- return super.onOptionsItemSelected(item)
- }
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- binding = ActivityShareInstagramBinding.inflate(layoutInflater)
- setContentView(binding.root)
- setStatusBarColor(Color.TRANSPARENT)
-
- binding.toolbar.setBackgroundColor(Color.TRANSPARENT)
- setSupportActionBar(binding.toolbar)
-
- val song = intent.extras?.let { BundleCompat.getParcelable(it, EXTRA_SONG, Song::class.java) }
- song?.let { songFinal ->
- Glide.with(this)
- .asBitmapPalette()
- .songCoverOptions(songFinal)
- .load(RetroGlideExtension.getSongModel(songFinal))
- .into(object : RetroMusicColoredTarget(binding.image) {
- override fun onColorReady(colors: MediaNotificationProcessor) {
- setColors(colors.backgroundColor)
- }
- })
-
- binding.shareTitle.text = songFinal.title
- binding.shareText.text = songFinal.artistName
- binding.shareButton.setOnClickListener {
- val path: String = Media.insertImage(
- contentResolver,
- binding.mainContent.drawToBitmap(Bitmap.Config.ARGB_8888),
- "Design", null
- )
- Share.shareStoryToSocial(
- this@ShareInstagramStory,
- path.toUri()
- )
- }
- }
- binding.shareButton.setTextColor(
- MaterialValueHelper.getPrimaryTextColor(
- this,
- ColorUtil.isColorLight(accentColor())
- )
- )
- binding.shareButton.backgroundTintList =
- ColorStateList.valueOf(accentColor())
- }
-
- private fun setColors(color: Int) {
- binding.mainContent.background =
- GradientDrawable(
- GradientDrawable.Orientation.TOP_BOTTOM,
- intArrayOf(color, Color.BLACK)
- )
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/WhatsNewFragment.kt b/app/src/main/java/code/name/monkey/retromusic/activities/WhatsNewFragment.kt
deleted file mode 100644
index 48b39ed35..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/WhatsNewFragment.kt
+++ /dev/null
@@ -1,153 +0,0 @@
-package code.name.monkey.retromusic.activities
-
-import android.content.Context
-import android.content.Intent
-import android.content.pm.PackageManager
-import android.graphics.Color
-import android.os.Bundle
-import android.view.LayoutInflater
-import android.view.View
-import android.view.ViewGroup
-import android.webkit.WebResourceRequest
-import android.webkit.WebView
-import android.webkit.WebViewClient
-import androidx.core.content.pm.PackageInfoCompat
-import androidx.core.widget.NestedScrollView
-import androidx.fragment.app.FragmentActivity
-import code.name.monkey.appthemehelper.util.ATHUtil.isWindowBackgroundDark
-import code.name.monkey.appthemehelper.util.ColorUtil.isColorLight
-import code.name.monkey.appthemehelper.util.ColorUtil.lightenColor
-import code.name.monkey.appthemehelper.util.MaterialValueHelper.getPrimaryTextColor
-import code.name.monkey.retromusic.BuildConfig
-import code.name.monkey.retromusic.Constants
-import code.name.monkey.retromusic.databinding.FragmentWhatsNewBinding
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.openUrl
-import code.name.monkey.retromusic.util.PreferenceUtil.lastVersion
-import com.google.android.material.bottomsheet.BottomSheetDialogFragment
-import java.nio.charset.StandardCharsets
-import java.util.*
-
-class WhatsNewFragment : BottomSheetDialogFragment() {
- private var _binding: FragmentWhatsNewBinding? = null
- val binding get() = _binding!!
-
- override fun onCreateView(
- inflater: LayoutInflater,
- container: ViewGroup?,
- savedInstanceState: Bundle?
- ): View {
- _binding = FragmentWhatsNewBinding.inflate(inflater, container, false)
- return binding.root
- }
-
- override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
- super.onViewCreated(view, savedInstanceState)
- try {
- val buf = StringBuilder()
- val stream = requireContext().assets.open("retro-changelog.html")
- stream.reader(StandardCharsets.UTF_8).buffered().use { br ->
- var str: String?
- while (br.readLine().also { str = it } != null) {
- buf.append(str)
- }
- }
-
- // Inject color values for WebView body background and links
- val isDark = isWindowBackgroundDark(requireContext())
- val accentColor = accentColor()
- binding.webView.setBackgroundColor(0)
- val contentColor = colorToCSS(Color.parseColor(if (isDark) "#ffffff" else "#000000"))
- val textColor = colorToCSS(Color.parseColor(if (isDark) "#60FFFFFF" else "#80000000"))
- val accentColorString = colorToCSS(accentColor())
- val cardBackgroundColor =
- colorToCSS(Color.parseColor(if (isDark) "#353535" else "#ffffff"))
- val accentTextColor = colorToCSS(
- getPrimaryTextColor(
- requireContext(), isColorLight(accentColor)
- )
- )
- val changeLog = buf.toString()
- .replace(
- "{style-placeholder}",
- "body { color: $contentColor; } li {color: $textColor;} h3 {color: $accentColorString;} .tag {background-color: $accentColorString; color: $accentTextColor; } div{background-color: $cardBackgroundColor;}"
- )
- .replace("{link-color}", colorToCSS(accentColor()))
- .replace(
- "{link-color-active}",
- colorToCSS(
- lightenColor(accentColor())
- )
- )
- binding.webView.loadData(changeLog, "text/html", "UTF-8")
- binding.webView.webViewClient = object : WebViewClient() {
- override fun shouldOverrideUrlLoading(
- view: WebView?,
- request: WebResourceRequest?
- ): Boolean {
- val url = request?.url ?: return false
- //you can do checks here e.g. url.host equals to target one
- startActivity(Intent(Intent.ACTION_VIEW, url))
- return true
- }
- }
- } catch (e: Throwable) {
- binding.webView.loadData(
- "Unable to load " + e.localizedMessage + "
", "text/html", "UTF-8"
- )
- }
- setChangelogRead(requireContext())
- binding.tgFab.setOnClickListener {
- openUrl(Constants.TELEGRAM_CHANGE_LOG)
- }
- binding.tgFab.accentColor()
- binding.tgFab.shrink()
- binding.container.setOnScrollChangeListener { _: NestedScrollView?, _: Int, scrollY: Int, _: Int, oldScrollY: Int ->
- val dy = scrollY - oldScrollY
- if (dy > 0) {
- binding.tgFab.shrink()
- } else if (dy < 0) {
- binding.tgFab.extend()
- }
- }
- }
-
- override fun onDestroy() {
- super.onDestroy()
- _binding = null
- }
-
- companion object {
-
- const val TAG = "WhatsNewFragment"
- private fun colorToCSS(color: Int): String {
- return String.format(
- Locale.getDefault(),
- "rgba(%d, %d, %d, %d)",
- Color.red(color),
- Color.green(color),
- Color.blue(color),
- Color.alpha(color)
- ) // on API 29, WebView doesn't load with hex colors
- }
-
- private fun setChangelogRead(context: Context) {
- try {
- val pInfo = context.packageManager.getPackageInfo(context.packageName, 0)
- val currentVersion = PackageInfoCompat.getLongVersionCode(pInfo)
- lastVersion = currentVersion
- } catch (e: PackageManager.NameNotFoundException) {
- e.printStackTrace()
- }
- }
-
- fun showChangeLog(activity: FragmentActivity) {
- val pInfo = activity.packageManager.getPackageInfo(activity.packageName, 0)
- val currentVersion = PackageInfoCompat.getLongVersionCode(pInfo)
- if (currentVersion > lastVersion && !BuildConfig.DEBUG) {
- val changelogBottomSheet = WhatsNewFragment()
- changelogBottomSheet.show(activity.supportFragmentManager, TAG)
- }
- }
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsBaseActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsBaseActivity.kt
deleted file mode 100644
index 1e0c110d5..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsBaseActivity.kt
+++ /dev/null
@@ -1,204 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities.base
-
-import android.Manifest
-import android.content.Intent
-import android.content.pm.PackageManager
-import android.graphics.Rect
-import android.media.AudioManager
-import android.net.Uri
-import android.os.Bundle
-import android.provider.Settings
-import android.view.KeyEvent
-import android.view.MotionEvent
-import android.view.View
-import android.view.inputmethod.InputMethodManager
-import android.widget.EditText
-import androidx.core.app.ActivityCompat
-import androidx.core.content.getSystemService
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.rootView
-import code.name.monkey.retromusic.util.logD
-import com.google.android.material.snackbar.Snackbar
-
-abstract class AbsBaseActivity : AbsThemeActivity() {
- private var hadPermissions: Boolean = false
- private lateinit var permissions: Array
- private var permissionDeniedMessage: String? = null
-
- open fun getPermissionsToRequest(): Array {
- return arrayOf()
- }
-
- protected fun setPermissionDeniedMessage(message: String) {
- permissionDeniedMessage = message
- }
-
- fun getPermissionDeniedMessage(): String {
- return if (permissionDeniedMessage == null) getString(R.string.permissions_denied) else permissionDeniedMessage!!
- }
-
- private val snackBarContainer: View
- get() = rootView
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- volumeControlStream = AudioManager.STREAM_MUSIC
- permissions = getPermissionsToRequest()
- hadPermissions = hasPermissions()
- permissionDeniedMessage = null
- }
-
- override fun onResume() {
- super.onResume()
- val hasPermissions = hasPermissions()
- if (hasPermissions != hadPermissions) {
- hadPermissions = hasPermissions
- if (VersionUtils.hasMarshmallow()) {
- onHasPermissionsChanged(hasPermissions)
- }
- }
- }
-
- protected open fun onHasPermissionsChanged(hasPermissions: Boolean) {
- // implemented by sub classes
- logD(hasPermissions)
- }
-
- override fun dispatchKeyEvent(event: KeyEvent): Boolean {
- if (event.keyCode == KeyEvent.KEYCODE_MENU && event.action == KeyEvent.ACTION_UP) {
- showOverflowMenu()
- return true
- }
- return super.dispatchKeyEvent(event)
- }
-
- private fun showOverflowMenu() {
- }
-
- protected open fun requestPermissions() {
- ActivityCompat.requestPermissions(this, permissions, PERMISSION_REQUEST)
- }
-
- protected fun hasPermissions(): Boolean {
- for (permission in permissions) {
- if (ActivityCompat.checkSelfPermission(this,
- permission) != PackageManager.PERMISSION_GRANTED
- ) {
- return false
- }
- }
- return true
- }
-
- override fun onRequestPermissionsResult(
- requestCode: Int,
- permissions: Array,
- grantResults: IntArray,
- ) {
- super.onRequestPermissionsResult(requestCode, permissions, grantResults)
- if (requestCode == PERMISSION_REQUEST) {
- for (grantResult in grantResults) {
- if (grantResult != PackageManager.PERMISSION_GRANTED) {
- if (ActivityCompat.shouldShowRequestPermissionRationale(
- this@AbsBaseActivity, Manifest.permission.READ_EXTERNAL_STORAGE,
- ) || ActivityCompat.shouldShowRequestPermissionRationale(
- this@AbsBaseActivity, Manifest.permission.WRITE_EXTERNAL_STORAGE,
- )
- ) {
- // User has deny from permission dialog
- Snackbar.make(
- snackBarContainer,
- permissionDeniedMessage!!,
- Snackbar.LENGTH_SHORT
- )
- .setAction(R.string.action_grant) { requestPermissions() }
- .setActionTextColor(accentColor()).show()
- } else {
- // User has deny permission and checked never show permission dialog so you can redirect to Application settings page
- Snackbar.make(
- snackBarContainer,
- permissionDeniedMessage!!,
- Snackbar.LENGTH_INDEFINITE
- )
- .setAction(R.string.action_settings) {
- val intent = Intent()
- intent.action = Settings.ACTION_APPLICATION_DETAILS_SETTINGS
- val uri = Uri.fromParts(
- "package",
- this@AbsBaseActivity.packageName,
- null
- )
- intent.data = uri
- startActivity(intent)
- }.setActionTextColor(accentColor()).show()
- }
- return
- }
- }
- hadPermissions = true
- onHasPermissionsChanged(true)
- } else if (requestCode == BLUETOOTH_PERMISSION_REQUEST) {
- for (grantResult in grantResults) {
- if (grantResult != PackageManager.PERMISSION_GRANTED) {
- if (ActivityCompat.shouldShowRequestPermissionRationale(
- this@AbsBaseActivity, Manifest.permission.BLUETOOTH_CONNECT
- )
- ) {
- // User has deny from permission dialog
- Snackbar.make(
- snackBarContainer,
- R.string.permission_bluetooth_denied,
- Snackbar.LENGTH_SHORT
- )
- .setAction(R.string.action_grant) {
- ActivityCompat.requestPermissions(this,
- arrayOf(Manifest.permission.BLUETOOTH_CONNECT),
- BLUETOOTH_PERMISSION_REQUEST)
- }
- .setActionTextColor(accentColor()).show()
- }
- }
- }
- }
- }
-
- companion object {
- const val PERMISSION_REQUEST = 100
- const val BLUETOOTH_PERMISSION_REQUEST = 101
- }
-
- // this lets keyboard close when clicked in background
- override fun dispatchTouchEvent(event: MotionEvent): Boolean {
- if (event.action == MotionEvent.ACTION_DOWN) {
- val v = currentFocus
- if (v is EditText) {
- val outRect = Rect()
- v.getGlobalVisibleRect(outRect)
- if (!outRect.contains(event.rawX.toInt(), event.rawY.toInt())) {
- v.clearFocus()
- getSystemService()?.hideSoftInputFromWindow(
- v.windowToken,
- 0
- )
- }
- }
- }
- return super.dispatchTouchEvent(event)
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsSlidingMusicPanelActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsSlidingMusicPanelActivity.kt
deleted file mode 100644
index 2a81ca9b4..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsSlidingMusicPanelActivity.kt
+++ /dev/null
@@ -1,581 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities.base
-
-import android.animation.ArgbEvaluator
-import android.animation.ValueAnimator
-import android.content.Intent
-import android.content.SharedPreferences
-import android.content.res.ColorStateList
-import android.graphics.Color
-import android.os.Bundle
-import android.view.View
-import android.view.ViewGroup
-import android.view.ViewTreeObserver
-import android.view.animation.PathInterpolator
-import android.widget.FrameLayout
-import androidx.activity.OnBackPressedCallback
-import androidx.core.animation.doOnEnd
-import androidx.core.view.*
-import androidx.fragment.app.commit
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.ADAPTIVE_COLOR_APP
-import code.name.monkey.retromusic.ALBUM_COVER_STYLE
-import code.name.monkey.retromusic.ALBUM_COVER_TRANSFORM
-import code.name.monkey.retromusic.CAROUSEL_EFFECT
-import code.name.monkey.retromusic.CIRCLE_PLAY_BUTTON
-import code.name.monkey.retromusic.EXTRA_SONG_INFO
-import code.name.monkey.retromusic.KEEP_SCREEN_ON
-import code.name.monkey.retromusic.LIBRARY_CATEGORIES
-import code.name.monkey.retromusic.NOW_PLAYING_SCREEN_ID
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.SCREEN_ON_LYRICS
-import code.name.monkey.retromusic.SWIPE_ANYWHERE_NOW_PLAYING
-import code.name.monkey.retromusic.SWIPE_DOWN_DISMISS
-import code.name.monkey.retromusic.TAB_TEXT_MODE
-import code.name.monkey.retromusic.TOGGLE_ADD_CONTROLS
-import code.name.monkey.retromusic.TOGGLE_FULL_SCREEN
-import code.name.monkey.retromusic.TOGGLE_VOLUME
-import code.name.monkey.retromusic.activities.PermissionActivity
-import code.name.monkey.retromusic.databinding.SlidingMusicPanelLayoutBinding
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.fragments.NowPlayingScreen
-import code.name.monkey.retromusic.fragments.NowPlayingScreen.*
-import code.name.monkey.retromusic.fragments.base.AbsPlayerFragment
-import code.name.monkey.retromusic.fragments.other.MiniPlayerFragment
-import code.name.monkey.retromusic.fragments.player.adaptive.AdaptiveFragment
-import code.name.monkey.retromusic.fragments.player.blur.BlurPlayerFragment
-import code.name.monkey.retromusic.fragments.player.card.CardFragment
-import code.name.monkey.retromusic.fragments.player.cardblur.CardBlurFragment
-import code.name.monkey.retromusic.fragments.player.circle.CirclePlayerFragment
-import code.name.monkey.retromusic.fragments.player.classic.ClassicPlayerFragment
-import code.name.monkey.retromusic.fragments.player.color.ColorFragment
-import code.name.monkey.retromusic.fragments.player.fit.FitFragment
-import code.name.monkey.retromusic.fragments.player.flat.FlatPlayerFragment
-import code.name.monkey.retromusic.fragments.player.full.FullPlayerFragment
-import code.name.monkey.retromusic.fragments.player.gradient.GradientPlayerFragment
-import code.name.monkey.retromusic.fragments.player.material.MaterialFragment
-import code.name.monkey.retromusic.fragments.player.md3.MD3PlayerFragment
-import code.name.monkey.retromusic.fragments.player.normal.PlayerFragment
-import code.name.monkey.retromusic.fragments.player.peek.PeekPlayerFragment
-import code.name.monkey.retromusic.fragments.player.plain.PlainPlayerFragment
-import code.name.monkey.retromusic.fragments.player.simple.SimplePlayerFragment
-import code.name.monkey.retromusic.fragments.player.tiny.TinyPlayerFragment
-import code.name.monkey.retromusic.fragments.queue.PlayingQueueFragment
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.model.CategoryInfo
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.ViewUtil
-import code.name.monkey.retromusic.util.logD
-import com.google.android.material.bottomnavigation.BottomNavigationView
-import com.google.android.material.bottomsheet.BottomSheetBehavior
-import com.google.android.material.bottomsheet.BottomSheetBehavior.BottomSheetCallback
-import com.google.android.material.bottomsheet.BottomSheetBehavior.STATE_COLLAPSED
-import com.google.android.material.bottomsheet.BottomSheetBehavior.STATE_DRAGGING
-import com.google.android.material.bottomsheet.BottomSheetBehavior.STATE_EXPANDED
-import com.google.android.material.bottomsheet.BottomSheetBehavior.STATE_HIDDEN
-import com.google.android.material.bottomsheet.BottomSheetBehavior.STATE_SETTLING
-import com.google.android.material.bottomsheet.BottomSheetBehavior.from
-import org.koin.androidx.viewmodel.ext.android.viewModel
-
-
-abstract class AbsSlidingMusicPanelActivity : AbsMusicServiceActivity(),
- SharedPreferences.OnSharedPreferenceChangeListener {
- companion object {
- val TAG: String = AbsSlidingMusicPanelActivity::class.java.simpleName
- }
-
- var fromNotification = false
- private var windowInsets: WindowInsetsCompat? = null
- protected val libraryViewModel by viewModel()
- private lateinit var bottomSheetBehavior: BottomSheetBehavior
- private lateinit var playerFragment: AbsPlayerFragment
- private var miniPlayerFragment: MiniPlayerFragment? = null
- private var nowPlayingScreen: NowPlayingScreen? = null
- private var taskColor: Int = 0
- private var paletteColor: Int = Color.WHITE
- private var navigationBarColor = 0
-
- private val panelState: Int
- get() = bottomSheetBehavior.state
- private lateinit var binding: SlidingMusicPanelLayoutBinding
- private var isInOneTabMode = false
-
- private var navigationBarColorAnimator: ValueAnimator? = null
- private val argbEvaluator: ArgbEvaluator = ArgbEvaluator()
-
- private val onBackPressedCallback = object : OnBackPressedCallback(true) {
- override fun handleOnBackPressed() {
- println("Handle back press ${bottomSheetBehavior.state}")
- if (!handleBackPress()) {
- remove()
- onBackPressedDispatcher.onBackPressed()
- }
- }
- }
-
- private val bottomSheetCallbackList by lazy {
- object : BottomSheetCallback() {
-
- override fun onSlide(bottomSheet: View, slideOffset: Float) {
- setMiniPlayerAlphaProgress(slideOffset)
- navigationBarColorAnimator?.cancel()
- setNavigationBarColorPreOreo(
- argbEvaluator.evaluate(
- slideOffset,
- surfaceColor(),
- navigationBarColor
- ) as Int
- )
- }
-
- override fun onStateChanged(bottomSheet: View, newState: Int) {
- onBackPressedCallback.isEnabled = newState == STATE_EXPANDED
- when (newState) {
- STATE_EXPANDED -> {
- onPanelExpanded()
- if (PreferenceUtil.lyricsScreenOn && PreferenceUtil.showLyrics) {
- keepScreenOn(true)
- }
- }
-
- STATE_COLLAPSED -> {
- onPanelCollapsed()
- if ((PreferenceUtil.lyricsScreenOn && PreferenceUtil.showLyrics) || !PreferenceUtil.isScreenOnEnabled) {
- keepScreenOn(false)
- }
- }
-
- STATE_SETTLING, STATE_DRAGGING -> {
- if (fromNotification) {
- binding.navigationView.bringToFront()
- fromNotification = false
- }
- }
-
- STATE_HIDDEN -> {
- MusicPlayerRemote.clearQueue()
- }
-
- else -> {
- logD("Do a flip")
- }
- }
- }
- }
- }
-
- fun getBottomSheetBehavior() = bottomSheetBehavior
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- if (!hasPermissions()) {
- startActivity(Intent(this, PermissionActivity::class.java))
- finish()
- }
- binding = SlidingMusicPanelLayoutBinding.inflate(layoutInflater)
- setContentView(binding.root)
- binding.root.setOnApplyWindowInsetsListener { _, insets ->
- windowInsets = WindowInsetsCompat.toWindowInsetsCompat(insets)
- insets
- }
- chooseFragmentForTheme()
- setupSlidingUpPanel()
- setupBottomSheet()
- updateColor()
- if (!PreferenceUtil.materialYou) {
- binding.slidingPanel.backgroundTintList = ColorStateList.valueOf(darkAccentColor())
- navigationView.backgroundTintList = ColorStateList.valueOf(darkAccentColor())
- }
-
- navigationBarColor = surfaceColor()
-
- onBackPressedDispatcher.addCallback(onBackPressedCallback)
- }
-
- private fun setupBottomSheet() {
- bottomSheetBehavior = from(binding.slidingPanel)
- bottomSheetBehavior.addBottomSheetCallback(bottomSheetCallbackList)
- bottomSheetBehavior.isHideable = PreferenceUtil.swipeDownToDismiss
- bottomSheetBehavior.significantVelocityThreshold = 300
- setMiniPlayerAlphaProgress(0F)
- }
-
- override fun onResume() {
- super.onResume()
- PreferenceUtil.registerOnSharedPreferenceChangedListener(this)
- if (nowPlayingScreen != PreferenceUtil.nowPlayingScreen) {
- postRecreate()
- }
- if (bottomSheetBehavior.state == STATE_EXPANDED) {
- setMiniPlayerAlphaProgress(1f)
- }
- }
-
- override fun onDestroy() {
- super.onDestroy()
- bottomSheetBehavior.removeBottomSheetCallback(bottomSheetCallbackList)
- PreferenceUtil.unregisterOnSharedPreferenceChangedListener(this)
- }
-
- override fun onSharedPreferenceChanged(sharedPreferences: SharedPreferences?, key: String?) {
- when (key) {
- SWIPE_DOWN_DISMISS -> {
- bottomSheetBehavior.isHideable = PreferenceUtil.swipeDownToDismiss
- }
-
- TOGGLE_ADD_CONTROLS -> {
- miniPlayerFragment?.setUpButtons()
- }
-
- NOW_PLAYING_SCREEN_ID -> {
- chooseFragmentForTheme()
- binding.slidingPanel.updateLayoutParams {
- height = if (nowPlayingScreen != Peek) {
- ViewGroup.LayoutParams.MATCH_PARENT
- } else {
- ViewGroup.LayoutParams.WRAP_CONTENT
- }
- onServiceConnected()
- }
- }
-
- ALBUM_COVER_TRANSFORM, CAROUSEL_EFFECT,
- ALBUM_COVER_STYLE, TOGGLE_VOLUME, EXTRA_SONG_INFO, CIRCLE_PLAY_BUTTON,
- -> {
- chooseFragmentForTheme()
- onServiceConnected()
- }
-
- SWIPE_ANYWHERE_NOW_PLAYING -> {
- playerFragment.addSwipeDetector()
- }
-
- ADAPTIVE_COLOR_APP -> {
- if (PreferenceUtil.nowPlayingScreen in listOf(Normal, Material, Flat)) {
- chooseFragmentForTheme()
- onServiceConnected()
- }
- }
-
- LIBRARY_CATEGORIES -> {
- updateTabs()
- }
-
- TAB_TEXT_MODE -> {
- navigationView.labelVisibilityMode = PreferenceUtil.tabTitleMode
- }
-
- TOGGLE_FULL_SCREEN -> {
- recreate()
- }
-
- SCREEN_ON_LYRICS -> {
- keepScreenOn(bottomSheetBehavior.state == STATE_EXPANDED && PreferenceUtil.lyricsScreenOn && PreferenceUtil.showLyrics || PreferenceUtil.isScreenOnEnabled)
- }
-
- KEEP_SCREEN_ON -> {
- maybeSetScreenOn()
- }
- }
- }
-
- fun collapsePanel() {
- bottomSheetBehavior.state = STATE_COLLAPSED
- }
-
- fun expandPanel() {
- bottomSheetBehavior.state = STATE_EXPANDED
- }
-
- private fun setMiniPlayerAlphaProgress(progress: Float) {
- if (progress < 0) return
- val alpha = 1 - progress
- miniPlayerFragment?.view?.alpha = 1 - (progress / 0.2F)
- miniPlayerFragment?.view?.isGone = alpha == 0f
- if (!isLandscape) {
- binding.navigationView.translationY = progress * 500
- binding.navigationView.alpha = alpha
- }
- binding.playerFragmentContainer.alpha = (progress - 0.2F) / 0.2F
- }
-
- private fun animateNavigationBarColor(color: Int) {
- if (VersionUtils.hasOreo()) return
- navigationBarColorAnimator?.cancel()
- navigationBarColorAnimator = ValueAnimator
- .ofArgb(window.navigationBarColor, color).apply {
- duration = ViewUtil.RETRO_MUSIC_ANIM_TIME.toLong()
- interpolator = PathInterpolator(0.4f, 0f, 1f, 1f)
- addUpdateListener { animation: ValueAnimator ->
- setNavigationBarColorPreOreo(
- animation.animatedValue as Int
- )
- }
- start()
- }
- }
-
- open fun onPanelCollapsed() {
- setMiniPlayerAlphaProgress(0F)
- // restore values
- animateNavigationBarColor(surfaceColor())
- setLightStatusBarAuto()
- setLightNavigationBarAuto()
- setTaskDescriptionColor(taskColor)
- //playerFragment?.onHide()
- }
-
- open fun onPanelExpanded() {
- setMiniPlayerAlphaProgress(1F)
- onPaletteColorChanged()
- //playerFragment?.onShow()
- }
-
- private fun setupSlidingUpPanel() {
- binding.slidingPanel.viewTreeObserver.addOnGlobalLayoutListener(object :
- ViewTreeObserver.OnGlobalLayoutListener {
- override fun onGlobalLayout() {
- binding.slidingPanel.viewTreeObserver.removeOnGlobalLayoutListener(this)
- if (nowPlayingScreen != Peek) {
- binding.slidingPanel.updateLayoutParams {
- height = ViewGroup.LayoutParams.MATCH_PARENT
- }
- }
- when (panelState) {
- STATE_EXPANDED -> onPanelExpanded()
- STATE_COLLAPSED -> onPanelCollapsed()
- else -> {
- // playerFragment!!.onHide()
- }
- }
- }
- })
- }
-
- val navigationView get() = binding.navigationView
-
- val slidingPanel get() = binding.slidingPanel
-
- val isBottomNavVisible get() = navigationView.isVisible && navigationView is BottomNavigationView
-
- override fun onServiceConnected() {
- super.onServiceConnected()
- hideBottomSheet(false)
- }
-
- override fun onQueueChanged() {
- super.onQueueChanged()
- // Mini player should be hidden in Playing Queue
- // it may pop up if hideBottomSheet is called
- if (currentFragment(R.id.fragment_container) !is PlayingQueueFragment) {
- hideBottomSheet(MusicPlayerRemote.playingQueue.isEmpty())
- }
- }
-
- private fun handleBackPress(): Boolean {
- if (panelState == STATE_EXPANDED) {
- collapsePanel()
- return true
- }
- return false
- }
-
- private fun onPaletteColorChanged() {
- if (panelState == STATE_EXPANDED) {
- navigationBarColor = surfaceColor()
- setTaskDescColor(paletteColor)
- val isColorLight = paletteColor.isColorLight
- if (PreferenceUtil.isAdaptiveColor && (nowPlayingScreen == Normal || nowPlayingScreen == Flat || nowPlayingScreen == Material)) {
- setLightNavigationBar(true)
- setLightStatusBar(isColorLight)
- } else if (nowPlayingScreen == Card || nowPlayingScreen == Blur || nowPlayingScreen == BlurCard) {
- animateNavigationBarColor(Color.BLACK)
- navigationBarColor = Color.BLACK
- setLightStatusBar(false)
- setLightNavigationBar(true)
- } else if (nowPlayingScreen == Color || nowPlayingScreen == Tiny || nowPlayingScreen == Gradient) {
- animateNavigationBarColor(paletteColor)
- navigationBarColor = paletteColor
- setLightNavigationBar(isColorLight)
- setLightStatusBar(isColorLight)
- } else if (nowPlayingScreen == Full) {
- animateNavigationBarColor(paletteColor)
- navigationBarColor = paletteColor
- setLightNavigationBar(isColorLight)
- setLightStatusBar(false)
- } else if (nowPlayingScreen == Classic) {
- setLightStatusBar(false)
- } else if (nowPlayingScreen == Fit) {
- setLightStatusBar(false)
- }
- }
- }
-
- private fun setTaskDescColor(color: Int) {
- taskColor = color
- if (panelState == STATE_COLLAPSED) {
- setTaskDescriptionColor(color)
- }
- }
-
- fun updateTabs() {
- binding.navigationView.menu.clear()
- val currentTabs: List = PreferenceUtil.libraryCategory
- for (tab in currentTabs) {
- if (tab.visible) {
- val menu = tab.category
- binding.navigationView.menu.add(0, menu.id, 0, menu.stringRes)
- .setIcon(menu.icon)
- }
- }
- if (binding.navigationView.menu.size() == 1) {
- isInOneTabMode = true
- binding.navigationView.isVisible = false
- } else {
- isInOneTabMode = false
- }
- }
-
- private fun updateColor() {
- libraryViewModel.paletteColor.observe(this) { color ->
- this.paletteColor = color
- onPaletteColorChanged()
- }
- }
-
- fun setBottomNavVisibility(
- visible: Boolean,
- animate: Boolean = false,
- hideBottomSheet: Boolean = MusicPlayerRemote.playingQueue.isEmpty(),
- ) {
- if (!ViewCompat.isLaidOut(navigationView)) {
- return
- }
- if (isInOneTabMode) {
- hideBottomSheet(
- hide = hideBottomSheet,
- animate = animate,
- isBottomNavVisible = false
- )
- return
- }
- if (visible xor navigationView.isVisible) {
- val mAnimate = animate && bottomSheetBehavior.state == STATE_COLLAPSED
- if (mAnimate) {
- if (visible) {
- binding.navigationView.bringToFront()
- binding.navigationView.show()
- } else {
- binding.navigationView.hide()
- }
- } else {
- binding.navigationView.isVisible = visible
- if (visible && bottomSheetBehavior.state != STATE_EXPANDED) {
- binding.navigationView.bringToFront()
- }
- }
- }
- hideBottomSheet(
- hide = hideBottomSheet,
- animate = animate,
- isBottomNavVisible = visible && navigationView is BottomNavigationView
- )
- }
-
- fun hideBottomSheet(
- hide: Boolean,
- animate: Boolean = false,
- isBottomNavVisible: Boolean = navigationView.isVisible && navigationView is BottomNavigationView,
- ) {
- val heightOfBar = windowInsets.getBottomInsets() + dip(R.dimen.mini_player_height)
- val heightOfBarWithTabs = heightOfBar + dip(R.dimen.bottom_nav_height)
- if (hide) {
- bottomSheetBehavior.peekHeight = -windowInsets.getBottomInsets()
- bottomSheetBehavior.state = STATE_COLLAPSED
- libraryViewModel.setFabMargin(
- this,
- if (isBottomNavVisible) dip(R.dimen.bottom_nav_height) else 0
- )
- } else {
- if (MusicPlayerRemote.playingQueue.isNotEmpty()) {
- binding.slidingPanel.elevation = 0F
- binding.navigationView.elevation = 5F
- if (isBottomNavVisible) {
- logD("List")
- if (animate) {
- bottomSheetBehavior.peekHeightAnimate(heightOfBarWithTabs)
- } else {
- bottomSheetBehavior.peekHeight = heightOfBarWithTabs
- }
- libraryViewModel.setFabMargin(
- this,
- dip(R.dimen.bottom_nav_mini_player_height)
- )
- } else {
- logD("Details")
- if (animate) {
- bottomSheetBehavior.peekHeightAnimate(heightOfBar).doOnEnd {
- binding.slidingPanel.bringToFront()
- }
- } else {
- bottomSheetBehavior.peekHeight = heightOfBar
- binding.slidingPanel.bringToFront()
- }
- libraryViewModel.setFabMargin(this, dip(R.dimen.mini_player_height))
- }
- }
- }
- }
-
- fun setAllowDragging(allowDragging: Boolean) {
- bottomSheetBehavior.isDraggable = allowDragging
- hideBottomSheet(false)
- }
-
- private fun chooseFragmentForTheme() {
- nowPlayingScreen = PreferenceUtil.nowPlayingScreen
-
- val fragment: AbsPlayerFragment = when (nowPlayingScreen) {
- Blur -> BlurPlayerFragment()
- Adaptive -> AdaptiveFragment()
- Normal -> PlayerFragment()
- Card -> CardFragment()
- BlurCard -> CardBlurFragment()
- Fit -> FitFragment()
- Flat -> FlatPlayerFragment()
- Full -> FullPlayerFragment()
- Plain -> PlainPlayerFragment()
- Simple -> SimplePlayerFragment()
- Material -> MaterialFragment()
- Color -> ColorFragment()
- Gradient -> GradientPlayerFragment()
- Tiny -> TinyPlayerFragment()
- Peek -> PeekPlayerFragment()
- Circle -> CirclePlayerFragment()
- Classic -> ClassicPlayerFragment()
- MD3 -> MD3PlayerFragment()
- else -> PlayerFragment()
- } // must extend AbsPlayerFragment
- supportFragmentManager.commit {
- replace(R.id.playerFragmentContainer, fragment)
- }
- supportFragmentManager.executePendingTransactions()
- playerFragment = whichFragment(R.id.playerFragmentContainer)
- miniPlayerFragment = whichFragment(R.id.miniPlayerFragment)
- miniPlayerFragment?.view?.setOnClickListener { expandPanel() }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsThemeActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsThemeActivity.kt
deleted file mode 100644
index 32b025f01..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/base/AbsThemeActivity.kt
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities.base
-
-import android.content.Context
-import android.os.Bundle
-import android.os.Handler
-import android.os.Looper
-import android.view.KeyEvent
-import androidx.appcompat.app.AppCompatDelegate
-import androidx.appcompat.app.AppCompatDelegate.setDefaultNightMode
-import androidx.core.os.LocaleListCompat
-import code.name.monkey.appthemehelper.common.ATHToolbarActivity
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.theme.getNightMode
-import code.name.monkey.retromusic.util.theme.getThemeResValue
-
-abstract class AbsThemeActivity : ATHToolbarActivity(), Runnable {
-
- private val handler = Handler(Looper.getMainLooper())
-
- override fun onCreate(savedInstanceState: Bundle?) {
- updateLocale()
- updateTheme()
- hideStatusBar()
- super.onCreate(savedInstanceState)
- setEdgeToEdgeOrImmersive()
- maybeSetScreenOn()
- setLightNavigationBarAuto()
- setLightStatusBarAuto(surfaceColor())
- if (VersionUtils.hasQ()) {
- window.decorView.isForceDarkAllowed = false
- }
- }
-
- private fun updateTheme() {
- setTheme(getThemeResValue())
- if (PreferenceUtil.materialYou) {
- setDefaultNightMode(getNightMode())
- }
-
- if (PreferenceUtil.isCustomFont) {
- setTheme(R.style.FontThemeOverlay)
- }
- }
-
- private fun updateLocale() {
- val localeCode = PreferenceUtil.languageCode
- if (PreferenceUtil.isLocaleAutoStorageEnabled) {
- AppCompatDelegate.setApplicationLocales(LocaleListCompat.forLanguageTags(localeCode))
- PreferenceUtil.isLocaleAutoStorageEnabled = true
- }
- }
-
- override fun onWindowFocusChanged(hasFocus: Boolean) {
- super.onWindowFocusChanged(hasFocus)
- if (hasFocus) {
- hideStatusBar()
- handler.removeCallbacks(this)
- handler.postDelayed(this, 300)
- } else {
- handler.removeCallbacks(this)
- }
- }
-
- override fun run() {
- setImmersiveFullscreen()
- }
-
- override fun onStop() {
- handler.removeCallbacks(this)
- super.onStop()
- }
-
- public override fun onDestroy() {
- super.onDestroy()
- exitFullscreen()
- }
-
- override fun onKeyDown(keyCode: Int, event: KeyEvent): Boolean {
- if (keyCode == KeyEvent.KEYCODE_VOLUME_DOWN || keyCode == KeyEvent.KEYCODE_VOLUME_UP) {
- handler.removeCallbacks(this)
- handler.postDelayed(this, 500)
- }
- return super.onKeyDown(keyCode, event)
- }
-
- override fun attachBaseContext(newBase: Context?) {
- super.attachBaseContext(newBase)
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/bugreport/BugReportActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/bugreport/BugReportActivity.kt
deleted file mode 100644
index e99881953..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/bugreport/BugReportActivity.kt
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities.bugreport
-
-import android.content.ClipData
-import android.content.ClipboardManager
-import android.content.Intent
-import android.os.Bundle
-import android.view.MenuItem
-import androidx.core.content.getSystemService
-import androidx.core.net.toUri
-import code.name.monkey.appthemehelper.util.TintHelper
-import code.name.monkey.appthemehelper.util.ToolbarContentTintHelper
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.base.AbsThemeActivity
-import code.name.monkey.retromusic.activities.bugreport.model.DeviceInfo
-import code.name.monkey.retromusic.databinding.ActivityBugReportBinding
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.setTaskDescriptionColorAuto
-import code.name.monkey.retromusic.extensions.showToast
-
-open class BugReportActivity : AbsThemeActivity() {
-
- private lateinit var binding: ActivityBugReportBinding
- private var deviceInfo: DeviceInfo? = null
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- binding = ActivityBugReportBinding.inflate(layoutInflater)
- setContentView(binding.root)
- setTaskDescriptionColorAuto()
-
- initViews()
-
- if (title.isNullOrEmpty()) setTitle(R.string.report_an_issue)
-
- deviceInfo = DeviceInfo(this)
- binding.cardDeviceInfo.airTextDeviceInfo.text = deviceInfo.toString()
- }
-
- private fun initViews() {
- val accentColor = accentColor()
- setSupportActionBar(binding.toolbar)
- ToolbarContentTintHelper.colorBackButton(binding.toolbar)
- supportActionBar?.setDisplayHomeAsUpEnabled(true)
-
- binding.cardDeviceInfo.airTextDeviceInfo.setOnClickListener { copyDeviceInfoToClipBoard() }
-
- TintHelper.setTintAuto(binding.sendFab, accentColor, true)
- binding.sendFab.setOnClickListener { reportIssue() }
- }
-
- private fun reportIssue() {
- copyDeviceInfoToClipBoard()
- val i = Intent(Intent.ACTION_VIEW)
- i.data = ISSUE_TRACKER_LINK.toUri()
- i.flags = Intent.FLAG_ACTIVITY_NEW_TASK
- startActivity(i)
- }
-
- private fun copyDeviceInfoToClipBoard() {
- val clipboard = getSystemService()
- val clip = ClipData.newPlainText(getString(R.string.device_info), deviceInfo?.toMarkdown())
- clipboard?.setPrimaryClip(clip)
- showToast(R.string.copied_device_info_to_clipboard)
- }
-
- override fun onOptionsItemSelected(item: MenuItem): Boolean {
- if (item.itemId == android.R.id.home) {
- onBackPressedDispatcher.onBackPressed()
- }
- return super.onOptionsItemSelected(item)
- }
-
- companion object {
- private const val ISSUE_TRACKER_LINK =
- "https://github.com/MuntashirAkon/Metro/issues/new"
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/bugreport/model/DeviceInfo.kt b/app/src/main/java/code/name/monkey/retromusic/activities/bugreport/model/DeviceInfo.kt
deleted file mode 100644
index 19aff73a2..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/bugreport/model/DeviceInfo.kt
+++ /dev/null
@@ -1,111 +0,0 @@
-package code.name.monkey.retromusic.activities.bugreport.model
-
-import android.annotation.SuppressLint
-import android.content.Context
-import android.content.pm.PackageManager
-import android.os.Build
-import androidx.annotation.IntRange
-import androidx.appcompat.app.AppCompatDelegate
-import androidx.core.content.pm.PackageInfoCompat
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.PreferenceUtil.isAdaptiveColor
-import code.name.monkey.retromusic.util.PreferenceUtil.nowPlayingScreen
-import java.util.*
-
-class DeviceInfo(context: Context) {
- @SuppressLint("NewApi")
- private val abis = Build.SUPPORTED_ABIS
-
- @SuppressLint("NewApi")
- private val abis32Bits = Build.SUPPORTED_32_BIT_ABIS
-
- @SuppressLint("NewApi")
- private val abis64Bits = Build.SUPPORTED_64_BIT_ABIS
- private val baseTheme: String
- private val brand = Build.BRAND
- private val buildID = Build.DISPLAY
- private val buildVersion = Build.VERSION.INCREMENTAL
- private val device = Build.DEVICE
- private val hardware = Build.HARDWARE
- private val isAdaptive: Boolean
- private val manufacturer = Build.MANUFACTURER
- private val model = Build.MODEL
- private val nowPlayingTheme: String
- private val product = Build.PRODUCT
- private val releaseVersion = Build.VERSION.RELEASE
-
- @IntRange(from = 0)
- private val sdkVersion = Build.VERSION.SDK_INT
- private var versionCode = 0L
- private var versionName: String? = null
- private val selectedLang: String
- fun toMarkdown(): String {
- return """
- Device info:
- ---
-
- App version $versionName
- App version code $versionCode
- Android build version $buildVersion
- Android release version $releaseVersion
- Android SDK version $sdkVersion
- Android build ID $buildID
- Device brand $brand
- Device manufacturer $manufacturer
- Device name $device
- Device model $model
- Device product name $product
- Device hardware name $hardware
- ABIs ${Arrays.toString(abis)}
- ABIs (32bit) ${Arrays.toString(abis32Bits)}
- ABIs (64bit) ${Arrays.toString(abis64Bits)}
- Language $selectedLang
-
-
- """.trimIndent()
- }
-
- override fun toString(): String {
- return """
- App version: $versionName
- App version code: $versionCode
- Android build version: $buildVersion
- Android release version: $releaseVersion
- Android SDK version: $sdkVersion
- Android build ID: $buildID
- Device brand: $brand
- Device manufacturer: $manufacturer
- Device name: $device
- Device model: $model
- Device product name: $product
- Device hardware name: $hardware
- ABIs: ${Arrays.toString(abis)}
- ABIs (32bit): ${Arrays.toString(abis32Bits)}
- ABIs (64bit): ${Arrays.toString(abis64Bits)}
- Base theme: $baseTheme
- Now playing theme: $nowPlayingTheme
- Adaptive: $isAdaptive
- System language: ${Locale.getDefault().toLanguageTag()}
- In-App Language: $selectedLang
- """.trimIndent()
- }
-
- init {
- val packageInfo = try {
- context.packageManager.getPackageInfo(context.packageName, 0)
- } catch (e: PackageManager.NameNotFoundException) {
- null
- }
- if (packageInfo != null) {
- versionCode = PackageInfoCompat.getLongVersionCode(packageInfo)
- versionName = packageInfo.versionName
- } else {
- versionCode = -1
- versionName = null
- }
- baseTheme = PreferenceUtil.baseTheme
- nowPlayingTheme = context.getString(nowPlayingScreen.titleRes)
- isAdaptive = isAdaptiveColor
- selectedLang = AppCompatDelegate.getApplicationLocales().toLanguageTags()
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/saf/SAFGuideActivity.java b/app/src/main/java/code/name/monkey/retromusic/activities/saf/SAFGuideActivity.java
deleted file mode 100644
index efd56210e..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/saf/SAFGuideActivity.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright (c) 2019 Hemanth Savarala.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it under
- * the terms of the GNU General Public License as published by
- * the Free Software Foundation either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- */
-
-package code.name.monkey.retromusic.activities.saf;
-
-import android.os.Build;
-import android.os.Bundle;
-
-import androidx.annotation.Nullable;
-
-import com.heinrichreimersoftware.materialintro.app.IntroActivity;
-import com.heinrichreimersoftware.materialintro.slide.SimpleSlide;
-
-import code.name.monkey.retromusic.R;
-
-/** Created by hemanths on 2019-07-31. */
-public class SAFGuideActivity extends IntroActivity {
-
- public static final int REQUEST_CODE_SAF_GUIDE = 98;
-
- @Override
- protected void onCreate(@Nullable Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- setButtonCtaVisible(false);
- setButtonNextVisible(false);
- setButtonBackVisible(false);
-
- setButtonCtaTintMode(BUTTON_CTA_TINT_MODE_TEXT);
-
- String title =
- String.format(getString(R.string.saf_guide_slide1_title), getString(R.string.app_name));
-
- addSlide(
- new SimpleSlide.Builder()
- .title(title)
- .description(
- Build.VERSION.SDK_INT <= Build.VERSION_CODES.N_MR1
- ? R.string.saf_guide_slide1_description_before_o
- : R.string.saf_guide_slide1_description)
- .image(R.drawable.saf_guide_1)
- .background(code.name.monkey.appthemehelper.R.color.md_deep_purple_300)
- .backgroundDark(code.name.monkey.appthemehelper.R.color.md_deep_purple_400)
- .layout(R.layout.fragment_simple_slide_large_image)
- .build());
- addSlide(
- new SimpleSlide.Builder()
- .title(R.string.saf_guide_slide2_title)
- .description(R.string.saf_guide_slide2_description)
- .image(R.drawable.saf_guide_2)
- .background(code.name.monkey.appthemehelper.R.color.md_deep_purple_500)
- .backgroundDark(code.name.monkey.appthemehelper.R.color.md_deep_purple_600)
- .layout(R.layout.fragment_simple_slide_large_image)
- .build());
- addSlide(
- new SimpleSlide.Builder()
- .title(R.string.saf_guide_slide3_title)
- .description(R.string.saf_guide_slide3_description)
- .image(R.drawable.saf_guide_3)
- .background(code.name.monkey.appthemehelper.R.color.md_deep_purple_700)
- .backgroundDark(code.name.monkey.appthemehelper.R.color.md_deep_purple_800)
- .layout(R.layout.fragment_simple_slide_large_image)
- .build());
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/saf/SAFRequestActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/saf/SAFRequestActivity.kt
deleted file mode 100644
index 1b389b9d2..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/saf/SAFRequestActivity.kt
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright (c) 2021 Bartlomiej Uliasz.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it under
- * the terms of the GNU General Public License as published by
- * the Free Software Foundation either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- */
-package code.name.monkey.retromusic.activities.saf
-
-import android.app.Activity
-import android.content.Intent
-import android.os.Bundle
-import code.name.monkey.retromusic.activities.saf.SAFGuideActivity.REQUEST_CODE_SAF_GUIDE
-import code.name.monkey.retromusic.util.SAFUtil
-
-/** Created by buliasz on 2021-02-07. */
-class SAFRequestActivity : Activity() {
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- val intent = Intent(this, code.name.monkey.retromusic.activities.saf.SAFGuideActivity::class.java)
- startActivityForResult(intent, REQUEST_CODE_SAF_GUIDE)
- }
-
- override fun onActivityResult(requestCode: Int, resultCode: Int, intent: Intent?) {
- super.onActivityResult(requestCode, resultCode, intent)
- when (requestCode) {
- REQUEST_CODE_SAF_GUIDE -> {
- SAFUtil.openTreePicker(this)
- }
- SAFUtil.REQUEST_SAF_PICK_TREE -> {
- if (resultCode == RESULT_OK) {
- SAFUtil.saveTreeUri(this, intent)
- }
- finish()
- }
- }
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/AlbumTagEditorActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/AlbumTagEditorActivity.kt
deleted file mode 100755
index 2c9013657..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/AlbumTagEditorActivity.kt
+++ /dev/null
@@ -1,219 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities.tageditor
-
-import android.app.Activity
-import android.content.res.ColorStateList
-import android.graphics.Bitmap
-import android.graphics.BitmapFactory
-import android.graphics.Color
-import android.graphics.drawable.Drawable
-import android.net.Uri
-import android.os.Bundle
-import android.transition.Slide
-import android.view.LayoutInflater
-import android.widget.ImageView
-import android.widget.Toast
-import androidx.core.widget.doAfterTextChanged
-import code.name.monkey.appthemehelper.util.MaterialValueHelper
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.ActivityAlbumTagEditorBinding
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.palette.BitmapPaletteWrapper
-import code.name.monkey.retromusic.model.ArtworkInfo
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.ImageUtil
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.RetroColorUtil.generatePalette
-import code.name.monkey.retromusic.util.RetroColorUtil.getColor
-import code.name.monkey.retromusic.util.logD
-import com.bumptech.glide.Glide
-import com.bumptech.glide.load.engine.DiskCacheStrategy
-import com.bumptech.glide.request.target.ImageViewTarget
-import com.bumptech.glide.request.transition.Transition
-import com.google.android.material.shape.MaterialShapeDrawable
-import org.jaudiotagger.tag.FieldKey
-import java.util.*
-
-class AlbumTagEditorActivity : AbsTagEditorActivity() {
-
- override val bindingInflater: (LayoutInflater) -> ActivityAlbumTagEditorBinding =
- ActivityAlbumTagEditorBinding::inflate
-
- private fun windowEnterTransition() {
- val slide = Slide()
- slide.excludeTarget(R.id.appBarLayout, true)
- slide.excludeTarget(R.id.status_bar, true)
- slide.excludeTarget(android.R.id.statusBarBackground, true)
- slide.excludeTarget(android.R.id.navigationBarBackground, true)
-
- window.enterTransition = slide
- }
-
- private var albumArtBitmap: Bitmap? = null
- private var deleteAlbumArt: Boolean = false
-
- private fun setupToolbar() {
- setSupportActionBar(binding.toolbar)
- binding.appBarLayout?.statusBarForeground =
- MaterialShapeDrawable.createWithElevationOverlay(this)
- }
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- window.sharedElementsUseOverlay = true
- binding.imageContainer.transitionName = getString(R.string.transition_album_art)
- windowEnterTransition()
- setUpViews()
- setupToolbar()
- }
-
- private fun setUpViews() {
- fillViewsWithFileTags()
-
- binding.yearContainer.setTint(false)
- binding.genreContainer.setTint(false)
- binding.albumTitleContainer.setTint(false)
- binding.albumArtistContainer.setTint(false)
-
- binding.albumText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.albumArtistText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.genreTitle.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.yearTitle.appHandleColor().doAfterTextChanged { dataChanged() }
- }
-
- private fun fillViewsWithFileTags() {
- binding.albumText.setText(albumTitle)
- binding.albumArtistText.setText(albumArtistName)
- binding.genreTitle.setText(genreName)
- binding.yearTitle.setText(songYear)
- logD(albumTitle + albumArtistName)
- }
-
- override fun loadCurrentImage() {
- val bitmap = albumArt
- setImageBitmap(
- bitmap,
- getColor(
- generatePalette(bitmap),
- defaultFooterColor()
- )
- )
- deleteAlbumArt = false
- }
-
- private fun toastLoadingFailed() {
- showToast(R.string.could_not_download_album_cover)
- }
-
- override fun searchImageOnWeb() {
- searchWebFor(binding.albumText.text.toString(), binding.albumArtistText.text.toString())
- }
-
- override fun deleteImage() {
- setImageBitmap(
- BitmapFactory.decodeResource(resources, R.drawable.default_audio_art),
- defaultFooterColor()
- )
- deleteAlbumArt = true
- dataChanged()
- }
-
- override fun loadImageFromFile(selectedFile: Uri?) {
- Glide.with(this@AlbumTagEditorActivity)
- .asBitmapPalette()
- .load(selectedFile)
- .diskCacheStrategy(DiskCacheStrategy.NONE).skipMemoryCache(true)
- .into(object : ImageViewTarget(binding.editorImage) {
- override fun onResourceReady(
- resource: BitmapPaletteWrapper,
- transition: Transition?
- ) {
- getColor(resource.palette, Color.TRANSPARENT)
- albumArtBitmap = resource.bitmap?.let { ImageUtil.resizeBitmap(it, 2048) }
- setImageBitmap(
- albumArtBitmap,
- getColor(
- resource.palette,
- defaultFooterColor()
- )
- )
- deleteAlbumArt = false
- dataChanged()
- setResult(Activity.RESULT_OK)
- }
-
- override fun onLoadFailed(errorDrawable: Drawable?) {
- super.onLoadFailed(errorDrawable)
- showToast(R.string.error_load_failed, Toast.LENGTH_LONG)
- }
-
- override fun setResource(resource: BitmapPaletteWrapper?) {}
- })
- }
-
- override fun save() {
- val fieldKeyValueMap = EnumMap(FieldKey::class.java)
- fieldKeyValueMap[FieldKey.ALBUM] = binding.albumText.text.toString()
- // android seems not to recognize album_artist field so we additionally write the normal artist field
- fieldKeyValueMap[FieldKey.ARTIST] = binding.albumArtistText.text.toString()
- fieldKeyValueMap[FieldKey.ALBUM_ARTIST] = binding.albumArtistText.text.toString()
- fieldKeyValueMap[FieldKey.GENRE] = binding.genreTitle.text.toString()
- fieldKeyValueMap[FieldKey.YEAR] = binding.yearTitle.text.toString()
-
- writeValuesToFiles(
- fieldKeyValueMap,
- when {
- deleteAlbumArt -> ArtworkInfo(id, null)
- albumArtBitmap == null -> null
- else -> ArtworkInfo(id, albumArtBitmap!!)
- }
- )
- }
-
- override fun getSongPaths(): List {
- return repository.albumById(id).songs
- .map(Song::data)
- }
-
- override fun getSongUris(): List = repository.albumById(id).songs.map {
- MusicUtil.getSongFileUri(it.id)
- }
-
- override fun setColors(color: Int) {
- super.setColors(color)
- saveFab.backgroundTintList = ColorStateList.valueOf(color)
- saveFab.backgroundTintList = ColorStateList.valueOf(color)
- ColorStateList.valueOf(
- MaterialValueHelper.getPrimaryTextColor(
- this,
- color.isColorLight
- )
- ).also {
- saveFab.iconTint = it
- saveFab.setTextColor(it)
- }
- }
-
-
- override val editorImage: ImageView
- get() = binding.editorImage
-
- companion object {
-
- val TAG: String = AlbumTagEditorActivity::class.java.simpleName
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/SongTagEditorActivity.kt b/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/SongTagEditorActivity.kt
deleted file mode 100755
index 93dd8a44f..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/SongTagEditorActivity.kt
+++ /dev/null
@@ -1,214 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.activities.tageditor
-
-import android.annotation.SuppressLint
-import android.app.Activity
-import android.content.res.ColorStateList
-import android.graphics.Bitmap
-import android.graphics.BitmapFactory
-import android.graphics.Color
-import android.graphics.drawable.Drawable
-import android.net.Uri
-import android.os.Bundle
-import android.view.LayoutInflater
-import android.widget.ImageView
-import android.widget.Toast
-import androidx.core.widget.doAfterTextChanged
-import code.name.monkey.appthemehelper.util.MaterialValueHelper
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.ActivitySongTagEditorBinding
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.palette.BitmapPaletteWrapper
-import code.name.monkey.retromusic.model.ArtworkInfo
-import code.name.monkey.retromusic.repository.SongRepository
-import code.name.monkey.retromusic.util.ImageUtil
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.RetroColorUtil
-import code.name.monkey.retromusic.util.logD
-import com.bumptech.glide.Glide
-import com.bumptech.glide.load.engine.DiskCacheStrategy
-import com.bumptech.glide.request.target.ImageViewTarget
-import com.bumptech.glide.request.transition.Transition
-import com.google.android.material.shape.MaterialShapeDrawable
-import org.jaudiotagger.tag.FieldKey
-import org.koin.android.ext.android.inject
-import java.util.*
-
-class SongTagEditorActivity : AbsTagEditorActivity() {
-
- override val bindingInflater: (LayoutInflater) -> ActivitySongTagEditorBinding =
- ActivitySongTagEditorBinding::inflate
-
-
- private val songRepository by inject()
-
- private var albumArtBitmap: Bitmap? = null
- private var deleteAlbumArt: Boolean = false
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- setUpViews()
- setSupportActionBar(binding.toolbar)
- binding.appBarLayout?.statusBarForeground =
- MaterialShapeDrawable.createWithElevationOverlay(this)
- }
-
- @SuppressLint("ClickableViewAccessibility")
- private fun setUpViews() {
- fillViewsWithFileTags()
- binding.songTextContainer.setTint(false)
- binding.composerContainer.setTint(false)
- binding.albumTextContainer.setTint(false)
- binding.artistContainer.setTint(false)
- binding.albumArtistContainer.setTint(false)
- binding.yearContainer.setTint(false)
- binding.genreContainer.setTint(false)
- binding.trackNumberContainer.setTint(false)
- binding.discNumberContainer.setTint(false)
- binding.lyricsContainer.setTint(false)
-
- binding.songText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.albumText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.albumArtistText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.artistText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.genreText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.yearText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.trackNumberText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.discNumberText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.lyricsText.appHandleColor().doAfterTextChanged { dataChanged() }
- binding.songComposerText.appHandleColor().doAfterTextChanged { dataChanged() }
- }
-
- private fun fillViewsWithFileTags() {
- binding.songText.setText(songTitle)
- binding.albumArtistText.setText(albumArtist)
- binding.albumText.setText(albumTitle)
- binding.artistText.setText(artistName)
- binding.genreText.setText(genreName)
- binding.yearText.setText(songYear)
- binding.trackNumberText.setText(trackNumber)
- binding.discNumberText.setText(discNumber)
- binding.lyricsText.setText(lyrics)
- binding.songComposerText.setText(composer)
- logD(songTitle + songYear)
- }
-
- override fun loadCurrentImage() {
- val bitmap = albumArt
- setImageBitmap(
- bitmap,
- RetroColorUtil.getColor(
- RetroColorUtil.generatePalette(bitmap),
- defaultFooterColor()
- )
- )
- deleteAlbumArt = false
- }
-
- override fun searchImageOnWeb() {
- searchWebFor(binding.songText.text.toString(), binding.artistText.text.toString())
- }
-
- override fun deleteImage() {
- setImageBitmap(
- BitmapFactory.decodeResource(resources, R.drawable.default_audio_art),
- defaultFooterColor()
- )
- deleteAlbumArt = true
- dataChanged()
- }
-
- override fun setColors(color: Int) {
- super.setColors(color)
- saveFab.backgroundTintList = ColorStateList.valueOf(color)
- ColorStateList.valueOf(
- MaterialValueHelper.getPrimaryTextColor(
- this,
- color.isColorLight
- )
- ).also {
- saveFab.iconTint = it
- saveFab.setTextColor(it)
- }
- }
-
- override fun save() {
- val fieldKeyValueMap = EnumMap(FieldKey::class.java)
- fieldKeyValueMap[FieldKey.TITLE] = binding.songText.text.toString()
- fieldKeyValueMap[FieldKey.ALBUM] = binding.albumText.text.toString()
- fieldKeyValueMap[FieldKey.ARTIST] = binding.artistText.text.toString()
- fieldKeyValueMap[FieldKey.GENRE] = binding.genreText.text.toString()
- fieldKeyValueMap[FieldKey.YEAR] = binding.yearText.text.toString()
- fieldKeyValueMap[FieldKey.TRACK] = binding.trackNumberText.text.toString()
- fieldKeyValueMap[FieldKey.DISC_NO] = binding.discNumberText.text.toString()
- fieldKeyValueMap[FieldKey.LYRICS] = binding.lyricsText.text.toString()
- fieldKeyValueMap[FieldKey.ALBUM_ARTIST] = binding.albumArtistText.text.toString()
- fieldKeyValueMap[FieldKey.COMPOSER] = binding.songComposerText.text.toString()
- writeValuesToFiles(
- fieldKeyValueMap, when {
- deleteAlbumArt -> ArtworkInfo(id, null)
- albumArtBitmap == null -> null
- else -> ArtworkInfo(id, albumArtBitmap!!)
- }
- )
- }
-
- override fun getSongPaths(): List = listOf(songRepository.song(id).data)
-
- override fun getSongUris(): List = listOf(MusicUtil.getSongFileUri(id))
-
- override fun loadImageFromFile(selectedFile: Uri?) {
- Glide.with(this@SongTagEditorActivity)
- .asBitmapPalette()
- .load(selectedFile)
- .diskCacheStrategy(DiskCacheStrategy.NONE)
- .skipMemoryCache(true)
- .into(object : ImageViewTarget(binding.editorImage) {
- override fun onResourceReady(
- resource: BitmapPaletteWrapper,
- transition: Transition?
- ) {
- RetroColorUtil.getColor(resource.palette, Color.TRANSPARENT)
- albumArtBitmap = resource.bitmap?.let { ImageUtil.resizeBitmap(it, 2048) }
- setImageBitmap(
- albumArtBitmap,
- RetroColorUtil.getColor(
- resource.palette,
- defaultFooterColor()
- )
- )
- deleteAlbumArt = false
- dataChanged()
- setResult(Activity.RESULT_OK)
- }
-
- override fun onLoadFailed(errorDrawable: Drawable?) {
- super.onLoadFailed(errorDrawable)
- showToast(R.string.error_load_failed, Toast.LENGTH_LONG)
- }
-
- override fun setResource(resource: BitmapPaletteWrapper?) {}
- })
- }
-
- companion object {
- val TAG: String = SongTagEditorActivity::class.java.simpleName
- }
-
- override val editorImage: ImageView
- get() = binding.editorImage
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/TagWriter.kt b/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/TagWriter.kt
deleted file mode 100644
index b9d5f28dd..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/activities/tageditor/TagWriter.kt
+++ /dev/null
@@ -1,204 +0,0 @@
-package code.name.monkey.retromusic.activities.tageditor
-
-import android.app.Activity
-import android.content.Context
-import android.graphics.Bitmap
-import android.media.MediaScannerConnection
-import android.os.Build
-import android.util.Log
-import androidx.annotation.RequiresApi
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.extensions.showToast
-import code.name.monkey.retromusic.misc.UpdateToastMediaScannerCompletionListener
-import code.name.monkey.retromusic.model.AudioTagInfo
-import code.name.monkey.retromusic.util.MusicUtil.createAlbumArtFile
-import code.name.monkey.retromusic.util.MusicUtil.deleteAlbumArt
-import code.name.monkey.retromusic.util.MusicUtil.insertAlbumArt
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.withContext
-import org.jaudiotagger.audio.AudioFileIO
-import org.jaudiotagger.audio.exceptions.CannotReadException
-import org.jaudiotagger.audio.exceptions.CannotWriteException
-import org.jaudiotagger.audio.exceptions.InvalidAudioFrameException
-import org.jaudiotagger.audio.exceptions.ReadOnlyFileException
-import org.jaudiotagger.tag.FieldDataInvalidException
-import org.jaudiotagger.tag.TagException
-import org.jaudiotagger.tag.images.AndroidArtwork
-import org.jaudiotagger.tag.images.Artwork
-import java.io.File
-import java.io.IOException
-
-class TagWriter {
-
- companion object {
-
- suspend fun scan(context: Context, toBeScanned: List?) {
- if (toBeScanned.isNullOrEmpty()) {
- Log.i("scan", "scan: Empty")
- context.showToast("Scan file from folder")
- return
- }
- MediaScannerConnection.scanFile(
- context,
- toBeScanned.toTypedArray(),
- null,
- withContext(Dispatchers.Main) {
- if (context is Activity) UpdateToastMediaScannerCompletionListener(
- context, toBeScanned
- ) else null
- }
- )
- }
-
- suspend fun writeTagsToFiles(context: Context, info: AudioTagInfo) {
- withContext(Dispatchers.IO) {
- var artwork: Artwork? = null
- var albumArtFile: File? = null
- if (info.artworkInfo?.artwork != null) {
- try {
- albumArtFile = createAlbumArtFile(context).canonicalFile
- info.artworkInfo.artwork.compress(
- Bitmap.CompressFormat.JPEG,
- 100,
- albumArtFile.outputStream()
- )
- artwork = AndroidArtwork.createArtworkFromFile(albumArtFile)
- } catch (e: IOException) {
- e.printStackTrace()
- }
- }
- var wroteArtwork = false
- var deletedArtwork = false
- for (filePath in info.filePaths!!) {
- try {
- val audioFile = AudioFileIO.read(File(filePath))
- val tag = audioFile.tagOrCreateAndSetDefault
- if (info.fieldKeyValueMap != null) {
- for ((key, value) in info.fieldKeyValueMap) {
- try {
- tag.setField(key, value)
- } catch (e: FieldDataInvalidException) {
- withContext(Dispatchers.Main) {
- context.showToast(R.string.could_not_write_tags_to_file)
- }
- return@withContext listOf()
- } catch (e: Exception) {
- e.printStackTrace()
- }
- }
- }
- if (info.artworkInfo != null) {
- if (info.artworkInfo.artwork == null) {
- tag.deleteArtworkField()
- deletedArtwork = true
- } else if (artwork != null) {
- tag.deleteArtworkField()
- tag.setField(artwork)
- wroteArtwork = true
- }
- }
- audioFile.commit()
- } catch (e: CannotReadException) {
- e.printStackTrace()
- } catch (e: IOException) {
- e.printStackTrace()
- } catch (e: CannotWriteException) {
- e.printStackTrace()
- } catch (e: TagException) {
- e.printStackTrace()
- } catch (e: ReadOnlyFileException) {
- e.printStackTrace()
- } catch (e: InvalidAudioFrameException) {
- e.printStackTrace()
- }
- }
- if (wroteArtwork) {
- insertAlbumArt(context, info.artworkInfo!!.albumId, albumArtFile!!.path)
- } else if (deletedArtwork) {
- deleteAlbumArt(context, info.artworkInfo!!.albumId)
- }
- scan(context, info.filePaths)
- }
- }
-
- @RequiresApi(Build.VERSION_CODES.R)
- suspend fun writeTagsToFilesR(context: Context, info: AudioTagInfo): List =
- withContext(Dispatchers.IO) {
- val cacheFiles = mutableListOf()
- var artwork: Artwork? = null
- var albumArtFile: File? = null
- if (info.artworkInfo?.artwork != null) {
- try {
- albumArtFile = createAlbumArtFile(context).canonicalFile
- info.artworkInfo.artwork.compress(
- Bitmap.CompressFormat.JPEG,
- 100,
- albumArtFile.outputStream()
- )
- artwork = AndroidArtwork.createArtworkFromFile(albumArtFile)
- } catch (e: IOException) {
- e.printStackTrace()
- }
- }
- var wroteArtwork = false
- var deletedArtwork = false
- for (filePath in info.filePaths!!) {
- try {
- val originFile = File(filePath)
- val cacheFile = File(context.cacheDir, originFile.name)
- cacheFiles.add(cacheFile)
- originFile.inputStream().use { input ->
- cacheFile.outputStream().use { output ->
- input.copyTo(output)
- }
- }
- val audioFile = AudioFileIO.read(cacheFile)
- val tag = audioFile.tagOrCreateAndSetDefault
- if (info.fieldKeyValueMap != null) {
- for ((key, value) in info.fieldKeyValueMap) {
- try {
- tag.setField(key, value)
- } catch (e: FieldDataInvalidException) {
- withContext(Dispatchers.Main) {
- context.showToast(R.string.could_not_write_tags_to_file)
- }
- return@withContext listOf()
- } catch (e: Exception) {
- e.printStackTrace()
- }
- }
- }
- if (info.artworkInfo != null) {
- if (info.artworkInfo.artwork == null) {
- tag.deleteArtworkField()
- deletedArtwork = true
- } else if (artwork != null) {
- tag.deleteArtworkField()
- tag.setField(artwork)
- wroteArtwork = true
- }
- }
- audioFile.commit()
- } catch (e: CannotReadException) {
- e.printStackTrace()
- } catch (e: IOException) {
- e.printStackTrace()
- } catch (e: CannotWriteException) {
- e.printStackTrace()
- } catch (e: TagException) {
- e.printStackTrace()
- } catch (e: ReadOnlyFileException) {
- e.printStackTrace()
- } catch (e: InvalidAudioFrameException) {
- e.printStackTrace()
- }
- }
- if (wroteArtwork) {
- insertAlbumArt(context, info.artworkInfo!!.albumId, albumArtFile!!.path)
- } else if (deletedArtwork) {
- deleteAlbumArt(context, info.artworkInfo!!.albumId)
- }
- cacheFiles
- }
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/CategoryInfoAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/CategoryInfoAdapter.kt
deleted file mode 100644
index dd5cda1d3..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/CategoryInfoAdapter.kt
+++ /dev/null
@@ -1,116 +0,0 @@
-/*
- * Copyright (c) 2019 Hemanth Savarala.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it under
- * the terms of the GNU General Public License as published by
- * the Free Software Foundation either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- */
-package code.name.monkey.retromusic.adapter
-
-import android.annotation.SuppressLint
-import android.content.res.ColorStateList
-import android.view.LayoutInflater
-import android.view.MotionEvent
-import android.view.View
-import android.view.ViewGroup
-import androidx.recyclerview.widget.ItemTouchHelper
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.appthemehelper.ThemeStore.Companion.accentColor
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.PreferenceDialogLibraryCategoriesListitemBinding
-import code.name.monkey.retromusic.extensions.showToast
-import code.name.monkey.retromusic.model.CategoryInfo
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.SwipeAndDragHelper
-import code.name.monkey.retromusic.util.SwipeAndDragHelper.ActionCompletionContract
-
-class CategoryInfoAdapter : RecyclerView.Adapter(),
- ActionCompletionContract {
- var categoryInfos: MutableList =
- PreferenceUtil.libraryCategory.toMutableList()
- @SuppressLint("NotifyDataSetChanged")
- set(value) {
- field = value
- notifyDataSetChanged()
- }
- private val touchHelper: ItemTouchHelper
- fun attachToRecyclerView(recyclerView: RecyclerView?) {
- touchHelper.attachToRecyclerView(recyclerView)
- }
-
- override fun getItemCount(): Int {
- return categoryInfos.size
- }
-
- @SuppressLint("ClickableViewAccessibility")
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- val categoryInfo = categoryInfos[position]
- holder.binding.checkbox.isChecked = categoryInfo.visible
- holder.binding.title.text =
- holder.binding.title.resources.getString(categoryInfo.category.stringRes)
- holder.itemView.setOnClickListener {
- if (!(categoryInfo.visible && isLastCheckedCategory(categoryInfo))) {
- categoryInfo.visible = !categoryInfo.visible
- holder.binding.checkbox.isChecked = categoryInfo.visible
- } else {
- holder.itemView.context.showToast(R.string.you_have_to_select_at_least_one_category)
- }
- }
- holder.binding.dragView.setOnTouchListener { _: View?, event: MotionEvent ->
- if (event.actionMasked == MotionEvent.ACTION_DOWN) {
- touchHelper.startDrag(holder)
- }
- false
- }
- }
-
- override fun onCreateViewHolder(
- parent: ViewGroup, viewType: Int
- ): ViewHolder {
- return ViewHolder(
- PreferenceDialogLibraryCategoriesListitemBinding.inflate(
- LayoutInflater.from(
- parent.context
- ), parent, false
- )
- )
- }
-
- override fun onViewMoved(oldPosition: Int, newPosition: Int) {
- val categoryInfo = categoryInfos[oldPosition]
- categoryInfos.removeAt(oldPosition)
- categoryInfos.add(newPosition, categoryInfo)
- notifyItemMoved(oldPosition, newPosition)
- }
-
- private fun isLastCheckedCategory(categoryInfo: CategoryInfo): Boolean {
- if (categoryInfo.visible) {
- for (c in categoryInfos) {
- if (c !== categoryInfo && c.visible) {
- return false
- }
- }
- }
- return true
- }
-
- class ViewHolder(val binding: PreferenceDialogLibraryCategoriesListitemBinding) :
- RecyclerView.ViewHolder(binding.root) {
-
- init {
- binding.checkbox.buttonTintList =
- ColorStateList.valueOf(accentColor(binding.checkbox.context))
- }
- }
-
- init {
- val swipeAndDragHelper = SwipeAndDragHelper(this)
- touchHelper = ItemTouchHelper(swipeAndDragHelper)
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/GenreAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/GenreAdapter.kt
deleted file mode 100644
index b139a0af8..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/GenreAdapter.kt
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter
-
-import android.annotation.SuppressLint
-import android.view.LayoutInflater
-import android.view.View
-import android.view.ViewGroup
-import android.view.ViewOutlineProvider
-import androidx.fragment.app.FragmentActivity
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.ItemGenreBinding
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.RetroGlideExtension.songCoverOptions
-import code.name.monkey.retromusic.glide.RetroMusicColoredTarget
-import code.name.monkey.retromusic.interfaces.IGenreClickListener
-import code.name.monkey.retromusic.model.Genre
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.color.MediaNotificationProcessor
-import com.bumptech.glide.Glide
-import java.util.*
-
-/**
- * @author Hemanth S (h4h13).
- */
-
-class GenreAdapter(
- private val activity: FragmentActivity,
- var dataSet: List,
- private val listener: IGenreClickListener
-) : RecyclerView.Adapter() {
-
- init {
- this.setHasStableIds(true)
- }
-
- override fun getItemId(position: Int): Long {
- return dataSet[position].id
- }
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
- return ViewHolder(ItemGenreBinding.inflate(LayoutInflater.from(activity), parent, false))
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- val genre = dataSet[position]
- holder.binding.title.text = genre.name
- holder.binding.text.text = String.format(
- Locale.getDefault(),
- "%d %s",
- genre.songCount,
- if (genre.songCount > 1) activity.getString(R.string.songs) else activity.getString(R.string.song)
- )
- loadGenreImage(genre, holder)
- }
-
- private fun loadGenreImage(genre: Genre, holder: GenreAdapter.ViewHolder) {
- val genreSong = MusicUtil.songByGenre(genre.id)
- Glide.with(activity)
- .asBitmapPalette()
- .songCoverOptions(genreSong)
- .load(RetroGlideExtension.getSongModel(genreSong))
- .into(object : RetroMusicColoredTarget(holder.binding.image) {
- override fun onColorReady(colors: MediaNotificationProcessor) {
- setColors(holder, colors)
- }
- })
- // Just for a bit of shadow around image
- holder.binding.image.outlineProvider = ViewOutlineProvider.BOUNDS
- }
-
- private fun setColors(holder: ViewHolder, color: MediaNotificationProcessor) {
- holder.binding.imageContainerCard.setCardBackgroundColor(color.backgroundColor)
- holder.binding.title.setTextColor(color.primaryTextColor)
- holder.binding.text.setTextColor(color.secondaryTextColor)
- }
-
- override fun getItemCount(): Int {
- return dataSet.size
- }
-
- @SuppressLint("NotifyDataSetChanged")
- fun swapDataSet(list: List) {
- dataSet = list
- notifyDataSetChanged()
- }
-
- inner class ViewHolder(val binding: ItemGenreBinding) : RecyclerView.ViewHolder(binding.root),
- View.OnClickListener {
- override fun onClick(v: View?) {
- listener.onClickGenre(dataSet[layoutPosition], itemView)
- }
-
- init {
- itemView.setOnClickListener(this)
- }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/HomeAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/HomeAdapter.kt
deleted file mode 100644
index e3f809b5f..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/HomeAdapter.kt
+++ /dev/null
@@ -1,213 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter
-
-import android.annotation.SuppressLint
-import android.view.LayoutInflater
-import android.view.View
-import android.view.ViewGroup
-import androidx.appcompat.app.AppCompatActivity
-import androidx.appcompat.widget.AppCompatTextView
-import androidx.core.os.bundleOf
-import androidx.fragment.app.findFragment
-import androidx.navigation.findNavController
-import androidx.navigation.fragment.FragmentNavigatorExtras
-import androidx.recyclerview.widget.GridLayoutManager
-import androidx.recyclerview.widget.LinearLayoutManager
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.retromusic.*
-import code.name.monkey.retromusic.adapter.album.AlbumAdapter
-import code.name.monkey.retromusic.adapter.artist.ArtistAdapter
-import code.name.monkey.retromusic.adapter.song.SongAdapter
-import code.name.monkey.retromusic.fragments.home.HomeFragment
-import code.name.monkey.retromusic.interfaces.IAlbumClickListener
-import code.name.monkey.retromusic.interfaces.IArtistClickListener
-import code.name.monkey.retromusic.model.Album
-import code.name.monkey.retromusic.model.Artist
-import code.name.monkey.retromusic.model.Home
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.PreferenceUtil
-
-class HomeAdapter(private val activity: AppCompatActivity) :
- RecyclerView.Adapter(), IArtistClickListener, IAlbumClickListener {
-
- private var list = listOf()
-
- override fun getItemViewType(position: Int): Int {
- return list[position].homeSection
- }
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
- val layout =
- LayoutInflater.from(activity).inflate(R.layout.section_recycler_view, parent, false)
- return when (viewType) {
- RECENT_ARTISTS, TOP_ARTISTS -> ArtistViewHolder(layout)
- FAVOURITES -> PlaylistViewHolder(layout)
- TOP_ALBUMS, RECENT_ALBUMS -> AlbumViewHolder(layout)
- else -> {
- ArtistViewHolder(layout)
- }
- }
- }
-
- override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
- val home = list[position]
- when (getItemViewType(position)) {
- RECENT_ALBUMS -> {
- val viewHolder = holder as AlbumViewHolder
- viewHolder.bindView(home)
- viewHolder.clickableArea.setOnClickListener {
- it.findFragment().setSharedAxisXTransitions()
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.detailListFragment,
- bundleOf("type" to RECENT_ALBUMS)
- )
- }
- }
- TOP_ALBUMS -> {
- val viewHolder = holder as AlbumViewHolder
- viewHolder.bindView(home)
- viewHolder.clickableArea.setOnClickListener {
- it.findFragment().setSharedAxisXTransitions()
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.detailListFragment,
- bundleOf("type" to TOP_ALBUMS)
- )
- }
- }
- RECENT_ARTISTS -> {
- val viewHolder = holder as ArtistViewHolder
- viewHolder.bindView(home)
- viewHolder.clickableArea.setOnClickListener {
- it.findFragment().setSharedAxisXTransitions()
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.detailListFragment,
- bundleOf("type" to RECENT_ARTISTS)
- )
- }
- }
- TOP_ARTISTS -> {
- val viewHolder = holder as ArtistViewHolder
- viewHolder.bindView(home)
- viewHolder.clickableArea.setOnClickListener {
- it.findFragment().setSharedAxisXTransitions()
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.detailListFragment,
- bundleOf("type" to TOP_ARTISTS)
- )
- }
- }
- FAVOURITES -> {
- val viewHolder = holder as PlaylistViewHolder
- viewHolder.bindView(home)
- viewHolder.clickableArea.setOnClickListener {
- it.findFragment().setSharedAxisXTransitions()
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.detailListFragment,
- bundleOf("type" to FAVOURITES)
- )
- }
- }
- }
- }
-
- override fun getItemCount(): Int {
- return list.size
- }
-
- @SuppressLint("NotifyDataSetChanged")
- fun swapData(sections: List) {
- list = sections
- notifyDataSetChanged()
- }
-
- @Suppress("UNCHECKED_CAST")
- private inner class AlbumViewHolder(view: View) : AbsHomeViewItem(view) {
- fun bindView(home: Home) {
- title.setText(home.titleRes)
- recyclerView.apply {
- adapter = albumAdapter(home.arrayList as List)
- layoutManager = gridLayoutManager()
- }
- }
- }
-
- @Suppress("UNCHECKED_CAST")
- private inner class ArtistViewHolder(view: View) : AbsHomeViewItem(view) {
- fun bindView(home: Home) {
- title.setText(home.titleRes)
- recyclerView.apply {
- layoutManager = linearLayoutManager()
- adapter = artistsAdapter(home.arrayList as List)
- }
- }
- }
-
- @Suppress("UNCHECKED_CAST")
- private inner class PlaylistViewHolder(view: View) : AbsHomeViewItem(view) {
- fun bindView(home: Home) {
- title.setText(home.titleRes)
- recyclerView.apply {
- val songAdapter = SongAdapter(
- activity,
- home.arrayList as MutableList,
- R.layout.item_favourite_card
- )
- layoutManager = linearLayoutManager()
- adapter = songAdapter
- }
- }
- }
-
- open class AbsHomeViewItem(itemView: View) : RecyclerView.ViewHolder(itemView) {
- val recyclerView: RecyclerView = itemView.findViewById(R.id.recyclerView)
- val title: AppCompatTextView = itemView.findViewById(R.id.title)
- val clickableArea: ViewGroup = itemView.findViewById(R.id.clickable_area)
- }
-
- private fun artistsAdapter(artists: List) =
- ArtistAdapter(activity, artists, PreferenceUtil.homeArtistGridStyle, this)
-
- private fun albumAdapter(albums: List) =
- AlbumAdapter(activity, albums, PreferenceUtil.homeAlbumGridStyle, this)
-
- private fun gridLayoutManager() =
- GridLayoutManager(activity, 1, GridLayoutManager.HORIZONTAL, false)
-
- private fun linearLayoutManager() =
- LinearLayoutManager(activity, LinearLayoutManager.HORIZONTAL, false)
-
- override fun onArtist(artistId: Long, view: View) {
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.artistDetailsFragment,
- bundleOf(EXTRA_ARTIST_ID to artistId),
- null,
- FragmentNavigatorExtras(
- view to artistId.toString()
- )
- )
- }
-
- override fun onAlbumClick(albumId: Long, view: View) {
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.albumDetailsFragment,
- bundleOf(EXTRA_ALBUM_ID to albumId),
- null,
- FragmentNavigatorExtras(
- view to albumId.toString()
- )
- )
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/SearchAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/SearchAdapter.kt
deleted file mode 100644
index 22a60bd95..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/SearchAdapter.kt
+++ /dev/null
@@ -1,241 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter
-
-import android.annotation.SuppressLint
-import android.view.LayoutInflater
-import android.view.View
-import android.view.ViewGroup
-import androidx.core.os.bundleOf
-import androidx.core.view.isGone
-import androidx.core.view.isInvisible
-import androidx.core.view.isVisible
-import androidx.fragment.app.FragmentActivity
-import androidx.navigation.findNavController
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.appthemehelper.ThemeStore
-import code.name.monkey.retromusic.*
-import code.name.monkey.retromusic.adapter.base.MediaEntryViewHolder
-import code.name.monkey.retromusic.db.PlaylistWithSongs
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.albumCoverOptions
-import code.name.monkey.retromusic.glide.RetroGlideExtension.artistImageOptions
-import code.name.monkey.retromusic.glide.RetroGlideExtension.songCoverOptions
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.helper.menu.SongMenuHelper
-import code.name.monkey.retromusic.model.Album
-import code.name.monkey.retromusic.model.Artist
-import code.name.monkey.retromusic.model.Genre
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.MusicUtil
-import com.bumptech.glide.Glide
-import java.util.*
-
-class SearchAdapter(
- private val activity: FragmentActivity,
- private var dataSet: List
-) : RecyclerView.Adapter() {
-
- @SuppressLint("NotifyDataSetChanged")
- fun swapDataSet(dataSet: List) {
- this.dataSet = dataSet
- notifyDataSetChanged()
- }
-
- override fun getItemViewType(position: Int): Int {
- if (dataSet[position] is Album) return ALBUM
- if (dataSet[position] is Artist) return if ((dataSet[position] as Artist).isAlbumArtist) ALBUM_ARTIST else ARTIST
- if (dataSet[position] is Genre) return GENRE
- if (dataSet[position] is PlaylistWithSongs) return PLAYLIST
- return if (dataSet[position] is Song) SONG else HEADER
- }
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
- return when (viewType) {
- HEADER -> ViewHolder(
- LayoutInflater.from(activity).inflate(
- R.layout.sub_header,
- parent,
- false
- ), viewType
- )
-
- ALBUM, ARTIST, ALBUM_ARTIST -> ViewHolder(
- LayoutInflater.from(activity).inflate(
- R.layout.item_list_big,
- parent,
- false
- ), viewType
- )
-
- else -> ViewHolder(
- LayoutInflater.from(activity).inflate(R.layout.item_list, parent, false),
- viewType
- )
- }
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- when (getItemViewType(position)) {
- ALBUM -> {
- holder.imageTextContainer?.isVisible = true
- val album = dataSet[position] as Album
- holder.title?.text = album.title
- holder.text?.text = album.artistName
- Glide.with(activity).asDrawable().albumCoverOptions(album.safeGetFirstSong())
- .load(RetroGlideExtension.getSongModel(album.safeGetFirstSong()))
- .into(holder.image!!)
- }
-
- ARTIST -> {
- holder.imageTextContainer?.isVisible = true
- val artist = dataSet[position] as Artist
- holder.title?.text = artist.name
- holder.text?.text = MusicUtil.getArtistInfoString(activity, artist)
- Glide.with(activity).asDrawable().artistImageOptions(artist).load(
- RetroGlideExtension.getArtistModel(artist)
- ).into(holder.image!!)
- }
-
- SONG -> {
- holder.imageTextContainer?.isVisible = true
- val song = dataSet[position] as Song
- holder.title?.text = song.title
- holder.text?.text = song.albumName
- Glide.with(activity).asDrawable().songCoverOptions(song)
- .load(RetroGlideExtension.getSongModel(song)).into(holder.image!!)
- }
-
- GENRE -> {
- val genre = dataSet[position] as Genre
- holder.title?.text = genre.name
- holder.text?.text = String.format(
- Locale.getDefault(),
- "%d %s",
- genre.songCount,
- if (genre.songCount > 1) activity.getString(R.string.songs) else activity.getString(
- R.string.song
- )
- )
- }
-
- PLAYLIST -> {
- val playlist = dataSet[position] as PlaylistWithSongs
- holder.title?.text = playlist.playlistEntity.playlistName
- //holder.text?.text = MusicUtil.playlistInfoString(activity, playlist.songs)
- }
-
- ALBUM_ARTIST -> {
- holder.imageTextContainer?.isVisible = true
- val artist = dataSet[position] as Artist
- holder.title?.text = artist.name
- holder.text?.text = MusicUtil.getArtistInfoString(activity, artist)
- Glide.with(activity).asDrawable().artistImageOptions(artist).load(
- RetroGlideExtension.getArtistModel(artist)
- ).into(holder.image!!)
- }
-
- else -> {
- holder.title?.text = dataSet[position].toString()
- holder.title?.setTextColor(ThemeStore.accentColor(activity))
- }
- }
- }
-
- override fun getItemCount(): Int {
- return dataSet.size
- }
-
- inner class ViewHolder(itemView: View, itemViewType: Int) : MediaEntryViewHolder(itemView) {
- init {
- itemView.setOnLongClickListener(null)
- imageTextContainer?.isInvisible = true
- if (itemViewType == SONG) {
- imageTextContainer?.isGone = true
- menu?.isVisible = true
- menu?.setOnClickListener(object : SongMenuHelper.OnClickSongMenu(activity) {
- override val song: Song
- get() = dataSet[layoutPosition] as Song
- })
- } else {
- menu?.isVisible = false
- }
-
- when (itemViewType) {
- ALBUM -> setImageTransitionName(activity.getString(R.string.transition_album_art))
- ARTIST -> setImageTransitionName(activity.getString(R.string.transition_artist_image))
- else -> {
- val container = itemView.findViewById(R.id.imageContainer)
- container?.isVisible = false
- }
- }
- }
-
- override fun onClick(v: View?) {
- val item = dataSet[layoutPosition]
- when (itemViewType) {
- ALBUM -> {
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.albumDetailsFragment,
- bundleOf(EXTRA_ALBUM_ID to (item as Album).id)
- )
- }
-
- ARTIST -> {
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.artistDetailsFragment,
- bundleOf(EXTRA_ARTIST_ID to (item as Artist).id)
- )
- }
-
- ALBUM_ARTIST -> {
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.albumArtistDetailsFragment,
- bundleOf(EXTRA_ARTIST_NAME to (item as Artist).name)
- )
- }
-
- GENRE -> {
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.genreDetailsFragment,
- bundleOf(EXTRA_GENRE to (item as Genre))
- )
- }
-
- PLAYLIST -> {
- activity.findNavController(R.id.fragment_container).navigate(
- R.id.playlistDetailsFragment,
- bundleOf(EXTRA_PLAYLIST_ID to (item as PlaylistWithSongs).playlistEntity.playListId)
- )
- }
-
- SONG -> {
- MusicPlayerRemote.playNext(item as Song)
- MusicPlayerRemote.playNextSong()
- }
- }
- }
- }
-
- companion object {
- private const val HEADER = 0
- private const val ALBUM = 1
- private const val ARTIST = 2
- private const val SONG = 3
- private const val GENRE = 4
- private const val PLAYLIST = 5
- private const val ALBUM_ARTIST = 6
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/StorageAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/StorageAdapter.kt
deleted file mode 100644
index 98c2c632f..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/StorageAdapter.kt
+++ /dev/null
@@ -1,55 +0,0 @@
-package code.name.monkey.retromusic.adapter
-
-import android.view.LayoutInflater
-import android.view.View
-import android.view.ViewGroup
-import android.widget.TextView
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.retromusic.R
-import java.io.File
-
-class StorageAdapter(
- val storageList: List,
- val storageClickListener: StorageClickListener
-) :
- RecyclerView.Adapter() {
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
- return ViewHolder(
- LayoutInflater.from(parent.context).inflate(
- R.layout.item_storage,
- parent,
- false
- )
- )
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- holder.bindData(storageList[position])
- }
-
- override fun getItemCount(): Int {
- return storageList.size
- }
-
- inner class ViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
- val title: TextView = itemView.findViewById(R.id.title)
-
- fun bindData(storage: Storage) {
- title.text = storage.title
- }
-
- init {
- itemView.setOnClickListener { storageClickListener.onStorageClicked(storageList[bindingAdapterPosition]) }
- }
- }
-}
-
-interface StorageClickListener {
- fun onStorageClicked(storage: Storage)
-}
-
-class Storage {
- lateinit var title: String
- lateinit var file: File
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/album/HorizontalAlbumAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/album/HorizontalAlbumAdapter.kt
deleted file mode 100644
index 7a9f7fa6e..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/album/HorizontalAlbumAdapter.kt
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter.album
-
-import android.view.View
-import android.view.ViewGroup
-import androidx.fragment.app.FragmentActivity
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.albumCoverOptions
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.RetroMusicColoredTarget
-import code.name.monkey.retromusic.helper.HorizontalAdapterHelper
-import code.name.monkey.retromusic.interfaces.IAlbumClickListener
-import code.name.monkey.retromusic.model.Album
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.color.MediaNotificationProcessor
-import com.bumptech.glide.Glide
-
-class HorizontalAlbumAdapter(
- activity: FragmentActivity,
- dataSet: List,
- albumClickListener: IAlbumClickListener
-) : AlbumAdapter(
- activity, dataSet, HorizontalAdapterHelper.LAYOUT_RES, albumClickListener
-) {
-
- override fun createViewHolder(view: View, viewType: Int): ViewHolder {
- val params = view.layoutParams as ViewGroup.MarginLayoutParams
- HorizontalAdapterHelper.applyMarginToLayoutParams(activity, params, viewType)
- return ViewHolder(view)
- }
-
- override fun setColors(color: MediaNotificationProcessor, holder: ViewHolder) {
- // holder.title?.setTextColor(ATHUtil.resolveColor(activity, android.R.attr.textColorPrimary))
- // holder.text?.setTextColor(ATHUtil.resolveColor(activity, android.R.attr.textColorSecondary))
- }
-
- override fun loadAlbumCover(album: Album, holder: ViewHolder) {
- if (holder.image == null) return
- Glide.with(activity)
- .asBitmapPalette()
- .albumCoverOptions(album.safeGetFirstSong())
- .load(RetroGlideExtension.getSongModel(album.safeGetFirstSong()))
- .into(object : RetroMusicColoredTarget(holder.image!!) {
- override fun onColorReady(colors: MediaNotificationProcessor) {
- setColors(colors, holder)
- }
- })
- }
-
- override fun getAlbumText(album: Album): String {
- return MusicUtil.getYearString(album.year)
- }
-
- override fun getItemViewType(position: Int): Int {
- return HorizontalAdapterHelper.getItemViewType(position, itemCount)
- }
-
- override fun getItemCount(): Int {
- return dataSet.size
- }
-
- companion object {
- val TAG: String = AlbumAdapter::class.java.simpleName
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/artist/ArtistAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/artist/ArtistAdapter.kt
deleted file mode 100644
index e1ea2ca4c..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/artist/ArtistAdapter.kt
+++ /dev/null
@@ -1,186 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter.artist
-
-import android.annotation.SuppressLint
-import android.content.res.ColorStateList
-import android.content.res.Resources
-import android.view.LayoutInflater
-import android.view.MenuItem
-import android.view.View
-import android.view.ViewGroup
-import androidx.core.view.isVisible
-import androidx.fragment.app.FragmentActivity
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.adapter.base.AbsMultiSelectAdapter
-import code.name.monkey.retromusic.extensions.hide
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.artistImageOptions
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.RetroMusicColoredTarget
-import code.name.monkey.retromusic.helper.menu.SongsMenuHelper
-import code.name.monkey.retromusic.interfaces.IAlbumArtistClickListener
-import code.name.monkey.retromusic.interfaces.IArtistClickListener
-import code.name.monkey.retromusic.model.Artist
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.color.MediaNotificationProcessor
-import com.bumptech.glide.Glide
-import me.zhanghai.android.fastscroll.PopupTextProvider
-
-class ArtistAdapter(
- override val activity: FragmentActivity,
- var dataSet: List,
- var itemLayoutRes: Int,
- val IArtistClickListener: IArtistClickListener,
- val IAlbumArtistClickListener: IAlbumArtistClickListener? = null
-) : AbsMultiSelectAdapter(activity, R.menu.menu_media_selection),
- PopupTextProvider {
-
- var albumArtistsOnly = false
-
- init {
- this.setHasStableIds(true)
- }
-
- @SuppressLint("NotifyDataSetChanged")
- fun swapDataSet(dataSet: List) {
- this.dataSet = dataSet
- notifyDataSetChanged()
- albumArtistsOnly = PreferenceUtil.albumArtistsOnly
- }
-
- override fun getItemId(position: Int): Long {
- return dataSet[position].id
- }
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
- val view =
- try {
- LayoutInflater.from(activity).inflate(itemLayoutRes, parent, false)
- } catch (e: Resources.NotFoundException) {
- LayoutInflater.from(activity).inflate(R.layout.item_grid_circle, parent, false)
- }
- return createViewHolder(view)
- }
-
- private fun createViewHolder(view: View): ViewHolder {
- return ViewHolder(view)
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- val artist = dataSet[position]
- val isChecked = isChecked(artist)
- holder.itemView.isActivated = isChecked
- holder.title?.text = artist.name
- holder.text?.hide()
- val transitionName =
- if (albumArtistsOnly) artist.name else artist.id.toString()
- if (holder.imageContainer != null) {
- holder.imageContainer?.transitionName = transitionName
- } else {
- holder.image?.transitionName = transitionName
- }
- loadArtistImage(artist, holder)
- }
-
- private fun setColors(processor: MediaNotificationProcessor, holder: ViewHolder) {
- holder.mask?.backgroundTintList = ColorStateList.valueOf(processor.primaryTextColor)
- if (holder.paletteColorContainer != null) {
- holder.paletteColorContainer?.setBackgroundColor(processor.backgroundColor)
- holder.title?.setTextColor(processor.primaryTextColor)
- }
- holder.imageContainerCard?.setCardBackgroundColor(processor.backgroundColor)
- }
-
- private fun loadArtistImage(artist: Artist, holder: ViewHolder) {
- if (holder.image == null) {
- return
- }
- Glide.with(activity)
- .asBitmapPalette()
- .artistImageOptions(artist)
- .load(RetroGlideExtension.getArtistModel(artist))
- .transition(RetroGlideExtension.getDefaultTransition())
- .into(object : RetroMusicColoredTarget(holder.image!!) {
- override fun onColorReady(colors: MediaNotificationProcessor) {
- setColors(colors, holder)
- }
- })
- }
-
- override fun getItemCount(): Int {
- return dataSet.size
- }
-
- override fun getIdentifier(position: Int): Artist {
- return dataSet[position]
- }
-
- override fun getName(model: Artist): String {
- return model.name
- }
-
- override fun onMultipleItemAction(
- menuItem: MenuItem,
- selection: List
- ) {
- SongsMenuHelper.handleMenuClick(activity, getSongList(selection), menuItem.itemId)
- }
-
- private fun getSongList(artists: List): List {
- val songs = ArrayList()
- for (artist in artists) {
- songs.addAll(artist.songs) // maybe async in future?
- }
- return songs
- }
-
- override fun getPopupText(position: Int): String {
- return getSectionName(position)
- }
-
- private fun getSectionName(position: Int): String {
- return MusicUtil.getSectionName(dataSet[position].name)
- }
-
- inner class ViewHolder(itemView: View) : code.name.monkey.retromusic.adapter.base.MediaEntryViewHolder(itemView) {
-
- init {
- menu?.isVisible = false
- }
-
- override fun onClick(v: View?) {
- super.onClick(v)
- if (isInQuickSelectMode) {
- toggleChecked(layoutPosition)
- } else {
- val artist = dataSet[layoutPosition]
- image?.let {
- if (albumArtistsOnly && IAlbumArtistClickListener != null) {
- IAlbumArtistClickListener.onAlbumArtist(artist.name, imageContainer ?: it)
- } else {
- IArtistClickListener.onArtist(artist.id, imageContainer ?: it)
- }
- }
- }
- }
-
- override fun onLongClick(v: View?): Boolean {
- return toggleChecked(layoutPosition)
- }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/backup/BackupAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/backup/BackupAdapter.kt
deleted file mode 100644
index adfcecf1b..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/backup/BackupAdapter.kt
+++ /dev/null
@@ -1,65 +0,0 @@
-package code.name.monkey.retromusic.adapter.backup
-
-import android.annotation.SuppressLint
-import android.view.LayoutInflater
-import android.view.MenuItem
-import android.view.ViewGroup
-import androidx.appcompat.widget.PopupMenu
-import androidx.fragment.app.FragmentActivity
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.ItemListBackupBinding
-import java.io.File
-
-
-class BackupAdapter(
- val activity: FragmentActivity,
- var dataSet: MutableList,
- val backupClickedListener: BackupClickedListener
-) : RecyclerView.Adapter() {
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
- return ViewHolder(
- ItemListBackupBinding.inflate(LayoutInflater.from(activity), parent, false)
- )
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- holder.binding.title.text = dataSet[position].nameWithoutExtension
- }
-
- override fun getItemCount(): Int = dataSet.size
-
- @SuppressLint("NotifyDataSetChanged")
- fun swapDataset(dataSet: List) {
- this.dataSet = ArrayList(dataSet)
- notifyDataSetChanged()
- }
-
- inner class ViewHolder(val binding: ItemListBackupBinding) :
- RecyclerView.ViewHolder(binding.root) {
-
- init {
- binding.menu.setOnClickListener { view ->
- val popupMenu = PopupMenu(activity, view)
- popupMenu.inflate(R.menu.menu_backup)
- popupMenu.setOnMenuItemClickListener { menuItem ->
- return@setOnMenuItemClickListener backupClickedListener.onBackupMenuClicked(
- dataSet[bindingAdapterPosition],
- menuItem
- )
- }
- popupMenu.show()
- }
- itemView.setOnClickListener {
- backupClickedListener.onBackupClicked(dataSet[bindingAdapterPosition])
- }
- }
- }
-
- interface BackupClickedListener {
- fun onBackupClicked(file: File)
-
- fun onBackupMenuClicked(file: File, menuItem: MenuItem): Boolean
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/base/AbsMultiSelectAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/base/AbsMultiSelectAdapter.kt
deleted file mode 100644
index bb7b8491c..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/base/AbsMultiSelectAdapter.kt
+++ /dev/null
@@ -1,131 +0,0 @@
-package code.name.monkey.retromusic.adapter.base
-
-import android.graphics.Color
-import android.view.ActionMode
-import android.view.Menu
-import android.view.MenuItem
-import androidx.activity.OnBackPressedCallback
-import androidx.annotation.MenuRes
-import androidx.fragment.app.FragmentActivity
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.NumberRollViewBinding
-import code.name.monkey.retromusic.views.NumberRollView
-
-abstract class AbsMultiSelectAdapter(
- open val activity: FragmentActivity, @MenuRes menuRes: Int,
-) : RecyclerView.Adapter(), ActionMode.Callback {
- var actionMode: ActionMode? = null
- private val checked: MutableList
- private var menuRes: Int
-
- override fun onCreateActionMode(mode: ActionMode?, menu: Menu?): Boolean {
- val inflater = mode?.menuInflater
- inflater?.inflate(menuRes, menu)
- return true
- }
-
- override fun onPrepareActionMode(mode: ActionMode?, menu: Menu?): Boolean {
- return false
- }
-
- override fun onActionItemClicked(mode: ActionMode?, item: MenuItem?): Boolean {
- if (item?.itemId == R.id.action_multi_select_adapter_check_all) {
- checkAll()
- } else {
- onMultipleItemAction(item!!, ArrayList(checked))
- actionMode?.finish()
- clearChecked()
- }
- return true
- }
-
- override fun onDestroyActionMode(mode: ActionMode?) {
- clearChecked()
- activity.window.statusBarColor = when {
- VersionUtils.hasMarshmallow() -> Color.TRANSPARENT
- else -> Color.BLACK
- }
- actionMode = null
- onBackPressedCallback.remove()
- }
-
- private fun checkAll() {
- if (actionMode != null) {
- checked.clear()
- for (i in 0 until itemCount) {
- val identifier = getIdentifier(i)
- if (identifier != null) {
- checked.add(identifier)
- }
- }
- notifyDataSetChanged()
- updateCab()
- }
- }
-
- protected abstract fun getIdentifier(position: Int): I?
-
- protected abstract fun getName(model: I): String?
-
- protected fun isChecked(identifier: I): Boolean {
- return checked.contains(identifier)
- }
-
- protected val isInQuickSelectMode: Boolean
- get() = actionMode != null
-
- protected abstract fun onMultipleItemAction(menuItem: MenuItem, selection: List)
- protected fun setMultiSelectMenuRes(@MenuRes menuRes: Int) {
- this.menuRes = menuRes
- }
-
- protected fun toggleChecked(position: Int): Boolean {
- val identifier = getIdentifier(position) ?: return false
- if (!checked.remove(identifier)) {
- checked.add(identifier)
- }
- notifyItemChanged(position)
- updateCab()
- return true
- }
-
- private fun clearChecked() {
- checked.clear()
- notifyDataSetChanged()
- }
-
- private fun updateCab() {
- if (actionMode == null) {
- actionMode = activity.startActionMode(this)?.apply {
- customView = NumberRollViewBinding.inflate(activity.layoutInflater).root
- }
- activity.onBackPressedDispatcher.addCallback(onBackPressedCallback)
- }
- val size = checked.size
- when {
- size <= 0 -> {
- actionMode?.finish()
- }
- else -> {
- actionMode?.customView?.findViewById(R.id.selection_mode_number)
- ?.setNumber(size, true)
- }
- }
- }
-
- init {
- checked = ArrayList()
- this.menuRes = menuRes
- }
-
- private val onBackPressedCallback = object : OnBackPressedCallback(true) {
- override fun handleOnBackPressed() {
- if (actionMode != null) {
- actionMode?.finish()
- remove()
- }
- }
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/playlist/LegacyPlaylistAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/playlist/LegacyPlaylistAdapter.kt
deleted file mode 100644
index 19d681ecf..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/playlist/LegacyPlaylistAdapter.kt
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter.playlist
-
-import android.view.LayoutInflater
-import android.view.View
-import android.view.ViewGroup
-import androidx.fragment.app.FragmentActivity
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.retromusic.model.Playlist
-import code.name.monkey.retromusic.util.MusicUtil
-
-class LegacyPlaylistAdapter(
- private val activity: FragmentActivity,
- private var list: List,
- private val layoutRes: Int,
- private val playlistClickListener: PlaylistClickListener
-) :
- RecyclerView.Adapter() {
-
- fun swapData(list: List) {
- this.list = list
- notifyDataSetChanged()
- }
-
- class ViewHolder(itemView: View) : code.name.monkey.retromusic.adapter.base.MediaEntryViewHolder(itemView)
-
- override fun onCreateViewHolder(
- parent: ViewGroup,
- viewType: Int
- ): ViewHolder {
- return ViewHolder(
- LayoutInflater.from(parent.context).inflate(layoutRes, parent, false)
- )
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- val playlist: Playlist = list[position]
- holder.title?.text = playlist.name
- holder.text?.text = MusicUtil.getPlaylistInfoString(activity, playlist.getSongs())
- holder.itemView.setOnClickListener {
- playlistClickListener.onPlaylistClick(playlist)
- }
- }
-
- override fun getItemCount(): Int {
- return list.size
- }
-
- interface PlaylistClickListener {
- fun onPlaylistClick(playlist: Playlist)
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/playlist/PlaylistAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/playlist/PlaylistAdapter.kt
deleted file mode 100755
index 6e5b0c001..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/playlist/PlaylistAdapter.kt
+++ /dev/null
@@ -1,186 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter.playlist
-
-import android.graphics.Color
-import android.graphics.drawable.Drawable
-import android.view.LayoutInflater
-import android.view.MenuItem
-import android.view.View
-import android.view.ViewGroup
-import androidx.appcompat.widget.PopupMenu
-import androidx.core.view.isGone
-import androidx.core.view.setPadding
-import androidx.fragment.app.FragmentActivity
-import code.name.monkey.appthemehelper.util.ATHUtil
-import code.name.monkey.appthemehelper.util.TintHelper
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.adapter.base.AbsMultiSelectAdapter
-import code.name.monkey.retromusic.db.PlaylistEntity
-import code.name.monkey.retromusic.db.PlaylistWithSongs
-import code.name.monkey.retromusic.db.toSongs
-import code.name.monkey.retromusic.extensions.dipToPix
-import code.name.monkey.retromusic.glide.RetroGlideExtension.playlistOptions
-import code.name.monkey.retromusic.glide.playlistPreview.PlaylistPreview
-import code.name.monkey.retromusic.helper.SortOrder.PlaylistSortOrder
-import code.name.monkey.retromusic.helper.menu.PlaylistMenuHelper
-import code.name.monkey.retromusic.helper.menu.SongsMenuHelper
-import code.name.monkey.retromusic.interfaces.IPlaylistClickListener
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.PreferenceUtil
-import com.bumptech.glide.Glide
-import me.zhanghai.android.fastscroll.PopupTextProvider
-
-class PlaylistAdapter(
- override val activity: FragmentActivity,
- var dataSet: List,
- private var itemLayoutRes: Int,
- private val listener: IPlaylistClickListener
-) : AbsMultiSelectAdapter(
- activity,
- R.menu.menu_playlists_selection
-), PopupTextProvider {
-
- init {
- setHasStableIds(true)
- }
-
- fun swapDataSet(dataSet: List) {
- this.dataSet = dataSet
- notifyDataSetChanged()
- }
-
- override fun getItemId(position: Int): Long {
- return dataSet[position].playlistEntity.playListId
- }
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
- val view = LayoutInflater.from(activity).inflate(itemLayoutRes, parent, false)
- return createViewHolder(view)
- }
-
- private fun createViewHolder(view: View): ViewHolder {
- return ViewHolder(view)
- }
-
- private fun getPlaylistTitle(playlist: PlaylistEntity): String {
- return playlist.playlistName.ifEmpty { "-" }
- }
-
- private fun getPlaylistText(playlist: PlaylistWithSongs): String {
- return MusicUtil.getPlaylistInfoString(activity, playlist.songs.toSongs())
- }
-
- override fun getPopupText(position: Int): String {
- val sectionName: String = when (PreferenceUtil.playlistSortOrder) {
- PlaylistSortOrder.PLAYLIST_A_Z, PlaylistSortOrder.PLAYLIST_Z_A -> dataSet[position].playlistEntity.playlistName
- PlaylistSortOrder.PLAYLIST_SONG_COUNT, PlaylistSortOrder.PLAYLIST_SONG_COUNT_DESC -> dataSet[position].songs.size.toString()
- else -> {
- return ""
- }
- }
- return MusicUtil.getSectionName(sectionName)
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- val playlist = dataSet[position]
- holder.itemView.isActivated = isChecked(playlist)
- holder.title?.text = getPlaylistTitle(playlist.playlistEntity)
- holder.text?.text = getPlaylistText(playlist)
- holder.menu?.isGone = isChecked(playlist)
- if (itemLayoutRes == R.layout.item_list) {
- holder.image?.setPadding(activity.dipToPix(8F).toInt())
- holder.image?.setImageDrawable(getIconRes())
- } else {
- Glide.with(activity)
- .load(PlaylistPreview(playlist))
- .playlistOptions()
- .into(holder.image!!)
- }
- }
-
- private fun getIconRes(): Drawable = TintHelper.createTintedDrawable(
- activity,
- R.drawable.ic_playlist_play,
- ATHUtil.resolveColor(activity, android.R.attr.colorControlNormal)
- )
-
- override fun getItemCount(): Int {
- return dataSet.size
- }
-
- override fun getIdentifier(position: Int): PlaylistWithSongs {
- return dataSet[position]
- }
-
- override fun getName(model: PlaylistWithSongs): String {
- return model.playlistEntity.playlistName
- }
-
- override fun onMultipleItemAction(menuItem: MenuItem, selection: List) {
- when (menuItem.itemId) {
- else -> SongsMenuHelper.handleMenuClick(
- activity,
- getSongList(selection),
- menuItem.itemId
- )
- }
- }
-
- private fun getSongList(playlists: List): List {
- val songs = mutableListOf()
- playlists.forEach {
- songs.addAll(it.songs.toSongs())
- }
- return songs
- }
-
- inner class ViewHolder(itemView: View) : code.name.monkey.retromusic.adapter.base.MediaEntryViewHolder(itemView) {
- init {
- menu?.setOnClickListener { view ->
- val popupMenu = PopupMenu(activity, view)
- popupMenu.inflate(R.menu.menu_item_playlist)
- popupMenu.setOnMenuItemClickListener { item ->
- PlaylistMenuHelper.handleMenuClick(activity, dataSet[layoutPosition], item)
- }
- popupMenu.show()
- }
-
- imageTextContainer?.apply {
- cardElevation = 0f
- setCardBackgroundColor(Color.TRANSPARENT)
- }
- }
-
- override fun onClick(v: View?) {
- if (isInQuickSelectMode) {
- toggleChecked(layoutPosition)
- } else {
- itemView.transitionName = "playlist"
- listener.onPlaylistClick(dataSet[layoutPosition], itemView)
- }
- }
-
- override fun onLongClick(v: View?): Boolean {
- toggleChecked(layoutPosition)
- return true
- }
- }
-
- companion object {
- val TAG: String = PlaylistAdapter::class.java.simpleName
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/song/OrderablePlaylistSongAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/song/OrderablePlaylistSongAdapter.kt
deleted file mode 100644
index bf85fe28b..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/song/OrderablePlaylistSongAdapter.kt
+++ /dev/null
@@ -1,134 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter.song
-
-import android.view.MenuItem
-import android.view.View
-import androidx.core.view.isVisible
-import androidx.fragment.app.FragmentActivity
-import androidx.lifecycle.lifecycleScope
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.db.PlaylistEntity
-import code.name.monkey.retromusic.db.toSongEntity
-import code.name.monkey.retromusic.db.toSongsEntity
-import code.name.monkey.retromusic.dialogs.RemoveSongFromPlaylistDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.ViewUtil
-import com.h6ah4i.android.widget.advrecyclerview.draggable.DraggableItemAdapter
-import com.h6ah4i.android.widget.advrecyclerview.draggable.ItemDraggableRange
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.launch
-import org.koin.androidx.viewmodel.ext.android.viewModel
-
-class OrderablePlaylistSongAdapter(
- private val playlistId: Long,
- activity: FragmentActivity,
- dataSet: MutableList,
- itemLayoutRes: Int,
-) : SongAdapter(activity, dataSet, itemLayoutRes),
- DraggableItemAdapter {
-
- val libraryViewModel: LibraryViewModel by activity.viewModel()
-
- init {
- this.setHasStableIds(true)
- this.setMultiSelectMenuRes(R.menu.menu_playlists_songs_selection)
- }
-
- override fun getItemId(position: Int): Long {
- // requires static value, it means need to keep the same value
- // even if the item position has been changed.
- return dataSet[position].id
- }
-
- override fun createViewHolder(view: View): SongAdapter.ViewHolder {
- return ViewHolder(view)
- }
-
- override fun onMultipleItemAction(menuItem: MenuItem, selection: List) {
- when (menuItem.itemId) {
- R.id.action_remove_from_playlist -> RemoveSongFromPlaylistDialog.create(
- selection.toSongsEntity(
- playlistId
- )
- )
- .show(activity.supportFragmentManager, "REMOVE_FROM_PLAYLIST")
-
- else -> super.onMultipleItemAction(menuItem, selection)
- }
- }
-
- inner class ViewHolder(itemView: View) : SongAdapter.ViewHolder(itemView) {
-
- override var songMenuRes: Int
- get() = R.menu.menu_item_playlist_song
- set(value) {
- super.songMenuRes = value
- }
-
- override fun onSongMenuItemClick(item: MenuItem): Boolean {
- when (item.itemId) {
- R.id.action_remove_from_playlist -> {
- RemoveSongFromPlaylistDialog.create(song.toSongEntity(playlistId))
- .show(activity.supportFragmentManager, "REMOVE_FROM_PLAYLIST")
- return true
- }
- }
- return super.onSongMenuItemClick(item)
- }
-
- init {
- dragView?.isVisible = true
- }
- }
-
- override fun onCheckCanStartDrag(holder: ViewHolder, position: Int, x: Int, y: Int): Boolean {
- if (isInQuickSelectMode) {
- return false
- }
- return ViewUtil.hitTest(holder.imageText!!, x, y) || ViewUtil.hitTest(
- holder.dragView!!,
- x,
- y
- )
- }
-
- override fun onMoveItem(fromPosition: Int, toPosition: Int) {
- dataSet.add(toPosition, dataSet.removeAt(fromPosition))
- }
-
- override fun onGetItemDraggableRange(holder: ViewHolder, position: Int): ItemDraggableRange? {
- return null
- }
-
- override fun onCheckCanDrop(draggingPosition: Int, dropPosition: Int): Boolean {
- return true
- }
-
- override fun onItemDragStarted(position: Int) {
- notifyDataSetChanged()
- }
-
- override fun onItemDragFinished(fromPosition: Int, toPosition: Int, result: Boolean) {
- notifyDataSetChanged()
- }
-
- fun saveSongs(playlistEntity: PlaylistEntity) {
- activity.lifecycleScope.launch(Dispatchers.IO) {
- libraryViewModel.insertSongs(dataSet.toSongsEntity(playlistEntity))
- }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/song/ShuffleButtonSongAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/song/ShuffleButtonSongAdapter.kt
deleted file mode 100644
index 82ba1a7f7..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/song/ShuffleButtonSongAdapter.kt
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter.song
-
-import android.view.View
-import androidx.core.view.isVisible
-import androidx.fragment.app.FragmentActivity
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.accentOutlineColor
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.RetroUtil
-import com.google.android.material.button.MaterialButton
-
-class ShuffleButtonSongAdapter(
- activity: FragmentActivity,
- dataSet: MutableList,
- itemLayoutRes: Int
-) : AbsOffsetSongAdapter(activity, dataSet, itemLayoutRes) {
-
-
- override fun createViewHolder(view: View): SongAdapter.ViewHolder {
- return ViewHolder(view)
- }
-
- override fun getItemViewType(position: Int): Int {
- return if (position == 0) OFFSET_ITEM else SONG
- }
-
- override fun onBindViewHolder(holder: SongAdapter.ViewHolder, position: Int) {
- if (holder.itemViewType == OFFSET_ITEM) {
- val viewHolder = holder as ViewHolder
- viewHolder.playAction?.let {
- it.setOnClickListener {
- MusicPlayerRemote.openQueue(dataSet, 0, true)
- }
- it.accentOutlineColor()
- }
- viewHolder.shuffleAction?.let {
- it.setOnClickListener {
- MusicPlayerRemote.openAndShuffleQueue(dataSet, true)
- }
- it.accentColor()
- }
- } else {
- super.onBindViewHolder(holder, position - 1)
- val landscape = RetroUtil.isLandscape
- if ((PreferenceUtil.songGridSize > 2 && !landscape) || (PreferenceUtil.songGridSizeLand > 5 && landscape)) {
- holder.menu?.isVisible = false
- }
- }
- }
-
- inner class ViewHolder(itemView: View) : AbsOffsetSongAdapter.ViewHolder(itemView) {
- val playAction: MaterialButton? = itemView.findViewById(R.id.playAction)
- val shuffleAction: MaterialButton? = itemView.findViewById(R.id.shuffleAction)
-
- override fun onClick(v: View?) {
- if (itemViewType == OFFSET_ITEM) {
- MusicPlayerRemote.openAndShuffleQueue(dataSet, true)
- return
- }
- super.onClick(v)
- }
- }
-
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/adapter/song/SimpleSongAdapter.kt b/app/src/main/java/code/name/monkey/retromusic/adapter/song/SimpleSongAdapter.kt
deleted file mode 100755
index f1f50e627..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/adapter/song/SimpleSongAdapter.kt
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.adapter.song
-
-import android.view.LayoutInflater
-import android.view.ViewGroup
-import androidx.fragment.app.FragmentActivity
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.MusicUtil
-
-class SimpleSongAdapter(
- context: FragmentActivity,
- songs: ArrayList,
- layoutRes: Int
-) : SongAdapter(context, songs, layoutRes) {
-
- override fun swapDataSet(dataSet: List) {
- this.dataSet = dataSet.toMutableList()
- notifyDataSetChanged()
- }
-
- override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
- return ViewHolder(LayoutInflater.from(activity).inflate(itemLayoutRes, parent, false))
- }
-
- override fun onBindViewHolder(holder: ViewHolder, position: Int) {
- super.onBindViewHolder(holder, position)
- val fixedTrackNumber = MusicUtil.getFixedTrackNumber(dataSet[position].trackNumber)
- val trackAndTime = (if (fixedTrackNumber > 0) "$fixedTrackNumber | " else "") +
- MusicUtil.getReadableDurationString(dataSet[position].duration)
-
- holder.time?.text = trackAndTime
- holder.text2?.text = dataSet[position].artistName
- }
-
- override fun getItemCount(): Int {
- return dataSet.size
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/appshortcuts/AppShortcutLauncherActivity.kt b/app/src/main/java/code/name/monkey/retromusic/appshortcuts/AppShortcutLauncherActivity.kt
deleted file mode 100644
index 9f10d795b..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/appshortcuts/AppShortcutLauncherActivity.kt
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.appshortcuts
-
-import android.app.Activity
-import android.content.Intent
-import android.os.Bundle
-import androidx.core.os.bundleOf
-import code.name.monkey.retromusic.appshortcuts.shortcuttype.LastAddedShortcutType
-import code.name.monkey.retromusic.appshortcuts.shortcuttype.ShuffleAllShortcutType
-import code.name.monkey.retromusic.appshortcuts.shortcuttype.TopTracksShortcutType
-import code.name.monkey.retromusic.extensions.extraNotNull
-import code.name.monkey.retromusic.model.Playlist
-import code.name.monkey.retromusic.model.smartplaylist.LastAddedPlaylist
-import code.name.monkey.retromusic.model.smartplaylist.ShuffleAllPlaylist
-import code.name.monkey.retromusic.model.smartplaylist.TopTracksPlaylist
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.service.MusicService.Companion.ACTION_PLAY_PLAYLIST
-import code.name.monkey.retromusic.service.MusicService.Companion.INTENT_EXTRA_PLAYLIST
-import code.name.monkey.retromusic.service.MusicService.Companion.INTENT_EXTRA_SHUFFLE_MODE
-import code.name.monkey.retromusic.service.MusicService.Companion.SHUFFLE_MODE_NONE
-import code.name.monkey.retromusic.service.MusicService.Companion.SHUFFLE_MODE_SHUFFLE
-
-class AppShortcutLauncherActivity : Activity() {
-
- public override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- when (extraNotNull(KEY_SHORTCUT_TYPE, SHORTCUT_TYPE_NONE).value) {
- SHORTCUT_TYPE_SHUFFLE_ALL -> {
- startServiceWithPlaylist(
- SHUFFLE_MODE_SHUFFLE, ShuffleAllPlaylist()
- )
- DynamicShortcutManager.reportShortcutUsed(this, ShuffleAllShortcutType.id)
- }
- SHORTCUT_TYPE_TOP_TRACKS -> {
- startServiceWithPlaylist(
- SHUFFLE_MODE_NONE, TopTracksPlaylist()
- )
- DynamicShortcutManager.reportShortcutUsed(this, TopTracksShortcutType.id)
- }
- SHORTCUT_TYPE_LAST_ADDED -> {
- startServiceWithPlaylist(
- SHUFFLE_MODE_NONE, LastAddedPlaylist()
- )
- DynamicShortcutManager.reportShortcutUsed(this, LastAddedShortcutType.id)
- }
- }
- finish()
- }
-
- private fun startServiceWithPlaylist(shuffleMode: Int, playlist: Playlist) {
- val intent = Intent(this, MusicService::class.java)
- intent.action = ACTION_PLAY_PLAYLIST
-
- val bundle = bundleOf(
- INTENT_EXTRA_PLAYLIST to playlist,
- INTENT_EXTRA_SHUFFLE_MODE to shuffleMode
- )
-
- intent.putExtras(bundle)
-
- startService(intent)
- }
-
- companion object {
- const val KEY_SHORTCUT_TYPE = "io.github.muntashirakon.Music.appshortcuts.ShortcutType"
- const val SHORTCUT_TYPE_SHUFFLE_ALL = 0L
- const val SHORTCUT_TYPE_TOP_TRACKS = 1L
- const val SHORTCUT_TYPE_LAST_ADDED = 2L
- const val SHORTCUT_TYPE_NONE = 4L
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/appshortcuts/shortcuttype/ShuffleAllShortcutType.kt b/app/src/main/java/code/name/monkey/retromusic/appshortcuts/shortcuttype/ShuffleAllShortcutType.kt
deleted file mode 100644
index 21855cacd..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/appshortcuts/shortcuttype/ShuffleAllShortcutType.kt
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.appshortcuts.shortcuttype
-
-import android.annotation.TargetApi
-import android.content.Context
-import android.content.pm.ShortcutInfo
-import android.os.Build
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.appshortcuts.AppShortcutIconGenerator
-import code.name.monkey.retromusic.appshortcuts.AppShortcutLauncherActivity
-
-@TargetApi(Build.VERSION_CODES.N_MR1)
-class ShuffleAllShortcutType(context: Context) : BaseShortcutType(context) {
-
- override val shortcutInfo: ShortcutInfo
- get() = ShortcutInfo.Builder(context, id)
- .setShortLabel(context.getString(R.string.app_shortcut_shuffle_all_short))
- .setLongLabel(context.getString(R.string.app_shortcut_shuffle_all_long))
- .setIcon(AppShortcutIconGenerator.generateThemedIcon(context, R.drawable.ic_app_shortcut_shuffle_all))
- .setIntent(getPlaySongsIntent(AppShortcutLauncherActivity.SHORTCUT_TYPE_SHUFFLE_ALL))
- .build()
-
- companion object {
-
- val id: String
- get() = ID_PREFIX + "shuffle_all"
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/appwidgets/AppWidgetCircle.kt b/app/src/main/java/code/name/monkey/retromusic/appwidgets/AppWidgetCircle.kt
deleted file mode 100644
index cb3ae0e44..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/appwidgets/AppWidgetCircle.kt
+++ /dev/null
@@ -1,218 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.appwidgets
-
-import android.app.PendingIntent
-import android.content.ComponentName
-import android.content.Context
-import android.content.Intent
-import android.graphics.Bitmap
-import android.graphics.drawable.Drawable
-import android.widget.RemoteViews
-import androidx.core.graphics.drawable.toBitmap
-import code.name.monkey.appthemehelper.util.MaterialValueHelper
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.MainActivity
-import code.name.monkey.retromusic.appwidgets.base.BaseAppWidget
-import code.name.monkey.retromusic.extensions.getTintedDrawable
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.RetroGlideExtension.songCoverOptions
-import code.name.monkey.retromusic.glide.palette.BitmapPaletteWrapper
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.service.MusicService.Companion.ACTION_TOGGLE_PAUSE
-import code.name.monkey.retromusic.service.MusicService.Companion.TOGGLE_FAVORITE
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.RetroUtil
-import com.bumptech.glide.Glide
-import com.bumptech.glide.request.RequestOptions
-import com.bumptech.glide.request.target.CustomTarget
-import com.bumptech.glide.request.target.Target
-import com.bumptech.glide.request.transition.Transition
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.runBlocking
-
-class AppWidgetCircle : BaseAppWidget() {
- private var target: Target? = null // for cancellation
-
- /**
- * Initialize given widgets to default state, where we launch Music on default click and hide
- * actions if service not running.
- */
- override fun defaultAppWidget(context: Context, appWidgetIds: IntArray) {
- val appWidgetView = RemoteViews(context.packageName, R.layout.app_widget_circle)
-
- appWidgetView.setImageViewResource(R.id.image, R.drawable.default_audio_art)
- val secondaryColor = MaterialValueHelper.getSecondaryTextColor(context, true)
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_play_pause,
- context.getTintedDrawable(
- R.drawable.ic_play_arrow,
- secondaryColor
- ).toBitmap()
- )
-
- linkButtons(context, appWidgetView)
- pushUpdate(context, appWidgetIds, appWidgetView)
- }
-
- /**
- * Update all active widget instances by pushing changes
- */
- override fun performUpdate(service: MusicService, appWidgetIds: IntArray?) {
- val appWidgetView = RemoteViews(service.packageName, R.layout.app_widget_circle)
-
- val isPlaying = service.isPlaying
- val song = service.currentSong
-
- // Set correct drawable for pause state
- val playPauseRes =
- if (isPlaying) R.drawable.ic_pause else R.drawable.ic_play_arrow
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_play_pause,
- service.getTintedDrawable(
- playPauseRes,
- MaterialValueHelper.getSecondaryTextColor(service, true)
- ).toBitmap()
- )
- val isFavorite = runBlocking(Dispatchers.IO) {
- return@runBlocking MusicUtil.isFavorite(song)
- }
- val favoriteRes =
- if (isFavorite) R.drawable.ic_favorite else R.drawable.ic_favorite_border
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_favorite,
- service.getTintedDrawable(
- favoriteRes,
- MaterialValueHelper.getSecondaryTextColor(service, true)
- ).toBitmap()
- )
-
- // Link actions buttons to intents
- linkButtons(service, appWidgetView)
-
- if (imageSize == 0) {
- val p = RetroUtil.getScreenSize(service)
- imageSize = p.x.coerceAtMost(p.y)
- }
-
- // Load the album cover async and push the update on completion
- service.runOnUiThread {
- if (target != null) {
- Glide.with(service).clear(target)
- }
- target = Glide.with(service)
- .asBitmapPalette()
- .songCoverOptions(song)
- .load(RetroGlideExtension.getSongModel(song))
- .apply(RequestOptions.circleCropTransform())
- .into(object : CustomTarget(imageSize, imageSize) {
- override fun onResourceReady(
- resource: BitmapPaletteWrapper,
- transition: Transition?,
- ) {
- val palette = resource.palette
- update(
- resource.bitmap, palette.getVibrantColor(
- palette.getMutedColor(
- MaterialValueHelper.getSecondaryTextColor(
- service, true
- )
- )
- )
- )
- }
-
- override fun onLoadFailed(errorDrawable: Drawable?) {
- super.onLoadFailed(errorDrawable)
- update(null, MaterialValueHelper.getSecondaryTextColor(service, true))
- }
-
- private fun update(bitmap: Bitmap?, color: Int) {
- // Set correct drawable for pause state
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_play_pause,
- service.getTintedDrawable(
- playPauseRes, color
- ).toBitmap()
- )
-
- // Set favorite button drawables
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_favorite,
- service.getTintedDrawable(
- favoriteRes, color
- ).toBitmap()
- )
- if (bitmap != null) {
- appWidgetView.setImageViewBitmap(R.id.image, bitmap)
- }
-
- pushUpdate(service, appWidgetIds, appWidgetView)
- }
-
- override fun onLoadCleared(placeholder: Drawable?) {}
- })
- }
- }
-
- /**
- * Link up various button actions using [PendingIntent].
- */
- private fun linkButtons(context: Context, views: RemoteViews) {
- val action = Intent(context, MainActivity::class.java)
- .putExtra(
- MainActivity.EXPAND_PANEL,
- PreferenceUtil.isExpandPanel
- )
-
- val serviceName = ComponentName(context, MusicService::class.java)
-
- // Home
- action.flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TOP
- var pendingIntent =
- PendingIntent.getActivity(
- context, 0, action, if (VersionUtils.hasMarshmallow())
- PendingIntent.FLAG_IMMUTABLE
- else 0
- )
- views.setOnClickPendingIntent(R.id.image, pendingIntent)
- // Favorite track
- pendingIntent = buildPendingIntent(context, TOGGLE_FAVORITE, serviceName)
- views.setOnClickPendingIntent(R.id.button_toggle_favorite, pendingIntent)
-
- // Play and pause
- pendingIntent = buildPendingIntent(context, ACTION_TOGGLE_PAUSE, serviceName)
- views.setOnClickPendingIntent(R.id.button_toggle_play_pause, pendingIntent)
- }
-
- companion object {
-
- const val NAME = "app_widget_circle"
-
- private var mInstance: AppWidgetCircle? = null
- private var imageSize = 0
-
- val instance: AppWidgetCircle
- @Synchronized get() {
- if (mInstance == null) {
- mInstance = AppWidgetCircle()
- }
- return mInstance!!
- }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/appwidgets/AppWidgetMD3.kt b/app/src/main/java/code/name/monkey/retromusic/appwidgets/AppWidgetMD3.kt
deleted file mode 100644
index 618914ff3..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/appwidgets/AppWidgetMD3.kt
+++ /dev/null
@@ -1,264 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.appwidgets
-
-import android.app.PendingIntent
-import android.content.ComponentName
-import android.content.Context
-import android.content.Intent
-import android.graphics.Bitmap
-import android.graphics.drawable.Drawable
-import android.view.View
-import android.widget.RemoteViews
-import androidx.core.graphics.drawable.toBitmap
-import code.name.monkey.appthemehelper.util.MaterialValueHelper
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.MainActivity
-import code.name.monkey.retromusic.appwidgets.base.BaseAppWidget
-import code.name.monkey.retromusic.extensions.getTintedDrawable
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.RetroGlideExtension.songCoverOptions
-import code.name.monkey.retromusic.glide.palette.BitmapPaletteWrapper
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.service.MusicService.Companion.ACTION_REWIND
-import code.name.monkey.retromusic.service.MusicService.Companion.ACTION_SKIP
-import code.name.monkey.retromusic.service.MusicService.Companion.ACTION_TOGGLE_PAUSE
-import code.name.monkey.retromusic.util.DensityUtil
-import code.name.monkey.retromusic.util.PreferenceUtil
-import com.bumptech.glide.Glide
-import com.bumptech.glide.request.target.CustomTarget
-import com.bumptech.glide.request.target.Target
-import com.bumptech.glide.request.transition.Transition
-
-class AppWidgetMD3 : BaseAppWidget() {
- private var target: Target? = null // for cancellation
-
- /**
- * Initialize given widgets to default state, where we launch Music on default click and hide
- * actions if service not running.
- */
- override fun defaultAppWidget(context: Context, appWidgetIds: IntArray) {
- val appWidgetView = RemoteViews(context.packageName, R.layout.app_widget_md3)
-
- appWidgetView.setViewVisibility(R.id.media_titles, View.INVISIBLE)
- appWidgetView.setImageViewResource(R.id.image, R.drawable.default_audio_art)
- val secondaryColor = MaterialValueHelper.getSecondaryTextColor(context, true)
- appWidgetView.setImageViewBitmap(
- R.id.button_next,
- context.getTintedDrawable(
- R.drawable.ic_skip_next,
- secondaryColor
- ).toBitmap()
- )
- appWidgetView.setImageViewBitmap(
- R.id.button_prev,
- context.getTintedDrawable(
- R.drawable.ic_skip_previous,
- secondaryColor
- ).toBitmap()
- )
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_play_pause,
- context.getTintedDrawable(
- R.drawable.ic_play_arrow_white_32dp,
- secondaryColor
- ).toBitmap()
- )
-
- linkButtons(context, appWidgetView)
- pushUpdate(context, appWidgetIds, appWidgetView)
- }
-
- /**
- * Update all active widget instances by pushing changes
- */
- override fun performUpdate(service: MusicService, appWidgetIds: IntArray?) {
- val appWidgetView = RemoteViews(service.packageName, R.layout.app_widget_md3)
-
- val isPlaying = service.isPlaying
- val song = service.currentSong
-
- // Set the titles and artwork
- if (song.title.isEmpty() && song.artistName.isEmpty()) {
- appWidgetView.setViewVisibility(R.id.media_titles, View.INVISIBLE)
- } else {
- appWidgetView.setViewVisibility(R.id.media_titles, View.VISIBLE)
- appWidgetView.setTextViewText(R.id.title, song.title)
- appWidgetView.setTextViewText(R.id.text, getSongArtistAndAlbum(song))
- }
-
- // Set correct drawable for pause state
- val playPauseRes =
- if (isPlaying) R.drawable.ic_pause else R.drawable.ic_play_arrow_white_32dp
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_play_pause,
- service.getTintedDrawable(
- playPauseRes,
- MaterialValueHelper.getSecondaryTextColor(service, true)
- ).toBitmap()
- )
-
- // Set prev/next button drawables
- appWidgetView.setImageViewBitmap(
- R.id.button_next,
- service.getTintedDrawable(
- R.drawable.ic_skip_next,
- MaterialValueHelper.getSecondaryTextColor(service, true)
- ).toBitmap()
- )
- appWidgetView.setImageViewBitmap(
- R.id.button_prev,
- service.getTintedDrawable(
- R.drawable.ic_skip_previous,
- MaterialValueHelper.getSecondaryTextColor(service, true)
- ).toBitmap()
- )
-
- // Link actions buttons to intents
- linkButtons(service, appWidgetView)
-
- if (imageSize == 0) {
- imageSize =
- service.resources.getDimensionPixelSize(R.dimen.app_widget_card_image_size)
- }
- if (cardRadius == 0f) {
- cardRadius =
- DensityUtil.dip2px(service, 8F).toFloat()
- }
-
- // Load the album cover async and push the update on completion
- service.runOnUiThread {
- if (target != null) {
- Glide.with(service).clear(target)
- }
- target = Glide.with(service)
- .asBitmapPalette()
- .songCoverOptions(song)
- .load(RetroGlideExtension.getSongModel(song))
- .centerCrop()
- .into(object : CustomTarget(imageSize, imageSize) {
- override fun onResourceReady(
- resource: BitmapPaletteWrapper,
- transition: Transition?,
- ) {
- val palette = resource.palette
- update(
- resource.bitmap, palette.getVibrantColor(
- palette.getMutedColor(
- MaterialValueHelper.getSecondaryTextColor(
- service, true
- )
- )
- )
- )
- }
-
- override fun onLoadFailed(errorDrawable: Drawable?) {
- super.onLoadFailed(errorDrawable)
- update(null, MaterialValueHelper.getSecondaryTextColor(service, true))
- }
-
- override fun onLoadCleared(placeholder: Drawable?) {}
-
- private fun update(bitmap: Bitmap?, color: Int) {
- // Set correct drawable for pause state
- appWidgetView.setImageViewBitmap(
- R.id.button_toggle_play_pause,
- service.getTintedDrawable(playPauseRes, color).toBitmap()
- )
-
- // Set prev/next button drawables
- appWidgetView.setImageViewBitmap(
- R.id.button_next,
- service.getTintedDrawable(R.drawable.ic_skip_next, color).toBitmap()
- )
- appWidgetView.setImageViewBitmap(
- R.id.button_prev,
- service.getTintedDrawable(R.drawable.ic_skip_previous, color).toBitmap()
- )
-
- val image = getAlbumArtDrawable(service, bitmap)
- val roundedBitmap = createRoundedBitmap(
- image,
- imageSize,
- imageSize,
- cardRadius,
- cardRadius,
- cardRadius,
- cardRadius
- )
- appWidgetView.setImageViewBitmap(R.id.image, roundedBitmap)
-
- pushUpdate(service, appWidgetIds, appWidgetView)
- }
- })
- }
- }
-
- /**
- * Link up various button actions using [PendingIntent].
- */
- private fun linkButtons(context: Context, views: RemoteViews) {
- val action = Intent(context, MainActivity::class.java)
- .putExtra(
- MainActivity.EXPAND_PANEL,
- PreferenceUtil.isExpandPanel
- )
-
- val serviceName = ComponentName(context, MusicService::class.java)
-
- // Home
- action.flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TOP
- var pendingIntent =
- PendingIntent.getActivity(
- context, 0, action, if (VersionUtils.hasMarshmallow())
- PendingIntent.FLAG_IMMUTABLE
- else 0
- )
- views.setOnClickPendingIntent(R.id.image, pendingIntent)
- views.setOnClickPendingIntent(R.id.media_titles, pendingIntent)
-
- // Previous track
- pendingIntent = buildPendingIntent(context, ACTION_REWIND, serviceName)
- views.setOnClickPendingIntent(R.id.button_prev, pendingIntent)
-
- // Play and pause
- pendingIntent = buildPendingIntent(context, ACTION_TOGGLE_PAUSE, serviceName)
- views.setOnClickPendingIntent(R.id.button_toggle_play_pause, pendingIntent)
-
- // Next track
- pendingIntent = buildPendingIntent(context, ACTION_SKIP, serviceName)
- views.setOnClickPendingIntent(R.id.button_next, pendingIntent)
- }
-
- companion object {
-
- const val NAME = "app_widget_md3"
-
- private var mInstance: AppWidgetMD3? = null
- private var imageSize = 0
- private var cardRadius = 0F
-
- val instance: AppWidgetMD3
- @Synchronized get() {
- if (mInstance == null) {
- mInstance = AppWidgetMD3()
- }
- return mInstance!!
- }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/auto/AutoMediaIDHelper.java b/app/src/main/java/code/name/monkey/retromusic/auto/AutoMediaIDHelper.java
deleted file mode 100644
index 3d1f4815d..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/auto/AutoMediaIDHelper.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright (c) 2019 Hemanth Savarala.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it under
- * the terms of the GNU General Public License as published by
- * the Free Software Foundation either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- */
-
-package code.name.monkey.retromusic.auto;
-
-import androidx.annotation.NonNull;
-
-/**
- * Created by Beesham Sarendranauth (Beesham)
- */
-public class AutoMediaIDHelper {
-
- // Media IDs used on browseable items of MediaBrowser
- public static final String MEDIA_ID_EMPTY_ROOT = "__EMPTY_ROOT__";
- public static final String MEDIA_ID_ROOT = "__ROOT__";
- public static final String MEDIA_ID_MUSICS_BY_SEARCH = "__BY_SEARCH__"; // TODO
- public static final String MEDIA_ID_MUSICS_BY_HISTORY = "__BY_HISTORY__";
- public static final String MEDIA_ID_MUSICS_BY_TOP_TRACKS = "__BY_TOP_TRACKS__";
- public static final String MEDIA_ID_MUSICS_BY_SUGGESTIONS = "__BY_SUGGESTIONS__";
- public static final String MEDIA_ID_MUSICS_BY_PLAYLIST = "__BY_PLAYLIST__";
- public static final String MEDIA_ID_MUSICS_BY_ALBUM = "__BY_ALBUM__";
- public static final String MEDIA_ID_MUSICS_BY_ARTIST = "__BY_ARTIST__";
- public static final String MEDIA_ID_MUSICS_BY_ALBUM_ARTIST = "__BY_ALBUM_ARTIST__";
- public static final String MEDIA_ID_MUSICS_BY_GENRE = "__BY_GENRE__";
- public static final String MEDIA_ID_MUSICS_BY_SHUFFLE = "__BY_SHUFFLE__";
- public static final String MEDIA_ID_MUSICS_BY_QUEUE = "__BY_QUEUE__";
- public static final String RECENT_ROOT = "__RECENT__";
-
- private static final String CATEGORY_SEPARATOR = "__/__";
- private static final String LEAF_SEPARATOR = "__|__";
-
- /**
- * Create a String value that represents a playable or a browsable media.
- *
- * Encode the media browseable categories, if any, and the unique music ID, if any,
- * into a single String mediaID.
- *
- * MediaIDs are of the form __/____|__, to make it
- * easy to find the category (like genre) that a music was selected from, so we
- * can correctly build the playing queue. This is specially useful when
- * one music can appear in more than one list, like "by genre -> genre_1"
- * and "by artist -> artist_1".
- *
- * @param mediaID Unique ID for playable items, or null for browseable items.
- * @param categories Hierarchy of categories representing this item's browsing parents.
- * @return A hierarchy-aware media ID.
- */
- public static String createMediaID(String mediaID, String... categories) {
- StringBuilder sb = new StringBuilder();
- if (categories != null) {
- for (int i = 0; i < categories.length; i++) {
- if (!isValidCategory(categories[i])) {
- throw new IllegalArgumentException("Invalid category: " + categories[i]);
- }
- sb.append(categories[i]);
- if (i < categories.length - 1) {
- sb.append(CATEGORY_SEPARATOR);
- }
- }
- }
- if (mediaID != null) {
- sb.append(LEAF_SEPARATOR).append(mediaID);
- }
- return sb.toString();
- }
-
- public static String extractCategory(@NonNull String mediaID) {
- int pos = mediaID.indexOf(LEAF_SEPARATOR);
- if (pos >= 0) {
- return mediaID.substring(0, pos);
- }
- return mediaID;
- }
-
- public static String extractMusicID(@NonNull String mediaID) {
- int pos = mediaID.indexOf(LEAF_SEPARATOR);
- if (pos >= 0) {
- return mediaID.substring(pos + LEAF_SEPARATOR.length());
- }
- return null;
- }
-
- public static boolean isBrowseable(@NonNull String mediaID) {
- return !mediaID.contains(LEAF_SEPARATOR);
- }
-
- private static boolean isValidCategory(String category) {
- return category == null ||
- (!category.contains(CATEGORY_SEPARATOR) && !category.contains(LEAF_SEPARATOR));
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/auto/AutoMusicProvider.kt b/app/src/main/java/code/name/monkey/retromusic/auto/AutoMusicProvider.kt
deleted file mode 100644
index b6e267ed2..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/auto/AutoMusicProvider.kt
+++ /dev/null
@@ -1,283 +0,0 @@
-/*
- * Copyright (c) 2019 Hemanth Savarala.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it under
- * the terms of the GNU General Public License as published by
- * the Free Software Foundation either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- */
-package code.name.monkey.retromusic.auto
-
-import android.content.Context
-import android.content.res.Resources
-import android.support.v4.media.MediaBrowserCompat
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.model.CategoryInfo
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.repository.*
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.PreferenceUtil
-import java.lang.ref.WeakReference
-
-
-/**
- * Created by Beesham Sarendranauth (Beesham)
- */
-class AutoMusicProvider(
- private val mContext: Context,
- private val songsRepository: SongRepository,
- private val albumsRepository: AlbumRepository,
- private val artistsRepository: ArtistRepository,
- private val genresRepository: GenreRepository,
- private val playlistsRepository: PlaylistRepository,
- private val topPlayedRepository: TopPlayedRepository
-) {
- private var mMusicService: WeakReference? = null
-
- fun setMusicService(service: MusicService) {
- mMusicService = WeakReference(service)
- }
-
- fun getChildren(mediaId: String?, resources: Resources): List {
- val mediaItems: MutableList = ArrayList()
- when (mediaId) {
- AutoMediaIDHelper.MEDIA_ID_ROOT -> {
- mediaItems.addAll(getRootChildren(resources))
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_PLAYLIST -> for (playlist in playlistsRepository.playlists()) {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_PLAYLIST, playlist.id)
- .icon(R.drawable.ic_playlist_play)
- .title(playlist.name)
- .subTitle(playlist.getInfoString(mContext))
- .asPlayable()
- .build()
- )
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_ALBUM -> for (album in albumsRepository.albums()) {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .path(mediaId, album.id)
- .title(album.title)
- .subTitle(album.albumArtist ?: album.artistName)
- .icon(MusicUtil.getMediaStoreAlbumCoverUri(album.id))
- .asPlayable()
- .build()
- )
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_ARTIST -> for (artist in artistsRepository.artists()) {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asPlayable()
- .path(mediaId, artist.id)
- .title(artist.name)
- .build()
- )
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_ALBUM_ARTIST -> for (artist in artistsRepository.albumArtists()) {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asPlayable()
- // we just pass album id here as we don't have album artist id's
- .path(mediaId, artist.safeGetFirstAlbum().id)
- .title(artist.name)
- .build()
- )
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_GENRE -> for (genre in genresRepository.genres()) {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asPlayable()
- .path(mediaId, genre.id)
- .title(genre.name)
- .build()
- )
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_QUEUE ->
- mMusicService?.get()?.playingQueue
- ?.let {
- for (song in it) {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asPlayable()
- .path(mediaId, song.id)
- .title(song.title)
- .subTitle(song.artistName)
- .icon(MusicUtil.getMediaStoreAlbumCoverUri(song.albumId))
- .build()
- )
- }
- }
- else -> {
- getPlaylistChildren(mediaId, mediaItems)
- }
- }
- return mediaItems
- }
-
- private fun getPlaylistChildren(
- mediaId: String?,
- mediaItems: MutableList
- ) {
- val songs = when (mediaId) {
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_TOP_TRACKS -> {
- topPlayedRepository.topTracks()
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_HISTORY -> {
- topPlayedRepository.recentlyPlayedTracks()
- }
- AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_SUGGESTIONS -> {
- topPlayedRepository.notRecentlyPlayedTracks().take(8)
- }
- else -> {
- emptyList()
- }
- }
- songs.forEach { song ->
- mediaItems.add(
- getPlayableSong(mediaId, song)
- )
- }
- }
-
- private fun getRootChildren(resources: Resources): List {
- val mediaItems: MutableList = ArrayList()
- val libraryCategories = PreferenceUtil.libraryCategory
- libraryCategories.forEach {
- if (it.visible) {
- when (it.category) {
- CategoryInfo.Category.Albums -> {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_ALBUM)
- .gridLayout(true)
- .icon(R.drawable.ic_album)
- .title(resources.getString(R.string.albums)).build()
- )
- }
- CategoryInfo.Category.Artists -> {
- if (PreferenceUtil.albumArtistsOnly) {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_ALBUM_ARTIST)
- .icon(R.drawable.ic_album_artist)
- .title(resources.getString(R.string.album_artist)).build()
- )
- } else {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_ARTIST)
- .icon(R.drawable.ic_artist)
- .title(resources.getString(R.string.artists)).build()
- )
- }
- }
- CategoryInfo.Category.Genres -> {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_GENRE)
- .icon(R.drawable.ic_guitar)
- .title(resources.getString(R.string.genres)).build()
- )
- }
- CategoryInfo.Category.Playlists -> {
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_PLAYLIST)
- .icon(R.drawable.ic_playlist_play)
- .title(resources.getString(R.string.playlists)).build()
- )
- }
- else -> {
- }
- }
- }
- }
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asPlayable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_SHUFFLE)
- .icon(R.drawable.ic_shuffle)
- .title(resources.getString(R.string.action_shuffle_all))
- .subTitle(MusicUtil.getPlaylistInfoString(mContext, songsRepository.songs()))
- .build()
- )
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_QUEUE)
- .icon(R.drawable.ic_queue_music)
- .title(resources.getString(R.string.queue))
- .subTitle(MusicUtil.getPlaylistInfoString(mContext, MusicPlayerRemote.playingQueue))
- .asBrowsable().build()
- )
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_TOP_TRACKS)
- .icon(R.drawable.ic_trending_up)
- .title(resources.getString(R.string.my_top_tracks))
- .subTitle(
- MusicUtil.getPlaylistInfoString(
- mContext,
- topPlayedRepository.topTracks()
- )
- )
- .asBrowsable().build()
- )
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_SUGGESTIONS)
- .icon(R.drawable.ic_face)
- .title(resources.getString(R.string.suggestion_songs))
- .subTitle(
- MusicUtil.getPlaylistInfoString(
- mContext,
- topPlayedRepository.notRecentlyPlayedTracks().takeIf {
- it.size > 9
- } ?: emptyList()
- )
- )
- .asBrowsable().build()
- )
- mediaItems.add(
- AutoMediaItem.with(mContext)
- .asBrowsable()
- .path(AutoMediaIDHelper.MEDIA_ID_MUSICS_BY_HISTORY)
- .icon(R.drawable.ic_history)
- .title(resources.getString(R.string.history))
- .subTitle(
- MusicUtil.getPlaylistInfoString(
- mContext,
- topPlayedRepository.recentlyPlayedTracks()
- )
- )
- .asBrowsable().build()
- )
- return mediaItems
- }
-
- private fun getPlayableSong(mediaId: String?, song: Song): MediaBrowserCompat.MediaItem {
- return AutoMediaItem.with(mContext)
- .asPlayable()
- .path(mediaId, song.id)
- .title(song.title)
- .subTitle(song.artistName)
- .icon(MusicUtil.getMediaStoreAlbumCoverUri(song.albumId))
- .build()
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/auto/MediaItemBuilder.kt b/app/src/main/java/code/name/monkey/retromusic/auto/MediaItemBuilder.kt
deleted file mode 100644
index 534b0ec52..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/auto/MediaItemBuilder.kt
+++ /dev/null
@@ -1,100 +0,0 @@
-package code.name.monkey.retromusic.auto
-
-import android.content.Context
-import android.net.Uri
-import android.support.v4.media.MediaBrowserCompat
-import android.support.v4.media.MediaDescriptionCompat
-import androidx.core.content.res.ResourcesCompat
-import androidx.core.graphics.drawable.toBitmap
-import androidx.core.os.bundleOf
-
-
-internal object AutoMediaItem {
- fun with(context: Context): Builder {
- return Builder(context)
- }
-
- internal class Builder(private val mContext: Context) {
- private var mBuilder: MediaDescriptionCompat.Builder?
- private var mFlags = 0
- fun path(fullPath: String): Builder {
- mBuilder?.setMediaId(fullPath)
- return this
- }
-
- fun path(path: String?, id: Long): Builder {
- return path(AutoMediaIDHelper.createMediaID(id.toString(), path))
- }
-
- fun title(title: String): Builder {
- mBuilder?.setTitle(title)
- return this
- }
-
- fun subTitle(subTitle: String): Builder {
- mBuilder?.setSubtitle(subTitle)
- return this
- }
-
- fun icon(uri: Uri?): Builder {
- mBuilder?.setIconUri(uri)
- return this
- }
-
- fun icon(iconDrawableId: Int): Builder {
- mBuilder?.setIconBitmap(
- ResourcesCompat.getDrawable(
- mContext.resources,
- iconDrawableId,
- mContext.theme
- )?.toBitmap()
- )
- return this
- }
-
- fun gridLayout(isGrid: Boolean): Builder {
-
- val hints = bundleOf(
- CONTENT_STYLE_SUPPORTED to true,
- CONTENT_STYLE_BROWSABLE_HINT to
- if (isGrid) CONTENT_STYLE_GRID_ITEM_HINT_VALUE
- else CONTENT_STYLE_LIST_ITEM_HINT_VALUE,
- CONTENT_STYLE_PLAYABLE_HINT to
- if (isGrid) CONTENT_STYLE_GRID_ITEM_HINT_VALUE
- else CONTENT_STYLE_LIST_ITEM_HINT_VALUE
- )
- mBuilder?.setExtras(hints)
- return this
- }
-
- fun asBrowsable(): Builder {
- mFlags = mFlags or MediaBrowserCompat.MediaItem.FLAG_BROWSABLE
- return this
- }
-
- fun asPlayable(): Builder {
- mFlags = mFlags or MediaBrowserCompat.MediaItem.FLAG_PLAYABLE
- return this
- }
-
- fun build(): MediaBrowserCompat.MediaItem {
- val result = MediaBrowserCompat.MediaItem(mBuilder!!.build(), mFlags)
- mBuilder = null
- mFlags = 0
- return result
- }
-
- init {
- mBuilder = MediaDescriptionCompat.Builder()
- }
- companion object{
- // Hints - see https://developer.android.com/training/cars/media#default-content-style
- const val CONTENT_STYLE_SUPPORTED = "android.media.browse.CONTENT_STYLE_SUPPORTED"
- const val CONTENT_STYLE_BROWSABLE_HINT = "android.media.browse.CONTENT_STYLE_BROWSABLE_HINT"
- const val CONTENT_STYLE_PLAYABLE_HINT = "android.media.browse.CONTENT_STYLE_PLAYABLE_HINT"
- const val CONTENT_STYLE_LIST_ITEM_HINT_VALUE = 1
- const val CONTENT_STYLE_GRID_ITEM_HINT_VALUE = 2
- }
-
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/BlackListStoreDao.kt b/app/src/main/java/code/name/monkey/retromusic/db/BlackListStoreDao.kt
deleted file mode 100644
index 0bf40b736..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/BlackListStoreDao.kt
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.*
-
-@Dao
-interface BlackListStoreDao {
- @Insert(onConflict = OnConflictStrategy.REPLACE)
- fun insertBlacklistPath(blackListStoreEntity: BlackListStoreEntity)
-
- @Insert(onConflict = OnConflictStrategy.REPLACE)
- suspend fun insertBlacklistPath(blackListStoreEntities: List)
-
- @Delete
- suspend fun deleteBlacklistPath(blackListStoreEntity: BlackListStoreEntity)
-
- @Query("DELETE FROM BlackListStoreEntity")
- suspend fun clearBlacklist()
-
- @Query("SELECT * FROM BlackListStoreEntity")
- fun blackListPaths(): List
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/BlackListStoreEntity.kt b/app/src/main/java/code/name/monkey/retromusic/db/BlackListStoreEntity.kt
deleted file mode 100644
index 8592442a2..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/BlackListStoreEntity.kt
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.Entity
-import androidx.room.PrimaryKey
-
-@Entity
-class BlackListStoreEntity(
- @PrimaryKey
- val path: String
-)
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/HistoryDao.kt b/app/src/main/java/code/name/monkey/retromusic/db/HistoryDao.kt
deleted file mode 100644
index 2ceb309db..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/HistoryDao.kt
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.lifecycle.LiveData
-import androidx.room.*
-
-@Dao
-interface HistoryDao {
- companion object {
- private const val HISTORY_LIMIT = 100
- }
-
- @Upsert
- suspend fun upsertSongInHistory(historyEntity: HistoryEntity)
-
- @Query("DELETE FROM HistoryEntity WHERE id= :songId")
- fun deleteSongInHistory(songId: Long)
-
- @Query("SELECT * FROM HistoryEntity ORDER BY time_played DESC LIMIT $HISTORY_LIMIT")
- fun historySongs(): List
-
- @Query("SELECT * FROM HistoryEntity ORDER BY time_played DESC LIMIT $HISTORY_LIMIT")
- fun observableHistorySongs(): LiveData>
-
- @Query("DELETE FROM HistoryEntity")
- suspend fun clearHistory()
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/HistoryEntity.kt b/app/src/main/java/code/name/monkey/retromusic/db/HistoryEntity.kt
deleted file mode 100644
index 535a37964..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/HistoryEntity.kt
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.ColumnInfo
-import androidx.room.Entity
-import androidx.room.PrimaryKey
-
-@Entity
-class HistoryEntity(
- @PrimaryKey
- val id: Long,
- val title: String,
- @ColumnInfo(name = "track_number")
- val trackNumber: Int,
- val year: Int,
- val duration: Long,
- val data: String,
- @ColumnInfo(name = "date_modified")
- val dateModified: Long,
- @ColumnInfo(name = "album_id")
- val albumId: Long,
- @ColumnInfo(name = "album_name")
- val albumName: String,
- @ColumnInfo(name = "artist_id")
- val artistId: Long,
- @ColumnInfo(name = "artist_name")
- val artistName: String,
- val composer: String?,
- @ColumnInfo(name = "album_artist")
- val albumArtist: String?,
- @ColumnInfo(name = "time_played")
- val timePlayed: Long
-)
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/LyricsDao.kt b/app/src/main/java/code/name/monkey/retromusic/db/LyricsDao.kt
deleted file mode 100644
index fa14b1aca..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/LyricsDao.kt
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.*
-
-@Dao
-interface LyricsDao {
- @Query("SELECT * FROM LyricsEntity WHERE songId =:songId LIMIT 1")
- fun lyricsWithSongId(songId: Int): LyricsEntity?
-
- @Insert
- fun insertLyrics(lyricsEntity: LyricsEntity)
-
- @Delete
- fun deleteLyrics(lyricsEntity: LyricsEntity)
-
- @Update
- fun updateLyrics(lyricsEntity: LyricsEntity)
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/LyricsEntity.kt b/app/src/main/java/code/name/monkey/retromusic/db/LyricsEntity.kt
deleted file mode 100644
index 91d987d62..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/LyricsEntity.kt
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.Entity
-import androidx.room.PrimaryKey
-
-@Entity
-class LyricsEntity(
- @PrimaryKey val songId: Int,
- val lyrics: String
-)
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/PlayCountDao.kt b/app/src/main/java/code/name/monkey/retromusic/db/PlayCountDao.kt
deleted file mode 100644
index 087ae4faf..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/PlayCountDao.kt
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.*
-
-@Dao
-interface PlayCountDao {
-
- @Upsert
- fun upsertSongInPlayCount(playCountEntity: PlayCountEntity)
-
- @Delete
- fun deleteSongInPlayCount(playCountEntity: PlayCountEntity)
-
- @Query("SELECT * FROM PlayCountEntity WHERE id =:songId LIMIT 1")
- fun findSongExistInPlayCount(songId: Long): PlayCountEntity?
-
- @Query("SELECT * FROM PlayCountEntity ORDER BY play_count DESC")
- fun playCountSongs(): List
-
- @Query("DELETE FROM SongEntity WHERE id =:songId")
- fun deleteSong(songId: Long)
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/PlayCountEntity.kt b/app/src/main/java/code/name/monkey/retromusic/db/PlayCountEntity.kt
deleted file mode 100644
index 2fa41b227..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/PlayCountEntity.kt
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.ColumnInfo
-import androidx.room.Entity
-import androidx.room.PrimaryKey
-
-@Entity
-class PlayCountEntity(
- @PrimaryKey
- val id: Long,
- val title: String,
- @ColumnInfo(name = "track_number")
- val trackNumber: Int,
- val year: Int,
- val duration: Long,
- val data: String,
- @ColumnInfo(name = "date_modified")
- val dateModified: Long,
- @ColumnInfo(name = "album_id")
- val albumId: Long,
- @ColumnInfo(name = "album_name")
- val albumName: String,
- @ColumnInfo(name = "artist_id")
- val artistId: Long,
- @ColumnInfo(name = "artist_name")
- val artistName: String,
- val composer: String?,
- @ColumnInfo(name = "album_artist")
- val albumArtist: String?,
- @ColumnInfo(name = "time_played")
- val timePlayed: Long,
- @ColumnInfo(name = "play_count")
- var playCount: Int
-)
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/PlaylistDao.kt b/app/src/main/java/code/name/monkey/retromusic/db/PlaylistDao.kt
deleted file mode 100644
index dea1e6b7d..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/PlaylistDao.kt
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.lifecycle.LiveData
-import androidx.room.*
-
-@Dao
-interface PlaylistDao {
- @Insert
- suspend fun createPlaylist(playlistEntity: PlaylistEntity): Long
-
- @Query("UPDATE PlaylistEntity SET playlist_name = :name WHERE playlist_id = :playlistId")
- suspend fun renamePlaylist(playlistId: Long, name: String)
-
- @Query("SELECT * FROM PlaylistEntity WHERE playlist_name = :name")
- fun playlist(name: String): List
-
- @Query("SELECT * FROM PlaylistEntity")
- suspend fun playlists(): List
-
- @Query("DELETE FROM SongEntity WHERE playlist_creator_id = :playlistId")
- suspend fun deletePlaylistSongs(playlistId: Long)
-
- @Query("DELETE FROM SongEntity WHERE playlist_creator_id = :playlistId AND id = :songId")
- suspend fun deleteSongFromPlaylist(playlistId: Long, songId: Long)
-
- @Transaction
- @Query("SELECT * FROM PlaylistEntity")
- suspend fun playlistsWithSongs(): List
-
- @Transaction
- @Query("SELECT * FROM PlaylistEntity WHERE playlist_id= :playlistId")
- fun getPlaylist(playlistId: Long): LiveData
-
- @Insert(onConflict = OnConflictStrategy.REPLACE)
- suspend fun insertSongsToPlaylist(songEntities: List)
-
- @Query("SELECT * FROM SongEntity WHERE playlist_creator_id = :playlistId AND id = :songId")
- suspend fun isSongExistsInPlaylist(playlistId: Long, songId: Long): List
-
- @Query("SELECT * FROM SongEntity WHERE playlist_creator_id = :playlistId ORDER BY song_key asc")
- fun songsFromPlaylist(playlistId: Long): LiveData>
-
- @Delete
- suspend fun deletePlaylist(playlistEntity: PlaylistEntity)
-
- @Delete
- suspend fun deletePlaylists(playlistEntities: List)
-
- @Delete
- suspend fun deletePlaylistSongs(songs: List)
-
- @RewriteQueriesToDropUnusedColumns
- @Query("SELECT * FROM SongEntity ,(SELECT playlist_id FROM PlaylistEntity WHERE playlist_name= :playlistName LIMIT 1) AS playlist WHERE playlist_creator_id= playlist.playlist_id")
- fun favoritesSongsLiveData(playlistName: String): LiveData>
-
- @Query("SELECT * FROM SongEntity WHERE playlist_creator_id= :playlistId")
- fun favoritesSongs(playlistId: Long): List
-
- @Query("SELECT EXISTS(SELECT * FROM PlaylistEntity WHERE playlist_id = :playlistId)")
- fun checkPlaylistExists(playlistId: Long): LiveData
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/PlaylistEntity.kt b/app/src/main/java/code/name/monkey/retromusic/db/PlaylistEntity.kt
deleted file mode 100644
index 5493b1155..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/PlaylistEntity.kt
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import android.os.Parcelable
-import androidx.room.ColumnInfo
-import androidx.room.Entity
-import androidx.room.PrimaryKey
-import kotlinx.parcelize.Parcelize
-
-@Entity
-@Parcelize
-class PlaylistEntity(
- @PrimaryKey(autoGenerate = true)
- @ColumnInfo(name = "playlist_id")
- val playListId: Long = 0,
- @ColumnInfo(name = "playlist_name")
- val playlistName: String
-) : Parcelable
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/PlaylistWithSongs.kt b/app/src/main/java/code/name/monkey/retromusic/db/PlaylistWithSongs.kt
deleted file mode 100644
index da80d8228..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/PlaylistWithSongs.kt
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import android.os.Parcelable
-import androidx.room.Embedded
-import androidx.room.Relation
-import kotlinx.parcelize.Parcelize
-
-@Parcelize
-data class PlaylistWithSongs(
- @Embedded val playlistEntity: PlaylistEntity,
- @Relation(
- parentColumn = "playlist_id",
- entityColumn = "playlist_creator_id"
- )
- val songs: List
-) : Parcelable
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/RetroDatabase.kt b/app/src/main/java/code/name/monkey/retromusic/db/RetroDatabase.kt
deleted file mode 100644
index 6401766aa..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/RetroDatabase.kt
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import androidx.room.Database
-import androidx.room.RoomDatabase
-
-@Database(
- entities = [PlaylistEntity::class, SongEntity::class, HistoryEntity::class, PlayCountEntity::class],
- version = 24,
- exportSchema = false
-)
-abstract class RetroDatabase : RoomDatabase() {
- abstract fun playlistDao(): PlaylistDao
- abstract fun playCountDao(): PlayCountDao
- abstract fun historyDao(): HistoryDao
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/RoomMigrations.kt b/app/src/main/java/code/name/monkey/retromusic/db/RoomMigrations.kt
deleted file mode 100644
index b8b383c31..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/RoomMigrations.kt
+++ /dev/null
@@ -1,11 +0,0 @@
-package code.name.monkey.retromusic.db
-
-import androidx.room.migration.Migration
-import androidx.sqlite.db.SupportSQLiteDatabase
-
-val MIGRATION_23_24 = object : Migration(23, 24) {
- override fun migrate(database: SupportSQLiteDatabase) {
- database.execSQL("DROP TABLE LyricsEntity")
- database.execSQL("DROP TABLE BlackListStoreEntity")
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/SongEntity.kt b/app/src/main/java/code/name/monkey/retromusic/db/SongEntity.kt
deleted file mode 100644
index 206c91e27..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/SongEntity.kt
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import android.os.Parcelable
-import androidx.room.ColumnInfo
-import androidx.room.Entity
-import androidx.room.Index
-import androidx.room.PrimaryKey
-import kotlinx.parcelize.Parcelize
-
-@Parcelize
-@Entity(indices = [Index(value = ["playlist_creator_id", "id"], unique = true)])
-class SongEntity(
- @PrimaryKey(autoGenerate = true)
- @ColumnInfo(name = "song_key")
- val songPrimaryKey: Long = 0L,
- @ColumnInfo(name = "playlist_creator_id")
- val playlistCreatorId: Long,
- val id: Long,
- val title: String,
- @ColumnInfo(name = "track_number")
- val trackNumber: Int,
- val year: Int,
- val duration: Long,
- val data: String,
- @ColumnInfo(name = "date_modified")
- val dateModified: Long,
- @ColumnInfo(name = "album_id")
- val albumId: Long,
- @ColumnInfo(name = "album_name")
- val albumName: String,
- @ColumnInfo(name = "artist_id")
- val artistId: Long,
- @ColumnInfo(name = "artist_name")
- val artistName: String,
- val composer: String?,
- @ColumnInfo(name = "album_artist")
- val albumArtist: String?
-) : Parcelable
diff --git a/app/src/main/java/code/name/monkey/retromusic/db/SongExtension.kt b/app/src/main/java/code/name/monkey/retromusic/db/SongExtension.kt
deleted file mode 100644
index d6fe11b05..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/db/SongExtension.kt
+++ /dev/null
@@ -1,153 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.db
-
-import code.name.monkey.retromusic.model.Song
-
-fun List.fromHistoryToSongs(): List {
- return map {
- it.toSong()
- }
-}
-
-fun List.toSongs(): List {
- return map {
- it.toSong()
- }
-}
-
-fun Song.toHistoryEntity(timePlayed: Long): HistoryEntity {
- return HistoryEntity(
- id = id,
- title = title,
- trackNumber = trackNumber,
- year = year,
- duration = duration,
- data = data,
- dateModified = dateModified,
- albumId = albumId,
- albumName = albumName,
- artistId = artistId,
- artistName = artistName,
- composer = composer,
- albumArtist = albumArtist,
- timePlayed = timePlayed
- )
-}
-
-fun Song.toSongEntity(playListId: Long): SongEntity {
- return SongEntity(
- playlistCreatorId = playListId,
- id = id,
- title = title,
- trackNumber = trackNumber,
- year = year,
- duration = duration,
- data = data,
- dateModified = dateModified,
- albumId = albumId,
- albumName = albumName,
- artistId = artistId,
- artistName = artistName,
- composer = composer,
- albumArtist = albumArtist
- )
-}
-
-fun SongEntity.toSong(): Song {
- return Song(
- id = id,
- title = title,
- trackNumber = trackNumber,
- year = year,
- duration = duration,
- data = data,
- dateModified = dateModified,
- albumId = albumId,
- albumName = albumName,
- artistId = artistId,
- artistName = artistName,
- composer = composer,
- albumArtist = albumArtist
- )
-}
-
-fun PlayCountEntity.toSong(): Song {
- return Song(
- id = id,
- title = title,
- trackNumber = trackNumber,
- year = year,
- duration = duration,
- data = data,
- dateModified = dateModified,
- albumId = albumId,
- albumName = albumName,
- artistId = artistId,
- artistName = artistName,
- composer = composer,
- albumArtist = albumArtist
- )
-}
-
-fun HistoryEntity.toSong(): Song {
- return Song(
- id = id,
- title = title,
- trackNumber = trackNumber,
- year = year,
- duration = duration,
- data = data,
- dateModified = dateModified,
- albumId = albumId,
- albumName = albumName,
- artistId = artistId,
- artistName = artistName,
- composer = composer,
- albumArtist = albumArtist
- )
-}
-
-fun Song.toPlayCount(): PlayCountEntity {
- return PlayCountEntity(
- id = id,
- title = title,
- trackNumber = trackNumber,
- year = year,
- duration = duration,
- data = data,
- dateModified = dateModified,
- albumId = albumId,
- albumName = albumName,
- artistId = artistId,
- artistName = artistName,
- composer = composer,
- albumArtist = albumArtist,
- timePlayed = System.currentTimeMillis(),
- playCount = 1
- )
-}
-
-fun List.toSongsEntity(playlistEntity: PlaylistEntity): List {
- return map {
- it.toSongEntity(playlistEntity.playListId)
- }
-}
-
-fun List.toSongsEntity(playlistId: Long): List {
- return map {
- it.toSongEntity(playlistId)
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/AddToPlaylistDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/AddToPlaylistDialog.kt
deleted file mode 100644
index aa47f0fe2..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/AddToPlaylistDialog.kt
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.os.Bundle
-import androidx.core.os.bundleOf
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.EXTRA_PLAYLISTS
-import code.name.monkey.retromusic.EXTRA_SONG
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.db.PlaylistEntity
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.extraNotNull
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.model.Song
-import org.koin.androidx.viewmodel.ext.android.activityViewModel
-
-class AddToPlaylistDialog : DialogFragment() {
- private val libraryViewModel by activityViewModel()
-
- companion object {
- fun create(playlistEntities: List, song: Song): AddToPlaylistDialog {
- val list: MutableList = mutableListOf()
- list.add(song)
- return create(playlistEntities, list)
- }
-
- fun create(playlistEntities: List, songs: List): AddToPlaylistDialog {
- return AddToPlaylistDialog().apply {
- arguments = bundleOf(
- EXTRA_SONG to songs,
- EXTRA_PLAYLISTS to playlistEntities
- )
- }
- }
- }
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- val playlistEntities = extraNotNull>(EXTRA_PLAYLISTS).value
- val songs = extraNotNull>(EXTRA_SONG).value
- val playlistNames = mutableListOf()
- playlistNames.add(requireContext().resources.getString(R.string.action_new_playlist))
- for (entity: PlaylistEntity in playlistEntities) {
- playlistNames.add(entity.playlistName)
- }
- return materialDialog(R.string.add_playlist_title)
- .setItems(playlistNames.toTypedArray()) { dialog, which ->
- if (which == 0) {
- showCreateDialog(songs)
- } else {
- libraryViewModel.addToPlaylist(requireContext(), playlistNames[which], songs)
- }
- dialog.dismiss()
- }
- .setNegativeButton(R.string.action_cancel, null)
- .create()
- .colorButtons()
- }
-
- private fun showCreateDialog(songs: List) {
- CreatePlaylistDialog.create(songs).show(requireActivity().supportFragmentManager, "Dialog")
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/BlacklistFolderChooserDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/BlacklistFolderChooserDialog.kt
deleted file mode 100644
index 5701d858b..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/BlacklistFolderChooserDialog.kt
+++ /dev/null
@@ -1,140 +0,0 @@
-package code.name.monkey.retromusic.dialogs
-
-import android.Manifest
-import android.app.Dialog
-import android.content.Context
-import android.content.pm.PackageManager
-import android.os.Bundle
-import androidx.core.app.ActivityCompat
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.util.getExternalStorageDirectory
-import com.afollestad.materialdialogs.MaterialDialog
-import com.afollestad.materialdialogs.list.listItems
-import com.afollestad.materialdialogs.list.updateListItems
-import java.io.File
-
-class BlacklistFolderChooserDialog : DialogFragment() {
- private var initialPath: String = getExternalStorageDirectory().absolutePath
- private var parentFolder: File? = null
- private var parentContents: Array? = null
- private var canGoUp = false
- private var callback: FolderCallback? = null
- private val contentsArray: Array
- get() {
- if (parentContents == null) {
- return if (canGoUp) {
- arrayOf("..")
- } else arrayOf()
- }
- val results = arrayOfNulls(parentContents!!.size + if (canGoUp) 1 else 0)
- if (canGoUp) {
- results[0] = ".."
- }
- for (i in parentContents!!.indices) {
- results[if (canGoUp) i + 1 else i] = parentContents?.getOrNull(i)?.name
- }
- return results
- }
-
- private fun listFiles(): Array? {
- val results = mutableListOf()
- parentFolder?.listFiles()?.let { files ->
- files.forEach { file -> if (file.isDirectory) results.add(file) }
- return results.sortedBy { it.name }.toTypedArray()
- }
- return null
- }
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- var mSavedInstanceState = savedInstanceState
- if (VersionUtils.hasMarshmallow()
- && ActivityCompat.checkSelfPermission(
- requireActivity(), Manifest.permission.READ_EXTERNAL_STORAGE
- )
- != PackageManager.PERMISSION_GRANTED
- ) {
- return materialDialog().show {
- title(res = R.string.md_error_label)
- message(res = R.string.md_storage_perm_error)
- positiveButton(res = android.R.string.ok)
- }
- }
- if (mSavedInstanceState == null) {
- mSavedInstanceState = Bundle()
- }
- if (!mSavedInstanceState.containsKey("current_path")) {
- mSavedInstanceState.putString("current_path", initialPath)
- }
- parentFolder = File(mSavedInstanceState.getString("current_path", File.pathSeparator))
- checkIfCanGoUp()
- parentContents = listFiles()
- return materialDialog()
- .title(text = parentFolder?.absolutePath)
- .listItems(
- items = contentsArray.toCharSequence(),
- waitForPositiveButton = false
- ) { _: MaterialDialog, i: Int, _: CharSequence ->
- onSelection(i)
- }
- .noAutoDismiss()
- .positiveButton(res = R.string.add_action) {
- callback?.onFolderSelection(requireContext(), parentFolder!!)
- dismiss()
- }
- .negativeButton(res = android.R.string.cancel) { dismiss() }
- }
-
- private fun onSelection(i: Int) {
- if (canGoUp && i == 0) {
- parentFolder = parentFolder?.parentFile
- if (parentFolder?.absolutePath == "/storage/emulated") {
- parentFolder = parentFolder?.parentFile
- }
- checkIfCanGoUp()
- } else {
- parentFolder = parentContents?.getOrNull(if (canGoUp) i - 1 else i)
- canGoUp = true
- if (parentFolder?.absolutePath == "/storage/emulated") {
- parentFolder = getExternalStorageDirectory()
- }
- }
- reload()
- }
-
- private fun checkIfCanGoUp() {
- canGoUp = parentFolder?.parent != null
- }
-
- private fun reload() {
- parentContents = listFiles()
- val dialog = dialog as MaterialDialog?
- dialog?.setTitle(parentFolder?.absolutePath)
- dialog?.updateListItems(items = contentsArray.toCharSequence())
- }
-
- private fun Array.toCharSequence(): List {
- return map { it as CharSequence }
- }
-
- override fun onSaveInstanceState(outState: Bundle) {
- super.onSaveInstanceState(outState)
- outState.putString("current_path", parentFolder?.absolutePath)
- }
-
- fun setCallback(callback: FolderCallback?) {
- this.callback = callback
- }
-
- interface FolderCallback {
- fun onFolderSelection(context: Context, folder: File)
- }
-
- companion object {
- fun create(): BlacklistFolderChooserDialog {
- return BlacklistFolderChooserDialog()
- }
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/CreatePlaylistDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/CreatePlaylistDialog.kt
deleted file mode 100644
index 7d7a01c90..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/CreatePlaylistDialog.kt
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.os.Bundle
-import android.text.TextUtils
-import androidx.core.os.bundleOf
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.EXTRA_SONG
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.DialogPlaylistBinding
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.extra
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.model.Song
-import com.google.android.material.textfield.TextInputEditText
-import com.google.android.material.textfield.TextInputLayout
-import org.koin.androidx.viewmodel.ext.android.activityViewModel
-
-class CreatePlaylistDialog : DialogFragment() {
- private var _binding: DialogPlaylistBinding? = null
- private val binding get() = _binding!!
- private val libraryViewModel by activityViewModel()
-
- companion object {
- fun create(song: Song): CreatePlaylistDialog {
- val list = mutableListOf()
- list.add(song)
- return create(list)
- }
-
- fun create(songs: List): CreatePlaylistDialog {
- return CreatePlaylistDialog().apply {
- arguments = bundleOf(EXTRA_SONG to songs)
- }
- }
- }
-
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- _binding = DialogPlaylistBinding.inflate(layoutInflater)
-
- val songs: List = extra>(EXTRA_SONG).value ?: emptyList()
- val playlistView: TextInputEditText = binding.actionNewPlaylist
- val playlistContainer: TextInputLayout = binding.actionNewPlaylistContainer
- return materialDialog(R.string.new_playlist_title)
- .setView(binding.root)
- .setPositiveButton(
- R.string.create_action
- ) { _, _ ->
- val playlistName = playlistView.text.toString()
- if (!TextUtils.isEmpty(playlistName)) {
- libraryViewModel.addToPlaylist(requireContext(), playlistName, songs)
- } else {
- playlistContainer.error = "Playlist name can't be empty"
- }
- }
- .setNegativeButton(R.string.action_cancel, null)
- .create()
- .colorButtons()
- }
-
- override fun onDestroyView() {
- super.onDestroyView()
- _binding = null
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/DeletePlaylistDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/DeletePlaylistDialog.kt
deleted file mode 100644
index 30675d88a..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/DeletePlaylistDialog.kt
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.os.Bundle
-import androidx.core.os.bundleOf
-import androidx.core.text.parseAsHtml
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.EXTRA_PLAYLIST
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.db.PlaylistEntity
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.extraNotNull
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.fragments.ReloadType
-import org.koin.androidx.viewmodel.ext.android.activityViewModel
-
-class DeletePlaylistDialog : DialogFragment() {
-
- private val libraryViewModel by activityViewModel()
-
- companion object {
-
- fun create(playlist: PlaylistEntity): DeletePlaylistDialog {
- val list = mutableListOf()
- list.add(playlist)
- return create(list)
- }
-
- fun create(playlists: List): DeletePlaylistDialog {
- return DeletePlaylistDialog().apply {
- arguments = bundleOf(EXTRA_PLAYLIST to playlists)
- }
- }
- }
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- val playlists = extraNotNull>(EXTRA_PLAYLIST).value
- val title: Int
- val message: CharSequence
- //noinspection ConstantConditions
- if (playlists.size > 1) {
- title = R.string.delete_playlists_title
- message =
- String.format(getString(R.string.delete_x_playlists), playlists.size).parseAsHtml()
- } else {
- title = R.string.delete_playlist_title
- message =
- String.format(getString(R.string.delete_playlist_x), playlists[0].playlistName)
- .parseAsHtml()
- }
-
- return materialDialog(title)
- .setTitle(title)
- .setMessage(message)
- .setNegativeButton(android.R.string.cancel, null)
- .setPositiveButton(R.string.action_delete) { _, _ ->
- libraryViewModel.deleteSongsFromPlaylist(playlists)
- libraryViewModel.deleteRoomPlaylist(playlists)
- libraryViewModel.forceReload(ReloadType.Playlists)
- }
- .create()
- .colorButtons()
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/DeleteSongsDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/DeleteSongsDialog.kt
deleted file mode 100644
index 5fd45b060..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/DeleteSongsDialog.kt
+++ /dev/null
@@ -1,162 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Activity
-import android.app.Dialog
-import android.content.Intent
-import android.os.Bundle
-import android.provider.MediaStore
-import androidx.activity.result.IntentSenderRequest
-import androidx.activity.result.contract.ActivityResultContracts
-import androidx.core.os.bundleOf
-import androidx.core.text.parseAsHtml
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.EXTRA_SONG
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.extensions.extraNotNull
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.fragments.ReloadType
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.SAFUtil
-import kotlinx.coroutines.CoroutineScope
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.launch
-import org.koin.androidx.viewmodel.ext.android.getViewModel
-
-class DeleteSongsDialog : DialogFragment() {
- lateinit var libraryViewModel: LibraryViewModel
-
- companion object {
- fun create(song: Song): DeleteSongsDialog {
- val list = ArrayList()
- list.add(song)
- return create(list)
- }
-
- fun create(songs: List): DeleteSongsDialog {
- return DeleteSongsDialog().apply {
- arguments = bundleOf(
- EXTRA_SONG to ArrayList(songs)
- )
- }
- }
- }
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- libraryViewModel = activity?.getViewModel() as LibraryViewModel
- val songs = extraNotNull>(EXTRA_SONG).value
- if (VersionUtils.hasR()) {
- val deleteResultLauncher =
- registerForActivityResult(ActivityResultContracts.StartIntentSenderForResult()) { result ->
- if (result.resultCode == Activity.RESULT_OK) {
- if ((songs.size == 1) && MusicPlayerRemote.isPlaying(songs[0])) {
- MusicPlayerRemote.playNextSong()
- }
- MusicPlayerRemote.removeFromQueue(songs)
- reloadTabs()
- }
- dismiss()
- }
- val pendingIntent =
- MediaStore.createDeleteRequest(requireActivity().contentResolver, songs.map {
- MusicUtil.getSongFileUri(it.id)
- })
- deleteResultLauncher.launch(
- IntentSenderRequest.Builder(pendingIntent.intentSender).build()
- )
- return super.onCreateDialog(savedInstanceState)
- } else {
- val pair = if (songs.size > 1) {
- Pair(
- R.string.delete_songs_title,
- String.format(getString(R.string.delete_x_songs), songs.size).parseAsHtml()
- )
- } else {
- Pair(
- R.string.delete_song_title,
- String.format(getString(R.string.delete_song_x), songs[0].title).parseAsHtml()
- )
- }
-
- return materialDialog()
- .title(pair.first)
- .message(text = pair.second)
- .noAutoDismiss()
- .negativeButton(android.R.string.cancel)
- {
- dismiss()
- }
- .positiveButton(R.string.action_delete)
- {
- if ((songs.size == 1) && MusicPlayerRemote.isPlaying(songs[0])) {
- MusicPlayerRemote.playNextSong()
- }
- if (!SAFUtil.isSAFRequiredForSongs(songs)) {
- CoroutineScope(Dispatchers.IO).launch {
- dismiss()
- MusicUtil.deleteTracks(requireContext(), songs)
- reloadTabs()
- }
- } else {
- if (SAFUtil.isSDCardAccessGranted(requireActivity())) {
- deleteSongs(songs)
- } else {
- startActivityForResult(
- Intent(requireActivity(), code.name.monkey.retromusic.activities.saf.SAFGuideActivity::class.java),
- code.name.monkey.retromusic.activities.saf.SAFGuideActivity.REQUEST_CODE_SAF_GUIDE
- )
- }
- }
- }
- }
- }
-
- override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
- super.onActivityResult(requestCode, resultCode, data)
- when (requestCode) {
- code.name.monkey.retromusic.activities.saf.SAFGuideActivity.REQUEST_CODE_SAF_GUIDE -> {
- SAFUtil.openTreePicker(this)
- }
- SAFUtil.REQUEST_SAF_PICK_TREE,
- SAFUtil.REQUEST_SAF_PICK_FILE -> {
- if (resultCode == Activity.RESULT_OK) {
- SAFUtil.saveTreeUri(requireActivity(), data)
- val songs = extraNotNull>(EXTRA_SONG).value
- deleteSongs(songs)
- }
- }
- }
- }
-
- fun deleteSongs(songs: List) {
- CoroutineScope(Dispatchers.IO).launch {
- dismiss()
- MusicUtil.deleteTracks(requireActivity(), songs, null, null)
- reloadTabs()
- }
- }
-
- private fun reloadTabs() {
- libraryViewModel.forceReload(ReloadType.Songs)
- libraryViewModel.forceReload(ReloadType.HomeSections)
- libraryViewModel.forceReload(ReloadType.Artists)
- libraryViewModel.forceReload(ReloadType.Albums)
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/ImportPlaylistDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/ImportPlaylistDialog.kt
deleted file mode 100644
index 87e3b6dbd..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/ImportPlaylistDialog.kt
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.os.Bundle
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import org.koin.androidx.viewmodel.ext.android.activityViewModel
-
-class ImportPlaylistDialog : DialogFragment() {
- private val libraryViewModel by activityViewModel()
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- return materialDialog(R.string.import_playlist)
- .setMessage(R.string.import_playlist_message)
- .setPositiveButton(R.string.import_label) { _, _ ->
- try {
- libraryViewModel.importPlaylists()
- } catch (e: Exception) {
- e.printStackTrace()
- }
- }
- .create()
- .colorButtons()
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/PlaybackSpeedDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/PlaybackSpeedDialog.kt
deleted file mode 100644
index 6965d0831..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/PlaybackSpeedDialog.kt
+++ /dev/null
@@ -1,58 +0,0 @@
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.os.Bundle
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.DialogPlaybackSpeedBinding
-import code.name.monkey.retromusic.extensions.accent
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.util.PreferenceUtil
-import com.google.android.material.slider.Slider
-
-class PlaybackSpeedDialog : DialogFragment() {
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- val binding = DialogPlaybackSpeedBinding.inflate(layoutInflater)
- binding.playbackSpeedSlider.accent()
- binding.playbackPitchSlider.accent()
- binding.playbackSpeedSlider.addOnChangeListener(Slider.OnChangeListener { _, value, _ ->
- binding.speedValue.text = "$value"
- })
- binding.playbackPitchSlider.addOnChangeListener(Slider.OnChangeListener { _, value, _ ->
- binding.pitchValue.text = "$value"
- })
- binding.playbackSpeedSlider.value = PreferenceUtil.playbackSpeed
- binding.playbackPitchSlider.value = PreferenceUtil.playbackPitch
-
- return materialDialog(R.string.playback_settings)
- .setNegativeButton(android.R.string.cancel, null)
- .setPositiveButton(R.string.save) { _, _ ->
- updatePlaybackAndPitch(
- binding.playbackSpeedSlider.value,
- binding.playbackPitchSlider.value
- )
- }
- .setNeutralButton(R.string.reset_action) {_, _ ->
- updatePlaybackAndPitch(
- 1F,
- 1F
- )
- }
- .setView(binding.root)
- .create()
- .colorButtons()
- }
-
- private fun updatePlaybackAndPitch(speed: Float, pitch: Float) {
- PreferenceUtil.playbackSpeed = speed
- PreferenceUtil.playbackPitch = pitch
- }
-
- companion object {
- fun newInstance(): PlaybackSpeedDialog {
- return PlaybackSpeedDialog()
- }
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/RemoveSongFromPlaylistDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/RemoveSongFromPlaylistDialog.kt
deleted file mode 100644
index cd94bc480..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/RemoveSongFromPlaylistDialog.kt
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.os.Bundle
-import androidx.core.os.bundleOf
-import androidx.core.text.parseAsHtml
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.EXTRA_SONG
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.db.SongEntity
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.extraNotNull
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import org.koin.androidx.viewmodel.ext.android.activityViewModel
-
-class RemoveSongFromPlaylistDialog : DialogFragment() {
- private val libraryViewModel by activityViewModel()
-
- companion object {
- fun create(song: SongEntity): RemoveSongFromPlaylistDialog {
- val list = mutableListOf()
- list.add(song)
- return create(list)
- }
-
- fun create(songs: List): RemoveSongFromPlaylistDialog {
- return RemoveSongFromPlaylistDialog().apply {
- arguments = bundleOf(
- EXTRA_SONG to songs
- )
- }
- }
- }
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- val songs = extraNotNull>(EXTRA_SONG).value
- val pair = if (songs.size > 1) {
- Pair(
- R.string.remove_songs_from_playlist_title,
- String.format(getString(R.string.remove_x_songs_from_playlist), songs.size)
- .parseAsHtml()
- )
- } else {
- Pair(
- R.string.remove_song_from_playlist_title,
- String.format(
- getString(R.string.remove_song_x_from_playlist),
- songs[0].title
- ).parseAsHtml()
- )
- }
- return materialDialog(pair.first)
- .setMessage(pair.second)
- .setPositiveButton(R.string.remove_action) { _, _ ->
- libraryViewModel.deleteSongsInPlaylist(songs)
- }
- .setNegativeButton(android.R.string.cancel, null)
- .create()
- .colorButtons()
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/RenamePlaylistDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/RenamePlaylistDialog.kt
deleted file mode 100644
index 803315277..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/RenamePlaylistDialog.kt
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.os.Bundle
-import androidx.core.os.bundleOf
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.EXTRA_PLAYLIST_ID
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.db.PlaylistEntity
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.extraNotNull
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.fragments.ReloadType
-import com.google.android.material.textfield.TextInputEditText
-import com.google.android.material.textfield.TextInputLayout
-import org.koin.androidx.viewmodel.ext.android.activityViewModel
-
-class RenamePlaylistDialog : DialogFragment() {
-
- private val libraryViewModel by activityViewModel()
-
- companion object {
- fun create(playlistEntity: PlaylistEntity): RenamePlaylistDialog {
- return RenamePlaylistDialog().apply {
- arguments = bundleOf(
- EXTRA_PLAYLIST_ID to playlistEntity
- )
- }
- }
- }
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- val playlistEntity = extraNotNull(EXTRA_PLAYLIST_ID).value
- val layout = layoutInflater.inflate(R.layout.dialog_playlist, null)
- val inputEditText: TextInputEditText = layout.findViewById(R.id.actionNewPlaylist)
- val nameContainer: TextInputLayout = layout.findViewById(R.id.actionNewPlaylistContainer)
- nameContainer.accentColor()
- inputEditText.setText(playlistEntity.playlistName)
- return materialDialog(R.string.rename_playlist_title)
- .setView(layout)
- .setNegativeButton(android.R.string.cancel, null)
- .setPositiveButton(R.string.action_rename) { _, _ ->
- val name = inputEditText.text.toString()
- if (name.isNotEmpty()) {
- libraryViewModel.renameRoomPlaylist(playlistEntity.playListId, name)
- libraryViewModel.forceReload(ReloadType.Playlists)
- } else {
- nameContainer.error = "Playlist name should'nt be empty"
- }
- }
- .create()
- .colorButtons()
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/SavePlaylistDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/SavePlaylistDialog.kt
deleted file mode 100644
index 157a1b221..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/SavePlaylistDialog.kt
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.media.MediaScannerConnection
-import android.os.Bundle
-import android.widget.Toast
-import androidx.core.os.bundleOf
-import androidx.fragment.app.DialogFragment
-import androidx.lifecycle.lifecycleScope
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.EXTRA_PLAYLIST
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.db.PlaylistWithSongs
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.helper.M3UWriter
-import code.name.monkey.retromusic.util.PlaylistsUtil
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.launch
-import kotlinx.coroutines.withContext
-
-class SavePlaylistDialog : DialogFragment() {
- companion object {
- fun create(playlistWithSongs: PlaylistWithSongs): SavePlaylistDialog {
- return SavePlaylistDialog().apply {
- arguments = bundleOf(
- EXTRA_PLAYLIST to playlistWithSongs
- )
- }
- }
- }
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- val playlistWithSongs = extraNotNull(EXTRA_PLAYLIST).value
-
- if (VersionUtils.hasR()) {
- createNewFile(
- "audio/mpegurl",
- playlistWithSongs.playlistEntity.playlistName
- ) { outputStream, data ->
- try {
- if (outputStream != null) {
- lifecycleScope.launch(Dispatchers.IO) {
- M3UWriter.writeIO(
- outputStream,
- playlistWithSongs
- )
- withContext(Dispatchers.Main) {
- showToast(
- requireContext().getString(R.string.saved_playlist_to,
- data?.lastPathSegment),
- Toast.LENGTH_LONG
- )
- dismiss()
- }
- }
- }
- } catch (e: Exception) {
- showToast(
- "Something went wrong : " + e.message
- )
- }
- }
- } else {
- lifecycleScope.launch(Dispatchers.IO) {
- val file = PlaylistsUtil.savePlaylistWithSongs(playlistWithSongs)
- MediaScannerConnection.scanFile(
- requireActivity(),
- arrayOf(file.path),
- null
- ) { _, _ ->
- }
- withContext(Dispatchers.Main) {
- showToast(
- getString(R.string.saved_playlist_to, file),
- Toast.LENGTH_LONG
- )
- dismiss()
- }
- }
- }
- }
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- return materialDialog(R.string.save_playlist_title)
- .setView(R.layout.loading)
- .create().colorButtons()
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/SleepTimerDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/SleepTimerDialog.kt
deleted file mode 100755
index 32de5ba6c..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/SleepTimerDialog.kt
+++ /dev/null
@@ -1,189 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.AlarmManager
-import android.app.Dialog
-import android.app.PendingIntent
-import android.content.DialogInterface
-import android.content.Intent
-import android.os.Bundle
-import android.os.CountDownTimer
-import android.os.SystemClock
-import android.widget.CheckBox
-import android.widget.SeekBar
-import android.widget.TextView
-import android.widget.Toast
-import androidx.appcompat.app.AlertDialog
-import androidx.core.content.getSystemService
-import androidx.core.view.isVisible
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.DialogSleepTimerBinding
-import code.name.monkey.retromusic.extensions.addAccentColor
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.service.MusicService.Companion.ACTION_PENDING_QUIT
-import code.name.monkey.retromusic.service.MusicService.Companion.ACTION_QUIT
-import code.name.monkey.retromusic.util.MusicUtil
-import code.name.monkey.retromusic.util.PreferenceUtil
-
-class SleepTimerDialog : DialogFragment() {
-
- private var seekArcProgress: Int = 0
- private lateinit var timerUpdater: TimerUpdater
- private lateinit var dialog: AlertDialog
-
- private var _binding: DialogSleepTimerBinding? = null
- private val binding get() = _binding!!
-
- private val shouldFinishLastSong: CheckBox get() = binding.shouldFinishLastSong
- private val seekBar: SeekBar get() = binding.seekBar
- private val timerDisplay: TextView get() = binding.timerDisplay
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- timerUpdater = TimerUpdater()
- _binding = DialogSleepTimerBinding.inflate(layoutInflater)
-
- val finishMusic = PreferenceUtil.isSleepTimerFinishMusic
- shouldFinishLastSong.apply {
- addAccentColor()
- isChecked = finishMusic
- }
- seekBar.apply {
- addAccentColor()
- seekArcProgress = PreferenceUtil.lastSleepTimerValue
- updateTimeDisplayTime()
- progress = seekArcProgress
- }
-
- binding.seekBar.setOnSeekBarChangeListener(object : SeekBar.OnSeekBarChangeListener {
- override fun onProgressChanged(seekBar: SeekBar, i: Int, b: Boolean) {
- if (i < 1) {
- seekBar.progress = 1
- return
- }
- seekArcProgress = i
- updateTimeDisplayTime()
- }
-
- override fun onStartTrackingTouch(seekBar: SeekBar) {
- }
-
- override fun onStopTrackingTouch(seekBar: SeekBar) {
- PreferenceUtil.lastSleepTimerValue = seekArcProgress
- }
- })
-
- materialDialog(R.string.action_sleep_timer).apply {
- if (PreferenceUtil.nextSleepTimerElapsedRealTime > System.currentTimeMillis()) {
- seekBar.isVisible = false
- shouldFinishLastSong.isVisible = false
- timerUpdater.start()
- setPositiveButton(android.R.string.ok, null)
- setNegativeButton(R.string.action_cancel) { _, _ ->
- timerUpdater.cancel()
- val previous = makeTimerPendingIntent(PendingIntent.FLAG_NO_CREATE)
- if (previous != null) {
- val am = requireContext().getSystemService()
- am?.cancel(previous)
- previous.cancel()
- Toast.makeText(
- requireContext(),
- requireContext().resources.getString(R.string.sleep_timer_canceled),
- Toast.LENGTH_SHORT
- ).show()
- val musicService = MusicPlayerRemote.musicService
- if (musicService != null && musicService.pendingQuit) {
- musicService.pendingQuit = false
- Toast.makeText(
- requireContext(),
- requireContext().resources.getString(R.string.sleep_timer_canceled),
- Toast.LENGTH_SHORT
- ).show()
- }
- }
- }
- } else {
- seekBar.isVisible = true
- shouldFinishLastSong.isVisible = true
- setPositiveButton(R.string.action_set) { _, _ ->
- PreferenceUtil.isSleepTimerFinishMusic = shouldFinishLastSong.isChecked
- val minutes = seekArcProgress
- val pi = makeTimerPendingIntent(PendingIntent.FLAG_CANCEL_CURRENT)
- val nextSleepTimerElapsedTime =
- SystemClock.elapsedRealtime() + minutes * 60 * 1000
- PreferenceUtil.nextSleepTimerElapsedRealTime = nextSleepTimerElapsedTime.toInt()
- val am = requireContext().getSystemService()
- am?.setExact(
- AlarmManager.ELAPSED_REALTIME_WAKEUP,
- nextSleepTimerElapsedTime,
- pi
- )
-
- Toast.makeText(
- requireContext(),
- requireContext().resources.getString(R.string.sleep_timer_set, minutes),
- Toast.LENGTH_SHORT
- ).show()
- }
- }
- setView(binding.root)
- dialog = create()
-
- }
- return dialog
- }
-
- private fun updateTimeDisplayTime() {
- timerDisplay.text = "$seekArcProgress min"
- }
-
- private fun makeTimerPendingIntent(flag: Int): PendingIntent? {
- return PendingIntent.getService(
- requireActivity(), 0, makeTimerIntent(), flag or if (VersionUtils.hasMarshmallow())
- PendingIntent.FLAG_IMMUTABLE
- else 0
- )
- }
-
- private fun makeTimerIntent(): Intent {
- val intent = Intent(requireActivity(), MusicService::class.java)
- return if (shouldFinishLastSong.isChecked) {
- intent.setAction(ACTION_PENDING_QUIT)
- } else intent.setAction(ACTION_QUIT)
- }
-
- override fun onDismiss(dialog: DialogInterface) {
- super.onDismiss(dialog)
- timerUpdater.cancel()
- _binding = null
- }
-
- private inner class TimerUpdater :
- CountDownTimer(
- PreferenceUtil.nextSleepTimerElapsedRealTime - SystemClock.elapsedRealtime(),
- 1000
- ) {
-
- override fun onTick(millisUntilFinished: Long) {
- timerDisplay.text = MusicUtil.getReadableDurationString(millisUntilFinished)
- }
-
- override fun onFinish() {}
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/dialogs/SongDetailDialog.kt b/app/src/main/java/code/name/monkey/retromusic/dialogs/SongDetailDialog.kt
deleted file mode 100644
index 19995db30..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/dialogs/SongDetailDialog.kt
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.dialogs
-
-import android.app.Dialog
-import android.content.Context
-import android.os.Bundle
-import android.text.Spanned
-import android.util.Log
-import androidx.core.os.BundleCompat
-import androidx.core.os.bundleOf
-import androidx.core.text.parseAsHtml
-import androidx.fragment.app.DialogFragment
-import code.name.monkey.retromusic.EXTRA_SONG
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.DialogFileDetailsBinding
-import code.name.monkey.retromusic.extensions.colorButtons
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.MusicUtil
-import org.jaudiotagger.audio.AudioFileIO
-import java.io.File
-
-class SongDetailDialog : DialogFragment() {
-
- override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
- val context: Context = requireContext()
- val binding = DialogFileDetailsBinding.inflate(layoutInflater)
-
- val song = BundleCompat.getParcelable(requireArguments(), EXTRA_SONG, Song::class.java)
- with(binding) {
- fileName.text = makeTextWithTitle(context, R.string.label_file_name, "-")
- filePath.text = makeTextWithTitle(context, R.string.label_file_path, "-")
- fileSize.text = makeTextWithTitle(context, R.string.label_file_size, "-")
- fileFormat.text = makeTextWithTitle(context, R.string.label_file_format, "-")
- trackLength.text = makeTextWithTitle(context, R.string.label_track_length, "-")
- bitrate.text = makeTextWithTitle(context, R.string.label_bit_rate, "-")
- samplingRate.text = makeTextWithTitle(context, R.string.label_sampling_rate, "-")
- }
-
- if (song != null) {
- val songFile = File(song.data)
- if (songFile.exists()) {
- binding.fileName.text =
- makeTextWithTitle(context, R.string.label_file_name, songFile.name)
- binding.filePath.text =
- makeTextWithTitle(context, R.string.label_file_path, songFile.absolutePath)
-
- binding.dateModified.text = makeTextWithTitle(
- context, R.string.label_last_modified,
- MusicUtil.getDateModifiedString(songFile.lastModified())
- )
-
- binding.fileSize.text =
- makeTextWithTitle(
- context,
- R.string.label_file_size,
- getFileSizeString(songFile.length())
- )
- try {
- val audioFile = AudioFileIO.read(songFile)
- val audioHeader = audioFile.audioHeader
-
- binding.fileFormat.text =
- makeTextWithTitle(context, R.string.label_file_format, audioHeader.format)
- binding.trackLength.text = makeTextWithTitle(
- context,
- R.string.label_track_length,
- MusicUtil.getReadableDurationString((audioHeader.trackLength * 1000).toLong())
- )
- binding.bitrate.text = makeTextWithTitle(
- context,
- R.string.label_bit_rate,
- audioHeader.bitRate + " kb/s"
- )
- binding.samplingRate.text =
- makeTextWithTitle(
- context,
- R.string.label_sampling_rate,
- audioHeader.sampleRate + " Hz"
- )
- } catch (e: Exception) {
- Log.e(TAG, "error while reading the song file", e)
- // fallback
- binding.trackLength.text = makeTextWithTitle(
- context,
- R.string.label_track_length,
- MusicUtil.getReadableDurationString(song.duration)
- )
- }
- } else {
- // fallback
- binding.fileName.text =
- makeTextWithTitle(context, R.string.label_file_name, song.title)
- binding.trackLength.text = makeTextWithTitle(
- context,
- R.string.label_track_length,
- MusicUtil.getReadableDurationString(song.duration)
- )
- }
- }
- return materialDialog(R.string.action_details)
- .setPositiveButton(android.R.string.ok, null)
- .setView(binding.root)
- .create()
- .colorButtons()
- }
-
- companion object {
-
- val TAG: String = SongDetailDialog::class.java.simpleName
-
- fun create(song: Song): SongDetailDialog {
- return SongDetailDialog().apply {
- arguments = bundleOf(
- EXTRA_SONG to song
- )
- }
- }
-
- private fun makeTextWithTitle(context: Context, titleResId: Int, text: String?): Spanned {
- return ("" + context.resources.getString(titleResId) + ": " + " " + text)
- .parseAsHtml()
- }
-
- private fun getFileSizeString(sizeInBytes: Long): String {
- val fileSizeInKB = sizeInBytes / 1024
- val fileSizeInMB = fileSizeInKB / 1024
- return "$fileSizeInMB MB"
- }
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/ActivityExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/ActivityExtensions.kt
deleted file mode 100644
index bf3d9d8cd..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/ActivityExtensions.kt
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import android.app.Activity
-import android.content.Intent
-import android.view.View
-import android.view.ViewGroup
-import androidx.annotation.DimenRes
-import androidx.appcompat.app.AppCompatActivity
-import code.name.monkey.appthemehelper.util.ToolbarContentTintHelper
-import com.google.android.material.appbar.MaterialToolbar
-
-fun AppCompatActivity.applyToolbar(toolbar: MaterialToolbar) {
- ToolbarContentTintHelper.colorBackButton(toolbar)
- setSupportActionBar(toolbar)
-}
-
-inline fun Activity.extra(key: String, default: T? = null) = lazy {
- val value = intent?.extras?.get(key)
- if (value is T) value else default
-}
-
-inline fun Intent.extra(key: String, default: T? = null) = lazy {
- val value = extras?.get(key)
- if (value is T) value else default
-}
-
-inline fun Activity.extraNotNull(key: String, default: T? = null) = lazy {
- val value = intent?.extras?.get(key)
- requireNotNull(if (value is T) value else default) { key }
-}
-
-fun Activity.dip(@DimenRes id: Int): Int {
- return resources.getDimensionPixelSize(id)
-}
-
-inline val Activity.rootView: View get() = findViewById(android.R.id.content).getChildAt(0)
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/ActivityThemeExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/ActivityThemeExtensions.kt
deleted file mode 100644
index d6c5a559d..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/ActivityThemeExtensions.kt
+++ /dev/null
@@ -1,235 +0,0 @@
-package code.name.monkey.retromusic.extensions
-
-import android.app.ActivityManager
-import android.graphics.Color
-import android.os.Build
-import android.view.View
-import android.view.View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR
-import android.view.WindowManager
-import android.view.inputmethod.InputMethodManager
-import androidx.appcompat.app.AppCompatActivity
-import androidx.core.content.getSystemService
-import androidx.core.view.*
-import androidx.fragment.app.FragmentActivity
-import code.name.monkey.appthemehelper.util.ColorUtil
-import code.name.monkey.appthemehelper.util.VersionUtils
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.util.PreferenceUtil
-
-fun AppCompatActivity.maybeSetScreenOn() {
- if (PreferenceUtil.isScreenOnEnabled) {
- window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
- } else {
- window.clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
- }
-}
-
-fun AppCompatActivity.keepScreenOn(keepScreenOn: Boolean) {
- if (keepScreenOn) {
- window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
- } else {
- window.clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
- }
-}
-
-fun AppCompatActivity.setEdgeToEdgeOrImmersive() {
- if (PreferenceUtil.isFullScreenMode) {
- setImmersiveFullscreen()
- } else {
- setDrawBehindSystemBars()
- }
-}
-
-fun AppCompatActivity.setImmersiveFullscreen() {
- if (PreferenceUtil.isFullScreenMode) {
- WindowInsetsControllerCompat(window, window.decorView).apply {
- systemBarsBehavior =
- WindowInsetsControllerCompat.BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
- hide(WindowInsetsCompat.Type.systemBars())
- }
- if (VersionUtils.hasP()) {
- window.attributes.layoutInDisplayCutoutMode =
- WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES
- }
- ViewCompat.setOnApplyWindowInsetsListener(window.decorView) { _, insets ->
- if (insets.displayCutout != null) {
- insets
- } else {
- // Consume insets if display doesn't have a Cutout
- WindowInsetsCompat.CONSUMED
- }
- }
- }
-}
-
-fun AppCompatActivity.exitFullscreen() {
- WindowInsetsControllerCompat(window, window.decorView).apply {
- show(WindowInsetsCompat.Type.systemBars())
- }
-}
-
-fun AppCompatActivity.hideStatusBar() {
- hideStatusBar(PreferenceUtil.isFullScreenMode)
-}
-
-private fun AppCompatActivity.hideStatusBar(fullscreen: Boolean) {
- val statusBar = window.decorView.rootView.findViewById(R.id.status_bar)
- if (statusBar != null) {
- statusBar.isGone = fullscreen
- }
-}
-
-fun AppCompatActivity.setDrawBehindSystemBars() {
- if (VersionUtils.hasOreo()) {
- WindowCompat.setDecorFitsSystemWindows(window, false)
- window.navigationBarColor = Color.TRANSPARENT
- window.statusBarColor = Color.TRANSPARENT
- if (VersionUtils.hasQ()) {
- window.isNavigationBarContrastEnforced = false
- }
- } else {
- setNavigationBarColorPreOreo(surfaceColor())
- if (VersionUtils.hasMarshmallow()) {
- setStatusBarColor(Color.TRANSPARENT)
- } else {
- setStatusBarColor(Color.BLACK)
- }
- }
-}
-
-fun FragmentActivity.setTaskDescriptionColor(color: Int) {
- var colorFinal = color
- // Task description requires fully opaque color
- colorFinal = ColorUtil.stripAlpha(colorFinal)
- // Sets color of entry in the system recents page
- if (VersionUtils.hasP()) {
- setTaskDescription(
- ActivityManager.TaskDescription(
- title as String?,
- -1,
- colorFinal
- )
- )
- } else {
- setTaskDescription(ActivityManager.TaskDescription(title as String?))
- }
-}
-
-fun AppCompatActivity.setTaskDescriptionColorAuto() {
- setTaskDescriptionColor(surfaceColor())
-}
-
-@Suppress("Deprecation")
-fun AppCompatActivity.setLightStatusBar(enabled: Boolean) {
- if (VersionUtils.hasMarshmallow()) {
- val decorView = window.decorView
- val systemUiVisibility = decorView.systemUiVisibility
- if (enabled) {
- decorView.systemUiVisibility =
- systemUiVisibility or View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR
- } else {
- decorView.systemUiVisibility =
- systemUiVisibility and View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR.inv()
- }
- }
-}
-
-fun AppCompatActivity.setLightStatusBarAuto() {
- setLightStatusBar(surfaceColor().isColorLight)
-}
-
-fun AppCompatActivity.setLightStatusBarAuto(bgColor: Int) {
- setLightStatusBar(bgColor.isColorLight)
-}
-
-@Suppress("Deprecation")
-fun AppCompatActivity.setLightNavigationBar(enabled: Boolean) {
- if (VersionUtils.hasOreo()) {
- val decorView = window.decorView
- var systemUiVisibility = decorView.systemUiVisibility
- systemUiVisibility = if (enabled) {
- systemUiVisibility or SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR
- } else {
- systemUiVisibility and SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR.inv()
- }
- decorView.systemUiVisibility = systemUiVisibility
- }
-}
-
-fun AppCompatActivity.setLightNavigationBarAuto() {
- setLightNavigationBar(surfaceColor().isColorLight)
-}
-
-fun AppCompatActivity.setLightNavigationBarAuto(bgColor: Int) {
- setLightNavigationBar(bgColor.isColorLight)
-}
-
-
-/**
- * This will set the color of the view with the id "status_bar" on KitKat and Lollipop. On
- * Lollipop if no such view is found it will set the statusbar color using the native method.
- *
- * @param color the new statusbar color (will be shifted down on Lollipop and above)
- */
-fun AppCompatActivity.setStatusBarColor(color: Int) {
- val statusBar = window.decorView.rootView.findViewById(R.id.status_bar)
- if (statusBar != null) {
- when {
- VersionUtils.hasMarshmallow() -> statusBar.setBackgroundColor(color)
- else -> statusBar.setBackgroundColor(
- ColorUtil.darkenColor(
- color
- )
- )
- }
- } else {
- when {
- VersionUtils.hasMarshmallow() -> window.statusBarColor = color
- else -> window.statusBarColor = ColorUtil.darkenColor(color)
- }
- }
- setLightStatusBarAuto(surfaceColor())
-}
-
-fun AppCompatActivity.setStatusBarColorAuto() {
- // we don't want to use statusbar color because we are doing the color darkening on our own to support KitKat
- setStatusBarColor(surfaceColor())
- setLightStatusBarAuto(surfaceColor())
-}
-
-fun AppCompatActivity.setNavigationBarColor(color: Int) {
- if (VersionUtils.hasOreo()) {
- window.navigationBarColor = color
- } else {
- window.navigationBarColor = ColorUtil.darkenColor(color)
- }
- setLightNavigationBarAuto(color)
-}
-
-fun AppCompatActivity.setNavigationBarColorPreOreo(color: Int) {
- if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) {
- window.navigationBarColor = ColorUtil.darkenColor(color)
- }
-}
-
-fun AppCompatActivity.setStatusBarColorPreMarshmallow(color: Int) {
- val statusBar = window.decorView.rootView.findViewById(R.id.status_bar)
- if (statusBar != null) {
- statusBar.setBackgroundColor(
- ColorUtil.darkenColor(
- color
- )
- )
- } else {
- window.statusBarColor = ColorUtil.darkenColor(color)
- }
-}
-
-fun AppCompatActivity.hideSoftKeyboard() {
- val currentFocus: View? = currentFocus
- if (currentFocus != null) {
- val inputMethodManager =
- getSystemService()
- inputMethodManager?.hideSoftInputFromWindow(currentFocus.windowToken, 0)
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/ColorExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/ColorExtensions.kt
deleted file mode 100644
index b1ae4bec8..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/ColorExtensions.kt
+++ /dev/null
@@ -1,320 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import android.app.Dialog
-import android.content.Context
-import android.content.res.ColorStateList
-import android.graphics.Color
-import android.graphics.drawable.Drawable
-import android.widget.Button
-import android.widget.CheckBox
-import android.widget.SeekBar
-import androidx.annotation.AttrRes
-import androidx.annotation.CheckResult
-import androidx.annotation.ColorInt
-import androidx.annotation.ColorRes
-import androidx.appcompat.widget.AppCompatImageView
-import androidx.appcompat.widget.Toolbar
-import androidx.core.content.ContextCompat
-import androidx.core.graphics.ColorUtils
-import androidx.core.graphics.drawable.DrawableCompat
-import androidx.fragment.app.Fragment
-import code.name.monkey.appthemehelper.ThemeStore
-import code.name.monkey.appthemehelper.util.ATHUtil
-import code.name.monkey.appthemehelper.util.ColorUtil
-import code.name.monkey.appthemehelper.util.MaterialValueHelper
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.util.PreferenceUtil.materialYou
-import com.google.android.material.button.MaterialButton
-import com.google.android.material.floatingactionbutton.ExtendedFloatingActionButton
-import com.google.android.material.floatingactionbutton.FloatingActionButton
-import com.google.android.material.progressindicator.CircularProgressIndicator
-import com.google.android.material.slider.Slider
-import com.google.android.material.textfield.TextInputLayout
-
-fun Int.ripAlpha(): Int {
- return ColorUtil.stripAlpha(this)
-}
-
-fun Dialog.colorControlNormal() = resolveColor(android.R.attr.colorControlNormal)
-
-fun Toolbar.backgroundTintList() {
- val surfaceColor = ATHUtil.resolveColor(context, com.google.android.material.R.attr.colorSurface, Color.BLACK)
- val colorStateList = ColorStateList.valueOf(surfaceColor)
- backgroundTintList = colorStateList
-}
-
-fun Context.accentColor() = ThemeStore.accentColor(this)
-
-fun Fragment.accentColor() = ThemeStore.accentColor(requireContext())
-
-fun Context.surfaceColor() = resolveColor(com.google.android.material.R.attr.colorSurface, Color.WHITE)
-
-fun Fragment.surfaceColor() = resolveColor(com.google.android.material.R.attr.colorSurface, Color.WHITE)
-
-fun Context.surfaceColor(fallBackColor: Int) = resolveColor(com.google.android.material.R.attr.colorSurface, fallBackColor)
-
-fun Fragment.surfaceColor(fallBackColor: Int) = resolveColor(com.google.android.material.R.attr.colorSurface, fallBackColor)
-
-fun Context.textColorSecondary() = resolveColor(android.R.attr.textColorSecondary)
-
-fun Fragment.textColorSecondary() = resolveColor(android.R.attr.textColorSecondary)
-
-fun Context.colorControlNormal() = resolveColor(android.R.attr.colorControlNormal)
-
-fun Fragment.colorControlNormal() = resolveColor(android.R.attr.colorControlNormal)
-
-fun Context.colorBackground() = resolveColor(android.R.attr.colorBackground)
-
-fun Fragment.colorBackground() = resolveColor(android.R.attr.colorBackground)
-
-fun Context.textColorPrimary() = resolveColor(android.R.attr.textColorPrimary)
-
-fun Fragment.textColorPrimary() = resolveColor(android.R.attr.textColorPrimary)
-
-fun Context.defaultFooterColor() = resolveColor(R.attr.defaultFooterColor)
-
-fun Fragment.defaultFooterColor() = resolveColor(R.attr.defaultFooterColor)
-
-fun Context.resolveColor(@AttrRes attr: Int, fallBackColor: Int = 0) =
- ATHUtil.resolveColor(this, attr, fallBackColor)
-
-fun Fragment.resolveColor(@AttrRes attr: Int, fallBackColor: Int = 0) =
- ATHUtil.resolveColor(requireContext(), attr, fallBackColor)
-
-fun Dialog.resolveColor(@AttrRes attr: Int, fallBackColor: Int = 0) =
- ATHUtil.resolveColor(context, attr, fallBackColor)
-
-// Don't apply accent colors if Material You is enabled
-// Material Components will take care of applying material you colors
-fun CheckBox.addAccentColor() {
- if (materialYou) return
- buttonTintList = ColorStateList.valueOf(ThemeStore.accentColor(context))
-}
-
-fun SeekBar.addAccentColor() {
- if (materialYou) return
- val colorState = ColorStateList.valueOf(ThemeStore.accentColor(context))
- progressTintList = colorState
- thumbTintList = colorState
-}
-
-fun Slider.addAccentColor() {
- if (materialYou) return
- val accentColor = ThemeStore.accentColor(context)
- trackActiveTintList = accentColor.colorStateList
- trackInactiveTintList = ColorUtil.withAlpha(accentColor, 0.5F).colorStateList
- thumbTintList = accentColor.colorStateList
-}
-
-fun Slider.accent() {
- if (materialYou) return
- val accentColor = context.accentColor()
- thumbTintList = accentColor.colorStateList
- trackActiveTintList = accentColor.colorStateList
- trackInactiveTintList = ColorUtil.withAlpha(accentColor, 0.1F).colorStateList
-}
-
-fun Button.accentTextColor() {
- if (materialYou) return
- setTextColor(context.accentColor())
-}
-
-fun MaterialButton.accentBackgroundColor() {
- if (materialYou) return
- backgroundTintList = ColorStateList(
- arrayOf(intArrayOf(android.R.attr.state_enabled), intArrayOf()),
- intArrayOf(context.accentColor(), context.accentColor().addAlpha(0.12f)))
-}
-
-fun MaterialButton.accentOutlineColor() {
- if (materialYou) return
- val color = ThemeStore.accentColor(context)
- val colorStateList = ColorStateList.valueOf(color)
- iconTint = colorStateList
- strokeColor = colorStateList
- setTextColor(colorStateList)
- rippleColor = colorStateList
-}
-
-fun MaterialButton.elevatedAccentColor() {
- if (materialYou) return
- val color = context.darkAccentColorVariant()
- rippleColor = ColorStateList.valueOf(color)
- setBackgroundColor(color)
- setTextColor(MaterialValueHelper.getPrimaryTextColor(context, color.isColorLight))
- iconTint = ColorStateList.valueOf(context.accentColor())
-}
-
-fun SeekBar.applyColor(@ColorInt color: Int) {
- thumbTintList = ColorStateList.valueOf(color)
- progressTintList = ColorStateList.valueOf(color)
- progressBackgroundTintList = ColorStateList.valueOf(color)
-}
-
-fun Slider.applyColor(@ColorInt color: Int) {
- ColorStateList.valueOf(color).run {
- thumbTintList = this
- trackActiveTintList = this
- trackInactiveTintList = ColorStateList.valueOf(color.addAlpha(0.1f))
- haloTintList = this
- }
-}
-
-fun ExtendedFloatingActionButton.accentColor() {
- if (materialYou) return
- val color = ThemeStore.accentColor(context)
- val textColor = MaterialValueHelper.getPrimaryTextColor(context, ColorUtil.isColorLight(color))
- val colorStateList = ColorStateList.valueOf(color)
- val textColorStateList = ColorStateList.valueOf(textColor)
- backgroundTintList = colorStateList
- setTextColor(textColorStateList)
- iconTint = textColorStateList
-}
-
-fun FloatingActionButton.accentColor() {
- if (materialYou) return
- val color = ThemeStore.accentColor(context)
- val textColor = MaterialValueHelper.getPrimaryTextColor(context, ColorUtil.isColorLight(color))
- backgroundTintList = ColorStateList.valueOf(color)
- imageTintList = ColorStateList.valueOf(textColor)
-}
-
-fun MaterialButton.applyColor(color: Int) {
- val backgroundColorStateList = ColorStateList.valueOf(color)
- val textColorColorStateList = ColorStateList.valueOf(
- MaterialValueHelper.getPrimaryTextColor(
- context,
- ColorUtil.isColorLight(color)
- )
- )
- backgroundTintList = backgroundColorStateList
- setTextColor(textColorColorStateList)
- iconTint = textColorColorStateList
-}
-
-fun MaterialButton.accentColor() {
- if (materialYou) return
- applyColor(ThemeStore.accentColor(context))
-}
-
-fun MaterialButton.applyOutlineColor(color: Int) {
- val colorStateList = ColorStateList.valueOf(color)
- iconTint = colorStateList
- strokeColor = colorStateList
- setTextColor(colorStateList)
- rippleColor = colorStateList
-}
-
-fun TextInputLayout.accentColor() {
- if (materialYou) return
- val accentColor = ThemeStore.accentColor(context)
- val colorState = ColorStateList.valueOf(accentColor)
- boxStrokeColor = accentColor
- defaultHintTextColor = colorState
- isHintAnimationEnabled = true
-}
-
-fun CircularProgressIndicator.accentColor() {
- if (materialYou) return
- val color = ThemeStore.accentColor(context)
- setIndicatorColor(color)
- trackColor = ColorUtil.withAlpha(color, 0.2f)
-}
-
-fun CircularProgressIndicator.applyColor(color: Int) {
- setIndicatorColor(color)
- trackColor = ColorUtil.withAlpha(color, 0.2f)
-}
-
-fun AppCompatImageView.accentColor(): Int = ThemeStore.accentColor(context)
-
-fun TextInputLayout.setTint(background: Boolean = true) {
- if (materialYou) return
- val accentColor = ThemeStore.accentColor(context)
- val colorState = ColorStateList.valueOf(accentColor)
-
- if (background) {
- backgroundTintList = colorState
- defaultHintTextColor = colorState
- } else {
- boxStrokeColor = accentColor
- defaultHintTextColor = colorState
- isHintAnimationEnabled = true
- }
-}
-
-@CheckResult
-fun Drawable.tint(@ColorInt color: Int): Drawable {
- val tintedDrawable = DrawableCompat.wrap(this).mutate()
- setTint(color)
- return tintedDrawable
-}
-
-@CheckResult
-fun Drawable.tint(context: Context, @ColorRes color: Int): Drawable =
- tint(context.getColorCompat(color))
-
-@ColorInt
-fun Context.getColorCompat(@ColorRes colorRes: Int): Int {
- return ContextCompat.getColor(this, colorRes)
-}
-
-@ColorInt
-fun Context.darkAccentColor(): Int {
- return ColorUtils.blendARGB(
- accentColor(),
- surfaceColor(),
- if (surfaceColor().isColorLight) 0.9f else 0.92f
- )
-}
-
-@ColorInt
-fun Context.darkAccentColorVariant(): Int {
- return ColorUtils.blendARGB(
- accentColor(),
- surfaceColor(),
- if (surfaceColor().isColorLight) 0.9f else 0.95f
- )
-}
-
-@ColorInt
-fun Context.accentColorVariant(): Int {
- return if (surfaceColor().isColorLight) {
- accentColor().darkerColor
- } else {
- accentColor().lighterColor
- }
-}
-
-inline val @receiver:ColorInt Int.isColorLight
- get() = ColorUtil.isColorLight(this)
-
-inline val @receiver:ColorInt Int.lightColor
- get() = ColorUtil.withAlpha(this, 0.5F)
-
-inline val @receiver:ColorInt Int.lighterColor
- get() = ColorUtil.lightenColor(this)
-
-inline val @receiver:ColorInt Int.darkerColor
- get() = ColorUtil.darkenColor(this)
-
-inline val Int.colorStateList: ColorStateList
- get() = ColorStateList.valueOf(this)
-
-fun @receiver:ColorInt Int.addAlpha(alpha: Float): Int {
- return ColorUtil.withAlpha(this, alpha)
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/ContextExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/ContextExtensions.kt
deleted file mode 100644
index a479903d7..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/ContextExtensions.kt
+++ /dev/null
@@ -1,26 +0,0 @@
-package code.name.monkey.retromusic.extensions
-
-import android.content.Context
-import android.content.res.Configuration
-import android.graphics.drawable.Drawable
-import android.widget.Toast
-import androidx.annotation.ColorInt
-import androidx.annotation.DrawableRes
-import androidx.annotation.StringRes
-import androidx.core.content.ContextCompat
-
-fun Context.showToast(@StringRes stringRes: Int, duration: Int = Toast.LENGTH_SHORT) {
- showToast(getString(stringRes), duration)
-}
-
-fun Context.showToast(message: String, duration: Int = Toast.LENGTH_SHORT) {
- Toast.makeText(this, message, duration).show()
-}
-
-val Context.isLandscape: Boolean get() = resources.configuration.orientation == Configuration.ORIENTATION_LANDSCAPE
-
-val Context.isTablet: Boolean get() = resources.configuration.smallestScreenWidthDp >= 600
-
-fun Context.getTintedDrawable(@DrawableRes id: Int, @ColorInt color: Int): Drawable {
- return ContextCompat.getDrawable(this, id)?.tint(color)!!
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/CursorExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/CursorExtensions.kt
deleted file mode 100644
index 531c2e0bb..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/CursorExtensions.kt
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import android.database.Cursor
-
-// exception is rethrown manually in order to have a readable stacktrace
-
-internal fun Cursor.getInt(columnName: String): Int {
- try {
- return getInt(getColumnIndexOrThrow(columnName))
- } catch (ex: Throwable) {
- throw IllegalStateException("invalid column $columnName", ex)
- }
-}
-
-internal fun Cursor.getLong(columnName: String): Long {
- try {
- return getLong(getColumnIndexOrThrow(columnName))
- } catch (ex: Throwable) {
- throw IllegalStateException("invalid column $columnName", ex)
- }
-}
-
-internal fun Cursor.getString(columnName: String): String {
- try {
- return getString(getColumnIndexOrThrow(columnName))
- } catch (ex: Throwable) {
- throw IllegalStateException("invalid column $columnName", ex)
- }
-}
-
-internal fun Cursor.getStringOrNull(columnName: String): String? {
- try {
- return getString(getColumnIndexOrThrow(columnName))
- } catch (ex: Throwable) {
- throw IllegalStateException("invalid column $columnName", ex)
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/DialogExtension.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/DialogExtension.kt
deleted file mode 100644
index ffd894af4..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/DialogExtension.kt
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import androidx.appcompat.app.AlertDialog
-import androidx.fragment.app.Fragment
-import code.name.monkey.retromusic.BuildConfig
-import code.name.monkey.retromusic.R
-import com.afollestad.materialdialogs.MaterialDialog
-import com.google.android.material.dialog.MaterialAlertDialogBuilder
-
-fun Fragment.materialDialog(title: Int): MaterialAlertDialogBuilder {
- return if (BuildConfig.DEBUG) {
- MaterialAlertDialogBuilder(
- requireContext(),
- R.style.MaterialAlertDialogTheme
- )
- } else {
- MaterialAlertDialogBuilder(
- requireContext()
- )
- }.setTitle(title)
-}
-
-fun AlertDialog.colorButtons(): AlertDialog {
- setOnShowListener {
- getButton(AlertDialog.BUTTON_POSITIVE).accentTextColor()
- getButton(AlertDialog.BUTTON_NEGATIVE).accentTextColor()
- getButton(AlertDialog.BUTTON_NEUTRAL).accentTextColor()
- }
- return this
-}
-
-fun Fragment.materialDialog(): MaterialDialog {
- return MaterialDialog(requireContext())
- .cornerRadius(res = R.dimen.m3_dialog_corner_size)
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/DimenExtension.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/DimenExtension.kt
deleted file mode 100644
index 6e5cdeccc..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/DimenExtension.kt
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import android.app.Activity
-import androidx.annotation.DimenRes
-import androidx.appcompat.app.AppCompatActivity
-import androidx.fragment.app.Fragment
-
-fun AppCompatActivity.dimToPixel(@DimenRes dimenRes: Int): Int {
- return resources.getDimensionPixelSize(dimenRes)
-}
-
-fun Activity.dipToPix(dpInFloat: Float): Float {
- val scale = resources.displayMetrics.density
- return dpInFloat * scale + 0.5f
-}
-
-fun Fragment.dipToPix(dpInFloat: Float): Float {
- val scale = resources.displayMetrics.density
- return dpInFloat * scale + 0.5f
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/FileExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/FileExtensions.kt
deleted file mode 100644
index 5c4df1a37..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/FileExtensions.kt
+++ /dev/null
@@ -1,6 +0,0 @@
-package code.name.monkey.retromusic.extensions
-
-import java.io.BufferedOutputStream
-import java.util.zip.ZipOutputStream
-
-fun BufferedOutputStream.zipOutputStream(): ZipOutputStream = ZipOutputStream(this)
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/FragmentExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/FragmentExtensions.kt
deleted file mode 100644
index b1e8f5930..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/FragmentExtensions.kt
+++ /dev/null
@@ -1,98 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import android.content.Context
-import android.content.res.Configuration
-import android.graphics.drawable.Drawable
-import android.os.PowerManager
-import android.widget.Toast
-import androidx.annotation.*
-import androidx.appcompat.app.AppCompatActivity
-import androidx.appcompat.content.res.AppCompatResources
-import androidx.core.content.getSystemService
-import androidx.fragment.app.Fragment
-import androidx.navigation.fragment.NavHostFragment
-import code.name.monkey.retromusic.util.PreferenceUtil
-import com.google.android.material.appbar.MaterialToolbar
-
-fun Fragment.getIntRes(@IntegerRes int: Int): Int {
- return resources.getInteger(int)
-}
-
-fun Context.getIntRes(@IntegerRes int: Int): Int {
- return resources.getInteger(int)
-}
-
-val Context.generalThemeValue
- get() = PreferenceUtil.getGeneralThemeValue(isSystemDarkModeEnabled())
-
-fun Context.isSystemDarkModeEnabled(): Boolean {
- val isBatterySaverEnabled =
- (getSystemService())?.isPowerSaveMode ?: false
- val isDarkModeEnabled =
- (resources.configuration.uiMode and Configuration.UI_MODE_NIGHT_MASK) == Configuration.UI_MODE_NIGHT_YES
- return isBatterySaverEnabled or isDarkModeEnabled
-}
-
-inline fun Fragment.extra(key: String, default: T? = null) = lazy {
- val value = arguments?.get(key)
- if (value is T) value else default
-}
-
-inline fun Fragment.extraNotNull(key: String, default: T? = null) = lazy {
- val value = arguments?.get(key)
- requireNotNull(if (value is T) value else default) { key }
-}
-
-fun AppCompatActivity.currentFragment(navHostId: Int): Fragment? {
- val navHostFragment: NavHostFragment =
- supportFragmentManager.findFragmentById(navHostId) as NavHostFragment
- return navHostFragment.childFragmentManager.fragments.firstOrNull()
-}
-
-@Suppress("UNCHECKED_CAST")
-fun AppCompatActivity.whichFragment(@IdRes id: Int): T {
- return supportFragmentManager.findFragmentById(id) as T
-}
-
-@Suppress("UNCHECKED_CAST")
-fun Fragment.whichFragment(@IdRes id: Int): T {
- return childFragmentManager.findFragmentById(id) as T
-}
-
-fun Fragment.showToast(@StringRes stringRes: Int, duration: Int = Toast.LENGTH_SHORT) {
- showToast(getString(stringRes), duration)
-}
-
-fun Fragment.showToast(message: String, duration: Int = Toast.LENGTH_SHORT) {
- Toast.makeText(requireContext(), message, duration).show()
-}
-
-fun Context.getDrawableCompat(@DrawableRes drawableRes: Int): Drawable {
- return AppCompatResources.getDrawable(this, drawableRes)!!
-}
-
-fun Fragment.getDrawableCompat(@DrawableRes drawableRes: Int): Drawable {
- return AppCompatResources.getDrawable(requireContext(), drawableRes)!!
-}
-
-fun Fragment.applyToolbar(toolbar: MaterialToolbar) {
- (requireActivity() as AppCompatActivity).applyToolbar(toolbar)
-}
-
-fun Fragment.dip(@DimenRes id: Int): Int {
- return resources.getDimensionPixelSize(id)
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/FragmentMusicExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/FragmentMusicExtensions.kt
deleted file mode 100644
index ac35af672..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/FragmentMusicExtensions.kt
+++ /dev/null
@@ -1,38 +0,0 @@
-package code.name.monkey.retromusic.extensions
-
-import android.webkit.MimeTypeMap
-import androidx.core.net.toUri
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.RetroUtil
-import org.jaudiotagger.audio.AudioFileIO
-import java.io.File
-import java.net.URLEncoder
-
-fun getSongInfo(song: Song): String {
- val file = File(song.data)
- if (file.exists()) {
- return try {
- val audioHeader = AudioFileIO.read(File(song.data)).audioHeader
- val string: StringBuilder = StringBuilder()
- val uriFile = file.toUri()
- string.append(getMimeType(uriFile.toString())).append(" • ")
- string.append(audioHeader.bitRate).append(" kb/s").append(" • ")
- string.append(RetroUtil.frequencyCount(audioHeader.sampleRate.toInt()))
- .append(" kHz")
- string.toString()
- } catch (er: Exception) {
- " - "
- }
- }
- return "-"
-}
-
-private fun getMimeType(url: String): String {
- var type: String? = MimeTypeMap.getFileExtensionFromUrl(
- URLEncoder.encode(url, "utf-8")
- ).uppercase()
- if (type == null) {
- type = url.substring(url.lastIndexOf(".") + 1)
- }
- return type
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/InsetsExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/InsetsExtensions.kt
deleted file mode 100644
index 70c8a10f4..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/InsetsExtensions.kt
+++ /dev/null
@@ -1,13 +0,0 @@
-package code.name.monkey.retromusic.extensions
-
-import androidx.core.view.WindowInsetsCompat
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.RetroUtil
-
-fun WindowInsetsCompat?.getBottomInsets(): Int {
- return if (PreferenceUtil.isFullScreenMode) {
- return 0
- } else {
- this?.getInsets(WindowInsetsCompat.Type.systemBars())?.bottom ?: RetroUtil.navigationBarHeight
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/IntentExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/IntentExtensions.kt
deleted file mode 100644
index e91e81347..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/IntentExtensions.kt
+++ /dev/null
@@ -1,46 +0,0 @@
-package code.name.monkey.retromusic.extensions
-
-import android.app.Activity
-import android.content.Context
-import android.content.Intent
-import android.net.Uri
-import androidx.activity.result.ActivityResult
-import androidx.activity.result.contract.ActivityResultContracts
-import androidx.core.net.toUri
-import androidx.fragment.app.Fragment
-import java.io.OutputStream
-
-fun Fragment.createNewFile(
- mimeType: String,
- fileName: String,
- write: (outputStream: OutputStream?, data: Uri?) -> Unit
-) {
- val intent = Intent(Intent.ACTION_CREATE_DOCUMENT)
- intent.addCategory(Intent.CATEGORY_OPENABLE)
- intent.type = mimeType
- intent.putExtra(Intent.EXTRA_TITLE, fileName)
- val startForResult =
- registerForActivityResult(ActivityResultContracts.StartActivityForResult())
- { result: ActivityResult ->
- if (result.resultCode == Activity.RESULT_OK) {
- write(
- context?.contentResolver?.openOutputStream(result.data?.data!!),
- result.data?.data
- )
- }
-
- }
- startForResult.launch(intent)
-}
-
-fun Context.openUrl(url: String) {
- val i = Intent(Intent.ACTION_VIEW)
- i.data = url.toUri()
- i.flags = Intent.FLAG_ACTIVITY_NEW_TASK
- startActivity(i)
-}
-
-
-fun Fragment.openUrl(url: String) {
- requireContext().openUrl(url)
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/NavigationExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/NavigationExtensions.kt
deleted file mode 100644
index fc1f938d5..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/NavigationExtensions.kt
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import androidx.annotation.IdRes
-import androidx.appcompat.app.AppCompatActivity
-import androidx.fragment.app.Fragment
-import androidx.navigation.NavController
-import androidx.navigation.findNavController
-import androidx.navigation.fragment.NavHostFragment
-import androidx.navigation.fragment.findNavController
-import androidx.navigation.navOptions
-
-fun Fragment.navigate(@IdRes id: Int) = findNavController().navigate(id)
-
-fun Fragment.findNavController(@IdRes id: Int): NavController {
- val fragment = childFragmentManager.findFragmentById(id) as NavHostFragment
- return fragment.navController
-}
-
-fun Fragment.findActivityNavController(@IdRes id: Int): NavController {
- return requireActivity().findNavController(id)
-}
-
-fun AppCompatActivity.findNavController(@IdRes id: Int): NavController {
- val fragment = supportFragmentManager.findFragmentById(id) as NavHostFragment
- return fragment.navController
-}
-
-val fadeNavOptions
- get() = navOptions {
- anim {
- enter = android.R.anim.fade_in
- exit = android.R.anim.fade_out
- popEnter = android.R.anim.fade_in
- popExit = android.R.anim.fade_out
- }
- }
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/PreferenceExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/PreferenceExtensions.kt
deleted file mode 100644
index 317844afd..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/PreferenceExtensions.kt
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.extensions
-
-import android.content.SharedPreferences
-
-fun SharedPreferences.getStringOrDefault(key: String, default: String): String {
- return getString(key, default) ?: default
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/SongExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/SongExtensions.kt
deleted file mode 100644
index f28f05624..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/SongExtensions.kt
+++ /dev/null
@@ -1,22 +0,0 @@
-package code.name.monkey.retromusic.extensions
-
-import android.support.v4.media.MediaDescriptionCompat
-import android.support.v4.media.session.MediaSessionCompat.QueueItem
-import code.name.monkey.retromusic.model.Song
-import code.name.monkey.retromusic.util.MusicUtil
-
-val Song.uri get() = MusicUtil.getSongFileUri(songId = id)
-
-val Song.albumArtUri get() = MusicUtil.getMediaStoreAlbumCoverUri(albumId)
-
-fun ArrayList.toMediaSessionQueue(): List {
- return map { song ->
- val mediaDescription = MediaDescriptionCompat.Builder()
- .setMediaId(song.id.toString())
- .setTitle(song.title)
- .setSubtitle(song.artistName)
- .setIconUri(song.albumArtUri)
- .build()
- QueueItem(mediaDescription, song.hashCode().toLong())
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/extensions/ViewExtensions.kt b/app/src/main/java/code/name/monkey/retromusic/extensions/ViewExtensions.kt
deleted file mode 100644
index 114ecf6d5..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/extensions/ViewExtensions.kt
+++ /dev/null
@@ -1,325 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- */
-package code.name.monkey.retromusic.extensions
-
-import android.animation.Animator
-import android.animation.ObjectAnimator
-import android.animation.ValueAnimator
-import android.content.res.ColorStateList
-import android.graphics.drawable.BitmapDrawable
-import android.view.LayoutInflater
-import android.view.View
-import android.view.ViewGroup
-import android.view.ViewTreeObserver
-import android.view.animation.AnimationUtils
-import android.view.inputmethod.InputMethodManager
-import android.widget.EditText
-import androidx.annotation.ColorInt
-import androidx.annotation.LayoutRes
-import androidx.annotation.Px
-import androidx.core.animation.doOnEnd
-import androidx.core.animation.doOnStart
-import androidx.core.content.getSystemService
-import androidx.core.view.*
-import code.name.monkey.appthemehelper.ThemeStore
-import code.name.monkey.appthemehelper.util.TintHelper
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.RetroUtil
-import com.google.android.material.bottomnavigation.BottomNavigationView
-import com.google.android.material.bottomsheet.BottomSheetBehavior
-import com.google.android.material.card.MaterialCardView
-import com.google.android.material.navigation.NavigationBarView
-import com.google.android.material.navigationrail.NavigationRailView
-import dev.chrisbanes.insetter.applyInsetter
-
-const val ANIM_DURATION = 300L
-
-@Suppress("UNCHECKED_CAST")
-fun ViewGroup.inflate(@LayoutRes layout: Int): T {
- return LayoutInflater.from(context).inflate(layout, this, false) as T
-}
-
-fun View.show() {
- isVisible = true
-}
-
-fun View.hide() {
- isVisible = false
-}
-
-fun View.hidden() {
- isInvisible = true
-}
-
-fun EditText.appHandleColor(): EditText {
- if (PreferenceUtil.materialYou) return this
- TintHelper.colorHandles(this, ThemeStore.accentColor(context))
- return this
-}
-
-fun NavigationBarView.setItemColors(@ColorInt normalColor: Int, @ColorInt selectedColor: Int) {
- val csl = ColorStateList(
- arrayOf(intArrayOf(-android.R.attr.state_checked), intArrayOf(android.R.attr.state_checked)),
- intArrayOf(normalColor, selectedColor)
- )
- itemIconTintList = csl
- itemTextColor = csl
-}
-
-/**
- * Potentially animate showing a [BottomNavigationView].
- *
- * Abruptly changing the visibility leads to a re-layout of main content, animating
- * `translationY` leaves a gap where the view was that content does not fill.
- *
- * Instead, take a snapshot of the view, and animate this in, only changing the visibility (and
- * thus layout) when the animation completes.
- */
-fun NavigationBarView.show() {
- if (this is NavigationRailView) return
- if (isVisible) return
-
- val parent = parent as ViewGroup
- // View needs to be laid out to create a snapshot & know position to animate. If view isn't
- // laid out yet, need to do this manually.
- if (!isLaidOut) {
- measure(
- View.MeasureSpec.makeMeasureSpec(parent.width, View.MeasureSpec.EXACTLY),
- View.MeasureSpec.makeMeasureSpec(parent.height, View.MeasureSpec.AT_MOST)
- )
- layout(parent.left, parent.height - measuredHeight, parent.right, parent.height)
- }
-
- val drawable = BitmapDrawable(context.resources, drawToBitmap())
- drawable.setBounds(left, parent.height, right, parent.height + height)
- parent.overlay.add(drawable)
- ValueAnimator.ofInt(parent.height, top).apply {
- duration = ANIM_DURATION
- interpolator = AnimationUtils.loadInterpolator(
- context,
- android.R.interpolator.accelerate_decelerate
- )
- addUpdateListener {
- val newTop = it.animatedValue as Int
- drawable.setBounds(left, newTop, right, newTop + height)
- }
- doOnEnd {
- parent.overlay.remove(drawable)
- isVisible = true
- }
- start()
- }
-}
-
-/**
- * Potentially animate hiding a [BottomNavigationView].
- *
- * Abruptly changing the visibility leads to a re-layout of main content, animating
- * `translationY` leaves a gap where the view was that content does not fill.
- *
- * Instead, take a snapshot, instantly hide the view (so content lays out to fill), then animate
- * out the snapshot.
- */
-fun NavigationBarView.hide() {
- if (this is NavigationRailView) return
- if (isGone) return
-
- if (!isLaidOut) {
- isGone = true
- return
- }
-
- val drawable = BitmapDrawable(context.resources, drawToBitmap())
- val parent = parent as ViewGroup
- drawable.setBounds(left, top, right, bottom)
- parent.overlay.add(drawable)
- isGone = true
- ValueAnimator.ofInt(top, parent.height).apply {
- duration = ANIM_DURATION
- interpolator = AnimationUtils.loadInterpolator(
- context,
- android.R.interpolator.accelerate_decelerate
- )
- addUpdateListener {
- val newTop = it.animatedValue as Int
- drawable.setBounds(left, newTop, right, newTop + height)
- }
- doOnEnd {
- parent.overlay.remove(drawable)
- }
- start()
- }
-}
-
-fun View.translateYAnimate(value: Float): Animator {
- return ObjectAnimator.ofFloat(this, "translationY", value)
- .apply {
- duration = 300
- doOnStart {
- show()
- bringToFront()
- }
- doOnEnd {
- isGone = (value != 0f)
- }
- start()
- }
-}
-
-fun BottomSheetBehavior<*>.peekHeightAnimate(value: Int): Animator {
- return ObjectAnimator.ofInt(this, "peekHeight", value)
- .apply {
- duration = ANIM_DURATION
- start()
- }
-}
-
-fun MaterialCardView.animateRadius(cornerRadius: Float, pause: Boolean = true) {
- ValueAnimator.ofFloat(radius, cornerRadius).apply {
- addUpdateListener { radius = animatedValue as Float }
- start()
- }
- ValueAnimator.ofInt(measuredWidth, if (pause) (height * 1.5).toInt() else height).apply {
- addUpdateListener {
- updateLayoutParams { width = animatedValue as Int }
- }
- start()
- }
-}
-
-fun MaterialCardView.animateToCircle() {
- animateRadius(measuredHeight / 2F, pause = false)
-}
-
-fun View.focusAndShowKeyboard() {
- /**
- * This is to be called when the window already has focus.
- */
- fun View.showTheKeyboardNow() {
- if (isFocused) {
- post {
- // We still post the call, just in case we are being notified of the windows focus
- // but InputMethodManager didn't get properly setup yet.
- val imm =
- context.getSystemService()
- imm?.showSoftInput(this, InputMethodManager.SHOW_IMPLICIT)
- }
- }
- }
-
- requestFocus()
- if (hasWindowFocus()) {
- // No need to wait for the window to get focus.
- showTheKeyboardNow()
- } else {
- // We need to wait until the window gets focus.
- viewTreeObserver.addOnWindowFocusChangeListener(
- object : ViewTreeObserver.OnWindowFocusChangeListener {
- override fun onWindowFocusChanged(hasFocus: Boolean) {
- // This notification will arrive just before the InputMethodManager gets set up.
- if (hasFocus) {
- this@focusAndShowKeyboard.showTheKeyboardNow()
- // It’s very important to remove this listener once we are done.
- viewTreeObserver.removeOnWindowFocusChangeListener(this)
- }
- }
- })
- }
-}
-
-/**
- * This will draw our view above the navigation bar instead of behind it by adding margins.
- */
-fun View.drawAboveSystemBars(onlyPortrait: Boolean = true) {
- if (PreferenceUtil.isFullScreenMode) return
- if (onlyPortrait && RetroUtil.isLandscape) return
- applyInsetter {
- type(navigationBars = true) {
- margin()
- }
- }
-}
-
-/**
- * This will draw our view above the navigation bar instead of behind it by adding padding.
- */
-fun View.drawAboveSystemBarsWithPadding() {
- if (PreferenceUtil.isFullScreenMode) return
- applyInsetter {
- type(navigationBars = true) {
- padding()
- }
- }
-}
-
-fun View.drawNextToNavbar() {
- if (PreferenceUtil.isFullScreenMode) return
- applyInsetter {
- type(statusBars = true, navigationBars = true) {
- padding(horizontal = true)
- }
- }
-}
-
-fun View.updateMargin(
- @Px left: Int = marginLeft,
- @Px top: Int = marginTop,
- @Px right: Int = marginRight,
- @Px bottom: Int = marginBottom,
-) {
- (layoutParams as ViewGroup.MarginLayoutParams).updateMargins(left, top, right, bottom)
-}
-
-fun View.applyBottomInsets() {
- if (PreferenceUtil.isFullScreenMode) return
- val initialPadding = recordInitialPaddingForView(this)
-
- ViewCompat.setOnApplyWindowInsetsListener(
- (this)
- ) { v: View, windowInsets: WindowInsetsCompat ->
- val insets = windowInsets.getInsets(WindowInsetsCompat.Type.systemBars())
- v.updatePadding(
- bottom = initialPadding.bottom + insets.bottom
- )
- windowInsets
- }
- requestApplyInsetsWhenAttached()
-}
-
-fun View.requestApplyInsetsWhenAttached() {
- if (isAttachedToWindow) {
- // We're already attached, just request as normal
- requestApplyInsets()
- } else {
- // We're not attached to the hierarchy, add a listener to
- // request when we are
- addOnAttachStateChangeListener(object : View.OnAttachStateChangeListener {
- override fun onViewAttachedToWindow(v: View) {
- v.removeOnAttachStateChangeListener(this)
- v.requestApplyInsets()
- }
-
- override fun onViewDetachedFromWindow(v: View) = Unit
- })
- }
-}
-
-data class InitialPadding(
- val left: Int, val top: Int,
- val right: Int, val bottom: Int,
-)
-
-fun recordInitialPaddingForView(view: View) = InitialPadding(
- view.paddingLeft, view.paddingTop, view.paddingRight, view.paddingBottom
-)
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/AlbumCoverStyle.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/AlbumCoverStyle.kt
deleted file mode 100644
index d797c50fb..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/AlbumCoverStyle.kt
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments
-
-import androidx.annotation.DrawableRes
-import androidx.annotation.StringRes
-import code.name.monkey.retromusic.R
-
-enum class AlbumCoverStyle(
- @StringRes val titleRes: Int,
- @DrawableRes val drawableResId: Int,
- val id: Int
-) {
- Card(R.string.card, R.drawable.np_blur_card, 3),
- Circle(R.string.circular, R.drawable.np_circle, 2),
- Flat(R.string.flat, R.drawable.np_flat, 1),
- FullCard(R.string.full_card, R.drawable.np_adaptive, 5),
- Full(R.string.full, R.drawable.np_full, 4),
- Normal(R.string.normal, R.drawable.np_normal, 0),
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/GridStyle.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/GridStyle.kt
deleted file mode 100644
index 505564a1c..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/GridStyle.kt
+++ /dev/null
@@ -1,16 +0,0 @@
-package code.name.monkey.retromusic.fragments
-
-import androidx.annotation.LayoutRes
-import code.name.monkey.retromusic.R
-
-enum class GridStyle constructor(
- @param:LayoutRes @field:LayoutRes val layoutResId: Int,
- val id: Int
-) {
- Grid(R.layout.item_grid, 0),
- Card(R.layout.item_card, 1),
- ColoredCard(R.layout.item_card_color, 2),
- Circular(R.layout.item_grid_circle, 3),
- Image(R.layout.image, 4),
- GradientImage(R.layout.item_image_gradient, 5)
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/LibraryViewModel.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/LibraryViewModel.kt
deleted file mode 100644
index 3e6b01b88..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/LibraryViewModel.kt
+++ /dev/null
@@ -1,383 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments
-
-import android.animation.ValueAnimator
-import android.content.Context
-import androidx.core.animation.doOnEnd
-import androidx.lifecycle.*
-import code.name.monkey.retromusic.RECENT_ALBUMS
-import code.name.monkey.retromusic.RECENT_ARTISTS
-import code.name.monkey.retromusic.TOP_ALBUMS
-import code.name.monkey.retromusic.TOP_ARTISTS
-import code.name.monkey.retromusic.db.*
-import code.name.monkey.retromusic.*
-import code.name.monkey.retromusic.extensions.showToast
-import code.name.monkey.retromusic.fragments.ReloadType.*
-import code.name.monkey.retromusic.fragments.search.Filter
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.interfaces.IMusicServiceEventListener
-import code.name.monkey.retromusic.model.*
-import code.name.monkey.retromusic.repository.RealRepository
-import code.name.monkey.retromusic.util.DensityUtil
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.logD
-import kotlinx.coroutines.Dispatchers.IO
-import kotlinx.coroutines.Dispatchers.Main
-import kotlinx.coroutines.launch
-import kotlinx.coroutines.withContext
-import java.io.File
-
-class LibraryViewModel(
- private val repository: RealRepository,
-) : ViewModel(), IMusicServiceEventListener {
-
- private val _paletteColor = MutableLiveData()
- private val home = MutableLiveData>()
- private val suggestions = MutableLiveData>()
- private val albums = MutableLiveData>()
- private val songs = MutableLiveData>()
- private val artists = MutableLiveData>()
- private val playlists = MutableLiveData>()
- private val genres = MutableLiveData>()
- private val searchResults = MutableLiveData>()
- private val fabMargin = MutableLiveData(0)
- private val songHistory = MutableLiveData>()
- private var previousSongHistory = ArrayList()
- val paletteColor: LiveData = _paletteColor
-
- init {
- loadLibraryContent()
- }
-
- private fun loadLibraryContent() = viewModelScope.launch(IO) {
- fetchHomeSections()
- fetchSuggestions()
- fetchSongs()
- fetchAlbums()
- fetchArtists()
- fetchGenres()
- fetchPlaylists()
- }
-
- fun getSearchResult(): LiveData> = searchResults
-
- fun getSongs(): LiveData> = songs
-
- fun getAlbums(): LiveData> = albums
-
- fun getArtists(): LiveData> = artists
-
- fun getPlaylists(): LiveData> = playlists
-
- fun getGenre(): LiveData> = genres
-
- fun getHome(): LiveData> = home
-
- fun getSuggestions(): LiveData> = suggestions
-
- fun getFabMargin(): LiveData = fabMargin
-
- private suspend fun fetchSongs() {
- songs.postValue(repository.allSongs())
- }
-
- private suspend fun fetchAlbums() {
- albums.postValue(repository.fetchAlbums())
- }
-
- private suspend fun fetchArtists() {
- if (PreferenceUtil.albumArtistsOnly) {
- artists.postValue(repository.albumArtists())
- } else {
- artists.postValue(repository.fetchArtists())
- }
- }
-
- private suspend fun fetchPlaylists() {
- playlists.postValue(repository.fetchPlaylistWithSongs())
- }
-
- private suspend fun fetchGenres() {
- genres.postValue(repository.fetchGenres())
- }
-
- private suspend fun fetchHomeSections() {
- home.postValue(repository.homeSections())
- }
-
- private suspend fun fetchSuggestions() {
- suggestions.postValue(repository.suggestions())
- }
-
- fun search(query: String?, filter: Filter) =
- viewModelScope.launch(IO) {
- val result = repository.search(query, filter)
- searchResults.postValue(result)
- }
-
- fun forceReload(reloadType: ReloadType) = viewModelScope.launch(IO) {
- when (reloadType) {
- Songs -> fetchSongs()
- Albums -> fetchAlbums()
- Artists -> fetchArtists()
- HomeSections -> fetchHomeSections()
- Playlists -> fetchPlaylists()
- Genres -> fetchGenres()
- Suggestions -> fetchSuggestions()
- }
- }
-
- fun updateColor(newColor: Int) {
- _paletteColor.postValue(newColor)
- }
-
- override fun onMediaStoreChanged() {
- logD("onMediaStoreChanged")
- loadLibraryContent()
- }
-
- override fun onServiceConnected() {
- logD("onServiceConnected")
- }
-
- override fun onServiceDisconnected() {
- logD("onServiceDisconnected")
- }
-
- override fun onQueueChanged() {
- logD("onQueueChanged")
- }
-
- override fun onPlayingMetaChanged() {
- logD("onPlayingMetaChanged")
- }
-
- override fun onPlayStateChanged() {
- logD("onPlayStateChanged")
- }
-
- override fun onRepeatModeChanged() {
- logD("onRepeatModeChanged")
- }
-
- override fun onShuffleModeChanged() {
- logD("onShuffleModeChanged")
- }
-
- override fun onFavoriteStateChanged() {
- logD("onFavoriteStateChanged")
- }
-
- fun shuffleSongs() = viewModelScope.launch(IO) {
- val songs = repository.allSongs()
- withContext(Main) {
- MusicPlayerRemote.openAndShuffleQueue(songs, true)
- }
- }
-
- fun renameRoomPlaylist(playListId: Long, name: String) = viewModelScope.launch(IO) {
- repository.renameRoomPlaylist(playListId, name)
- }
-
- fun deleteSongsInPlaylist(songs: List) {
- viewModelScope.launch(IO) {
- repository.deleteSongsInPlaylist(songs)
- forceReload(Playlists)
- }
- }
-
- fun deleteSongsFromPlaylist(playlists: List) = viewModelScope.launch(IO) {
- repository.deletePlaylistSongs(playlists)
- }
-
- fun deleteRoomPlaylist(playlists: List) = viewModelScope.launch(IO) {
- repository.deleteRoomPlaylist(playlists)
- }
-
- fun albumById(id: Long) = repository.albumById(id)
- suspend fun artistById(id: Long) = repository.artistById(id)
- suspend fun favoritePlaylist() = repository.favoritePlaylist()
- suspend fun isFavoriteSong(song: SongEntity) = repository.isFavoriteSong(song)
- suspend fun isSongFavorite(songId: Long) = repository.isSongFavorite(songId)
- suspend fun insertSongs(songs: List) = repository.insertSongs(songs)
- suspend fun removeSongFromPlaylist(songEntity: SongEntity) =
- repository.removeSongFromPlaylist(songEntity)
-
- private suspend fun checkPlaylistExists(playlistName: String): List =
- repository.checkPlaylistExists(playlistName)
-
- private suspend fun createPlaylist(playlistEntity: PlaylistEntity): Long =
- repository.createPlaylist(playlistEntity)
-
- fun importPlaylists() = viewModelScope.launch(IO) {
- val playlists = repository.fetchLegacyPlaylist()
- playlists.forEach { playlist ->
- val playlistEntity = repository.checkPlaylistExists(playlist.name).firstOrNull()
- if (playlistEntity != null) {
- val songEntities = playlist.getSongs().map {
- it.toSongEntity(playlistEntity.playListId)
- }
- repository.insertSongs(songEntities)
- } else {
- if (playlist != Playlist.empty) {
- val playListId = createPlaylist(PlaylistEntity(playlistName = playlist.name))
- val songEntities = playlist.getSongs().map {
- it.toSongEntity(playListId)
- }
- repository.insertSongs(songEntities)
- }
- }
- forceReload(Playlists)
- }
- }
-
- fun recentSongs(): LiveData> = liveData(IO) {
- emit(repository.recentSongs())
- }
-
- fun playCountSongs(): LiveData> = liveData(IO) {
- repository.playCountSongs().forEach { song ->
- if (!File(song.data).exists() || song.id == -1L) {
- repository.deleteSongInPlayCount(song)
- }
- }
- emit(repository.playCountSongs().map {
- it.toSong()
- })
- }
-
- fun artists(type: Int): LiveData> = liveData(IO) {
- when (type) {
- TOP_ARTISTS -> emit(repository.topArtists())
- RECENT_ARTISTS -> {
- emit(repository.recentArtists())
- }
- }
- }
-
- fun albums(type: Int): LiveData> = liveData(IO) {
- when (type) {
- TOP_ALBUMS -> emit(repository.topAlbums())
- RECENT_ALBUMS -> {
- emit(repository.recentAlbums())
- }
- }
- }
-
- fun artist(artistId: Long): LiveData = liveData(IO) {
- emit(repository.artistById(artistId))
- }
-
- fun observableHistorySongs(): LiveData> {
- viewModelScope.launch(IO) {
- repository.historySong().forEach { song ->
- if (!File(song.data).exists() || song.id == -1L) {
- repository.deleteSongInHistory(song.id)
- }
- }
-
- songHistory.postValue(repository.historySong().map {
- it.toSong()
- })
- }
- return songHistory
- }
-
- fun clearHistory() {
- viewModelScope.launch(IO) {
- previousSongHistory = repository.historySong() as ArrayList
-
- repository.clearSongHistory()
- }
- songHistory.value = emptyList()
- }
-
-
- fun restoreHistory() {
- viewModelScope.launch(IO) {
- if (previousSongHistory.isNotEmpty()) {
- val history = ArrayList()
- for (song in previousSongHistory) {
- repository.upsertSongInHistory(song.toSong())
- history.add(song.toSong())
- }
- songHistory.postValue(history)
- }
- }
- }
-
- fun favorites() = repository.favorites()
-
- fun clearSearchResult() {
- searchResults.value = emptyList()
- }
-
- fun addToPlaylist(context: Context, playlistName: String, songs: List) {
- viewModelScope.launch(IO) {
- val playlists = checkPlaylistExists(playlistName)
- if (playlists.isEmpty()) {
- val playlistId: Long =
- createPlaylist(PlaylistEntity(playlistName = playlistName))
- insertSongs(songs.map { it.toSongEntity(playlistId) })
- withContext(Main) {
- context.showToast(context.getString(R.string.playlist_created_sucessfully,
- playlistName))
- }
- } else {
- val playlist = playlists.firstOrNull()
- if (playlist != null) {
- insertSongs(songs.map {
- it.toSongEntity(playListId = playlist.playListId)
- })
- }
- }
- forceReload(Playlists)
- withContext(Main) {
- context.showToast(
- context.getString(
- R.string.added_song_count_to_playlist,
- songs.size,
- playlistName))
- }
- }
- }
-
- fun setFabMargin(context: Context, bottomMargin: Int) {
- val currentValue = DensityUtil.dip2px(context, 16F) +
- bottomMargin
- ValueAnimator.ofInt(fabMargin.value!!, currentValue).apply {
- addUpdateListener {
- fabMargin.postValue(
- (it.animatedValue as Int)
- )
- }
- doOnEnd {
- fabMargin.postValue(currentValue)
- }
- start()
- }
- }
-}
-
-enum class ReloadType {
- Songs,
- Albums,
- Artists,
- HomeSections,
- Playlists,
- Genres,
- Suggestions
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/MusicSeekSkipTouchListener.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/MusicSeekSkipTouchListener.kt
deleted file mode 100644
index 946b34e21..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/MusicSeekSkipTouchListener.kt
+++ /dev/null
@@ -1,79 +0,0 @@
-package code.name.monkey.retromusic.fragments
-
-import android.annotation.SuppressLint
-import android.view.MotionEvent
-import android.view.View
-import android.view.ViewConfiguration
-import androidx.fragment.app.FragmentActivity
-import androidx.lifecycle.lifecycleScope
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import kotlinx.coroutines.*
-import kotlin.math.abs
-
-/**
- * @param activity, Activity
- * @param next, if the button is next, if false then it's considered previous
- */
-class MusicSeekSkipTouchListener(val activity: FragmentActivity, val next: Boolean) :
- View.OnTouchListener {
-
- private var job: Job? = null
- private var counter = 0
- private var wasSeeking = false
-
- private var startX = 0f
- private var startY = 0f
-
- private val scaledTouchSlop = ViewConfiguration.get(activity).scaledTouchSlop
-
- @SuppressLint("ClickableViewAccessibility")
- override fun onTouch(v: View?, event: MotionEvent?): Boolean {
- when (event?.actionMasked) {
- MotionEvent.ACTION_DOWN -> {
- startX = event.x
- startY = event.y
- job = activity.lifecycleScope.launch(Dispatchers.Default) {
- counter = 0
- while (isActive) {
- delay(500)
- wasSeeking = true
- var seekingDuration = MusicPlayerRemote.songProgressMillis
- if (next) {
- seekingDuration += 5000 * (counter.floorDiv(2) + 1)
- } else {
- seekingDuration -= 5000 * (counter.floorDiv(2) + 1)
- }
- withContext(Dispatchers.Main) {
- MusicPlayerRemote.seekTo(seekingDuration)
- }
- counter += 1
- }
- }
- }
- MotionEvent.ACTION_UP -> {
- job?.cancel()
- val endX = event.x
- val endY = event.y
- if (!wasSeeking && isAClick(startX, endX, startY, endY)) {
- if (next) {
- MusicPlayerRemote.playNextSong()
- } else {
- MusicPlayerRemote.back()
- }
- }
-
- wasSeeking = false
- }
- MotionEvent.ACTION_CANCEL -> {
- job?.cancel()
- }
- }
- return false
- }
-
- private fun isAClick(startX: Float, endX: Float, startY: Float, endY: Float): Boolean {
- val differenceX = abs(startX - endX)
- val differenceY = abs(startY - endY)
- return !(differenceX > scaledTouchSlop || differenceY > scaledTouchSlop)
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/NowPlayingScreen.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/NowPlayingScreen.kt
deleted file mode 100644
index 0b2e6b1ff..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/NowPlayingScreen.kt
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments
-
-import androidx.annotation.DrawableRes
-import androidx.annotation.StringRes
-import code.name.monkey.retromusic.R
-
-enum class NowPlayingScreen constructor(
- @param:StringRes @field:StringRes
- val titleRes: Int,
- @param:DrawableRes @field:DrawableRes val drawableResId: Int,
- val id: Int,
- val defaultCoverTheme: AlbumCoverStyle?
-) {
- // Some Now playing themes look better with particular Album cover theme
-
- Adaptive(R.string.adaptive, R.drawable.np_adaptive, 10, AlbumCoverStyle.FullCard),
- Blur(R.string.blur, R.drawable.np_blur, 4, AlbumCoverStyle.Normal),
- BlurCard(R.string.blur_card, R.drawable.np_blur_card, 9, AlbumCoverStyle.Card),
- Card(R.string.card, R.drawable.np_card, 6, AlbumCoverStyle.Full),
- Circle(R.string.circle, R.drawable.np_minimalistic_circle, 15, null),
- Classic(R.string.classic, R.drawable.np_classic, 16, AlbumCoverStyle.Full),
- Color(R.string.color, R.drawable.np_color, 5, AlbumCoverStyle.Normal),
- Fit(R.string.fit, R.drawable.np_fit, 12, AlbumCoverStyle.Full),
- Flat(R.string.flat, R.drawable.np_flat, 1, AlbumCoverStyle.Flat),
- Full(R.string.full, R.drawable.np_full, 2, AlbumCoverStyle.Full),
- Gradient(R.string.gradient, R.drawable.np_gradient, 17, AlbumCoverStyle.Full),
- Material(R.string.material, R.drawable.np_material, 11, AlbumCoverStyle.Normal),
- MD3(R.string.md3, R.drawable.np_normal, 18, AlbumCoverStyle.Normal),
- Normal(R.string.normal, R.drawable.np_normal, 0, AlbumCoverStyle.Normal),
- Peek(R.string.peek, R.drawable.np_peek, 14, AlbumCoverStyle.Normal),
- Plain(R.string.plain, R.drawable.np_plain, 3, AlbumCoverStyle.Normal),
- Simple(R.string.simple, R.drawable.np_simple, 8, AlbumCoverStyle.Normal),
- Tiny(R.string.tiny, R.drawable.np_tiny, 7, null),
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/about/AboutFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/about/AboutFragment.kt
deleted file mode 100644
index 89edeb1af..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/about/AboutFragment.kt
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.about
-
-import android.content.pm.PackageManager
-import android.os.Bundle
-import android.view.View
-import androidx.fragment.app.Fragment
-import code.name.monkey.retromusic.Constants
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.databinding.FragmentAboutBinding
-import code.name.monkey.retromusic.extensions.openUrl
-import code.name.monkey.retromusic.fragments.LibraryViewModel
-import code.name.monkey.retromusic.util.NavigationUtil
-import dev.chrisbanes.insetter.applyInsetter
-import org.koin.androidx.viewmodel.ext.android.activityViewModel
-
-class AboutFragment : Fragment(R.layout.fragment_about), View.OnClickListener {
- private var _binding: FragmentAboutBinding? = null
- private val binding get() = _binding!!
-
- override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
- super.onViewCreated(view, savedInstanceState)
- _binding = FragmentAboutBinding.bind(view)
- binding.aboutContent.cardRetroInfo.version.setSummary(getAppVersion())
- setUpView()
-
- binding.aboutContent.root.applyInsetter {
- type(navigationBars = true) {
- padding(vertical = true)
- }
- }
- }
-
- private fun setUpView() {
- binding.aboutContent.cardRetroInfo.appGithub.setOnClickListener(this)
- binding.aboutContent.cardRetroInfo.faqLink.setOnClickListener(this)
- binding.aboutContent.cardRetroInfo.appTranslation.setOnClickListener(this)
- binding.aboutContent.cardRetroInfo.bugReportLink.setOnClickListener(this)
- binding.aboutContent.cardRetroInfo.changelog.setOnClickListener(this)
- binding.aboutContent.cardRetroInfo.openSource.setOnClickListener(this)
- }
-
- override fun onClick(view: View) {
- when (view.id) {
- R.id.faqLink -> openUrl(Constants.FAQ_LINK)
- R.id.appGithub -> openUrl(Constants.GITHUB_PROJECT)
- R.id.appTranslation -> openUrl(Constants.TRANSLATE)
- R.id.changelog -> NavigationUtil.gotoWhatNews(requireActivity())
- R.id.openSource -> NavigationUtil.goToOpenSource(requireActivity())
- R.id.bugReportLink -> NavigationUtil.bugReport(requireActivity())
- }
- }
-
- private fun getAppVersion(): String {
- return try {
- requireActivity().packageManager.getPackageInfo(requireActivity().packageName, 0).versionName
- } catch (e: PackageManager.NameNotFoundException) {
- e.printStackTrace()
- "0.0.0"
- }
- }
-
- override fun onDestroyView() {
- super.onDestroyView()
- _binding = null
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumDetailsFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumDetailsFragment.kt
deleted file mode 100644
index 5b8dc638c..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumDetailsFragment.kt
+++ /dev/null
@@ -1,403 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.albums
-
-import android.app.ActivityOptions
-import android.content.Intent
-import android.graphics.Color
-import android.os.Bundle
-import android.view.*
-import androidx.appcompat.app.AppCompatActivity
-import androidx.core.os.bundleOf
-import androidx.core.view.doOnPreDraw
-import androidx.lifecycle.lifecycleScope
-import androidx.navigation.fragment.FragmentNavigatorExtras
-import androidx.navigation.fragment.findNavController
-import androidx.navigation.fragment.navArgs
-import androidx.recyclerview.widget.DefaultItemAnimator
-import androidx.recyclerview.widget.GridLayoutManager
-import androidx.recyclerview.widget.LinearLayoutManager
-import code.name.monkey.appthemehelper.common.ATHToolbarActivity.getToolbarBackgroundColor
-import code.name.monkey.appthemehelper.util.ToolbarContentTintHelper
-import code.name.monkey.retromusic.EXTRA_ALBUM_ID
-import code.name.monkey.retromusic.EXTRA_ARTIST_ID
-import code.name.monkey.retromusic.EXTRA_ARTIST_NAME
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.activities.tageditor.AbsTagEditorActivity
-import code.name.monkey.retromusic.activities.tageditor.AlbumTagEditorActivity
-import code.name.monkey.retromusic.adapter.album.HorizontalAlbumAdapter
-import code.name.monkey.retromusic.adapter.song.SimpleSongAdapter
-import code.name.monkey.retromusic.databinding.FragmentAlbumDetailsBinding
-import code.name.monkey.retromusic.dialogs.AddToPlaylistDialog
-import code.name.monkey.retromusic.dialogs.DeleteSongsDialog
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.fragments.base.AbsMainActivityFragment
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.albumCoverOptions
-import code.name.monkey.retromusic.glide.RetroGlideExtension.artistImageOptions
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.SingleColorTarget
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.helper.SortOrder.AlbumSongSortOrder.Companion.SONG_A_Z
-import code.name.monkey.retromusic.helper.SortOrder.AlbumSongSortOrder.Companion.SONG_DURATION
-import code.name.monkey.retromusic.helper.SortOrder.AlbumSongSortOrder.Companion.SONG_TRACK_LIST
-import code.name.monkey.retromusic.helper.SortOrder.AlbumSongSortOrder.Companion.SONG_Z_A
-import code.name.monkey.retromusic.interfaces.IAlbumClickListener
-import code.name.monkey.retromusic.model.Album
-import code.name.monkey.retromusic.model.Artist
-import code.name.monkey.retromusic.repository.RealRepository
-import code.name.monkey.retromusic.util.*
-import com.bumptech.glide.Glide
-import com.google.android.material.shape.MaterialShapeDrawable
-import com.google.android.material.transition.MaterialArcMotion
-import com.google.android.material.transition.MaterialContainerTransform
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.launch
-import kotlinx.coroutines.withContext
-import org.koin.android.ext.android.get
-import org.koin.androidx.viewmodel.ext.android.viewModel
-import org.koin.core.parameter.parametersOf
-import java.text.Collator
-
-class AlbumDetailsFragment : AbsMainActivityFragment(R.layout.fragment_album_details),
- IAlbumClickListener {
-
- private var _binding: FragmentAlbumDetailsBinding? = null
- private val binding get() = _binding!!
-
- private val arguments by navArgs()
- private val detailsViewModel by viewModel {
- parametersOf(arguments.extraAlbumId)
- }
-
- private lateinit var simpleSongAdapter: SimpleSongAdapter
- private lateinit var album: Album
- private var albumArtistExists = false
-
- private val savedSortOrder: String
- get() = PreferenceUtil.albumDetailSongSortOrder
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- sharedElementEnterTransition = MaterialContainerTransform().apply {
- drawingViewId = R.id.fragment_container
- scrimColor = Color.TRANSPARENT
- setAllContainerColors(surfaceColor())
- setPathMotion(MaterialArcMotion())
- }
- }
-
- override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
- super.onViewCreated(view, savedInstanceState)
- _binding = FragmentAlbumDetailsBinding.bind(view)
- mainActivity.addMusicServiceEventListener(detailsViewModel)
- mainActivity.setSupportActionBar(binding.toolbar)
-
- binding.toolbar.title = " "
- binding.albumCoverContainer.transitionName = arguments.extraAlbumId.toString()
- postponeEnterTransition()
- detailsViewModel.getAlbum().observe(viewLifecycleOwner) { album ->
- view.doOnPreDraw {
- startPostponedEnterTransition()
- }
- albumArtistExists = !album.albumArtist.isNullOrEmpty()
- showAlbum(album)
- binding.artistImage.transitionName = if (albumArtistExists) {
- album.albumArtist
- } else {
- album.artistId.toString()
- }
- }
-
- setupRecyclerView()
- binding.artistImage.setOnClickListener { artistView ->
- if (albumArtistExists) {
- findActivityNavController(R.id.fragment_container)
- .navigate(
- R.id.albumArtistDetailsFragment,
- bundleOf(EXTRA_ARTIST_NAME to album.albumArtist),
- null,
- FragmentNavigatorExtras(artistView to album.albumArtist.toString())
- )
- } else {
- findActivityNavController(R.id.fragment_container)
- .navigate(
- R.id.artistDetailsFragment,
- bundleOf(EXTRA_ARTIST_ID to album.artistId),
- null,
- FragmentNavigatorExtras(artistView to album.artistId.toString())
- )
- }
-
- }
- binding.fragmentAlbumContent.playAction.setOnClickListener {
- MusicPlayerRemote.openQueue(album.songs, 0, true)
- }
- binding.fragmentAlbumContent.shuffleAction.setOnClickListener {
- MusicPlayerRemote.openAndShuffleQueue(
- album.songs,
- true
- )
- }
-
- binding.appBarLayout?.statusBarForeground =
- MaterialShapeDrawable.createWithElevationOverlay(requireContext())
- }
-
- override fun onDestroy() {
- super.onDestroy()
- serviceActivity?.removeMusicServiceEventListener(detailsViewModel)
- }
-
- private fun setupRecyclerView() {
- simpleSongAdapter = SimpleSongAdapter(
- requireActivity() as AppCompatActivity,
- ArrayList(),
- R.layout.item_song
- )
- binding.fragmentAlbumContent.recyclerView.apply {
- layoutManager = LinearLayoutManager(requireContext())
- itemAnimator = DefaultItemAnimator()
- isNestedScrollingEnabled = false
- adapter = simpleSongAdapter
- }
- }
-
- private fun showAlbum(album: Album) {
- if (album.songs.isEmpty()) {
- findNavController().navigateUp()
- return
- }
- this.album = album
-
- binding.albumTitle.text = album.title
- val songText = resources.getQuantityString(
- R.plurals.albumSongs,
- album.songCount,
- album.songCount
- )
- binding.fragmentAlbumContent.songTitle.text = songText
- if (MusicUtil.getYearString(album.year) == "-") {
- binding.albumText.text = String.format(
- "%s • %s",
- if (albumArtistExists) album.albumArtist else album.artistName,
- MusicUtil.getReadableDurationString(MusicUtil.getTotalDuration(album.songs))
- )
- } else {
- binding.albumText.text = String.format(
- "%s • %s • %s",
- album.artistName,
- MusicUtil.getYearString(album.year),
- MusicUtil.getReadableDurationString(MusicUtil.getTotalDuration(album.songs))
- )
- }
- loadAlbumCover(album)
- simpleSongAdapter.swapDataSet(album.songs)
- if (albumArtistExists) {
- detailsViewModel.getAlbumArtist(album.albumArtist.toString())
- .observe(viewLifecycleOwner) {
- loadArtistImage(it)
- }
- } else {
- detailsViewModel.getArtist(album.artistId).observe(viewLifecycleOwner) {
- loadArtistImage(it)
- }
- }
- }
-
- private fun moreAlbums(albums: List) {
- binding.fragmentAlbumContent.moreTitle.show()
- binding.fragmentAlbumContent.moreRecyclerView.show()
- binding.fragmentAlbumContent.moreTitle.text =
- String.format(getString(R.string.label_more_from), album.artistName)
-
- val albumAdapter =
- HorizontalAlbumAdapter(requireActivity() as AppCompatActivity, albums, this)
- binding.fragmentAlbumContent.moreRecyclerView.layoutManager = GridLayoutManager(
- requireContext(),
- 1,
- GridLayoutManager.HORIZONTAL,
- false
- )
- binding.fragmentAlbumContent.moreRecyclerView.adapter = albumAdapter
- }
-
- private fun loadArtistImage(artist: Artist) {
- detailsViewModel.getMoreAlbums(artist).observe(viewLifecycleOwner) {
- moreAlbums(it)
- }
- Glide.with(requireContext())
- //.forceDownload(PreferenceUtil.isAllowedToDownloadMetadata())
- .load(
- RetroGlideExtension.getArtistModel(artist)
- )
- .artistImageOptions(artist)
- .dontAnimate()
- .dontTransform()
- .into(binding.artistImage)
- }
-
- private fun loadAlbumCover(album: Album) {
- Glide.with(requireContext())
- .asBitmapPalette()
- .albumCoverOptions(album.safeGetFirstSong())
- //.checkIgnoreMediaStore()
- .load(RetroGlideExtension.getSongModel(album.safeGetFirstSong()))
- .into(object : SingleColorTarget(binding.image) {
- override fun onColorReady(color: Int) {
- setColors(color)
- }
- })
- }
-
- private fun setColors(color: Int) {
- _binding?.fragmentAlbumContent?.apply {
- shuffleAction.applyColor(color)
- playAction.applyOutlineColor(color)
- }
- }
-
- override fun onAlbumClick(albumId: Long, view: View) {
- findNavController().navigate(
- R.id.albumDetailsFragment,
- bundleOf(EXTRA_ALBUM_ID to albumId),
- null,
- FragmentNavigatorExtras(
- view to albumId.toString()
- )
- )
- }
-
- override fun onCreateMenu(menu: Menu, inflater: MenuInflater) {
- inflater.inflate(R.menu.menu_album_detail, menu)
- val sortOrder = menu.findItem(R.id.action_sort_order)
- setUpSortOrderMenu(sortOrder.subMenu!!)
- ToolbarContentTintHelper.handleOnCreateOptionsMenu(
- requireContext(),
- binding.toolbar,
- menu,
- getToolbarBackgroundColor(binding.toolbar)
- )
- }
-
- override fun onMenuItemSelected(item: MenuItem): Boolean {
- return handleSortOrderMenuItem(item)
- }
-
- private fun handleSortOrderMenuItem(item: MenuItem): Boolean {
- var sortOrder: String? = null
- val songs = simpleSongAdapter.dataSet
- when (item.itemId) {
- android.R.id.home -> findNavController().navigateUp()
- R.id.action_play_next -> {
- MusicPlayerRemote.playNext(songs)
- return true
- }
-
- R.id.action_add_to_current_playing -> {
- MusicPlayerRemote.enqueue(songs)
- return true
- }
-
- R.id.action_add_to_playlist -> {
- lifecycleScope.launch(Dispatchers.IO) {
- val playlists = get().fetchPlaylists()
- withContext(Dispatchers.Main) {
- AddToPlaylistDialog.create(playlists, songs)
- .show(childFragmentManager, "ADD_PLAYLIST")
- }
- }
- return true
- }
-
- R.id.action_delete_from_device -> {
- DeleteSongsDialog.create(songs).show(childFragmentManager, "DELETE_SONGS")
- return true
- }
-
- R.id.action_tag_editor -> {
- val intent = Intent(requireContext(), AlbumTagEditorActivity::class.java)
- intent.putExtra(AbsTagEditorActivity.EXTRA_ID, album.id)
- val options = ActivityOptions.makeSceneTransitionAnimation(
- requireActivity(),
- binding.albumCoverContainer,
- "${getString(R.string.transition_album_art)}_${album.id}"
- )
- startActivity(
- intent, options.toBundle()
- )
- return true
- }
-
- R.id.action_sort_order_title -> sortOrder = SONG_A_Z
- R.id.action_sort_order_title_desc -> sortOrder = SONG_Z_A
- R.id.action_sort_order_track_list -> sortOrder = SONG_TRACK_LIST
- R.id.action_sort_order_artist_song_duration -> sortOrder = SONG_DURATION
- }
- if (sortOrder != null) {
- item.isChecked = true
- setSaveSortOrder(sortOrder)
- }
- return true
- }
-
- private fun setUpSortOrderMenu(sortOrder: SubMenu) {
- when (savedSortOrder) {
- SONG_A_Z -> sortOrder.findItem(R.id.action_sort_order_title).isChecked = true
- SONG_Z_A -> sortOrder.findItem(R.id.action_sort_order_title_desc).isChecked = true
- SONG_TRACK_LIST ->
- sortOrder.findItem(R.id.action_sort_order_track_list).isChecked = true
-
- SONG_DURATION ->
- sortOrder.findItem(R.id.action_sort_order_artist_song_duration).isChecked = true
- }
- }
-
- private fun setSaveSortOrder(sortOrder: String) {
- PreferenceUtil.albumDetailSongSortOrder = sortOrder
- val songs = when (sortOrder) {
- SONG_TRACK_LIST -> album.songs.sortedWith { o1, o2 ->
- o1.trackNumber.compareTo(
- o2.trackNumber
- )
- }
-
- SONG_A_Z -> {
- val collator = Collator.getInstance()
- album.songs.sortedWith { o1, o2 -> collator.compare(o1.title, o2.title) }
- }
-
- SONG_Z_A -> {
- val collator = Collator.getInstance()
- album.songs.sortedWith { o1, o2 -> collator.compare(o2.title, o1.title) }
- }
-
- SONG_DURATION -> album.songs.sortedWith { o1, o2 ->
- o1.duration.compareTo(
- o2.duration
- )
- }
-
- else -> throw IllegalArgumentException("invalid $sortOrder")
- }
- album = album.copy(songs = songs)
- simpleSongAdapter.swapDataSet(album.songs)
- }
-
- override fun onDestroyView() {
- super.onDestroyView()
- _binding = null
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumDetailsViewModel.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumDetailsViewModel.kt
deleted file mode 100644
index 261df90a6..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumDetailsViewModel.kt
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.albums
-
-import androidx.lifecycle.*
-import code.name.monkey.retromusic.interfaces.IMusicServiceEventListener
-import code.name.monkey.retromusic.model.Album
-import code.name.monkey.retromusic.model.Artist
-import code.name.monkey.retromusic.repository.RealRepository
-import kotlinx.coroutines.Dispatchers.IO
-import kotlinx.coroutines.launch
-
-class AlbumDetailsViewModel(
- private val repository: RealRepository,
- private val albumId: Long
-) : ViewModel(), IMusicServiceEventListener {
- private val albumDetails = MutableLiveData()
-
- init {
- fetchAlbum()
- }
-
- private fun fetchAlbum() {
- viewModelScope.launch(IO) {
- albumDetails.postValue(repository.albumByIdAsync(albumId))
- }
- }
-
- fun getAlbum(): LiveData = albumDetails
-
- fun getArtist(artistId: Long): LiveData = liveData(IO) {
- val artist = repository.artistById(artistId)
- emit(artist)
- }
-
- fun getAlbumArtist(artistName: String): LiveData = liveData(IO) {
- val artist = repository.albumArtistByName(artistName)
- emit(artist)
- }
-
- fun getMoreAlbums(artist: Artist): LiveData> = liveData(IO) {
- artist.albums.filter { item -> item.id != albumId }.let { albums ->
- if (albums.isNotEmpty()) emit(albums)
- }
- }
-
- override fun onMediaStoreChanged() {
- fetchAlbum()
- }
-
- override fun onServiceConnected() {}
- override fun onServiceDisconnected() {}
- override fun onQueueChanged() {}
- override fun onPlayingMetaChanged() {}
- override fun onPlayStateChanged() {}
- override fun onRepeatModeChanged() {}
- override fun onShuffleModeChanged() {}
- override fun onFavoriteStateChanged() {}
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumsFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumsFragment.kt
deleted file mode 100644
index 1b021bdf2..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/albums/AlbumsFragment.kt
+++ /dev/null
@@ -1,334 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.albums
-
-import android.os.Bundle
-import android.view.*
-import androidx.core.os.bundleOf
-import androidx.navigation.fragment.FragmentNavigatorExtras
-import androidx.navigation.fragment.findNavController
-import androidx.recyclerview.widget.GridLayoutManager
-import code.name.monkey.retromusic.EXTRA_ALBUM_ID
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.adapter.album.AlbumAdapter
-import code.name.monkey.retromusic.fragments.GridStyle
-import code.name.monkey.retromusic.fragments.ReloadType
-import code.name.monkey.retromusic.fragments.base.AbsRecyclerViewCustomGridSizeFragment
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.helper.SortOrder.AlbumSortOrder
-import code.name.monkey.retromusic.interfaces.IAlbumClickListener
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.RetroUtil
-
-class AlbumsFragment : AbsRecyclerViewCustomGridSizeFragment(),
- IAlbumClickListener {
-
- override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
- super.onViewCreated(view, savedInstanceState)
- libraryViewModel.getAlbums().observe(viewLifecycleOwner) {
- if (it.isNotEmpty())
- adapter?.swapDataSet(it)
- else
- adapter?.swapDataSet(listOf())
- }
- }
-
- override val titleRes: Int
- get() = R.string.albums
-
- override val emptyMessage: Int
- get() = R.string.no_albums
-
- override val isShuffleVisible: Boolean
- get() = true
-
- override fun onShuffleClicked() {
- libraryViewModel.getAlbums().value?.let {
- MusicPlayerRemote.setShuffleMode(MusicService.SHUFFLE_MODE_NONE)
- MusicPlayerRemote.openQueue(
- queue = it.shuffled().flatMap { album -> album.songs },
- startPosition = 0,
- startPlaying = true
- )
- }
- }
-
- override fun createLayoutManager(): GridLayoutManager {
- return GridLayoutManager(requireActivity(), getGridSize())
- }
-
- override fun createAdapter(): AlbumAdapter {
- val dataSet = if (adapter == null) ArrayList() else adapter!!.dataSet
- return AlbumAdapter(
- requireActivity(),
- dataSet,
- itemLayoutRes(),
- this
- )
- }
-
- override fun setGridSize(gridSize: Int) {
- layoutManager?.spanCount = gridSize
- adapter?.notifyDataSetChanged()
- }
-
- override fun loadSortOrder(): String {
- return PreferenceUtil.albumSortOrder
- }
-
- override fun saveSortOrder(sortOrder: String) {
- PreferenceUtil.albumSortOrder = sortOrder
- }
-
- override fun loadGridSize(): Int {
- return PreferenceUtil.albumGridSize
- }
-
- override fun saveGridSize(gridColumns: Int) {
- PreferenceUtil.albumGridSize = gridColumns
- }
-
- override fun loadGridSizeLand(): Int {
- return PreferenceUtil.albumGridSizeLand
- }
-
- override fun saveGridSizeLand(gridColumns: Int) {
- PreferenceUtil.albumGridSizeLand = gridColumns
- }
-
- override fun setSortOrder(sortOrder: String) {
- libraryViewModel.forceReload(ReloadType.Albums)
- }
-
- override fun loadLayoutRes(): Int {
- return PreferenceUtil.albumGridStyle.layoutResId
- }
-
- override fun saveLayoutRes(layoutRes: Int) {
- PreferenceUtil.albumGridStyle = GridStyle.values().first { gridStyle ->
- gridStyle.layoutResId == layoutRes
- }
- }
-
- companion object {
- fun newInstance(): AlbumsFragment {
- return AlbumsFragment()
- }
- }
-
- override fun onAlbumClick(albumId: Long, view: View) {
- findNavController().navigate(
- R.id.albumDetailsFragment,
- bundleOf(EXTRA_ALBUM_ID to albumId),
- null,
- FragmentNavigatorExtras(
- view to albumId.toString()
- )
- )
- reenterTransition = null
- }
-
- override fun onCreateMenu(menu: Menu, inflater: MenuInflater) {
- super.onCreateMenu(menu, inflater)
- val gridSizeItem: MenuItem = menu.findItem(R.id.action_grid_size)
- if (RetroUtil.isLandscape) {
- gridSizeItem.setTitle(R.string.action_grid_size_land)
- }
- setUpGridSizeMenu(gridSizeItem.subMenu!!)
- val layoutItem = menu.findItem(R.id.action_layout_type)
- setupLayoutMenu(layoutItem.subMenu!!)
- setUpSortOrderMenu(menu.findItem(R.id.action_sort_order).subMenu!!)
- }
-
- private fun setUpSortOrderMenu(
- sortOrderMenu: SubMenu
- ) {
- val currentSortOrder: String? = getSortOrder()
- sortOrderMenu.clear()
- sortOrderMenu.add(
- 0,
- R.id.action_album_sort_order_asc,
- 0,
- R.string.sort_order_a_z
- ).isChecked =
- currentSortOrder.equals(AlbumSortOrder.ALBUM_A_Z)
- sortOrderMenu.add(
- 0,
- R.id.action_album_sort_order_desc,
- 1,
- R.string.sort_order_z_a
- ).isChecked =
- currentSortOrder.equals(AlbumSortOrder.ALBUM_Z_A)
- sortOrderMenu.add(
- 0,
- R.id.action_album_sort_order_artist,
- 2,
- R.string.sort_order_album_artist
- ).isChecked =
- currentSortOrder.equals(AlbumSortOrder.ALBUM_ARTIST)
- sortOrderMenu.add(
- 0,
- R.id.action_album_sort_order_year,
- 3,
- R.string.sort_order_year
- ).isChecked =
- currentSortOrder.equals(AlbumSortOrder.ALBUM_YEAR)
- sortOrderMenu.add(
- 0,
- R.id.action_album_sort_order_num_songs,
- 4,
- R.string.sort_order_num_songs
- ).isChecked =
- currentSortOrder.equals(AlbumSortOrder.ALBUM_NUMBER_OF_SONGS)
-
- sortOrderMenu.setGroupCheckable(0, true, true)
- }
-
- private fun setupLayoutMenu(
- subMenu: SubMenu
- ) {
- when (itemLayoutRes()) {
- R.layout.item_card -> subMenu.findItem(R.id.action_layout_card).isChecked = true
- R.layout.item_grid -> subMenu.findItem(R.id.action_layout_normal).isChecked = true
- R.layout.item_card_color ->
- subMenu.findItem(R.id.action_layout_colored_card).isChecked = true
- R.layout.item_grid_circle ->
- subMenu.findItem(R.id.action_layout_circular).isChecked = true
- R.layout.image -> subMenu.findItem(R.id.action_layout_image).isChecked = true
- R.layout.item_image_gradient ->
- subMenu.findItem(R.id.action_layout_gradient_image).isChecked = true
- }
- }
-
- private fun setUpGridSizeMenu(
- gridSizeMenu: SubMenu
- ) {
- when (getGridSize()) {
- 1 -> gridSizeMenu.findItem(R.id.action_grid_size_1).isChecked =
- true
- 2 -> gridSizeMenu.findItem(R.id.action_grid_size_2).isChecked = true
- 3 -> gridSizeMenu.findItem(R.id.action_grid_size_3).isChecked = true
- 4 -> gridSizeMenu.findItem(R.id.action_grid_size_4).isChecked = true
- 5 -> gridSizeMenu.findItem(R.id.action_grid_size_5).isChecked = true
- 6 -> gridSizeMenu.findItem(R.id.action_grid_size_6).isChecked = true
- 7 -> gridSizeMenu.findItem(R.id.action_grid_size_7).isChecked = true
- 8 -> gridSizeMenu.findItem(R.id.action_grid_size_8).isChecked = true
- }
- val gridSize: Int = maxGridSize
- if (gridSize < 8) {
- gridSizeMenu.findItem(R.id.action_grid_size_8).isVisible = false
- }
- if (gridSize < 7) {
- gridSizeMenu.findItem(R.id.action_grid_size_7).isVisible = false
- }
- if (gridSize < 6) {
- gridSizeMenu.findItem(R.id.action_grid_size_6).isVisible = false
- }
- if (gridSize < 5) {
- gridSizeMenu.findItem(R.id.action_grid_size_5).isVisible = false
- }
- if (gridSize < 4) {
- gridSizeMenu.findItem(R.id.action_grid_size_4).isVisible = false
- }
- if (gridSize < 3) {
- gridSizeMenu.findItem(R.id.action_grid_size_3).isVisible = false
- }
- }
-
- override fun onMenuItemSelected(item: MenuItem): Boolean {
- if (handleGridSizeMenuItem(item)) {
- return true
- }
- if (handleLayoutResType(item)) {
- return true
- }
- if (handleSortOrderMenuItem(item)) {
- return true
- }
- return super.onMenuItemSelected(item)
- }
-
- private fun handleSortOrderMenuItem(
- item: MenuItem
- ): Boolean {
- val sortOrder: String = when (item.itemId) {
- R.id.action_album_sort_order_asc -> AlbumSortOrder.ALBUM_A_Z
- R.id.action_album_sort_order_desc -> AlbumSortOrder.ALBUM_Z_A
- R.id.action_album_sort_order_artist -> AlbumSortOrder.ALBUM_ARTIST
- R.id.action_album_sort_order_year -> AlbumSortOrder.ALBUM_YEAR
- R.id.action_album_sort_order_num_songs -> AlbumSortOrder.ALBUM_NUMBER_OF_SONGS
- else -> PreferenceUtil.albumSortOrder
- }
- if (sortOrder != PreferenceUtil.albumSortOrder) {
- item.isChecked = true
- setAndSaveSortOrder(sortOrder)
- return true
- }
- return false
- }
-
- private fun handleLayoutResType(
- item: MenuItem
- ): Boolean {
- val layoutRes = when (item.itemId) {
- R.id.action_layout_normal -> R.layout.item_grid
- R.id.action_layout_card -> R.layout.item_card
- R.id.action_layout_colored_card -> R.layout.item_card_color
- R.id.action_layout_circular -> R.layout.item_grid_circle
- R.id.action_layout_image -> R.layout.image
- R.id.action_layout_gradient_image -> R.layout.item_image_gradient
- else -> PreferenceUtil.albumGridStyle.layoutResId
- }
- if (layoutRes != PreferenceUtil.albumGridStyle.layoutResId) {
- item.isChecked = true
- setAndSaveLayoutRes(layoutRes)
- return true
- }
- return false
- }
-
- private fun handleGridSizeMenuItem(
- item: MenuItem
- ): Boolean {
- val gridSize = when (item.itemId) {
- R.id.action_grid_size_1 -> 1
- R.id.action_grid_size_2 -> 2
- R.id.action_grid_size_3 -> 3
- R.id.action_grid_size_4 -> 4
- R.id.action_grid_size_5 -> 5
- R.id.action_grid_size_6 -> 6
- R.id.action_grid_size_7 -> 7
- R.id.action_grid_size_8 -> 8
- else -> 0
- }
- if (gridSize > 0) {
- item.isChecked = true
- setAndSaveGridSize(gridSize)
- return true
- }
- return false
- }
-
- override fun onResume() {
- super.onResume()
- libraryViewModel.forceReload(ReloadType.Albums)
- }
-
- override fun onPause() {
- super.onPause()
- adapter?.actionMode?.finish()
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/AbsArtistDetailsFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/artists/AbsArtistDetailsFragment.kt
deleted file mode 100644
index 7eb541485..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/AbsArtistDetailsFragment.kt
+++ /dev/null
@@ -1,288 +0,0 @@
-package code.name.monkey.retromusic.fragments.artists
-
-import android.graphics.Color
-import android.os.Bundle
-import android.view.Menu
-import android.view.MenuInflater
-import android.view.MenuItem
-import android.view.View
-import androidx.activity.result.PickVisualMediaRequest
-import androidx.activity.result.contract.ActivityResultContracts
-import androidx.appcompat.widget.PopupMenu
-import androidx.core.os.bundleOf
-import androidx.core.view.doOnPreDraw
-import androidx.lifecycle.lifecycleScope
-import androidx.navigation.fragment.FragmentNavigatorExtras
-import androidx.navigation.fragment.findNavController
-import androidx.recyclerview.widget.DefaultItemAnimator
-import androidx.recyclerview.widget.GridLayoutManager
-import androidx.recyclerview.widget.LinearLayoutManager
-import code.name.monkey.retromusic.EXTRA_ALBUM_ID
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.adapter.album.HorizontalAlbumAdapter
-import code.name.monkey.retromusic.adapter.song.SimpleSongAdapter
-import code.name.monkey.retromusic.databinding.FragmentArtistDetailsBinding
-import code.name.monkey.retromusic.dialogs.AddToPlaylistDialog
-import code.name.monkey.retromusic.extensions.*
-import code.name.monkey.retromusic.fragments.base.AbsMainActivityFragment
-import code.name.monkey.retromusic.glide.RetroGlideExtension
-import code.name.monkey.retromusic.glide.RetroGlideExtension.artistImageOptions
-import code.name.monkey.retromusic.glide.RetroGlideExtension.asBitmapPalette
-import code.name.monkey.retromusic.glide.SingleColorTarget
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.helper.SortOrder
-import code.name.monkey.retromusic.interfaces.IAlbumClickListener
-import code.name.monkey.retromusic.model.Artist
-import code.name.monkey.retromusic.repository.RealRepository
-import code.name.monkey.retromusic.util.*
-import com.bumptech.glide.Glide
-import com.google.android.material.shape.MaterialShapeDrawable
-import com.google.android.material.transition.MaterialContainerTransform
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.launch
-import kotlinx.coroutines.withContext
-import org.koin.android.ext.android.get
-import java.util.*
-
-abstract class AbsArtistDetailsFragment : AbsMainActivityFragment(R.layout.fragment_artist_details),
- IAlbumClickListener {
- private var _binding: FragmentArtistDetailsBinding? = null
- private val binding get() = _binding!!
-
- abstract val detailsViewModel: ArtistDetailsViewModel
- abstract val artistId: Long?
- abstract val artistName: String?
- private lateinit var artist: Artist
- private lateinit var songAdapter: SimpleSongAdapter
- private lateinit var albumAdapter: HorizontalAlbumAdapter
- private var forceDownload: Boolean = false
-
- private val savedSongSortOrder: String
- get() = PreferenceUtil.artistDetailSongSortOrder
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- sharedElementEnterTransition = MaterialContainerTransform().apply {
- drawingViewId = R.id.fragment_container
- scrimColor = Color.TRANSPARENT
- setAllContainerColors(surfaceColor())
- }
- }
-
- override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
- super.onViewCreated(view, savedInstanceState)
- _binding = FragmentArtistDetailsBinding.bind(view)
- mainActivity.addMusicServiceEventListener(detailsViewModel)
- mainActivity.setSupportActionBar(binding.toolbar)
- binding.toolbar.title = null
- binding.artistCoverContainer.transitionName = (artistId ?: artistName).toString()
- postponeEnterTransition()
- detailsViewModel.getArtist().observe(viewLifecycleOwner) {
- view.doOnPreDraw {
- startPostponedEnterTransition()
- }
- showArtist(it)
- }
- setupRecyclerView()
-
- binding.fragmentArtistContent.playAction.apply {
- setOnClickListener { MusicPlayerRemote.openQueue(artist.sortedSongs, 0, true) }
- }
- binding.fragmentArtistContent.shuffleAction.apply {
- setOnClickListener { MusicPlayerRemote.openAndShuffleQueue(artist.songs, true) }
- }
-
- setupSongSortButton()
- binding.appBarLayout?.statusBarForeground =
- MaterialShapeDrawable.createWithElevationOverlay(requireContext())
- }
-
- private fun setupRecyclerView() {
- albumAdapter = HorizontalAlbumAdapter(requireActivity(), ArrayList(), this)
- binding.fragmentArtistContent.albumRecyclerView.apply {
- itemAnimator = DefaultItemAnimator()
- layoutManager = GridLayoutManager(this.context, 1, GridLayoutManager.HORIZONTAL, false)
- adapter = albumAdapter
- }
- songAdapter = SimpleSongAdapter(requireActivity(), ArrayList(), R.layout.item_song)
- binding.fragmentArtistContent.recyclerView.apply {
- itemAnimator = DefaultItemAnimator()
- layoutManager = LinearLayoutManager(this.context)
- adapter = songAdapter
- }
- }
-
- private fun showArtist(artist: Artist) {
- if (artist.songCount == 0) {
- findNavController().navigateUp()
- return
- }
- this.artist = artist
- loadArtistImage(artist)
- binding.artistTitle.text = artist.name
- binding.text.text = String.format(
- "%s • %s",
- MusicUtil.getArtistInfoString(requireContext(), artist),
- MusicUtil.getReadableDurationString(MusicUtil.getTotalDuration(artist.songs))
- )
- val songText = resources.getQuantityString(
- R.plurals.albumSongs, artist.songCount, artist.songCount
- )
- val albumText = resources.getQuantityString(
- R.plurals.albums, artist.songCount, artist.songCount
- )
- binding.fragmentArtistContent.songTitle.text = songText
- binding.fragmentArtistContent.albumTitle.text = albumText
- songAdapter.swapDataSet(artist.sortedSongs)
- albumAdapter.swapDataSet(artist.albums)
- }
-
- private fun loadArtistImage(artist: Artist) {
- Glide.with(requireContext()).asBitmapPalette().artistImageOptions(artist)
- .load(RetroGlideExtension.getArtistModel(artist)).dontAnimate()
- .into(object : SingleColorTarget(binding.image) {
- override fun onColorReady(color: Int) {
- setColors(color)
- }
- })
- }
-
- private fun setColors(color: Int) {
- if (_binding != null) {
- binding.fragmentArtistContent.shuffleAction.applyColor(color)
- binding.fragmentArtistContent.playAction.applyOutlineColor(color)
- }
- }
-
- override fun onAlbumClick(albumId: Long, view: View) {
- findNavController().navigate(
- R.id.albumDetailsFragment,
- bundleOf(EXTRA_ALBUM_ID to albumId),
- null,
- FragmentNavigatorExtras(
- view to albumId.toString()
- )
- )
- }
-
- override fun onMenuItemSelected(item: MenuItem): Boolean {
- return handleSortOrderMenuItem(item)
- }
-
- private fun handleSortOrderMenuItem(item: MenuItem): Boolean {
- val songs = artist.songs
- when (item.itemId) {
- android.R.id.home -> findNavController().navigateUp()
- R.id.action_play_next -> {
- MusicPlayerRemote.playNext(songs)
- return true
- }
-
- R.id.action_add_to_current_playing -> {
- MusicPlayerRemote.enqueue(songs)
- return true
- }
-
- R.id.action_add_to_playlist -> {
- lifecycleScope.launch(Dispatchers.IO) {
- val playlists = get().fetchPlaylists()
- withContext(Dispatchers.Main) {
- AddToPlaylistDialog.create(playlists, songs)
- .show(childFragmentManager, "ADD_PLAYLIST")
- }
- }
- return true
- }
-
- R.id.action_set_artist_image -> {
- selectImageLauncher.launch(
- PickVisualMediaRequest(ActivityResultContracts.PickVisualMedia.ImageOnly)
- )
- return true
- }
-
- R.id.action_reset_artist_image -> {
- showToast(resources.getString(R.string.updating))
- lifecycleScope.launch {
- CustomArtistImageUtil.getInstance(requireContext())
- .resetCustomArtistImage(artist)
- }
- forceDownload = true
- return true
- }
- }
- return true
- }
-
- private fun setupSongSortButton() {
- binding.fragmentArtistContent.songSortOrder.setOnClickListener {
- PopupMenu(requireContext(), binding.fragmentArtistContent.songSortOrder).apply {
- inflate(R.menu.menu_artist_song_sort_order)
- setUpSortOrderMenu(menu)
- setOnMenuItemClickListener { item ->
- val sortOrder = when (item.itemId) {
- R.id.action_sort_order_title -> SortOrder.ArtistSongSortOrder.SONG_A_Z
- R.id.action_sort_order_title_desc -> SortOrder.ArtistSongSortOrder.SONG_Z_A
- R.id.action_sort_order_album -> SortOrder.ArtistSongSortOrder.SONG_ALBUM
- R.id.action_sort_order_year -> SortOrder.ArtistSongSortOrder.SONG_YEAR
- R.id.action_sort_order_song_duration -> SortOrder.ArtistSongSortOrder.SONG_DURATION
- else -> {
- throw IllegalArgumentException("invalid ${item.title}")
- }
- }
- item.isChecked = true
- setSaveSortOrder(sortOrder)
- return@setOnMenuItemClickListener true
- }
- show()
- }
- }
- }
-
- private fun setSaveSortOrder(sortOrder: String) {
- PreferenceUtil.artistDetailSongSortOrder = sortOrder
- songAdapter.swapDataSet(artist.sortedSongs)
- }
-
- private fun setUpSortOrderMenu(sortOrder: Menu) {
- when (savedSongSortOrder) {
- SortOrder.ArtistSongSortOrder.SONG_A_Z -> sortOrder.findItem(R.id.action_sort_order_title).isChecked =
- true
-
- SortOrder.ArtistSongSortOrder.SONG_Z_A -> sortOrder.findItem(R.id.action_sort_order_title_desc).isChecked =
- true
-
- SortOrder.ArtistSongSortOrder.SONG_ALBUM -> sortOrder.findItem(R.id.action_sort_order_album).isChecked =
- true
-
- SortOrder.ArtistSongSortOrder.SONG_YEAR -> sortOrder.findItem(R.id.action_sort_order_year).isChecked =
- true
-
- SortOrder.ArtistSongSortOrder.SONG_DURATION -> sortOrder.findItem(R.id.action_sort_order_song_duration).isChecked =
- true
-
- else -> {
- throw IllegalArgumentException("invalid $savedSongSortOrder")
- }
- }
- }
-
- private val selectImageLauncher =
- registerForActivityResult(ActivityResultContracts.PickVisualMedia()) { uri ->
- lifecycleScope.launch {
- if (uri != null) {
- CustomArtistImageUtil.getInstance(requireContext())
- .setCustomArtistImage(artist, uri)
- }
- }
- }
-
- override fun onCreateMenu(menu: Menu, inflater: MenuInflater) {
- inflater.inflate(R.menu.menu_artist_detail, menu)
- }
-
- override fun onDestroyView() {
- super.onDestroyView()
- _binding = null
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/AlbumArtistDetailsFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/artists/AlbumArtistDetailsFragment.kt
deleted file mode 100644
index 3480ac15e..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/AlbumArtistDetailsFragment.kt
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.artists
-
-import androidx.navigation.fragment.navArgs
-import org.koin.androidx.viewmodel.ext.android.viewModel
-import org.koin.core.parameter.parametersOf
-
-class AlbumArtistDetailsFragment : AbsArtistDetailsFragment() {
-
- private val arguments by navArgs()
-
- override val detailsViewModel: ArtistDetailsViewModel by viewModel {
- parametersOf(null, arguments.extraArtistName)
- }
- override val artistId: Long?
- get() = null
- override val artistName: String
- get() = arguments.extraArtistName
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistDetailsFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistDetailsFragment.kt
deleted file mode 100644
index 6e556a24e..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistDetailsFragment.kt
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.artists
-
-import androidx.navigation.fragment.navArgs
-import org.koin.androidx.viewmodel.ext.android.viewModel
-import org.koin.core.parameter.parametersOf
-
-class ArtistDetailsFragment : AbsArtistDetailsFragment() {
- private val arguments by navArgs()
- override val detailsViewModel: ArtistDetailsViewModel by viewModel {
- parametersOf(arguments.extraArtistId, null)
- }
- override val artistId: Long
- get() = arguments.extraArtistId
- override val artistName: String?
- get() = null
-
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistDetailsViewModel.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistDetailsViewModel.kt
deleted file mode 100644
index b89aa88df..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistDetailsViewModel.kt
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.artists
-
-import androidx.lifecycle.*
-import code.name.monkey.retromusic.interfaces.IMusicServiceEventListener
-import code.name.monkey.retromusic.model.Artist
-import code.name.monkey.retromusic.repository.RealRepository
-import kotlinx.coroutines.Dispatchers.IO
-import kotlinx.coroutines.launch
-
-class ArtistDetailsViewModel(
- private val realRepository: RealRepository,
- private val artistId: Long?,
- private val artistName: String?
-) : ViewModel(), IMusicServiceEventListener {
- private val artistDetails = MutableLiveData()
-
- init {
- fetchArtist()
- }
-
- private fun fetchArtist() {
- viewModelScope.launch(IO) {
- artistId?.let { artistDetails.postValue(realRepository.artistById(it)) }
-
- artistName?.let { artistDetails.postValue(realRepository.albumArtistByName(it)) }
- }
- }
-
- fun getArtist(): LiveData = artistDetails
-
- override fun onMediaStoreChanged() {
- fetchArtist()
- }
-
- override fun onServiceConnected() {}
- override fun onServiceDisconnected() {}
- override fun onQueueChanged() {}
- override fun onPlayingMetaChanged() {}
- override fun onPlayStateChanged() {}
- override fun onRepeatModeChanged() {}
- override fun onShuffleModeChanged() {}
- override fun onFavoriteStateChanged() {}
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistsFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistsFragment.kt
deleted file mode 100644
index 81d0f35f5..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/artists/ArtistsFragment.kt
+++ /dev/null
@@ -1,335 +0,0 @@
-/*
- * Copyright (c) 2020 Hemanth Savarla.
- *
- * Licensed under the GNU General Public License v3
- *
- * This is free software: you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
- *
- * This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
- * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public License for more details.
- *
- */
-package code.name.monkey.retromusic.fragments.artists
-
-import android.os.Bundle
-import android.view.*
-import androidx.core.os.bundleOf
-import androidx.navigation.fragment.FragmentNavigatorExtras
-import androidx.navigation.fragment.findNavController
-import androidx.recyclerview.widget.GridLayoutManager
-import code.name.monkey.retromusic.EXTRA_ARTIST_ID
-import code.name.monkey.retromusic.EXTRA_ARTIST_NAME
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.adapter.artist.ArtistAdapter
-import code.name.monkey.retromusic.fragments.GridStyle
-import code.name.monkey.retromusic.fragments.ReloadType
-import code.name.monkey.retromusic.fragments.base.AbsRecyclerViewCustomGridSizeFragment
-import code.name.monkey.retromusic.helper.MusicPlayerRemote
-import code.name.monkey.retromusic.helper.SortOrder.ArtistSortOrder
-import code.name.monkey.retromusic.interfaces.IAlbumArtistClickListener
-import code.name.monkey.retromusic.interfaces.IArtistClickListener
-import code.name.monkey.retromusic.service.MusicService
-import code.name.monkey.retromusic.util.PreferenceUtil
-import code.name.monkey.retromusic.util.RetroUtil
-
-class ArtistsFragment : AbsRecyclerViewCustomGridSizeFragment(),
- IArtistClickListener, IAlbumArtistClickListener {
- override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
- super.onViewCreated(view, savedInstanceState)
- libraryViewModel.getArtists().observe(viewLifecycleOwner) {
- if (it.isNotEmpty())
- adapter?.swapDataSet(it)
- else
- adapter?.swapDataSet(listOf())
- }
- }
-
- override val titleRes: Int
- get() = R.string.artists
-
- override val emptyMessage: Int
- get() = R.string.no_artists
-
- override val isShuffleVisible: Boolean
- get() = true
-
- override fun onShuffleClicked() {
- libraryViewModel.getArtists().value?.let {
- MusicPlayerRemote.setShuffleMode(MusicService.SHUFFLE_MODE_NONE)
- MusicPlayerRemote.openQueue(
- queue = it.shuffled().flatMap { artist -> artist.songs },
- startPosition = 0,
- startPlaying = true
- )
- }
- }
-
- override fun setSortOrder(sortOrder: String) {
- libraryViewModel.forceReload(ReloadType.Artists)
- }
-
- override fun createLayoutManager(): GridLayoutManager {
- return GridLayoutManager(requireActivity(), getGridSize())
- }
-
- override fun createAdapter(): ArtistAdapter {
- val dataSet = if (adapter == null) ArrayList() else adapter!!.dataSet
- return ArtistAdapter(
- requireActivity(),
- dataSet,
- itemLayoutRes(),
- this,
- this
- )
- }
-
- override fun loadGridSize(): Int {
- return PreferenceUtil.artistGridSize
- }
-
- override fun saveGridSize(gridColumns: Int) {
- PreferenceUtil.artistGridSize = gridColumns
- }
-
- override fun loadGridSizeLand(): Int {
- return PreferenceUtil.artistGridSizeLand
- }
-
- override fun saveGridSizeLand(gridColumns: Int) {
- PreferenceUtil.artistGridSizeLand = gridColumns
- }
-
- override fun setGridSize(gridSize: Int) {
- layoutManager?.spanCount = gridSize
- adapter?.notifyDataSetChanged()
- }
-
- override fun loadSortOrder(): String {
- return PreferenceUtil.artistSortOrder
- }
-
- override fun saveSortOrder(sortOrder: String) {
- PreferenceUtil.artistSortOrder = sortOrder
- }
-
- override fun loadLayoutRes(): Int {
- return PreferenceUtil.artistGridStyle.layoutResId
- }
-
- override fun saveLayoutRes(layoutRes: Int) {
- PreferenceUtil.artistGridStyle = GridStyle.values().first { gridStyle ->
- gridStyle.layoutResId == layoutRes
- }
- }
-
- companion object {
-
- fun newInstance(): ArtistsFragment {
- return ArtistsFragment()
- }
- }
-
- override fun onArtist(artistId: Long, view: View) {
- findNavController().navigate(
- R.id.artistDetailsFragment,
- bundleOf(EXTRA_ARTIST_ID to artistId),
- null,
- FragmentNavigatorExtras(view to artistId.toString())
- )
- reenterTransition = null
- }
-
- override fun onAlbumArtist(artistName: String, view: View) {
- findNavController().navigate(
- R.id.albumArtistDetailsFragment,
- bundleOf(EXTRA_ARTIST_NAME to artistName),
- null,
- FragmentNavigatorExtras(view to artistName)
- )
- reenterTransition = null
- }
-
- override fun onCreateMenu(menu: Menu, inflater: MenuInflater) {
- super.onCreateMenu(menu, inflater)
- val gridSizeItem: MenuItem = menu.findItem(R.id.action_grid_size)
- if (RetroUtil.isLandscape) {
- gridSizeItem.setTitle(R.string.action_grid_size_land)
- }
- setUpGridSizeMenu(gridSizeItem.subMenu!!)
- val layoutItem = menu.findItem(R.id.action_layout_type)
- setupLayoutMenu(layoutItem.subMenu!!)
- setUpSortOrderMenu(menu.findItem(R.id.action_sort_order).subMenu!!)
- setupAlbumArtistMenu(menu)
- }
-
- private fun setupAlbumArtistMenu(menu: Menu) {
- menu.add(0, R.id.action_album_artist, 0, R.string.show_album_artists).apply {
- isCheckable = true
- isChecked = PreferenceUtil.albumArtistsOnly
- }
- }
-
- private fun setUpSortOrderMenu(
- sortOrderMenu: SubMenu
- ) {
- val currentSortOrder: String? = getSortOrder()
- sortOrderMenu.clear()
- sortOrderMenu.add(
- 0,
- R.id.action_artist_sort_order_asc,
- 0,
- R.string.sort_order_a_z
- ).isChecked = currentSortOrder.equals(ArtistSortOrder.ARTIST_A_Z)
- sortOrderMenu.add(
- 0,
- R.id.action_artist_sort_order_desc,
- 1,
- R.string.sort_order_z_a
- ).isChecked = currentSortOrder.equals(ArtistSortOrder.ARTIST_Z_A)
- sortOrderMenu.setGroupCheckable(0, true, true)
- }
-
- private fun setupLayoutMenu(
- subMenu: SubMenu
- ) {
- when (itemLayoutRes()) {
- R.layout.item_card -> subMenu.findItem(R.id.action_layout_card).isChecked = true
- R.layout.item_grid -> subMenu.findItem(R.id.action_layout_normal).isChecked = true
- R.layout.item_card_color -> subMenu.findItem(R.id.action_layout_colored_card).isChecked =
- true
- R.layout.item_grid_circle -> subMenu.findItem(R.id.action_layout_circular).isChecked =
- true
- R.layout.image -> subMenu.findItem(R.id.action_layout_image).isChecked = true
- R.layout.item_image_gradient -> subMenu.findItem(R.id.action_layout_gradient_image).isChecked =
- true
- }
- }
-
- private fun setUpGridSizeMenu(
- gridSizeMenu: SubMenu
- ) {
- when (getGridSize()) {
- 1 -> gridSizeMenu.findItem(R.id.action_grid_size_1).isChecked =
- true
- 2 -> gridSizeMenu.findItem(R.id.action_grid_size_2).isChecked = true
- 3 -> gridSizeMenu.findItem(R.id.action_grid_size_3).isChecked = true
- 4 -> gridSizeMenu.findItem(R.id.action_grid_size_4).isChecked = true
- 5 -> gridSizeMenu.findItem(R.id.action_grid_size_5).isChecked = true
- 6 -> gridSizeMenu.findItem(R.id.action_grid_size_6).isChecked = true
- 7 -> gridSizeMenu.findItem(R.id.action_grid_size_7).isChecked = true
- 8 -> gridSizeMenu.findItem(R.id.action_grid_size_8).isChecked = true
- }
- val gridSize: Int = maxGridSize
- if (gridSize < 8) {
- gridSizeMenu.findItem(R.id.action_grid_size_8).isVisible = false
- }
- if (gridSize < 7) {
- gridSizeMenu.findItem(R.id.action_grid_size_7).isVisible = false
- }
- if (gridSize < 6) {
- gridSizeMenu.findItem(R.id.action_grid_size_6).isVisible = false
- }
- if (gridSize < 5) {
- gridSizeMenu.findItem(R.id.action_grid_size_5).isVisible = false
- }
- if (gridSize < 4) {
- gridSizeMenu.findItem(R.id.action_grid_size_4).isVisible = false
- }
- if (gridSize < 3) {
- gridSizeMenu.findItem(R.id.action_grid_size_3).isVisible = false
- }
- }
-
- override fun onMenuItemSelected(item: MenuItem): Boolean {
- if (handleGridSizeMenuItem(item)) {
- return true
- }
- if (handleLayoutResType(item)) {
- return true
- }
- if (handleSortOrderMenuItem(item)) {
- return true
- }
- if (handleAlbumArtistMenu(item)) {
- return true
- }
- return super.onMenuItemSelected(item)
- }
-
- private fun handleAlbumArtistMenu(item: MenuItem): Boolean {
- return if (item.itemId == R.id.action_album_artist) {
- PreferenceUtil.albumArtistsOnly = !item.isChecked
- item.isChecked = !item.isChecked
- libraryViewModel.forceReload(ReloadType.Artists)
- true
- } else {
- false
- }
- }
-
- private fun handleSortOrderMenuItem(
- item: MenuItem
- ): Boolean {
- val sortOrder: String = when (item.itemId) {
- R.id.action_artist_sort_order_asc -> ArtistSortOrder.ARTIST_A_Z
- R.id.action_artist_sort_order_desc -> ArtistSortOrder.ARTIST_Z_A
- else -> PreferenceUtil.artistSortOrder
- }
- if (sortOrder != PreferenceUtil.artistSortOrder) {
- item.isChecked = true
- setAndSaveSortOrder(sortOrder)
- return true
- }
- return false
- }
-
- private fun handleLayoutResType(
- item: MenuItem
- ): Boolean {
- val layoutRes = when (item.itemId) {
- R.id.action_layout_normal -> R.layout.item_grid
- R.id.action_layout_card -> R.layout.item_card
- R.id.action_layout_colored_card -> R.layout.item_card_color
- R.id.action_layout_circular -> R.layout.item_grid_circle
- R.id.action_layout_image -> R.layout.image
- R.id.action_layout_gradient_image -> R.layout.item_image_gradient
- else -> PreferenceUtil.artistGridStyle.layoutResId
- }
- if (layoutRes != PreferenceUtil.artistGridStyle.layoutResId) {
- item.isChecked = true
- setAndSaveLayoutRes(layoutRes)
- return true
- }
- return false
- }
-
- private fun handleGridSizeMenuItem(
- item: MenuItem
- ): Boolean {
- val gridSize = when (item.itemId) {
- R.id.action_grid_size_1 -> 1
- R.id.action_grid_size_2 -> 2
- R.id.action_grid_size_3 -> 3
- R.id.action_grid_size_4 -> 4
- R.id.action_grid_size_5 -> 5
- R.id.action_grid_size_6 -> 6
- R.id.action_grid_size_7 -> 7
- R.id.action_grid_size_8 -> 8
- else -> 0
- }
- if (gridSize > 0) {
- item.isChecked = true
- setAndSaveGridSize(gridSize)
- return true
- }
- return false
- }
-
- override fun onResume() {
- super.onResume()
- libraryViewModel.forceReload(ReloadType.Artists)
- }
-}
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/backup/BackupFragment.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/backup/BackupFragment.kt
deleted file mode 100644
index bb4a57ecb..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/backup/BackupFragment.kt
+++ /dev/null
@@ -1,162 +0,0 @@
-package code.name.monkey.retromusic.fragments.backup
-
-import android.annotation.SuppressLint
-import android.content.Intent
-import android.os.Bundle
-import android.view.MenuItem
-import android.view.View
-import androidx.activity.result.contract.ActivityResultContracts
-import androidx.core.net.toUri
-import androidx.core.view.isVisible
-import androidx.fragment.app.Fragment
-import androidx.fragment.app.viewModels
-import androidx.lifecycle.lifecycleScope
-import androidx.recyclerview.widget.LinearLayoutManager
-import androidx.recyclerview.widget.RecyclerView
-import code.name.monkey.retromusic.R
-import code.name.monkey.retromusic.adapter.backup.BackupAdapter
-import code.name.monkey.retromusic.databinding.FragmentBackupBinding
-import code.name.monkey.retromusic.extensions.accentColor
-import code.name.monkey.retromusic.extensions.accentOutlineColor
-import code.name.monkey.retromusic.extensions.materialDialog
-import code.name.monkey.retromusic.extensions.showToast
-import code.name.monkey.retromusic.helper.BackupHelper
-import code.name.monkey.retromusic.helper.sanitize
-import code.name.monkey.retromusic.util.Share
-import com.afollestad.materialdialogs.input.input
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.launch
-import java.io.File
-
-class BackupFragment : Fragment(R.layout.fragment_backup), BackupAdapter.BackupClickedListener {
-
- private val backupViewModel by viewModels()
- private var backupAdapter: BackupAdapter? = null
-
- private var _binding: FragmentBackupBinding? = null
- private val binding get() = _binding!!
-
- override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
- super.onViewCreated(view, savedInstanceState)
- _binding = FragmentBackupBinding.bind(view)
- initAdapter()
- setupRecyclerview()
- backupViewModel.backupsLiveData.observe(viewLifecycleOwner) {
- if (it.isNotEmpty())
- backupAdapter?.swapDataset(it)
- else
- backupAdapter?.swapDataset(listOf())
- }
- backupViewModel.loadBackups()
- val openFilePicker = registerForActivityResult(ActivityResultContracts.OpenDocument()) {
- lifecycleScope.launch(Dispatchers.IO) {
- it?.let {
- startActivity(Intent(context, RestoreActivity::class.java).apply {
- data = it
- })
- }
- }
- }
- binding.createBackup.accentOutlineColor()
- binding.restoreBackup.accentColor()
- binding.createBackup.setOnClickListener {
- showCreateBackupDialog()
- }
- binding.restoreBackup.setOnClickListener {
- openFilePicker.launch(arrayOf("application/octet-stream"))
- }
- }
-
- private fun initAdapter() {
- backupAdapter = BackupAdapter(requireActivity(), ArrayList(), this)
- backupAdapter?.registerAdapterDataObserver(object : RecyclerView.AdapterDataObserver() {
- override fun onChanged() {
- super.onChanged()
- checkIsEmpty()
- }
- })
- }
-
- private fun checkIsEmpty() {
- val isEmpty = backupAdapter?.itemCount == 0
- binding.backupTitle.isVisible = !isEmpty
- binding.backupRecyclerview.isVisible = !isEmpty
- }
-
- fun setupRecyclerview() {
- binding.backupRecyclerview.apply {
- layoutManager = LinearLayoutManager(context)
- adapter = backupAdapter
- }
- }
-
- @SuppressLint("CheckResult")
- private fun showCreateBackupDialog() {
- materialDialog().show {
- title(res = R.string.action_rename)
- input(prefill = BackupHelper.getTimeStamp()) { _, text ->
- // Text submitted with the action button
- lifecycleScope.launch {
- BackupHelper.createBackup(requireContext(), text.sanitize())
- backupViewModel.loadBackups()
- }
- }
- positiveButton(android.R.string.ok)
- negativeButton(R.string.action_cancel)
- setTitle(R.string.title_new_backup)
- }
- }
-
- override fun onBackupClicked(file: File) {
- lifecycleScope.launch {
- startActivity(Intent(context, RestoreActivity::class.java).apply {
- data = file.toUri()
- })
- }
- }
-
- @SuppressLint("CheckResult")
- override fun onBackupMenuClicked(file: File, menuItem: MenuItem): Boolean {
- when (menuItem.itemId) {
- R.id.action_delete -> {
- try {
- file.delete()
- } catch (exception: SecurityException) {
- showToast(R.string.error_delete_backup)
- }
- backupViewModel.loadBackups()
- return true
- }
- R.id.action_share -> {
- Share.shareFile(requireContext(), file, "*/*")
- return true
- }
- R.id.action_rename -> {
- materialDialog().show {
- title(res = R.string.action_rename)
- input(prefill = file.nameWithoutExtension) { _, text ->
- // Text submitted with the action button
- val renamedFile =
- File(file.parent, "$text${BackupHelper.APPEND_EXTENSION}")
- if (!renamedFile.exists()) {
- file.renameTo(renamedFile)
- backupViewModel.loadBackups()
- } else {
- showToast(R.string.file_already_exists)
- }
- }
- positiveButton(android.R.string.ok)
- negativeButton(R.string.action_cancel)
- setTitle(R.string.action_rename)
- }
- return true
- }
- }
- return false
- }
-
- override fun onDestroyView() {
- super.onDestroyView()
- _binding = null
- }
-}
\ No newline at end of file
diff --git a/app/src/main/java/code/name/monkey/retromusic/fragments/backup/BackupViewModel.kt b/app/src/main/java/code/name/monkey/retromusic/fragments/backup/BackupViewModel.kt
deleted file mode 100644
index f3b67abec..000000000
--- a/app/src/main/java/code/name/monkey/retromusic/fragments/backup/BackupViewModel.kt
+++ /dev/null
@@ -1,44 +0,0 @@
-package code.name.monkey.retromusic.fragments.backup
-
-import android.app.Activity
-import android.content.Intent
-import androidx.lifecycle.LiveData
-import androidx.lifecycle.MutableLiveData
-import androidx.lifecycle.ViewModel
-import code.name.monkey.retromusic.activities.MainActivity
-import code.name.monkey.retromusic.helper.BackupContent
-import code.name.monkey.retromusic.helper.BackupHelper
-import kotlinx.coroutines.Dispatchers
-import kotlinx.coroutines.withContext
-import java.io.File
-import java.io.InputStream
-import kotlin.system.exitProcess
-
-
-class BackupViewModel : ViewModel() {
- private val backupsMutableLiveData = MutableLiveData