diff --git a/src/Terminal/commands/ls.tsx b/src/Terminal/commands/ls.tsx index f784f217f..1fddc05e8 100644 --- a/src/Terminal/commands/ls.tsx +++ b/src/Terminal/commands/ls.tsx @@ -9,6 +9,8 @@ import { evaluateDirectoryPath, getFirstParentDirectory, isValidDirectoryPath } import { IRouter } from "../../ui/Router"; import { ITerminal } from "../ITerminal"; import * as libarg from "arg"; +import { showLiterature } from "../../Literature/LiteratureHelpers"; +import { MessageFilenames, showMessage } from "../../Message/MessageHelpers"; export function ls( terminal: ITerminal, @@ -121,13 +123,13 @@ export function ls( allMessages.sort(); folders.sort(); - interface ClickableScriptRowProps { + interface ClickableRowProps { row: string; prefix: string; hostname: string; } - function ClickableScriptRow({ row, prefix, hostname }: ClickableScriptRowProps): React.ReactElement { + function ClickableScriptRow({ row, prefix, hostname }: ClickableRowProps): React.ReactElement { const classes = makeStyles((theme: Theme) => createStyles({ scriptLinksWrap: { @@ -160,18 +162,82 @@ export function ls( return ( {rowSplitArray.map((rowItem) => ( - - onScriptLinkClick(rowItem[0])}> + + onScriptLinkClick(rowItem[0])}> {rowItem[0]} - {rowItem[1]} + {rowItem[1]} ))} ); } - function postSegments(segments: string[], flags: any, style?: any, linked?: boolean): void { + function ClickableMessageRow({ row, prefix, hostname }: ClickableRowProps): React.ReactElement { + const classes = makeStyles((theme: Theme) => + createStyles({ + linksWrap: { + display: "inline-flex", + color: theme.palette.primary.main, + }, + link: { + cursor: "pointer", + textDecorationLine: "underline", + paddingRight: "1.15em", + "&:last-child": { padding: 0 }, + }, + }), + )(); + + const rowSplit = row.split("~"); + let rowSplitArray = rowSplit.map((x) => [x.trim(), x.replace(x.trim(), "")]); + rowSplitArray = rowSplitArray.filter((x) => !!x[0]); + + function onMessageLinkClick(filename: string): void { + if (player.getCurrentServer().hostname !== hostname) { + return terminal.error(`File is not on this server, connect to ${hostname} and try again`); + } + if (filename.startsWith("/")) filename = filename.slice(1); + const filepath = terminal.getFilepath(`${prefix}${filename}`); + + if (filepath.endsWith(".lit")) { + showLiterature(filepath); + } else if (filepath.endsWith(".msg")) { + showMessage(filepath as MessageFilenames); + } + } + + return ( + + {rowSplitArray.map((rowItem) => ( + + onMessageLinkClick(rowItem[0])}> + {rowItem[0]} + + {rowItem[1]} + + ))} + + ); + } + + enum FileType { + Folder, + Message, + TextFile, + Program, + Contract, + Script, + } + + interface FileGroup { + type: FileType; + segments: string[]; + } + + function postSegments(group: FileGroup, flags: any): void { + const segments = group.segments; + const linked = group.type === FileType.Script || group.type === FileType.Message; const maxLength = Math.max(...segments.map((s) => s.length)) + 1; const filesPerRow = flags["-l"] === true ? 1 : Math.ceil(80 / maxLength); for (let i = 0; i < segments.length; i++) { @@ -186,25 +252,32 @@ export function ls( i++; } i--; - if (!style) { - terminal.print(row); - } else if (linked) { - terminal.printRaw(); - } else { - terminal.printRaw({row}); + + switch (group.type) { + case FileType.Folder: + terminal.printRaw({row}); + break; + case FileType.Script: + terminal.printRaw(); + break; + case FileType.Message: + terminal.printRaw(); + break; + default: + terminal.print(row); } } } - const groups = [ - { segments: folders, style: { color: "cyan" } }, - { segments: allMessages }, - { segments: allTextFiles }, - { segments: allPrograms }, - { segments: allContracts }, - { segments: allScripts, style: { color: "yellow", fontStyle: "bold" }, linked: true }, + const groups: FileGroup[] = [ + { type: FileType.Folder, segments: folders }, + { type: FileType.Message, segments: allMessages }, + { type: FileType.TextFile, segments: allTextFiles }, + { type: FileType.Program, segments: allPrograms }, + { type: FileType.Contract, segments: allContracts }, + { type: FileType.Script, segments: allScripts }, ].filter((g) => g.segments.length > 0); - for (let i = 0; i < groups.length; i++) { - postSegments(groups[i].segments, flags, groups[i].style, groups[i].linked); + for (const group of groups) { + postSegments(group, flags); } }