drop files to import

This commit is contained in:
zombieFox 2021-08-27 13:09:28 +01:00
parent 31e24626bd
commit b813386aab
6 changed files with 214 additions and 18 deletions

View File

@ -3,7 +3,6 @@
} }
:root { :root {
--alert-text: var(--theme-primary-text-020);
--alert-header-background: var(--theme-primary-030); --alert-header-background: var(--theme-primary-030);
--alert-body-background: var(--theme-primary-020); --alert-body-background: var(--theme-primary-020);
} }

View File

@ -120,3 +120,8 @@ html.is-theme-background-type-color,
justify-content: flex-end; justify-content: flex-end;
align-items: flex-end; align-items: flex-end;
} }
.drop {
padding: 3em;
border: 1px solid hsl(var(--theme-primary-060));
}

View File

@ -32,18 +32,41 @@ data.import = {
}; };
}, },
file: (input, feedback) => { file: ({
fileList = false,
const fileList = input.files; feedback = false,
input = false
} = {}) => {
if (fileList.length > 0) { if (fileList.length > 0) {
data.validateFile(fileList, input, feedback); data.validateFile({
fileList: fileList,
feedback: feedback,
input: input
});
};
},
drop: ({
fileList = false,
feedback = false
}) => {
if (fileList.length > 0) {
data.validateFile({
fileList: fileList,
feedback: feedback
});
}; };
} }
}; };
data.validateFile = (fileList, input, feedback) => { data.validateFile = ({
fileList = false,
feedback = false,
input = false
} = {}) => {
// make new file reader // make new file reader
var reader = new FileReader(); var reader = new FileReader();
@ -116,26 +139,44 @@ data.validateFile = (fileList, input, feedback) => {
data.feedback.success.render(feedback, fileList[0].name, validFileSuccessAction); data.feedback.success.render(feedback, fileList[0].name, validFileSuccessAction);
input.value = ''; if (input) {
} else {
data.feedback.clear.render(feedback);
data.feedback.fail.notAppJson.render(feedback, fileList[0].name);
input.value = ''; input.value = '';
}; };
} else {
data.feedback.clear.render(feedback);
data.feedback.fail.notAppJson.render(feedback, fileList[0].name);
if (input) {
input.value = '';
};
};
} else { } else {
// not a JSON file // not a JSON file
data.feedback.clear.render(feedback); data.feedback.clear.render(feedback);
data.feedback.fail.notJson.render(feedback, fileList[0].name); data.feedback.fail.notJson.render(feedback, fileList[0].name);
if (input) {
input.value = ''; input.value = '';
}; };
}; };
};
// invoke the reader // invoke the reader
reader.readAsText(fileList.item(0)); reader.readAsText(fileList.item(0));

View File

@ -0,0 +1,33 @@
:root {
--drop-file-space: 24;
}
:root {
--drop-file-background: var(--theme-primary-030);
--drop-file-border: var(--theme-primary-030);
--drop-file-border-focus-hover: var(--theme-accent);
}
.drop-file {
border-width: calc(var(--layout-line-width) * 2);
border-style: solid;
border-color: hsl(var(--drop-file-border));
border-radius: calc(var(--theme-radius) * 0.01em);
padding: calc(((var(--alert-space) * 2) / 4) * 1em) calc((var(--alert-space) / 4) * 1em);
width: 100%;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
gap: 1em;
transform: scale(1);
transition: background-color var(--layout-transition-extra-fast), border var(--layout-transition-extra-fast), transform var(--layout-transition-extra-fast);
}
.drop-file-heading {}
.drop-file-over {
background: hsl(var(--drop-file-background));
border-color: rgb(var(--drop-file-border-focus-hover));
transform: scale(1.05);
}

View File

