/* * 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.dialogs import android.Manifest import android.app.Dialog import android.content.pm.PackageManager import android.os.Build import android.os.Bundle import android.os.Environment import androidx.core.app.ActivityCompat import androidx.fragment.app.DialogFragment import code.name.monkey.retromusic.R import code.name.monkey.retromusic.util.PreferenceUtil import com.afollestad.materialdialogs.LayoutMode import com.afollestad.materialdialogs.MaterialDialog import com.afollestad.materialdialogs.bottomsheets.BottomSheet import com.afollestad.materialdialogs.list.listItems import java.io.File import java.util.* import kotlin.collections.ArrayList class BlacklistFolderChooserDialog : DialogFragment() { private val initialPath = Environment.getExternalStorageDirectory().absolutePath private var parentFolder: File? = null private var parentContents: Array? = null private var canGoUp = false private var callback: FolderCallback? = null private fun contentsArray(): List { if (parentContents == null) { return if (canGoUp) { return listOf("..") } else listOf() } 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!![i].name } val data = ArrayList() for (i in results) { data.add(i!!) } return data } private fun listFiles(): Array? { val contents = parentFolder!!.listFiles() val results = ArrayList() if (contents != null) { for (fi in contents) { if (fi.isDirectory) { results.add(fi) } } Collections.sort(results, FolderSorter()) return results.toTypedArray() } return null } override fun onCreateDialog(savedInstanceState: Bundle?): Dialog { var savedInstanceStateFinal = savedInstanceState if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && ActivityCompat.checkSelfPermission(requireActivity(), Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) { return MaterialDialog(requireActivity(), BottomSheet(LayoutMode.WRAP_CONTENT)).show { title(R.string.md_error_label) cornerRadius(PreferenceUtil.getInstance(requireContext()).dialogCorner) message(R.string.md_storage_perm_error) positiveButton(android.R.string.ok) } } if (savedInstanceStateFinal == null) { savedInstanceStateFinal = Bundle() } if (!savedInstanceStateFinal.containsKey("current_path")) { savedInstanceStateFinal.putString("current_path", initialPath) } parentFolder = File(savedInstanceStateFinal.getString("current_path", File.pathSeparator)) checkIfCanGoUp() parentContents = listFiles() return MaterialDialog(requireContext(), BottomSheet(LayoutMode.WRAP_CONTENT)).show { title(text = parentFolder!!.absolutePath) cornerRadius(PreferenceUtil.getInstance(requireContext()).dialogCorner) listItems(items = contentsArray(), waitForPositiveButton = false) { _, index, _ -> onSelection(index) } noAutoDismiss() positiveButton(R.string.add_action) { dismiss() callback!!.onFolderSelection(this@BlacklistFolderChooserDialog, parentFolder!!) } negativeButton(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!![if (canGoUp) i - 1 else i] canGoUp = true if (parentFolder!!.absolutePath == "/storage/emulated") { parentFolder = Environment.getExternalStorageDirectory() } } reload() } private fun checkIfCanGoUp() { canGoUp = parentFolder!!.parent != null } private fun reload() { parentContents = listFiles() val dialog = dialog as MaterialDialog? dialog?.apply { cornerRadius(PreferenceUtil.getInstance(requireContext()).dialogCorner) setTitle(parentFolder!!.absolutePath) listItems(items = contentsArray()) { _, index, _ -> onSelection(index) } } } 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(dialog: BlacklistFolderChooserDialog, folder: File) } private class FolderSorter : Comparator { override fun compare(lhs: File, rhs: File): Int { return lhs.name.compareTo(rhs.name) } } companion object { fun create(): BlacklistFolderChooserDialog { return BlacklistFolderChooserDialog() } } }