@@ -18,72 +18,14 @@ import kotlinx.coroutines.withContext
18
18
class OnWithFiltersQuery : ViewModel () {
19
19
20
20
// Main parameters
21
- private val channelError = " on_audio_error "
21
+ private var projection : Array < String > ? = arrayOf()
22
22
private lateinit var resolver: ContentResolver
23
23
@SuppressLint(" StaticFieldLeak" )
24
24
private lateinit var context: Context
25
25
private lateinit var resultWithFiltersList: ArrayList <MutableMap <String , Any >>
26
26
private lateinit var withType: Uri
27
27
private lateinit var args: String
28
- private lateinit var argsKey: String
29
-
30
- // Uri projection
31
- private val withTypeProjection = arrayOf(
32
- MediaStore .Audio .Media .EXTERNAL_CONTENT_URI ,
33
- MediaStore .Audio .Albums .EXTERNAL_CONTENT_URI ,
34
- MediaStore .Audio .Playlists .EXTERNAL_CONTENT_URI ,
35
- MediaStore .Audio .Artists .EXTERNAL_CONTENT_URI ,
36
- MediaStore .Audio .Genres .EXTERNAL_CONTENT_URI
37
- )
38
-
39
- // Query songs projection
40
- @SuppressLint(" InlinedApi" )
41
- private val songProjection = arrayOf(
42
- MediaStore .Audio .Media .DATA , //
43
- MediaStore .Audio .Media .DISPLAY_NAME ,
44
- MediaStore .Audio .Media ._ID ,
45
- MediaStore .Audio .Media .SIZE ,
46
- MediaStore .Audio .Media .ALBUM ,
47
- MediaStore .Audio .Media .ALBUM_ARTIST ,
48
- MediaStore .Audio .Media .ALBUM_ID ,
49
- MediaStore .Audio .Media .ARTIST ,
50
- MediaStore .Audio .Media .ARTIST_ID ,
51
- MediaStore .Audio .Media .BOOKMARK ,
52
- MediaStore .Audio .Media .COMPOSER ,
53
- MediaStore .Audio .Media .DATE_ADDED ,
54
- MediaStore .Audio .Media .DURATION ,
55
- MediaStore .Audio .Media .TITLE ,
56
- MediaStore .Audio .Media .TRACK ,
57
- MediaStore .Audio .Media .YEAR ,
58
- MediaStore .Audio .Media .IS_ALARM ,
59
- MediaStore .Audio .Media .IS_MUSIC , // 17
60
- MediaStore .Audio .Media .IS_NOTIFICATION ,
61
- MediaStore .Audio .Media .IS_PODCAST ,
62
- MediaStore .Audio .Media .IS_RINGTONE
63
- )
64
-
65
- // Query playlists projection
66
- private val playlistProjection = arrayOf(
67
- MediaStore .Audio .Playlists .DATA ,
68
- MediaStore .Audio .Playlists ._ID ,
69
- MediaStore .Audio .Playlists .DATE_ADDED ,
70
- MediaStore .Audio .Playlists .DATE_MODIFIED ,
71
- MediaStore .Audio .Playlists .NAME
72
- )
73
-
74
- // Query artists projection
75
- private val artistProjection = arrayOf(
76
- MediaStore .Audio .Artists ._ID ,
77
- MediaStore .Audio .Artists .ARTIST ,
78
- MediaStore .Audio .Artists .NUMBER_OF_ALBUMS ,
79
- MediaStore .Audio .Artists .NUMBER_OF_TRACKS
80
- )
81
-
82
- // Query genres projection
83
- private val genreProjection = arrayOf(
84
- MediaStore .Audio .Genres ._ID ,
85
- MediaStore .Audio .Genres .NAME
86
- )
28
+ private lateinit var argsKey: String
87
29
88
30
//
89
31
fun queryWithFilters (context : Context , result : MethodChannel .Result , call : MethodCall ) {
@@ -92,97 +34,30 @@ class OnWithFiltersQuery : ViewModel() {
92
34
// Setup Type and Args
93
35
withType = checkWithFiltersType(call.argument<Int >(" withType" )!! )
94
36
args = call.argument<String >(" argsVal" )!! + " %"
37
+ projection = checkProjection(withType)
38
+
39
+ // Setup Args
40
+ argsKey = when (withType) {
41
+ MediaStore .Audio .Media .EXTERNAL_CONTENT_URI -> checkSongsArgs(call.argument<Int >(" args" )!! )
42
+ MediaStore .Audio .Albums .EXTERNAL_CONTENT_URI -> checkAlbumsArgs(call.argument<Int >(" args" )!! )
43
+ MediaStore .Audio .Playlists .EXTERNAL_CONTENT_URI -> checkPlaylistsArgs(call.argument<Int >(" args" )!! )
44
+ MediaStore .Audio .Artists .EXTERNAL_CONTENT_URI -> checkArtistsArgs(call.argument<Int >(" args" )!! )
45
+ MediaStore .Audio .Genres .EXTERNAL_CONTENT_URI -> checkGenresArgs(call.argument<Int >(" args" )!! )
46
+ else -> throw Exception (" [argsKey] returned null. Report this issue on [on_audio_query] GitHub." )
47
+ }
95
48
96
- //
97
- when (withType) {
98
- //
99
- withTypeProjection[0 ] ->
100
- viewModelScope.launch { argsKey = checkSongsArgs(call.argument<Int >(" args" )!! )
101
- resultWithFiltersList = loadSongsWithFilters() ; result.success(resultWithFiltersList) }
102
-
103
- //
104
- withTypeProjection[1 ] ->
105
- viewModelScope.launch { argsKey = checkAlbumsArgs(call.argument<Int >(" args" )!! )
106
- resultWithFiltersList = loadAlbumsWithFilters() ; result.success(resultWithFiltersList) }
107
-
108
- //
109
- withTypeProjection[2 ] ->
110
- viewModelScope.launch { argsKey = checkPlaylistsArgs(call.argument<Int >(" args" )!! )
111
- resultWithFiltersList = loadPlaylistsWithFilters() ; result.success(resultWithFiltersList) }
49
+ // Query everything in the Background it's necessary for better performance
50
+ viewModelScope.launch {
51
+ // Start querying
52
+ resultWithFiltersList = loadSongsWithFilters()
112
53
113
54
//
114
- withTypeProjection[3 ] ->
115
- viewModelScope.launch { argsKey = checkArtistsArgs(call.argument<Int >(" args" )!! )
116
- resultWithFiltersList = loadArtistsWithFilters() ; result.success(resultWithFiltersList) }
117
-
118
- //
119
- withTypeProjection[4 ] ->
120
- viewModelScope.launch { argsKey = checkGenresArgs(call.argument<Int >(" args" )!! )
121
- resultWithFiltersList = loadGenresWithFilters() ; result.success(resultWithFiltersList) }
122
-
123
- //
124
- else -> result.error(channelError, " Filter type in [queryWithFilters] not found" , null )
125
- }
55
+ result.success(resultWithFiltersList) }
126
56
}
127
57
128
58
// Loading in Background
129
59
private suspend fun loadSongsWithFilters () : ArrayList <MutableMap <String , Any >> = withContext(Dispatchers .IO ) {
130
- val cursor = resolver.query(withType, songProjection, argsKey, arrayOf(args), null )
131
- val withFiltersList: ArrayList <MutableMap <String , Any >> = ArrayList ()
132
- while (cursor != null && cursor.moveToNext()) {
133
- val withFiltersData: MutableMap <String , Any > = HashMap ()
134
- for (audioMedia in cursor.columnNames) {
135
- if (cursor.getString(cursor.getColumnIndex(audioMedia)) != null ) {
136
- withFiltersData[audioMedia] = cursor.getString(cursor.getColumnIndex(audioMedia))
137
- } else withFiltersData[audioMedia] = " "
138
- }
139
-
140
- // Artwork
141
- val art = loadArtwork(context, withFiltersData[" album" ].toString())
142
- if (art.isNotEmpty()) withFiltersData[" artwork" ] = art
143
- withFiltersList.add(withFiltersData)
144
- }
145
- cursor?.close()
146
- return @withContext withFiltersList
147
- }
148
-
149
- // Loading in Background
150
- private suspend fun loadAlbumsWithFilters () : ArrayList <MutableMap <String , Any >> = withContext(Dispatchers .IO ) {
151
- val cursor = resolver.query(withType, null , argsKey, arrayOf(args), null )
152
- val withFiltersList: ArrayList <MutableMap <String , Any >> = ArrayList ()
153
- while (cursor != null && cursor.moveToNext()) {
154
- val withFiltersData: MutableMap <String , Any > = HashMap ()
155
- for (audioMedia in cursor.columnNames) {
156
- if (cursor.getString(cursor.getColumnIndex(audioMedia)) != null ) {
157
- withFiltersData[audioMedia] = cursor.getString(cursor.getColumnIndex(audioMedia))
158
- } else withFiltersData[audioMedia] = " "
159
- }
160
- withFiltersList.add(withFiltersData)
161
- }
162
- cursor?.close()
163
- return @withContext withFiltersList
164
- }
165
-
166
- // Loading in Background
167
- private suspend fun loadArtistsWithFilters () : ArrayList <MutableMap <String , Any >> = withContext(Dispatchers .IO ) {
168
- val cursor = resolver.query(withType, artistProjection, argsKey, arrayOf(args), null )
169
- val withFiltersList: ArrayList <MutableMap <String , Any >> = ArrayList ()
170
- while (cursor != null && cursor.moveToNext()) {
171
- val withFiltersData: MutableMap <String , Any > = HashMap ()
172
- for (audioMedia in cursor.columnNames) {
173
- if (cursor.getString(cursor.getColumnIndex(audioMedia)) != null ) {
174
- withFiltersData[audioMedia] = cursor.getString(cursor.getColumnIndex(audioMedia))
175
- } else withFiltersData[audioMedia] = " "
176
- }
177
- withFiltersList.add(withFiltersData)
178
- }
179
- cursor?.close()
180
- return @withContext withFiltersList
181
- }
182
-
183
- // Loading in Background
184
- private suspend fun loadPlaylistsWithFilters () : ArrayList <MutableMap <String , Any >> = withContext(Dispatchers .IO ) {
185
- val cursor = resolver.query(withType, playlistProjection, argsKey, arrayOf(args), null )
60
+ val cursor = resolver.query(withType, projection, argsKey, arrayOf(args), null )
186
61
val withFiltersList: ArrayList <MutableMap <String , Any >> = ArrayList ()
187
62
while (cursor != null && cursor.moveToNext()) {
188
63
val withFiltersData: MutableMap <String , Any > = HashMap ()
@@ -191,24 +66,13 @@ class OnWithFiltersQuery : ViewModel() {
191
66
withFiltersData[audioMedia] = cursor.getString(cursor.getColumnIndex(audioMedia))
192
67
} else withFiltersData[audioMedia] = " "
193
68
}
194
- withFiltersList.add(withFiltersData)
195
- }
196
- cursor?.close()
197
- return @withContext withFiltersList
198
- }
199
69
200
- // Loading in Background
201
- private suspend fun loadGenresWithFilters () : ArrayList <MutableMap <String , Any >> = withContext(Dispatchers .IO ) {
202
- val cursor = resolver.query(withType, genreProjection, argsKey, arrayOf(args), null )
203
- val withFiltersList: ArrayList <MutableMap <String , Any >> = ArrayList ()
204
- while (cursor != null && cursor.moveToNext()) {
205
- val withFiltersData: MutableMap <String , Any > = HashMap ()
206
- for (audioMedia in cursor.columnNames) {
207
- if (cursor.getString(cursor.getColumnIndex(audioMedia)) != null ) {
208
- withFiltersData[audioMedia] = cursor.getString(cursor.getColumnIndex(audioMedia))
209
- } else withFiltersData[audioMedia] = " "
210
- }
211
- withFiltersList.add(withFiltersData)
70
+ if (withType == MediaStore .Audio .Media .EXTERNAL_CONTENT_URI ) {
71
+ // Artwork
72
+ val art = loadArtwork(context, withFiltersData[" album" ].toString())
73
+ if (art.isNotEmpty()) withFiltersData[" artwork" ] = art
74
+ withFiltersList.add(withFiltersData)
75
+ } else withFiltersList.add(withFiltersData)
212
76
}
213
77
cursor?.close()
214
78
return @withContext withFiltersList
0 commit comments