Skip to content

Commit

Permalink
notepad: folder selecting
Browse files Browse the repository at this point in the history
  • Loading branch information
binzume committed Dec 1, 2023
1 parent d542376 commit bc97979
Show file tree
Hide file tree
Showing 2 changed files with 64 additions and 11 deletions.
72 changes: 62 additions & 10 deletions apps/notepad/notepad.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,12 @@ AFRAME.registerComponent('notepad-app', {
this.appManager = null;
let editorEl = /** @type {AFRAME.AEntity & {value: string}} */ (this.el.querySelector('[texteditor]'));
let editor = editorEl.components.texteditor;
let formats = [
{ name: 'Text', type: 'text/plain', ext: 'txt' },
{ name: 'JavaScript', type: 'text/javascript', ext: 'js' },
{ name: 'Go', type: 'text/x-go', ext: 'go' },
{ name: 'C/C++', type: 'text/x-c', ext: 'c' },
];
editorEl.value = `# Example text
Hello, world!
Expand All @@ -25,7 +31,7 @@ TODO:
// TODO: more languages
let keywords = [];
let common = ['if', 'else', 'for', 'while', 'break', 'continue', 'switch', 'case', 'default',
'return', 'class', 'new', 'throw', 'try', 'catch', 'finally'];
'return', 'class', 'new', 'throw', 'try', 'catch', 'finally', 'void'];
if (type.startsWith('text/javascript')) {
keywords = common.concat(['this', 'true', 'false', 'null', 'function', 'var', 'let', 'const',
'undefined', 'NaN', 'instanceof', 'async', 'of', 'in', 'import', 'export', 'extends']);
Expand Down Expand Up @@ -106,6 +112,10 @@ TODO:
editor.textView.undo(true);
}
});
this._elByName('format-menu').addEventListener('change', async (ev) => {
setMimeType(formats[ev.detail.index].type);
});
this._elByName('format-menu').setAttribute('values', formats.map(f => f.name).join(','));

this.el.addEventListener('app-start', async (ev) => {
this.appManager = ev.detail.appManager;
Expand Down Expand Up @@ -135,7 +145,6 @@ TODO:
}
}, { once: true });


this.el.addEventListener('keydown', (ev) => {
if (ev.ctrlKey && ev.code == 'KeyA') {
editor.selectAll();
Expand All @@ -161,15 +170,57 @@ TODO:
attrs instanceof Function ? attrs(el) : (attrs && Object.entries(attrs).forEach(([k, v]) => el.setAttribute(k, v)));
return el;
}
let task = new Promise((resolve, reject) => {
/** @type {Folder} */
let folder = this._appFolder();
let task = new Promise(async (resolve, reject) => {
let buttonEl = mkEl('a-xybutton', [], { label: 'Save' });
let cancelEl = mkEl('a-xybutton', [], { label: 'Cancel' });
let inputEl = mkEl('a-xyinput', [], { value: 'Untitled.' + (options.extension || 'txt') });
let inputEl = mkEl('a-xyinput', [], { value: 'Untitled.' + (options.extension || 'txt'), width: 3 });
let selectFolderEl = mkEl('a-xyselect', [], { values: '' });
// TODO: tree view
let roots = [
[this._appFolder(), this.el.components.vrapp.app.name],
[this.el.components.vrapp.services.storage, '/']
];
let path = [];
let folders = [];
let selectFolder = async (fi) => {
folder = fi[0];
if (roots.includes(fi)) {
path = [fi];
} else if (path.includes(fi)) {
path = path.slice(0, path.indexOf(fi) + 1);
} else {
path.push(fi);
}
let ff = path.slice();
for (let f of (await folder.getFiles(0, 1000)).items) {
if (f.type == 'folder') {
ff.push([this.el.components.vrapp.services.storage.getFolder(f.path), f.name]);
}
}
folders = roots.slice();
folders.splice(roots.indexOf(ff[0]), 1, ...ff);
selectFolderEl.setAttribute('values', folders.map(fi => fi[1]).join(','));
return folders.indexOf(fi);
};
selectFolder(roots[0]);
let el = mkEl('a-xycontainer', [
mkEl('a-entity', [], {
xyitem: 'fixed: true',
geometry: 'primitive: xy-rounded-rect; width: 4; height: 2.5',
material: 'color: #000000',
position: '0 0 -0.1',
}),
mkEl('a-xycontainer', [
mkEl('a-xylabel', ['Folder:'], { value: 'Folder:', width: 1.5, height: 0.4 }),
selectFolderEl,
], { direction: 'row' }),
inputEl,
buttonEl,
cancelEl,
], { position: '0 0 0.05', direction: 'row', xyitem: 'fixed: true' });
mkEl('a-xycontainer', [buttonEl, cancelEl], { direction: 'row' }),
], {
position: '0 0 0.2', direction: 'column', xyitem: 'fixed: true',
});
buttonEl.addEventListener('click', ev => {
this.el.removeChild(el);
resolve(inputEl.value);
Expand All @@ -178,13 +229,14 @@ TODO:
this.el.removeChild(el);
reject();
});
selectFolderEl.addEventListener('change', async (ev) => {
selectFolderEl.setAttribute('select', await selectFolder(folders[ev.detail.index]));
});
this.el.append(el);
setTimeout(() => inputEl.focus(), 0);
});
let name = await task;
console.log("Save", name);
let folder = this._appFolder();
return folder.writeFile(name, content, { mkdir: true });
return await folder.writeFile(name, content, { mkdir: true });
},
_elByName(name) {
return this.el.querySelector("[name=" + name + "]");
Expand Down
3 changes: 2 additions & 1 deletion apps/notepad/template.html
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,11 @@
<body style="background-color: black; color:white;">
<a-scene cursor="rayOrigin: mouse; fuse:false" raycaster="objects:.collidable">

<a-xywindow id="app" xyresize="minWidth:6" notepad-app scale='0.2 0.2 0.2' title="Notepad" width="6" height="3.4" position="0.5 0.5 -1" xywindow="background:true" xycontainer="direction:column;alignItems:stretch;justifyItems:stretch">
<a-xywindow id="app" xyresize="minWidth:6" notepad-app scale='0.2 0.2 0.2' title="Notepad" width="6" height="3.4" position="0 0.8 -1" xywindow="background:true" xycontainer="direction:column;alignItems:stretch;justifyItems:stretch">
<a-xycontainer width="6" height="0.3" direction="row" align-items="stretch" justify-items="stretch" spacing="0.05" xyitem="grow:0;shrink:0">
<a-xyselect name="file-menu" label="File" width="0.5" values="New,Save,Save As..."></a-xyselect>
<a-xyselect name="edit-menu" label="Edit" width="0.5" values="Copy,Cut,Paste,Undo,Redo"></a-xyselect>
<a-xyselect name="format-menu" label="FileType" width="0.3"></a-xyselect>
<a-xybutton name="pgup-button" label="PgUp" width="0.3"></a-xybutton>
<a-xybutton name="pgdn-button" label="PgDn" width="0.3"></a-xybutton>
</a-xycontainer>
Expand Down

0 comments on commit bc97979

Please sign in to comment.