Split admin css from app.css

Cleanup normalize and bootstrap css
Removed almost all css float
Removed CKEditor from app.css
This commit is contained in:
djmaze 2021-02-18 21:06:19 +01:00
parent 6dacfb3cf4
commit b6d8fa5b3f
74 changed files with 455 additions and 1014 deletions

View file

@ -137,11 +137,12 @@ For a user its around 65% smaller and faster than traditional RainLoop.
### CSS changes
* Solve jQuery removed "features" with native css code
* Cleanup unused css
* Themes work in mobile mode
* Bugfix invalid/conflicting css rules
* Use flexbox
* Split app.css to have seperate admin.css
* Remove oldschool 'float'
* Remove unused css
* Removed html.no-css
* Removed dev/Styles/Cmd.less
* Removed dev/Styles/Scroll.less
@ -163,10 +164,12 @@ For a user its around 65% smaller and faster than traditional RainLoop.
|css/* |RainLoop |Snappy |RL gzip |SM gzip |SM brotli |
|------------ |-------: |-------: |------: |------: |--------: |
|app.css | 340.334 | 139.393 | 46,959 | 23.019 | 19.624 |
|app.min.css | 274.791 | 114.661 | 39.618 | 20.495 | 17.899 |
|boot.css | | 1.836 | | 795 | 630 |
|boot.min.css | | 1.492 | | 707 | 555 |
|app.css | 340.334 | 115.927 | 46,959 | 19.501 | 16.699 |
|app.min.css | 274.791 | 96.071 | 39.618 | 17.475 | 15.295 |
|boot.css | | 2.066 | | 795 | 630 |
|boot.min.css | | 1.696 | | 707 | 555 |
|admin.css | | 53.966 | | 10.376 | 9.070 |
|admin.min.css | | 43.137 | | 9.126 | 8.133 |
### Squire vs CKEditor

44
dev/Styles/@Admin.less Normal file
View file

@ -0,0 +1,44 @@
@import "../../vendors/bootstrap/less/variables.less";
@import "../../vendors/bootstrap/less/mixins.less";
@import "_Values.less";
@import "../../vendors/bootstrap/less/grid.less";
@import "../../vendors/bootstrap/less/type.less";
@import "../../vendors/bootstrap/less/code.less";
@import "../../vendors/bootstrap/less/forms.less";
@import "../../vendors/bootstrap/less/tables.less";
@import "../../vendors/bootstrap/less/dropdowns.less";
@import "../../vendors/bootstrap/less/close.less";
@import "../../vendors/bootstrap/less/buttons.less";
@import "../../vendors/bootstrap/less/button-groups.less";
@import "../../vendors/bootstrap/less/alerts.less";
@import "../../vendors/bootstrap/less/modals.less";
@import "../../vendors/bootstrap/less/utilities.less";
@import "../../vendors/bootstrap/less/wells.less";
@import "_FontasticToBoot.less";
@import "_BootstrapFix.less";
@import "Ui.less";
@import "Main.less";
@import "Layout.less";
@import "Components.less";
@import "Login.less";
@import "Ask.less";
@import "Languages.less";
@import "Admin.less";
@import "AdminGeneral.less";
@import "AdminBranding.less";
@import "AdminDomains.less";
@import "AdminDomain.less";
@import "AdminPackages.less";
@import "AdminPlugins.less";
@import "AdminPlugin.less";
@import "AdminAbout.less";
@import "Animations.less";
@import "_End.less";

View file

@ -1,5 +1,11 @@
:root {
--fontSans: "DejaVu Sans", Verdana, Geneva, "Bitstream Vera Sans", "DejaVu LGC Sans", Arial, sans-serif;
--fontSerif: "Nimbus Roman No9 L", "Times New Roman", Times, FreeSerif, serif;
--fontMono: "Liberation Mono", Monaco, Menlo, Consolas, "Courier New", FreeMono, Courier, monospace;
}
html, body {
font-family: "DejaVu Sans", Verdana, Geneva, "Bitstream Vera Sans", "DejaVu LGC Sans", sans-serif;
font-family: var(--fontSans);
margin: 0;
padding: 0;
}

View file

@ -10,27 +10,27 @@
@import "../../vendors/bootstrap/less/forms.less";
@import "../../vendors/bootstrap/less/tables.less";
@import "../../vendors/bootstrap/less/dropdowns.less";
@import "../../vendors/bootstrap/less/wells.less";
@import "../../vendors/bootstrap/less/close.less";
@import "../../vendors/bootstrap/less/buttons.less";
@import "../../vendors/bootstrap/less/button-groups.less";
@import "../../vendors/bootstrap/less/alerts.less";
@import "../../vendors/bootstrap/less/navs.less";
@import "../../vendors/bootstrap/less/modals.less";
@import "../../vendors/bootstrap/less/labels-badges.less";
@import "../../vendors/bootstrap/less/utilities.less";
@import "../../vendors/bootstrap/less/navs.less";
@import "../../vendors/bootstrap/less/labels-badges.less";
@import "_FontasticToBoot.less";
@import "_BootstrapFix.less";
@import "_CkeFix.less";
@import "Ui.less";
@import "Main.less";
@import "Layout.less";
@import "Components.less";
@import "SystemDropDown.less";
@import "Login.less";
@import "Ask.less";
@import "Languages.less";
@import "SystemDropDown.less";
@import "Shortcuts.less";
@import "FolderList.less";
/*
@ -40,7 +40,6 @@
@import "Account.less";
*/
@import "Filter.less";
@import "Languages.less";
@import "Template.less";
@import "OpenPgpKey.less";
@import "TwoFactor.less";
@ -53,16 +52,6 @@
@import "Compose.less";
@import "EmailAddresses.less";
@import "Admin.less";
@import "AdminGeneral.less";
@import "AdminBranding.less";
@import "AdminDomains.less";
@import "AdminDomain.less";
@import "AdminPackages.less";
@import "AdminPlugins.less";
@import "AdminPlugin.less";
@import "AdminAbout.less";
@import "Settings.less";
@import "SettingsGeneral.less";
@import "SettingsAccounts.less";
@ -72,8 +61,12 @@
@import "SettingsThemes.less";
@import "SettingsFilters.less";
@import "Animations.less";
@import "SquireUI.less";
@import "AnimationsUser.less";
@import "Animations.less";
@import "_End.less";
/*
@import "_CkeFix.less";
*/

View file

@ -3,14 +3,7 @@
.rl-logo {
display: inline-block;
width: 250px;
height: 250px;
margin-top: -10px;
margin-bottom: -10px;
background-image: url("images/snappymail-logo.png");
}
.rl-desc {
margin-top: 20px;
margin-left: -20px;
height: 200px;
background: url("images/snappymail-logo.png") -30px -30px;
}
}

View file

@ -20,6 +20,7 @@
width: 1600px;
height: 400px;
left: 0;
transition: left 500ms ease;
}
&.domain-edit .modal-body {

View file

@ -25,6 +25,8 @@
.b-admin-plugin-property {
.help-block {
color: lighten(@textColor, 15%); // lighten the text some for contrast
display: block; // account for any element using help-block
margin-bottom: 5px;
}
}

View file

@ -1,12 +1,12 @@
#rl-popups {
.b-advanced-search-content {
&.modal {
width: 750px;
width: 780px;
.control-label {
width: 100px;
width: 110px;
}
.controls {
margin-left: 110px;
.span4 {
width: 360px;
}
}
}

View file

@ -1,22 +1,4 @@
.rl-strip-animation(@rgba, @stripOpacity) {
background-image: linear-gradient(135deg, rgba(@rgba, @rgba, @rgba, @stripOpacity) 25%, transparent 25%,
transparent 50%, rgba(@rgba, @rgba, @rgba, @stripOpacity) 50%, rgba(@rgba, @rgba, @rgba, @stripOpacity) 75%,
transparent 75%, transparent);
}
@keyframes highlight-folder-row {
0% { transform: scale(1); } 50% { transform: scale(1.1); } 100% { transform: scale(1); }
}
@keyframes textLoadingAnimationKeyFrame {
0% { opacity: 1; } 33% { opacity: 0; } 100% { opacity: 1; }
}
@keyframes animate-stripes {
0% {background-position: 0 0;} 100% {background-position: 60px 0;}
}
@keyframes login-form-shake {
0% {transform: translateX(0);}
12.5% {transform: translateX(-6px) rotateY(-5deg)}
@ -41,14 +23,6 @@ html.rl-started-delay {
}
}
html {
.e-strip-animation {
background-size: 60px 60px;
.rl-strip-animation(0, 0.1);
animation: animate-stripes 2s linear infinite;
}
}
@media screen and (min-width: 1000px) {
html.rl-started-trigger .b-login-content .loginFormWrapper {
@ -57,90 +31,38 @@ html {
opacity: 0.5;
}
html {
.b-login-content {
.alertError {
display: block;
opacity: 1;
transition: opacity 0.5s linear;
}
.alertError[hidden] {
opacity: 0;
}
}
.b-login-content .errorAnimated {
animation: login-form-shake 400ms ease-in-out;
}
.b-login-content .errorAnimated {
animation: login-form-shake 400ms ease-in-out;
}
.b-login-content .errorAnimated .buttonLogin {
color: #b94a48;
font-weight: bold;
}
.b-login-content .errorAnimated .buttonLogin {
color: #b94a48;
font-weight: bold;
}
.b-login-content .afterLoginHide {
opacity: 0;
}
.b-login-content .afterLoginHide {
opacity: 0;
}
.b-login-content .loginFormWrapper {
transition: all 0.3s ease-out;
}
.b-login-content .loginFormWrapper {
transition: all 0.3s ease-out;
}
.button-delete-transitions {
transition: all 0.2s linear;
}
& .button-delete-transitions {
transition: all 0.2s linear;
}
& .b-folders .e-item .anim-action-class {
animation: highlight-folder-row 0.5s linear;
}
& .b-folders .btn.buttonContacts {
transition: margin 0.3s linear;
}
& .b-folders .b-content.opacity-on-panel-disabled {
transition: opacity 0.3s linear;
}
& .messageList {
.messageListItem {
transition: max-height 400ms ease;
}
.listDragOver {
transition: all 400ms ease;
}
}
& .b-list-content {
.e-contact-item {
transition: max-height 400ms ease;
}
}
& .modal.b-domain-content {
.modal-body {
transition: left 500ms ease;
}
}
#rl-popups > .rl-view-model .modal {
transition: all .2s ease-out;
}
#rl-popups > .rl-view-model:not(.show) .modal {
top: -25%;
}
#rl-popups > .rl-view-model .modal.fade {
opacity: 1;
}
#rl-popups > .rl-view-model:not(.show) .modal.fade {
opacity: 0;
}
& .b-compose.loading .b-header-toolbar {
background-size: 60px 60px;
.rl-strip-animation(255, 0.2);
animation: animate-stripes 2s linear infinite;
}
#rl-popups > .rl-view-model .modal {
transition: all .2s ease-out;
}
#rl-popups > .rl-view-model:not(.show) .modal {
top: -25%;
}
#rl-popups > .rl-view-model .modal.fade {
opacity: 1;
}
#rl-popups > .rl-view-model:not(.show) .modal.fade {
opacity: 0;
}
}
@ -150,15 +72,3 @@ html {
#rl-popups > .rl-view-model:not(.show) {
background-color: rgba(0,0,0,0);
}
.textLoadingAnimationD1, .textLoadingAnimationD2, .textLoadingAnimationD3 {
animation: textLoadingAnimationKeyFrame 1s linear infinite 0s;
}
.textLoadingAnimationD2 {
animation-delay: 0.3s;
}
.textLoadingAnimationD3 {
animation-delay: 0.6s;
}

View file

