From ed6e20c3ed7dd7c855e1366d1998fdd6ced89593 Mon Sep 17 00:00:00 2001 From: tom79 Date: Wed, 3 Jul 2019 16:50:35 +0200 Subject: [PATCH] Allow to select folder for storing media --- app/build.gradle | 2 +- .../android/filelister/FileListerAdapter.java | 336 ++++++++++++++++++ .../android/filelister/FileListerDialog.java | 185 ++++++++++ .../android/filelister/FilesListerView.java | 72 ++++ .../filelister/OnFileSelectedListener.java | 11 + .../fragments/ContentSettingsFragment.java | 26 +- .../ic_audiotrack_black_48dp.png | Bin 0 -> 309 bytes .../ic_create_new_folder_black_48dp.png | Bin 0 -> 254 bytes .../drawable-hdpi/ic_folder_black_48dp.png | Bin 0 -> 239 bytes .../ic_insert_drive_file_black_48dp.png | Bin 0 -> 273 bytes .../res/drawable-hdpi/ic_photo_black_48dp.png | Bin 0 -> 424 bytes .../ic_subdirectory_arrow_left_black_48dp.png | Bin 0 -> 236 bytes .../drawable-hdpi/ic_videocam_black_48dp.png | Bin 0 -> 224 bytes .../ic_audiotrack_black_48dp.png | Bin 0 -> 226 bytes .../ic_create_new_folder_black_48dp.png | Bin 0 -> 191 bytes .../drawable-mdpi/ic_folder_black_48dp.png | Bin 0 -> 180 bytes .../ic_insert_drive_file_black_48dp.png | Bin 0 -> 197 bytes .../res/drawable-mdpi/ic_photo_black_48dp.png | Bin 0 -> 295 bytes .../ic_subdirectory_arrow_left_black_48dp.png | Bin 0 -> 173 bytes .../drawable-mdpi/ic_videocam_black_48dp.png | Bin 0 -> 171 bytes .../ic_audiotrack_black_48dp.png | Bin 0 -> 399 bytes .../ic_create_new_folder_black_48dp.png | Bin 0 -> 321 bytes .../drawable-xhdpi/ic_folder_black_48dp.png | Bin 0 -> 307 bytes .../ic_insert_drive_file_black_48dp.png | Bin 0 -> 345 bytes .../drawable-xhdpi/ic_photo_black_48dp.png | Bin 0 -> 548 bytes .../ic_subdirectory_arrow_left_black_48dp.png | Bin 0 -> 269 bytes .../drawable-xhdpi/ic_videocam_black_48dp.png | Bin 0 -> 270 bytes .../ic_audiotrack_black_48dp.png | Bin 0 -> 586 bytes .../ic_create_new_folder_black_48dp.png | Bin 0 -> 473 bytes .../drawable-xxhdpi/ic_folder_black_48dp.png | Bin 0 -> 467 bytes .../ic_insert_drive_file_black_48dp.png | Bin 0 -> 506 bytes .../drawable-xxhdpi/ic_photo_black_48dp.png | Bin 0 -> 807 bytes .../ic_subdirectory_arrow_left_black_48dp.png | Bin 0 -> 349 bytes .../ic_videocam_black_48dp.png | Bin 0 -> 376 bytes .../ic_audiotrack_black_48dp.png | Bin 0 -> 806 bytes .../ic_create_new_folder_black_48dp.png | Bin 0 -> 678 bytes .../drawable-xxxhdpi/ic_folder_black_48dp.png | Bin 0 -> 661 bytes .../ic_insert_drive_file_black_48dp.png | Bin 0 -> 719 bytes .../drawable-xxxhdpi/ic_photo_black_48dp.png | Bin 0 -> 1108 bytes .../ic_subdirectory_arrow_left_black_48dp.png | Bin 0 -> 463 bytes .../ic_videocam_black_48dp.png | Bin 0 -> 558 bytes .../ic_subdirectory_up_black_48dp.xml | 8 + .../main/res/layout/dialog_create_folder.xml | 22 ++ app/src/main/res/layout/dialog_main.xml | 12 + app/src/main/res/layout/item_file_lister.xml | 31 ++ .../res/layout/item_file_lister_light.xml | 31 ++ app/src/main/res/values/strings.xml | 8 + app/src/main/res/values/styles.xml | 10 + 48 files changed, 751 insertions(+), 3 deletions(-) create mode 100644 app/src/main/java/app/fedilab/android/filelister/FileListerAdapter.java create mode 100644 app/src/main/java/app/fedilab/android/filelister/FileListerDialog.java create mode 100644 app/src/main/java/app/fedilab/android/filelister/FilesListerView.java create mode 100644 app/src/main/java/app/fedilab/android/filelister/OnFileSelectedListener.java create mode 100644 app/src/main/res/drawable-hdpi/ic_audiotrack_black_48dp.png create mode 100644 app/src/main/res/drawable-hdpi/ic_create_new_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-hdpi/ic_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-hdpi/ic_insert_drive_file_black_48dp.png create mode 100644 app/src/main/res/drawable-hdpi/ic_photo_black_48dp.png create mode 100644 app/src/main/res/drawable-hdpi/ic_subdirectory_arrow_left_black_48dp.png create mode 100644 app/src/main/res/drawable-hdpi/ic_videocam_black_48dp.png create mode 100644 app/src/main/res/drawable-mdpi/ic_audiotrack_black_48dp.png create mode 100644 app/src/main/res/drawable-mdpi/ic_create_new_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-mdpi/ic_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-mdpi/ic_insert_drive_file_black_48dp.png create mode 100644 app/src/main/res/drawable-mdpi/ic_photo_black_48dp.png create mode 100644 app/src/main/res/drawable-mdpi/ic_subdirectory_arrow_left_black_48dp.png create mode 100644 app/src/main/res/drawable-mdpi/ic_videocam_black_48dp.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_audiotrack_black_48dp.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_create_new_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_insert_drive_file_black_48dp.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_photo_black_48dp.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_subdirectory_arrow_left_black_48dp.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_videocam_black_48dp.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_audiotrack_black_48dp.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_create_new_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_insert_drive_file_black_48dp.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_photo_black_48dp.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_subdirectory_arrow_left_black_48dp.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_videocam_black_48dp.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_audiotrack_black_48dp.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_create_new_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_folder_black_48dp.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_insert_drive_file_black_48dp.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_photo_black_48dp.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_subdirectory_arrow_left_black_48dp.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_videocam_black_48dp.png create mode 100644 app/src/main/res/drawable/ic_subdirectory_up_black_48dp.xml create mode 100644 app/src/main/res/layout/dialog_create_folder.xml create mode 100644 app/src/main/res/layout/dialog_main.xml create mode 100644 app/src/main/res/layout/item_file_lister.xml create mode 100644 app/src/main/res/layout/item_file_lister_light.xml diff --git a/app/build.gradle b/app/build.gradle index 2c6edba04..ab804e23d 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -112,5 +112,5 @@ dependencies { implementation "info.guardianproject.netcipher:netcipher-okhttp3:$netCipherVersion" implementation 'com.github.adrielcafe:AndroidAudioRecorder:0.3.0' - + implementation 'yogesh.firzen:MukkiyaSevaigal:1.0.6' } diff --git a/app/src/main/java/app/fedilab/android/filelister/FileListerAdapter.java b/app/src/main/java/app/fedilab/android/filelister/FileListerAdapter.java new file mode 100644 index 000000000..a0407b4ca --- /dev/null +++ b/app/src/main/java/app/fedilab/android/filelister/FileListerAdapter.java @@ -0,0 +1,336 @@ +package app.fedilab.android.filelister; + +import android.content.Context; +import android.content.DialogInterface; +import android.content.SharedPreferences; +import android.os.Environment; +import android.text.TextUtils; +import android.view.View; +import android.view.ViewGroup; +import android.widget.EditText; +import android.widget.ImageView; +import android.widget.TextView; + +import androidx.appcompat.app.AlertDialog; +import androidx.appcompat.widget.AppCompatEditText; +import androidx.recyclerview.widget.RecyclerView; + +import org.jetbrains.annotations.NotNull; + +import java.io.File; +import java.io.FileFilter; +import java.util.Arrays; +import java.util.Collections; +import java.util.Comparator; +import java.util.LinkedList; +import java.util.List; +import java.util.Objects; + +import app.fedilab.android.R; +import app.fedilab.android.helper.Helper; +import yogesh.firzen.mukkiasevaigal.M; +import yogesh.firzen.mukkiasevaigal.S; + +import static android.content.Context.MODE_PRIVATE; + + +/** + * Created by root on 9/7/17. + */ + +class FileListerAdapter extends RecyclerView.Adapter { + + private List data = new LinkedList<>(); + //private File parent = Environment.getExternalStorageDirectory(); + private File defaultDir = Environment.getExternalStorageDirectory(); + private File selectedFile = defaultDir; + private FileListerDialog.FILE_FILTER fileFilter = FileListerDialog.FILE_FILTER.ALL_FILES; + private Context context; + private FilesListerView listerView; + private boolean unreadableDir; + + + FileListerAdapter(File defaultDir, FilesListerView view) { + this.defaultDir = defaultDir; + selectedFile = defaultDir; + this.context = view.getContext(); + listerView = view; + } + + FileListerAdapter(FilesListerView view) { + //parent = defaultDir; + this.context = view.getContext(); + listerView = view; + } + + void start() { + fileLister(defaultDir); + } + + void setDefaultDir(File dir) { + defaultDir = dir; + //parent = defaultDir; + } + + File getDefaultDir() { + return defaultDir; + } + + FileListerDialog.FILE_FILTER getFileFilter() { + return fileFilter; + } + + void setFileFilter(FileListerDialog.FILE_FILTER fileFilter) { + this.fileFilter = fileFilter; + + } + + private void fileLister(File dir) { + LinkedList fs = new LinkedList<>(); + if (dir.getAbsolutePath().equals("/") + || dir.getAbsolutePath().equals("/storage") + || dir.getAbsolutePath().equals("/storage/emulated") + || dir.getAbsolutePath().equals("/mnt")) { + unreadableDir = true; + if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.KITKAT) { + File[] vols = context.getExternalFilesDirs(null); + if (vols != null && vols.length > 0) { + for (File file : vols) { + if (file != null) { + String path = file.getAbsolutePath(); + path = path.replaceAll("/Android/data/([a-zA-Z_][.\\w]*)/files", ""); + fs.add(new File(path)); + } + } + } else { + fs.add(Environment.getExternalStorageDirectory()); + } + } else { + String s = System.getenv("EXTERNAL_STORAGE"); + if (!TextUtils.isEmpty(s)) + fs.add(new File(s)); + else { + String[] paths = getPhysicalPaths(); + for (String path : paths) { + File f = new File(path); + if (f.exists()) + fs.add(f); + } + } + s = System.getenv("SECONDARY_STORAGE"); + if (!TextUtils.isEmpty(s)) { + assert s != null; + final String[] rawSecondaryStorages = s.split(File.pathSeparator); + for (String path : rawSecondaryStorages) { + File f = new File(path); + if (f.exists()) + fs.add(f); + } + } + } + } else { + unreadableDir = false; + File[] files = dir.listFiles(new FileFilter() { + @Override + public boolean accept(File file) { + switch (getFileFilter()) { + case ALL_FILES: + return true; + case AUDIO_ONLY: + return S.isAudio(file) || file.isDirectory(); + case IMAGE_ONLY: + return S.isImage(file) || file.isDirectory(); + case VIDEO_ONLY: + return S.isVideo(file) || file.isDirectory(); + case DIRECTORY_ONLY: + return file.isDirectory(); + } + return false; + } + }); + if (files != null) { + fs = new LinkedList<>(Arrays.asList(files)); + } + } + M.L("From FileListAdapter", fs); + data = new LinkedList<>(fs); + Collections.sort(data, new Comparator() { + @Override + public int compare(File f1, File f2) { + if ((f1.isDirectory() && f2.isDirectory())) + return f1.getName().compareToIgnoreCase(f2.getName()); + else if (f1.isDirectory() && !f2.isDirectory()) + return -1; + else if (!f1.isDirectory() && f2.isDirectory()) + return 1; + else if (!f1.isDirectory() && !f2.isDirectory()) + return f1.getName().compareToIgnoreCase(f2.getName()); + else return 0; + } + }); + selectedFile = dir; + if (!dir.getAbsolutePath().equals("/")) { + dirUp(); + } + notifyDataSetChanged(); + listerView.scrollToPosition(0); + } + + private void dirUp() { + if (!unreadableDir) { + data.add(0, selectedFile.getParentFile()); + data.add(1, null); + } + + } + + @NotNull + @Override + public FileListHolder onCreateViewHolder(@NotNull ViewGroup parent, int viewType) { + SharedPreferences sharedpreferences = context.getSharedPreferences(Helper.APP_PREFS, MODE_PRIVATE); + int theme = sharedpreferences.getInt(Helper.SET_THEME, Helper.THEME_DARK); + switch (theme){ + case Helper.THEME_LIGHT: + return new FileListHolder(View.inflate(getContext(), R.layout.item_file_lister_light, null)); + case Helper.THEME_DARK: + case Helper.THEME_BLACK: + return new FileListHolder(View.inflate(getContext(), R.layout.item_file_lister, null)); + default: + return new FileListHolder(View.inflate(getContext(), R.layout.item_file_lister, null)); + } + + } + + @Override + public void onBindViewHolder(@NotNull FileListHolder holder, int position) { + File f = data.get(position); + if (f != null) { + holder.name.setText(f.getName()); + } else if (!unreadableDir) { + holder.name.setText(context.getString(R.string.new_folder)); + holder.icon.setImageResource(R.drawable.ic_create_new_folder_black_48dp); + } + if (unreadableDir) { + if (f != null) { + if (position == 0) { + holder.name.setText(f.getName() + " (Internal)"); + } else { + holder.name.setText(f.getName() + " (External)"); + } + } + } + if (position == 0 && f != null && !unreadableDir) { + holder.icon.setImageResource(R.drawable.ic_subdirectory_up_black_48dp); + } else if (f != null) { + if (f.isDirectory()) + holder.icon.setImageResource(R.drawable.ic_folder_black_48dp); + else if (S.isImage(f)) + holder.icon.setImageResource(R.drawable.ic_photo_black_48dp); + else if (S.isVideo(f)) + holder.icon.setImageResource(R.drawable.ic_videocam_black_48dp); + else if (S.isAudio(f)) + holder.icon.setImageResource(R.drawable.ic_audiotrack_black_48dp); + else + holder.icon.setImageResource(R.drawable.ic_insert_drive_file_black_48dp); + } + } + + @Override + public int getItemCount() { + return data.size(); + } + + File getSelected() { + return selectedFile; + } + + void goToDefault() { + fileLister(defaultDir); + } + + class FileListHolder extends RecyclerView.ViewHolder implements View.OnClickListener { + + TextView name; + ImageView icon; + + FileListHolder(View itemView) { + super(itemView); + name = itemView.findViewById(R.id.name); + icon = itemView.findViewById(R.id.icon); + itemView.findViewById(R.id.layout).setOnClickListener(this); + } + + @Override + public void onClick(View v) { + if (data.get(getPosition()) == null) { + View view = View.inflate(getContext(), R.layout.dialog_create_folder, null); + final EditText editText = view.findViewById(R.id.edittext); + AlertDialog.Builder builder = new AlertDialog.Builder(getContext()) + .setView(view) + .setTitle(context.getString(R.string.folder_name)) + .setPositiveButton("Create", new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + + } + }); + final AlertDialog dialog = builder.create(); + dialog.show(); + dialog.getButton(AlertDialog.BUTTON_POSITIVE).setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + String name = Objects.requireNonNull(editText.getText()).toString(); + if (TextUtils.isEmpty(name)) { + M.T(getContext(), context.getString(R.string.valid_folder_name)); + } else { + File file = new File(selectedFile, name); + if (file.exists()) { + M.T(getContext(), context.getString(R.string.folder_exists)); + } else { + dialog.dismiss(); + file.mkdirs(); + fileLister(file); + } + } + } + }); + } else { + File f = data.get(getPosition()); + selectedFile = f; + M.L("From FileLister", f.getAbsolutePath()); + if (f.isDirectory()) { + fileLister(f); + } + } + } + } + + private static String[] getPhysicalPaths() { + return new String[]{ + "/storage/sdcard0", + "/storage/sdcard1", //Motorola Xoom + "/storage/extsdcard", //Samsung SGS3 + "/storage/sdcard0/external_sdcard", //User request + "/mnt/extsdcard", + "/mnt/sdcard/external_sd", //Samsung galaxy family + "/mnt/external_sd", + "/mnt/media_rw/sdcard1", //4.4.2 on CyanogenMod S3 + "/removable/microsd", //Asus transformer prime + "/mnt/emmc", + "/storage/external_SD", //LG + "/storage/ext_sd", //HTC One Max + "/storage/removable/sdcard1", //Sony Xperia Z1 + "/data/sdext", + "/data/sdext2", + "/data/sdext3", + "/data/sdext4", + "/sdcard1", //Sony Xperia Z + "/sdcard2", //HTC One M8s + "/storage/microsd" //ASUS ZenFone 2 + }; + } + + private Context getContext() { + return context; + } +} \ No newline at end of file diff --git a/app/src/main/java/app/fedilab/android/filelister/FileListerDialog.java b/app/src/main/java/app/fedilab/android/filelister/FileListerDialog.java new file mode 100644 index 000000000..87621ecf6 --- /dev/null +++ b/app/src/main/java/app/fedilab/android/filelister/FileListerDialog.java @@ -0,0 +1,185 @@ +package app.fedilab.android.filelister; + +import android.content.Context; +import android.content.DialogInterface; +import android.view.View; + +import androidx.annotation.NonNull; +import androidx.appcompat.app.AlertDialog; + +import java.io.File; + + +import app.fedilab.android.R; + +import static android.content.DialogInterface.BUTTON_NEGATIVE; +import static android.content.DialogInterface.BUTTON_NEUTRAL; +import static android.content.DialogInterface.BUTTON_POSITIVE; + +/** + * A File Lister Dialog + */ + +public class FileListerDialog { + + /** + * File Filter for the FileListerDialog + */ + public enum FILE_FILTER { + /** + * List All Files + */ + ALL_FILES, + /** + * List only directories + */ + DIRECTORY_ONLY, + /** + * List Directory and Image files + */ + IMAGE_ONLY, + /** + * List Directory and Video files + */ + VIDEO_ONLY, + /** + * List Directory and Audio files + */ + AUDIO_ONLY + } + + private AlertDialog alertDialog; + + private FilesListerView filesListerView; + + private OnFileSelectedListener onFileSelectedListener; + + private FileListerDialog(@NonNull Context context) { + //super(context); + alertDialog = new AlertDialog.Builder(context).create(); + init(context); + } + + private FileListerDialog(@NonNull Context context, int themeResId) { + //super(context, themeResId); + alertDialog = new AlertDialog.Builder(context, themeResId).create(); + init(context); + } + + /** + * Creates a default instance of FileListerDialog + * + * @param context Context of the App + * @return Instance of FileListerDialog + */ + public static FileListerDialog createFileListerDialog(@NonNull Context context) { + return new FileListerDialog(context); + } + + /** + * Creates an instance of FileListerDialog with the specified Theme + * + * @param context Context of the App + * @param themeId Theme Id for the dialog + * @return Instance of FileListerDialog + */ + public static FileListerDialog createFileListerDialog(@NonNull Context context, int themeId) { + return new FileListerDialog(context, themeId); + } + + private void init(Context context) { + filesListerView = new FilesListerView(context); + alertDialog.setView(filesListerView); + alertDialog.setButton(BUTTON_POSITIVE, context.getString(R.string.select), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + dialogInterface.dismiss(); + if (onFileSelectedListener != null) + onFileSelectedListener.onFileSelected(filesListerView.getSelected(), filesListerView.getSelected().getAbsolutePath()); + } + }); + alertDialog.setButton(BUTTON_NEUTRAL, context.getString(R.string.default_directory), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + //filesListerView.goToDefaultDir(); + } + }); + alertDialog.setButton(BUTTON_NEGATIVE, context.getString(R.string.cancel), new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialogInterface, int i) { + dialogInterface.dismiss(); + } + }); + } + + /** + * Display the FileListerDialog + */ + public void show() { + //getWindow().setLayout(WindowManager.LayoutParams.MATCH_PARENT, WindowManager.LayoutParams.MATCH_PARENT); + switch (filesListerView.getFileFilter()) { + case DIRECTORY_ONLY: + alertDialog.setTitle("Select a directory"); + break; + case VIDEO_ONLY: + alertDialog.setTitle("Select a Video file"); + break; + case IMAGE_ONLY: + alertDialog.setTitle("Select an Image file"); + break; + case AUDIO_ONLY: + alertDialog.setTitle("Select an Audio file"); + break; + case ALL_FILES: + alertDialog.setTitle("Select a file"); + break; + default: + alertDialog.setTitle("Select a file"); + } + filesListerView.start(); + alertDialog.show(); + alertDialog.getButton(BUTTON_NEUTRAL).setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + filesListerView.goToDefaultDir(); + } + }); + } + + /** + * Listener to know which file/directory is selected + * + * @param onFileSelectedListener Instance of the Listener + */ + public void setOnFileSelectedListener(OnFileSelectedListener onFileSelectedListener) { + this.onFileSelectedListener = onFileSelectedListener; + } + + /** + * Set the initial directory to show the list of files in that directory + * + * @param file File pointing to the directory + */ + public void setDefaultDir(@NonNull File file) { + filesListerView.setDefaultDir(file); + } + + /** + * Set the initial directory to show the list of files in that directory + * + * @param file String denoting to the directory + */ + public void setDefaultDir(@NonNull String file) { + filesListerView.setDefaultDir(file); + } + + /** + * Set the file filter for listing the files + * + * @param fileFilter One of the FILE_FILTER values + */ + public void setFileFilter(FILE_FILTER fileFilter) { + filesListerView.setFileFilter(fileFilter); + } + +} diff --git a/app/src/main/java/app/fedilab/android/filelister/FilesListerView.java b/app/src/main/java/app/fedilab/android/filelister/FilesListerView.java new file mode 100644 index 000000000..96f611430 --- /dev/null +++ b/app/src/main/java/app/fedilab/android/filelister/FilesListerView.java @@ -0,0 +1,72 @@ +package app.fedilab.android.filelister; + +import android.annotation.SuppressLint; +import android.content.Context; +import android.util.AttributeSet; + + +import androidx.annotation.Nullable; +import androidx.recyclerview.widget.LinearLayoutManager; +import androidx.recyclerview.widget.RecyclerView; + +import java.io.File; + + + +/** + * Created by S.Yogesh on 14-02-2016. + */ +class FilesListerView extends RecyclerView { + + private FileListerAdapter adapter; + + FilesListerView(Context context) { + super(context); + init(); + } + + FilesListerView(Context context, @Nullable AttributeSet attrs) { + super(context, attrs); + init(); + } + + FilesListerView(Context context, @Nullable AttributeSet attrs, int defStyle) { + super(context, attrs, defStyle); + init(); + } + + @SuppressLint("WrongConstant") + private void init() { + setLayoutManager(new LinearLayoutManager(getContext(), LinearLayoutManager.VERTICAL, false)); + adapter = new FileListerAdapter(this); + } + + void start() { + setAdapter(adapter); + adapter.start(); + } + + void setDefaultDir(File file) { + adapter.setDefaultDir(file); + } + + void setDefaultDir(String path) { + setDefaultDir(new File(path)); + } + + File getSelected() { + return adapter.getSelected(); + } + + void goToDefaultDir() { + adapter.goToDefault(); + } + + void setFileFilter(FileListerDialog.FILE_FILTER fileFilter) { + adapter.setFileFilter(fileFilter); + } + + FileListerDialog.FILE_FILTER getFileFilter() { + return adapter.getFileFilter(); + } +} diff --git a/app/src/main/java/app/fedilab/android/filelister/OnFileSelectedListener.java b/app/src/main/java/app/fedilab/android/filelister/OnFileSelectedListener.java new file mode 100644 index 000000000..504b3f577 --- /dev/null +++ b/app/src/main/java/app/fedilab/android/filelister/OnFileSelectedListener.java @@ -0,0 +1,11 @@ +package app.fedilab.android.filelister; + +import java.io.File; + +/** + * Created by root on 9/7/17. + */ + +public interface OnFileSelectedListener { + void onFileSelected(File file, String path); +} diff --git a/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java b/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java index 172d044a2..d603e666a 100644 --- a/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java +++ b/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java @@ -68,6 +68,7 @@ import com.google.common.collect.ImmutableSet; import org.jetbrains.annotations.NotNull; +import java.io.File; import java.util.ArrayList; import java.util.Collection; import java.util.List; @@ -80,12 +81,15 @@ import app.fedilab.android.animatemenu.interfaces.ScreenShotable; import app.fedilab.android.asynctasks.DownloadTrackingDomainsAsyncTask; import app.fedilab.android.asynctasks.UpdateAccountInfoAsyncTask; import app.fedilab.android.client.Entities.Account; +import app.fedilab.android.filelister.FileListerDialog; +import app.fedilab.android.filelister.OnFileSelectedListener; import app.fedilab.android.helper.Helper; import app.fedilab.android.sqlite.AccountDAO; import app.fedilab.android.sqlite.Sqlite; import es.dmoral.toasty.Toasty; import mabbas007.tagsedittext.TagsEditText; + import static android.app.Activity.RESULT_OK; import static android.content.Context.MODE_PRIVATE; import static app.fedilab.android.fragments.ContentSettingsFragment.type.ADMIN; @@ -1040,7 +1044,7 @@ public class ContentSettingsFragment extends Fragment implements ScreenShotable set_folder = rootView.findViewById(R.id.set_folder); set_folder.setText(targeted_folder); - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + /*if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { set_folder.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { @@ -1052,7 +1056,25 @@ public class ContentSettingsFragment extends Fragment implements ScreenShotable }else { LinearLayout file_chooser = rootView.findViewById(R.id.file_chooser); file_chooser.setVisibility(View.GONE); - } + }*/ + set_folder.setOnClickListener(view ->{ + FileListerDialog fileListerDialog = FileListerDialog.createFileListerDialog(context, style); + fileListerDialog.setDefaultDir(targeted_folder); + fileListerDialog.setFileFilter(FileListerDialog.FILE_FILTER.DIRECTORY_ONLY); + fileListerDialog.setOnFileSelectedListener(new OnFileSelectedListener() { + @Override + public void onFileSelected(File file, String path) { + if( path == null ) + path = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS).getAbsolutePath(); + final SharedPreferences sharedpreferences = context.getSharedPreferences(Helper.APP_PREFS, Context.MODE_PRIVATE); + SharedPreferences.Editor editor = sharedpreferences.edit(); + editor.putString(Helper.SET_FOLDER_RECORD, path); + editor.apply(); + set_folder.setText(path); + } + }); + fileListerDialog.show(); + }); final Spinner set_night_mode = rootView.findViewById(R.id.set_night_mode); ArrayAdapter adapterTheme = ArrayAdapter.createFromResource(getContext(), diff --git a/app/src/main/res/drawable-hdpi/ic_audiotrack_black_48dp.png b/app/src/main/res/drawable-hdpi/ic_audiotrack_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..8e38265f728b70a8dcc8423f34afd78ad47257f2 GIT binary patch literal 309 zcmV-50m}Y~P)C=YAb|w>x1h!eB#=M?(Jp}m5=bC{x(t~xW5JpwFWht74%B1J zD$eaZAjLW6J6w|u71&a z{Q8&X98tYJZu$5Dv*e0h8nw+Sk4#B?l9=*9pDjF6N-6aXZ9lyV>*GM}00000NkvXX Hu0mjfvNeSc literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-hdpi/ic_create_new_folder_black_48dp.png b/app/src/main/res/drawable-hdpi/ic_create_new_folder_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..a76477fb2115bf926e399a784143538610a55265 GIT binary patch literal 254 zcmeAS@N?(olHy`uVBq!ia0vp^9w5xY0wn)GsXhawj(WN{hEy=Vy>WEvVFv-Whr2Q- zO)!e_OIRG8)^YgE1-n@{nXmm`{l02`gw&KEua%dc?s(R!w(anp$9w18|Jv|jNsl~_ zcY8@^qUJ=ojaxiIb#yNYaGS;2?Kr$~qo7#DKh31(X`Xtz6AEWbz0frcur{5*DI#xj zxp2Y9$R-vc4~52WIrDXAI52TO`MFIT$Ytr`|76Kj$xs>`-S@MDsVX(MJka6#nzJ9} z=X~})*4A}kNqo_^Cp(_@mNj_)oSJO}a?>PJ#`)r59Oi++Z9oq(c)I$ztaD0e0s!SK BY1#k) literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-hdpi/ic_folder_black_48dp.png b/app/src/main/res/drawable-hdpi/ic_folder_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..5c4360af8a40f06dd81af3da036a90f0c8cf31e0 GIT binary patch literal 239 zcmeAS@N?(olHy`uVBq!ia0vp^9w5xY0wn)GsXhawwt2cZhEy=Vz2V5!R3Om$G5_m# zzN#Yvwoc2rgFL^eI4bC^%Dn58d)eZ|?|ZCu-I2UrnoF-d^qLY=nPC6s%>C0Zw=32y zIl_DR(F8vUvCfi%NfX~i=v)#mzU|}gdn`-;Or^4`&IH2=NsT>PQY(7dW-V%byWCkb_9eLrdM2 ziV8R8zfl#9n46&REQxWN0>>-IUe-4+ZPPj){JDIfT*Bgc*xCh;I;5vP_%`86GM~be zB~8IhN-A%KI5b~QaEd8elFhZ{>clurfs!TVLPyjD9dd*iL6nLRql-eJBa4tY3MGF; z{iCC<=ACw?EDw8zERQOI=DZ1xY?3JfJB}(e^BA3g6EF5V_-j7zE0`=|qI5@rHMHe* z!L-6O5tUmV9>!HFuMH9oHCH?p6lK+ZHs?3f*TOG%d=mZV1O3S0>FVdQ&MBb@07Tkj AL;wH) literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-hdpi/ic_photo_black_48dp.png b/app/src/main/res/drawable-hdpi/ic_photo_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..7297bd5d29836b39d398d97961bc312fd9152bb5 GIT binary patch literal 424 zcmeAS@N?(olHy`uVBq!ia0vp^9w5xY0wn)GsXoKNz?kpp;uuoF`1a;TufqW%4G;IP z;N;S~n0IdihI998&O^-W#$ zE8eR<`gyLR?O%&Chls5choVhVmCp&?Gd)wx?0#|VP~L8%%w$p-R(yr$;{~C~*0aQ- zs?IgBWz4kTp0!A|+(Jmj5e0owZ&G_RIaKonL&qxNl4CJJy$iIb&5VA0&o>}y-{Vf+ zDHG1r1x#19Qr&G{7AbO*Pb!!_%zNG?L)Xr;3&OX}$oL zDwTSQHR(l^wA|V&5Tv(BaLS|4S6@E=HsQVMvgUa=7p*v^YH9g=O3?HaqZf1cUXtJS zaF%GD*rb`FVdQ&MBb@09A9bRsaA1 literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-hdpi/ic_subdirectory_arrow_left_black_48dp.png b/app/src/main/res/drawable-hdpi/ic_subdirectory_arrow_left_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..812e1ccc65f7b38c44dbf35d0017da8b2c562432 GIT binary patch literal 236 zcmVHKLoGp(mAPC^B2?PQ-_vY{*h68{A4gdl;hlB@l8~_Ax01&{r zHHQcB93I4TI8bxQ4dZMyN6`MHOe5jf9*%!D29Q=s$WL0*Gsk>S(rFs$HIcN;BAvqp mkS+n@NY@OiQrRyvGkXJ{fRTl#J(->W0000H?k2;OXk;vd$@?2>^U;U)TTu literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-mdpi/ic_audiotrack_black_48dp.png b/app/src/main/res/drawable-mdpi/ic_audiotrack_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..4778e0086cee620ce06d074ec0f7019aa66c3aa7 GIT binary patch literal 226 zcmeAS@N?(olHy`uVBq!ia0vp^1|ZDA0wn)(8}b0Dm7Xq+Ar*{oujuj}au9KSczLQq zfUkLgx0XVz+^iOXU7Rvq6S%|<_?J5fC}ap8X7aFBH0D2Jd;b1;+bO@C^B(N;Z)nKi z6i{$zSl%+JtF2GmU2J1x&#h0@Vm3PWi=WNpXA#PpqZ;rir}30j#+t@+QWwXlhs~+HRFve|7-avB Z*T`q3#RJQ$wm?TSc)I$ztaD0e0sw^^QtvPMV^&Q^E|L6=z;p_=Kfc zWEx{?RAa_+v7TV=FRV?b=Gz6Z28Xndkxb#%ktD@EPwvW0=kI7)78&qol`;+0NlMnlmGw# literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-mdpi/ic_folder_black_48dp.png b/app/src/main/res/drawable-mdpi/ic_folder_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..49272b0f94868394c8be1c63c97e8a4877584b28 GIT binary patch literal 180 zcmeAS@N?(olHy`uVBq!ia0vp^1|ZDA0wn)(8}b0DYEKu(kP61PR}J|N83?#ste^ED zxkzEj1Q{KdBdP{h#N0&gxs8U&uF3XJkIyz$5X)mYFT<+r@b2#+m(G)?BxavDhX(A-PL#CT5Az5qiARtADF310vJ002ovPDHLkV1k7`cx3

FS$kP61P7Y(@@3`CkA%6Qw( zc(7>arZ@-3Bj)ZL( VF%S*V+5@zo!PC{xWt~$(69C2TImQ40 literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-mdpi/ic_videocam_black_48dp.png b/app/src/main/res/drawable-mdpi/ic_videocam_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..b0a3b44d154ae04a54b04ceac0d7322a08f8bf68 GIT binary patch literal 171 zcmeAS@N?(olHy`uVBq!ia0vp^1|ZDA0wn)(8}b0DB2O2`kP61PR}XR?HV|;Rct645 zWyYzqyE;z>o>WZWp5|eY|L&jo;#5mPL4U6McTOHmZB-Ae5w@=^n%`p0d}uD?!*dM< z=?*)L74Aq1yyLZKWV!a=SF$s9e%HhsKX=M?+Rr;9?Ej|p?+f`WN1n^Oxahp&eQwIR UE#vBiFre)Wp00i_>zopr08juyvH$=8 literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xhdpi/ic_audiotrack_black_48dp.png b/app/src/main/res/drawable-xhdpi/ic_audiotrack_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..e0e829fc346b2b9bc2248d7361bc193763a7d273 GIT binary patch literal 399 zcmeAS@N?(olHy`uVBq!ia0vp^2_VeD0wg^q?%&M7z!>J~;uuoF`1Xda7jvLU+e2}7 z$KV-S%Qk&TXV!DbVewQCOF9r{xO>AjR*qS2o~i5SYG^o4Hk@l8>Ew~`bfT2i(b)Xq zJ>~n>(m&=U&Umz7*^D4B&81ULfBTc&z`(?z045wRg!Yf~|JD2t z%-hRo&XRjydV}W$A-lcL?1lE^_WxwQ*14ejOoQ;EjCpR$ewM4aTvC!xK3|{M*rD~o z>e`>`PcGMFp4ZFRKk12Fl+*n^{`vA8fkMt|o8Fqw{BMk!8>d-5nx!UN_2tEd2VKt7 g0zjS*3VzML_~}y4pDh8OfC0_m>FVdQ&MBb@02ZX7k^lez literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xhdpi/ic_create_new_folder_black_48dp.png b/app/src/main/res/drawable-xhdpi/ic_create_new_folder_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..750374b71cb23e7e79b4555419892182931be4f1 GIT binary patch literal 321 zcmeAS@N?(olHy`uVBq!ia0vp^2_VeD0wg^q?%&M7z{uh0;uuoF`1a<}P!~rLwuiTT zk2ke@aO`;6w4}jVV$HGNn~u$WSM7IozueDb&u!nhrh&k=V|L$rI`#AB@@dHgc1}O- zs4+)Ke|q}{cY#XI?hqy8#K{Uq!g?KdTG*A$6J1KS8h(GX`P6c0VcB&>4xVfk8;!m4 z95&3C4TwC;%TczOIq&BN&+83=We!W&IRrkexzFx1n~8-(Kp~-xfrZ0?!T#;->(=55 z4h;><8nhO?6rah!$n?lv7%0HNxK@3^N0y$=^IzEJpwMfTiCfS8a zN?<_+77hUg2cX3N`3+0Ix__S{Rj}~Z1gU}rQT~dP)_pk9b!!kpia@m&)- wmeL+#vFY);D!-VSoxSG84-2Y)r-4EJ_03`13fdgb0Yibo)78&qol`;+0Hz9iPXGV_ literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xhdpi/ic_insert_drive_file_black_48dp.png b/app/src/main/res/drawable-xhdpi/ic_insert_drive_file_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..56063aaa66a76ee08e2e9b1a797b7aca1b8d7a08 GIT binary patch literal 345 zcmeAS@N?(olHy`uVBq!ia0vp^2_VeD0wg^q?%&M7z^LHq;uuoF`1Ztl~{bZWo_KtgO!K&8k_m=_|m8DzvFY;GtT#+#lbD-l^TLtibWM%U$io`Phg+X zVsk*{38R`KzX4}ugXalmA1Ap9N;RR3KsrI_6T|cg>_31?)SocgDe`~dtUOTCboYA? z!%AIQg{@1OmrP^1Vs8xe!5<)IU}y+su44o-4y%!=MQ+83q+&6hmpV?zqE?6#+uzr%>7qOZD7xjj?R?Pcb@$J@%EzznI1;~zt(?`HLvucvGPndIr}=d#Wzp$P!4B7;N# literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xhdpi/ic_photo_black_48dp.png b/app/src/main/res/drawable-xhdpi/ic_photo_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..ebe206ff7bb1de48d109e24282501264d1c85251 GIT binary patch literal 548 zcmeAS@N?(olHy`uVBq!ia0vp^2_VeD0wg^q?%&M7!1&tJ#WAFU@$D_&t}6}_?H}DG zUtF78%ap#9!};-X(IfrAEF$5LMBUCCTvqAkux#a8#IvsSCC_EOFHChgM@+0V!-Go} ztWHi{v5xCs{noXv_7lwYO&kTx1qB6n`W>9Znszw-prK{(xhG7jYOgXiB))yeH<#dZofRb8aKMh65v4Km(J=0tQxe zrh}*HlLr2tohObjWUF~<#BlwG<&g&AcZFKgNe6i} zfNYr$^8};!yxS34JUMjJ3C3@0i#mVas^%|TnZ!1yV0v))k9T{%%dlH>PGl;JESr7* z+|{QE>WW?mxX)euR&jJ~e$Hi8Zm9Tj<;&2I@{RDB)ul%4IcxY~~shuCjiJz7=%!}+XkP3S}BH?LlOXmQ{1 zbtX&xyQ`v;<^mP(Zkg7~vthON3ayZa*jUD$>Ib8bzq<89<;SOp*oW$l^*Ndhtbf|& z_sOY?7IbX4S=nH_$2U{x*PlA}wm*#j?DqCp9#AQ`XVkQh)Ab4a%EbAC=|-u?1WQ}Q jpDR|sd7z>M1oey&Pa+y;l`K*O#y*3mtDnm{r-UW|Gl}p9 literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xhdpi/ic_subdirectory_arrow_left_black_48dp.png b/app/src/main/res/drawable-xhdpi/ic_subdirectory_arrow_left_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..40a5dc65e7852783c748e55d2fd54191c4c7b455 GIT binary patch literal 269 zcmeAS@N?(olHy`uVBq!ia0vp^2_VeD0wg^q?%xcgu6VjQhEy=Vy?T)MkbwZ}#axD} z7P|&rzKqiz`y%H{a~fRg;lA;oFYr~rk+HGy=8blYOe`D%3Jen&APk2FAY<1oo)?vy z0vl$`XW>{deX}ofiAqo`8)yJnpocE8RWU|_J_i3@NKo2r_y85}Sb4q9e0RN|LDgXcg literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxhdpi/ic_audiotrack_black_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_audiotrack_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..08a8c98fc0cbad1df5934c9e96e63f7144dcbf06 GIT binary patch literal 586 zcmeAS@N?(olHy`uVBq!ia0vp^6F``Q1xWh(YZ)^zFbR6PIEGX(zP+_KOC(Xk{o`k+ z66u524jocjBB;1D^oTBtwRNj#aw<;;zFq@$|+;Vv8f0 zRJj@#{rafW7{=1&)x+8~tJj@#i%P(qfCW2B8y}gmbV+lIY*(G&V3+jI^Z)UA=EsWr zb#~vDxS+b}O;WPMagI+Be^1J7(lN|pd7*mq+XBG_+9|g$vQ^Y=oS);pXT9tT&dBWn z)&cX^y#BZ`Y+iWE{g+ae+bn%1s2|r_n=wm%>xY^IechKKy6?{yZ&~qrDzol|RYLsQ zPa~I=`fiMpJRcer`6xut)<*>rM7)ABnHZP-0i=FEhFoAR1V WKg+!LnHT^}BMhFdelF{r5}E*?p!Jpj literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxhdpi/ic_create_new_folder_black_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_create_new_folder_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..5f4513690af6df6e39dc299cde12da0b411ec31e GIT binary patch literal 473 zcmeAS@N?(olHy`uVBq!ia0vp^6F``Q1xWh(YZ)^zFfQfy%}mgTdoKc?KXzQ5M}o#gdD-jh^3A?VV%m@}XEocF0Z zZF2qcjIt+jR?T9rB?igO(_KmyMG0J-SHiB}o>9CnbhYBHz_qOz$!V*X3dpVvclxp; zj^pC$Dp{BLuTlkimtH?H^K|>3GfUr`5|Z{`fAR9kzi(JV&PVVuOPM`q;GON<@JjMD zpTpNXCzWPp2nMKIGhQv03$Q)UaP>1^fbHgnwzEyMSy(s(6dW3+?K&`v(U*}4%v0tz z;RTB_^y*yTSuh_gykKgc>$$@^K(!2vOeUKgia|6B$AuI7BHl8<^j%?v80RLof*oRl z?tiGH@!Cf-Pc~IQe_!}&-tXq6ySTpw{xUx*`*KU$^2xH1F6Gh8CEDFt)yJX^ezv{6 z=>*?4ri}V&7hWFwJm;K{^@R7l`wHKlH`=1RUHV7IwUcXePH)<3`}~thzR}$Vanbjm ibe{jS-+&0n6j+D#u^PeuAIrF*N|AXx$)84QB zDxQ-d=!?DYXPfY!vs|ya-#X2+Ozr)pTq}`_k+;seD^&%_cD$$yo89kRVs5|cvcTR| z=bTE^PruS|>3=<0pmqhn)0drg>=(cPl5okr)_f;--_zi@Cvkjl(yukgP5(ZVY1Q>- zf(vqIGv3k@E{JAe+{Jh$8q8qY!T@Knz*r^RE4G7FF|n**hKX%qg0t*$z;a+Cfr_5kcXhwH zbLX=~X}Da(s%kT>1(9XzJk6!%>G^(p@iwDDZ&SE>ru)I-xt`zNvw&0o+zy$ R<_nB022WQ%mvv4FO#owvzWD$E literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxhdpi/ic_insert_drive_file_black_48dp.png b/app/src/main/res/drawable-xxhdpi/ic_insert_drive_file_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..86d7596087e43e4a8c88102f1a866b133bcc37f6 GIT binary patch literal 506 zcmeAS@N?(olHy`uVBq!ia0vp^6F``Q1xWh(YZ)^zFdp=DaSW+oe0$3dDD_@iKl-1FZTSX|`W z&bfcl*uC(v;9e;^*^A3H1+9c?X9{S@cJA}#yfX1cqSt~x7yIRGt2!B`x-@txIj9OQ zn8Xp_$+AL)$)tMG*_Dl1C}JT(j9Q%xXZv1UztezCCe&r|_i8Z*Q^5tZI0AfGR;V$B z2!CbIYUbm(@ZxWzhJb=Y0|O%y3&(}Bg-{kyXm=|UNDM6bHx@}z9g?DUBt>U4bYKR- zO`Pz*d7I?k-`5<TRQx`DU eRaQp+XN+HW*>AQ-&|_enGI+ZBxvXESqacg#PH`B$rqARC7 zd%MkZMt5@hvrjR8&%gY(dA<2((|McjgN|CNN-%Kv%%!AW*-s8>?V(X;E-WZ=woz8* zFEJ8Z8N85l+X?3RzQbC^vr&$_DLwCFYoK;RUbat z-(B8t$Twx#pUf9UUF+-p4kt%=?q$)cm$I6Ze!W)eR=$#aqnhS(wd)(6-gA*-GW|JS zK>ghJTKxIND~XMI%IEGX(zP)q4lgUxw*v0oI zQio5qX>Utws4qe zElqU^*ri=?`M$x`CvGRiE`|lGEDZG(>8z1HJ+WoxrOV4)0}cH?KQ4Z-C%*pB@5bt{ z=N`J0TsSWw`RwGR#V6RZYZBT_w!cVQ&veC$+u3JBP|*pU@0PxMsu)!qyELzzo@E?A zm*LVG4)0x`&$=le)_Hx&R@+moR>PN|Bay5Vx^o_^ zVe(l2@DJAk&n^qr4VT>HmNSISnsHRKVQ%3ZrW>A*L=N~Vb8{tRN-Sq6n-v+x;H?Z) zHaWqQQDW!0vSad`W09&ct_N?X)*kA@0rb#eq}X7I)~r(7|CAj|L$w;C-iKxr!{F~fs+XqcEwA+O}r}u=4|%) zw06zQ{YIYrfmdKI;Vst0Es?27XSbN literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxxhdpi/ic_create_new_folder_black_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_create_new_folder_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..6cbb30e536dea7a3e274c5240aceb49c615268a7 GIT binary patch literal 678 zcmeAS@N?(olHy`uVBq!ia0vp^2SAvE1xWt5x}=AJfhpJ1#WAFU@$H?hiA%~wj$WMI zv6Su1Hw~j{57~N-N(gP1<^Em3o^~gLJ3>gOEApk$ng6qEn?CQB-J>kirQ$gW6--Dw$p>nbZ{im|K8_ca)cu!fO=VL=**wSkX;pF!wzJE2`p?;zD8Fpy%6<0M*RL5*=el zDNAPT)k(R#Qhw9dGf#VMrmKApO#7TYZIf{PXYZe;n|~SzTTVw$9g~(M&kjvU+}NZU P3i6AmtDnm{r-UW|w|)zv literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxxhdpi/ic_folder_black_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_folder_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..27e524f61183ea265d215277599e4c447559abab GIT binary patch literal 661 zcmeAS@N?(olHy`uVBq!ia0vp^2SAvE1xWt5x}=AJfhoq*#WAFU@$FrIzu;VnV-KrY zOb>AR_$)Z%lOnl}p=q{ZU&jOsea+tmoW53$GCLU!d4KG0c)R@35APnQ^DF&5*1x`Y z@UwMuxr3LO2+&j**f34~W%`WIKE<}rZBPH-FmrK?nZ*hg-jYrCKg^!Kpz-UTQ>7PG zP8^;yZEk#%&57H)9(!+?lKAwcYDH9K8Rxs_t3JID+OxuD2aC7mdYkPm{n`Dx2S48m z_WrQx+XbOLD{VKkEMKZV?SX#2!t7@{hreu|z4gq|YWIB)^@^sPy~SX5*3oJ!;~SN` zK<25isLux-)4eXN&ju z2eO!AEEX{^0d+eI54c{EO^?%#F4Bw^XDvPc{~x+pu@bv$#0x z7rNzho^Dw&d*b4IN$)q!o0fZ5sqwS@DVdVuM?1`K6kan{pZlg-@NePdH>sAzSAFmQ z7yJG8nB^I_f1Ov~ESc`;HuJ|b<5LQIbJA70IbjI^NdI8vV2?cYDMsH6BCvo#3!=Y9g}}$AjAn1s_ZKP0ru{ zU9;~zU)}u4vx~chV>LY|sen<5^8Y81WkqvN|Iyi}d3M+AwR5ia^gf7^yK4KHW7_9s zc_}RQDf{yhSjs=G%Zp**zPWOa*umygk%D*5RX$z8As5cqm7sWhYO&If-DN&3{Oz;1 zNgiB%kl|8qLcT>q8q05HrY%YqazYCP51w4W@RWt&6eq(JVTKi|3;_-d3#1SJ{>b!7_6g85kCPoC*>Ff;r4U-cz6uP&qe{*kS`> zG8h1b9Ug0gM1WuiFyVNmVwfkGLTVDSg+KuRh;6r#vs z@=UM=5FU*D;Zr*8Q(qLb%(6XquQA-#%wKJK!0puU?WPB!PVJt#dE4jtX`0Mm7U>>H zYs=XB(p_rvnv@Ciwy;E;H_&~WyZdK+x*_w{S(C#)%cod2e+^e|YW_2margASYW8-g zCAYk;w0fTJvUyFqp>w&tezD>5`rT%mC*5BZ{Zs$^=Glv5&K)$apYb*)Mb~>GB;BZZ c?sD4Cuwv?|H&FVdQ&MBb@0A929asU7T literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxxhdpi/ic_photo_black_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_photo_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..ab700a31baa62ff83bb872ceae6838e546c32080 GIT binary patch literal 1108 zcmeAS@N?(olHy`uVBq!ia0vp^2SAvE1xWt5x}=AJfkoQW#WAFU@$HSfSu&+E?H`W^ zcm_!yyuxj8b6Xa_&c1t%H&!jzeS6c%RnX-N*CLJ9Y4f@|rC-Oi>Wh3d5SSuyQCPIb za^lvjT1#H#MgMOSkT`KpW%ir=WtVI1&dWZD{x$!;lIJ891Y$m0(8jkqW~u+K!>@~5 zL#^hdwcS1>sP|DklV|riqxKb7O~iLPNizT!sW zpU=- zt+LvQ?t0E5nFs7?CxHwZh3ob<=M-|;S1c3Pm}Kct^FCPNi)ul`otL2sKU5jmACy14 z;dh(ylkR7}Oqai>H@|Ut#xT3~oXYPVK2o0fK|23bImEw5pRKL&zEv!5?AYk2-^hID zk;QDeCsLXIe^2Nf&aghfROw%w?7#fFFpswMdq%q_dY>MMURqZ@an7u`rh<$6uO8UF zB=#%g(MR!3YUtlEa%!h2%mK4spkrq6D6=lo%dSa!zwkKvV< zUu7(}?qj*=R#7#zx^4Cn*>7T&ru%{XDj^LE`Mg~gM4 zk27$;xpKE=+uN64RVu#%RWtdmH`-j|uk}*3P5ifz3%BLoQ#LW5Y^NCRc`;of>cq>? zcNGV}UzqMAthl?F-Qx7SJz@n_u6tQ79`ajX^gh>e@4V#>XZ0Po9Jri4;9(O31Hi(2Q$J&k*w zy6SS?Kaf*9H?i>u6jUAUuI4;+bbj1NrTC_TkITdNoS3c<^XKK&Hw389{_Af5m7r2a zh*T%Nn^9(g|E5D#ExVmI9op3rts0rA-ST?Enhmap=Bh;|s&kqL|Cqccw}Ag+gc|Re zX)BH_Y@EO7TJpTE7=@eD&IQiQ+^6)^_}YvmPP)66ob8F9u{h~?k?@b_^(|6cBGe_b z&je1^JlFqIJg~pmCup^ptl6`L-x-YH`SEG-y3UHx3vIVCg!01&SITmS$7 literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxxhdpi/ic_subdirectory_arrow_left_black_48dp.png b/app/src/main/res/drawable-xxxhdpi/ic_subdirectory_arrow_left_black_48dp.png new file mode 100644 index 0000000000000000000000000000000000000000..dbe7ee6b03a1ead2aa293b24f4dcdbf6be41dd6b GIT binary patch literal 463 zcmeAS@N?(olHy`uVBq!ia0vp^2SAvE1xWt5x}=AJfpMCri(^Oy&q3+t1;&HIpZ2UhaR0=`UKP(t2y}Pd`)*+d1||jv1_lnGDGUk>3@i){ z3=9Iq3eK@)*mdr`x*Ws9Ka7kGbN4GTZ1}9t*ii6Kl|kU_einvVKc_P|82lGv(0Crt z#BlJBH-o~A`uE9l45xn1|HJtA55upYj9)%8zj)4m;XMC>`SK3-_6>D)3_yupKN(p* zGjlv+7dXSOFhjoKr#>T?;b36jkWdFSis6hr!wh={gL;O9e+&oyFgE-YX86o}s^g5l|3dVsUD4s8|0n=eZ!5 z$swSjRw1eApuob>!qE86x8VUdBNGdUfPzB}F)3hS`M=_397UwfIkP#FF*NE#(&0t0!Yx))z4*}Q$iB}FILFz literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable/ic_subdirectory_up_black_48dp.xml b/app/src/main/res/drawable/ic_subdirectory_up_black_48dp.xml new file mode 100644 index 000000000..d001db865 --- /dev/null +++ b/app/src/main/res/drawable/ic_subdirectory_up_black_48dp.xml @@ -0,0 +1,8 @@ + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/dialog_create_folder.xml b/app/src/main/res/layout/dialog_create_folder.xml new file mode 100644 index 000000000..9614e4f9b --- /dev/null +++ b/app/src/main/res/layout/dialog_create_folder.xml @@ -0,0 +1,22 @@ + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/dialog_main.xml b/app/src/main/res/layout/dialog_main.xml new file mode 100644 index 000000000..ff0c7f1e4 --- /dev/null +++ b/app/src/main/res/layout/dialog_main.xml @@ -0,0 +1,12 @@ + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/item_file_lister.xml b/app/src/main/res/layout/item_file_lister.xml new file mode 100644 index 000000000..6750fd111 --- /dev/null +++ b/app/src/main/res/layout/item_file_lister.xml @@ -0,0 +1,31 @@ + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/item_file_lister_light.xml b/app/src/main/res/layout/item_file_lister_light.xml new file mode 100644 index 000000000..df29a222d --- /dev/null +++ b/app/src/main/res/layout/item_file_lister_light.xml @@ -0,0 +1,31 @@ + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 211e3d278..146cb7dde 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1099,6 +1099,14 @@ Interface Battery Compose + Create a new Folder here + Enter the folder name + Please enter a valid folder name + This folder already exists.\n Please provide another name for the folder + Select + Default Directory + Folder + Create folder %d vote diff --git a/app/src/main/res/values/styles.xml b/app/src/main/res/values/styles.xml index f7c992029..7599e21a0 100644 --- a/app/src/main/res/values/styles.xml +++ b/app/src/main/res/values/styles.xml @@ -347,6 +347,16 @@ @drawable/button_selector + + + +