diff --git a/base-component/tools/screen/System/LogViewer.xml b/base-component/tools/screen/System/LogViewer.xml
index fbd0ba730..8ec77b842 100644
--- a/base-component/tools/screen/System/LogViewer.xml
+++ b/base-component/tools/screen/System/LogViewer.xml
@@ -112,7 +112,7 @@ along with this software (see the LICENSE.md file). If not, see
All delay, run, etc times are in milliseconds (ms), rates in runs per second Average Run Time Runs per Second Entity Finds per Second Entity Writes per Second{{JSON.stringify(serviceInfo.lastResult, null, 2)}}
+
${ec.l10n.localize("Enter your username and password to sign in")}
--> <#-- not needed for this request: --> - disabled="disabled"#if> - required="required" class="form-control top" id="login_form_username" + required="required" class="form-control top" placeholder="${ec.l10n.localize("Username")}" aria-label="${ec.l10n.localize("Username")}"> <#-- secondFactorRequired will only be set if a user is pre-authenticated, and in that case password not required again --> <#if secondFactorRequired> - + <#else> @@ -56,16 +56,16 @@ <#if expiredCredentials>WARNING: Your password has expired
#if> <#if passwordChangeRequired>WARNING: Password change required
#if> -${ec.l10n.localize("Enter details to change your password")}
- disabled="disabled"#if> + required="required" class="form-control top" placeholder="${ec.l10n.localize("Username")}" aria-label="${ec.l10n.localize("Username")}"> <#-- secondFactorRequired will only be set if a user is pre-authenticated, and in that case password not required again --> <#if secondFactorRequired> - + <#else> + placeholder="${ec.l10n.localize("Old Password")}" aria-label="${ec.l10n.localize("Old Password")}"> #if> <#-- FUTURE: fancy JS to validate PW as it is entered or on blur --> + if (tabName === "login") { $("#login_form_code").focus(); } + else if (tabName === "change") { $("#change_form_code").focus(); } + else if (tabName === "reset") { $("#reset_form_username").focus(); } + <#else> + if (tabName === "login") { $("#login_form_username").focus(); } + else if (tabName === "change") { $("#change_form_username").focus(); } + else if (tabName === "reset") { $("#reset_form_username").focus(); } + #if> }); $('a[href="' + (location.hash || '${initialTab!"#login"}') + '"]').tab('show'); }) diff --git a/base-component/webroot/screen/webroot/css/WebrootVue.qvt.css b/base-component/webroot/screen/webroot/css/WebrootVue.qvt.css index 99099e090..1791f7a61 100644 --- a/base-component/webroot/screen/webroot/css/WebrootVue.qvt.css +++ b/base-component/webroot/screen/webroot/css/WebrootVue.qvt.css @@ -21,7 +21,7 @@ h6, .text-h6 { font-size:1.0rem; line-height:1.0rem; letter-spacing:initial; mar p { margin-bottom:8px; } /* orig 16px */ pre { text-wrap: normal; white-space: pre-line; word-wrap: normal; word-break: normal; } -body.dev #top { background: #0c1b29!important; } +body.dev #top { background: #5d5d5d!important; } body.test #top { background: #224422!important; } /* example for header that changes light and dark along with rest of screen: @@ -38,7 +38,9 @@ body.test.body--dark #top { background:#224422!important; color:white; } .body--dark .q-menu { background-color:black; } .body--dark img.invertible { -webkit-filter: invert(90%); filter: invert(90%); } -.q-dark, .q-card { background:transparent; } +@media (min-width:576px) { + .q-dark, .q-card { background:transparent; } +} .q-card__actions h5 { font-size: 1.1rem; display:inline-block; margin-block-start:0; margin-block-end:0; } .q-dialog .q-card { background-color:white; } .body--dark .q-dialog .q-card { background-color:black; } diff --git a/base-component/webroot/screen/webroot/js/MoquiLib.js b/base-component/webroot/screen/webroot/js/MoquiLib.js index 7ce729a26..9ea697027 100644 --- a/base-component/webroot/screen/webroot/js/MoquiLib.js +++ b/base-component/webroot/screen/webroot/js/MoquiLib.js @@ -200,8 +200,10 @@ var moqui = { return moment(value).format(format); } else if (type === "bigdecimal" || type === "currency") { // TODO format numbers with format string, localize - return value.toFixed(2).replace(/(\d)(?=(\d{3})+(?!\d))/g, '$1,'); + if (moqui.isNumber(value)) value = value.toFixed(2); + return ("" + value).replace(/(\d)(?=(\d{3})+(?!\d))/g, '$1,'); } else if (type === "long" || type === "integer" || type === "double" || type === "float") { + if (!moqui.isString(value)) value = "" + value; // TODO format numbers with format string, localize return value.replace(/(\d)(?=(\d{3})+(?!\d))/g, '$1,'); } else { diff --git a/base-component/webroot/screen/webroot/js/WebrootVue.qvt.js b/base-component/webroot/screen/webroot/js/WebrootVue.qvt.js index f6871f698..df3a7bbfb 100644 --- a/base-component/webroot/screen/webroot/js/WebrootVue.qvt.js +++ b/base-component/webroot/screen/webroot/js/WebrootVue.qvt.js @@ -141,9 +141,13 @@ moqui.handleAjaxError = function(jqXHR, textStatus, errorThrown, responseText) { /* Override moqui.notifyGrowl */ moqui.notifyGrowl = function(jsonObj) { if (!jsonObj) return; - // TODO: jsonObj.link, jsonObj.icon - moqui.webrootVue.$q.notify($.extend({}, moqui.notifyOptsInfo, { type:jsonObj.type, message:jsonObj.title })); - moqui.webrootVue.addNotify(jsonObj.title, jsonObj.type); + // TODO: jsonObj.icon + moqui.webrootVue.$q.notify($.extend({}, moqui.notifyOptsInfo, { type:jsonObj.type, message:jsonObj.title, + actions: [ + { label: 'View', color: 'white', handler: function () { moqui.webrootVue.setUrl(jsonObj.link); } } + ] + })); + moqui.webrootVue.addNotify(jsonObj.title, jsonObj.type, jsonObj.link, jsonObj.icon); }; /* ========== component loading methods ========== */ @@ -1005,7 +1009,7 @@ Vue.component('m-form-paginate', { name: "mFormPaginate", props: { paginate:Object, formList:Object }, template: - '', + mounted: function() { + var vm = this; + moqui.loadScript('https://cdnjs.cloudflare.com/ajax/libs/mermaid/9.3.0/mermaid.min.js', function(err) { + if (err) return; + mermaid.init(vm.config, vm.$refs.mermaid); + }, function() { return !!window.mermaid; }); } }); /* Lazy loading CK Editor wrapper component, based on https://github.com/ckeditor/ckeditor4-vue */ @@ -2229,13 +2262,13 @@ moqui.webrootVue = new Vue({ this.urlListeners.push(urlListenerFunction); }, - addNotify: function(message, type) { + addNotify: function(message, type, link, icon) { var histList = this.notifyHistoryList.slice(0); var nowDate = new Date(); var nh = nowDate.getHours(); if (nh < 10) nh = '0' + nh; var nm = nowDate.getMinutes(); if (nm < 10) nm = '0' + nm; // var ns = nowDate.getSeconds(); if (ns < 10) ns = '0' + ns; - histList.unshift({message:message, type:type, time:(nh + ':' + nm)}); // + ':' + ns + histList.unshift({message:message, type:type, time:(nh + ':' + nm), link:link, icon:icon}); // + ':' + ns while (histList.length > 25) { histList.pop(); } this.notifyHistoryList = histList; }, @@ -2384,6 +2417,14 @@ moqui.webrootVue = new Vue({ if (resp.loggedIn) { this.reLoginPostLogin(); } + }, + qLayoutMinHeight: function(offset) { + // "offset" is a Number (pixels) that refers to the total + // height of header + footer that occupies on screen, + // based on the QLayout "view" prop configuration + + // this is actually what the default style-fn does in Quasar + return { minHeight: offset ? `calc(100vh - ${offset}px)` : '100vh' } } }, watch: { diff --git a/template/screen-macro/DefaultScreenMacros.qvt.ftl b/template/screen-macro/DefaultScreenMacros.qvt.ftl index 3ec5cfc17..834ce2be0 100644 --- a/template/screen-macro/DefaultScreenMacros.qvt.ftl +++ b/template/screen-macro/DefaultScreenMacros.qvt.ftl @@ -69,6 +69,15 @@ along with this software (see the LICENSE.md file). If not, see #macro> <#macro "section-include"> <#if sri.doBoundaryComments()>#if> + <#assign sectionNode = sri.getSectionIncludedNode(.node)> + <#if sectionNode["@paginate"]! == "true"> + <#assign listName = sectionNode["@list"]> + <#assign listObj = context.get(listName)> + <#assign pagParms = Static["org.moqui.util.CollectionUtilities"].paginateParameters(listObj?size, listName, context)> +