updating some dialog and documentfile related things
This commit is contained in:
parent
db42b53658
commit
464482bf1a
42 changed files with 278 additions and 188 deletions
|
@ -6,7 +6,7 @@ buildscript {
|
||||||
propMinSdkVersion = 16
|
propMinSdkVersion = 16
|
||||||
propTargetSdkVersion = propCompileSdkVersion
|
propTargetSdkVersion = propCompileSdkVersion
|
||||||
propVersionCode = 1
|
propVersionCode = 1
|
||||||
propVersionName = '3.11.47'
|
propVersionName = '3.11.48'
|
||||||
kotlin_version = '1.2.21'
|
kotlin_version = '1.2.21'
|
||||||
support_libs = '27.0.2'
|
support_libs = '27.0.2'
|
||||||
}
|
}
|
||||||
|
|
|
@ -183,8 +183,7 @@ open class BaseSimpleActivity : AppCompatActivity() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
val destinationFolder = File(destination)
|
if (!doesFilePathExist(destination)) {
|
||||||
if (!destinationFolder.exists() && getSomeDocumentFile(destination) == null) {
|
|
||||||
toast(R.string.invalid_destination)
|
toast(R.string.invalid_destination)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -203,6 +202,7 @@ open class BaseSimpleActivity : AppCompatActivity() {
|
||||||
val updatedFiles = ArrayList<FileDirItem>(fileDirItems.size * 2)
|
val updatedFiles = ArrayList<FileDirItem>(fileDirItems.size * 2)
|
||||||
updatedFiles.addAll(fileDirItems)
|
updatedFiles.addAll(fileDirItems)
|
||||||
try {
|
try {
|
||||||
|
val destinationFolder = File(destination)
|
||||||
for (oldFileDirItem in fileDirItems) {
|
for (oldFileDirItem in fileDirItems) {
|
||||||
val newFile = File(destinationFolder, oldFileDirItem.name)
|
val newFile = File(destinationFolder, oldFileDirItem.name)
|
||||||
if (!newFile.exists() && File(oldFileDirItem.path).renameTo(newFile)) {
|
if (!newFile.exists() && File(oldFileDirItem.path).renameTo(newFile)) {
|
||||||
|
@ -244,15 +244,15 @@ open class BaseSimpleActivity : AppCompatActivity() {
|
||||||
}
|
}
|
||||||
|
|
||||||
val file = files[index]
|
val file = files[index]
|
||||||
val newFile = File(destinationFileDirItem.path, file.name)
|
val newFileDirItem = FileDirItem("${destinationFileDirItem.path}/${file.name}", file.name, file.isDirectory)
|
||||||
if (newFile.exists()) {
|
if (doesFilePathExist(newFileDirItem.path)) {
|
||||||
FileConflictDialog(this, newFile) { resolution, applyForAll ->
|
FileConflictDialog(this, newFileDirItem) { resolution, applyForAll ->
|
||||||
if (applyForAll) {
|
if (applyForAll) {
|
||||||
conflictResolutions.clear()
|
conflictResolutions.clear()
|
||||||
conflictResolutions[""] = resolution
|
conflictResolutions[""] = resolution
|
||||||
checkConflict(files, destinationFileDirItem, files.size, conflictResolutions, callback)
|
checkConflict(files, destinationFileDirItem, files.size, conflictResolutions, callback)
|
||||||
} else {
|
} else {
|
||||||
conflictResolutions[newFile.absolutePath] = resolution
|
conflictResolutions[newFileDirItem.path] = resolution
|
||||||
checkConflict(files, destinationFileDirItem, index + 1, conflictResolutions, callback)
|
checkConflict(files, destinationFileDirItem, index + 1, conflictResolutions, callback)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -232,9 +232,9 @@ class CopyMoveTask(val activity: BaseSimpleActivity, val copyOnly: Boolean = fal
|
||||||
while (bytes >= 0) {
|
while (bytes >= 0) {
|
||||||
out!!.write(buffer, 0, bytes)
|
out!!.write(buffer, 0, bytes)
|
||||||
copiedSize += bytes
|
copiedSize += bytes
|
||||||
|
mCurrentProgress += bytes
|
||||||
bytes = inputStream.read(buffer)
|
bytes = inputStream.read(buffer)
|
||||||
}
|
}
|
||||||
mCurrentProgress += copiedSize
|
|
||||||
|
|
||||||
if (source.size == copiedSize) {
|
if (source.size == copiedSize) {
|
||||||
mTransferredFiles.add(source)
|
mTransferredFiles.add(source)
|
||||||
|
|
|
@ -12,7 +12,7 @@ import java.io.File
|
||||||
class CreateNewFolderDialog(val activity: BaseSimpleActivity, val path: String, val callback: (path: String) -> Unit) {
|
class CreateNewFolderDialog(val activity: BaseSimpleActivity, val path: String, val callback: (path: String) -> Unit) {
|
||||||
init {
|
init {
|
||||||
val view = activity.layoutInflater.inflate(R.layout.dialog_create_new_folder, null)
|
val view = activity.layoutInflater.inflate(R.layout.dialog_create_new_folder, null)
|
||||||
view.folder_path.text = activity.humanizePath(path).trimEnd('/') + "/"
|
view.folder_path.text = "${activity.humanizePath(path)}/"
|
||||||
|
|
||||||
AlertDialog.Builder(activity)
|
AlertDialog.Builder(activity)
|
||||||
.setPositiveButton(R.string.ok, null)
|
.setPositiveButton(R.string.ok, null)
|
||||||
|
@ -45,9 +45,12 @@ class CreateNewFolderDialog(val activity: BaseSimpleActivity, val path: String,
|
||||||
when {
|
when {
|
||||||
activity.needsStupidWritePermissions(path) -> activity.handleSAFDialog(path) {
|
activity.needsStupidWritePermissions(path) -> activity.handleSAFDialog(path) {
|
||||||
try {
|
try {
|
||||||
val documentFile = activity.getDocumentFile(path)
|
val documentFile = activity.getDocumentFile(path.getParentPath())
|
||||||
documentFile?.createDirectory(path.getFilenameFromPath())
|
if (documentFile?.createDirectory(path.getFilenameFromPath()) != null) {
|
||||||
sendSuccess(alertDialog, path)
|
sendSuccess(alertDialog, path)
|
||||||
|
} else {
|
||||||
|
activity.toast(R.string.unknown_error_occurred)
|
||||||
|
}
|
||||||
} catch (e: SecurityException) {
|
} catch (e: SecurityException) {
|
||||||
activity.showErrorToast(e)
|
activity.showErrorToast(e)
|
||||||
}
|
}
|
||||||
|
|
|
@ -11,18 +11,18 @@ import com.simplemobiletools.commons.extensions.setupDialogStuff
|
||||||
import com.simplemobiletools.commons.helpers.CONFLICT_MERGE
|
import com.simplemobiletools.commons.helpers.CONFLICT_MERGE
|
||||||
import com.simplemobiletools.commons.helpers.CONFLICT_OVERWRITE
|
import com.simplemobiletools.commons.helpers.CONFLICT_OVERWRITE
|
||||||
import com.simplemobiletools.commons.helpers.CONFLICT_SKIP
|
import com.simplemobiletools.commons.helpers.CONFLICT_SKIP
|
||||||
|
import com.simplemobiletools.commons.models.FileDirItem
|
||||||
import kotlinx.android.synthetic.main.dialog_file_conflict.view.*
|
import kotlinx.android.synthetic.main.dialog_file_conflict.view.*
|
||||||
import java.io.File
|
|
||||||
|
|
||||||
class FileConflictDialog(val activity: Activity, val file: File, val callback: (resolution: Int, applyForAll: Boolean) -> Unit) {
|
class FileConflictDialog(val activity: Activity, val fileDirItem: FileDirItem, val callback: (resolution: Int, applyForAll: Boolean) -> Unit) {
|
||||||
val view = activity.layoutInflater.inflate(R.layout.dialog_file_conflict, null)!!
|
val view = activity.layoutInflater.inflate(R.layout.dialog_file_conflict, null)!!
|
||||||
|
|
||||||
init {
|
init {
|
||||||
view.apply {
|
view.apply {
|
||||||
val stringBase = if (file.isDirectory) R.string.folder_already_exists else R.string.file_already_exists
|
val stringBase = if (fileDirItem.isDirectory) R.string.folder_already_exists else R.string.file_already_exists
|
||||||
conflict_dialog_title.text = String.format(activity.getString(stringBase), file.name)
|
conflict_dialog_title.text = String.format(activity.getString(stringBase), fileDirItem.name)
|
||||||
conflict_dialog_apply_to_all.isChecked = activity.baseConfig.lastConflictApplyToAll
|
conflict_dialog_apply_to_all.isChecked = activity.baseConfig.lastConflictApplyToAll
|
||||||
conflict_dialog_radio_merge.beVisibleIf(file.isDirectory)
|
conflict_dialog_radio_merge.beVisibleIf(fileDirItem.isDirectory)
|
||||||
|
|
||||||
val resolutionButton = when (activity.baseConfig.lastConflictResolution) {
|
val resolutionButton = when (activity.baseConfig.lastConflictResolution) {
|
||||||
CONFLICT_OVERWRITE -> conflict_dialog_radio_overwrite
|
CONFLICT_OVERWRITE -> conflict_dialog_radio_overwrite
|
||||||
|
|
|
@ -94,7 +94,7 @@ class FilePickerDialog(val activity: BaseSimpleActivity,
|
||||||
|
|
||||||
private fun createNewFolder() {
|
private fun createNewFolder() {
|
||||||
CreateNewFolderDialog(activity, currPath) {
|
CreateNewFolderDialog(activity, currPath) {
|
||||||
callback(it.trimEnd('/'))
|
callback(it)
|
||||||
mDialog.dismiss()
|
mDialog.dismiss()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,15 +6,16 @@ import android.media.ExifInterface
|
||||||
import android.provider.MediaStore
|
import android.provider.MediaStore
|
||||||
import android.support.v7.app.AlertDialog
|
import android.support.v7.app.AlertDialog
|
||||||
import android.view.LayoutInflater
|
import android.view.LayoutInflater
|
||||||
|
import android.view.View
|
||||||
import android.view.ViewGroup
|
import android.view.ViewGroup
|
||||||
import android.widget.TextView
|
import android.widget.TextView
|
||||||
import com.simplemobiletools.commons.R
|
import com.simplemobiletools.commons.R
|
||||||
import com.simplemobiletools.commons.extensions.*
|
import com.simplemobiletools.commons.extensions.*
|
||||||
import com.simplemobiletools.commons.helpers.sumByInt
|
import com.simplemobiletools.commons.helpers.sumByInt
|
||||||
import com.simplemobiletools.commons.helpers.sumByLong
|
import com.simplemobiletools.commons.helpers.sumByLong
|
||||||
|
import com.simplemobiletools.commons.models.FileDirItem
|
||||||
import kotlinx.android.synthetic.main.dialog_properties.view.*
|
import kotlinx.android.synthetic.main.dialog_properties.view.*
|
||||||
import kotlinx.android.synthetic.main.property_item.view.*
|
import kotlinx.android.synthetic.main.property_item.view.*
|
||||||
import java.io.File
|
|
||||||
import java.io.FileNotFoundException
|
import java.io.FileNotFoundException
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
|
@ -31,28 +32,33 @@ class PropertiesDialog() {
|
||||||
* @param countHiddenItems toggle determining if we will count hidden files themselves and their sizes (reasonable only at directory properties)
|
* @param countHiddenItems toggle determining if we will count hidden files themselves and their sizes (reasonable only at directory properties)
|
||||||
*/
|
*/
|
||||||
constructor(activity: Activity, path: String, countHiddenItems: Boolean = false) : this() {
|
constructor(activity: Activity, path: String, countHiddenItems: Boolean = false) : this() {
|
||||||
|
if (!activity.doesFilePathExist(path)) {
|
||||||
|
activity.toast(String.format(activity.getString(R.string.source_file_doesnt_exist), path))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
mInflater = LayoutInflater.from(activity)
|
mInflater = LayoutInflater.from(activity)
|
||||||
mResources = activity.resources
|
mResources = activity.resources
|
||||||
val view = mInflater.inflate(R.layout.dialog_properties, null)
|
val view = mInflater.inflate(R.layout.dialog_properties, null)
|
||||||
mPropertyView = view.properties_holder
|
mPropertyView = view.properties_holder
|
||||||
|
|
||||||
val file = File(path)
|
val fileDirItem = FileDirItem(path, path.getFilenameFromPath(), activity.getIsPathDirectory(path))
|
||||||
addProperty(R.string.name, file.name)
|
addProperty(R.string.name, fileDirItem.name)
|
||||||
addProperty(R.string.path, file.parent)
|
addProperty(R.string.path, fileDirItem.getParentPath())
|
||||||
addProperty(R.string.size, "…", R.id.properties_size)
|
addProperty(R.string.size, "…", R.id.properties_size)
|
||||||
|
|
||||||
Thread {
|
Thread {
|
||||||
val fileCount = file.getFileCount(countHiddenItems)
|
val fileCount = fileDirItem.getProperFileCount(activity, countHiddenItems)
|
||||||
val size = file.getProperSize(countHiddenItems).formatSize()
|
val size = fileDirItem.getProperSize(activity, countHiddenItems).formatSize()
|
||||||
activity.runOnUiThread {
|
activity.runOnUiThread {
|
||||||
view.findViewById<TextView>(R.id.properties_size).property_value.text = size
|
view.findViewById<TextView>(R.id.properties_size).property_value.text = size
|
||||||
|
|
||||||
if (file.isDirectory) {
|
if (fileDirItem.isDirectory) {
|
||||||
view.findViewById<TextView>(R.id.properties_file_count).property_value.text = fileCount.toString()
|
view.findViewById<TextView>(R.id.properties_file_count).property_value.text = fileCount.toString()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!file.isDirectory) {
|
if (!fileDirItem.isDirectory) {
|
||||||
val projection = arrayOf(MediaStore.Images.Media.DATE_MODIFIED)
|
val projection = arrayOf(MediaStore.Images.Media.DATE_MODIFIED)
|
||||||
val uri = MediaStore.Files.getContentUri("external")
|
val uri = MediaStore.Files.getContentUri("external")
|
||||||
val selection = "${MediaStore.MediaColumns.DATA} = ?"
|
val selection = "${MediaStore.MediaColumns.DATA} = ?"
|
||||||
|
@ -60,37 +66,39 @@ class PropertiesDialog() {
|
||||||
val cursor = activity.contentResolver.query(uri, projection, selection, selectionArgs, null)
|
val cursor = activity.contentResolver.query(uri, projection, selection, selectionArgs, null)
|
||||||
cursor?.use {
|
cursor?.use {
|
||||||
if (cursor.moveToFirst()) {
|
if (cursor.moveToFirst()) {
|
||||||
val dateModified = cursor.getIntValue(MediaStore.Images.Media.DATE_MODIFIED)
|
val dateModified = cursor.getLongValue(MediaStore.Images.Media.DATE_MODIFIED)
|
||||||
activity.runOnUiThread {
|
updateLastModified(activity, view, dateModified)
|
||||||
view.findViewById<TextView>(R.id.properties_last_modified).property_value.text = (dateModified * 1000L).formatDate()
|
} else {
|
||||||
}
|
updateLastModified(activity, view, fileDirItem.getLastModified(activity))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.start()
|
}.start()
|
||||||
|
|
||||||
when {
|
when {
|
||||||
file.isDirectory -> {
|
fileDirItem.isDirectory -> {
|
||||||
addProperty(R.string.direct_children_count, getDirectChildrenCount(file, countHiddenItems))
|
addProperty(R.string.direct_children_count, fileDirItem.getDirectChildrenCount(activity, countHiddenItems).toString())
|
||||||
addProperty(R.string.files_count, "…", R.id.properties_file_count)
|
addProperty(R.string.files_count, "…", R.id.properties_file_count)
|
||||||
}
|
}
|
||||||
file.isImageSlow() -> addProperty(R.string.resolution, file.getResolution().formatAsResolution())
|
fileDirItem.path.isImageSlow() -> {
|
||||||
file.isAudioSlow() -> {
|
fileDirItem.getResolution()?.let { addProperty(R.string.resolution, it.formatAsResolution()) }
|
||||||
file.getDuration().let { addProperty(R.string.duration, it) }
|
|
||||||
file.getSongTitle()?.let { addProperty(R.string.song_title, it) }
|
|
||||||
file.getArtist()?.let { addProperty(R.string.artist, it) }
|
|
||||||
file.getAlbum()?.let { addProperty(R.string.album, it) }
|
|
||||||
}
|
}
|
||||||
file.isVideoSlow() -> {
|
fileDirItem.path.isAudioSlow() -> {
|
||||||
file.getDuration().let { addProperty(R.string.duration, it) }
|
fileDirItem.getDuration()?.let { addProperty(R.string.duration, it) }
|
||||||
addProperty(R.string.resolution, file.getResolution().formatAsResolution())
|
fileDirItem.getSongTitle()?.let { addProperty(R.string.song_title, it) }
|
||||||
file.getArtist()?.let { addProperty(R.string.artist, it) }
|
fileDirItem.getArtist()?.let { addProperty(R.string.artist, it) }
|
||||||
file.getAlbum()?.let { addProperty(R.string.album, it) }
|
fileDirItem.getAlbum()?.let { addProperty(R.string.album, it) }
|
||||||
|
}
|
||||||
|
fileDirItem.path.isVideoSlow() -> {
|
||||||
|
fileDirItem.getDuration()?.let { addProperty(R.string.duration, it) }
|
||||||
|
fileDirItem.getResolution()?.let { addProperty(R.string.resolution, it.formatAsResolution()) }
|
||||||
|
fileDirItem.getArtist()?.let { addProperty(R.string.artist, it) }
|
||||||
|
fileDirItem.getAlbum()?.let { addProperty(R.string.album, it) }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (file.isDirectory) {
|
if (fileDirItem.isDirectory) {
|
||||||
addProperty(R.string.last_modified, file.lastModified().formatDate())
|
addProperty(R.string.last_modified, fileDirItem.getLastModified(activity).formatDate())
|
||||||
} else {
|
} else {
|
||||||
addProperty(R.string.last_modified, "…", R.id.properties_last_modified)
|
addProperty(R.string.last_modified, "…", R.id.properties_last_modified)
|
||||||
try {
|
try {
|
||||||
|
@ -108,6 +116,12 @@ class PropertiesDialog() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun updateLastModified(activity: Activity, view: View, timestamp: Long) {
|
||||||
|
activity.runOnUiThread {
|
||||||
|
view.findViewById<TextView>(R.id.properties_last_modified).property_value.text = timestamp.formatDate()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A File Properties dialog constructor with an optional parameter, usable at multiple items selected
|
* A File Properties dialog constructor with an optional parameter, usable at multiple items selected
|
||||||
*
|
*
|
||||||
|
@ -121,22 +135,25 @@ class PropertiesDialog() {
|
||||||
val view = mInflater.inflate(R.layout.dialog_properties, null)
|
val view = mInflater.inflate(R.layout.dialog_properties, null)
|
||||||
mPropertyView = view.properties_holder
|
mPropertyView = view.properties_holder
|
||||||
|
|
||||||
val files = ArrayList<File>(paths.size)
|
val fileDirItems = ArrayList<FileDirItem>(paths.size)
|
||||||
paths.forEach { files.add(File(it)) }
|
paths.forEach {
|
||||||
|
val fileDirItem = FileDirItem(it, it.getFilenameFromPath(), activity.getIsPathDirectory(it))
|
||||||
|
fileDirItems.add(fileDirItem)
|
||||||
|
}
|
||||||
|
|
||||||
val isSameParent = isSameParent(files)
|
val isSameParent = isSameParent(fileDirItems)
|
||||||
|
|
||||||
addProperty(R.string.items_selected, paths.size.toString())
|
addProperty(R.string.items_selected, paths.size.toString())
|
||||||
if (isSameParent) {
|
if (isSameParent) {
|
||||||
addProperty(R.string.path, files[0].parent)
|
addProperty(R.string.path, fileDirItems[0].getParentPath())
|
||||||
}
|
}
|
||||||
|
|
||||||
addProperty(R.string.size, "…", R.id.properties_size)
|
addProperty(R.string.size, "…", R.id.properties_size)
|
||||||
addProperty(R.string.files_count, "…", R.id.properties_file_count)
|
addProperty(R.string.files_count, "…", R.id.properties_file_count)
|
||||||
|
|
||||||
Thread {
|
Thread {
|
||||||
val fileCount = files.sumByInt { it.getFileCount(countHiddenItems) }
|
val fileCount = fileDirItems.sumByInt { it.getProperFileCount(activity, countHiddenItems) }
|
||||||
val size = files.sumByLong { it.getProperSize(countHiddenItems) }.formatSize()
|
val size = fileDirItems.sumByLong { it.getProperSize(activity, countHiddenItems) }.formatSize()
|
||||||
activity.runOnUiThread {
|
activity.runOnUiThread {
|
||||||
view.findViewById<TextView>(R.id.properties_size).property_value.text = size
|
view.findViewById<TextView>(R.id.properties_size).property_value.text = size
|
||||||
view.findViewById<TextView>(R.id.properties_file_count).property_value.text = fileCount.toString()
|
view.findViewById<TextView>(R.id.properties_file_count).property_value.text = fileCount.toString()
|
||||||
|
@ -168,10 +185,10 @@ class PropertiesDialog() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun isSameParent(files: List<File>): Boolean {
|
private fun isSameParent(fileDirItems: List<FileDirItem>): Boolean {
|
||||||
var parent = files[0].parent
|
var parent = fileDirItems[0].getParentPath()
|
||||||
for (file in files) {
|
for (file in fileDirItems) {
|
||||||
val curParent = file.parent
|
val curParent = file.getParentPath()
|
||||||
if (curParent != parent) {
|
if (curParent != parent) {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
@ -181,14 +198,6 @@ class PropertiesDialog() {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getDirectChildrenCount(file: File, countHiddenItems: Boolean): String {
|
|
||||||
return if (file.listFiles() == null) {
|
|
||||||
"0"
|
|
||||||
} else {
|
|
||||||
file.listFiles().filter { it != null && (!it.isHidden || (it.isHidden && countHiddenItems)) }.size.toString()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun addProperty(labelId: Int, value: String?, viewId: Int = 0) {
|
private fun addProperty(labelId: Int, value: String?, viewId: Int = 0) {
|
||||||
if (value == null)
|
if (value == null)
|
||||||
return
|
return
|
||||||
|
|
|
@ -6,18 +6,16 @@ import com.simplemobiletools.commons.R
|
||||||
import com.simplemobiletools.commons.activities.BaseSimpleActivity
|
import com.simplemobiletools.commons.activities.BaseSimpleActivity
|
||||||
import com.simplemobiletools.commons.extensions.*
|
import com.simplemobiletools.commons.extensions.*
|
||||||
import kotlinx.android.synthetic.main.dialog_rename_item.view.*
|
import kotlinx.android.synthetic.main.dialog_rename_item.view.*
|
||||||
import java.io.File
|
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
class RenameItemDialog(val activity: BaseSimpleActivity, val path: String, val callback: (newPath: String) -> Unit) {
|
class RenameItemDialog(val activity: BaseSimpleActivity, val path: String, val callback: (newPath: String) -> Unit) {
|
||||||
init {
|
init {
|
||||||
val file = File(path)
|
val fullName = path.getFilenameFromPath()
|
||||||
val fullName = file.name
|
|
||||||
val dotAt = fullName.lastIndexOf(".")
|
val dotAt = fullName.lastIndexOf(".")
|
||||||
var name = fullName
|
var name = fullName
|
||||||
|
|
||||||
val view = activity.layoutInflater.inflate(R.layout.dialog_rename_item, null).apply {
|
val view = activity.layoutInflater.inflate(R.layout.dialog_rename_item, null).apply {
|
||||||
if (dotAt > 0 && !file.isDirectory) {
|
if (dotAt > 0 && !activity.getIsPathDirectory(path)) {
|
||||||
name = fullName.substring(0, dotAt)
|
name = fullName.substring(0, dotAt)
|
||||||
val extension = fullName.substring(dotAt + 1)
|
val extension = fullName.substring(dotAt + 1)
|
||||||
rename_item_extension.setText(extension)
|
rename_item_extension.setText(extension)
|
||||||
|
@ -27,7 +25,7 @@ class RenameItemDialog(val activity: BaseSimpleActivity, val path: String, val c
|
||||||
}
|
}
|
||||||
|
|
||||||
rename_item_name.setText(name)
|
rename_item_name.setText(name)
|
||||||
rename_item_path.text = activity.humanizePath(file.parent ?: "") + "/"
|
rename_item_path.text = activity.humanizePath(path.getParentPath())
|
||||||
}
|
}
|
||||||
|
|
||||||
AlertDialog.Builder(activity)
|
AlertDialog.Builder(activity)
|
||||||
|
@ -50,22 +48,29 @@ class RenameItemDialog(val activity: BaseSimpleActivity, val path: String, val c
|
||||||
return@setOnClickListener
|
return@setOnClickListener
|
||||||
}
|
}
|
||||||
|
|
||||||
val updatedFiles = ArrayList<File>()
|
val updatedPaths = ArrayList<String>()
|
||||||
updatedFiles.add(file)
|
updatedPaths.add(path)
|
||||||
if (!newExtension.isEmpty()) {
|
if (!newExtension.isEmpty()) {
|
||||||
newName += ".$newExtension"
|
newName += ".$newExtension"
|
||||||
}
|
}
|
||||||
|
|
||||||
val newFile = File(file.parent, newName)
|
if (!activity.doesFilePathExist(path)) {
|
||||||
if (newFile.exists()) {
|
activity.toast(String.format(activity.getString(R.string.source_file_doesnt_exist), path))
|
||||||
|
return@setOnClickListener
|
||||||
|
}
|
||||||
|
|
||||||
|
val newPath = "${path.getParentPath()}/$newName"
|
||||||
|
if (activity.doesFilePathExist(newPath)) {
|
||||||
activity.toast(R.string.name_taken)
|
activity.toast(R.string.name_taken)
|
||||||
return@setOnClickListener
|
return@setOnClickListener
|
||||||
}
|
}
|
||||||
|
|
||||||
updatedFiles.add(newFile)
|
updatedPaths.add(newPath)
|
||||||
activity.renameFile(path, "${file.parent}/$newName") {
|
activity.renameFile(path, newPath) {
|
||||||
if (it) {
|
if (it) {
|
||||||
sendSuccess(updatedFiles)
|
activity.scanPaths(updatedPaths) {
|
||||||
|
callback(newPath)
|
||||||
|
}
|
||||||
dismiss()
|
dismiss()
|
||||||
} else {
|
} else {
|
||||||
activity.toast(R.string.unknown_error_occurred)
|
activity.toast(R.string.unknown_error_occurred)
|
||||||
|
@ -75,30 +80,4 @@ class RenameItemDialog(val activity: BaseSimpleActivity, val path: String, val c
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun sendSuccess(updatedFiles: ArrayList<File>) {
|
|
||||||
activity.apply {
|
|
||||||
if (updatedFiles[1].isDirectory) {
|
|
||||||
val files = updatedFiles[1].listFiles()
|
|
||||||
if (files != null) {
|
|
||||||
if (files.isEmpty()) {
|
|
||||||
scanPath(updatedFiles[1].absolutePath) {
|
|
||||||
callback(updatedFiles[1].absolutePath.trimEnd('/'))
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
for (file in files) {
|
|
||||||
scanPath(file.absolutePath) {
|
|
||||||
callback(updatedFiles[1].absolutePath.trimEnd('/'))
|
|
||||||
}
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
scanFiles(updatedFiles) {
|
|
||||||
callback(updatedFiles[1].absolutePath.trimEnd('/'))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -452,7 +452,7 @@ fun BaseSimpleActivity.renameFile(oldPath: String, newPath: String, callback: ((
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
val uri = DocumentsContract.renameDocument(applicationContext.contentResolver, document.uri, newPath)
|
val uri = DocumentsContract.renameDocument(applicationContext.contentResolver, document.uri, newPath.getFilenameFromPath())
|
||||||
if (document.uri != uri) {
|
if (document.uri != uri) {
|
||||||
updateInMediaStore(oldPath, newPath)
|
updateInMediaStore(oldPath, newPath)
|
||||||
scanPaths(arrayListOf(oldPath, newPath)) {
|
scanPaths(arrayListOf(oldPath, newPath)) {
|
||||||
|
|
|
@ -98,7 +98,7 @@ fun Context.humanizePath(path: String): String {
|
||||||
val basePath = path.getBasePath(this)
|
val basePath = path.getBasePath(this)
|
||||||
return when (basePath) {
|
return when (basePath) {
|
||||||
"/" -> "${getHumanReadablePath(basePath)}$path"
|
"/" -> "${getHumanReadablePath(basePath)}$path"
|
||||||
OTG_PATH -> path.replaceFirst(basePath, "${getHumanReadablePath(basePath)}/")
|
OTG_PATH -> path.replaceFirst(basePath, getHumanReadablePath(basePath)).replaceFirst("otg://", OTG_PATH).trimEnd('/')
|
||||||
else -> path.replaceFirst(basePath, getHumanReadablePath(basePath))
|
else -> path.replaceFirst(basePath, getHumanReadablePath(basePath))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -357,6 +357,14 @@ fun Context.trySAFFileDelete(fileDirItem: FileDirItem, allowDeleteFolder: Boolea
|
||||||
|
|
||||||
fun Context.doesFilePathExist(path: String) = if (isPathOnOTG(path)) getFastDocumentFile(path)?.exists() ?: false else File(path).exists()
|
fun Context.doesFilePathExist(path: String) = if (isPathOnOTG(path)) getFastDocumentFile(path)?.exists() ?: false else File(path).exists()
|
||||||
|
|
||||||
|
fun Context.getIsPathDirectory(path: String): Boolean {
|
||||||
|
return if (isPathOnOTG(path)) {
|
||||||
|
getFastDocumentFile(path)?.isDirectory ?: false
|
||||||
|
} else {
|
||||||
|
File(path).isDirectory
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// avoid these being set as SD card paths
|
// avoid these being set as SD card paths
|
||||||
private val physicalPaths = arrayListOf(
|
private val physicalPaths = arrayListOf(
|
||||||
"/storage/sdcard1", // Motorola Xoom
|
"/storage/sdcard1", // Motorola Xoom
|
||||||
|
|
|
@ -27,3 +27,29 @@ private fun getDirectorySize(dir: DocumentFile, countHiddenItems: Boolean): Long
|
||||||
}
|
}
|
||||||
return size
|
return size
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun DocumentFile.getFileCount(countHiddenItems: Boolean): Int {
|
||||||
|
return if (isDirectory) {
|
||||||
|
getDirectoryFileCount(this, countHiddenItems)
|
||||||
|
} else {
|
||||||
|
1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun getDirectoryFileCount(dir: DocumentFile, countHiddenItems: Boolean): Int {
|
||||||
|
var count = 0
|
||||||
|
if (dir.exists()) {
|
||||||
|
val files = dir.listFiles()
|
||||||
|
if (files != null) {
|
||||||
|
for (i in files.indices) {
|
||||||
|
val file = files[i]
|
||||||
|
if (file.isDirectory) {
|
||||||
|
count += getDirectoryFileCount(file, countHiddenItems)
|
||||||
|
} else if (!file.name.startsWith(".") || countHiddenItems) {
|
||||||
|
count++
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return count
|
||||||
|
}
|
||||||
|
|
|
@ -2,9 +2,6 @@ package com.simplemobiletools.commons.extensions
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import android.graphics.Bitmap
|
import android.graphics.Bitmap
|
||||||
import android.graphics.BitmapFactory
|
|
||||||
import android.graphics.Point
|
|
||||||
import android.media.MediaMetadataRetriever
|
|
||||||
import com.simplemobiletools.commons.models.FileDirItem
|
import com.simplemobiletools.commons.models.FileDirItem
|
||||||
import java.io.File
|
import java.io.File
|
||||||
|
|
||||||
|
@ -20,80 +17,6 @@ fun File.isAudioSlow() = absolutePath.isAudioFast() || getMimeType().startsWith(
|
||||||
|
|
||||||
fun File.getMimeType() = absolutePath.getMimeTypeFromPath()
|
fun File.getMimeType() = absolutePath.getMimeTypeFromPath()
|
||||||
|
|
||||||
fun File.getDuration() = getDurationSeconds().getFormattedDuration()
|
|
||||||
|
|
||||||
fun File.getDurationSeconds(): Int {
|
|
||||||
return try {
|
|
||||||
val retriever = MediaMetadataRetriever()
|
|
||||||
retriever.setDataSource(absolutePath)
|
|
||||||
val time = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION)
|
|
||||||
val timeInMs = java.lang.Long.parseLong(time)
|
|
||||||
(timeInMs / 1000).toInt()
|
|
||||||
} catch (e: Exception) {
|
|
||||||
0
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun File.getArtist(): String? {
|
|
||||||
return try {
|
|
||||||
val retriever = MediaMetadataRetriever()
|
|
||||||
retriever.setDataSource(absolutePath)
|
|
||||||
retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_ARTIST)
|
|
||||||
} catch (ignored: Exception) {
|
|
||||||
null
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun File.getAlbum(): String? {
|
|
||||||
return try {
|
|
||||||
val retriever = MediaMetadataRetriever()
|
|
||||||
retriever.setDataSource(absolutePath)
|
|
||||||
retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_ALBUM)
|
|
||||||
} catch (ignored: Exception) {
|
|
||||||
null
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun File.getSongTitle(): String? {
|
|
||||||
return try {
|
|
||||||
val retriever = MediaMetadataRetriever()
|
|
||||||
retriever.setDataSource(absolutePath)
|
|
||||||
retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_TITLE)
|
|
||||||
} catch (ignored: Exception) {
|
|
||||||
null
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun File.getResolution(): Point {
|
|
||||||
return if (isImageFast() || isImageSlow()) {
|
|
||||||
getImageResolution()
|
|
||||||
} else if (isVideoFast() || isVideoSlow()) {
|
|
||||||
getVideoResolution()
|
|
||||||
} else {
|
|
||||||
return Point(0, 0)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fun File.getVideoResolution(): Point {
|
|
||||||
try {
|
|
||||||
val retriever = MediaMetadataRetriever()
|
|
||||||
retriever.setDataSource(absolutePath)
|
|
||||||
val width = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_WIDTH).toInt()
|
|
||||||
val height = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_HEIGHT).toInt()
|
|
||||||
return Point(width, height)
|
|
||||||
} catch (ignored: Exception) {
|
|
||||||
|
|
||||||
}
|
|
||||||
return Point(0, 0)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun File.getImageResolution(): Point {
|
|
||||||
val options = BitmapFactory.Options()
|
|
||||||
options.inJustDecodeBounds = true
|
|
||||||
BitmapFactory.decodeFile(absolutePath, options)
|
|
||||||
return Point(options.outWidth, options.outHeight)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun File.getCompressionFormat() = when (extension.toLowerCase()) {
|
fun File.getCompressionFormat() = when (extension.toLowerCase()) {
|
||||||
"png" -> Bitmap.CompressFormat.PNG
|
"png" -> Bitmap.CompressFormat.PNG
|
||||||
"webp" -> Bitmap.CompressFormat.WEBP
|
"webp" -> Bitmap.CompressFormat.WEBP
|
||||||
|
@ -102,7 +25,7 @@ fun File.getCompressionFormat() = when (extension.toLowerCase()) {
|
||||||
|
|
||||||
fun File.getProperSize(countHiddenItems: Boolean): Long {
|
fun File.getProperSize(countHiddenItems: Boolean): Long {
|
||||||
return if (isDirectory) {
|
return if (isDirectory) {
|
||||||
getDirectorySize(File(path), countHiddenItems)
|
getDirectorySize(this, countHiddenItems)
|
||||||
} else {
|
} else {
|
||||||
length()
|
length()
|
||||||
}
|
}
|
||||||
|
@ -127,7 +50,7 @@ private fun getDirectorySize(dir: File, countHiddenItems: Boolean): Long {
|
||||||
|
|
||||||
fun File.getFileCount(countHiddenItems: Boolean): Int {
|
fun File.getFileCount(countHiddenItems: Boolean): Int {
|
||||||
return if (isDirectory) {
|
return if (isDirectory) {
|
||||||
getDirectoryFileCount(File(path), countHiddenItems)
|
getDirectoryFileCount(this, countHiddenItems)
|
||||||
} else {
|
} else {
|
||||||
1
|
1
|
||||||
}
|
}
|
||||||
|
@ -151,4 +74,4 @@ private fun getDirectoryFileCount(dir: File, countHiddenItems: Boolean): Int {
|
||||||
return count
|
return count
|
||||||
}
|
}
|
||||||
|
|
||||||
fun File.toFileDirItem(context: Context) = FileDirItem(absolutePath, name, absolutePath.getIsDirectory(context), 0, 0L)
|
fun File.toFileDirItem(context: Context) = FileDirItem(absolutePath, name, context.getIsPathDirectory(absolutePath), 0, 0L)
|
||||||
|
|
|
@ -1,9 +1,11 @@
|
||||||
package com.simplemobiletools.commons.extensions
|
package com.simplemobiletools.commons.extensions
|
||||||
|
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
|
import android.graphics.BitmapFactory
|
||||||
|
import android.graphics.Point
|
||||||
import android.media.ExifInterface
|
import android.media.ExifInterface
|
||||||
|
import android.media.MediaMetadataRetriever
|
||||||
import com.simplemobiletools.commons.helpers.OTG_PATH
|
import com.simplemobiletools.commons.helpers.OTG_PATH
|
||||||
import java.io.File
|
|
||||||
import java.text.SimpleDateFormat
|
import java.text.SimpleDateFormat
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
|
@ -126,11 +128,83 @@ fun String.getGenericMimeType(): String {
|
||||||
|
|
||||||
fun String.getParentPath() = substring(0, length - getFilenameFromPath().length)
|
fun String.getParentPath() = substring(0, length - getFilenameFromPath().length)
|
||||||
|
|
||||||
fun String.getIsDirectory(context: Context): Boolean {
|
fun String.getDuration() = getFileDurationSeconds()?.getFormattedDuration()
|
||||||
return if (context.isPathOnOTG(this)) {
|
|
||||||
context.getFastDocumentFile(this)?.isDirectory ?: false
|
fun String.getFileDurationSeconds(): Int? {
|
||||||
|
return try {
|
||||||
|
val retriever = MediaMetadataRetriever()
|
||||||
|
retriever.setDataSource(this)
|
||||||
|
val time = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION)
|
||||||
|
val timeInMs = java.lang.Long.parseLong(time)
|
||||||
|
(timeInMs / 1000).toInt()
|
||||||
|
} catch (e: Exception) {
|
||||||
|
null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun String.getFileArtist(): String? {
|
||||||
|
return try {
|
||||||
|
val retriever = MediaMetadataRetriever()
|
||||||
|
retriever.setDataSource(this)
|
||||||
|
retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_ARTIST)
|
||||||
|
} catch (ignored: Exception) {
|
||||||
|
null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun String.getFileAlbum(): String? {
|
||||||
|
return try {
|
||||||
|
val retriever = MediaMetadataRetriever()
|
||||||
|
retriever.setDataSource(this)
|
||||||
|
retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_ALBUM)
|
||||||
|
} catch (ignored: Exception) {
|
||||||
|
null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun String.getFileSongTitle(): String? {
|
||||||
|
return try {
|
||||||
|
val retriever = MediaMetadataRetriever()
|
||||||
|
retriever.setDataSource(this)
|
||||||
|
retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_TITLE)
|
||||||
|
} catch (ignored: Exception) {
|
||||||
|
null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun String.getResolution(): Point? {
|
||||||
|
return if (isImageFast() || isImageSlow()) {
|
||||||
|
getImageResolution()
|
||||||
|
} else if (isVideoFast() || isVideoSlow()) {
|
||||||
|
getVideoResolution()
|
||||||
} else {
|
} else {
|
||||||
File(this).isDirectory
|
return null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun String.getVideoResolution(): Point? {
|
||||||
|
try {
|
||||||
|
val retriever = MediaMetadataRetriever()
|
||||||
|
retriever.setDataSource(this)
|
||||||
|
val width = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_WIDTH).toInt()
|
||||||
|
val height = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_HEIGHT).toInt()
|
||||||
|
return Point(width, height)
|
||||||
|
} catch (ignored: Exception) {
|
||||||
|
|
||||||
|
}
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
fun String.getImageResolution(): Point? {
|
||||||
|
val options = BitmapFactory.Options()
|
||||||
|
options.inJustDecodeBounds = true
|
||||||
|
BitmapFactory.decodeFile(this, options)
|
||||||
|
val width = options.outWidth
|
||||||
|
val height = options.outHeight
|
||||||
|
return if (width > 0 && height > 0) {
|
||||||
|
Point(options.outWidth, options.outHeight)
|
||||||
|
} else {
|
||||||
|
null
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -63,5 +63,45 @@ data class FileDirItem(val path: String, val name: String = "", var isDirectory:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun getProperFileCount(context: Context, countHidden: Boolean): Int {
|
||||||
|
return if (context.isPathOnOTG(path)) {
|
||||||
|
context.getDocumentFile(path)?.getFileCount(countHidden) ?: 0
|
||||||
|
} else {
|
||||||
|
File(path).getFileCount(countHidden)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getDirectChildrenCount(context: Context, countHiddenItems: Boolean): Int {
|
||||||
|
return if (context.isPathOnOTG(path)) {
|
||||||
|
context.getDocumentFile(path)?.listFiles()?.filter { if (countHiddenItems) true else !it.name.startsWith(".") }?.size ?: 0
|
||||||
|
} else {
|
||||||
|
File(path).listFiles().filter { if (countHiddenItems) true else it.isHidden }.size
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getLastModified(context: Context): Long {
|
||||||
|
return if (context.isPathOnOTG(path)) {
|
||||||
|
context.getFastDocumentFile(path)?.lastModified() ?: 0L
|
||||||
|
} else {
|
||||||
|
File(path).lastModified()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fun getParentPath() = path.getParentPath()
|
fun getParentPath() = path.getParentPath()
|
||||||
|
|
||||||
|
fun getDuration() = path.getDuration()
|
||||||
|
|
||||||
|
fun getFileDurationSeconds() = path.getFileDurationSeconds()
|
||||||
|
|
||||||
|
fun getArtist() = path.getFileArtist()
|
||||||
|
|
||||||
|
fun getAlbum() = path.getFileAlbum()
|
||||||
|
|
||||||
|
fun getSongTitle() = path.getFileSongTitle()
|
||||||
|
|
||||||
|
fun getResolution() = path.getResolution()
|
||||||
|
|
||||||
|
fun getVideoResolution() = path.getVideoResolution()
|
||||||
|
|
||||||
|
fun getImageResolution() = path.getImageResolution()
|
||||||
}
|
}
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">El nom de l\'arxiu no pot ser buit</string>
|
<string name="filename_cannot_be_empty">El nom de l\'arxiu no pot ser buit</string>
|
||||||
<string name="filename_invalid_characters">El nom de l\'arxiu conté caràcters no vàlids</string>
|
<string name="filename_invalid_characters">El nom de l\'arxiu conté caràcters no vàlids</string>
|
||||||
<string name="extension_cannot_be_empty">La extensió no pot estar buida</string>
|
<string name="extension_cannot_be_empty">La extensió no pot estar buida</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copiar</string>
|
<string name="copy">Copiar</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Název souboru nemůže být prázdný</string>
|
<string name="filename_cannot_be_empty">Název souboru nemůže být prázdný</string>
|
||||||
<string name="filename_invalid_characters">Název souboru obsahuje neplatné znaky</string>
|
<string name="filename_invalid_characters">Název souboru obsahuje neplatné znaky</string>
|
||||||
<string name="extension_cannot_be_empty">Přípona nemůže být prázdná</string>
|
<string name="extension_cannot_be_empty">Přípona nemůže být prázdná</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopírovat</string>
|
<string name="copy">Kopírovat</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Filen skal have et navn</string>
|
<string name="filename_cannot_be_empty">Filen skal have et navn</string>
|
||||||
<string name="filename_invalid_characters">Filnavnet indeholder ugyldige tegn</string>
|
<string name="filename_invalid_characters">Filnavnet indeholder ugyldige tegn</string>
|
||||||
<string name="extension_cannot_be_empty">Filtypen kan ikke stå tom</string>
|
<string name="extension_cannot_be_empty">Filtypen kan ikke stå tom</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopier</string>
|
<string name="copy">Kopier</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Dateiname darf nicht leer sein</string>
|
<string name="filename_cannot_be_empty">Dateiname darf nicht leer sein</string>
|
||||||
<string name="filename_invalid_characters">Dateiname enthält ungültige Zeichen</string>
|
<string name="filename_invalid_characters">Dateiname enthält ungültige Zeichen</string>
|
||||||
<string name="extension_cannot_be_empty">Dateiendung darf nicht leer sein</string>
|
<string name="extension_cannot_be_empty">Dateiendung darf nicht leer sein</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopieren</string>
|
<string name="copy">Kopieren</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">El nombre de archivo no puede estar vacío</string>
|
<string name="filename_cannot_be_empty">El nombre de archivo no puede estar vacío</string>
|
||||||
<string name="filename_invalid_characters">El nombre archivo contiene caracteres no válidos</string>
|
<string name="filename_invalid_characters">El nombre archivo contiene caracteres no válidos</string>
|
||||||
<string name="extension_cannot_be_empty">La extensión no puede estar vacía</string>
|
<string name="extension_cannot_be_empty">La extensión no puede estar vacía</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copiar</string>
|
<string name="copy">Copiar</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
||||||
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
||||||
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copy</string>
|
<string name="copy">Copy</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Le nom de fichier ne peut pas rester vide</string>
|
<string name="filename_cannot_be_empty">Le nom de fichier ne peut pas rester vide</string>
|
||||||
<string name="filename_invalid_characters">Le nom de fichier contient des caractères invalides</string>
|
<string name="filename_invalid_characters">Le nom de fichier contient des caractères invalides</string>
|
||||||
<string name="extension_cannot_be_empty">L\'extension ne peut pas rester vide</string>
|
<string name="extension_cannot_be_empty">L\'extension ne peut pas rester vide</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copier</string>
|
<string name="copy">Copier</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
||||||
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
||||||
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copy</string>
|
<string name="copy">Copy</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Naziv datoteke ne smije biti prazan</string>
|
<string name="filename_cannot_be_empty">Naziv datoteke ne smije biti prazan</string>
|
||||||
<string name="filename_invalid_characters">Naziv datoteke sadrži ne podržane znakove</string>
|
<string name="filename_invalid_characters">Naziv datoteke sadrži ne podržane znakove</string>
|
||||||
<string name="extension_cannot_be_empty">Ekstenzija ne smije biti prazna</string>
|
<string name="extension_cannot_be_empty">Ekstenzija ne smije biti prazna</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopiraj</string>
|
<string name="copy">Kopiraj</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
||||||
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
||||||
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copy</string>
|
<string name="copy">Copy</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Nama File Tidak Boleh Kosong</string>
|
<string name="filename_cannot_be_empty">Nama File Tidak Boleh Kosong</string>
|
||||||
<string name="filename_invalid_characters">Nama mengandung Karakter Tidak Di Dukung</string>
|
<string name="filename_invalid_characters">Nama mengandung Karakter Tidak Di Dukung</string>
|
||||||
<string name="extension_cannot_be_empty">Extension Tidak Boleh Kosong</string>
|
<string name="extension_cannot_be_empty">Extension Tidak Boleh Kosong</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Salin</string>
|
<string name="copy">Salin</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Il nome del file non deve essere vuoto</string>
|
<string name="filename_cannot_be_empty">Il nome del file non deve essere vuoto</string>
|
||||||
<string name="filename_invalid_characters">Il nome contiene caratteri non validi</string>
|
<string name="filename_invalid_characters">Il nome contiene caratteri non validi</string>
|
||||||
<string name="extension_cannot_be_empty">L\'estensione non può essere vuota</string>
|
<string name="extension_cannot_be_empty">L\'estensione non può essere vuota</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copia</string>
|
<string name="copy">Copia</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">ファイル名は空にできません</string>
|
<string name="filename_cannot_be_empty">ファイル名は空にできません</string>
|
||||||
<string name="filename_invalid_characters">ファイル名に無効な文字が含まれています</string>
|
<string name="filename_invalid_characters">ファイル名に無効な文字が含まれています</string>
|
||||||
<string name="extension_cannot_be_empty">拡張子は省略できません</string>
|
<string name="extension_cannot_be_empty">拡張子は省略できません</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">コピー</string>
|
<string name="copy">コピー</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">파일명이 비어있으면 안됨</string>
|
<string name="filename_cannot_be_empty">파일명이 비어있으면 안됨</string>
|
||||||
<string name="filename_invalid_characters">파일명에 사용할 수 없는 문자가 포함됨</string>
|
<string name="filename_invalid_characters">파일명에 사용할 수 없는 문자가 포함됨</string>
|
||||||
<string name="extension_cannot_be_empty">확장자가 비어있으면 안됨</string>
|
<string name="extension_cannot_be_empty">확장자가 비어있으면 안됨</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">복사</string>
|
<string name="copy">복사</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Failo pavadinimas negali bûti paliktas tusèias</string>
|
<string name="filename_cannot_be_empty">Failo pavadinimas negali bûti paliktas tusèias</string>
|
||||||
<string name="filename_invalid_characters">Failo varde yra negalimø simboliø</string>
|
<string name="filename_invalid_characters">Failo varde yra negalimø simboliø</string>
|
||||||
<string name="extension_cannot_be_empty">Papildinys negali bûti paliktas tuðèias</string>
|
<string name="extension_cannot_be_empty">Papildinys negali bûti paliktas tuðèias</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopijuoti</string>
|
<string name="copy">Kopijuoti</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
||||||
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
||||||
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopier</string>
|
<string name="copy">Kopier</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Bestandsnaam mag niet leeg zijn</string>
|
<string name="filename_cannot_be_empty">Bestandsnaam mag niet leeg zijn</string>
|
||||||
<string name="filename_invalid_characters">Bestandsnaam bevat ongeldige tekens</string>
|
<string name="filename_invalid_characters">Bestandsnaam bevat ongeldige tekens</string>
|
||||||
<string name="extension_cannot_be_empty">Extensie mag niet leeg zijn</string>
|
<string name="extension_cannot_be_empty">Extensie mag niet leeg zijn</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopiëren</string>
|
<string name="copy">Kopiëren</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
||||||
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
||||||
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopier</string>
|
<string name="copy">Kopier</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Nazwa pliku nie może być pusta</string>
|
<string name="filename_cannot_be_empty">Nazwa pliku nie może być pusta</string>
|
||||||
<string name="filename_invalid_characters">Nazwa pliku zawiera niedozwolone znaki</string>
|
<string name="filename_invalid_characters">Nazwa pliku zawiera niedozwolone znaki</string>
|
||||||
<string name="extension_cannot_be_empty">Rozszerzenie pliku nie może być puste</string>
|
<string name="extension_cannot_be_empty">Rozszerzenie pliku nie może być puste</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopiuj</string>
|
<string name="copy">Kopiuj</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">O nome do arquivo não pode ficar em branco</string>
|
<string name="filename_cannot_be_empty">O nome do arquivo não pode ficar em branco</string>
|
||||||
<string name="filename_invalid_characters">O nome do arquivo contém caracteres inválidos</string>
|
<string name="filename_invalid_characters">O nome do arquivo contém caracteres inválidos</string>
|
||||||
<string name="extension_cannot_be_empty">A extensão não pode ficar em branco</string>
|
<string name="extension_cannot_be_empty">A extensão não pode ficar em branco</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copiar</string>
|
<string name="copy">Copiar</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">O nome do ficheiro não pode estar vazio</string>
|
<string name="filename_cannot_be_empty">O nome do ficheiro não pode estar vazio</string>
|
||||||
<string name="filename_invalid_characters">O nome do ficheiro contém caracteres inválidos</string>
|
<string name="filename_invalid_characters">O nome do ficheiro contém caracteres inválidos</string>
|
||||||
<string name="extension_cannot_be_empty">A extensão não pode estar vazia</string>
|
<string name="extension_cannot_be_empty">A extensão não pode estar vazia</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copiar</string>
|
<string name="copy">Copiar</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Имя файла не может быть пустым</string>
|
<string name="filename_cannot_be_empty">Имя файла не может быть пустым</string>
|
||||||
<string name="filename_invalid_characters">Имя файла содержит недопустимые символы</string>
|
<string name="filename_invalid_characters">Имя файла содержит недопустимые символы</string>
|
||||||
<string name="extension_cannot_be_empty">Расширение не может быть пустым</string>
|
<string name="extension_cannot_be_empty">Расширение не может быть пустым</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Копировать</string>
|
<string name="copy">Копировать</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Názov súboru nemôže byť prázdny</string>
|
<string name="filename_cannot_be_empty">Názov súboru nemôže byť prázdny</string>
|
||||||
<string name="filename_invalid_characters">Názov súboru obsahuje neplatné znaky</string>
|
<string name="filename_invalid_characters">Názov súboru obsahuje neplatné znaky</string>
|
||||||
<string name="extension_cannot_be_empty">Prípona nesmie byť prázdna</string>
|
<string name="extension_cannot_be_empty">Prípona nesmie byť prázdna</string>
|
||||||
|
<string name="source_file_doesnt_exist">Zdrojový súbor %s neexistuje</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopírovať</string>
|
<string name="copy">Kopírovať</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Du måste ange ett filnamn</string>
|
<string name="filename_cannot_be_empty">Du måste ange ett filnamn</string>
|
||||||
<string name="filename_invalid_characters">Filnamnet innehåller ogiltiga tecken</string>
|
<string name="filename_invalid_characters">Filnamnet innehåller ogiltiga tecken</string>
|
||||||
<string name="extension_cannot_be_empty">Filändelsen får inte vara tom</string>
|
<string name="extension_cannot_be_empty">Filändelsen får inte vara tom</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopiera</string>
|
<string name="copy">Kopiera</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Dosya adı boş olamaz</string>
|
<string name="filename_cannot_be_empty">Dosya adı boş olamaz</string>
|
||||||
<string name="filename_invalid_characters">Dosya adı geçersiz karakterler içeriyor</string>
|
<string name="filename_invalid_characters">Dosya adı geçersiz karakterler içeriyor</string>
|
||||||
<string name="extension_cannot_be_empty">Uzantı boş olamaz</string>
|
<string name="extension_cannot_be_empty">Uzantı boş olamaz</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Kopyala</string>
|
<string name="copy">Kopyala</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">文件名不能为空</string>
|
<string name="filename_cannot_be_empty">文件名不能为空</string>
|
||||||
<string name="filename_invalid_characters">文件名包含非法字符</string>
|
<string name="filename_invalid_characters">文件名包含非法字符</string>
|
||||||
<string name="extension_cannot_be_empty">扩展名不能为空</string>
|
<string name="extension_cannot_be_empty">扩展名不能为空</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">复制</string>
|
<string name="copy">复制</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">檔名不得空白</string>
|
<string name="filename_cannot_be_empty">檔名不得空白</string>
|
||||||
<string name="filename_invalid_characters">檔名包含無效字符</string>
|
<string name="filename_invalid_characters">檔名包含無效字符</string>
|
||||||
<string name="extension_cannot_be_empty">副檔名不得空白</string>
|
<string name="extension_cannot_be_empty">副檔名不得空白</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">複製</string>
|
<string name="copy">複製</string>
|
||||||
|
|
|
@ -43,6 +43,7 @@
|
||||||
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
<string name="filename_cannot_be_empty">Filename cannot be empty</string>
|
||||||
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
<string name="filename_invalid_characters">Filename contains invalid characters</string>
|
||||||
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
<string name="extension_cannot_be_empty">Extension cannot be empty</string>
|
||||||
|
<string name="source_file_doesnt_exist">Source file %s doesn\'t exist</string>
|
||||||
|
|
||||||
<!-- Copy / Move -->
|
<!-- Copy / Move -->
|
||||||
<string name="copy">Copy</string>
|
<string name="copy">Copy</string>
|
||||||
|
|
Loading…
Reference in a new issue