basic import and export working

This commit is contained in:
Christian Seyfferth 2019-01-16 10:35:46 +01:00
parent 921bc18061
commit a89539c9bb
5 changed files with 184 additions and 42 deletions

22
.vscode/launch.json vendored Normal file
View File

@ -0,0 +1,22 @@
{
// Use IntelliSense to learn about possible attributes.
// Hover to view descriptions of existing attributes.
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
"type": "chrome",
"request": "attach",
"name": "Attach to Chrome",
"port": 9222,
"webRoot": "${workspaceFolder}"
},
{
"type": "chrome",
"request": "launch",
"name": "Launch Chrome against localhost",
"url": "http://localhost:5500",
"webRoot": "${workspaceFolder}"
},
]
}

82
app.js
View File

@ -118,38 +118,48 @@ var app = new Vue({
}
},
methods: {
makeToast(message) {
M.toast({
html: message,
displayLength: this.config.toast_length
});
},
onFileChange: function (event) {
var files = event.target.files || event.dataTransfer.files;
this.handleInputFile(files[0]);
this.uploadFileName = files[0].name + " [" + Math.round(files[0].size / 1024) + " kB]";
M.toast({html:this.uploadFileName + " ausgewählt", displayLength:this.config.toast_length});
this.makeToast(this.uploadFileName + " ausgewählt");
},
handleInputFile: function (file) {
var reader = new FileReader();
var vm = this;
reader.onload = (e) => {
var data = !e ? reader.content : e.target.result;
var workbook = XLSX.read(data, {
type: 'binary',
cellDates: true,
});
if(workbook.Sheets["Dienstplan"] == null){
file.status = "error";
var isErfurterDienstplan = workbook.SheetNames.indexOf("Dienstplan") > -1;
if(isErfurterDienstplan){
vm.parseForErfurt(workbook.Sheets["Dienstplan"]);
} else {
vm.parseWorksheet(workbook.Sheets["Dienstplan"]);
file.status = "success";
var sheetName = workbook.SheetNames[0];
vm.parseForStuttgart(workbook.Sheets[sheetName]);
}
};
reader.readAsBinaryString(file);
M.toast({html:this.uploadFileName + " wird eingelesen",displayLength: this.config.toast_length});
},
parseWorksheet: function (dp) {
parseForErfurt: function (dp) {
var arr = XLSX.utils.sheet_to_row_object_array(dp, {
range: 1
});
var vm = this;
var day;
this.makeToast("Erfurter Dienstplan erkannt.");
arr.forEach(element => {
moment.locale(vm.config.moment.parse_language);
if (element.hasOwnProperty('Datum')) {
@ -157,11 +167,51 @@ var app = new Vue({
}
if (element.hasOwnProperty('Dienst')) {
var time = element.Zeit ? moment(element.Zeit) : day;
var date = day.hour(time.hour()).minute(time.minute());
var bemerkung = !element.Bemerkung ? "" : element.Bemerkung.trim();
var art = !element.Dienst ? "" : element.Dienst.trim();
var name = !element.__EMPTY ? "" : element.__EMPTY.trim();
vm.addShift(new Shift(art, name, date, bemerkung));
var termin = {
datum: day.clone().hour(time.hour()).minute(time.minute()),
art: element.Dienst ? element.Dienst.trim() : "",
beschreibung: element.Bemerkung ? element.Bemerkung.trim(): "",
name: element.__EMPTY ? element.__EMPTY.trim() : ""
}
vm.addShift(new Shift(termin));
}
});
},
parseForStuttgart: function (dp) {
var arr = XLSX.utils.sheet_to_json(dp, {
header: "A",
blankrows: false,
});
var vm = this;
var day;
this.makeToast("Stuttgarter Dienstplan erkannt.");
arr.forEach(element => {
moment.locale(vm.config.moment.parse_language);
if (element.hasOwnProperty('C')) {
day = moment(element.C);
}
if (element.hasOwnProperty('D') && moment(element.D, "HH:mm").isValid()) {
var time = day.clone();
var end = null;
if (typeof(element.D) === "object") {
time = moment(element.D);
} else if(element.D.indexOf("-") > -1 ) {
var tArray = element.D.split(" - ");
time = moment(tArray[0],"HH:mm");
end = moment(tArray[1], "HH:mm");
}
var termin = {
datum: day.clone().hour(time.hour()).minute(time.minute()),
ende: end ? end.format("HH:mm"): null,
ort: element.H ? element.H.trim() : "",
art: element.E ? element.E.trim() : "",
beschreibung: element.H ? element.H.trim(): "",
name: element.F ? element.F.trim() : ""
}
vm.addShift(new Shift(termin));
}
});
},
@ -170,11 +220,11 @@ var app = new Vue({
},
removeShift: function (shift) {
this.shifts.splice(this.shifts.indexOf(shift), 1);
M.toast({html:shift.VEventTitle + " gelöscht",displayLength: this.config.toast_length});
this.makeToast(shift.VEventTitle + " gelöscht");
},
cleanStorage: function () {
this.shifts = [];
M.toast({html:"Alle Einträge gelöscht",displayLength: this.config.toast_length});
this.makeToast("Alle Einträge gelöscht");
},
createDownloadFile: function () {
var vCal = new VCalendar("Dienstplan Kalender");
@ -191,7 +241,7 @@ var app = new Vue({
}
this.icsFile = window.URL.createObjectURL(this.blob);
M.toast({html:this.saveto + " erstellt.",displayLength: this.config.toast_length});
this.makeToast(this.saveto + " erstellt.");
},
downloadFile: function () {
if (window.navigator.msSaveOrOpenBlob) {

View File

@ -29,7 +29,7 @@
<ul class="side-nav" id="mobile-demo">
</ul>
<ul class="tabs tabs-transparent">
<li class="tab"><a class="active" href="#Dienste">Dienste</a></li>
<li class="tab"><a class="active" href="#termine">Termine</a></li>
<li class="tab"><a href="#Einstellungen">Regeln</a></li>
</ul>
</div>
@ -37,10 +37,10 @@
</div>
<div id="body">
<main class="container">
<div id="Dienste">
<div id="termine">
<div class="card" v-if="shifts.length > 0">
<div class="card-content">
<h3 class="card-title">Dienste</h3>
<h3 class="card-title">Termine</h3>
<table class="highlight" >
<thead class="">
<tr>
@ -61,6 +61,7 @@
</td>
<td class="">
{{s.VEventTitle}}
<small>{{ s.Ort }}</small>
</td>
<td class="" v-if="s.Beginn !== '00:00'">
{{s.Beginn}} - {{s.Ende}}
@ -75,7 +76,7 @@
</tbody>
<tfoot>
<tr>
<th colspan="5" class="text-right"> {{shifts.length }} Dienste</th>
<th colspan="5" class="right-align"> {{shifts.length }} Dienste</th>
</tr>
</tfoot>
</table>
@ -96,14 +97,14 @@
<a class="btn-flat red-text waves-effect"
@click="cleanStorage"
:disabled=" (remaining > 0) ? null : 'disabled'">
Dienste löschen
Termine löschen
</a>
</div>
</div>
<div class="card" v-else>
<div class="card-content center-align" style="height:100px;">
<h3 class="card-title">
Noch keine Dienste da
Noch keine Termine da
</h3>
</div>

View File

@ -88,15 +88,42 @@ Rule.defaults = function () {
}
var DURATION_RULES = Rule.defaults();
function Shift(kind, name, date, info) {
'use strict';
this.Datum = date.format(DATE_INPUT_FORMAT);
this.Beginn = date.format(TIME_FORMAT);
this.Art = kind;
this.Beschreibung = info;
this.Name = name;
Shift.setDurationFromRules(this);
function Shift() {
var evt = window.event || arguments[1] || arguments.callee.caller.arguments[0];
var target = evt.target || evt.srcElement;
var options = {};
if (arguments[0]) options = arguments[0];
var default_args = {
'art' : "",
'name' : "DUMMY",
'datum' : moment(),
'beschreibung' : "",
'ort' : "",
}
for (var index in default_args) {
if (typeof options[index] == "undefined") options[index] = default_args[index];
}
this.Datum = options.datum.format(DATE_INPUT_FORMAT);
this.Beginn = options.datum.format(TIME_FORMAT);
this.Art = options.art;
this.Beschreibung = options.beschreibung;
this.Name = options.name;
this.Ort = options.ort;
if (typeof options.ende != "undefined") {
this.Ende = options.ende;
} else {
if (!options.dontSetDurationFromRules) {
Shift.setDurationFromRules(this);
}
}
}
Shift.prototype = {
get Wochentag() {
return this._date.clone().locale(MOMENT_LOCALE).format(WEEKDAY_FORMAT);
@ -153,6 +180,13 @@ Shift.prototype = {
this._name = value ? value.trim() : "";
},
get Ort() {
return this._ort;
},
set Ort(value) {
this._ort = value ? value.trim() : "";
},
get VEventTitle() {
return this.Name + " " + this.Art;
},
@ -197,15 +231,25 @@ Shift.setDurationFromRules = function (shift) {
shift.Dauer = moment.duration(duration, 'm').locale(MOMENT_LOCALE);
}
Shift.prototype.toVEvent = function () {
'use strict';
var end = this._begin.clone().add(this._duration);
return new VEvent(TIMEZONE_NAME, this._begin, end, this.VEventTitle, this.Beschreibung);
return new VEvent({
startMoment: this._begin,
endMoment: end,
title: this.VEventTitle,
description: this.Beschreibung,
location: this.Ort
});
};
Shift.thaw = function (jsonShift) {
'use strict';
moment.locale(MOMENT_LOCALE);
var begin = moment(jsonShift._begin);
var shift = new Shift(jsonShift._kind, jsonShift._name, begin, jsonShift._description);
var shift = new Shift(
{
art: jsonShift._kind,
name: jsonShift._name,
datum: begin,
beschreibung: jsonShift._description
});
shift.id = jsonShift.id;
shift.Dauer = moment.duration(jsonShift._duration);
return shift;

View File

@ -72,21 +72,46 @@ function VCalendar(calendarName) {
VCalendar.prototype = Object.create(VMeta.prototype);
VCalendar.prototype.constructor = VCalendar;
function VEvent(timezoneName, startMoment, endMoment, title, description) {
function VEvent() {
var evt = window.event || arguments[1] || arguments.callee.caller.arguments[0];
var target = evt.target || evt.srcElement;
var options = {};
if (arguments[0]) options = arguments[0];
var default_args = {
'tzName' : "Europe/Berlin",
'startMoment' : moment(),
'endMoment' : moment(),
'uid' : VMeta.generateUID(),
'dtStamp' : VMeta.formatDate(moment()) + "Z",
'title' : "",
'description' : "",
'location' : "",
'organizer' : "",
}
for (var index in default_args) {
if (typeof options[index] == "undefined") options[index] = default_args[index];
}
VMeta.call(this);
this.tag = "VEVENT";
this.set('DTSTART;TZID=' + timezoneName, VMeta.formatDate(startMoment));
this.set('DTEND;TZID=' + timezoneName, VMeta.formatDate(endMoment));
this.set('DTSTAMP', VMeta.formatDate(moment()) + "Z");
this.set('UID', VMeta.generateUID());
this.set('SUMMARY', title);
this.set('DESCRIPTION', description);
this.set('DTSTART;TZID=' + options.tzName, VMeta.formatDate(options.startMoment));
this.set('DTEND;TZID=' + options.tzName, VMeta.formatDate(options.endMoment));
this.set('DTSTAMP', options.dtStamp);
this.set('UID', options.uid);
this.set('SUMMARY', options.title);
this.set('DESCRIPTION', options.description);
this.set('LOCATION', options.location)
this.set('CLASS', "PUBLIC");
this.set('TRANSP', "OPAQUE");
this.set('STATUS', "CONFIRMED");
this.set('ORGANIZER', "");
this.set('ORGANIZER', options.organizer);
}
VEvent.prototype = Object.create(VMeta.prototype);
VEvent.prototype.constructor = VEvent;