forked from conaticus/FileExplorer
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
15 changed files
with
239 additions
and
108 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,59 @@ | ||
use std::fs; | ||
use std::fs::read_dir; | ||
use crate::errors::Error; | ||
use crate::filesystem::volume::DirectoryChild; | ||
use crate::filesystem::volume::DirectoryChild::File; | ||
|
||
/// Opens a file at the given path. Returns a string if there was an error. | ||
// NOTE(conaticus): I tried handling the errors nicely here but Tauri was mega cringe and wouldn't let me nest results in async functions, so used string error messages instead. | ||
#[tauri::command] | ||
pub async fn open_file(path: String) -> Result<(), Error> { | ||
let output_res = open::commands(path)[0].output(); | ||
let output = match output_res { | ||
Ok(output) => output, | ||
Err(err) => { | ||
let err_msg = format!("Failed to get open command output: {}", err); | ||
return Err(Error::Custom(err_msg)); | ||
} | ||
}; | ||
|
||
if output.status.success() { | ||
return Ok(()); | ||
} | ||
|
||
let err_msg = String::from_utf8(output.stderr).unwrap_or(String::from("Failed to open file and deserialize stderr.")); | ||
Err(Error::Custom(err_msg)) | ||
} | ||
|
||
/// Searches and returns the files in a given directory. This is not recursive. | ||
#[tauri::command] | ||
pub async fn open_directory(path: String) -> Result<Vec<DirectoryChild>, ()> { | ||
let Ok(directory) = read_dir(path) else { | ||
return Ok(Vec::new()); | ||
}; | ||
|
||
Ok(directory | ||
.map(|entry| { | ||
let entry = entry.unwrap(); | ||
|
||
let file_name = entry.file_name().to_string_lossy().to_string(); | ||
let entry_is_file = entry.file_type().unwrap().is_file(); | ||
let entry = entry.path().to_string_lossy().to_string(); | ||
|
||
if entry_is_file { | ||
return DirectoryChild::File(file_name, entry); | ||
} | ||
|
||
DirectoryChild::Directory(file_name, entry) | ||
}) | ||
.collect()) | ||
} | ||
|
||
#[tauri::command] | ||
pub async fn create_file(path: String) -> Result<(), Error> { | ||
let res = fs::File::create(path); | ||
match res { | ||
Ok(_) => Ok(()), | ||
Err(err) => Err(Error::Custom(err.to_string())), | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,58 +1,10 @@ | ||
pub mod explorer; | ||
pub mod cache; | ||
pub mod volume; | ||
|
||
use crate::filesystem::volume::DirectoryChild; | ||
use std::fs::read_dir; | ||
use crate::errors::Error; | ||
|
||
pub const DIRECTORY: &str = "directory"; | ||
pub const FILE: &str = "file"; | ||
|
||
pub const fn bytes_to_gb(bytes: u64) -> u16 { | ||
(bytes / (1e+9 as u64)) as u16 | ||
} | ||
|
||
/// Opens a file at the given path. Returns a string if there was an error. | ||
// NOTE(conaticus): I tried handling the errors nicely here but Tauri was mega cringe and wouldn't let me nest results in async functions, so used string error messages instead. | ||
#[tauri::command] | ||
pub async fn open_file(path: String) -> Result<(), Error> { | ||
let output_res = open::commands(path)[0].output(); | ||
let output = match output_res { | ||
Ok(output) => output, | ||
Err(err) => { | ||
let err_msg = format!("Failed to get open command output: {}", err); | ||
return Err(Error::Custom(err_msg)); | ||
} | ||
}; | ||
|
||
if output.status.success() { | ||
return Ok(()); | ||
} | ||
|
||
let err_msg = String::from_utf8(output.stderr).unwrap_or(String::from("Failed to open file and deserialize stderr.")); | ||
Err(Error::Custom(err_msg)) | ||
} | ||
|
||
/// Searches and returns the files in a given directory. This is not recursive. | ||
#[tauri::command] | ||
pub async fn open_directory(path: String) -> Result<Vec<DirectoryChild>, ()> { | ||
let Ok(directory) = read_dir(path) else { | ||
return Ok(Vec::new()); | ||
}; | ||
|
||
Ok(directory | ||
.map(|entry| { | ||
let entry = entry.unwrap(); | ||
|
||
let file_name = entry.file_name().to_string_lossy().to_string(); | ||
let entry_is_file = entry.file_type().unwrap().is_file(); | ||
let entry = entry.path().to_string_lossy().to_string(); | ||
|
||
if entry_is_file { | ||
return DirectoryChild::File(file_name, entry); | ||
} | ||
|
||
DirectoryChild::Directory(file_name, entry) | ||
}) | ||
.collect()) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,24 +1,72 @@ | ||
import {ContextMenuType} from "../../types"; | ||
import {ContextMenuType, DirectoryContent} from "../../types"; | ||
import ContextMenu from "./ContextMenu"; | ||
import {useAppSelector} from "../../state/hooks"; | ||
import {selectCurrentContextMenu} from "../../state/slices/contextMenuSlice"; | ||
import {useAppDispatch, useAppSelector} from "../../state/hooks"; | ||
import InputModal from "../InputModal"; | ||
import {useState} from "react"; | ||
import {confirm} from "@tauri-apps/api/dialog"; | ||
import { | ||
ContextMenuState, | ||
DirectoryEntityContextPayload, | ||
GeneralContextPayload | ||
} from "../../state/slices/contextMenuSlice"; | ||
import {createFile} from "../../ipc"; | ||
import {addContent, selectContentIdx} from "../../state/slices/currentDirectorySlice"; | ||
|
||
export default function ContextMenus() { | ||
const currentContextMenu = useAppSelector(selectCurrentContextMenu); | ||
|
||
switch (currentContextMenu) { | ||
case ContextMenuType.General: return ( | ||
<ContextMenu options={[ | ||
{ name: "General Opt 1", onClick: () => {} }, | ||
{ name: "General Opt 2", onClick: () => {} } | ||
]} /> | ||
) | ||
case ContextMenuType.DirectoryEntity: return ( | ||
<ContextMenu options={[ | ||
{ name: "Entity Opt 1", onClick: () => {} }, | ||
{ name: "Entity Opt 2", onClick: () => {} } | ||
]} /> | ||
) | ||
default: return <></>; | ||
const { currentContextMenu, contextMenuPayload } = useAppSelector(state => state.contextMenu); | ||
const [newFileShown, setNewFileShown] = useState(false); | ||
const [newDirectoryShown, setNewDirectoryShown] = useState(false); | ||
const [renameFileShown, setRenameFileShown] = useState(false); | ||
|
||
// Typescript pain | ||
const directoryEntityPayload = contextMenuPayload as DirectoryEntityContextPayload; | ||
const generalPayload = contextMenuPayload as GeneralContextPayload; | ||
|
||
const dispatch = useAppDispatch(); | ||
|
||
async function onNewFile(name: string) { | ||
try { | ||
const path = generalPayload.currentPath + name; | ||
await createFile(path); | ||
|
||
const newDirectoryContent = {"File": [name, path]} as DirectoryContent; | ||
dispatch(addContent(newDirectoryContent)); | ||
dispatch(selectContentIdx(0)) // Select top item as content is added to the top. | ||
} catch (e) { | ||
alert(e); | ||
} | ||
} | ||
|
||
function onNewFolder(name: string) { | ||
|
||
} | ||
|
||
function onRename(name: string) { | ||
|
||
} | ||
|
||
return ( | ||
<> | ||
{currentContextMenu == ContextMenuType.General ? ( | ||
<ContextMenu options={[ | ||
{ name: "New File", onClick: () => setNewFileShown(true) }, | ||
{ name: "New Folder", onClick: () => setNewDirectoryShown(true)} | ||
]} /> | ||
) : currentContextMenu == ContextMenuType.DirectoryEntity ? ( | ||
<ContextMenu options={[ | ||
{ name: "Rename", onClick: () => setRenameFileShown(true) }, | ||
{ name: "Delete", onClick: async () => { | ||
const result = await confirm("Are you sure you want to delete this file?"); | ||
if (result) { | ||
// Delete file | ||
} | ||
}} | ||
]} /> | ||
) : ""} | ||
|
||
<InputModal shown={newFileShown} setShown={setNewFileShown} title="New File" onSubmit={onNewFile} submitName="Create" /> | ||
<InputModal shown={newDirectoryShown} setShown={setNewDirectoryShown} title="New Folder" onSubmit={onNewFolder} submitName="Create" /> | ||
<InputModal shown={renameFileShown} setShown={setRenameFileShown} title="Rename File" onSubmit={onRename} submitName="Rename" /> | ||
</> | ||
) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.