@ -0,0 +1,83 @@
.rl-strip-animation(@rgba, @stripOpacity) {
background-image: linear-gradient(135deg, rgba(@rgba, @rgba, @rgba, @stripOpacity) 25%, transparent 25%,
transparent 50%, rgba(@rgba, @rgba, @rgba, @stripOpacity) 50%, rgba(@rgba, @rgba, @rgba, @stripOpacity) 75%,
transparent 75%, transparent);
}
@keyframes highlight-folder-row {
0% { transform: scale(1); }
50% { transform: scale(1.1); }
100% { transform: scale(1); }
}
@keyframes textLoadingAnimationKeyFrame {
0% { opacity: 1; }
33% { opacity: 0; }
100% { opacity: 1; }
}
@keyframes animate-stripes {
0% {background-position: 0 0;}
100% {background-position: 60px 0;}
}
html {
.e-strip-animation {
background-size: 60px 60px;
.rl-strip-animation(0, 0.1);
animation: animate-stripes 2s linear infinite;
}
}
@media screen and (min-width: 1000px) {
.button-delete-transitions {
transition: all 0.2s linear;
}
.b-folders .e-item .anim-action-class {
animation: highlight-folder-row 0.5s linear;
}
.b-folders .btn.buttonContacts {
transition: margin 0.3s linear;
}
.b-folders .b-content.opacity-on-panel-disabled {
transition: opacity 0.3s linear;
}
.messageList {
.messageListItem {
transition: max-height 400ms ease;
}
.listDragOver {
transition: all 400ms ease;
}
}
.b-list-content {
.e-contact-item {
transition: max-height 400ms ease;
}
}
.b-compose.loading .b-header-toolbar {
background-size: 60px 60px;
.rl-strip-animation(255, 0.2);
animation: animate-stripes 2s linear infinite;
}
}
.textLoadingAnimationD1, .textLoadingAnimationD2, .textLoadingAnimationD3 {
animation: textLoadingAnimationKeyFrame 1s linear infinite 0s;
}
.textLoadingAnimationD2 {
animation-delay: 0.3s;
}
.textLoadingAnimationD3 {
animation-delay: 0.6s;
}

View file

