From dd74fcb12e038e0be26227bf64c3312d533b7d57 Mon Sep 17 00:00:00 2001 From: Justin Schroeder Date: Tue, 19 Nov 2019 07:15:13 -0500 Subject: [PATCH] Fixes stray drag/drop on missed dropzones, allows removing of non uploaded files --- dist/formulate.esm.js | 198 ++++++++++++++++++++++++------ dist/formulate.min.js | 198 ++++++++++++++++++++++++------ dist/formulate.umd.js | 198 ++++++++++++++++++++++++------ dist/snow.css | 117 ++++++++++++++++-- dist/snow.min.css | 4 +- src/FileUpload.js | 56 +++++++-- src/Formulate.js | 1 + src/FormulateFiles.vue | 35 ++++-- src/FormulateInput.vue | 6 +- src/inputs/FormulateInputFile.vue | 26 +++- src/libs/context.js | 3 +- src/libs/faux-uploader.js | 16 ++- src/libs/rules.js | 12 +- src/locales/en.js | 7 ++ test/FormulateInputBox.test.js | 1 - test/rules.test.js | 22 +++- themes/snow/_inputs.scss | 164 ++++++++++++++++++++++++- themes/snow/_variables.scss | 3 + 18 files changed, 895 insertions(+), 172 deletions(-) diff --git a/dist/formulate.esm.js b/dist/formulate.esm.js index 76bf251..b31c712 100644 --- a/dist/formulate.esm.js +++ b/dist/formulate.esm.js @@ -115,11 +115,12 @@ var library = { * The file upload class holds and represents a file’s upload state durring * the upload flow. */ -var FileUpload = function FileUpload (fileList, context, options) { - this.fileList = fileList; +var FileUpload = function FileUpload (input, context, options) { + this.input = input; + this.fileList = input.files; this.files = []; this.options = options; - this.setFileList(fileList); + this.addFileList(this.fileList); this.context = context; }; @@ -127,16 +128,28 @@ var FileUpload = function FileUpload (fileList, context, options) { * Produce an array of files and alert the callback. * @param {FileList} */ -FileUpload.prototype.setFileList = function setFileList (fileList) { - for (var i = 0; i < fileList.length; i++) { - var file = fileList.item(i); - this.files.push({ - progress: 0, +FileUpload.prototype.addFileList = function addFileList (fileList) { + var this$1 = this; + + var loop = function ( i ) { + var file = fileList[i]; + var uuid = nanoid(); + var removeFile = function () { + this.removeFile(uuid); + }; + this$1.files.push({ + progress: false, + error: false, + complete: false, + justFinished: false, name: file.name || 'file-upload', file: file, - uuid: nanoid() + uuid: uuid, + removeFile: removeFile.bind(this$1) }); - } + }; + + for (var i = 0; i < fileList.length; i++) loop( i ); }; /** @@ -196,8 +209,21 @@ FileUpload.prototype.upload = function upload () { Promise.all(this$1.files.map(function (file) { return this$1.getUploader( file.file, - function (progress) { file.progress = progress; }, - function (error) { return reject(new Error(error)); }, + function (progress) { + file.progress = progress; + if (progress >= 100) { + if (!file.complete) { + file.justFinished = true; + setTimeout(function () { file.justFinished = false; }, this$1.options.uploadJustCompleteDuration); + } + file.complete = true; + } + }, + function (error) { + file.progress = 0; + file.error = error; + file.complete = true; + }, this$1.options ) })) @@ -206,6 +232,20 @@ FileUpload.prototype.upload = function upload () { }) }; +/** + * Remove a file from the uploader (and the file list) + * @param {string} uuid + */ +FileUpload.prototype.removeFile = function removeFile (uuid) { + this.files = this.files.filter(function (file) { return file.uuid !== uuid; }); + if (window) { + var transfer = new DataTransfer(); + this.files.map(function (file) { return transfer.items.add(file.file); }); + this.fileList = transfer.files; + this.input.files = this.fileList; + } +}; + /** * Get the files. */ @@ -538,14 +578,10 @@ var rules = { return Promise.resolve((function () { if (files instanceof FileUpload) { - if (files.hasUploader()) { - return false - } - files = files.getFiles(); - } - if (typeof window !== 'undefined' && typeof FileReader !== 'undefined' && typeof Blob !== 'undefined') { - for (var i in files) { - if (!types.includes(files[i].type)) { + var fileList = files.getFileList(); + for (var i = 0; i < fileList.length; i++) { + var file = fileList[i]; + if (!types.includes(file.type)) { return false } } @@ -776,6 +812,16 @@ var en = { return ((sentence(name)) + " must be less than " + (args[0]) + " characters long.") }, + /** + * The (field-level) error message for mime errors. + */ + mime: function (ref) { + var name = ref.name; + var args = ref.args; + + return ((sentence(name)) + " must of the the type: " + (args[0] || 'No file formats allowed.')) + }, + /** * The maximum value allowed. */ @@ -842,17 +888,29 @@ var en = { */ function fauxUploader (file, progress, error, options) { return new Promise(function (resolve, reject) { - var totalTime = options.fauxUploaderDuration || 2000; + var totalTime = (options.fauxUploaderDuration || 2000) * (0.5 + Math.random()); var start = performance.now(); + /** + * @todo - remove, intentional failure + */ + var fail = (Math.random() > 0.5); var advance = function () { return setTimeout(function () { var elapsed = performance.now() - start; var currentProgress = Math.min(100, Math.round(elapsed / totalTime * 100)); progress(currentProgress); + + /** + * @todo - remove, intentional failure + */ + if (fail && currentProgress > 50) { + return error('There was an error uploading the file.') + } + if (currentProgress >= 100) { - resolve({ + return resolve({ url: 'http://via.placeholder.com/350x150.png', name: file.name - }); + }) } else { advance(); } @@ -881,7 +939,8 @@ var context = { showImage: this.showImage, uploadUrl: this.uploadUrl, uploader: this.uploader || this.$formulate.getUploader(), - immediateUpload: this.immediateUpload}, + uploadBehavior: this.uploadBehavior, + preventWindowDrops: this.preventWindowDrops}, this.typeContext)) }, nameOrFallback: nameOrFallback, @@ -1182,7 +1241,11 @@ var script = { type: [Function, Object, Boolean], default: false }, - immediateUpload: { + uploadBehavior: { + type: Boolean, + default: true + }, + preventWindowDrops: { type: Boolean, default: true } @@ -2200,18 +2263,52 @@ var __vue_render__$6 = function() { "ul", { staticClass: "formulate-files" }, _vm._l(_vm.fileUploads, function(file) { - return _c("li", { key: file.uuid, staticClass: "formulate-file" }, [ - _c("span", { - staticClass: "formualte-file-name", - domProps: { textContent: _vm._s(file.name) } - }), - _vm._v(" "), - file.progress > 0 && file.progress < 100 - ? _c("span", { - domProps: { textContent: _vm._s(file.progress + "%") } - }) - : _vm._e() - ]) + return _c( + "li", + { key: file.uuid, attrs: { "data-has-error": !!file.error } }, + [ + _c("div", { staticClass: "formulate-file" }, [ + _c("div", { + staticClass: "formualte-file-name", + domProps: { textContent: _vm._s(file.name) } + }), + _vm._v(" "), + file.progress !== false + ? _c( + "div", + { + staticClass: "formulate-file-progress", + attrs: { + "data-just-finished": file.justFinished, + "data-is-finished": + !file.justFinished && file.complete + } + }, + [ + _c("div", { + staticClass: "formulate-file-progress-inner", + style: { width: file.progress + "%" } + }) + ] + ) + : _vm._e(), + _vm._v(" "), + (file.complete && !file.justFinished) || file.progress === false + ? _c("div", { + staticClass: "formulate-file-remove", + on: { click: file.removeFile } + }) + : _vm._e() + ]), + _vm._v(" "), + file.error + ? _c("div", { + staticClass: "formulate-file-upload-error", + domProps: { textContent: _vm._s(file.error) } + }) + : _vm._e() + ] + ) }), 0 ) @@ -2264,16 +2361,36 @@ var script$7 = { }, computed: { hasFiles: function hasFiles () { - return (this.context.model instanceof FileUpload && this.context.model.files.length) + return !!(this.context.model instanceof FileUpload && this.context.model.files.length) + } + }, + mounted: function mounted () { + // Add a listener to the window to prevent drag/drops that miss the dropzone + // from opening the file and navigating the user away from the page. + if (window && this.context.preventWindowDrops) { + window.addEventListener('dragover', this.preventDefault); + window.addEventListener('drop', this.preventDefault); + } + }, + destroyed: function destroyed () { + if (window && this.context.preventWindowDrops) { + window.removeEventListener('dragover', this.preventDefault); + window.removeEventListener('drop', this.preventDefault); } }, methods: { + preventDefault: function preventDefault (e) { + if (e.target.tagName !== 'INPUT' && e.target.getAttribute('type') !== 'file') { + e = e || event; + e.preventDefault(); + } + }, handleFile: function handleFile () { var input = this.$refs.file; if (input.files.length) { - this.context.model = this.$formulate.createUpload(input.files, this.context); + this.context.model = this.$formulate.createUpload(input, this.context); } - if (this.context.immediateUpload && this.context.model instanceof FileUpload) { + if (this.context.uploadBehavior === 'live' && this.context.model instanceof FileUpload) { this.context.model.upload(); } }, @@ -2819,6 +2936,7 @@ var Formulate = function Formulate () { rules: rules, locale: 'en', uploader: fauxUploader, + uploadJustCompleteDuration: 1000, locales: { en: en } diff --git a/dist/formulate.min.js b/dist/formulate.min.js index dbc0489..9c7985a 100644 --- a/dist/formulate.min.js +++ b/dist/formulate.min.js @@ -118,11 +118,12 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { * The file upload class holds and represents a file’s upload state durring * the upload flow. */ - var FileUpload = function FileUpload (fileList, context, options) { - this.fileList = fileList; + var FileUpload = function FileUpload (input, context, options) { + this.input = input; + this.fileList = input.files; this.files = []; this.options = options; - this.setFileList(fileList); + this.addFileList(this.fileList); this.context = context; }; @@ -130,16 +131,28 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { * Produce an array of files and alert the callback. * @param {FileList} */ - FileUpload.prototype.setFileList = function setFileList (fileList) { - for (var i = 0; i < fileList.length; i++) { - var file = fileList.item(i); - this.files.push({ - progress: 0, + FileUpload.prototype.addFileList = function addFileList (fileList) { + var this$1 = this; + + var loop = function ( i ) { + var file = fileList[i]; + var uuid = nanoid(); + var removeFile = function () { + this.removeFile(uuid); + }; + this$1.files.push({ + progress: false, + error: false, + complete: false, + justFinished: false, name: file.name || 'file-upload', file: file, - uuid: nanoid() + uuid: uuid, + removeFile: removeFile.bind(this$1) }); - } + }; + + for (var i = 0; i < fileList.length; i++) loop( i ); }; /** @@ -199,8 +212,21 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { Promise.all(this$1.files.map(function (file) { return this$1.getUploader( file.file, - function (progress) { file.progress = progress; }, - function (error) { return reject(new Error(error)); }, + function (progress) { + file.progress = progress; + if (progress >= 100) { + if (!file.complete) { + file.justFinished = true; + setTimeout(function () { file.justFinished = false; }, this$1.options.uploadJustCompleteDuration); + } + file.complete = true; + } + }, + function (error) { + file.progress = 0; + file.error = error; + file.complete = true; + }, this$1.options ) })) @@ -209,6 +235,20 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { }) }; + /** + * Remove a file from the uploader (and the file list) + * @param {string} uuid + */ + FileUpload.prototype.removeFile = function removeFile (uuid) { + this.files = this.files.filter(function (file) { return file.uuid !== uuid; }); + if (window) { + var transfer = new DataTransfer(); + this.files.map(function (file) { return transfer.items.add(file.file); }); + this.fileList = transfer.files; + this.input.files = this.fileList; + } + }; + /** * Get the files. */ @@ -541,14 +581,10 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { return Promise.resolve((function () { if (files instanceof FileUpload) { - if (files.hasUploader()) { - return false - } - files = files.getFiles(); - } - if (typeof window !== 'undefined' && typeof FileReader !== 'undefined' && typeof Blob !== 'undefined') { - for (var i in files) { - if (!types.includes(files[i].type)) { + var fileList = files.getFileList(); + for (var i = 0; i < fileList.length; i++) { + var file = fileList[i]; + if (!types.includes(file.type)) { return false } } @@ -779,6 +815,16 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { return ((sentence(name)) + " must be less than " + (args[0]) + " characters long.") }, + /** + * The (field-level) error message for mime errors. + */ + mime: function (ref) { + var name = ref.name; + var args = ref.args; + + return ((sentence(name)) + " must of the the type: " + (args[0] || 'No file formats allowed.')) + }, + /** * The maximum value allowed. */ @@ -845,17 +891,29 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { */ function fauxUploader (file, progress, error, options) { return new Promise(function (resolve, reject) { - var totalTime = options.fauxUploaderDuration || 2000; + var totalTime = (options.fauxUploaderDuration || 2000) * (0.5 + Math.random()); var start = performance.now(); + /** + * @todo - remove, intentional failure + */ + var fail = (Math.random() > 0.5); var advance = function () { return setTimeout(function () { var elapsed = performance.now() - start; var currentProgress = Math.min(100, Math.round(elapsed / totalTime * 100)); progress(currentProgress); + + /** + * @todo - remove, intentional failure + */ + if (fail && currentProgress > 50) { + return error('There was an error uploading the file.') + } + if (currentProgress >= 100) { - resolve({ + return resolve({ url: 'http://via.placeholder.com/350x150.png', name: file.name - }); + }) } else { advance(); } @@ -884,7 +942,8 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { showImage: this.showImage, uploadUrl: this.uploadUrl, uploader: this.uploader || this.$formulate.getUploader(), - immediateUpload: this.immediateUpload}, + uploadBehavior: this.uploadBehavior, + preventWindowDrops: this.preventWindowDrops}, this.typeContext)) }, nameOrFallback: nameOrFallback, @@ -1185,7 +1244,11 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { type: [Function, Object, Boolean], default: false }, - immediateUpload: { + uploadBehavior: { + type: Boolean, + default: true + }, + preventWindowDrops: { type: Boolean, default: true } @@ -2203,18 +2266,52 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { "ul", { staticClass: "formulate-files" }, _vm._l(_vm.fileUploads, function(file) { - return _c("li", { key: file.uuid, staticClass: "formulate-file" }, [ - _c("span", { - staticClass: "formualte-file-name", - domProps: { textContent: _vm._s(file.name) } - }), - _vm._v(" "), - file.progress > 0 && file.progress < 100 - ? _c("span", { - domProps: { textContent: _vm._s(file.progress + "%") } - }) - : _vm._e() - ]) + return _c( + "li", + { key: file.uuid, attrs: { "data-has-error": !!file.error } }, + [ + _c("div", { staticClass: "formulate-file" }, [ + _c("div", { + staticClass: "formualte-file-name", + domProps: { textContent: _vm._s(file.name) } + }), + _vm._v(" "), + file.progress !== false + ? _c( + "div", + { + staticClass: "formulate-file-progress", + attrs: { + "data-just-finished": file.justFinished, + "data-is-finished": + !file.justFinished && file.complete + } + }, + [ + _c("div", { + staticClass: "formulate-file-progress-inner", + style: { width: file.progress + "%" } + }) + ] + ) + : _vm._e(), + _vm._v(" "), + (file.complete && !file.justFinished) || file.progress === false + ? _c("div", { + staticClass: "formulate-file-remove", + on: { click: file.removeFile } + }) + : _vm._e() + ]), + _vm._v(" "), + file.error + ? _c("div", { + staticClass: "formulate-file-upload-error", + domProps: { textContent: _vm._s(file.error) } + }) + : _vm._e() + ] + ) }), 0 ) @@ -2267,16 +2364,36 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { }, computed: { hasFiles: function hasFiles () { - return (this.context.model instanceof FileUpload && this.context.model.files.length) + return !!(this.context.model instanceof FileUpload && this.context.model.files.length) + } + }, + mounted: function mounted () { + // Add a listener to the window to prevent drag/drops that miss the dropzone + // from opening the file and navigating the user away from the page. + if (window && this.context.preventWindowDrops) { + window.addEventListener('dragover', this.preventDefault); + window.addEventListener('drop', this.preventDefault); + } + }, + destroyed: function destroyed () { + if (window && this.context.preventWindowDrops) { + window.removeEventListener('dragover', this.preventDefault); + window.removeEventListener('drop', this.preventDefault); } }, methods: { + preventDefault: function preventDefault (e) { + if (e.target.tagName !== 'INPUT' && e.target.getAttribute('type') !== 'file') { + e = e || event; + e.preventDefault(); + } + }, handleFile: function handleFile () { var input = this.$refs.file; if (input.files.length) { - this.context.model = this.$formulate.createUpload(input.files, this.context); + this.context.model = this.$formulate.createUpload(input, this.context); } - if (this.context.immediateUpload && this.context.model instanceof FileUpload) { + if (this.context.uploadBehavior === 'live' && this.context.model instanceof FileUpload) { this.context.model.upload(); } }, @@ -2822,6 +2939,7 @@ var Formulate = (function (exports, isUrl, nanoid, isPlainObject) { rules: rules, locale: 'en', uploader: fauxUploader, + uploadJustCompleteDuration: 1000, locales: { en: en } diff --git a/dist/formulate.umd.js b/dist/formulate.umd.js index 2f1fb26..374a0f7 100644 --- a/dist/formulate.umd.js +++ b/dist/formulate.umd.js @@ -121,11 +121,12 @@ * The file upload class holds and represents a file’s upload state durring * the upload flow. */ - var FileUpload = function FileUpload (fileList, context, options) { - this.fileList = fileList; + var FileUpload = function FileUpload (input, context, options) { + this.input = input; + this.fileList = input.files; this.files = []; this.options = options; - this.setFileList(fileList); + this.addFileList(this.fileList); this.context = context; }; @@ -133,16 +134,28 @@ * Produce an array of files and alert the callback. * @param {FileList} */ - FileUpload.prototype.setFileList = function setFileList (fileList) { - for (var i = 0; i < fileList.length; i++) { - var file = fileList.item(i); - this.files.push({ - progress: 0, + FileUpload.prototype.addFileList = function addFileList (fileList) { + var this$1 = this; + + var loop = function ( i ) { + var file = fileList[i]; + var uuid = nanoid(); + var removeFile = function () { + this.removeFile(uuid); + }; + this$1.files.push({ + progress: false, + error: false, + complete: false, + justFinished: false, name: file.name || 'file-upload', file: file, - uuid: nanoid() + uuid: uuid, + removeFile: removeFile.bind(this$1) }); - } + }; + + for (var i = 0; i < fileList.length; i++) loop( i ); }; /** @@ -202,8 +215,21 @@ Promise.all(this$1.files.map(function (file) { return this$1.getUploader( file.file, - function (progress) { file.progress = progress; }, - function (error) { return reject(new Error(error)); }, + function (progress) { + file.progress = progress; + if (progress >= 100) { + if (!file.complete) { + file.justFinished = true; + setTimeout(function () { file.justFinished = false; }, this$1.options.uploadJustCompleteDuration); + } + file.complete = true; + } + }, + function (error) { + file.progress = 0; + file.error = error; + file.complete = true; + }, this$1.options ) })) @@ -212,6 +238,20 @@ }) }; + /** + * Remove a file from the uploader (and the file list) + * @param {string} uuid + */ + FileUpload.prototype.removeFile = function removeFile (uuid) { + this.files = this.files.filter(function (file) { return file.uuid !== uuid; }); + if (window) { + var transfer = new DataTransfer(); + this.files.map(function (file) { return transfer.items.add(file.file); }); + this.fileList = transfer.files; + this.input.files = this.fileList; + } + }; + /** * Get the files. */ @@ -544,14 +584,10 @@ return Promise.resolve((function () { if (files instanceof FileUpload) { - if (files.hasUploader()) { - return false - } - files = files.getFiles(); - } - if (typeof window !== 'undefined' && typeof FileReader !== 'undefined' && typeof Blob !== 'undefined') { - for (var i in files) { - if (!types.includes(files[i].type)) { + var fileList = files.getFileList(); + for (var i = 0; i < fileList.length; i++) { + var file = fileList[i]; + if (!types.includes(file.type)) { return false } } @@ -782,6 +818,16 @@ return ((sentence(name)) + " must be less than " + (args[0]) + " characters long.") }, + /** + * The (field-level) error message for mime errors. + */ + mime: function (ref) { + var name = ref.name; + var args = ref.args; + + return ((sentence(name)) + " must of the the type: " + (args[0] || 'No file formats allowed.')) + }, + /** * The maximum value allowed. */ @@ -848,17 +894,29 @@ */ function fauxUploader (file, progress, error, options) { return new Promise(function (resolve, reject) { - var totalTime = options.fauxUploaderDuration || 2000; + var totalTime = (options.fauxUploaderDuration || 2000) * (0.5 + Math.random()); var start = performance.now(); + /** + * @todo - remove, intentional failure + */ + var fail = (Math.random() > 0.5); var advance = function () { return setTimeout(function () { var elapsed = performance.now() - start; var currentProgress = Math.min(100, Math.round(elapsed / totalTime * 100)); progress(currentProgress); + + /** + * @todo - remove, intentional failure + */ + if (fail && currentProgress > 50) { + return error('There was an error uploading the file.') + } + if (currentProgress >= 100) { - resolve({ + return resolve({ url: 'http://via.placeholder.com/350x150.png', name: file.name - }); + }) } else { advance(); } @@ -887,7 +945,8 @@ showImage: this.showImage, uploadUrl: this.uploadUrl, uploader: this.uploader || this.$formulate.getUploader(), - immediateUpload: this.immediateUpload}, + uploadBehavior: this.uploadBehavior, + preventWindowDrops: this.preventWindowDrops}, this.typeContext)) }, nameOrFallback: nameOrFallback, @@ -1188,7 +1247,11 @@ type: [Function, Object, Boolean], default: false }, - immediateUpload: { + uploadBehavior: { + type: Boolean, + default: true + }, + preventWindowDrops: { type: Boolean, default: true } @@ -2206,18 +2269,52 @@ "ul", { staticClass: "formulate-files" }, _vm._l(_vm.fileUploads, function(file) { - return _c("li", { key: file.uuid, staticClass: "formulate-file" }, [ - _c("span", { - staticClass: "formualte-file-name", - domProps: { textContent: _vm._s(file.name) } - }), - _vm._v(" "), - file.progress > 0 && file.progress < 100 - ? _c("span", { - domProps: { textContent: _vm._s(file.progress + "%") } - }) - : _vm._e() - ]) + return _c( + "li", + { key: file.uuid, attrs: { "data-has-error": !!file.error } }, + [ + _c("div", { staticClass: "formulate-file" }, [ + _c("div", { + staticClass: "formualte-file-name", + domProps: { textContent: _vm._s(file.name) } + }), + _vm._v(" "), + file.progress !== false + ? _c( + "div", + { + staticClass: "formulate-file-progress", + attrs: { + "data-just-finished": file.justFinished, + "data-is-finished": + !file.justFinished && file.complete + } + }, + [ + _c("div", { + staticClass: "formulate-file-progress-inner", + style: { width: file.progress + "%" } + }) + ] + ) + : _vm._e(), + _vm._v(" "), + (file.complete && !file.justFinished) || file.progress === false + ? _c("div", { + staticClass: "formulate-file-remove", + on: { click: file.removeFile } + }) + : _vm._e() + ]), + _vm._v(" "), + file.error + ? _c("div", { + staticClass: "formulate-file-upload-error", + domProps: { textContent: _vm._s(file.error) } + }) + : _vm._e() + ] + ) }), 0 ) @@ -2270,16 +2367,36 @@ }, computed: { hasFiles: function hasFiles () { - return (this.context.model instanceof FileUpload && this.context.model.files.length) + return !!(this.context.model instanceof FileUpload && this.context.model.files.length) + } + }, + mounted: function mounted () { + // Add a listener to the window to prevent drag/drops that miss the dropzone + // from opening the file and navigating the user away from the page. + if (window && this.context.preventWindowDrops) { + window.addEventListener('dragover', this.preventDefault); + window.addEventListener('drop', this.preventDefault); + } + }, + destroyed: function destroyed () { + if (window && this.context.preventWindowDrops) { + window.removeEventListener('dragover', this.preventDefault); + window.removeEventListener('drop', this.preventDefault); } }, methods: { + preventDefault: function preventDefault (e) { + if (e.target.tagName !== 'INPUT' && e.target.getAttribute('type') !== 'file') { + e = e || event; + e.preventDefault(); + } + }, handleFile: function handleFile () { var input = this.$refs.file; if (input.files.length) { - this.context.model = this.$formulate.createUpload(input.files, this.context); + this.context.model = this.$formulate.createUpload(input, this.context); } - if (this.context.immediateUpload && this.context.model instanceof FileUpload) { + if (this.context.uploadBehavior === 'live' && this.context.model instanceof FileUpload) { this.context.model.upload(); } }, @@ -2825,6 +2942,7 @@ rules: rules, locale: 'en', uploader: fauxUploader, + uploadJustCompleteDuration: 1000, locales: { en: en } diff --git a/dist/snow.css b/dist/snow.css index 4f9360b..cc9cf17 100644 --- a/dist/snow.css +++ b/dist/snow.css @@ -19,7 +19,8 @@ list-style-type: none; padding: 0; margin: 0; } - .formulate-input .formulate-input-error { + .formulate-input .formulate-input-error, + .formulate-input .formulate-file-upload-error { color: #960505; font-size: .8em; font-weight: 300; @@ -220,9 +221,7 @@ .formulate-input[data-classification="file"] .formulate-input-upload-area { width: 100%; position: relative; - padding: 2em; } - .formulate-input[data-classification="file"] .formulate-input-upload-area[data-has-files] { - padding: 0; } + padding: 2em 0; } .formulate-input[data-classification="file"] .formulate-input-upload-area input { cursor: pointer; appearance: none; @@ -235,6 +234,10 @@ width: 100%; height: 100%; z-index: 5; } + .formulate-input[data-classification="file"] .formulate-input-upload-area[data-has-files] { + padding: 0; } + .formulate-input[data-classification="file"] .formulate-input-upload-area[data-has-files] input { + display: none; } .formulate-input[data-classification="file"] .formulate-input-upload-area-mask { border-radius: .4em; position: absolute; @@ -253,6 +256,8 @@ content: ''; background-color: #a8a8a8; mask-image: url('data:image/svg+xml;utf8,'); + mask-repeat: no-repeat; + mask-position: center; width: 2em; height: 2em; position: absolute; @@ -269,7 +274,98 @@ list-style-type: none; margin: 0; padding: 0; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-progress { + background-color: #cecece; + height: .3em; + border-radius: 1.25em; + width: 5em; + overflow: hidden; + position: absolute; + right: .75em; + transition: height .25s, width .25s; + z-index: 2; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-progress::before { + content: ''; + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + display: block; + opacity: 0; + transform: scale(0.08); + background-color: #ffffff; + mask-image: url('data:image/svg+xml;utf8,'); + mask-size: 77%; + mask-repeat: no-repeat; + mask-position: center; + z-index: 3; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-progress[data-just-finished] { + width: 1.25em; + height: 1.25em; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-progress[data-just-finished]::before { + transition: transform .25s .2s, opacity .25s .2s; + transform: scale(1); + opacity: 1; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-progress[data-is-finished] { + transition: height .25s, width .25s, left .25s, top, .25s, border-radius .25s; + width: .3em; + height: 100%; + right: 0; + border-radius: 0; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-progress[data-is-finished]::before { + transition: opacity .1s; + opacity: 0; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-progress .formulate-file-progress-inner { + background-color: #41b883; + width: 1%; + position: absolute; + left: 0; + bottom: 0; + top: 0; + z-index: 2; } + .formulate-input[data-classification="file"] .formulate-files .formualte-file-name { + padding-left: 1.5em; + padding-right: 2em; } + .formulate-input[data-classification="file"] .formulate-files .formualte-file-name::before { + position: absolute; + left: .7em; + top: 50%; + margin-top: -.7em; + background-color: #a8a8a8; + content: ''; + mask-image: url('data:image/svg+xml;utf8,'); + mask-repeat: no-repeat; + mask-size: contain; + width: 1.25em; + height: 1.25em; + display: inline-block; + margin-right: .5em; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file-remove { + width: 1.25em; + height: 1.25em; + border-radius: 1em; + border: 1px solid #a8a8a8; + background-color: #a8a8a8; + mask-image: url('data:image/svg+xml;utf8,'); + mask-size: .6em; + mask-repeat: no-repeat; + mask-position: center; + cursor: pointer; + position: absolute; + right: .75em; + z-index: 1; + transition: transform .25s; } + @media (pointer: fine) { + .formulate-input[data-classification="file"] .formulate-files .formulate-file-remove:hover { + transform: scale(1.5); } } .formulate-input[data-classification="file"] .formulate-files li { + display: block; } + .formulate-input[data-classification="file"] .formulate-files li[data-has-error] .formulate-file-progress { + background-color: #dc2c2c; } + .formulate-input[data-classification="file"] .formulate-files li + li { + margin-top: .5em; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file { appearance: none; border-radius: .3em; border: 1px solid #cecece; @@ -286,14 +382,19 @@ display: block; width: 100%; display: flex; - justify-content: space-between; } - .formulate-input[data-classification="file"] .formulate-files li::placeholder { + justify-content: space-between; + align-items: center; + position: relative; + overflow: hidden; } + .formulate-input[data-classification="file"] .formulate-files .formulate-file::placeholder { color: #a8a8a8; } - .formulate-input[data-classification="file"] .formulate-files li:focus { + .formulate-input[data-classification="file"] .formulate-files .formulate-file:focus { outline: 0; border: 1px solid #41b883; } - .formulate-input[data-classification="file"] .formulate-files li ::-webkit-progress-bar { + .formulate-input[data-classification="file"] .formulate-files .formulate-file ::-webkit-progress-bar { appearance: none; height: .5em; border-radius: .5em; overflow: hidden; } + .formulate-input[data-classification="file"] [data-type="image"] .formulate-input-upload-area .formulate-input-upload-area-mask::before { + mask-image: url('data:image/svg+xml;utf8,'); } diff --git a/dist/snow.min.css b/dist/snow.min.css index 8532588..d9304a4 100644 --- a/dist/snow.min.css +++ b/dist/snow.min.css @@ -1,2 +1,2 @@ -.formulate-input{margin-bottom:2em}.formulate-input .formulate-input-label{display:block;line-height:1.5;font-size:.9em;font-weight:600;margin-bottom:.1em}.formulate-input .formulate-input-element{max-width:20em;margin-bottom:.1em}.formulate-input .formulate-input-help{color:#6d6d6d;font-size:.7em;font-weight:400;line-height:1.5;margin-bottom:.25em}.formulate-input .formulate-input-errors{list-style-type:none;padding:0;margin:0}.formulate-input .formulate-input-error{color:#960505;font-size:.8em;font-weight:300;line-height:1.5;margin-bottom:.25em}.formulate-input .formulate-input-group-item{margin-bottom:.5em}.formulate-input:last-child{margin-bottom:0}.formulate-input[data-classification=text] input{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;padding:.75em;display:block;width:100%;font-weight:400;line-height:1.1em;margin:0}.formulate-input[data-classification=text] input::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input::placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=text] input[type=color]{height:1.1em;box-sizing:content-box}.formulate-input[data-classification=text] input[type=color]::-webkit-color-swatch-wrapper{padding:0 0 0 1.5em;display:-webkit-box;display:flex;-webkit-box-align:center;align-items:center;background-image:url('data:image/svg+xml;utf8,');background-repeat:no-repeat;background-size:.9em .9em;background-position:left .1em}.formulate-input[data-classification=text] input[type=color]::-webkit-color-swatch{display:block;height:1em;border-radius:.2em;border:0;-webkit-box-flex:1;flex:auto}.formulate-input[data-classification=text] input[type=color]::-moz-color-swatch{display:block;height:1em;border-radius:.2em;border:0;flex:auto}.formulate-input[data-classification=slider] input{-webkit-appearance:none;-moz-appearance:none;appearance:none;width:100%;font-size:1em;padding:.5em 0}.formulate-input[data-classification=slider] input:focus{outline:0}.formulate-input[data-classification=slider] input::-webkit-slider-thumb{cursor:pointer;-webkit-appearance:none;appearance:none;width:1em;height:1em;border-radius:1em;background-color:#41b883;margin-top:calc(-.5em + 2px)}.formulate-input[data-classification=slider] input::-moz-range-thumb{cursor:pointer;-moz-appearance:none;appearance:none;width:1em;height:1em;border-radius:1em;background-color:#41b883;margin-top:calc(-.5em + 2px)}.formulate-input[data-classification=slider] input::-ms-thumb{cursor:pointer;appearance:none;width:1em;height:1em;border-radius:1em;background-color:#41b883;margin-top:calc(-.5em + 2px)}.formulate-input[data-classification=slider] input::-webkit-slider-runnable-track{-webkit-appearance:none;appearance:none;width:100%;height:4px;background-color:#efefef;border-radius:3px;margin:0;padding:0}.formulate-input[data-classification=textarea] textarea{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;padding:.75em;display:block;width:100%;font-weight:400;line-height:1.1em;margin:0}.formulate-input[data-classification=textarea] textarea::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea::placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=select] .formulate-input-element{position:relative}.formulate-input[data-classification=select] .formulate-input-element:before{content:"";width:0;height:0;border-color:#cecece transparent transparent;border-style:solid;border-width:.3em .3em 0;top:50%;margin-top:-.1em;right:1em;position:absolute}.formulate-input[data-classification=select] select{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;display:block;width:100%;font-weight:400;line-height:1.1em;margin:0;padding:.75em 2em .75em .75em}.formulate-input[data-classification=select] select::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select::placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=select] select[data-placeholder-selected]{color:#a8a8a8}.formulate-input[data-classification=box] .formulate-input-element,.formulate-input[data-classification=box] .formulate-input-wrapper{display:-webkit-box;display:flex;-webkit-box-align:center;align-items:center}.formulate-input[data-classification=box] .formulate-input-element{overflow:hidden}.formulate-input[data-classification=box] .formulate-input-element input{position:absolute;left:-999px}.formulate-input[data-classification=box] .formulate-input-element-decorator{display:block;width:1em;height:1em;border-radius:.25em;border:1px solid #cecece;position:relative}.formulate-input[data-classification=box] .formulate-input-element-decorator:before{content:"";display:block;background-size:contain;background-position:100%;width:calc(100% - .125em);height:calc(100% - .125em);box-sizing:border-box;position:absolute;top:.0625em;left:.0625em}.formulate-input[data-classification=box] .formulate-input-element[data-type=radio] .formulate-input-element-decorator{border-radius:1em}.formulate-input[data-classification=box] .formulate-input-element[data-type=radio] .formulate-input-element-decorator:before{border-radius:1em;width:calc(100% - .5em);height:calc(100% - .5em);top:.25em;left:.25em}.formulate-input[data-classification=box] .formulate-input-element input[type=checkbox]:checked~.formulate-input-element-decorator{border-color:#41b883}.formulate-input[data-classification=box] .formulate-input-element input[type=checkbox]:checked~.formulate-input-element-decorator:before{background-color:#41b883;-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,')}.formulate-input[data-classification=box] .formulate-input-element input[type=radio]:checked~.formulate-input-element-decorator{border-color:#41b883}.formulate-input[data-classification=box] .formulate-input-element input[type=radio]:checked~.formulate-input-element-decorator:before{background-color:#41b883}.formulate-input[data-classification=box] .formulate-input-element input:focus~.formulate-input-element-decorator{border-color:#41b883}.formulate-input[data-classification=box] .formulate-input-label--after{margin-left:.5em}.formulate-input[data-classification=box] .formulate-input-label--before{margin-right:.5em}.formulate-input[data-classification=group]>.formulate-input-wrapper>.formulate-input-label{margin-bottom:.5em}.formulate-input[data-classification=file] .formulate-input-upload-area{width:100%;position:relative;padding:2em}.formulate-input[data-classification=file] .formulate-input-upload-area[data-has-files]{padding:0}.formulate-input[data-classification=file] .formulate-input-upload-area input{cursor:pointer;-webkit-appearance:none;-moz-appearance:none;appearance:none;opacity:0;position:absolute;left:0;right:0;bottom:0;top:0;width:100%;height:100%;z-index:5}.formulate-input[data-classification=file] .formulate-input-upload-area-mask{border-radius:.4em;pointer-events:none;position:absolute;display:-webkit-box;display:flex;-webkit-box-pack:center;justify-content:center;-webkit-box-align:center;align-items:center;left:0;right:0;top:0;bottom:0;border:2px dashed #a8a8a8;z-index:2}.formulate-input[data-classification=file] .formulate-input-upload-area-mask:before{content:"";background-color:#a8a8a8;-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,');width:2em;height:2em;position:absolute;pointer-events:none}.formulate-input[data-classification=file] .formulate-input-upload-area input:focus~.formulate-input-upload-area-mask,.formulate-input[data-classification=file] .formulate-input-upload-area input:hover~.formulate-input-upload-area-mask,.formulate-input[data-classification=file] .formulate-input-upload-area input[data-is-drag-hover]~.formulate-input-upload-area-mask{border-color:#41b883}.formulate-input[data-classification=file] .formulate-input-upload-area input:focus~.formulate-input-upload-area-mask:before,.formulate-input[data-classification=file] .formulate-input-upload-area input:hover~.formulate-input-upload-area-mask:before,.formulate-input[data-classification=file] .formulate-input-upload-area input[data-is-drag-hover]~.formulate-input-upload-area-mask:before{background-color:#41b883}.formulate-input[data-classification=file] .formulate-files{list-style-type:none;margin:0;padding:0}.formulate-input[data-classification=file] .formulate-files li{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;padding:.75em;font-weight:400;line-height:1.1em;margin:0;display:block;width:100%;display:-webkit-box;display:flex;-webkit-box-pack:justify;justify-content:space-between}.formulate-input[data-classification=file] .formulate-files li::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files li::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files li:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files li::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files li::placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files li:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=file] .formulate-files li ::-webkit-progress-bar{-webkit-appearance:none;appearance:none;height:.5em;border-radius:.5em;overflow:hidden} -/*# sourceMappingURL=data:application/json;base64,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QUFnQixDQURsQixzRkFDRSxhQUFnQixDQURsQiw0RUFDRSxhQUFnQixDQUNsQixxRUFDRSxTQUFVLENBQ1Ysd0JBQTJCLENBQzdCLHNGQUNFLHVCQUFnQixDQUFoQixlQUFnQixDQUNoQixXQUFZLENBQ1osa0JBQW1CLENBQ25CLGVBQWtCIiwiZmlsZSI6InN0ZGluIiwic291cmNlc0NvbnRlbnQiOlsiLmZvcm11bGF0ZS1pbnB1dCB7XG4gIG1hcmdpbi1ib3R0b206IDJlbTsgfVxuICAuZm9ybXVsYXRlLWlucHV0IC5mb3JtdWxhdGUtaW5wdXQtbGFiZWwge1xuICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgIGxpbmUtaGVpZ2h0OiAxLjU7XG4gICAgZm9udC1zaXplOiAuOWVtO1xuICAgIGZvbnQtd2VpZ2h0OiA2MDA7XG4gICAgbWFyZ2luLWJvdHRvbTogLjFlbTsgfVxuICAuZm9ybXVsYXRlLWlucHV0IC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCB7XG4gICAgbWF4LXdpZHRoOiAyMGVtO1xuICAgIG1hcmdpbi1ib3R0b206IC4xZW07IH1cbiAgLmZvcm11bGF0ZS1pbnB1dCAuZm9ybXVsYXRlLWlucHV0LWhlbHAge1xuICAgIGNvbG9yOiAjNmQ2ZDZkO1xuICAgIGZvbnQtc2l6ZTogLjdlbTtcbiAgICBmb250LXdlaWdodDogNDAwO1xuICAgIGxpbmUtaGVpZ2h0OiAxLjU7XG4gICAgbWFyZ2luLWJvdHRvbTogLjI1ZW07IH1cbiAgLmZvcm11bGF0ZS1pbnB1dCAuZm9ybXVsYXRlLWlucHV0LWVycm9ycyB7XG4gICAgbGlzdC1zdHlsZS10eXBlOiBub25lO1xuICAgIHBhZGRpbmc6IDA7XG4gICAgbWFyZ2luOiAwOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXQgLmZvcm11bGF0ZS1pbnB1dC1lcnJvciB7XG4gICAgY29sb3I6ICM5NjA1MDU7XG4gICAgZm9udC1zaXplOiAuOGVtO1xuICAgIGZvbnQtd2VpZ2h0OiAzMDA7XG4gICAgbGluZS1oZWlnaHQ6IDEuNTtcbiAgICBtYXJnaW4tYm90dG9tOiAuMjVlbTsgfVxuICAuZm9ybXVsYXRlLWlucHV0IC5mb3JtdWxhdGUtaW5wdXQtZ3JvdXAtaXRlbSB7XG4gICAgbWFyZ2luLWJvdHRvbTogLjVlbTsgfVxuICAuZm9ybXVsYXRlLWlucHV0Omxhc3QtY2hpbGQge1xuICAgIG1hcmdpbi1ib3R0b206IDA7IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSd0ZXh0J10gaW5wdXQge1xuICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgYm9yZGVyLXJhZGl1czogLjNlbTtcbiAgICBib3JkZXI6IDFweCBzb2xpZCAjY2VjZWNlO1xuICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gICAgYmFja2dyb3VuZC1jb2xvcjogdHJhbnNwYXJlbnQ7XG4gICAgZm9udC1zaXplOiAuOWVtO1xuICAgIGZvbnQtZmFtaWx5OiAtYXBwbGUtc3lzdGVtLCBCbGlua01hY1N5c3RlbUZvbnQsIFwiU2Vnb2UgVUlcIiwgUm9ib3RvLCBIZWx2ZXRpY2EsIEFyaWFsLCBzYW5zLXNlcmlmLCBcIkFwcGxlIENvbG9yIEVtb2ppXCIsIFwiU2Vnb2UgVUkgRW1vamlcIiwgXCJTZWdvZSBVSSBTeW1ib2xcIjtcbiAgICBwYWRkaW5nOiAuNzVlbTtcbiAgICBkaXNwbGF5OiBibG9jaztcbiAgICB3aWR0aDogMTAwJTtcbiAgICBmb250LXdlaWdodDogNDAwO1xuICAgIGxpbmUtaGVpZ2h0OiAxLjFlbTtcbiAgICBtYXJnaW46IDA7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHQnXSBpbnB1dDo6cGxhY2Vob2xkZXIge1xuICAgICAgY29sb3I6ICNhOGE4YTg7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHQnXSBpbnB1dDpmb2N1cyB7XG4gICAgICBvdXRsaW5lOiAwO1xuICAgICAgYm9yZGVyOiAxcHggc29saWQgIzQxYjg4MzsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHQnXSBpbnB1dFt0eXBlPVwiY29sb3JcIl0ge1xuICAgIGhlaWdodDogMS4xZW07XG4gICAgYm94LXNpemluZzogY29udGVudC1ib3g7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHQnXSBpbnB1dFt0eXBlPVwiY29sb3JcIl06Oi13ZWJraXQtY29sb3Itc3dhdGNoLXdyYXBwZXIge1xuICAgICAgcGFkZGluZzogMCAwIDAgMS41ZW07XG4gICAgICBkaXNwbGF5OiBmbGV4O1xuICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgICAgIGJhY2tncm91bmQtaW1hZ2U6IHVybCgnZGF0YTppbWFnZS9zdmcreG1sO3V0ZjgsPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCA3OS4xNyA3OS4xN1wiPjxwYXRoIGZpbGw9XCIlMjM2ZDZkNmRcIiBkPVwiTTQwLjgsMjIuOTJjLTMuNC0zLjQtNC43Ni04LjQ0LTEtMTIuMjRzOC44NC0yLjQ0LDEyLjI0LDFjNS01LDEwLjY5LTEzLjMzLDE4LjgxLTExLjMxYTExLDExLDAsMCwxLDcuNjIsMTQuMzRjLTEuMjYsMy40NS00LjYzLDYuMDYtNy4xNiw4LjU5LS45Mi45My0zLDIuMjYtMy40NiwzLjQ2LS40MiwxLDEuODIsMi42MywyLjM2LDRhOCw4LDAsMCwxLTEyLjQyLDkuMTljLS4yMS0uMTYtMS4zNS0xLjUxLTEuNTktMS41MXMtLjgzLjgzLTEsMUw0OS43MSw0NC45LDMyLjQzLDYyLjE4Yy0zLjM3LDMuMzgtNi42LDcuMTQtMTAuMjYsMTAuMjFhMTEsMTEsMCwwLDEtNC40OCwyLjI4Yy0xLjI1LjMtMy4xMS0uMjItNC4xOC4xOC0xLjI4LjQ4LTIuNDIsMi42NS0zLjY4LDMuNC02LjA1LDMuNjEtMTIuNjQtNC04LjQ2LTkuNTcuNzMtMSwyLjUzLTEuOTIsMy0zYTE0LjQ2LDE0LjQ2LDAsMCwwLS4wOS0yLjUyLDEwLjc1LDEwLjc1LDAsMCwxLDMuMTQtNi43N2MuOTItMSwxLjkzLTEuOTMsMi44OS0yLjlabTQuNC0xLjVjNC4xOSw0LDguMjQsOC4yNCwxMi4zNiwxMi4zNiwyLjA2LDIuMDYsNSw1LjU5LDgsMi42MSw0LjY1LTQuNjItNS02LjgtMi40Mi0xMC43OEM2Ni4zLDIwLjcsNzYuNCwxNi40OCw3NC44NCw5LjQ1LDczLjYyLDQsNjcuMTIsMi43OCw2My4yOSw2LjMyYy0yLjU1LDIuMzYtNC45Myw0Ljk0LTcuMzksNy40LS43OS43OC0xLjgsMi4yOC0yLjg4LDIuNzMtMi4xNC44OC0zLjQtMS42Mi00Ljc5LTIuNzctMi41OC0yLjE0LTYuODktLjgyLTYuNTMsM0M0MS44OSwxOC42OCw0My44NywyMC4wOSw0NS4yLDIxLjQyWm0tMS40NSw0LjQ0TDI3LjgyLDQxLjc5QzIyLDQ3LjU3LDE1Ljg5LDUzLjE0LDEwLjQxLDU5LjJhOC4yMyw4LjIzLDAsMCwwLTEuNDQsMmMtLjkzLDIsLjI1LDQuMTQtLjUsNlM0LjkyLDY5Ljk0LDQuMyw3MmEyLjM0LDIuMzQsMCwwLDAsMi41NiwzYzEuMTEtLjE3LDItMS4zMywyLjcxLTIuMDdhMTEuMTcsMTEuMTcsMCwwLDEsMi4wOC0yYzEuNjgtLjk0LDQsLjE3LDUuOTMtLjU3QzIwLDY5LjQxLDIyLDY2LjczLDIzLjc2LDY1TDM0LjQyLDU0LjMsNTMuMywzNS40MlpcIi8+PC9zdmc+Jyk7XG4gICAgICBiYWNrZ3JvdW5kLXJlcGVhdDogbm8tcmVwZWF0O1xuICAgICAgYmFja2dyb3VuZC1zaXplOiAuOWVtIC45ZW07XG4gICAgICBiYWNrZ3JvdW5kLXBvc2l0aW9uOiBsZWZ0IC4xZW07IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHQnXSBpbnB1dFt0eXBlPVwiY29sb3JcIl06Oi13ZWJraXQtY29sb3Itc3dhdGNoIHtcbiAgICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgICAgaGVpZ2h0OiAxZW07XG4gICAgICBib3JkZXItcmFkaXVzOiAuMmVtO1xuICAgICAgYm9yZGVyOiAwO1xuICAgICAgZmxleDogYXV0bzsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dCddIGlucHV0W3R5cGU9XCJjb2xvclwiXTo6LW1vei1jb2xvci1zd2F0Y2gge1xuICAgICAgZGlzcGxheTogYmxvY2s7XG4gICAgICBoZWlnaHQ6IDFlbTtcbiAgICAgIGJvcmRlci1yYWRpdXM6IC4yZW07XG4gICAgICBib3JkZXI6IDA7XG4gICAgICBmbGV4OiBhdXRvOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2xpZGVyJ10gaW5wdXQge1xuICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgd2lkdGg6IDEwMCU7XG4gICAgZm9udC1zaXplOiAxZW07XG4gICAgcGFkZGluZzogLjVlbSAwOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzbGlkZXInXSBpbnB1dDpmb2N1cyB7XG4gICAgICBvdXRsaW5lOiAwOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzbGlkZXInXSBpbnB1dDo6LXdlYmtpdC1zbGlkZXItdGh1bWIge1xuICAgICAgY3Vyc29yOiBwb2ludGVyO1xuICAgICAgYXBwZWFyYW5jZTogbm9uZTtcbiAgICAgIHdpZHRoOiAxZW07XG4gICAgICBoZWlnaHQ6IDFlbTtcbiAgICAgIGJvcmRlci1yYWRpdXM6IDFlbTtcbiAgICAgIGJhY2tncm91bmQtY29sb3I6ICM0MWI4ODM7XG4gICAgICBtYXJnaW4tdG9wOiBjYWxjKC0uNWVtICsgMnB4KTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2xpZGVyJ10gaW5wdXQ6Oi1tb3otcmFuZ2UtdGh1bWIge1xuICAgICAgY3Vyc29yOiBwb2ludGVyO1xuICAgICAgYXBwZWFyYW5jZTogbm9uZTtcbiAgICAgIHdpZHRoOiAxZW07XG4gICAgICBoZWlnaHQ6IDFlbTtcbiAgICAgIGJvcmRlci1yYWRpdXM6IDFlbTtcbiAgICAgIGJhY2tncm91bmQtY29sb3I6ICM0MWI4ODM7XG4gICAgICBtYXJnaW4tdG9wOiBjYWxjKC0uNWVtICsgMnB4KTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2xpZGVyJ10gaW5wdXQ6Oi1tcy10aHVtYiB7XG4gICAgICBjdXJzb3I6IHBvaW50ZXI7XG4gICAgICBhcHBlYXJhbmNlOiBub25lO1xuICAgICAgd2lkdGg6IDFlbTtcbiAgICAgIGhlaWdodDogMWVtO1xuICAgICAgYm9yZGVyLXJhZGl1czogMWVtO1xuICAgICAgYmFja2dyb3VuZC1jb2xvcjogIzQxYjg4MztcbiAgICAgIG1hcmdpbi10b3A6IGNhbGMoLS41ZW0gKyAycHgpOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzbGlkZXInXSBpbnB1dDo6LXdlYmtpdC1zbGlkZXItcnVubmFibGUtdHJhY2sge1xuICAgICAgYXBwZWFyYW5jZTogbm9uZTtcbiAgICAgIHdpZHRoOiAxMDAlO1xuICAgICAgaGVpZ2h0OiA0cHg7XG4gICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjZWZlZmVmO1xuICAgICAgYm9yZGVyLXJhZGl1czogM3B4O1xuICAgICAgbWFyZ2luOiAwO1xuICAgICAgcGFkZGluZzogMDsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHRhcmVhJ10gdGV4dGFyZWEge1xuICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgYm9yZGVyLXJhZGl1czogLjNlbTtcbiAgICBib3JkZXI6IDFweCBzb2xpZCAjY2VjZWNlO1xuICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gICAgYmFja2dyb3VuZC1jb2xvcjogdHJhbnNwYXJlbnQ7XG4gICAgZm9udC1zaXplOiAuOWVtO1xuICAgIGZvbnQtZmFtaWx5OiAtYXBwbGUtc3lzdGVtLCBCbGlua01hY1N5c3RlbUZvbnQsIFwiU2Vnb2UgVUlcIiwgUm9ib3RvLCBIZWx2ZXRpY2EsIEFyaWFsLCBzYW5zLXNlcmlmLCBcIkFwcGxlIENvbG9yIEVtb2ppXCIsIFwiU2Vnb2UgVUkgRW1vamlcIiwgXCJTZWdvZSBVSSBTeW1ib2xcIjtcbiAgICBwYWRkaW5nOiAuNzVlbTtcbiAgICBkaXNwbGF5OiBibG9jaztcbiAgICB3aWR0aDogMTAwJTtcbiAgICBmb250LXdlaWdodDogNDAwO1xuICAgIGxpbmUtaGVpZ2h0OiAxLjFlbTtcbiAgICBtYXJnaW46IDA7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHRhcmVhJ10gdGV4dGFyZWE6OnBsYWNlaG9sZGVyIHtcbiAgICAgIGNvbG9yOiAjYThhOGE4OyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSd0ZXh0YXJlYSddIHRleHRhcmVhOmZvY3VzIHtcbiAgICAgIG91dGxpbmU6IDA7XG4gICAgICBib3JkZXI6IDFweCBzb2xpZCAjNDFiODgzOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2VsZWN0J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IHtcbiAgICBwb3NpdGlvbjogcmVsYXRpdmU7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3NlbGVjdCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudDo6YmVmb3JlIHtcbiAgICAgIGNvbnRlbnQ6ICcnO1xuICAgICAgd2lkdGg6IDA7XG4gICAgICBoZWlnaHQ6IDA7XG4gICAgICBib3JkZXI6IC4zZW0gc29saWQgdHJhbnNwYXJlbnQ7XG4gICAgICBib3JkZXItdG9wLWNvbG9yOiAjY2VjZWNlO1xuICAgICAgYm9yZGVyLWJvdHRvbS13aWR0aDogMDtcbiAgICAgIHRvcDogNTAlO1xuICAgICAgbWFyZ2luLXRvcDogLS4xZW07XG4gICAgICByaWdodDogMWVtO1xuICAgICAgcG9zaXRpb246IGFic29sdXRlOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2VsZWN0J10gc2VsZWN0IHtcbiAgICBhcHBlYXJhbmNlOiBub25lO1xuICAgIGJvcmRlci1yYWRpdXM6IC4zZW07XG4gICAgYm9yZGVyOiAxcHggc29saWQgI2NlY2VjZTtcbiAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuICAgIGJhY2tncm91bmQtY29sb3I6IHRyYW5zcGFyZW50O1xuICAgIGZvbnQtc2l6ZTogLjllbTtcbiAgICBmb250LWZhbWlseTogLWFwcGxlLXN5c3RlbSwgQmxpbmtNYWNTeXN0ZW1Gb250LCBcIlNlZ29lIFVJXCIsIFJvYm90bywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZiwgXCJBcHBsZSBDb2xvciBFbW9qaVwiLCBcIlNlZ29lIFVJIEVtb2ppXCIsIFwiU2Vnb2UgVUkgU3ltYm9sXCI7XG4gICAgcGFkZGluZzogLjc1ZW07XG4gICAgZGlzcGxheTogYmxvY2s7XG4gICAgd2lkdGg6IDEwMCU7XG4gICAgZm9udC13ZWlnaHQ6IDQwMDtcbiAgICBsaW5lLWhlaWdodDogMS4xZW07XG4gICAgbWFyZ2luOiAwO1xuICAgIHBhZGRpbmctcmlnaHQ6IDJlbTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2VsZWN0J10gc2VsZWN0OjpwbGFjZWhvbGRlciB7XG4gICAgICBjb2xvcjogI2E4YThhODsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2VsZWN0J10gc2VsZWN0OmZvY3VzIHtcbiAgICAgIG91dGxpbmU6IDA7XG4gICAgICBib3JkZXI6IDFweCBzb2xpZCAjNDFiODgzOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzZWxlY3QnXSBzZWxlY3RbZGF0YS1wbGFjZWhvbGRlci1zZWxlY3RlZF0ge1xuICAgICAgY29sb3I6ICNhOGE4YTg7IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdib3gnXSAuZm9ybXVsYXRlLWlucHV0LXdyYXBwZXIge1xuICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCB7XG4gICAgb3ZlcmZsb3c6IGhpZGRlbjtcbiAgICBkaXNwbGF5OiBmbGV4O1xuICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCBpbnB1dCB7XG4gICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICBsZWZ0OiAtOTk5cHg7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3Ige1xuICAgICAgZGlzcGxheTogYmxvY2s7XG4gICAgICB3aWR0aDogMWVtO1xuICAgICAgaGVpZ2h0OiAxZW07XG4gICAgICBib3JkZXItcmFkaXVzOiAuMjVlbTtcbiAgICAgIGJvcmRlcjogMXB4IHNvbGlkICNjZWNlY2U7XG4gICAgICBwb3NpdGlvbjogcmVsYXRpdmU7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvcjo6YmVmb3JlIHtcbiAgICAgICAgY29udGVudDogJyc7XG4gICAgICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgICAgICBiYWNrZ3JvdW5kLXNpemU6IGNvbnRhaW47XG4gICAgICAgIGJhY2tncm91bmQtcG9zaXRpb246IHJpZ2h0O1xuICAgICAgICB3aWR0aDogY2FsYygxMDAlIC0gLjEyNWVtKTtcbiAgICAgICAgaGVpZ2h0OiBjYWxjKDEwMCUgLSAuMTI1ZW0pO1xuICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICAgIHRvcDogLjA2MjVlbTtcbiAgICAgICAgbGVmdDogLjA2MjVlbTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50W2RhdGEtdHlwZT1cInJhZGlvXCJdIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3Ige1xuICAgICAgYm9yZGVyLXJhZGl1czogMWVtOyB9XG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudFtkYXRhLXR5cGU9XCJyYWRpb1wiXSAuZm9ybXVsYXRlLWlucHV0LWVsZW1lbnQtZGVjb3JhdG9yOjpiZWZvcmUge1xuICAgICAgICBib3JkZXItcmFkaXVzOiAxZW07XG4gICAgICAgIHdpZHRoOiBjYWxjKDEwMCUgLSAuNWVtKTtcbiAgICAgICAgaGVpZ2h0OiBjYWxjKDEwMCUgLSAuNWVtKTtcbiAgICAgICAgdG9wOiAuMjVlbTtcbiAgICAgICAgbGVmdDogLjI1ZW07IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCBpbnB1dFt0eXBlPVwiY2hlY2tib3hcIl06Y2hlY2tlZCB+IC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3Ige1xuICAgICAgYm9yZGVyLWNvbG9yOiAjNDFiODgzOyB9XG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCBpbnB1dFt0eXBlPVwiY2hlY2tib3hcIl06Y2hlY2tlZCB+IC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3I6OmJlZm9yZSB7XG4gICAgICAgIGJhY2tncm91bmQtY29sb3I6ICM0MWI4ODM7XG4gICAgICAgIG1hc2staW1hZ2U6IHVybCgnZGF0YTppbWFnZS9zdmcreG1sO3V0ZjgsPHN2ZyB4bWxucz1cImh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnXCIgdmlld0JveD1cIjAgMCAxMDAgMTAwXCI+PHBhdGggZD1cIk04Ljc2LDU2LjJjLTYuMzgtNi4zNCwzLjI2LTE2LDkuNjQtOS42OUwzOCw2NS44OCw4MC41NiwyMy4yOWM2LjM4LTYuMzgsMTYuMDcsMy4zMiw5LjY5LDkuNjlMNDIuODQsODAuMzdhNi44Myw2LjgzLDAsMCwxLTkuNjUsMFpcIi8+PC9zdmc+Jyk7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCBpbnB1dFt0eXBlPVwicmFkaW9cIl06Y2hlY2tlZCB+IC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3Ige1xuICAgICAgYm9yZGVyLWNvbG9yOiAjNDFiODgzOyB9XG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCBpbnB1dFt0eXBlPVwicmFkaW9cIl06Y2hlY2tlZCB+IC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3I6OmJlZm9yZSB7XG4gICAgICAgIGJhY2tncm91bmQtY29sb3I6ICM0MWI4ODM7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCBpbnB1dDpmb2N1cyB+IC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3Ige1xuICAgICAgYm9yZGVyLWNvbG9yOiAjNDFiODgzOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1sYWJlbC0tYWZ0ZXIge1xuICAgIG1hcmdpbi1sZWZ0OiAuNWVtOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1sYWJlbC0tYmVmb3JlIHtcbiAgICBtYXJnaW4tcmlnaHQ6IC41ZW07IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZ3JvdXBcIl0gPiAuZm9ybXVsYXRlLWlucHV0LXdyYXBwZXIgPiAuZm9ybXVsYXRlLWlucHV0LWxhYmVsIHtcbiAgICBtYXJnaW4tYm90dG9tOiAuNWVtOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYSB7XG4gICAgd2lkdGg6IDEwMCU7XG4gICAgcG9zaXRpb246IHJlbGF0aXZlO1xuICAgIHBhZGRpbmc6IDJlbTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYVtkYXRhLWhhcy1maWxlc10ge1xuICAgICAgcGFkZGluZzogMDsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYSBpbnB1dCB7XG4gICAgICBjdXJzb3I6IHBvaW50ZXI7XG4gICAgICBhcHBlYXJhbmNlOiBub25lO1xuICAgICAgb3BhY2l0eTogMDtcbiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgIGxlZnQ6IDA7XG4gICAgICByaWdodDogMDtcbiAgICAgIGJvdHRvbTogMDtcbiAgICAgIHRvcDogMDtcbiAgICAgIHdpZHRoOiAxMDAlO1xuICAgICAgaGVpZ2h0OiAxMDAlO1xuICAgICAgei1pbmRleDogNTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrIHtcbiAgICAgIGJvcmRlci1yYWRpdXM6IC40ZW07XG4gICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICBwb2ludGVyLWV2ZW50czogbm9uZTtcbiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICBqdXN0aWZ5LWNvbnRlbnQ6IGNlbnRlcjtcbiAgICAgIGFsaWduLWl0ZW1zOiBjZW50ZXI7XG4gICAgICBsZWZ0OiAwO1xuICAgICAgcmlnaHQ6IDA7XG4gICAgICB0b3A6IDA7XG4gICAgICBib3R0b206IDA7XG4gICAgICBib3JkZXI6IDJweCBkYXNoZWQgI2E4YThhODtcbiAgICAgIHotaW5kZXg6IDI7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrOjpiZWZvcmUge1xuICAgICAgICBjb250ZW50OiAnJztcbiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogI2E4YThhODtcbiAgICAgICAgbWFzay1pbWFnZTogdXJsKCdkYXRhOmltYWdlL3N2Zyt4bWw7dXRmOCw8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDU4IDU4XCI+PHBhdGggZD1cIk0yOSw1OEEyOSwyOSwwLDEsMCwwLDI5LDI5LDI5LDAsMCwwLDI5LDU4Wk0yOSw0QTI1LDI1LDAsMSwxLDQsMjksMjUsMjUsMCwwLDEsMjksNFpcIi8+PHBvbHlnb24gcG9pbnRzPVwiMjcgMjIgMjcgNDQuNCAzMSA0NC40IDMxIDIyIDQxLjcgMzEuMSA0NC4zIDI4LjEgMjkgMTUgMTMuNyAyOC4xIDE2LjMgMzEuMSAyNyAyMlwiLz48L3N2Zz4nKTtcbiAgICAgICAgd2lkdGg6IDJlbTtcbiAgICAgICAgaGVpZ2h0OiAyZW07XG4gICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgICAgcG9pbnRlci1ldmVudHM6IG5vbmU7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEgaW5wdXQ6Zm9jdXMgfiAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhLW1hc2ssXG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhIGlucHV0OmhvdmVyIH4gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrLFxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYSBpbnB1dFtkYXRhLWlzLWRyYWctaG92ZXJdIH4gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrIHtcbiAgICAgIGJvcmRlci1jb2xvcjogIzQxYjg4MzsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhIGlucHV0OmZvY3VzIH4gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrOjpiZWZvcmUsXG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEgaW5wdXQ6aG92ZXIgfiAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhLW1hc2s6OmJlZm9yZSxcbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYSBpbnB1dFtkYXRhLWlzLWRyYWctaG92ZXJdIH4gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrOjpiZWZvcmUge1xuICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjNDFiODgzOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1maWxlcyB7XG4gICAgbGlzdC1zdHlsZS10eXBlOiBub25lO1xuICAgIG1hcmdpbjogMDtcbiAgICBwYWRkaW5nOiAwOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIGxpIHtcbiAgICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgICBib3JkZXItcmFkaXVzOiAuM2VtO1xuICAgICAgYm9yZGVyOiAxcHggc29saWQgI2NlY2VjZTtcbiAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gICAgICBiYWNrZ3JvdW5kLWNvbG9yOiB0cmFuc3BhcmVudDtcbiAgICAgIGZvbnQtc2l6ZTogLjllbTtcbiAgICAgIGZvbnQtZmFtaWx5OiAtYXBwbGUtc3lzdGVtLCBCbGlua01hY1N5c3RlbUZvbnQsIFwiU2Vnb2UgVUlcIiwgUm9ib3RvLCBIZWx2ZXRpY2EsIEFyaWFsLCBzYW5zLXNlcmlmLCBcIkFwcGxlIENvbG9yIEVtb2ppXCIsIFwiU2Vnb2UgVUkgRW1vamlcIiwgXCJTZWdvZSBVSSBTeW1ib2xcIjtcbiAgICAgIHBhZGRpbmc6IC43NWVtO1xuICAgICAgZGlzcGxheTogYmxvY2s7XG4gICAgICB3aWR0aDogMTAwJTtcbiAgICAgIGZvbnQtd2VpZ2h0OiA0MDA7XG4gICAgICBsaW5lLWhlaWdodDogMS4xZW07XG4gICAgICBtYXJnaW46IDA7XG4gICAgICBkaXNwbGF5OiBibG9jaztcbiAgICAgIHdpZHRoOiAxMDAlO1xuICAgICAgZGlzcGxheTogZmxleDtcbiAgICAgIGp1c3RpZnktY29udGVudDogc3BhY2UtYmV0d2VlbjsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIGxpOjpwbGFjZWhvbGRlciB7XG4gICAgICAgIGNvbG9yOiAjYThhOGE4OyB9XG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgbGk6Zm9jdXMge1xuICAgICAgICBvdXRsaW5lOiAwO1xuICAgICAgICBib3JkZXI6IDFweCBzb2xpZCAjNDFiODgzOyB9XG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgbGkgOjotd2Via2l0LXByb2dyZXNzLWJhciB7XG4gICAgICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgICAgIGhlaWdodDogLjVlbTtcbiAgICAgICAgYm9yZGVyLXJhZGl1czogLjVlbTtcbiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsgfVxuIl19 */ \ No newline at end of file +.formulate-input{margin-bottom:2em}.formulate-input .formulate-input-label{display:block;line-height:1.5;font-size:.9em;font-weight:600;margin-bottom:.1em}.formulate-input .formulate-input-element{max-width:20em;margin-bottom:.1em}.formulate-input .formulate-input-help{color:#6d6d6d;font-size:.7em;font-weight:400;line-height:1.5;margin-bottom:.25em}.formulate-input .formulate-input-errors{list-style-type:none;padding:0;margin:0}.formulate-input .formulate-file-upload-error,.formulate-input .formulate-input-error{color:#960505;font-size:.8em;font-weight:300;line-height:1.5;margin-bottom:.25em}.formulate-input .formulate-input-group-item{margin-bottom:.5em}.formulate-input:last-child{margin-bottom:0}.formulate-input[data-classification=text] input{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;padding:.75em;display:block;width:100%;font-weight:400;line-height:1.1em;margin:0}.formulate-input[data-classification=text] input::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input::placeholder{color:#a8a8a8}.formulate-input[data-classification=text] input:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=text] input[type=color]{height:1.1em;box-sizing:content-box}.formulate-input[data-classification=text] input[type=color]::-webkit-color-swatch-wrapper{padding:0 0 0 1.5em;display:-webkit-box;display:flex;-webkit-box-align:center;align-items:center;background-image:url('data:image/svg+xml;utf8,');background-repeat:no-repeat;background-size:.9em .9em;background-position:left .1em}.formulate-input[data-classification=text] input[type=color]::-webkit-color-swatch{display:block;height:1em;border-radius:.2em;border:0;-webkit-box-flex:1;flex:auto}.formulate-input[data-classification=text] input[type=color]::-moz-color-swatch{display:block;height:1em;border-radius:.2em;border:0;flex:auto}.formulate-input[data-classification=slider] input{-webkit-appearance:none;-moz-appearance:none;appearance:none;width:100%;font-size:1em;padding:.5em 0}.formulate-input[data-classification=slider] input:focus{outline:0}.formulate-input[data-classification=slider] input::-webkit-slider-thumb{cursor:pointer;-webkit-appearance:none;appearance:none;width:1em;height:1em;border-radius:1em;background-color:#41b883;margin-top:calc(-.5em + 2px)}.formulate-input[data-classification=slider] input::-moz-range-thumb{cursor:pointer;-moz-appearance:none;appearance:none;width:1em;height:1em;border-radius:1em;background-color:#41b883;margin-top:calc(-.5em + 2px)}.formulate-input[data-classification=slider] input::-ms-thumb{cursor:pointer;appearance:none;width:1em;height:1em;border-radius:1em;background-color:#41b883;margin-top:calc(-.5em + 2px)}.formulate-input[data-classification=slider] input::-webkit-slider-runnable-track{-webkit-appearance:none;appearance:none;width:100%;height:4px;background-color:#efefef;border-radius:3px;margin:0;padding:0}.formulate-input[data-classification=textarea] textarea{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;padding:.75em;display:block;width:100%;font-weight:400;line-height:1.1em;margin:0}.formulate-input[data-classification=textarea] textarea::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea::placeholder{color:#a8a8a8}.formulate-input[data-classification=textarea] textarea:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=select] .formulate-input-element{position:relative}.formulate-input[data-classification=select] .formulate-input-element:before{content:"";width:0;height:0;border-color:#cecece transparent transparent;border-style:solid;border-width:.3em .3em 0;top:50%;margin-top:-.1em;right:1em;position:absolute}.formulate-input[data-classification=select] select{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;display:block;width:100%;font-weight:400;line-height:1.1em;margin:0;padding:.75em 2em .75em .75em}.formulate-input[data-classification=select] select::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select::placeholder{color:#a8a8a8}.formulate-input[data-classification=select] select:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=select] select[data-placeholder-selected]{color:#a8a8a8}.formulate-input[data-classification=box] .formulate-input-element,.formulate-input[data-classification=box] .formulate-input-wrapper{display:-webkit-box;display:flex;-webkit-box-align:center;align-items:center}.formulate-input[data-classification=box] .formulate-input-element{overflow:hidden}.formulate-input[data-classification=box] .formulate-input-element input{position:absolute;left:-999px}.formulate-input[data-classification=box] .formulate-input-element-decorator{display:block;width:1em;height:1em;border-radius:.25em;border:1px solid #cecece;position:relative}.formulate-input[data-classification=box] .formulate-input-element-decorator:before{content:"";display:block;background-size:contain;background-position:100%;width:calc(100% - .125em);height:calc(100% - .125em);box-sizing:border-box;position:absolute;top:.0625em;left:.0625em}.formulate-input[data-classification=box] .formulate-input-element[data-type=radio] .formulate-input-element-decorator{border-radius:1em}.formulate-input[data-classification=box] .formulate-input-element[data-type=radio] .formulate-input-element-decorator:before{border-radius:1em;width:calc(100% - .5em);height:calc(100% - .5em);top:.25em;left:.25em}.formulate-input[data-classification=box] .formulate-input-element input[type=checkbox]:checked~.formulate-input-element-decorator{border-color:#41b883}.formulate-input[data-classification=box] .formulate-input-element input[type=checkbox]:checked~.formulate-input-element-decorator:before{background-color:#41b883;-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,')}.formulate-input[data-classification=box] .formulate-input-element input[type=radio]:checked~.formulate-input-element-decorator{border-color:#41b883}.formulate-input[data-classification=box] .formulate-input-element input[type=radio]:checked~.formulate-input-element-decorator:before{background-color:#41b883}.formulate-input[data-classification=box] .formulate-input-element input:focus~.formulate-input-element-decorator{border-color:#41b883}.formulate-input[data-classification=box] .formulate-input-label--after{margin-left:.5em}.formulate-input[data-classification=box] .formulate-input-label--before{margin-right:.5em}.formulate-input[data-classification=group]>.formulate-input-wrapper>.formulate-input-label{margin-bottom:.5em}.formulate-input[data-classification=file] .formulate-input-upload-area{width:100%;position:relative;padding:2em 0}.formulate-input[data-classification=file] .formulate-input-upload-area input{cursor:pointer;-webkit-appearance:none;-moz-appearance:none;appearance:none;opacity:0;position:absolute;left:0;right:0;bottom:0;top:0;width:100%;height:100%;z-index:5}.formulate-input[data-classification=file] .formulate-input-upload-area[data-has-files]{padding:0}.formulate-input[data-classification=file] .formulate-input-upload-area[data-has-files] input{display:none}.formulate-input[data-classification=file] .formulate-input-upload-area-mask{border-radius:.4em;pointer-events:none;position:absolute;display:-webkit-box;display:flex;-webkit-box-pack:center;justify-content:center;-webkit-box-align:center;align-items:center;left:0;right:0;top:0;bottom:0;border:2px dashed #a8a8a8;z-index:2}.formulate-input[data-classification=file] .formulate-input-upload-area-mask:before{content:"";background-color:#a8a8a8;-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,');-webkit-mask-repeat:no-repeat;mask-repeat:no-repeat;-webkit-mask-position:center;mask-position:center;width:2em;height:2em;position:absolute;pointer-events:none}.formulate-input[data-classification=file] .formulate-input-upload-area input:focus~.formulate-input-upload-area-mask,.formulate-input[data-classification=file] .formulate-input-upload-area input:hover~.formulate-input-upload-area-mask,.formulate-input[data-classification=file] .formulate-input-upload-area input[data-is-drag-hover]~.formulate-input-upload-area-mask{border-color:#41b883}.formulate-input[data-classification=file] .formulate-input-upload-area input:focus~.formulate-input-upload-area-mask:before,.formulate-input[data-classification=file] .formulate-input-upload-area input:hover~.formulate-input-upload-area-mask:before,.formulate-input[data-classification=file] .formulate-input-upload-area input[data-is-drag-hover]~.formulate-input-upload-area-mask:before{background-color:#41b883}.formulate-input[data-classification=file] .formulate-files{list-style-type:none;margin:0;padding:0}.formulate-input[data-classification=file] .formulate-files .formulate-file-progress{background-color:#cecece;height:.3em;border-radius:1.25em;width:5em;overflow:hidden;position:absolute;right:.75em;-webkit-transition:height .25s,width .25s;transition:height .25s,width .25s;z-index:2}.formulate-input[data-classification=file] .formulate-files .formulate-file-progress:before{content:"";position:absolute;top:0;left:0;right:0;bottom:0;display:block;opacity:0;-webkit-transform:scale(.08);transform:scale(.08);background-color:#fff;-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,');-webkit-mask-size:77%;mask-size:77%;-webkit-mask-repeat:no-repeat;mask-repeat:no-repeat;-webkit-mask-position:center;mask-position:center;z-index:3}.formulate-input[data-classification=file] .formulate-files .formulate-file-progress[data-just-finished]{width:1.25em;height:1.25em}.formulate-input[data-classification=file] .formulate-files .formulate-file-progress[data-just-finished]:before{-webkit-transition:opacity .25s .2s,-webkit-transform .25s .2s;transition:opacity .25s .2s,-webkit-transform .25s .2s;transition:transform .25s .2s,opacity .25s .2s;transition:transform .25s .2s,opacity .25s .2s,-webkit-transform .25s .2s;-webkit-transform:scale(1);transform:scale(1);opacity:1}.formulate-input[data-classification=file] .formulate-files .formulate-file-progress[data-is-finished]{-webkit-transition:height .25s,width .25s,left .25s,top,.25s,border-radius .25s;transition:height .25s,width .25s,left .25s,top,.25s,border-radius .25s;width:.3em;height:100%;right:0;border-radius:0}.formulate-input[data-classification=file] .formulate-files .formulate-file-progress[data-is-finished]:before{-webkit-transition:opacity .1s;transition:opacity .1s;opacity:0}.formulate-input[data-classification=file] .formulate-files .formulate-file-progress .formulate-file-progress-inner{background-color:#41b883;width:1%;position:absolute;left:0;bottom:0;top:0;z-index:2}.formulate-input[data-classification=file] .formulate-files .formualte-file-name{padding-left:1.5em;padding-right:2em}.formulate-input[data-classification=file] .formulate-files .formualte-file-name:before{position:absolute;left:.7em;top:50%;margin-top:-.7em;background-color:#a8a8a8;content:"";-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,');-webkit-mask-repeat:no-repeat;mask-repeat:no-repeat;-webkit-mask-size:contain;mask-size:contain;width:1.25em;height:1.25em;display:inline-block;margin-right:.5em}.formulate-input[data-classification=file] .formulate-files .formulate-file-remove{width:1.25em;height:1.25em;border-radius:1em;border:1px solid #a8a8a8;background-color:#a8a8a8;-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,');-webkit-mask-size:.6em;mask-size:.6em;-webkit-mask-repeat:no-repeat;mask-repeat:no-repeat;-webkit-mask-position:center;mask-position:center;cursor:pointer;position:absolute;right:.75em;z-index:1;-webkit-transition:-webkit-transform .25s;transition:-webkit-transform .25s;transition:transform .25s;transition:transform .25s,-webkit-transform .25s}@media (pointer:fine){.formulate-input[data-classification=file] .formulate-files .formulate-file-remove:hover{-webkit-transform:scale(1.5);transform:scale(1.5)}}.formulate-input[data-classification=file] .formulate-files li{display:block}.formulate-input[data-classification=file] .formulate-files li[data-has-error] .formulate-file-progress{background-color:#dc2c2c}.formulate-input[data-classification=file] .formulate-files li+li{margin-top:.5em}.formulate-input[data-classification=file] .formulate-files .formulate-file{-webkit-appearance:none;-moz-appearance:none;appearance:none;border-radius:.3em;border:1px solid #cecece;box-sizing:border-box;background-color:transparent;font-size:.9em;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica,Arial,sans-serif,Apple Color Emoji,Segoe UI Emoji,Segoe UI Symbol;padding:.75em;font-weight:400;line-height:1.1em;margin:0;display:block;width:100%;display:-webkit-box;display:flex;-webkit-box-pack:justify;justify-content:space-between;-webkit-box-align:center;align-items:center;position:relative;overflow:hidden}.formulate-input[data-classification=file] .formulate-files .formulate-file::-webkit-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files .formulate-file::-moz-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files .formulate-file:-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files .formulate-file::-ms-input-placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files .formulate-file::placeholder{color:#a8a8a8}.formulate-input[data-classification=file] .formulate-files .formulate-file:focus{outline:0;border:1px solid #41b883}.formulate-input[data-classification=file] .formulate-files .formulate-file ::-webkit-progress-bar{-webkit-appearance:none;appearance:none;height:.5em;border-radius:.5em;overflow:hidden}.formulate-input[data-classification=file] [data-type=image] .formulate-input-upload-area .formulate-input-upload-area-mask:before{-webkit-mask-image:url('data:image/svg+xml;utf8,');mask-image:url('data:image/svg+xml;utf8,')} +/*# sourceMappingURL=data:application/json;base64,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QVksQ0FDWixTQUFVLENBQ1YseUNBQTBCLENBQTFCLGlDQUEwQixDQUExQix5QkFBMEIsQ0FBMUIsZ0RBQTRCLENBQzVCLHNCQUNFLHlGQUNFLDRCQUFxQixDQUFyQixvQkFBdUIsQ0FBRSxDQUMvQiwrREFDRSxhQUFnQixDQUNoQix3R0FDRSx3QkFBMkIsQ0FDN0Isa0VBQ0UsZUFBa0IsQ0FDdEIsNEVBQ0UsdUJBQWdCLENBQWhCLG9CQUFnQixDQUFoQixlQUFnQixDQUNoQixrQkFBbUIsQ0FDbkIsd0JBQXlCLENBQ3pCLHFCQUFzQixDQUN0Qiw0QkFBNkIsQ0FDN0IsY0FBZSxDQUNmLHdJQUEwSixDQUMxSixhQUFjLENBR2QsZUFBZ0IsQ0FDaEIsaUJBQWtCLENBQ2xCLFFBQVMsQ0FDVCxhQUFjLENBQ2QsVUFBVyxDQUNYLG1CQUFhLENBQWIsWUFBYSxDQUNiLHdCQUE4QixDQUE5Qiw2QkFBOEIsQ0FDOUIsd0JBQW1CLENBQW5CLGtCQUFtQixDQUNuQixpQkFBa0IsQ0FDbEIsZUFBa0IsQ0FDbEIsdUdBQ0UsYUFBZ0IsQ0FEbEIsOEZBQ0UsYUFBZ0IsQ0FEbEIsa0dBQ0UsYUFBZ0IsQ0FEbEIsbUdBQ0UsYUFBZ0IsQ0FEbEIseUZBQ0UsYUFBZ0IsQ0FDbEIsa0ZBQ0UsU0FBVSxDQUNWLHdCQUEyQixDQUM3QixtR0FDRSx1QkFBZ0IsQ0FBaEIsZUFBZ0IsQ0FDaEIsV0FBWSxDQUNaLGtCQUFtQixDQUNuQixlQUFrQixDQUN4QixtSUFDRSwrYkFBd2IsQ0FBeGIsdWJBQTBiIiwiZmlsZSI6InN0ZGluIiwic291cmNlc0NvbnRlbnQiOlsiLmZvcm11bGF0ZS1pbnB1dCB7XG4gIG1hcmdpbi1ib3R0b206IDJlbTsgfVxuICAuZm9ybXVsYXRlLWlucHV0IC5mb3JtdWxhdGUtaW5wdXQtbGFiZWwge1xuICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgIGxpbmUtaGVpZ2h0OiAxLjU7XG4gICAgZm9udC1zaXplOiAuOWVtO1xuICAgIGZvbnQtd2VpZ2h0OiA2MDA7XG4gICAgbWFyZ2luLWJvdHRvbTogLjFlbTsgfVxuICAuZm9ybXVsYXRlLWlucHV0IC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudCB7XG4gICAgbWF4LXdpZHRoOiAyMGVtO1xuICAgIG1hcmdpbi1ib3R0b206IC4xZW07IH1cbiAgLmZvcm11bGF0ZS1pbnB1dCAuZm9ybXVsYXRlLWlucHV0LWhlbHAge1xuICAgIGNvbG9yOiAjNmQ2ZDZkO1xuICAgIGZvbnQtc2l6ZTogLjdlbTtcbiAgICBmb250LXdlaWdodDogNDAwO1xuICAgIGxpbmUtaGVpZ2h0OiAxLjU7XG4gICAgbWFyZ2luLWJvdHRvbTogLjI1ZW07IH1cbiAgLmZvcm11bGF0ZS1pbnB1dCAuZm9ybXVsYXRlLWlucHV0LWVycm9ycyB7XG4gICAgbGlzdC1zdHlsZS10eXBlOiBub25lO1xuICAgIHBhZGRpbmc6IDA7XG4gICAgbWFyZ2luOiAwOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXQgLmZvcm11bGF0ZS1pbnB1dC1lcnJvcixcbiAgLmZvcm11bGF0ZS1pbnB1dCAuZm9ybXVsYXRlLWZpbGUtdXBsb2FkLWVycm9yIHtcbiAgICBjb2xvcjogIzk2MDUwNTtcbiAgICBmb250LXNpemU6IC44ZW07XG4gICAgZm9udC13ZWlnaHQ6IDMwMDtcbiAgICBsaW5lLWhlaWdodDogMS41O1xuICAgIG1hcmdpbi1ib3R0b206IC4yNWVtOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXQgLmZvcm11bGF0ZS1pbnB1dC1ncm91cC1pdGVtIHtcbiAgICBtYXJnaW4tYm90dG9tOiAuNWVtOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXQ6bGFzdC1jaGlsZCB7XG4gICAgbWFyZ2luLWJvdHRvbTogMDsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHQnXSBpbnB1dCB7XG4gICAgYXBwZWFyYW5jZTogbm9uZTtcbiAgICBib3JkZXItcmFkaXVzOiAuM2VtO1xuICAgIGJvcmRlcjogMXB4IHNvbGlkICNjZWNlY2U7XG4gICAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgICBiYWNrZ3JvdW5kLWNvbG9yOiB0cmFuc3BhcmVudDtcbiAgICBmb250LXNpemU6IC45ZW07XG4gICAgZm9udC1mYW1pbHk6IC1hcHBsZS1zeXN0ZW0sIEJsaW5rTWFjU3lzdGVtRm9udCwgXCJTZWdvZSBVSVwiLCBSb2JvdG8sIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWYsIFwiQXBwbGUgQ29sb3IgRW1vamlcIiwgXCJTZWdvZSBVSSBFbW9qaVwiLCBcIlNlZ29lIFVJIFN5bWJvbFwiO1xuICAgIHBhZGRpbmc6IC43NWVtO1xuICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgIHdpZHRoOiAxMDAlO1xuICAgIGZvbnQtd2VpZ2h0OiA0MDA7XG4gICAgbGluZS1oZWlnaHQ6IDEuMWVtO1xuICAgIG1hcmdpbjogMDsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dCddIGlucHV0OjpwbGFjZWhvbGRlciB7XG4gICAgICBjb2xvcjogI2E4YThhODsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dCddIGlucHV0OmZvY3VzIHtcbiAgICAgIG91dGxpbmU6IDA7XG4gICAgICBib3JkZXI6IDFweCBzb2xpZCAjNDFiODgzOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dCddIGlucHV0W3R5cGU9XCJjb2xvclwiXSB7XG4gICAgaGVpZ2h0OiAxLjFlbTtcbiAgICBib3gtc2l6aW5nOiBjb250ZW50LWJveDsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dCddIGlucHV0W3R5cGU9XCJjb2xvclwiXTo6LXdlYmtpdC1jb2xvci1zd2F0Y2gtd3JhcHBlciB7XG4gICAgICBwYWRkaW5nOiAwIDAgMCAxLjVlbTtcbiAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICBhbGlnbi1pdGVtczogY2VudGVyO1xuICAgICAgYmFja2dyb3VuZC1pbWFnZTogdXJsKCdkYXRhOmltYWdlL3N2Zyt4bWw7dXRmOCw8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDc5LjE3IDc5LjE3XCI+PHBhdGggZmlsbD1cIiUyMzZkNmQ2ZFwiIGQ9XCJNNDAuOCwyMi45MmMtMy40LTMuNC00Ljc2LTguNDQtMS0xMi4yNHM4Ljg0LTIuNDQsMTIuMjQsMWM1LTUsMTAuNjktMTMuMzMsMTguODEtMTEuMzFhMTEsMTEsMCwwLDEsNy42MiwxNC4zNGMtMS4yNiwzLjQ1LTQuNjMsNi4wNi03LjE2LDguNTktLjkyLjkzLTMsMi4yNi0zLjQ2LDMuNDYtLjQyLDEsMS44MiwyLjYzLDIuMzYsNGE4LDgsMCwwLDEtMTIuNDIsOS4xOWMtLjIxLS4xNi0xLjM1LTEuNTEtMS41OS0xLjUxcy0uODMuODMtMSwxTDQ5LjcxLDQ0LjksMzIuNDMsNjIuMThjLTMuMzcsMy4zOC02LjYsNy4xNC0xMC4yNiwxMC4yMWExMSwxMSwwLDAsMS00LjQ4LDIuMjhjLTEuMjUuMy0zLjExLS4yMi00LjE4LjE4LTEuMjguNDgtMi40MiwyLjY1LTMuNjgsMy40LTYuMDUsMy42MS0xMi42NC00LTguNDYtOS41Ny43My0xLDIuNTMtMS45MiwzLTNhMTQuNDYsMTQuNDYsMCwwLDAtLjA5LTIuNTIsMTAuNzUsMTAuNzUsMCwwLDEsMy4xNC02Ljc3Yy45Mi0xLDEuOTMtMS45MywyLjg5LTIuOVptNC40LTEuNWM0LjE5LDQsOC4yNCw4LjI0LDEyLjM2LDEyLjM2LDIuMDYsMi4wNiw1LDUuNTksOCwyLjYxLDQuNjUtNC42Mi01LTYuOC0yLjQyLTEwLjc4QzY2LjMsMjAuNyw3Ni40LDE2LjQ4LDc0Ljg0LDkuNDUsNzMuNjIsNCw2Ny4xMiwyLjc4LDYzLjI5LDYuMzJjLTIuNTUsMi4zNi00LjkzLDQuOTQtNy4zOSw3LjQtLjc5Ljc4LTEuOCwyLjI4LTIuODgsMi43My0yLjE0Ljg4LTMuNC0xLjYyLTQuNzktMi43Ny0yLjU4LTIuMTQtNi44OS0uODItNi41MywzQzQxLjg5LDE4LjY4LDQzLjg3LDIwLjA5LDQ1LjIsMjEuNDJabS0xLjQ1LDQuNDRMMjcuODIsNDEuNzlDMjIsNDcuNTcsMTUuODksNTMuMTQsMTAuNDEsNTkuMmE4LjIzLDguMjMsMCwwLDAtMS40NCwyYy0uOTMsMiwuMjUsNC4xNC0uNSw2UzQuOTIsNjkuOTQsNC4zLDcyYTIuMzQsMi4zNCwwLDAsMCwyLjU2LDNjMS4xMS0uMTcsMi0xLjMzLDIuNzEtMi4wN2ExMS4xNywxMS4xNywwLDAsMSwyLjA4LTJjMS42OC0uOTQsNCwuMTcsNS45My0uNTdDMjAsNjkuNDEsMjIsNjYuNzMsMjMuNzYsNjVMMzQuNDIsNTQuMyw1My4zLDM1LjQyWlwiLz48L3N2Zz4nKTtcbiAgICAgIGJhY2tncm91bmQtcmVwZWF0OiBuby1yZXBlYXQ7XG4gICAgICBiYWNrZ3JvdW5kLXNpemU6IC45ZW0gLjllbTtcbiAgICAgIGJhY2tncm91bmQtcG9zaXRpb246IGxlZnQgLjFlbTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dCddIGlucHV0W3R5cGU9XCJjb2xvclwiXTo6LXdlYmtpdC1jb2xvci1zd2F0Y2gge1xuICAgICAgZGlzcGxheTogYmxvY2s7XG4gICAgICBoZWlnaHQ6IDFlbTtcbiAgICAgIGJvcmRlci1yYWRpdXM6IC4yZW07XG4gICAgICBib3JkZXI6IDA7XG4gICAgICBmbGV4OiBhdXRvOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSd0ZXh0J10gaW5wdXRbdHlwZT1cImNvbG9yXCJdOjotbW96LWNvbG9yLXN3YXRjaCB7XG4gICAgICBkaXNwbGF5OiBibG9jaztcbiAgICAgIGhlaWdodDogMWVtO1xuICAgICAgYm9yZGVyLXJhZGl1czogLjJlbTtcbiAgICAgIGJvcmRlcjogMDtcbiAgICAgIGZsZXg6IGF1dG87IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzbGlkZXInXSBpbnB1dCB7XG4gICAgYXBwZWFyYW5jZTogbm9uZTtcbiAgICB3aWR0aDogMTAwJTtcbiAgICBmb250LXNpemU6IDFlbTtcbiAgICBwYWRkaW5nOiAuNWVtIDA7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3NsaWRlciddIGlucHV0OmZvY3VzIHtcbiAgICAgIG91dGxpbmU6IDA7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3NsaWRlciddIGlucHV0Ojotd2Via2l0LXNsaWRlci10aHVtYiB7XG4gICAgICBjdXJzb3I6IHBvaW50ZXI7XG4gICAgICBhcHBlYXJhbmNlOiBub25lO1xuICAgICAgd2lkdGg6IDFlbTtcbiAgICAgIGhlaWdodDogMWVtO1xuICAgICAgYm9yZGVyLXJhZGl1czogMWVtO1xuICAgICAgYmFja2dyb3VuZC1jb2xvcjogIzQxYjg4MztcbiAgICAgIG1hcmdpbi10b3A6IGNhbGMoLS41ZW0gKyAycHgpOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzbGlkZXInXSBpbnB1dDo6LW1vei1yYW5nZS10aHVtYiB7XG4gICAgICBjdXJzb3I6IHBvaW50ZXI7XG4gICAgICBhcHBlYXJhbmNlOiBub25lO1xuICAgICAgd2lkdGg6IDFlbTtcbiAgICAgIGhlaWdodDogMWVtO1xuICAgICAgYm9yZGVyLXJhZGl1czogMWVtO1xuICAgICAgYmFja2dyb3VuZC1jb2xvcjogIzQxYjg4MztcbiAgICAgIG1hcmdpbi10b3A6IGNhbGMoLS41ZW0gKyAycHgpOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzbGlkZXInXSBpbnB1dDo6LW1zLXRodW1iIHtcbiAgICAgIGN1cnNvcjogcG9pbnRlcjtcbiAgICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgICB3aWR0aDogMWVtO1xuICAgICAgaGVpZ2h0OiAxZW07XG4gICAgICBib3JkZXItcmFkaXVzOiAxZW07XG4gICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjNDFiODgzO1xuICAgICAgbWFyZ2luLXRvcDogY2FsYygtLjVlbSArIDJweCk7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3NsaWRlciddIGlucHV0Ojotd2Via2l0LXNsaWRlci1ydW5uYWJsZS10cmFjayB7XG4gICAgICBhcHBlYXJhbmNlOiBub25lO1xuICAgICAgd2lkdGg6IDEwMCU7XG4gICAgICBoZWlnaHQ6IDRweDtcbiAgICAgIGJhY2tncm91bmQtY29sb3I6ICNlZmVmZWY7XG4gICAgICBib3JkZXItcmFkaXVzOiAzcHg7XG4gICAgICBtYXJnaW46IDA7XG4gICAgICBwYWRkaW5nOiAwOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dGFyZWEnXSB0ZXh0YXJlYSB7XG4gICAgYXBwZWFyYW5jZTogbm9uZTtcbiAgICBib3JkZXItcmFkaXVzOiAuM2VtO1xuICAgIGJvcmRlcjogMXB4IHNvbGlkICNjZWNlY2U7XG4gICAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgICBiYWNrZ3JvdW5kLWNvbG9yOiB0cmFuc3BhcmVudDtcbiAgICBmb250LXNpemU6IC45ZW07XG4gICAgZm9udC1mYW1pbHk6IC1hcHBsZS1zeXN0ZW0sIEJsaW5rTWFjU3lzdGVtRm9udCwgXCJTZWdvZSBVSVwiLCBSb2JvdG8sIEhlbHZldGljYSwgQXJpYWwsIHNhbnMtc2VyaWYsIFwiQXBwbGUgQ29sb3IgRW1vamlcIiwgXCJTZWdvZSBVSSBFbW9qaVwiLCBcIlNlZ29lIFVJIFN5bWJvbFwiO1xuICAgIHBhZGRpbmc6IC43NWVtO1xuICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgIHdpZHRoOiAxMDAlO1xuICAgIGZvbnQtd2VpZ2h0OiA0MDA7XG4gICAgbGluZS1oZWlnaHQ6IDEuMWVtO1xuICAgIG1hcmdpbjogMDsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0ndGV4dGFyZWEnXSB0ZXh0YXJlYTo6cGxhY2Vob2xkZXIge1xuICAgICAgY29sb3I6ICNhOGE4YTg7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3RleHRhcmVhJ10gdGV4dGFyZWE6Zm9jdXMge1xuICAgICAgb3V0bGluZTogMDtcbiAgICAgIGJvcmRlcjogMXB4IHNvbGlkICM0MWI4ODM7IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzZWxlY3QnXSAuZm9ybXVsYXRlLWlucHV0LWVsZW1lbnQge1xuICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nc2VsZWN0J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50OjpiZWZvcmUge1xuICAgICAgY29udGVudDogJyc7XG4gICAgICB3aWR0aDogMDtcbiAgICAgIGhlaWdodDogMDtcbiAgICAgIGJvcmRlcjogLjNlbSBzb2xpZCB0cmFuc3BhcmVudDtcbiAgICAgIGJvcmRlci10b3AtY29sb3I6ICNjZWNlY2U7XG4gICAgICBib3JkZXItYm90dG9tLXdpZHRoOiAwO1xuICAgICAgdG9wOiA1MCU7XG4gICAgICBtYXJnaW4tdG9wOiAtLjFlbTtcbiAgICAgIHJpZ2h0OiAxZW07XG4gICAgICBwb3NpdGlvbjogYWJzb2x1dGU7IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzZWxlY3QnXSBzZWxlY3Qge1xuICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgYm9yZGVyLXJhZGl1czogLjNlbTtcbiAgICBib3JkZXI6IDFweCBzb2xpZCAjY2VjZWNlO1xuICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gICAgYmFja2dyb3VuZC1jb2xvcjogdHJhbnNwYXJlbnQ7XG4gICAgZm9udC1zaXplOiAuOWVtO1xuICAgIGZvbnQtZmFtaWx5OiAtYXBwbGUtc3lzdGVtLCBCbGlua01hY1N5c3RlbUZvbnQsIFwiU2Vnb2UgVUlcIiwgUm9ib3RvLCBIZWx2ZXRpY2EsIEFyaWFsLCBzYW5zLXNlcmlmLCBcIkFwcGxlIENvbG9yIEVtb2ppXCIsIFwiU2Vnb2UgVUkgRW1vamlcIiwgXCJTZWdvZSBVSSBTeW1ib2xcIjtcbiAgICBwYWRkaW5nOiAuNzVlbTtcbiAgICBkaXNwbGF5OiBibG9jaztcbiAgICB3aWR0aDogMTAwJTtcbiAgICBmb250LXdlaWdodDogNDAwO1xuICAgIGxpbmUtaGVpZ2h0OiAxLjFlbTtcbiAgICBtYXJnaW46IDA7XG4gICAgcGFkZGluZy1yaWdodDogMmVtOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzZWxlY3QnXSBzZWxlY3Q6OnBsYWNlaG9sZGVyIHtcbiAgICAgIGNvbG9yOiAjYThhOGE4OyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdzZWxlY3QnXSBzZWxlY3Q6Zm9jdXMge1xuICAgICAgb3V0bGluZTogMDtcbiAgICAgIGJvcmRlcjogMXB4IHNvbGlkICM0MWI4ODM7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J3NlbGVjdCddIHNlbGVjdFtkYXRhLXBsYWNlaG9sZGVyLXNlbGVjdGVkXSB7XG4gICAgICBjb2xvcjogI2E4YThhODsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249J2JveCddIC5mb3JtdWxhdGUtaW5wdXQtd3JhcHBlciB7XG4gICAgZGlzcGxheTogZmxleDtcbiAgICBhbGlnbi1pdGVtczogY2VudGVyOyB9XG4gIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IHtcbiAgICBvdmVyZmxvdzogaGlkZGVuO1xuICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgYWxpZ24taXRlbXM6IGNlbnRlcjsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IGlucHV0IHtcbiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgIGxlZnQ6IC05OTlweDsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvciB7XG4gICAgICBkaXNwbGF5OiBibG9jaztcbiAgICAgIHdpZHRoOiAxZW07XG4gICAgICBoZWlnaHQ6IDFlbTtcbiAgICAgIGJvcmRlci1yYWRpdXM6IC4yNWVtO1xuICAgICAgYm9yZGVyOiAxcHggc29saWQgI2NlY2VjZTtcbiAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdib3gnXSAuZm9ybXVsYXRlLWlucHV0LWVsZW1lbnQtZGVjb3JhdG9yOjpiZWZvcmUge1xuICAgICAgICBjb250ZW50OiAnJztcbiAgICAgICAgZGlzcGxheTogYmxvY2s7XG4gICAgICAgIGJhY2tncm91bmQtc2l6ZTogY29udGFpbjtcbiAgICAgICAgYmFja2dyb3VuZC1wb3NpdGlvbjogcmlnaHQ7XG4gICAgICAgIHdpZHRoOiBjYWxjKDEwMCUgLSAuMTI1ZW0pO1xuICAgICAgICBoZWlnaHQ6IGNhbGMoMTAwJSAtIC4xMjVlbSk7XG4gICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgICAgdG9wOiAuMDYyNWVtO1xuICAgICAgICBsZWZ0OiAuMDYyNWVtOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdib3gnXSAuZm9ybXVsYXRlLWlucHV0LWVsZW1lbnRbZGF0YS10eXBlPVwicmFkaW9cIl0gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvciB7XG4gICAgICBib3JkZXItcmFkaXVzOiAxZW07IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50W2RhdGEtdHlwZT1cInJhZGlvXCJdIC5mb3JtdWxhdGUtaW5wdXQtZWxlbWVudC1kZWNvcmF0b3I6OmJlZm9yZSB7XG4gICAgICAgIGJvcmRlci1yYWRpdXM6IDFlbTtcbiAgICAgICAgd2lkdGg6IGNhbGMoMTAwJSAtIC41ZW0pO1xuICAgICAgICBoZWlnaHQ6IGNhbGMoMTAwJSAtIC41ZW0pO1xuICAgICAgICB0b3A6IC4yNWVtO1xuICAgICAgICBsZWZ0OiAuMjVlbTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IGlucHV0W3R5cGU9XCJjaGVja2JveFwiXTpjaGVja2VkIH4gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvciB7XG4gICAgICBib3JkZXItY29sb3I6ICM0MWI4ODM7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IGlucHV0W3R5cGU9XCJjaGVja2JveFwiXTpjaGVja2VkIH4gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvcjo6YmVmb3JlIHtcbiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogIzQxYjg4MztcbiAgICAgICAgbWFzay1pbWFnZTogdXJsKCdkYXRhOmltYWdlL3N2Zyt4bWw7dXRmOCw8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDEwMCAxMDBcIj48cGF0aCBkPVwiTTguNzYsNTYuMmMtNi4zOC02LjM0LDMuMjYtMTYsOS42NC05LjY5TDM4LDY1Ljg4LDgwLjU2LDIzLjI5YzYuMzgtNi4zOCwxNi4wNywzLjMyLDkuNjksOS42OUw0Mi44NCw4MC4zN2E2LjgzLDYuODMsMCwwLDEtOS42NSwwWlwiLz48L3N2Zz4nKTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IGlucHV0W3R5cGU9XCJyYWRpb1wiXTpjaGVja2VkIH4gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvciB7XG4gICAgICBib3JkZXItY29sb3I6ICM0MWI4ODM7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IGlucHV0W3R5cGU9XCJyYWRpb1wiXTpjaGVja2VkIH4gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvcjo6YmVmb3JlIHtcbiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogIzQxYjg4MzsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj0nYm94J10gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50IGlucHV0OmZvY3VzIH4gLmZvcm11bGF0ZS1pbnB1dC1lbGVtZW50LWRlY29yYXRvciB7XG4gICAgICBib3JkZXItY29sb3I6ICM0MWI4ODM7IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdib3gnXSAuZm9ybXVsYXRlLWlucHV0LWxhYmVsLS1hZnRlciB7XG4gICAgbWFyZ2luLWxlZnQ6IC41ZW07IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPSdib3gnXSAuZm9ybXVsYXRlLWlucHV0LWxhYmVsLS1iZWZvcmUge1xuICAgIG1hcmdpbi1yaWdodDogLjVlbTsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJncm91cFwiXSA+IC5mb3JtdWxhdGUtaW5wdXQtd3JhcHBlciA+IC5mb3JtdWxhdGUtaW5wdXQtbGFiZWwge1xuICAgIG1hcmdpbi1ib3R0b206IC41ZW07IH1cbiAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhIHtcbiAgICB3aWR0aDogMTAwJTtcbiAgICBwb3NpdGlvbjogcmVsYXRpdmU7XG4gICAgcGFkZGluZzogMmVtIDA7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEgaW5wdXQge1xuICAgICAgY3Vyc29yOiBwb2ludGVyO1xuICAgICAgYXBwZWFyYW5jZTogbm9uZTtcbiAgICAgIG9wYWNpdHk6IDA7XG4gICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICBsZWZ0OiAwO1xuICAgICAgcmlnaHQ6IDA7XG4gICAgICBib3R0b206IDA7XG4gICAgICB0b3A6IDA7XG4gICAgICB3aWR0aDogMTAwJTtcbiAgICAgIGhlaWdodDogMTAwJTtcbiAgICAgIHotaW5kZXg6IDU7IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWFbZGF0YS1oYXMtZmlsZXNdIHtcbiAgICAgIHBhZGRpbmc6IDA7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYVtkYXRhLWhhcy1maWxlc10gaW5wdXQge1xuICAgICAgICBkaXNwbGF5OiBub25lOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhLW1hc2sge1xuICAgICAgYm9yZGVyLXJhZGl1czogLjRlbTtcbiAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lO1xuICAgICAgcG9zaXRpb246IGFic29sdXRlO1xuICAgICAgZGlzcGxheTogZmxleDtcbiAgICAgIGp1c3RpZnktY29udGVudDogY2VudGVyO1xuICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgICAgIGxlZnQ6IDA7XG4gICAgICByaWdodDogMDtcbiAgICAgIHRvcDogMDtcbiAgICAgIGJvdHRvbTogMDtcbiAgICAgIGJvcmRlcjogMnB4IGRhc2hlZCAjYThhOGE4O1xuICAgICAgei1pbmRleDogMjsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhLW1hc2s6OmJlZm9yZSB7XG4gICAgICAgIGNvbnRlbnQ6ICcnO1xuICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjYThhOGE4O1xuICAgICAgICBtYXNrLWltYWdlOiB1cmwoJ2RhdGE6aW1hZ2Uvc3ZnK3htbDt1dGY4LDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgNTggNThcIj48cGF0aCBkPVwiTTI5LDU4QTI5LDI5LDAsMSwwLDAsMjksMjksMjksMCwwLDAsMjksNThaTTI5LDRBMjUsMjUsMCwxLDEsNCwyOSwyNSwyNSwwLDAsMSwyOSw0WlwiLz48cG9seWdvbiBwb2ludHM9XCIyNyAyMiAyNyA0NC40IDMxIDQ0LjQgMzEgMjIgNDEuNyAzMS4xIDQ0LjMgMjguMSAyOSAxNSAxMy43IDI4LjEgMTYuMyAzMS4xIDI3IDIyXCIvPjwvc3ZnPicpO1xuICAgICAgICBtYXNrLXJlcGVhdDogbm8tcmVwZWF0O1xuICAgICAgICBtYXNrLXBvc2l0aW9uOiBjZW50ZXI7XG4gICAgICAgIHdpZHRoOiAyZW07XG4gICAgICAgIGhlaWdodDogMmVtO1xuICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhIGlucHV0OmZvY3VzIH4gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrLFxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYSBpbnB1dDpob3ZlciB+IC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEtbWFzayxcbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEgaW5wdXRbZGF0YS1pcy1kcmFnLWhvdmVyXSB+IC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEtbWFzayB7XG4gICAgICBib3JkZXItY29sb3I6ICM0MWI4ODM7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYSBpbnB1dDpmb2N1cyB+IC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEtbWFzazo6YmVmb3JlLFxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhIGlucHV0OmhvdmVyIH4gLmZvcm11bGF0ZS1pbnB1dC11cGxvYWQtYXJlYS1tYXNrOjpiZWZvcmUsXG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEgaW5wdXRbZGF0YS1pcy1kcmFnLWhvdmVyXSB+IC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEtbWFzazo6YmVmb3JlIHtcbiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogIzQxYjg4MzsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMge1xuICAgIGxpc3Qtc3R5bGUtdHlwZTogbm9uZTtcbiAgICBtYXJnaW46IDA7XG4gICAgcGFkZGluZzogMDsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1maWxlcyAuZm9ybXVsYXRlLWZpbGUtcHJvZ3Jlc3Mge1xuICAgICAgYmFja2dyb3VuZC1jb2xvcjogI2NlY2VjZTtcbiAgICAgIGhlaWdodDogLjNlbTtcbiAgICAgIGJvcmRlci1yYWRpdXM6IDEuMjVlbTtcbiAgICAgIHdpZHRoOiA1ZW07XG4gICAgICBvdmVyZmxvdzogaGlkZGVuO1xuICAgICAgcG9zaXRpb246IGFic29sdXRlO1xuICAgICAgcmlnaHQ6IC43NWVtO1xuICAgICAgdHJhbnNpdGlvbjogaGVpZ2h0IC4yNXMsIHdpZHRoIC4yNXM7XG4gICAgICB6LWluZGV4OiAyOyB9XG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgLmZvcm11bGF0ZS1maWxlLXByb2dyZXNzOjpiZWZvcmUge1xuICAgICAgICBjb250ZW50OiAnJztcbiAgICAgICAgcG9zaXRpb246IGFic29sdXRlO1xuICAgICAgICB0b3A6IDA7XG4gICAgICAgIGxlZnQ6IDA7XG4gICAgICAgIHJpZ2h0OiAwO1xuICAgICAgICBib3R0b206IDA7XG4gICAgICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgICAgICBvcGFjaXR5OiAwO1xuICAgICAgICB0cmFuc2Zvcm06IHNjYWxlKDAuMDgpO1xuICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjZmZmZmZmO1xuICAgICAgICBtYXNrLWltYWdlOiB1cmwoJ2RhdGE6aW1hZ2Uvc3ZnK3htbDt1dGY4LDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgMTAwIDEwMFwiPjxwYXRoIGQ9XCJNOC43Niw1Ni4yYy02LjM4LTYuMzQsMy4yNi0xNiw5LjY0LTkuNjlMMzgsNjUuODgsODAuNTYsMjMuMjljNi4zOC02LjM4LDE2LjA3LDMuMzIsOS42OSw5LjY5TDQyLjg0LDgwLjM3YTYuODMsNi44MywwLDAsMS05LjY1LDBaXCIvPjwvc3ZnPicpO1xuICAgICAgICBtYXNrLXNpemU6IDc3JTtcbiAgICAgICAgbWFzay1yZXBlYXQ6IG5vLXJlcGVhdDtcbiAgICAgICAgbWFzay1wb3NpdGlvbjogY2VudGVyO1xuICAgICAgICB6LWluZGV4OiAzOyB9XG4gICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgLmZvcm11bGF0ZS1maWxlLXByb2dyZXNzW2RhdGEtanVzdC1maW5pc2hlZF0ge1xuICAgICAgICB3aWR0aDogMS4yNWVtO1xuICAgICAgICBoZWlnaHQ6IDEuMjVlbTsgfVxuICAgICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgLmZvcm11bGF0ZS1maWxlLXByb2dyZXNzW2RhdGEtanVzdC1maW5pc2hlZF06OmJlZm9yZSB7XG4gICAgICAgICAgdHJhbnNpdGlvbjogdHJhbnNmb3JtIC4yNXMgLjJzLCBvcGFjaXR5IC4yNXMgLjJzO1xuICAgICAgICAgIHRyYW5zZm9ybTogc2NhbGUoMSk7XG4gICAgICAgICAgb3BhY2l0eTogMTsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIC5mb3JtdWxhdGUtZmlsZS1wcm9ncmVzc1tkYXRhLWlzLWZpbmlzaGVkXSB7XG4gICAgICAgIHRyYW5zaXRpb246IGhlaWdodCAuMjVzLCB3aWR0aCAuMjVzLCBsZWZ0IC4yNXMsIHRvcCwgLjI1cywgYm9yZGVyLXJhZGl1cyAuMjVzO1xuICAgICAgICB3aWR0aDogLjNlbTtcbiAgICAgICAgaGVpZ2h0OiAxMDAlO1xuICAgICAgICByaWdodDogMDtcbiAgICAgICAgYm9yZGVyLXJhZGl1czogMDsgfVxuICAgICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgLmZvcm11bGF0ZS1maWxlLXByb2dyZXNzW2RhdGEtaXMtZmluaXNoZWRdOjpiZWZvcmUge1xuICAgICAgICAgIHRyYW5zaXRpb246IG9wYWNpdHkgLjFzO1xuICAgICAgICAgIG9wYWNpdHk6IDA7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1maWxlcyAuZm9ybXVsYXRlLWZpbGUtcHJvZ3Jlc3MgLmZvcm11bGF0ZS1maWxlLXByb2dyZXNzLWlubmVyIHtcbiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogIzQxYjg4MztcbiAgICAgICAgd2lkdGg6IDElO1xuICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICAgIGxlZnQ6IDA7XG4gICAgICAgIGJvdHRvbTogMDtcbiAgICAgICAgdG9wOiAwO1xuICAgICAgICB6LWluZGV4OiAyOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIC5mb3JtdWFsdGUtZmlsZS1uYW1lIHtcbiAgICAgIHBhZGRpbmctbGVmdDogMS41ZW07XG4gICAgICBwYWRkaW5nLXJpZ2h0OiAyZW07IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1maWxlcyAuZm9ybXVhbHRlLWZpbGUtbmFtZTo6YmVmb3JlIHtcbiAgICAgICAgcG9zaXRpb246IGFic29sdXRlO1xuICAgICAgICBsZWZ0OiAuN2VtO1xuICAgICAgICB0b3A6IDUwJTtcbiAgICAgICAgbWFyZ2luLXRvcDogLS43ZW07XG4gICAgICAgIGJhY2tncm91bmQtY29sb3I6ICNhOGE4YTg7XG4gICAgICAgIGNvbnRlbnQ6ICcnO1xuICAgICAgICBtYXNrLWltYWdlOiB1cmwoJ2RhdGE6aW1hZ2Uvc3ZnK3htbDt1dGY4LDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgNjQuMDYgODMuNTlcIj48cGF0aCBkPVwiTTU1Ljk0LDgzLjU5YTguMTYsOC4xNiwwLDAsMCw4LjEyLTguMTZWMTkuMTJhMS43NywxLjc3LDAsMCwwLS41Mi0xLjI1TDQ2LjIxLjU5QTEuNjksMS42OSwwLDAsMCw0NS4xNC4wOEw0NC42OSwwbC0uMTgsMEg4LjEzQTguMTgsOC4xOCwwLDAsMCwwLDguMTZWNzUuNDFhOC4xNiw4LjE2LDAsMCwwLDguMTMsOC4xNkg1NS45NFpNNDYuNjgsNiw1OC4xMSwxNy4zOEg0Ni42OFpNMy41Miw3NS40M1Y4LjE2QTQuNjQsNC42NCwwLDAsMSw4LjEzLDMuNTJoMzVWMTkuMTZhMS43NSwxLjc1LDAsMCwwLDEuNzYsMS43NEg2MC41NVY3NS40M2E0LjY1LDQuNjUsMCwwLDEtNC42MSw0LjY1SDguMTNBNC42NSw0LjY1LDAsMCwxLDMuNTIsNzUuNDNaXCIvPjwvc3ZnPicpO1xuICAgICAgICBtYXNrLXJlcGVhdDogbm8tcmVwZWF0O1xuICAgICAgICBtYXNrLXNpemU6IGNvbnRhaW47XG4gICAgICAgIHdpZHRoOiAxLjI1ZW07XG4gICAgICAgIGhlaWdodDogMS4yNWVtO1xuICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7XG4gICAgICAgIG1hcmdpbi1yaWdodDogLjVlbTsgfVxuICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1maWxlcyAuZm9ybXVsYXRlLWZpbGUtcmVtb3ZlIHtcbiAgICAgIHdpZHRoOiAxLjI1ZW07XG4gICAgICBoZWlnaHQ6IDEuMjVlbTtcbiAgICAgIGJvcmRlci1yYWRpdXM6IDFlbTtcbiAgICAgIGJvcmRlcjogMXB4IHNvbGlkICNhOGE4YTg7XG4gICAgICBiYWNrZ3JvdW5kLWNvbG9yOiAjYThhOGE4O1xuICAgICAgbWFzay1pbWFnZTogdXJsKCdkYXRhOmltYWdlL3N2Zyt4bWw7dXRmOCw8c3ZnIHhtbG5zPVwiaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmdcIiB2aWV3Qm94PVwiMCAwIDU5LjEgNTkuMlwiPjxwYXRoIGQ9XCJNMS42LDU3LjdhNSw1LDAsMCwwLDMuNSwxLjUsNC44NSw0Ljg1LDAsMCwwLDMuNS0xLjVsMjEtMjEsMjEsMjFhNSw1LDAsMCwwLDMuNSwxLjUsNC44NSw0Ljg1LDAsMCwwLDMuNS0xLjUsNSw1LDAsMCwwLDAtNy4xbC0yMS0yMSwyMS0yMWE1LDUsMCwwLDAsMC03LjEsNSw1LDAsMCwwLTcuMSwwbC0yMSwyMUw4LjYsMS43YTUsNSwwLDAsMC03LjEsMCw1LDUsMCwwLDAsMCw3LjFsMjEsMjFMMS42LDUwLjdBNC44Myw0LjgzLDAsMCwwLDEuNiw1Ny43WlwiLz48L3N2Zz4nKTtcbiAgICAgIG1hc2stc2l6ZTogLjZlbTtcbiAgICAgIG1hc2stcmVwZWF0OiBuby1yZXBlYXQ7XG4gICAgICBtYXNrLXBvc2l0aW9uOiBjZW50ZXI7XG4gICAgICBjdXJzb3I6IHBvaW50ZXI7XG4gICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICByaWdodDogLjc1ZW07XG4gICAgICB6LWluZGV4OiAxO1xuICAgICAgdHJhbnNpdGlvbjogdHJhbnNmb3JtIC4yNXM7IH1cbiAgICAgIEBtZWRpYSAocG9pbnRlcjogZmluZSkge1xuICAgICAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgLmZvcm11bGF0ZS1maWxlLXJlbW92ZTpob3ZlciB7XG4gICAgICAgICAgdHJhbnNmb3JtOiBzY2FsZSgxLjUpOyB9IH1cbiAgICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIC5mb3JtdWxhdGUtZmlsZXMgbGkge1xuICAgICAgZGlzcGxheTogYmxvY2s7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1maWxlcyBsaVtkYXRhLWhhcy1lcnJvcl0gLmZvcm11bGF0ZS1maWxlLXByb2dyZXNzIHtcbiAgICAgICAgYmFja2dyb3VuZC1jb2xvcjogI2RjMmMyYzsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIGxpICsgbGkge1xuICAgICAgICBtYXJnaW4tdG9wOiAuNWVtOyB9XG4gICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIC5mb3JtdWxhdGUtZmlsZSB7XG4gICAgICBhcHBlYXJhbmNlOiBub25lO1xuICAgICAgYm9yZGVyLXJhZGl1czogLjNlbTtcbiAgICAgIGJvcmRlcjogMXB4IHNvbGlkICNjZWNlY2U7XG4gICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuICAgICAgYmFja2dyb3VuZC1jb2xvcjogdHJhbnNwYXJlbnQ7XG4gICAgICBmb250LXNpemU6IC45ZW07XG4gICAgICBmb250LWZhbWlseTogLWFwcGxlLXN5c3RlbSwgQmxpbmtNYWNTeXN0ZW1Gb250LCBcIlNlZ29lIFVJXCIsIFJvYm90bywgSGVsdmV0aWNhLCBBcmlhbCwgc2Fucy1zZXJpZiwgXCJBcHBsZSBDb2xvciBFbW9qaVwiLCBcIlNlZ29lIFVJIEVtb2ppXCIsIFwiU2Vnb2UgVUkgU3ltYm9sXCI7XG4gICAgICBwYWRkaW5nOiAuNzVlbTtcbiAgICAgIGRpc3BsYXk6IGJsb2NrO1xuICAgICAgd2lkdGg6IDEwMCU7XG4gICAgICBmb250LXdlaWdodDogNDAwO1xuICAgICAgbGluZS1oZWlnaHQ6IDEuMWVtO1xuICAgICAgbWFyZ2luOiAwO1xuICAgICAgZGlzcGxheTogYmxvY2s7XG4gICAgICB3aWR0aDogMTAwJTtcbiAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICBqdXN0aWZ5LWNvbnRlbnQ6IHNwYWNlLWJldHdlZW47XG4gICAgICBhbGlnbi1pdGVtczogY2VudGVyO1xuICAgICAgcG9zaXRpb246IHJlbGF0aXZlO1xuICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIC5mb3JtdWxhdGUtZmlsZTo6cGxhY2Vob2xkZXIge1xuICAgICAgICBjb2xvcjogI2E4YThhODsgfVxuICAgICAgLmZvcm11bGF0ZS1pbnB1dFtkYXRhLWNsYXNzaWZpY2F0aW9uPVwiZmlsZVwiXSAuZm9ybXVsYXRlLWZpbGVzIC5mb3JtdWxhdGUtZmlsZTpmb2N1cyB7XG4gICAgICAgIG91dGxpbmU6IDA7XG4gICAgICAgIGJvcmRlcjogMXB4IHNvbGlkICM0MWI4ODM7IH1cbiAgICAgIC5mb3JtdWxhdGUtaW5wdXRbZGF0YS1jbGFzc2lmaWNhdGlvbj1cImZpbGVcIl0gLmZvcm11bGF0ZS1maWxlcyAuZm9ybXVsYXRlLWZpbGUgOjotd2Via2l0LXByb2dyZXNzLWJhciB7XG4gICAgICAgIGFwcGVhcmFuY2U6IG5vbmU7XG4gICAgICAgIGhlaWdodDogLjVlbTtcbiAgICAgICAgYm9yZGVyLXJhZGl1czogLjVlbTtcbiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjsgfVxuICAuZm9ybXVsYXRlLWlucHV0W2RhdGEtY2xhc3NpZmljYXRpb249XCJmaWxlXCJdIFtkYXRhLXR5cGU9XCJpbWFnZVwiXSAuZm9ybXVsYXRlLWlucHV0LXVwbG9hZC1hcmVhIC5mb3JtdWxhdGUtaW5wdXQtdXBsb2FkLWFyZWEtbWFzazo6YmVmb3JlIHtcbiAgICBtYXNrLWltYWdlOiB1cmwoJ2RhdGE6aW1hZ2Uvc3ZnK3htbDt1dGY4LDxzdmcgeG1sbnM9XCJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2Z1wiIHZpZXdCb3g9XCIwIDAgOTAgNzEuMDVcIj48cGF0aCBkPVwiTTgyLjg5LDBINy4xQTcuMTIsNy4xMiwwLDAsMCwwLDcuMTFWNjRhNy4xMSw3LjExLDAsMCwwLDcuMSw3LjFIODIuOUE3LjExLDcuMTEsMCwwLDAsOTAsNjRWNy4xMUE3LjEyLDcuMTIsMCwwLDAsODIuODksMFpNNjkuMjgsMzkuMzVhNS40NCw1LjQ0LDAsMCwwLTgsMEw1MC41OCw1MC43NCwzMi4zOCwzMC44OGE1LjMxLDUuMzEsMCwwLDAtNy45MiwwTDQuNzQsNTIuNFY3LjExQTIuMzcsMi4zNywwLDAsMSw3LjExLDQuNzRIODIuOWEyLjM3LDIuMzcsMCwwLDEsMi4zNiwyLjM3VjU2LjNaXCIvPjxjaXJjbGUgY3g9XCI2Ny43NFwiIGN5PVwiMjIuMjZcIiByPVwiOC41M1wiLz48L3N2Zz4nKTsgfVxuIl19 */ \ No newline at end of file diff --git a/src/FileUpload.js b/src/FileUpload.js index b13befe..85d222c 100644 --- a/src/FileUpload.js +++ b/src/FileUpload.js @@ -10,11 +10,12 @@ class FileUpload { * @param {FileList} fileList * @param {object} context */ - constructor (fileList, context, options) { - this.fileList = fileList + constructor (input, context, options) { + this.input = input + this.fileList = input.files this.files = [] this.options = options - this.setFileList(fileList) + this.addFileList(this.fileList) this.context = context } @@ -22,14 +23,22 @@ class FileUpload { * Produce an array of files and alert the callback. * @param {FileList} */ - setFileList (fileList) { + addFileList (fileList) { for (let i = 0; i < fileList.length; i++) { - const file = fileList.item(i) + const file = fileList[i] + const uuid = nanoid() + const removeFile = function () { + this.removeFile(uuid) + } this.files.push({ - progress: 0, + progress: false, + error: false, + complete: false, + justFinished: false, name: file.name || 'file-upload', - file: file, - uuid: nanoid() + file, + uuid, + removeFile: removeFile.bind(this) }) } } @@ -85,8 +94,21 @@ class FileUpload { Promise.all(this.files.map(file => { return this.getUploader( file.file, - (progress) => { file.progress = progress }, - (error) => reject(new Error(error)), + (progress) => { + file.progress = progress + if (progress >= 100) { + if (!file.complete) { + file.justFinished = true + setTimeout(() => { file.justFinished = false }, this.options.uploadJustCompleteDuration) + } + file.complete = true + } + }, + (error) => { + file.progress = 0 + file.error = error + file.complete = true + }, this.options ) })) @@ -95,6 +117,20 @@ class FileUpload { }) } + /** + * Remove a file from the uploader (and the file list) + * @param {string} uuid + */ + removeFile (uuid) { + this.files = this.files.filter(file => file.uuid !== uuid) + if (window) { + const transfer = new DataTransfer() + this.files.map(file => transfer.items.add(file.file)) + this.fileList = transfer.files + this.input.files = this.fileList + } + } + /** * Get the files. */ diff --git a/src/Formulate.js b/src/Formulate.js index 1fb38a1..2651721 100644 --- a/src/Formulate.js +++ b/src/Formulate.js @@ -40,6 +40,7 @@ class Formulate { rules, locale: 'en', uploader: fauxUploader, + uploadJustCompleteDuration: 1000, locales: { en } diff --git a/src/FormulateFiles.vue b/src/FormulateFiles.vue index b7392d5..6049c5d 100644 --- a/src/FormulateFiles.vue +++ b/src/FormulateFiles.vue @@ -6,15 +6,34 @@
  • - - +
    +
    +
    +
    +
    +
    +
  • diff --git a/src/FormulateInput.vue b/src/FormulateInput.vue index 8f85a2a..90f854e 100644 --- a/src/FormulateInput.vue +++ b/src/FormulateInput.vue @@ -149,7 +149,11 @@ export default { type: [Function, Object, Boolean], default: false }, - immediateUpload: { + uploadBehavior: { + type: Boolean, + default: true + }, + preventWindowDrops: { type: Boolean, default: true } diff --git a/src/inputs/FormulateInputFile.vue b/src/inputs/FormulateInputFile.vue index 078a2a9..1a7724d 100644 --- a/src/inputs/FormulateInputFile.vue +++ b/src/inputs/FormulateInputFile.vue @@ -48,16 +48,36 @@ export default { }, computed: { hasFiles () { - return (this.context.model instanceof FileUpload && this.context.model.files.length) + return !!(this.context.model instanceof FileUpload && this.context.model.files.length) + } + }, + mounted () { + // Add a listener to the window to prevent drag/drops that miss the dropzone + // from opening the file and navigating the user away from the page. + if (window && this.context.preventWindowDrops) { + window.addEventListener('dragover', this.preventDefault) + window.addEventListener('drop', this.preventDefault) + } + }, + destroyed () { + if (window && this.context.preventWindowDrops) { + window.removeEventListener('dragover', this.preventDefault) + window.removeEventListener('drop', this.preventDefault) } }, methods: { + preventDefault (e) { + if (e.target.tagName !== 'INPUT' && e.target.getAttribute('type') !== 'file') { + e = e || event + e.preventDefault() + } + }, handleFile () { const input = this.$refs.file if (input.files.length) { - this.context.model = this.$formulate.createUpload(input.files, this.context) + this.context.model = this.$formulate.createUpload(input, this.context) } - if (this.context.immediateUpload && this.context.model instanceof FileUpload) { + if (this.context.uploadBehavior === 'live' && this.context.model instanceof FileUpload) { this.context.model.upload() } }, diff --git a/src/libs/context.js b/src/libs/context.js index d45aeb0..02f2883 100644 --- a/src/libs/context.js +++ b/src/libs/context.js @@ -22,7 +22,8 @@ export default { showImage: this.showImage, uploadUrl: this.uploadUrl, uploader: this.uploader || this.$formulate.getUploader(), - immediateUpload: this.immediateUpload, + uploadBehavior: this.uploadBehavior, + preventWindowDrops: this.preventWindowDrops, ...this.typeContext }) }, diff --git a/src/libs/faux-uploader.js b/src/libs/faux-uploader.js index 672631c..2f6a0c4 100644 --- a/src/libs/faux-uploader.js +++ b/src/libs/faux-uploader.js @@ -8,14 +8,26 @@ */ export default function (file, progress, error, options) { return new Promise((resolve, reject) => { - const totalTime = options.fauxUploaderDuration || 2000 + const totalTime = (options.fauxUploaderDuration || 2000) * (0.5 + Math.random()) const start = performance.now() + /** + * @todo - remove, intentional failure + */ + const fail = (Math.random() > 0.5) const advance = () => setTimeout(() => { const elapsed = performance.now() - start const currentProgress = Math.min(100, Math.round(elapsed / totalTime * 100)) progress(currentProgress) + + /** + * @todo - remove, intentional failure + */ + if (fail && currentProgress > 50) { + return error('There was an error uploading the file.') + } + if (currentProgress >= 100) { - resolve({ + return resolve({ url: 'http://via.placeholder.com/350x150.png', name: file.name }) diff --git a/src/libs/rules.js b/src/libs/rules.js index 4be177a..8959009 100644 --- a/src/libs/rules.js +++ b/src/libs/rules.js @@ -149,14 +149,10 @@ export default { mime: function (files, ...types) { return Promise.resolve((() => { if (files instanceof FileUpload) { - if (files.hasUploader()) { - return false - } - files = files.getFiles() - } - if (typeof window !== 'undefined' && typeof FileReader !== 'undefined' && typeof Blob !== 'undefined') { - for (const i in files) { - if (!types.includes(files[i].type)) { + const fileList = files.getFileList() + for (let i = 0; i < fileList.length; i++) { + const file = fileList[i] + if (!types.includes(file.type)) { return false } } diff --git a/src/locales/en.js b/src/locales/en.js index bbc3310..1d40f27 100644 --- a/src/locales/en.js +++ b/src/locales/en.js @@ -113,6 +113,13 @@ export default { return `${s(name)} must be less than ${args[0]} characters long.` }, + /** + * The (field-level) error message for mime errors. + */ + mime: function ({ name, args }) { + return `${s(name)} must of the the type: ${args[0] || 'No file formats allowed.'}` + }, + /** * The maximum value allowed. */ diff --git a/test/FormulateInputBox.test.js b/test/FormulateInputBox.test.js index cbd17f1..b7f45a3 100644 --- a/test/FormulateInputBox.test.js +++ b/test/FormulateInputBox.test.js @@ -32,7 +32,6 @@ test('type "radio" with options renders a group', () => { expect(wrapper.contains(FormulateInputGroup)).toBe(true) }) - test('labelPosition of type "checkbox" defaults to after', () => { const wrapper = mount(FormulateInput, { propsData: { type: 'checkbox' } }) expect(wrapper.vm.context.labelPosition).toBe('after') diff --git a/test/rules.test.js b/test/rules.test.js index 3e6bb91..ae1538d 100644 --- a/test/rules.test.js +++ b/test/rules.test.js @@ -1,4 +1,5 @@ import rules from '@/libs/rules' +import FileUpload from '../src/FileUpload' /** * Required rule @@ -295,9 +296,26 @@ describe('email', () => { * Mime types. */ describe('mime', () => { - it('passes basic image/jpeg stack', async () => expect(await rules.mime([{type: 'image/jpeg'}], 'image/png', 'image/jpeg')).toBe(true)) + it('passes basic image/jpeg stack', async () => { + const fileUpload = new FileUpload({ + files: [ { type: 'image/jpeg' } ] + }) + expect(await rules.mime(fileUpload, 'image/png', 'image/jpeg')).toBe(true) + }) - it('fails when not in stack', async () => expect(await rules.mime([{type: 'application/json'}], 'image/png', 'image/jpeg')).toBe(false)) + it('passes when match is at begining of stack', async () => { + const fileUpload = new FileUpload({ + files: [ { type: 'document/pdf' } ] + }) + expect(await rules.mime(fileUpload, 'document/pdf')).toBe(true) + }) + + it('fails when not in stack', async () => { + const fileUpload = new FileUpload({ + files: [ { type: 'application/json' } ] + }) + expect(await rules.mime(fileUpload, 'image/png', 'image/jpeg')).toBe(false) + }) }) /** diff --git a/themes/snow/_inputs.scss b/themes/snow/_inputs.scss index ccde311..5eb32bd 100644 --- a/themes/snow/_inputs.scss +++ b/themes/snow/_inputs.scss @@ -31,7 +31,8 @@ margin: 0; } - .formulate-input-error { + .formulate-input-error, + .formulate-file-upload-error { color: $formulate-error; font-size: .8em; font-weight: 300; @@ -286,11 +287,7 @@ .formulate-input-upload-area { width: 100%; position: relative; - padding: 2em; - - &[data-has-files] { - padding: 0; - } + padding: 2em 0; input { cursor: pointer; @@ -306,6 +303,15 @@ z-index: 5; } + + &[data-has-files] { + padding: 0; + + input { + display: none; + } + } + &-mask { border-radius: .4em; position: absolute; @@ -325,6 +331,8 @@ content: ''; background-color: $formulate-gray-dd; mask-image: url('data:image/svg+xml;utf8,'); + mask-repeat: no-repeat; + mask-position: center; width: 2em; height: 2em; position: absolute; @@ -345,17 +353,145 @@ } } + + .formulate-files { list-style-type: none; margin: 0; padding: 0; + .formulate-file-progress { + background-color: $formulate-gray-d; + height: .3em; + border-radius: 1.25em; + width: 5em; + overflow: hidden; + position: absolute; + right: .75em; + transition: height .25s, width .25s; + z-index: 2; + + &::before { + content: ''; + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + display: block; + opacity: 0; + transform: scale(.08); + background-color: $formulate-white; + mask-image: url('data:image/svg+xml;utf8,'); + mask-size: 77%; + mask-repeat: no-repeat; + mask-position: center; + z-index: 3; + } + + &[data-just-finished] { + width: 1.25em; + height: 1.25em; + + &::before { + transition: transform .25s .2s, opacity .25s .2s; + transform: scale(1); + opacity: 1; + } + } + + &[data-is-finished] { + transition: height .25s, width .25s, left .25s, top, .25s, border-radius .25s; + width: .3em; + height: 100%; + right: 0; + border-radius: 0; + + + &::before { + transition: opacity .1s; + opacity: 0; + } + } + + .formulate-file-progress-inner { + background-color: $formulate-green; + width: 1%; + position: absolute; + left: 0; + bottom: 0; + top: 0; + z-index: 2; + } + } + + .formualte-file-name { + padding-left: 1.5em; + padding-right: 2em; + + &::before { + position: absolute; + left: .7em; + top: 50%; + margin-top: -.7em; + background-color: $formulate-gray-dd; + content: ''; + mask-image: url('data:image/svg+xml;utf8,'); + mask-repeat: no-repeat; + mask-size: contain; + width: 1.25em; + height: 1.25em; + display: inline-block; + margin-right: .5em; + } + } + + .formulate-file-remove { + width: 1.25em; + height: 1.25em; + border-radius: 1em; + border: 1px solid $formulate-gray-dd; + background-color: $formulate-gray-dd; + mask-image: url('data:image/svg+xml;utf8,'); + mask-size: .6em; + mask-repeat: no-repeat; + mask-position: center; + cursor: pointer; + position: absolute; + right: .75em; + z-index: 1; + transition: transform .25s; + + @media (pointer: fine) { + &:hover { + transform: scale(1.5); + } + } + } + li { + display: block; + + &[data-has-error] { + .formulate-file-progress { + background-color: $formulate-error-l; + } + } + + & + li { + margin-top: .5em; + } + } + + .formulate-file { @include baseinput; display: block; width: 100%; display: flex; justify-content: space-between; + align-items: center; + position: relative; + overflow: hidden; @mixin progress { appearance: none; @@ -369,5 +505,21 @@ } } } + + +// Image uploads +// ----------------------------------------------------------------------------- + + [data-type="image"] { + .formulate-input-upload-area { + .formulate-input-upload-area-mask { + &::before { + mask-image: url('data:image/svg+xml;utf8,'); + } + } + } + } + + } } diff --git a/themes/snow/_variables.scss b/themes/snow/_variables.scss index 80c6c7a..cbaa47e 100644 --- a/themes/snow/_variables.scss +++ b/themes/snow/_variables.scss @@ -16,11 +16,14 @@ $formulate-blue-l: #f3f4f4; $formulate-green: #41b883; $formulate-error: #960505; +$formulate-error-l: #dc2c2c; $formulate-yellow-d: #6b5900; $formulate-yellow: #e6c000; $formulate-yellow-l: #fff8d2; +$formulate-white: #ffffff; + // Mixins