@ -0,0 +1,100 @@
import { state } from '../state';
import { data } from '../data';
import * as form from '../form';
import { node } from '../../utility/node';
import { complexNode } from '../../utility/complexNode';
import './index.css';
export const DropFile = function({
heading = 'Drop file here',
dropAaction = false,
enterAction = false,
leaveAction = false,
children = []
} = {}) {
this.files = false;
this.element = {
drop: node('div|class:drop-file', children),
heading: node(`p:${heading}|class:drop-file-heading small`)
};
this.assemble = () => {
this.element.drop.appendChild(this.element.heading);
};
this.bind = () => {
this.element.drop.addEventListener('dragenter', (event) => {
event.stopPropagation();
event.preventDefault();
if (enterAction) {
enterAction();
};
});
this.element.drop.addEventListener('dragleave', (event) => {
event.stopPropagation();
event.preventDefault();
this.element.drop.classList.remove('drop-file-over');
if (leaveAction) {
leaveAction();
};
});
this.element.drop.addEventListener('dragover', (event) => {
event.stopPropagation();
event.preventDefault();
this.element.drop.classList.add('drop-file-over');
});
this.element.drop.addEventListener('drop', (event) => {
event.stopPropagation();
event.preventDefault();
this.element.drop.classList.remove('drop-file-over');
this.files = event.dataTransfer.files;
if (dropAaction) {
dropAaction();
};
});
};
this.drop = () => {
return this.element.drop;
};
this.wrap = () => {
return form.wrap({
children: [
this.element.drop
]
})
};
this.assemble();
this.bind();
};

View File

@ -18,6 +18,7 @@ import { Button } from '../../button';
import { Collapse } from '../../collapse'; import { Collapse } from '../../collapse';
import { Edge } from '../../edge'; import { Edge } from '../../edge';
import { Alert } from '../../alert'; import { Alert } from '../../alert';
import { DropFile } from '../../dropFile';
import { Control_helperText } from '../../control/helperText'; import { Control_helperText } from '../../control/helperText';
import { Control_inputButton } from '../../control/inputButton'; import { Control_inputButton } from '../../control/inputButton';
@ -50,10 +51,6 @@ dataSetting.control = {
dataSetting.restore = (parent) => { dataSetting.restore = (parent) => {
const restoreFeedback = form.feedback();
data.feedback.empty.render(restoreFeedback);
dataSetting.control.restore.restoreElement = new Control_inputButton({ dataSetting.control.restore.restoreElement = new Control_inputButton({
id: 'restore-data', id: 'restore-data',
type: 'file', type: 'file',
@ -61,7 +58,11 @@ dataSetting.restore = (parent) => {
labelText: 'Import data', labelText: 'Import data',
inputButtonStyle: ['line'], inputButtonStyle: ['line'],
action: () => { action: () => {
data.import.file(dataSetting.control.restore.restoreElement.input, restoreFeedback) data.import.file({
fileList: dataSetting.control.restore.restoreElement.input.files,
feedback: dataSetting.control.restore.feedback,
input: dataSetting.control.restore.restoreElement
});
} }
}); });
@ -69,15 +70,32 @@ dataSetting.restore = (parent) => {
text: ['Restore a previously exported ' + appName + ' backup.'] text: ['Restore a previously exported ' + appName + ' backup.']
}); });
dataSetting.control.restore.feedback = form.feedback();
data.feedback.empty.render(dataSetting.control.restore.feedback);
dataSetting.control.restore.drop = new DropFile({
heading: 'Or drop a ' + appName + ' backup file here.',
dropAaction: () => {
data.import.drop({
fileList: dataSetting.control.restore.drop.files,
feedback: dataSetting.control.restore.feedback,
});
},
children: [
dataSetting.control.restore.restoreElement.button
]
});
parent.appendChild( parent.appendChild(
node('div', [ node('div', [
dataSetting.control.restore.restoreElement.wrap(), dataSetting.control.restore.drop.wrap(),
dataSetting.control.restore.restoreHelper.wrap(),
form.wrap({ form.wrap({
children: [ children: [
restoreFeedback dataSetting.control.restore.feedback
] ]
}) }),
dataSetting.control.restore.restoreHelper.wrap()
]) ])
); );