using afIoc
using afReflux
using gfx
using fwt
** (Service) -
** The main service API for Explorer operations.
mixin Explorer {
abstract Void rename(File file)
abstract Void delete(File file)
abstract Void cut(File file)
abstract Void copy(File file)
abstract Void paste(File destDir)
abstract Void newFile(File containingFolder)
abstract Void newFolder(File containingFolder)
abstract Void openFileInSystem(File file)
abstract Image fileToIcon(File f)
abstract Image urlToIcon(Uri url)
abstract ExplorerPrefs preferences()
}
internal class ExplorerImpl : Explorer {
@Inject private Registry registry
@Inject private RefluxIcons icons
@Inject private Images images
@Inject private Preferences prefs
@Inject private Reflux reflux
Uri fileIconsRoot := `fan://afExplorer/res/icons-file/`
private File? copiedFile
private File? cutFile
new make(|This| in) { in(this) }
override Void rename(File file) {
newName := Dialog.openPromptStr(reflux.window, "Rename", file.name)
if (newName != null) {
file.rename(newName)
reflux.refresh
}
}
override Void delete(File file) {
okay := Dialog.openQuestion(reflux.window, "Delete ${file.osPath}?", null, Dialog.yesNo)
if (okay == Dialog.yes) {
file.delete
reflux.refresh
}
}
override Void cut(File file) {
cutFile = file
copiedFile = null
}
override Void copy(File file) {
cutFile = null
copiedFile = file
}
override Void paste(File destDir) {
// TODO: dialog for copy overwrite options
if (cutFile != null) {
cutFile.moveInto(destDir)
cutFile = null
}
if (copiedFile != null) {
copiedFile.copyInto(destDir)
copiedFile = null
}
reflux := (Reflux) registry.serviceById(Reflux#.qname)
reflux.refresh
}
override Void newFile(File containingFolder) {
fileName := Dialog.openPromptStr(reflux.window, "New File", "NewFile.txt")
if (fileName != null) {
containingFolder.createFile(fileName)
reflux.refresh
}
}
override Void newFolder(File containingFolder) {
dirName := Dialog.openPromptStr(reflux.window, "New Folder", "NewFolder")
if (dirName != null) {
containingFolder.createDir(dirName)
reflux.refresh
}
}
override Void openFileInSystem(File file) {
Desktop.launchProgram(file.uri)
}
override Image fileToIcon(File f) {
hidden := preferences.isHidden(f)
if (f.isDir) {
// can't cache osRoots 'cos it changes with flash drives et al
osRoots := File.osRoots.map { it.normalize }
name := osRoots.contains(f) ? "icoFolderRoot" : "icoFolder"
return hidden ? icons.getFaded(name) : icons.get(name)
}
// look for explicit match based off ext
if (f.ext != null) {
icon := fileIcon("file${f.ext.capitalize}.png", hidden)
if (icon != null) return icon
}
mimeType := f.mimeType?.noParams
if (mimeType != null) {
mime := mimeType.mediaType.fromDisplayName.capitalize + mimeType.subType.fromDisplayName.capitalize
icon := fileIcon("file${mime}.png", hidden)
if (icon != null) return icon
mime = mimeType.mediaType.fromDisplayName.capitalize
icon = fileIcon("file${mime}.png", hidden)
if (icon != null) return icon
}
return fileIcon("file.png", hidden)
}
override Image urlToIcon(Uri url) {
// look for explicit match based off ext
if (url.ext != null) {
icon := fileIcon("file${url.ext.capitalize}.png", false)
if (icon != null) return icon
}
mimeType := url.mimeType?.noParams
if (mimeType != null) {
mime := mimeType.mediaType.fromDisplayName.capitalize + mimeType.subType.fromDisplayName.capitalize
icon := fileIcon("file${mime}.png", false)
if (icon != null) return icon
mime = mimeType.mediaType.fromDisplayName.capitalize
icon = fileIcon("file${mime}.png", false)
if (icon != null) return icon
}
return fileIcon("fileTextHtml.png", false)
}
override once ExplorerPrefs preferences() {
prefs.loadPrefs(ExplorerPrefs#)
}
private Image? fileIcon(Str fileName, Bool hidden) {
uri := fileIconsRoot.plusName(fileName)
return hidden ? images.getFaded(uri, false) : images.get(uri, false)
}
}