@ -45,7 +45,7 @@
height: 40px;
color: #fff;
background-color: rgba(0,0,0,0.8) !important;
background-color: rgba(0,0,0,0.8);
.close, .minimize-custom {
opacity: 1;
@ -123,7 +123,7 @@
padding: 2px 0;
textarea, input[type="text"] {
width: 98%;
width: 100%;
}
textarea {
height: 40px;

View file

@ -4,10 +4,11 @@
.b-contacts-content {
.control-group {
.control-label.fix-width {
.control-label {
padding-top: 0;
width: 50px;
}
.controls.fix-width {
.controls {
margin-left: 70px;
}
}
@ -32,11 +33,9 @@
.b-header-toolbar {
height: 40px;
background-color: rgba(0,0,0,0.8);
color: #fff;
background-color: rgba(0,0,0,0.8) !important;
height: 40px;
.close {
color: #fff;
@ -119,8 +118,7 @@
// }
.e-contact-item {
position: relative;
height: 45px;
display: flex;
max-height: 45px;
line-height: 45px;
overflow: hidden;
@ -129,7 +127,6 @@
margin: 0;
border: 0;
border-left: 6px solid #eee;
z-index: 100;
border-bottom: 1px solid #ddd;
&.focused {
@ -142,39 +139,21 @@
}
.checkboxItem {
display: inline-block;
float: left;
padding: 0 8px 0 6px;
line-height: 45px;
padding: 0 8px 0 6px;
}
.nameParent {
display: block;
overflow: hidden;
text-overflow: ellipsis;
color: #333;
font-size: 16px;
}
.nameParent, .emailParent {
white-space: nowrap;
}
.displayName, .displayEmail {
overflow: hidden;
text-overflow: ellipsis;
}
.displayImg {
display: inline-block;
float: right;
position: relative;
margin: 0 5px;
white-space: nowrap;
width: 100%;
}
&.checked {
border-left-color: #69A8F5;
z-index: 101;
&.focused {
border-left-color: darken(#69A8F5, 5%);
@ -185,7 +164,6 @@
background-color: #fff;
border-left-color: #398CF2;
z-index: 102;
&.focused {
border-left-color: darken(#398CF2, 5%);
@ -365,7 +343,6 @@
margin: 0;
border: 0;
z-index: 100;
border-bottom: 1px solid #ddd;
}
}

View file

@ -2,21 +2,13 @@
.b-identity-content {
&.modal {
width: 800px;
width: 770px;
}
.modal-body {
overflow: hidden;
}
.control-label {
width: 100px;
}
.controls {
margin-left: 120px;
}
.e-signature-place {
border: 1px solid #ccc;
border-radius: 3px;

View file

@ -61,7 +61,7 @@
padding-left: 12px;
padding-right: 12px;
}
.inputEmail, .inputPassword {
.inputEmail, .inputLogin, .inputPassword {
padding-right: 35px;
}
@ -145,6 +145,12 @@
left: 0;
right: 0;
z-index: 1;
display: block;
opacity: 1;
transition: opacity 0.5s linear;
}
.alert[hidden] {
opacity: 0;
}
.flag-selector {

View file

@ -46,10 +46,6 @@ option:disabled {
-webkit-tap-highlight-color: rgba(0,0,0,0);
}
input[type="search"]{
box-sizing: content-box;
}
.button-confirm-delete {
margin-right: 15px;
opacity: 0;

View file

@ -100,7 +100,7 @@ html.rl-no-preview-pane {
}
.inputSearch {
width: calc(100% - 14px);
width: 100%;
}
}
}

View file

@ -1,4 +1,8 @@
.g-ui-min-height-300 {
min-height: 300px;
}
.messageView {
z-index: 100;
@ -344,7 +348,6 @@
.bodyText {
color: #000;
font-family: Arial, Verdana, Geneva, sans-serif;
.b-text-part {
@ -404,7 +407,7 @@
}
img[data-x-src]:not([src]):hover::after {
content: attr(data-x-src);
font-family: sans-serif;
font-family: var(--fontSans);
height: auto;
transform: translate(-25%,0);
width: auto;
@ -420,7 +423,7 @@
background: #fff;
border: none;
border-radius: 0;
font-family: Monaco, Menlo, Consolas, 'Courier New', monospace;
font-family: var(--fontMono);
display: block;
word-break: normal;
word-wrap: break-word;
@ -447,14 +450,14 @@
padding: 15px;
/*white-space: pre-wrap;*/
font-family: Monaco, Menlo, Consolas, 'Courier New', monospace;
font-family: var(--fontMono);
pre {
margin: 0;
padding: 0;
background: #fff;
border: none;
font-family: Monaco, Menlo, Consolas, 'Courier New', monospace;
font-family: var(--fontMono);
display: block;
word-break: normal;
}
@ -497,7 +500,6 @@
display: inline-block;
cursor: pointer;
color: #777;
/*float: left;*/
&:hover {
color: #111;

View file

@ -6,7 +6,7 @@
}
.inputKey {
font-family: Monaco, Menlo, Consolas, "Courier New", monospace;
font-family: var(--fontMono);
}
.key-viewer {
@ -25,8 +25,6 @@
background-color: #f9f9f9;
border-radius: 5px;
padding: 10px 15px;
margin-top: 10px;
min-height: 40px;
&-wrp {
@ -51,6 +49,7 @@
color: #333;
white-space: nowrap;
padding-bottom: 4px;
display: flex;
&:last-child {
padding-bottom: 0;
@ -66,6 +65,7 @@
&-names {
color: #333;
width: 80%;
&.empty {
color: red;
@ -79,10 +79,12 @@
&-error {
color: red;
width: 80%;
}
&-hash {
color: #aaa;
width: 20%;
}
}
}

View file

@ -33,5 +33,5 @@
.b-filter-script textarea {
height: 300px;
font-family: Monaco, Menlo, Consolas, 'Courier New', monospace;
font-family: var(--fontMono);
}

View file

@ -1,5 +1,6 @@
#top-system-dropdown-id {
overflow: hidden;
padding-left: 10px;
padding-right: 10px;
}
@ -20,11 +21,6 @@
z-index: 103;
}
.dropdown-menu {
right: 0;
left: auto;
}
.email-title {
display: inline-block;
max-width: 200px;

View file

@ -19,10 +19,6 @@
}
}
.g-ui-min-height-300 {
min-height: 300px;
}
.g-ui-menu {
max-height: 400px;
max-width: 300px;

View file

@ -19,18 +19,14 @@ label.inline, span.inline {
border-bottom: 1px solid #e5e5e5;
small {
font-size: @baseLineHeight * .75;
color: @grayLight;
font-size: @baseLineHeight * .75;
color: @grayLight;
}
}
.legend + .control-group {
margin-top: @baseLineHeight;
-webkit-margin-top-collapse: separate;
}
.input-append input, .input-append select {
border-radius: 3px;
margin-top: @baseLineHeight;
-webkit-margin-top-collapse: separate;
}
.btn-small.btn-small-small {
@ -46,12 +42,6 @@ label.inline, span.inline {
padding: 4px 7px;
}
.btn.btn-ellipsis {
text-overflow: ellipsis;
overflow: hidden;
white-space: nowrap;
}
.btn.btn-transparent {
background: none !important;
border-color: transparent !important;
@ -102,20 +92,8 @@ label.inline, span.inline {
}
}
input:not([type="radio"]):not([type="checkbox"]):not([type="hidden"]) {
height: @baseLineHeight - (@rlInputBorderSize - 1) * 2;
line-height: @baseLineHeight - (@rlInputBorderSize - 1) * 2;
}
.alert a {
text-decoration: underline;
}
.alert.alert-null-left-margin {
margin-left: 0;
}
.alert a {
color: #c09853;
}
@ -127,21 +105,10 @@ input:not([type="radio"]):not([type="checkbox"]):not([type="hidden"]) {
color: #b94a48;
}
.nav-tabs > li > a {
color: #555;
}
.form-horizontal.long-label .control-group {
.control-label {
width: 160px;
}
.controls {
margin-left: 180px;
}
}
.control-label.remove-padding-top {
padding-top: 0;
}
/* mobile and tablet */
@ -160,10 +127,9 @@ input:not([type="radio"]):not([type="checkbox"]):not([type="hidden"]) {
.control-group {
.control-label {
text-align: left;
float: none;
}
.controls {
margin-left: 0;
margin-left: 10px;
}
}
}

View file

@ -64,7 +64,7 @@
}
.cke_source {
font-family: Monaco, Menlo, Consolas, 'Courier New', monospace !important;
font-family: var(--fontMono) !important;
padding: 10px !important;
padding-right: 0 !important;
box-shadow: none !important;
@ -82,7 +82,7 @@
padding: 10px;
padding-right: 0;
white-space: pre-wrap;
font-family: Monaco, Menlo, Consolas, 'Courier New', monospace;
font-family: var(--fontMono), monospace;
font-size: 13px;
line-height: 16px;
color: #333;
@ -107,7 +107,7 @@
.cke_wysiwyg_div {
padding: 10px !important;
font-family: arial, sans-serif;
font-family: var(--fontSans);
font-size: 13px;
line-height: 16px;
color: #333;
@ -132,7 +132,7 @@
background: #fff;
border: none;
border-radius: 0;
font-family: Monaco, Menlo, Consolas, 'Courier New', monospace;
font-family: var(--fontMono);
display: block;
word-break: normal;
word-wrap: break-word;

View file

@ -97,6 +97,6 @@
}
.fontastic.icon-spinner {
text-indent: -1em;
text-indent: -5em;
overflow: hidden;
}

View file

@ -99,6 +99,7 @@ if ($gzip = trim(`which gzip`)) {
echo "\x1b[33;1m === Gzip *.js and *.css === \x1b[0m\n";
passthru("{$gzip} -k --best {$cmddir}/js/*.js");
passthru("{$gzip} -k --best {$cmddir}/js/min/*.js");
passthru("{$gzip} -k --best {$cmddir}/css/admin*.css");
passthru("{$gzip} -k --best {$cmddir}/css/app*.css");
unlink(__DIR__ . '/snappymail/v/0.0.0/static/js/boot.js.gz');
unlink(__DIR__ . '/snappymail/v/0.0.0/static/js/min/boot.min.js.gz');
@ -108,6 +109,7 @@ if ($brotli = trim(`which brotli`)) {
echo "\x1b[33;1m === Brotli *.js and *.css === \x1b[0m\n";
passthru("{$brotli} -k --best {$cmddir}/js/*.js");
passthru("{$brotli} -k --best {$cmddir}/js/min/*.js");
passthru("{$brotli} -k --best {$cmddir}/css/admin*.css");
passthru("{$brotli} -k --best {$cmddir}/css/app*.css");
unlink(__DIR__ . '/snappymail/v/0.0.0/static/js/boot.js.br');
unlink(__DIR__ . '/snappymail/v/0.0.0/static/js/min/boot.min.js.br');

View file

@ -230,7 +230,7 @@ class Service
'{{BaseAppBodyScript}}' => '',
'{{BaseAppFaviconPngLinkTag}}' => $sFaviconPngLink ? '<link type="image/png" rel="shortcut icon" href="'.$sFaviconPngLink.'" />' : '',
'{{BaseAppFaviconTouchLinkTag}}' => $sAppleTouchLink ? '<link type="image/png" rel="apple-touch-icon" href="'.$sAppleTouchLink.'" />' : '',
'{{BaseAppMainCssLink}}' => $this->staticPath('css/app'.($bAppCssDebug ? '' : '.min').'.css'),
'{{BaseAppMainCssLink}}' => $this->staticPath('css/'.($bAdmin ? 'admin' : 'app').($bAppCssDebug ? '' : '.min').'.css'),
'{{BaseAppThemeCssLink}}' => $this->oActions->ThemeLink($sTheme, $bAdmin),
'{{BaseAppPolyfillsScriptLink}}' => '',
'{{BaseAppBootScriptLink}}' => $this->staticPath('js/'.($bAppJsDebug ? '' : 'min/').'boot'.($bAppJsDebug ? '' : '.min').'.js'),

View file

@ -103,7 +103,7 @@ nl_NL:
TAB_ABOUT:
LEGEND_ABOUT: "Over"
LABEL_TAG_HINT: "Simpel, modern en snelle web-based e-mail client"
LABEL_ALL_RIGHTS_RESERVED: "Alle rechten gereserveerd."
LABEL_ALL_RIGHTS_RESERVED: "Alle rechten voorbehouden."
POPUPS_DOMAIN_ALIAS:
TITLE_ADD_DOMAIN_ALIAS: "Voeg alias toe"
LABEL_ALIAS: "Alias"

View file

@ -192,7 +192,7 @@ nl_NL:
ATTACHMENTS_UPLOAD_ERROR_DESC: "Toevoegen van bijlage(n) is nog niet gereed"
BUTTON_REQUEST_READ_RECEIPT: "Leesbevestiging vragen"
BUTTON_MARK_AS_IMPORTANT: "Markeer als belangrijk"
BUTTON_OPEN_PGP: "OpenPGP (allen bij Platte Tekst)"
BUTTON_OPEN_PGP: "OpenPGP (alleen bij Platte Tekst)"
BUTTON_REQUEST_DSN: "Ontvangstbevestiging vragen"
POPUPS_ASK:
BUTTON_YES: "Ja"

View file

@ -1,6 +1,6 @@
<div class="b-login-content">
<div class="loginFormWrapper" data-bind="css: {'afterLoginHide': formHidden}">
<div class="alert alertError" data-bind="visible: '' !== submitError()">
<div class="alert" data-bind="hidden: !submitError()">
<button type="button" class="close" data-bind="click: function () { submitError('') }">×</button>
<span data-bind="text: submitError"></span>
</div>

View file

@ -10,12 +10,12 @@
<div class="b-admin-menu" data-bind="foreach: menu">
<!-- ko if: disabled -->
<span class="e-item disabled">
<span class="i18n e-link" data-bind="attr: { 'data-i18n': label }"></span>
<span class="e-link" data-bind="attr: { 'data-i18n': label }"></span>
</span>
<!-- /ko -->
<!-- ko ifnot: disabled -->
<a class="e-item selectable" href="#" data-bind="css: {'selected': selected }, attr: { 'href': $root.link(route) }">
<span class="i18n e-link" data-bind="attr: { 'data-i18n': label }"></span>
<span class="e-link" data-bind="attr: { 'data-i18n': label }"></span>
</a>
<!-- /ko -->
</div>

View file

@ -4,13 +4,13 @@
<div class="row" style="min-width: 800px;">
<div class="span4">
<div class="rl-logo"></div>
<div style="margin-left: 30px;">
<div>
2021 © <span data-i18n="TAB_ABOUT/LABEL_ALL_RIGHTS_RESERVED"></span>
<br />
<a class="g-ui-link" href="https://snappymail.eu/" target="_blank" style="padding-left: 0">https://snappymail.eu/</a>
</div>
</div>
<div class="rl-desc" style="float: left">
<div class="rl-desc span6">
<h1 style="margin-bottom: 0;">SnappyMail</h1>
<h4 style="margin-top: 0;" data-bind="text: version"></h4>
<h4 style="color: #aaa; font-weight: normal;">An advanced fork of <a href="https://www.rainloop.net/" target="_blank">RainLoop</a></h4>

View file

@ -45,7 +45,7 @@
<div class="controls">
<input type="text" class="span6" autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="value: pdoDsn, saveTrigger: pdoDsnTrigger" />
<blockquote style="margin: 10px 0 0 0">
<blockquote style="margin: 0">
<p class="muted">
mysql:host=127.0.0.1;port=3306;dbname=rainloop<br />
pgsql:host=127.0.0.1;port=5432;dbname=rainloop
@ -79,7 +79,7 @@ pgsql:host=127.0.0.1;port=5432;dbname=rainloop
<div data-bind="visible: 'sqlite' === contactsType()">
<div class="control-group">
<div class="controls">
<div class="alert alert-null-left-margin span8">
<div class="alert">
<h4 data-i18n="TAB_CONTACTS/ALERT_NOTICE"></h4>
<br />
<div data-i18n="[html]TAB_CONTACTS/HTML_ALERT_DO_NOT_USE_THIS_DATABASE"></div>

View file

@ -17,7 +17,7 @@
</div>
</div>
<div class="form-horizontal">
<div class="legend i18n i18n-animation" data-i18n="TAB_GENERAL/LEGEND_INTERFACE"></div>
<div class="legend" data-i18n="TAB_GENERAL/LEGEND_INTERFACE"></div>
<div class="control-group" style="margin-bottom: 10px;">
<label class="control-label" data-i18n="TAB_GENERAL/LABEL_LANGUAGE"></label>
<div class="controls">
@ -99,7 +99,7 @@
}"></div>
</div>
</div>
<div class="legend i18n i18n-animation" data-i18n="TAB_GENERAL/LEGEND_MAIN"></div>
<div class="legend" data-i18n="TAB_GENERAL/LEGEND_MAIN"></div>
<div class="control-group">
<label class="control-label" data-i18n="TAB_GENERAL/LABEL_ATTACHMENT_SIZE_LIMIT"></label>
<div class="controls">

View file

@ -215,8 +215,8 @@
</div>
<div class="span10" data-bind="visible: 'white-list' === page()">
<div class="legend white-list-header" data-i18n="POPUPS_DOMAIN/LABEL_WHITE_LIST"></div>
<div class="alert alert-block span6 alert-null-left-margin" style="width: 562px;" data-i18n="POPUPS_DOMAIN/WHITE_LIST_ALERT"></div>
<textarea class="input-xxlarge" style="width: 600px" rows="8" data-bind="value: whiteList" tabindex="-1"></textarea>
<div class="alert alert-block" data-i18n="POPUPS_DOMAIN/WHITE_LIST_ALERT"></div>
<textarea class="input-xxlarge" style="width: 100%" rows="8" data-bind="value: whiteList" tabindex="-1"></textarea>
</div>
</div>
</form>

View file

@ -1,9 +1,7 @@
<div class="modal fade b-languages-content g-ui-user-select-none" data-bind="modal: modalVisibility">
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_LANGUAGES/TITLE_LANGUAGES"></span>
</h3>
<h3 data-i18n="POPUPS_LANGUAGES/TITLE_LANGUAGES"></h3>
</div>
<div class="modal-body" style="min-height: 150px;">
<div data-bind="foreach: languages">

View file

@ -4,7 +4,7 @@
data-bind="visible: '' !== loadingDesc">
<span class="desc" data-bind="text: loadingDesc"></span>
</div>
<div class="alert alertError" data-bind="hidden: !submitError()" hidden="">
<div class="alert" data-bind="hidden: !submitError()" hidden="">
<button type="button" class="close" data-bind="click: function () { submitError('') }">×</button>
<span data-bind="text: submitError"></span>
<div data-bind="visible: '' !== submitErrorAddidional()">
@ -18,7 +18,7 @@
<div class="controls plugin-mark-Login-TopControlGroup"
data-bind="css: {'error': emailError}">
<div class="input-append">
<input type="email" class="i18n input-block-level inputEmail"
<input type="email" class="input-block-level inputEmail"
name="RainLoopEmail" id="RainLoopEmail"
autofocus=""
autocomplete="email" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -31,7 +31,7 @@
</div>
<div class="controls" data-bind="css: {'error': passwordError}">
<div class="input-append">
<input type="password" class="i18n input-block-level inputPassword"
<input type="password" class="input-block-level inputPassword"
name="RainLoopPassword" id="RainLoopPassword"
autocomplete="current-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="textInput: password, disable: submitRequest"
@ -46,7 +46,7 @@
<div class="controls"
data-bind="visible: additionalCodeVisibility(), css: {'error': additionalCodeError}">
<div class="input-append">
<input type="text" class="i18n input-block-level inputAdditionalCode" autocomplete="off"
<input type="text" class="input-block-level inputAdditionalCode" autocomplete="off"
autocorrect="off" autocapitalize="off" spellcheck="false" style="padding-right: 35px;"
data-bind="textInput: additionalCode, disable: submitRequest"
data-i18n="[placeholder]LOGIN/LABEL_VERIFICATION_CODE" />
@ -65,7 +65,7 @@
</div>
<div class="controls controls-submit-wrp" data-bind="hidden: hideSubmitButton">
<button type="submit" class="btn btn-large btn-block buttonLogin" data-bind="command: submitCommand">
<span class="i18n i18n-animation" data-i18n="LOGIN/BUTTON_SIGN_IN"></span>
<span class="i18n-animation" data-i18n="LOGIN/BUTTON_SIGN_IN"></span>
</button>
</div>
<div class="controls clearfix" style="margin-bottom: 10px">

View file

@ -112,7 +112,7 @@
<div class="input-append" data-bind="visible: allowSearch">
<div class="close-input-wrp">
<a class="close" data-bind="click: cancelSearch, visible: '' !== messageListSearchDesc()">×</a>
<input type="text" class="i18n span4 inputSearch" tabindex="-1" placeholder="Search" autocorrect="off" autocapitalize="off" data-i18n="[placeholder]GLOBAL/SEARCH" data-bind="value: inputProxyMessageListSearch, onEnter: searchEnterAction, hasfocus: inputMessageListSearchFocus" />
<input type="text" class="span4 inputSearch" tabindex="-1" placeholder="Search" autocorrect="off" autocapitalize="off" data-i18n="[placeholder]GLOBAL/SEARCH" data-bind="value: inputProxyMessageListSearch, onEnter: searchEnterAction, hasfocus: inputMessageListSearchFocus" />
</div>
<a class="btn buttonMoreSearch" data-bind="visible: allowSearchAdv, click: advancedSearchClick">
<span class="caret"></span>

View file

@ -164,7 +164,7 @@
<span class="flagParent g-ui-user-select-none flagOff fontastic" data-bind="text: viewIsFlagged() ? '★' : '☆', css: {'flagOn': viewIsFlagged, 'flagOff': !viewIsFlagged()}"></span>
<b style="color: red; margin-right: 5px" data-bind="visible: viewIsImportant">!</b>
<span class="subject" data-bind="text: viewSubject, title: viewSubject, event: { 'dblclick': toggleFullScreen }"></span>
<span class="i18n emptySubjectText" data-i18n="MESSAGE/EMPTY_SUBJECT_TEXT" data-bind="event: { 'dblclick': toggleFullScreen }"></span>
<span class="emptySubjectText" data-i18n="MESSAGE/EMPTY_SUBJECT_TEXT" data-bind="event: { 'dblclick': toggleFullScreen }"></span>
</div>
<div>
<div style="overflow: hidden;">
@ -183,13 +183,13 @@
<div class="informationShortWrp">
<div class="informationShort" data-bind="visible: viewTo, event: { 'dblclick': toggleFullScreen }">
<span>
<span class="i18n uiLabel labelTo" data-i18n="GLOBAL/TO"
<span class="uiLabel labelTo" data-i18n="GLOBAL/TO"
></span>:&nbsp;<span class="to" data-bind="text: viewTo"></span>
</span>
</div>
<div class="informationShort" data-bind="visible: viewCc, event: { 'dblclick': toggleFullScreen }">
<span>
<span class="i18n uiLabel labelTo" data-i18n="GLOBAL/CC"
<span class="uiLabel labelTo" data-i18n="GLOBAL/CC"
></span>:&nbsp;<span class="to" data-bind="text: viewCc"></span>
</span>
</div>
@ -198,30 +198,30 @@
<div class="informationFull" data-bind="visible: showFullInfo()">
<table>
<tr data-bind="visible: '' !== viewFrom()">
<td><span class="i18n uiLabel" data-i18n="GLOBAL/FROM"></span></td>
<td><span class="uiLabel" data-i18n="GLOBAL/FROM"></span></td>
<td>
<span class="pull-right size" data-bind="text: viewSize"></span>
<span class="from uiLabelValue" data-bind="text: viewFrom, title: viewFrom"></span>
</td>
</tr>
<tr data-bind="visible: '' !== viewTo()">
<td><span class="i18n uiLabel" data-i18n="GLOBAL/TO"></span></td>
<td><span class="uiLabel" data-i18n="GLOBAL/TO"></span></td>
<td><span class="to uiLabelValue" data-bind="text: viewTo, title: viewTo"></span></td>
</tr>
<tr data-bind="visible: '' !== viewCc()">
<td><span class="i18n uiLabel" data-i18n="GLOBAL/CC"></span></td>
<td><span class="uiLabel" data-i18n="GLOBAL/CC"></span></td>
<td><span class="cc uiLabelValue" data-bind="text: viewCc, title: viewCc"></span></td>
</tr>
<tr data-bind="visible: '' !== viewBcc()">
<td><span class="i18n uiLabel" data-i18n="GLOBAL/BCC"></span></td>
<td><span class="uiLabel" data-i18n="GLOBAL/BCC"></span></td>
<td><span class="bcc uiLabelValue" data-bind="text: viewBcc, title: viewBcc"></span></td>
</tr>
<tr data-bind="visible: '' !== viewReplyTo()">
<td><span class="i18n uiLabel" data-i18n="GLOBAL/REPLY_TO"></span></td>
<td><span class="uiLabel" data-i18n="GLOBAL/REPLY_TO"></span></td>
<td><span class="replyTo uiLabelValue" data-bind="text: viewReplyTo, title: viewReplyTo"></span></td>
</tr>
<tr data-bind="visible: 0 < viewTimeStamp()">
<td><span class="i18n uiLabel" data-i18n="MESSAGE/LABEL_DATE"></span></td>
<td><span class="uiLabel" data-i18n="MESSAGE/LABEL_DATE"></span></td>
<td>
<time class="date uiLabelValue" data-moment-format="FULL" data-bind="moment: viewTimeStamp"></time>
&nbsp;
@ -249,7 +249,7 @@
<div class="line-loading e-strip-animation" data-bind="visible: messageLoadingThrottle()"></div>
<div class="loading g-ui-min-height-300" data-bind="visible: messageLoadingThrottle()">
<span class="i18n text" data-i18n="GLOBAL/LOADING"></span><span class="textLoadingAnimationD1">.</span><span class="textLoadingAnimationD2">.</span><span class="textLoadingAnimationD3">.</span>
<span class="text" data-i18n="GLOBAL/LOADING"></span><span class="textLoadingAnimationD1">.</span><span class="textLoadingAnimationD2">.</span><span class="textLoadingAnimationD3">.</span>
</div>
</div>
@ -257,11 +257,11 @@
<div class="bodySubHeader">
<div class="showImages" data-bind="visible: message() && message().hasImages(), click: function() { showImages(message()); }">
<i class="fontastic">🖼</i>
<span class="i18n text" data-i18n="MESSAGE/BUTTON_SHOW_IMAGES"></span>
<span class="text" data-i18n="MESSAGE/BUTTON_SHOW_IMAGES"></span>
</div>
<div class="readReceipt" data-bind="visible: message() && !isDraftOrSentFolder() && '' !== message().readReceipt() && !message().isReadReceipt(), click: function() { readReceipt(message()); }">
<i class="icon-mail"></i>
<span class="i18n text" data-i18n="MESSAGE/BUTTON_NOTIFY_READ_RECEIPT"></span>
<span class="text" data-i18n="MESSAGE/BUTTON_NOTIFY_READ_RECEIPT"></span>
</div>
<div class="attachmentsPlace" data-bind="visible: message() && message().attachments().hasVisible(),
css: {'selection-mode' : showAttachmnetControls, 'unselectedAttachmentsError': highlightUnselectedAttachments}">

View file

@ -19,7 +19,7 @@
</div>
<br />
<div class="control-group" data-bind="css: {'error': emailError}">
<label class="i18n control-label" data-i18n="GLOBAL/EMAIL"></label>
<label class="control-label" data-i18n="GLOBAL/EMAIL"></label>
<div class="controls">
<label style="margin-top: 5px;" data-bind="visible: !isNew()"><strong data-bind="text: email"></strong></label>
<input type="email" class="inputEmail input-xlarge" autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -27,7 +27,7 @@
</div>
</div>
<div class="control-group" data-bind="css: {'error': passwordError}">
<label class="i18n control-label" data-i18n="GLOBAL/PASSWORD"></label>
<label class="control-label" data-i18n="GLOBAL/PASSWORD"></label>
<div class="controls">
<input type="password" class="inputPassword input-xlarge" autocomplete="current-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="value: password, onEnter: addAccountCommand" />

View file

@ -2,9 +2,7 @@
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_IMPORT_OPEN_PGP_KEY/TITLE_IMPORT_OPEN_PGP_KEY"></span>
</h3>
<h3 data-i18n="POPUPS_IMPORT_OPEN_PGP_KEY/TITLE_IMPORT_OPEN_PGP_KEY"></h3>
</div>
<div class="modal-body">
<div class="alert" data-bind="visible: keyError() && keyErrorMessage(), text: keyErrorMessage"></div>

View file

@ -1,12 +1,9 @@
<div class="modal fade b-advanced-search-content g-ui-user-select-none" data-bind="modal: modalVisibility">
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="SEARCH/TITLE_ADV"></span>
</h3>
<h3 data-i18n="SEARCH/TITLE_ADV"></h3>
</div>
<div class="modal-body">
<br />
<form class="form-horizontal" action="#/" autocomplete="off" onsubmit="return false;" data-bind="command: searchCommand">
<div class="row">
<div class="span4">

View file

@ -2,11 +2,11 @@
<div class="modal-header b-header-toolbar g-ui-user-select-none">
<a class="btn btn-large button-send" data-bind="command: sendCommand, tooltipErrorTip: sendErrorDesc, css: {'btn-success': sendButtonSuccess, 'btn-danger': sendError, 'btn-warning': sendSuccessButSaveError }">
<i class="icon-white" data-bind="css: {'icon-paper-plane': !sending(), 'icon-spinner big': sending()}"></i>
<span class="i18n hide-mobile" data-i18n="COMPOSE/BUTTON_SEND"></span>
<span class="hide-mobile" data-i18n="COMPOSE/BUTTON_SEND"></span>
</a>
<a class="btn button-save" data-bind="visible: allowFolders, command: saveCommand, tooltipErrorTip: savedErrorDesc, css: {'btn-danger': savedError }">
<i class="fontastic" data-bind="css: {'icon-spinner': saving(), 'icon-white': savedError()}">💾</i>
<span class="i18n hide-mobile" data-i18n="GLOBAL/SAVE"></span>
<span class="hide-mobile" data-i18n="GLOBAL/SAVE"></span>
</a>
<a class="close" data-bind="click: tryToClosePopup, tooltip: 'GLOBAL/CANCEL'">×</a>
@ -47,7 +47,7 @@
<div class="pull-right">
<div class="btn-group dropdown colored-toggle pull-right" style="margin-right: 4px;" data-bind="registerBootstrapDropdown: true">
<a class="btn dropdown-toggle fontastic" data-toggle="dropdown"></a>
<ul class="dropdown-menu g-ui-menu" role="menu">
<ul class="dropdown-menu right-edge g-ui-menu" role="menu">
<li class="e-item" data-bind="click: function () { requestReadReceipt(!requestReadReceipt()); }">
<a class="e-link">
<i class="fontastic" data-bind="text: requestReadReceipt() ? '☑' : '☐'"></i>
@ -81,15 +81,15 @@
<div class="btn-group pull-right">&nbsp;</div>
</div>
<span class="pull-right">
<span class="i18n g-ui-link" data-i18n="GLOBAL/CC"
<span class="g-ui-link" data-i18n="GLOBAL/CC"
data-bind="visible: !showCc(), click: function () { showCc(true); }"></span>
&nbsp;&nbsp;
<span data-bind="visible: !showBcc()">
<span class="i18n g-ui-link" data-i18n="GLOBAL/BCC"
<span class="g-ui-link" data-i18n="GLOBAL/BCC"
data-bind="click: function () { showBcc(true); }"></span>
&nbsp;&nbsp;
</span>
<span class="i18n g-ui-link" data-i18n="GLOBAL/REPLY_TO"
<span class="g-ui-link" data-i18n="GLOBAL/REPLY_TO"
data-bind="visible: !showReplyTo(), click: function () { showReplyTo(true); }"></span>
&nbsp;
</span>

View file

@ -2,17 +2,14 @@
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_COMPOSE_OPEN_PGP/TITLE_COMPOSE_OPEN_PGP"></span>
</h3>
<h3 data-i18n="POPUPS_COMPOSE_OPEN_PGP/TITLE_COMPOSE_OPEN_PGP"></h3>
</div>
<div class="modal-body">
<div class="alert" data-bind="visible: '' !== notification()">
<span data-bind="text: notification"></span>
</div>
<div class="row-fluid">
<div class="span6">
<div>
<div>
<div data-bind="component: {
name: 'Checkbox',
params: {
@ -26,11 +23,11 @@
No private key found
</div>
<div class="key-list-wrp" data-bind="visible: signKey()">
<div class="key-list__item row-fluid">
<div class="key-list__item-hash span4">
<div class="key-list__item">
<div class="key-list__item-hash">
(<span data-bind="text: signKey() ? signKey().hash : ''"></span>)
</div>
<div class="key-list__item-names span8">
<div class="key-list__item-names">
<!-- ko if: signKey() -->
<!-- ko foreach: signKey().users -->
<div class="key-list__item-name" data-bind="text: $data"></div>
@ -41,8 +38,7 @@
</div>
</div>
</div>
<div class="span6">
<div>
<div data-bind="component: {
name: 'Checkbox',
params: {
@ -57,50 +53,38 @@
</div>
<div class="key-list-wrp" data-bind="visible: encryptKeys() && encryptKeys().length > 0">
<!-- ko foreach: encryptKeys -->
<div class="key-list__item row-fluid">
<div class="key-list__item-delete span1" data-bind="click: removable() ? $parent.deletePublickKey : null, css: {'disabled': !removable()}">
<i class="fontastic">🗑</i>
</div>
<div class="key-list__item-hash span3" data-bind="visible: !empty">
<div class="key-list__item">
<div class="key-list__item-hash" data-bind="visible: !empty">
(<span data-bind="text: hash"></span>)
</div>
<div class="span8">
<span class="key-list__item-names" data-bind="css: {'empty': empty}">
<!-- ko foreach: users -->
<div class="key-list__item-name" data-bind="text: $data"></div>
<!-- /ko -->
</span>
<span class="key-list__item-error" data-bind="visible: empty">
(Public key not found)
</span>
<div class="key-list__item-names" data-bind="css: {'empty': empty}">
<!-- ko foreach: users -->
<div class="key-list__item-name" data-bind="text: $data"></div>
<!-- /ko -->
</div>
<div class="key-list__item-error" data-bind="visible: empty">
(Public key not found)
</div>
<div class="key-list__item-delete fontastic" data-bind="click: removable() ? $parent.deletePublickKey : null, css: {'disabled': !removable()}">🗑</div>
</div>
<!-- /ko -->
</div>
</div>
</div>
</div>
<div class="row-fluid key-actions">
<div class="span6">
<div data-bind="visible: sign()">
<input type="password" class="inputPassword input-block-level"
autocomplete="current-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-i18n="[placeholder]GLOBAL/PASSWORD"
data-bind="textInput: password, onEnter: doCommand" />
<div class="form-inline" data-bind="visible: 0 < privateKeysOptions().length">
<select class="input-block-level" data-bind="options: privateKeysOptions, value: selectedPrivateKey,
optionsCaption: privateKeysOptionsCaption, optionsText: 'name', optionsValue: 'id',
optionsAfterRender: addOptionClass"></select>
</div>
</div>
</div>
<div class="span6">
<div class="form-inline" data-bind="visible: encrypt() && 0 < publicKeysOptions().length">
<select class="input-block-level" data-bind="options: publicKeysOptions, value: selectedPublicKey,
optionsCaption: publicKeysOptionsCaption, optionsText: 'name', optionsValue: 'id',
optionsAfterRender: addOptionClass"></select>
</div>
<div class="key-actions">
<div data-bind="visible: sign()">
<input type="password" class="inputPassword input-block-level"
autocomplete="current-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-i18n="[placeholder]GLOBAL/PASSWORD"
data-bind="textInput: password, onEnter: doCommand" />
<select class="input-block-level" data-bind="visible: 0 < privateKeysOptions().length, options: privateKeysOptions, value: selectedPrivateKey,
optionsCaption: privateKeysOptionsCaption, optionsText: 'name', optionsValue: 'id',
optionsAfterRender: addOptionClass"></select>
</div>
<select class="input-block-level" data-bind="visible: encrypt() && 0 < publicKeysOptions().length, options: publicKeysOptions, value: selectedPublicKey,
optionsCaption: publicKeysOptionsCaption, optionsText: 'name', optionsValue: 'id',
optionsAfterRender: addOptionClass"></select>
</div>
</div>
<div class="modal-footer">

View file

@ -56,7 +56,7 @@
</div>
<div class="modal-body" style="position: relative;">
<div class="b-list-toolbar">
<input type="text" class="i18n span3 e-search" placeholder="Search" autocorrect="off" autocapitalize="off" data-i18n="[placeholder]GLOBAL/SEARCH" data-bind="value: search" />
<input type="text" class="span3 e-search" placeholder="Search" autocorrect="off" autocapitalize="off" data-i18n="[placeholder]GLOBAL/SEARCH" data-bind="value: search" />
</div>
<div class="b-list-content g-ui-user-select-none" data-bind="css: {'hideContactListCheckbox': !useCheckboxesInList()}">
<div class="content">
@ -76,10 +76,7 @@
<div class="e-contact-foreach g-ui-user-select-none" data-bind="foreach: contacts, visible: 0 < contacts().length">
<div class="e-contact-item g-ui-user-select-none" data-bind="css: lineAsCss()">
<div class="checkboxItem fontastic" data-bind="text: checked() ? '☑' : '☐'"></div>
<div class="nameParent actionHandle">
<span class="listName" data-bind="text: display"></span>
&nbsp;
</div>
<div class="nameParent actionHandle" data-bind="text: display"></div>
</div>
</div>
</div>
@ -101,7 +98,6 @@
<div class="btn-group dropdown colored-toggle button-add-prop" data-bind="visible: !emptySelection(), registerBootstrapDropdown: true">
<a id="button-add-prop-dropdown-id" href="#" tabindex="-1" class="btn dropdown-toggle" data-toggle="dropdown">
<span data-i18n="CONTACTS/ADD_MENU_LABEL"></span>
&nbsp;&nbsp;
<span class="caret"></span>
</a>
<ul class="dropdown-menu g-ui-menu right-edge" style="text-align: left" tabindex="-1" role="menu" aria-labelledby="button-add-prop-dropdown-id">
@ -146,8 +142,8 @@
<div data-bind="visible: !emptySelection()">
<div class="form-horizontal top-part">
<div class="control-group" data-bind="visible: !viewReadOnly() || contactHasValidName()">
<label class="control-label remove-padding-top fix-width fontastic iconsize24">👤</label>
<div class="controls fix-width">
<label class="control-label fontastic iconsize24">👤</label>
<div class="controls">
<div data-bind="foreach: viewPropertiesNames">
<div class="property-line">
<span class="contactValueStatic" data-bind="text: value"></span>
@ -175,8 +171,8 @@
</div>
</div>
<div class="control-group" data-bind="visible: !viewReadOnly() || 0 < viewPropertiesEmails().length">
<label class="control-label remove-padding-top fix-width fontastic iconsize24" data-bind="tooltip: 'GLOBAL/EMAIL'">@</label>
<div class="controls fix-width">
<label class="control-label fontastic iconsize24" data-bind="tooltip: 'GLOBAL/EMAIL'">@</label>
<div class="controls">
<div data-bind="foreach: viewPropertiesEmails">
<div class="property-line">
<span class="contactValueStatic" data-bind="text: value"></span>
@ -189,8 +185,8 @@
</div>
</div>
<div class="control-group" data-bind="visible: 0 < viewPropertiesPhones().length">
<label class="control-label remove-padding-top fix-width fontastic iconsize24" data-bind="tooltip: 'CONTACTS/LABEL_PHONE'">📞</label>
<div class="controls fix-width">
<label class="control-label fontastic iconsize24" data-bind="tooltip: 'CONTACTS/LABEL_PHONE'">📞</label>
<div class="controls">
<div data-bind="foreach: viewPropertiesPhones">
<div class="property-line">
<span class="contactValueStatic" data-bind="text: value"></span>
@ -202,8 +198,8 @@
</div>
</div>
<div class="control-group" data-bind="visible: 0 < viewPropertiesWeb().length">
<label class="control-label remove-padding-top fix-width fontastic iconsize24" data-bind="tooltip: 'CONTACTS/LABEL_WEB'">🌍</label>
<div class="controls fix-width">
<label class="control-label fontastic iconsize24" data-bind="tooltip: 'CONTACTS/LABEL_WEB'">🌍</label>
<div class="controls">
<div data-bind="foreach: viewPropertiesWeb">
<div class="property-line">
<span class="contactValueLargeStatic" data-bind="text: value"></span>
@ -214,12 +210,6 @@
</div>
</div>
</div>
<div class="control-group">
<div class="controls fix-width">
<br />
<br />
</div>
</div>
</div>
<!--
<div class="e-read-only-sign fontastic iconsize24" data-bind="tooltip: 'CONTACTS/LABEL_READ_ONLY'">🔒</div>

View file

@ -13,7 +13,7 @@
<div class="control-group" data-bind="css: {'error': nameError}">
<div class="controls">
<input type="text" class="i18n span5"
<input type="text" class="span5"
data-bind="value: name, hasfocus: nameFocused"
autocorrect="off" autocapitalize="off" spellcheck="false"
data-i18n="[placeholder]GLOBAL/NAME"

View file

@ -2,9 +2,7 @@
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_CREATE_FOLDER/TITLE_CREATE_FOLDER"></span>
</h3>
<h3 data-i18n="POPUPS_CREATE_FOLDER/TITLE_CREATE_FOLDER"></h3>
</div>
<div class="modal-body">
<div class="form-horizontal">

View file

@ -1,9 +1,7 @@
<div class="modal fade b-folder-system-content g-ui-user-select-none" data-bind="modal: modalVisibility">
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_SYSTEM_FOLDERS/TITLE_SYSTEM_FOLDERS"></span>
</h3>
<h3 data-i18n="POPUPS_SYSTEM_FOLDERS/TITLE_SYSTEM_FOLDERS"></h3>
</div>
<div class="modal-body">
<div class="form-horizontal">

View file

@ -15,7 +15,7 @@
</div>
<br />
<div class="control-group" data-bind="visible: !owner(), css: {'error': emailHasError}">
<label class="i18n control-label" data-i18n="GLOBAL/EMAIL"></label>
<label class="control-label" data-i18n="GLOBAL/EMAIL"></label>
<div class="controls">
<input type="email" class="inputEmail input-xlarge" autofocus=""
autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -23,13 +23,13 @@
</div>
</div>
<div class="control-group" data-bind="visible: owner">
<label class="i18n control-label" data-i18n="GLOBAL/EMAIL"></label>
<label class="control-label" data-i18n="GLOBAL/EMAIL"></label>
<div class="controls">
<div class="textEmail" data-bind="text: email"></div>
</div>
</div>
<div class="control-group">
<label class="i18n control-label" data-i18n="GLOBAL/NAME"></label>
<label class="control-label" data-i18n="GLOBAL/NAME"></label>
<div class="controls">
<input type="text" class="inputName input-xlarge"
autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -37,7 +37,7 @@
</div>
</div>
<div class="control-group" data-bind="visible: showReplyTo, css: {'error': replyToHasError}">
<label class="i18n control-label" data-i18n="GLOBAL/REPLY_TO"></label>
<label class="control-label" data-i18n="GLOBAL/REPLY_TO"></label>
<div class="controls">
<input type="text" class="inputReplyTo input-xlarge"
autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -45,7 +45,7 @@
</div>
</div>
<div class="control-group" data-bind="visible: showBcc, css: {'error': bccHasError}">
<label class="i18n control-label" data-i18n="GLOBAL/BCC"></label>
<label class="control-label" data-i18n="GLOBAL/BCC"></label>
<div class="controls">
<input type="text" class="inputBcc input-xlarge"
autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -55,12 +55,12 @@
<div class="control-group" data-bind="visible: !showReplyTo() || !showBcc()">
<div class="controls">
<span data-bind="visible: !showReplyTo()">
<span class="i18n g-ui-link" data-i18n="GLOBAL/REPLY_TO"
<span class="g-ui-link" data-i18n="GLOBAL/REPLY_TO"
data-bind="click: function () { showReplyTo(true); }"></span>
&nbsp;&nbsp;
</span>
<span data-bind="visible: !showBcc()">
<span class="i18n g-ui-link" data-i18n="GLOBAL/BCC"
<span class="g-ui-link" data-i18n="GLOBAL/BCC"
data-bind="click: function () { showBcc(true); }"></span>
</span>
</div>

View file

@ -2,9 +2,7 @@
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_MESSAGE_OPEN_PGP/TITLE_MESSAGE_OPEN_PGP"></span>
</h3>
<h3 data-i18n="POPUPS_MESSAGE_OPEN_PGP/TITLE_MESSAGE_OPEN_PGP"></h3>
</div>
<div class="modal-body">
<div class="form-horizontal">
@ -13,7 +11,7 @@
</div>
<br />
<div class="control-group">
<label class="i18n control-label" data-i18n="POPUPS_MESSAGE_OPEN_PGP/LABEL_KEY"></label>
<label class="control-label" data-i18n="POPUPS_MESSAGE_OPEN_PGP/LABEL_KEY"></label>
<div class="controls key-list" data-bind="foreach: privateKeys" style="margin-top: 5px">
<div class="key-list__item">
<i class="key-list__item__radio fontastic"></i>
@ -32,7 +30,7 @@
</div>
</div>
<div class="control-group">
<label class="i18n control-label" data-i18n="GLOBAL/PASSWORD"></label>
<label class="control-label" data-i18n="GLOBAL/PASSWORD"></label>
<div class="controls">
<input type="password" class="inputPassword input-xlarge" autofocus="" autocomplete="current-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="textInput: password, onEnter: doCommand" />

View file

@ -2,9 +2,7 @@
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_GENERATE_OPEN_PGP_KEYS/TITLE_GENERATE_OPEN_PGP_KEYS"></span>
</h3>
<h3 data-i18n="POPUPS_GENERATE_OPEN_PGP_KEYS/TITLE_GENERATE_OPEN_PGP_KEYS"></h3>
</div>
<div class="modal-body">
<div class="form-horizontal">
@ -14,7 +12,7 @@
</div>
<br />
<div class="control-group" data-bind="css: {'error': emailError}">
<label class="i18n control-label" data-i18n="GLOBAL/EMAIL"></label>
<label class="control-label" data-i18n="GLOBAL/EMAIL"></label>
<div class="controls">
<input type="email" class="inputEmail input-large"
autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -22,7 +20,7 @@
</div>
</div>
<div class="control-group">
<label class="i18n control-label" data-i18n="GLOBAL/NAME"></label>
<label class="control-label" data-i18n="GLOBAL/NAME"></label>
<div class="controls">
<input type="text" class="inputName input-large"
autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -30,7 +28,7 @@
</div>
</div>
<div class="control-group">
<label class="i18n control-label" data-i18n="GLOBAL/PASSWORD"></label>
<label class="control-label" data-i18n="GLOBAL/PASSWORD"></label>
<div class="controls">
<input type="password" class="inputPassword input-large"
autocomplete="current-password" autocorrect="off" autocapitalize="off" spellcheck="false"
@ -38,7 +36,7 @@
</div>
</div>
<div class="control-group">
<label class="i18n control-label" data-i18n="POPUPS_GENERATE_OPEN_PGP_KEYS/LABEL_KEY_BIT_LENGTH"></label>
<label class="control-label" data-i18n="POPUPS_GENERATE_OPEN_PGP_KEYS/LABEL_KEY_BIT_LENGTH"></label>
<div class="controls">
<select data-bind="value: keyBitLength, options: [2048, 4096]"></select>
</div>

View file

@ -11,7 +11,7 @@
<div class="control-group" data-bind="css: {'error': nameError}">
<div class="controls">
<input type="text" class="i18n span5"
<input type="text" class="span5"
data-bind="value: name, hasfocus: !exists(), visible: !exists()"
autocorrect="off" autocapitalize="off" spellcheck="false"
data-i18n="[placeholder]GLOBAL/NAME"

View file

@ -15,7 +15,7 @@
</div>
<br />
<div class="control-group" data-bind="css: {'error': nameError}">
<label class="i18n control-label" data-i18n="GLOBAL/NAME"></label>
<label class="control-label" data-i18n="GLOBAL/NAME"></label>
<div class="controls">
<input type="text" class="inputName input-xlarge" autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="textInput: name, onEnter: addTemplateCommand, hasfocus: nameFocus" />

View file

@ -2,9 +2,7 @@
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="visible: viewEnable() || !lock(), command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_TWO_FACTOR_CFG/LEGEND_TWO_FACTOR_AUTH"></span>
</h3>
<h3 data-i18n="POPUPS_TWO_FACTOR_CFG/LEGEND_TWO_FACTOR_AUTH"></h3>
</div>
<div class="modal-body">
<div class="form-horizontal" data-bind="visible: capaTwoFactor" style="margin-top: 10px;">
@ -22,7 +20,7 @@
}"></div>
</div>
&nbsp;&nbsp;&nbsp;
<span class="i18n g-ui-link" data-bind="click: testTwoFactor, visible: twoFactorStatus"
<span class="g-ui-link" data-bind="click: testTwoFactor, visible: twoFactorStatus"
data-i18n="POPUPS_TWO_FACTOR_CFG/LINK_TEST"></span>
</div>
</div>
@ -34,7 +32,7 @@
<strong><span data-bind="text: viewUser"></span></strong>
<div style="padding-top: 15px;" data-bind="visible: lock">
<blockquote>
<p class="muted i18n width100-on-mobile" style="width: 550px" data-i18n="POPUPS_TWO_FACTOR_CFG/TWO_FACTOR_REQUIRE_DESC"></p>
<p class="muted width100-on-mobile" style="width: 550px" data-i18n="POPUPS_TWO_FACTOR_CFG/TWO_FACTOR_REQUIRE_DESC"></p>
</blockquote>
</div>
</div>
@ -57,7 +55,7 @@
<br />
<br />
<blockquote>
<p class="muted i18n width100-on-mobile" style="width: 550px" data-i18n="POPUPS_TWO_FACTOR_CFG/TWO_FACTOR_SECRET_DESC"></p>
<p class="muted width100-on-mobile" style="width: 550px" data-i18n="POPUPS_TWO_FACTOR_CFG/TWO_FACTOR_SECRET_DESC"></p>
</blockquote>
<!-- ko if: '' !== viewUrl() -->
<img style="margin-left: -7px;" src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAAC0lEQVQIW2P8DwQACgAD/il4QJ8AAAAASUVORK5CYII=" data-bind="attr: {'src': viewUrl}" />
@ -72,7 +70,7 @@
<pre data-bind="text: viewBackupCodes" style="width: 230px; word-break: break-word;"></pre>
<br />
<blockquote>
<p class="muted i18n width100-on-mobile" style="width: 550px" data-i18n="POPUPS_TWO_FACTOR_CFG/TWO_FACTOR_BACKUP_CODES_DESC"></p>
<p class="muted width100-on-mobile" style="width: 550px" data-i18n="POPUPS_TWO_FACTOR_CFG/TWO_FACTOR_BACKUP_CODES_DESC"></p>
</blockquote>
</div>
</div>

View file

@ -2,9 +2,7 @@
<div>
<div class="modal-header">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_TWO_FACTOR_TEST/TITLE_TEST_CODE"></span>
</h3>
<h3 data-i18n="POPUPS_TWO_FACTOR_TEST/TITLE_TEST_CODE"></h3>
</div>
<div class="modal-body">
<div class="form-horizontal">

View file

@ -2,9 +2,7 @@
<div>
<div class="modal-header g-ui-user-select-none">
<button type="button" class="close" data-bind="command: cancelCommand">×</button>
<h3>
<span data-i18n="POPUPS_VIEW_OPEN_PGP_KEY/TITLE_VIEW_OPEN_PGP_KEY"></span>
</h3>
<h3 data-i18n="POPUPS_VIEW_OPEN_PGP_KEY/TITLE_VIEW_OPEN_PGP_KEY"></h3>
</div>
<div class="modal-body">
<div class="form-horizontal">

View file

@ -1,47 +0,0 @@
<div class="b-settings-general g-ui-user-select-none">
<div class="form-horizontal long-label">
<div class="legend">
<span data-i18n="SETTINGS_CHANGE_PASSWORD/LEGEND_CHANGE_PASSWORD"></span>
</div>
<div class="row">
<div class="span6">
<div class="control-group" data-bind="css: {'error': currentPassword.error}">
<label class="control-label">
<span data-i18n="SETTINGS_CHANGE_PASSWORD/LABEL_CURRENT_PASSWORD"></span>
</label>
<div class="controls">
<input type="password" autocomplete="current-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="textInput: currentPassword" />
</div>
</div>
<div class="control-group" data-bind="css: {'error': passwordMismatch}">
<label class="control-label">
<span data-i18n="SETTINGS_CHANGE_PASSWORD/LABEL_NEW_PASSWORD"></span>
</label>
<div class="controls">
<input type="password" autocomplete="new-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="textInput: newPassword" />
</div>
</div>
<div class="control-group" data-bind="css: {'error': passwordMismatch}">
<label class="control-label">
<span data-i18n="SETTINGS_CHANGE_PASSWORD/LABEL_REPEAT_PASSWORD"></span>
</label>
<div class="controls">
<input type="password" autocomplete="new-password" autocorrect="off" autocapitalize="off" spellcheck="false"
data-bind="textInput: newPassword2" />
</div>
</div>
<div class="control-group">
<div class="controls">
<a class="btn" data-bind="command: saveNewPasswordCommand, css: { 'btn-success': passwordUpdateSuccess, 'btn-danger': passwordUpdateError }">
<i class="fontastic" data-bind="css: {'icon-spinner': changeProcess(), 'icon-white': passwordUpdateSuccess() || passwordUpdateError() }">🔑</i>
<span data-i18n="SETTINGS_CHANGE_PASSWORD/BUTTON_UPDATE_PASSWORD"></span>
</a>
</div>
</div>
</div>
<div class="span4 alert alert-error alert-null-left-margin" data-bind="visible: '' !== errorDescription(), text: errorDescription"></div>
</div>
</div>
</div>

View file

@ -1,7 +1,7 @@
<div class="b-settings-general g-ui-user-select-none">
<div class="form-horizontal">
<div class="legend">
<span class="i18n i18n-animation" data-i18n="SETTINGS_GENERAL/LEGEND_GENERAL"></span>
<span class="i18n-animation" data-i18n="SETTINGS_GENERAL/LEGEND_GENERAL"></span>
</div>
<div class="control-group">
<label class="control-label">
@ -112,7 +112,7 @@
</div>
<div class="form-horizontal">
<div class="legend">
<span class="i18n i18n-animation" data-i18n="SETTINGS_GENERAL/LABEL_NOTIFICATIONS"></span>
<span class="i18n-animation" data-i18n="SETTINGS_GENERAL/LABEL_NOTIFICATIONS"></span>
</div>
<div class="control-group">
<div class="controls">

View file

@ -3,12 +3,12 @@
<div class="b-settings-menu" data-bind="foreach: menu">
<!-- ko if: disabled -->
<span class="e-item disabled">
<span class="i18n e-link" data-bind="attr: { 'data-i18n': label }"></span>
<span class="e-link" data-bind="attr: { 'data-i18n': label }"></span>
</span>
<!-- /ko -->
<!-- ko ifnot: disabled -->
<a class="e-item selectable" href="#" data-bind="css: {'selected': selected }, attr: { 'href': $root.link(route) }">
<span class="i18n e-link" data-bind="attr: { 'data-i18n': label }"></span>
<span class="e-link" data-bind="attr: { 'data-i18n': label }"></span>
</a>
<!-- /ko -->
</div>

View file

@ -9,7 +9,7 @@
</div>
<a class="btn button-back" data-bind="click: backToMailBoxClick">
<i class="fontastic"></i>
<span class="i18n i18n-animation" data-i18n="GLOBAL/BACK"></span>
<span class="i18n-animation" data-i18n="GLOBAL/BACK"></span>
</a>
</div>
</div>

View file

@ -27,7 +27,7 @@
<div class="controls">
<i class="fontastic">🔒</i>
&nbsp;
<span class="i18n g-ui-link" tabindex="0" data-i18n="SETTINGS_SECURITY/LABEL_CONFIGURE_TWO_FACTOR" data-bind="click: configureTwoFactor, onSpace: configureTwoFactor, onEnter: configureTwoFactor"></span>
<span class="g-ui-link" tabindex="0" data-i18n="SETTINGS_SECURITY/LABEL_CONFIGURE_TWO_FACTOR" data-bind="click: configureTwoFactor, onSpace: configureTwoFactor, onEnter: configureTwoFactor"></span>
</div>
</div>
</div>

View file

@ -12,7 +12,7 @@
</div>
<div class="accountPlace hide-mobile" data-bind="text: emailTitle()"></div>
<div class="btn-group dropdown colored-toggle" data-bind="registerBootstrapDropdown: true, openDropdownTrigger: accountMenuDropdownTrigger">
<a id="top-system-dropdown-id" href="#" tabindex="-1" class="btn single btn-ellipsis btn-block dropdown-toggle system-dropdown" data-toggle="dropdown">
<a id="top-system-dropdown-id" href="#" tabindex="-1" class="btn single btn-block dropdown-toggle" data-toggle="dropdown">
<i class="fontastic" data-bind="css: {'icon-spinner': accounts.loading()}">👤</i>
<!--
<b data-bind="text: accountsUnreadCount, visible: 100 > accountsUnreadCount() && 0 < accountsUnreadCount()"></b>
@ -21,7 +21,7 @@
-->
<span class="caret"></span>
</a>
<ul class="dropdown-menu g-ui-menu" tabindex="-1" role="menu" aria-labelledby="top-system-dropdown-id">
<ul class="dropdown-menu right-edge g-ui-menu" tabindex="-1" role="menu" aria-labelledby="top-system-dropdown-id">
<!-- ko if: accounts().length -->
<!-- ko foreach: accounts -->

View file

@ -50,6 +50,29 @@ const cssMainBuild = () => {
.pipe(livereload());
};
const cssAdminBuild = () => {
const
less = require('gulp-less'),
lessFilter = filter('**/*.less', { restore: true }),
src = config.paths.css.main.src.concat([config.paths.less.admin.src]);
return gulp
.src(src)
.pipe(expect.real({ errorOnFailure: true }, src))
.pipe(lessFilter)
.pipe(
less({
'paths': config.paths.less.main.options.paths
})
)
.pipe(lessFilter.restore)
.pipe(concat(config.paths.css.admin.name))
.pipe(replace(/\.\.\/(img|images|fonts|svg)\//g, '$1/'))
.pipe(eol('\n', true))
.pipe(gulp.dest(config.paths.staticCSS))
.pipe(livereload());
};
const cssBootMin = () => {
return gulp
.src(config.paths.staticCSS + config.paths.css.boot.name)
@ -68,8 +91,17 @@ const cssMainMin = () => {
.pipe(gulp.dest(config.paths.staticCSS));
};
const cssBuild = gulp.parallel(cssBootBuild, cssMainBuild);
const cssMin = gulp.parallel(cssBootMin, cssMainMin);
const cssAdminMin = () => {
return gulp
.src(config.paths.staticCSS + config.paths.css.admin.name)
.pipe(cleanCss())
.pipe(rename({ suffix: '.min' }))
.pipe(eol('\n', true))
.pipe(gulp.dest(config.paths.staticCSS));
};
const cssBuild = gulp.parallel(cssBootBuild, cssMainBuild, cssAdminBuild);
const cssMin = gulp.parallel(cssBootMin, cssMainMin, cssAdminMin);
const cssLint = (done) => done();

View file

@ -16,6 +16,17 @@
const t = e.target, href = t.href || (t.parentNode && t.parentNode.href);
(href && href.slice(-1) === '#') && e.preventDefault();
},
open = bool => {
menu && menu.classList.toggle('show', bool);
parent.classList.toggle('show', bool);
element.setAttribute('aria-expanded', bool);
element.open = bool;
if (bool) {
element.removeEventListener('click',clickHandler);
} else {
setTimeout(() => element.addEventListener('click',clickHandler), 1);
}
},
toggleEvents = () => {
let action = (element.open ? 'add' : 'remove') + 'EventListener';
doc[action]('click',dismissHandler);
@ -63,28 +74,19 @@
menu = parent.querySelector('.dropdown-menu');
menuItems = [...menu.querySelectorAll('A')].filter(item => 'none' != item.parentNode.style.display);
!('tabindex' in menu) && menu.setAttribute('tabindex', '0');
menu.classList.add('show');
parent.classList.add('show');
element.setAttribute('aria-expanded',true);
element.open = true;
element.removeEventListener('click',clickHandler);
open(true);
setTimeout(() => {
setFocus( menu.getElementsByTagName('INPUT')[0] || element );
toggleEvents();
},1);
};
self.hide = () => {
menu.classList.remove('show');
parent.classList.remove('show');
element.setAttribute('aria-expanded',false);
element.open = false;
open(false);
toggleEvents();
setFocus(element);
setTimeout(() => element.Dropdown && element.addEventListener('click',clickHandler), 1);
};
self.toggle = () => element.open ? self.hide() : self.show();
element.addEventListener('click',clickHandler);
element.open = false;
open(false);
element.Dropdown = self;
},

View file

@ -5,9 +5,11 @@
// Inline and block code styles
code,
kbd,
samp,
pre {
padding: 0 3px 2px;
font-family: @monoFontFamily;
font-family: var(--fontMono);
font-size: @baseFontSize;
font-weight: normal;
line-height: @baseLineHeight;

View file

@ -19,10 +19,8 @@
width: 0;
height: 0;
vertical-align: top;
border-top: 4px solid @black;
border-right: 4px solid transparent;
border-left: 4px solid transparent;
content: "";
border: 4px solid transparent;
border-top-color: @black;
}
// Place the caret
@ -39,7 +37,6 @@
left: 0;
z-index: @zindexDropdown;
display: none; // none by default, but block on "open" of the menu
float: left;
min-width: 160px;
padding: 5px 0;
margin: 2px 0 0; // override default ul
@ -108,10 +105,3 @@
display: block;
}
}
// Right aligned dropdowns
// ---------------------------
.pull-right > .dropdown-menu {
right: 0;
left: auto;
}

View file

@ -36,29 +36,28 @@ legend {
}
}
// Set font for forms
label,
input,
button,
select,
textarea {
font-size: @baseFontSize;
font-weight: normal;
line-height: @baseLineHeight;
}
input,
button,
select,
textarea {
font-family: @baseFontFamily; // And only set font-family here for those that need it (note the missing label element)
}
// Identify controls by their labels
label {
display: block;
font-size: @baseFontSize;
font-weight: normal;
line-height: @baseLineHeight;
margin-bottom: 5px;
}
// Set font for forms
button,
input,
optgroup,
select,
textarea {
font-family: inherit;
font-size: @baseFontSize;
line-height: @baseLineHeight;
margin: 0;
text-transform: none;
}
// Form controls
// -------------------------
@ -66,12 +65,11 @@ label {
select,
textarea,
input:not([type="radio"]):not([type="checkbox"]):not([type="hidden"]) {
box-sizing: border-box;
display: inline-block;
height: @baseLineHeight;
height: @baseLineHeight + 10;
padding: 4px 6px;
margin-bottom: 9px;
font-size: @baseFontSize;
line-height: @baseLineHeight;
color: @gray;
border-radius: @inputBorderRadius;
}
@ -118,13 +116,6 @@ input[type="checkbox"] {
width: auto; // Override of generic input selector
}
// Set the height of select and file controls to match text inputs
select,
input[type="file"] {
height: 30px;
line-height: 30px;
}
// Make select elements obey height by applying a border
select {
width: 223px; // default input width + 10px of padding that doesn't get applied
@ -169,7 +160,6 @@ textarea::placeholder {
input[class*="span"],
select[class*="span"],
textarea[class*="span"] {
float: none;
margin-left: 0;
}
// Ensure input-prepend/append never wraps
@ -179,14 +169,6 @@ textarea[class*="span"] {
// GRID SIZING FOR INPUTS
// ----------------------
// Grid sizes
#grid > .input(@gridColumnWidth, @gridGutterWidth);
// DISABLED STATE
// --------------
@ -214,18 +196,10 @@ input[type="checkbox"][readonly] {
// FORM FIELD FEEDBACK STATES
// --------------------------
// Warning
.control-group.warning {
.formFieldState(@warningText, @warningText, @warningBackground);
}
// Error
.control-group.error {
.formFieldState(@errorText, @errorText, @errorBackground);
}
// Success
.control-group.success {
.formFieldState(@successText, @successText, @successBackground);
}
// HTML5 invalid states
// Shares styles with the .control-group.error above
@ -242,15 +216,6 @@ select:focus:required:invalid {
// HELP TEXT
// ---------
.help-block {
color: lighten(@textColor, 15%); // lighten the text some for contrast
display: block; // account for any element using help-block
margin-bottom: @baseLineHeight / 2;
}
// INPUT GROUPS
// ------------
@ -266,7 +231,7 @@ select:focus:required:invalid {
margin-bottom: 0; // prevent bottom margin from screwing up alignment in stacked forms
font-size: @baseFontSize;
vertical-align: top;
border-radius: 0 @inputBorderRadius @inputBorderRadius 0;
border-radius: @inputBorderRadius;
// Make input on top when focused so blue border and shadow always show
&:focus {
z-index: 2;
@ -296,12 +261,6 @@ select:focus:required:invalid {
background-color: lighten(@green, 30);
border-color: @green;
}
}
.input-append {
input,
select {
border-radius: @inputBorderRadius 0 0 @inputBorderRadius;
}
.add-on:last-child,
.btn:last-child {
border-radius: 0 @inputBorderRadius @inputBorderRadius 0;
@ -359,11 +318,10 @@ legend + .control-group {
// Increase spacing between groups
.control-group {
margin-bottom: @baseLineHeight;
.clearfix();
}
// Float the labels left
.control-label {
float: left;
display: inline-block;
width: 140px;
padding-top: 5px;
text-align: right;
@ -372,11 +330,8 @@ legend + .control-group {
.controls {
// Super jank IE7 fix to ensure the inputs in .input-append and input-prepend
// don't inherit the margin of the parent, in this case .controls
margin-left: 160px;
}
// Remove bottom margin on block level help text since that's accounted for on .control-group
.help-block {
margin-top: @baseLineHeight / 2;
margin-bottom: 0;
display: inline-block;
margin-left: 20px;
vertical-align: top;
}
}

View file

@ -2,9 +2,5 @@
// Grid system
// --------------------------------------------------
// Fixed (940px)
#grid > .core(@gridColumnWidth, @gridGutterWidth);
// Fluid (940px)
#grid > .fluid(@fluidGridColumnWidth, @fluidGridGutterWidth);

View file

@ -10,15 +10,13 @@
// --------
// For clearing floats like a boss h5bp.com/q
.clearfix {
&:before,
&:after {
&::before,
&::after {
display: table;
content: "";
// Fixes Opera/contenteditable bug:
// http://nicolasgallagher.com/micro-clearfix-hack/#comment-36952
line-height: 0;
}
&:after {
clear: both;
}
}
@ -49,8 +47,7 @@
// Mixin for form field states
.formFieldState(@textColor: #555, @borderColor: #ccc, @backgroundColor: #f5f5f5) {
// Set the text color
> label,
.help-block {
> label {
color: @textColor;
}
// Style inputs accordingly
@ -84,9 +81,7 @@
// Table columns
.tableColumns(@columnSpan: 1) {
float: none; // undo default grid column styles
width: ((@gridColumnWidth) * @columnSpan) + (@gridGutterWidth * (@columnSpan - 1)) - 16; // 16 is total padding on left and right of table cells
margin-left: 0; // undo default grid column styles
}
// The Grid
@ -101,119 +96,25 @@
}
.spanX (0) {}
.offsetX (@index) when (@index > 0) {
// (~".offset@{index}") { .offset(@index); }
.offset@{index} { .offset(@index); }
.offsetX(@index - 1);
}
.offsetX (0) {}
.offset (@columns) {
margin-left: (@gridColumnWidth * @columns) + (@gridGutterWidth * (@columns + 1));
}
.span (@columns) {
width: (@gridColumnWidth * @columns) + (@gridGutterWidth * (@columns - 1));
}
.row {
margin-left: @gridGutterWidth * -1;
.clearfix();
}
[class*="span"] {
float: left;
display: inline-block;
margin-left: @gridGutterWidth;
vertical-align: top;
}
// Set the container width
.container { .span(@gridColumns); }
// generate .spanX and .offsetX
.spanX (@gridColumns);
.offsetX (@gridColumns);
}
.fluid (@fluidGridColumnWidth, @fluidGridGutterWidth) {
.spanX (@index) when (@index > 0) {
// (~".span@{index}") { .span(@index); }
.span@{index} { .span(@index); }
.spanX(@index - 1);
}
.spanX (0) {}
.offsetX (@index) when (@index > 0) {
// (~'.offset@{index}') { .offset(@index); }
// (~'.offset@{index}:first-child') { .offsetFirstChild(@index); }
.offset@{index} { .offset(@index); }
.offset@{index}:first-child { .offsetFirstChild(@index); }
.offsetX(@index - 1);
}
.offsetX (0) {}
.offset (@columns) {
margin-left: (@fluidGridColumnWidth * @columns) + (@fluidGridGutterWidth * (@columns - 1)) + (@fluidGridGutterWidth*2);
}
.offsetFirstChild (@columns) {
margin-left: (@fluidGridColumnWidth * @columns) + (@fluidGridGutterWidth * (@columns - 1)) + (@fluidGridGutterWidth);
}
.span (@columns) {
width: (@fluidGridColumnWidth * @columns) + (@fluidGridGutterWidth * (@columns - 1));
}
.row-fluid {
width: 100%;
.clearfix();
[class*="span"] {
display: block;
width: 100%;
min-height: 30px; // Make inputs at least the height of their button counterpart
box-sizing: border-box; // Makes inputs behave like true block-level elements
float: left;
margin-left: @fluidGridGutterWidth;
}
[class*="span"]:first-child {
margin-left: 0;
}
// generate .spanX and .offsetX
.spanX (@gridColumns);
.offsetX (@gridColumns);
}
}
.input(@gridColumnWidth, @gridGutterWidth) {
.spanX (@index) when (@index > 0) {
// (~"input.span@{index}, textarea.span@{index}, .uneditable-input.span@{index}") { .span(@index); }
input.span@{index}, textarea.span@{index}, .uneditable-input.span@{index} { .span(@index); }
.spanX(@index - 1);
}
.spanX (0) {}
.span(@columns) {
width: ((@gridColumnWidth) * @columns) + (@gridGutterWidth * (@columns - 1)) - 14;
}
input,
textarea,
.uneditable-input {
margin-left: 0; // override margin-left from core grid system
}
// Space grid-sized controls properly if multiple per line
.controls-row [class*="span"] + [class*="span"] {
margin-left: @gridGutterWidth;
}
// generate .spanX
.spanX (@gridColumns);
}
}

View file

@ -21,11 +21,6 @@
background-color: @grayLighter;
}
// Redeclare pull classes because of specifity
.nav > .pull-right {
float: right;
}
// TABS
@ -42,6 +37,7 @@
}
// Actual tabs (as links)
.nav-tabs > li > a {
color: #555;
padding-top: 8px 12px;
margin-right: 2px;
line-height: 14px; // keeps the overall height an even number
@ -64,65 +60,6 @@
}
// DROPDOWNS
// ---------
.nav-tabs .dropdown-menu {
border-radius: 0 0 6px 6px; // remove the top rounded corners here since there is a hard edge above the menu
}
// Default dropdown links
// -------------------------
// Make carets use linkColor to start
.nav .dropdown-toggle .caret {
border-top-color: @linkColor;
border-bottom-color: @linkColor;
margin-top: 6px;
}
.nav .dropdown-toggle:hover .caret {
border-top-color: @linkColorHover;
border-bottom-color: @linkColorHover;
}
/* move down carets for tabs */
.nav-tabs .dropdown-toggle .caret {
margin-top: 8px;
}
// Active dropdown links
// -------------------------
.nav .active .dropdown-toggle .caret {
border-top-color: #fff;
border-bottom-color: #fff;
}
.nav-tabs .active .dropdown-toggle .caret {
border-top-color: @gray;
border-bottom-color: @gray;
}
// Active:hover dropdown links
// -------------------------
.nav > .dropdown.active > a:hover {
cursor: pointer;
}
// Open dropdowns
// -------------------------
.nav-tabs .open .dropdown-toggle,
.nav > li.dropdown.open.active > a:hover {
color: @white;
background-color: @grayLight;
border-color: @grayLight;
}
.nav li.dropdown.open .caret,
.nav li.dropdown.open.active .caret,
.nav li.dropdown.open a:hover .caret {
border-top-color: @white;
border-bottom-color: @white;
opacity: 1;
}
// TABBABLE
// --------
@ -141,18 +78,3 @@
.tab-content > .active {
display: block;
}
// DISABLED STATES
// ---------------
// Gray out text
.nav > .disabled > a {
color: @grayLight;
}
// Nuke hover effects
.nav > .disabled > a:hover {
text-decoration: none;
background-color: transparent;
cursor: default;
}

View file

@ -37,8 +37,6 @@
vertical-align: bottom;
}
// Remove top border from thead by default
caption + thead tr:first-child th,
caption + thead tr:first-child td,
colgroup + thead tr:first-child th,
colgroup + thead tr:first-child td,
thead:first-child tr:first-child th,
@ -66,9 +64,6 @@
border-left: 1px solid @tableBorder;
}
// Prevent a double border
caption + thead tr:first-child th,
caption + tbody tr:first-child th,
caption + tbody tr:first-child td,
colgroup + thead tr:first-child th,
colgroup + tbody tr:first-child th,
colgroup + tbody tr:first-child td,
@ -99,14 +94,10 @@
}
// Special fixes to round the left border on the first td/th
caption + thead tr:first-child th:first-child,
caption + tbody tr:first-child td:first-child,
colgroup + thead tr:first-child th:first-child,
colgroup + tbody tr:first-child td:first-child {
border-radius: 4px 0 0 0;
}
caption + thead tr:first-child th:last-child,
caption + tbody tr:first-child td:last-child,
colgroup + thead tr:first-child th:last-child,
colgroup + tbody tr:first-child td:last-child {
border-radius: 0 4px 0 0;
@ -148,10 +139,8 @@
// -----------------
// Reset default grid behavior
table [class*=span],
.row-fluid table [class*=span] {
table [class*=span] {
display: table-cell;
float: none; // undo default grid column styles
margin-left: 0; // undo default grid column styles
}
@ -163,39 +152,6 @@ table {
.span4 { .tableColumns(4); }
.span5 { .tableColumns(5); }
.span6 { .tableColumns(6); }
.span7 { .tableColumns(7); }
.span8 { .tableColumns(8); }
.span9 { .tableColumns(9); }
.span10 { .tableColumns(10); }
.span11 { .tableColumns(11); }
.span12 { .tableColumns(12); }
.span13 { .tableColumns(13); }
.span14 { .tableColumns(14); }
.span15 { .tableColumns(15); }
.span16 { .tableColumns(16); }
.span17 { .tableColumns(17); }
.span18 { .tableColumns(18); }
.span19 { .tableColumns(19); }
.span20 { .tableColumns(20); }
.span21 { .tableColumns(21); }
.span22 { .tableColumns(22); }
.span23 { .tableColumns(23); }
.span24 { .tableColumns(24); }
}
// TABLE BACKGROUNDS
// -----------------
// Exact selectors below required to override .table-striped
.table {
tbody tr.success td {
background-color: @successBackground;
}
tbody tr.error td {
background-color: @errorBackground;
}
tbody tr.info td {
background-color: @infoBackground;
}
}

View file

@ -15,10 +15,10 @@ p {
// -------------------------
small {
font-size: 85%; // Ex: 14px base font * 85% = about 12px
font-size: 80%; // Ex: 14px base font * 85% = about 12px
}
strong {
font-weight: bold;
b, strong {
font-weight: bolder;
}
em {
font-style: italic;
@ -36,16 +36,8 @@ cite {
h1, h2, h3, h4, h5, h6 {
margin: (@baseLineHeight / 2) 0;
font-family: @headingsFontFamily;
font-weight: @headingsFontWeight;
line-height: 1;
color: @headingsColor;
text-rendering: optimizelegibility; // Fix the character spacing for headings
small {
font-weight: normal;
line-height: 1;
color: @grayLight;
}
}
h1 { font-size: 36px; line-height: 40px; }
h2 { font-size: 30px; line-height: 40px; }
@ -54,11 +46,6 @@ h4 { font-size: 18px; line-height: 20px; }
h5 { font-size: 14px; line-height: 20px; }
h6 { font-size: 12px; line-height: 20px; }
h1 small { font-size: 24px; }
h2 small { font-size: 18px; }
h3 small { font-size: 14px; }
h4 small { font-size: 14px; }
// Lists
// --------------------------------------------------
@ -77,26 +64,6 @@ ol ul {
li {
line-height: @baseLineHeight;
}
ul.unstyled,
ol.unstyled {
margin-left: 0;
list-style: none;
}
// Description Lists
dl {
margin-bottom: @baseLineHeight;
}
dt,
dd {
line-height: @baseLineHeight;
}
dt {
font-weight: bold;
}
dd {
margin-left: @baseLineHeight / 2;
}
// MISC
// ----
@ -107,16 +74,15 @@ hr {
border: 0;
border-top: 1px solid @hrBorder;
border-bottom: 1px solid @white;
box-sizing: content-box;
height: 0;
}
// Abbreviations and acronyms
abbr[title] {
cursor: help;
border-bottom: 1px dotted @grayLight;
}
abbr.initialism {
font-size: 90%;
text-transform: uppercase;
text-decoration: none;
}
// Blockquotes
@ -126,46 +92,15 @@ blockquote {
border-left: 5px solid @grayLighter;
p {
margin-bottom: 0;
font-size: 16px;
font-weight: 300;
line-height: @baseLineHeight * 1.25;
}
small {
display: block;
line-height: @baseLineHeight;
color: @grayLight;
&:before {
content: '\2014 \00A0';
}
}
// Float right with text-align: right
&.pull-right {
float: right;
padding-right: 15px;
padding-left: 0;
border-right: 5px solid @grayLighter;
border-left: 0;
p,
small {
text-align: right;
}
small {
&:before {
content: '';
}
&:after {
content: '\00A0 \2014';
}
}
}
}
// Quotes
q:before,
q:after,
blockquote:before,
blockquote:after {
q::before,
q::after,
blockquote::before,
blockquote::after {
content: "";
}

View file

@ -44,19 +44,8 @@
// Typography
// -------------------------
@sansFontFamily: "Helvetica Neue", Helvetica, Arial, sans-serif;
@serifFontFamily: Georgia, "Times New Roman", Times, serif;
@monoFontFamily: Monaco, Menlo, Consolas, "Courier New", monospace;
@baseFontSize: 14px;
@baseFontFamily: @sansFontFamily;
@baseLineHeight: 20px;
@altFontFamily: @serifFontFamily;
@headingsFontFamily: inherit; // empty to use BS default, @baseFontFamily
@headingsFontWeight: bold; // instead of browser default, bold
@headingsColor: inherit; // empty to use BS default, @textColor
// Tables
// -------------------------

View file

@ -1,82 +1,8 @@
/*! normalize.css v8.0.1 | MIT License | github.com/necolas/normalize.css */
/* Document
========================================================================== */
/**
* Correct the font size and margin on `h1` elements within `section` and
* `article` contexts in Chrome, Firefox, and Safari.
*/
h1 {
font-size: 2em;
margin: 0.67em 0;
}
/* Grouping content
========================================================================== */
/**
* 1. Add the correct box sizing in Firefox.
*/
hr {
box-sizing: content-box; /* 1 */
height: 0; /* 1 */
}
/**
* 1. Correct the inheritance and scaling of font size in all browsers.
* 2. Correct the odd `em` font sizing in all browsers.
*/
pre {
font-family: monospace; /* 1 */
font-size: 1em; /* 2 */
}
/* Text-level semantics
========================================================================== */
/**
* 1. Remove the bottom border in Chrome 57-
* 2. Add the correct text decoration in Chrome, Edge, Opera, and Safari.
*/
abbr[title] {
border-bottom: none; /* 1 */
text-decoration: underline dotted; /* 2 */
}
/**
* Add the correct font weight in Chrome, Edge, and Safari.
*/
b,
strong {
font-weight: bolder;
}
/**
* 1. Correct the inheritance and scaling of font size in all browsers.
* 2. Correct the odd `em` font sizing in all browsers.
*/
code,
kbd,
samp {
font-family: monospace; /* 1 */
font-size: 1em; /* 2 */
}
/**
* Add the correct font size in all browsers.
*/
small {
font-size: 80%;
}
/**
* Prevent `sub` and `sup` elements from affecting the line height in
* all browsers.
@ -101,32 +27,6 @@ sup {
/* Forms
========================================================================== */
/**
* 1. Change the font styles in all browsers.
* 2. Remove the margin in Firefox and Safari.
*/
button,
input,
optgroup,
select,
textarea {
font-family: inherit; /* 1 */
font-size: 100%; /* 1 */
line-height: 1.15; /* 1 */
margin: 0; /* 2 */
}
/**
* Remove the inheritance of text transform in Edge, Firefox.
* 1. Remove the inheritance of text transform in Firefox.
*/
button,
select { /* 1 */
text-transform: none;
}
/**
* Correct the inability to style clickable types in iOS and Safari.
*/
@ -161,15 +61,6 @@ button:-moz-focusring,
outline: 1px dotted ButtonText;
}
/**
* 3. Remove the padding so developers are not caught out when they zero out
* `fieldset` elements in all browsers.
*/
legend {
padding: 0; /* 3 */
}
/**
* Correct the cursor style of increment and decrement buttons in Chrome.
*/

View file

@ -7,7 +7,7 @@
(global => {
const isFunction = obj => typeof obj === 'function';
const isFunction = obj => typeof obj === 'function';
// Crossroads --------
//====================
@ -124,14 +124,10 @@
}
_getParamsArray(request) {
var norm = this.rules.normalize_,
params;
if (isFunction(norm)) {
params = norm(request, this._getParamsObject(request));
} else {
params = patternLexer.getParamValues(request, this._matchRegexp);
}
return params;
var norm = this.rules.normalize_;
return isFunction(norm)
? norm(request, this._getParamsObject(request))
: patternLexer.getParamValues(request, this._matchRegexp);
}
}
@ -162,7 +158,6 @@
SAVED_OPTIONAL_SLASHES_REGEXP = new RegExp(SAVE_OPTIONAL_SLASHES, 'g'),
SAVED_REQUIRED_SLASHES_REGEXP = new RegExp(SAVE_REQUIRED_SLASHES, 'g'),
captureVals = (regex, pattern) => {
var vals = [], match;
while (match = regex.exec(pattern)) {
@ -197,12 +192,11 @@
return vals;
},
compilePattern : pattern => {
pattern = pattern || '';
if (pattern) {
pattern = untokenize(
pattern = pattern
? untokenize(
tokenize(pattern.replace(UNNECESSARY_SLASHES_REGEXP, '')).replace(ESCAPE_CHARS_REGEXP, '\\$&')
);
}
)
: '';
return new RegExp('^'+ pattern + '/?$'); //trailing slash is optional
}
};