@@ -31,6 +31,7 @@ import com.owncloud.android.datamodel.FileDataStorageManager
3131import com.owncloud.android.datamodel.GalleryItems
3232import com.owncloud.android.datamodel.GalleryRow
3333import com.owncloud.android.datamodel.OCFile
34+ import com.owncloud.android.lib.common.utils.Log_OC
3435import com.owncloud.android.ui.activity.ComponentsGetter
3536import com.owncloud.android.ui.fragment.GalleryFragment
3637import com.owncloud.android.ui.fragment.GalleryFragmentBottomSheetDialog
@@ -57,7 +58,24 @@ class GalleryAdapter(
5758) : SectionedRecyclerViewAdapter<SectionedViewHolder>(),
5859 CommonOCFileListAdapterInterface ,
5960 PopupTextProvider {
60- var files: List <GalleryItems > = mutableListOf ()
61+
62+ companion object {
63+ private const val TAG = " GalleryAdapter"
64+ }
65+
66+ // fileId -> (section, row)
67+ private val filePositionMap = mutableMapOf<Long , Pair <Int , Int >>()
68+ private var cachedAllFiles: List <OCFile >? = null
69+ private var cachedFilesCount: Int = 0
70+
71+ private var _files : List <GalleryItems > = mutableListOf ()
72+ var files: List <GalleryItems >
73+ get() = _files
74+ private set(value) {
75+ _files = value
76+ invalidateCaches()
77+ }
78+
6179 private val ocFileListDelegate: OCFileListDelegate
6280 private var storageManager: FileDataStorageManager = transferServiceGetter.storageManager
6381
@@ -78,6 +96,28 @@ class GalleryAdapter(
7896 )
7997 }
8098
99+ private fun invalidateCaches () {
100+ Log_OC .d(TAG , " invalidating caches" )
101+ cachedAllFiles = null
102+ updateFilesCount()
103+ rebuildFilePositionMap()
104+ }
105+
106+ private fun updateFilesCount () {
107+ cachedFilesCount = files.sumOf { it.rows.size }
108+ }
109+
110+ private fun rebuildFilePositionMap () {
111+ filePositionMap.clear()
112+ files.forEachIndexed { sectionIndex, galleryItem ->
113+ galleryItem.rows.forEachIndexed { rowIndex, row ->
114+ row.files.forEach { file ->
115+ filePositionMap[file.fileId] = sectionIndex to rowIndex
116+ }
117+ }
118+ }
119+ }
120+
81121 override fun getItemId (section : Int , position : Int ): Long = files[section].rows[position].calculateHashCode()
82122
83123 override fun selectAll (value : Boolean ) {
@@ -150,6 +190,7 @@ class GalleryAdapter(
150190 }
151191 }
152192
193+ @SuppressLint(" NotifyDataSetChanged" )
153194 fun showAllGalleryItems (
154195 remotePath : String ,
155196 mediaState : GalleryFragmentBottomSheetDialog .MediaState ,
@@ -195,11 +236,14 @@ class GalleryAdapter(
195236 }
196237 }
197238
198- private fun transformToRows (list : List <OCFile >): List <GalleryRow > = list
199- .sortedBy { it.modificationTimestamp }
200- .reversed()
201- .chunked(columns)
202- .map { entry -> GalleryRow (entry, defaultThumbnailSize, defaultThumbnailSize) }
239+ private fun transformToRows (list : List <OCFile >): List <GalleryRow > {
240+ if (list.isEmpty()) return emptyList()
241+
242+ return list
243+ .sortedByDescending { it.modificationTimestamp }
244+ .chunked(columns)
245+ .map { chunk -> GalleryRow (chunk, defaultThumbnailSize, defaultThumbnailSize) }
246+ }
203247
204248 @SuppressLint(" NotifyDataSetChanged" )
205249 fun clear () {
@@ -240,16 +284,8 @@ class GalleryAdapter(
240284 }
241285
242286 override fun getItemPosition (file : OCFile ): Int {
243- val findResult = files
244- .asSequence()
245- .flatMapIndexed { itemIndex, item ->
246- item.rows.withIndex().map { row -> Triple (itemIndex, row.index, row.value) }
247- }.find {
248- it.third.files.contains(file)
249- }
250-
251- val (item, row) = findResult ? : Triple (0 , 0 , null )
252- return getAbsolutePosition(item, row)
287+ val (section, row) = filePositionMap[file.fileId] ? : return - 1
288+ return getAbsolutePosition(section, row)
253289 }
254290
255291 override fun addCheckedFile (file : OCFile ) {
@@ -268,17 +304,15 @@ class GalleryAdapter(
268304 notifyItemChanged(getItemPosition(file))
269305 }
270306
271- override fun getFilesCount (): Int = files.fold( 0 ) { acc, item -> acc + item.rows.size }
307+ override fun getFilesCount (): Int = cachedFilesCount
272308
273309 override fun setMultiSelect (boolean : Boolean ) {
274310 ocFileListDelegate.isMultiSelect = boolean
275311 }
276312
277- private fun getAllFiles (): List <OCFile > = files.flatMap { galleryItem ->
278- galleryItem.rows.flatMap { row ->
279- row.files
280- }
281- }
313+ private fun getAllFiles (): List <OCFile > = cachedAllFiles ? : files.flatMap { galleryItem ->
314+ galleryItem.rows.flatMap { row -> row.files }
315+ }.also { cachedAllFiles = it }
282316
283317 private fun addAllFilesToCheckedFiles () {
284318 val allFiles = getAllFiles()
@@ -309,6 +343,16 @@ class GalleryAdapter(
309343 }
310344 }
311345
346+ private fun List<OCFile>.toGalleryItems (): List <GalleryItems > {
347+ if (isEmpty()) return emptyList()
348+
349+ return groupBy { firstOfMonth(it.modificationTimestamp) }
350+ .map { (date, filesList) ->
351+ GalleryItems (date, transformToRows(filesList))
352+ }
353+ .sortedByDescending { it.date }
354+ }
355+
312356 override fun onBindFooterViewHolder (holder : SectionedViewHolder ? , section : Int ) = Unit
313357
314358 override fun swapDirectory (
@@ -322,9 +366,4 @@ class GalleryAdapter(
322366 override fun setHighlightedItem (file : OCFile ) = Unit
323367
324368 override fun setSortOrder (mFile : OCFile , sortOrder : FileSortOrder ) = Unit
325-
326- private fun List<OCFile>.toGalleryItems (): List <GalleryItems > = this
327- .groupBy { firstOfMonth(it.modificationTimestamp) }
328- .map { GalleryItems (it.key, transformToRows(it.value)) }
329- .sortedBy { it.date }.reversed()
330369}
0 commit comments