diff --git a/app/assets/javascripts/app/frontend/controllers/footer.js b/app/assets/javascripts/app/frontend/controllers/footer.js index e59321187..6028de680 100644 --- a/app/assets/javascripts/app/frontend/controllers/footer.js +++ b/app/assets/javascripts/app/frontend/controllers/footer.js @@ -22,7 +22,8 @@ angular.module('app.frontend') } } }) - .controller('FooterCtrl', function ($rootScope, authManager, modelManager, $timeout, dbManager, syncManager, storageManager, passcodeManager) { + .controller('FooterCtrl', function ($rootScope, authManager, modelManager, $timeout, dbManager, + syncManager, storageManager, passcodeManager, componentManager, singletonManager) { this.user = authManager.user; @@ -106,4 +107,63 @@ angular.module('app.frontend') this.newUpdateAvailable = false; alert("A new update is ready to install. Updates address performance and security issues, as well as bug fixes and feature enhancements. Simply quit Standard Notes and re-open it for the update to be applied.") } + + + /* Rooms */ + + this.componentManager = componentManager; + this.rooms = []; + + modelManager.addItemSyncObserver("room-bar", "SN|Component", (allItems, validItems, deletedItems, source) => { + this.rooms = _.uniq(this.rooms.concat(allItems.filter((candidate) => {return candidate.area == "rooms"}))) + .filter((candidate) => {return !candidate.deleted}); + }); + + componentManager.registerHandler({identifier: "roomBar", areas: ["rooms"], activationHandler: (component) => { + if(component.active) { + $timeout(() => { + var iframe = componentManager.iframeForComponent(component); + if(iframe) { + var lastSize = component.getRoomLastSize(); + if(lastSize) { + componentManager.handleSetSizeEvent(component, lastSize); + } + iframe.onload = function() { + componentManager.registerComponentWindow(component, iframe.contentWindow); + }.bind(this); + } + }); + } + }, actionHandler: (component, action, data) => { + if(action == "set-size") { + componentManager.handleSetSizeEvent(component, data); + component.setRoomLastSize(data); + } + }}); + + this.selectRoom = function(room) { + room.show = !room.show; + if(room.show) { + this.componentManager.activateComponent(room); + } else { + this.hideRoom(room); + } + } + + this.hideRoom = function(room) { + room.show = false; + this.componentManager.deactivateComponent(room); + } + + // Handle singleton ProLink instance + singletonManager.registerSingleton({content_type: "SN|Component", package_info: {identifier: "org.standardnotes.prolink"}}, (resolvedSingleton) => { + console.log("Roombar received resolved ProLink", resolvedSingleton); + }, (valueCallback) => { + console.log("Creating prolink"); + // Safe to create. Create and return object. + let url = window._prolink_package_url; + packageManager.installPackage(url, (component) => { + valueCallback(component); + }) + }); }); diff --git a/app/assets/javascripts/app/services/directives/views/roomBar.js b/app/assets/javascripts/app/services/directives/views/roomBar.js deleted file mode 100644 index f237f1aa7..000000000 --- a/app/assets/javascripts/app/services/directives/views/roomBar.js +++ /dev/null @@ -1,73 +0,0 @@ -class RoomBar { - - constructor() { - this.restrict = "E"; - this.templateUrl = "frontend/directives/room-bar.html"; - this.scope = { - }; - } - - controller($rootScope, $scope, desktopManager, syncManager, modelManager, componentManager, $timeout, singletonManager, packageManager) { - 'ngInject'; - - $scope.componentManager = componentManager; - $scope.rooms = []; - - modelManager.addItemSyncObserver("room-bar", "SN|Component", (allItems, validItems, deletedItems, source) => { - $scope.rooms = _.uniq($scope.rooms.concat(allItems.filter((candidate) => {return candidate.area == "rooms"}))) - .filter((candidate) => {return !candidate.deleted}); - }); - - componentManager.registerHandler({identifier: "roomBar", areas: ["rooms"], activationHandler: (component) => { - if(component.active) { - $timeout(() => { - var iframe = componentManager.iframeForComponent(component); - if(iframe) { - var lastSize = component.getRoomLastSize(); - if(lastSize) { - componentManager.handleSetSizeEvent(component, lastSize); - } - iframe.onload = function() { - componentManager.registerComponentWindow(component, iframe.contentWindow); - }.bind(this); - } - }); - } - }, actionHandler: (component, action, data) => { - if(action == "set-size") { - componentManager.handleSetSizeEvent(component, data); - component.setRoomLastSize(data); - } - }}); - - $scope.selectRoom = function(room) { - room.show = !room.show; - if(room.show) { - this.componentManager.activateComponent(room); - } else { - $scope.hideRoom(room); - } - } - - $scope.hideRoom = function(room) { - room.show = false; - this.componentManager.deactivateComponent(room); - } - - // Handle singleton ProLink instance - singletonManager.registerSingleton({content_type: "SN|Component", package_info: {identifier: "org.standardnotes.prolink"}}, (resolvedSingleton) => { - console.log("Roombar received resolved ProLink", resolvedSingleton); - }, (valueCallback) => { - console.log("Creating prolink"); - // Safe to create. Create and return object. - let url = window._prolink_package_url; - packageManager.installPackage(url, (component) => { - valueCallback(component); - }) - }); - } - - -} - -angular.module('app.frontend').directive('roomBar', () => new RoomBar); diff --git a/app/assets/stylesheets/app/_footer.scss b/app/assets/stylesheets/app/_footer.scss index c705c0a69..c9110a733 100644 --- a/app/assets/stylesheets/app/_footer.scss +++ b/app/assets/stylesheets/app/_footer.scss @@ -33,6 +33,7 @@ #account-panel { width: 400px; + cursor: default; } a.disabled { @@ -67,60 +68,11 @@ a.disabled { // padding-bottom: 6px; } } - } - - - -#room-bar { - display: inline-block; - border-left: 1px solid rgba(black, 0.1); - padding-left: 15px; - padding-right: 10px; - margin-left: 15px; - position: relative; - - .room-item { - display: inline-block; - position: relative; - vertical-align: middle; - - .label { - display: inline-block; - vertical-align: middle; - font-size: 11px; - margin-top: -2px; - } - - .icon { - width: 16px; - height: 16px; - display: inline-block; - vertical-align: middle; - } - - .room-container { - max-height: 85vh; - position: absolute; - right: 0px; - bottom: 20px; - min-width: 300px; - z-index: 1000; - margin-top: 15px; - - box-shadow: 0px 0px 15px rgba(black, 0.2); - border: none; - cursor: default; - overflow: auto; - background-color: white; - } - - .room-iframe { - width: 100%; - height: 100%; - } - } +.room-iframe { + width: 100%; + height: 100%; } diff --git a/app/assets/stylesheets/app/_notes.scss b/app/assets/stylesheets/app/_notes.scss index 468c999da..88fce804f 100644 --- a/app/assets/stylesheets/app/_notes.scss +++ b/app/assets/stylesheets/app/_notes.scss @@ -20,7 +20,7 @@ font-weight: normal; font-size: 18px; - .title { + .section-title-bar-header .title { color: rgba(black, 0.40); width: calc(90% - 45px); } diff --git a/app/assets/templates/frontend/directives/account-menu.html.haml b/app/assets/templates/frontend/directives/account-menu.html.haml index 19da283c1..3c674d434 100644 --- a/app/assets/templates/frontend/directives/account-menu.html.haml +++ b/app/assets/templates/frontend/directives/account-menu.html.haml @@ -55,17 +55,20 @@ %div{"ng-if" => "!formData.showLogin && !formData.showRegister"} .panel-section{"ng-if" => "user"} - %h2 {{user.email}} - %p {{server}} - %div.bold.mt-10.tinted{"delay-hide" => "true", "show" => "syncStatus.syncOpInProgress || syncStatus.needsMoreSync", "delay" => "1000"} - .spinner.inline.mr-5.tinted - {{"Syncing" + (syncStatus.total > 0 ? ":" : "")}} - %span{"ng-if" => "syncStatus.total > 0"} {{syncStatus.current}}/{{syncStatus.total}} - %p.bold.mt-10.red.block{"ng-if" => "syncStatus.error"} Error syncing: {{syncStatus.error.message}} + .panel-row + %h2.title.wrap {{user.email}} + .horizontal-group{"delay-hide" => "true", "show" => "syncStatus.syncOpInProgress || syncStatus.needsMoreSync", "delay" => "1000"} + .spinner.small.info + .sublabel + {{"Syncing" + (syncStatus.total > 0 ? ":" : "")}} + %span{"ng-if" => "syncStatus.total > 0"} {{syncStatus.current}}/{{syncStatus.total}} + + .subtitle.danger.panel-row{"ng-if" => "syncStatus.error"} Error syncing: {{syncStatus.error.message}} + + .subtitle.subtle.panel-row {{server}} - - %a.panel-row{"ng-click" => "newPasswordData.changePassword = !newPasswordData.changePassword"} Change Password + %a.panel-row.condensed{"ng-click" => "newPasswordData.changePassword = !newPasswordData.changePassword"} Change Password .notification.default{"ng-if" => "newPasswordData.changePassword"} %h1.title Change Password (Beta) .text @@ -87,21 +90,10 @@ - %a.panel-row{"ng-click" => "showAdvanced = !showAdvanced"} Advanced + %a.panel-row.condensed{"ng-click" => "showAdvanced = !showAdvanced"} Advanced %div{"ng-if" => "showAdvanced"} %a.panel-row{"href" => "{{dashboardURL()}}", "target" => "_blank"} Data Dashboard %a.panel-row{"ng-click" => "reencryptPressed()"} Re-encrypt All Items - %a.panel-row{"ng-click" => "showCredentials = !showCredentials"} Show Credentials - %section.gray-bg.mt-10.medium-padding{"ng-if" => "showCredentials"} - %label.block - Encryption key: - .wrap.normal.mt-1.selectable {{encryptionKey()}} - %label.block.mt-5.mb-0 - Server password: - .wrap.normal.mt-1.selectable {{serverPassword() ? serverPassword() : 'Not available. Sign out then sign back in to compute.'}} - %label.block.mt-5.mb-0 - Authentication key: - .wrap.normal.mt-1.selectable {{authKey() ? authKey() : 'Not available. Sign out then sign back in to compute.'}} %div{"ng-if" => "securityUpdateAvailable()"} @@ -119,19 +111,21 @@ .panel-section - %h3.title Encryption - %h5.subtitle{"ng-if" => "encryptionEnabled()"} + %h3.title.panel-row Encryption + %h5.subtitle.info.panel-row{"ng-if" => "encryptionEnabled()"} {{encryptionStatusForNotes()}} %p {{encryptionStatusString()}} .panel-section - %h3.title Passcode Lock + %h3.title.panel-row Passcode Lock %div{"ng-if" => "!hasPasscode() && passcodeOptionAvailable()"} - .button.info{"ng-click" => "addPasscodeClicked()", "ng-if" => "!formData.showPasscodeForm"} - .label Add Passcode + .panel-row + .button.info{"ng-click" => "addPasscodeClicked(); $event.stopPropagation();", "ng-if" => "!formData.showPasscodeForm"} + .label Add Passcode - %p Add an app passcode to lock the app and encrypt on-device key storage. + .panel-row + %p Add an app passcode to lock the app and encrypt on-device key storage. %form.mt-5{"ng-if" => "formData.showPasscodeForm", "ng-submit" => "submitPasscodeForm()"} %input.form-control.mt-10{:type => 'password', "ng-model" => "formData.passcode", "placeholder" => "Passcode", "autofocus" => "true"} @@ -139,12 +133,13 @@ .button-group.stretch.panel-row.form-submit .button.info{"type" => "submit"} .label Set Passcode - %div{"ng-if" => "hasPasscode()"} + %a.panel-row{"ng-click" => "formData.showPasscodeForm = false"} Cancel + .panel-row{"ng-if" => "hasPasscode()"} %p Passcode lock is enabled. %span{"ng-if" => "isDesktopApplication()"} Your passcode will be required on new sessions after app quit. %a.block.mt-5{"ng-click" => "removePasscodePressed()"} Remove Passcode - %div{"ng-if" => "!passcodeOptionAvailable()"} + .panel-row{"ng-if" => "!passcodeOptionAvailable()"} %p Passcode lock is only available to permanent sessions. (You chose not to stay signed in.) diff --git a/app/assets/templates/frontend/directives/room-bar.html.haml b/app/assets/templates/frontend/directives/room-bar.html.haml deleted file mode 100644 index 76002f265..000000000 --- a/app/assets/templates/frontend/directives/room-bar.html.haml +++ /dev/null @@ -1,5 +0,0 @@ -.room-item{"ng-repeat" => "room in rooms", "ng-click" => "selectRoom(room)", "click-outside" => "hideRoom(room)", "is-open" => "room.show && room.active"} - %img.icon{"ng-src" => "{{room.package_info.icon_bar}}"} - .label {{room.name}} - .room-container.panel-right{"ng-if" => "room.show && room.active", "ng-attr-id" => "component-{{room.uuid}}"} - %iframe.room-iframe{"ng-src" => "{{componentManager.urlForComponent(room) | trusted}}", "frameBorder" => "0", "sandbox" => "allow-scripts allow-top-navigation-by-user-activation allow-popups allow-popups-to-escape-sandbox allow-modals", "data-component-id" => "{{room.uuid}}"} diff --git a/app/assets/templates/frontend/editor.html.haml b/app/assets/templates/frontend/editor.html.haml index b63d1f280..574fe2f88 100644 --- a/app/assets/templates/frontend/editor.html.haml +++ b/app/assets/templates/frontend/editor.html.haml @@ -21,7 +21,7 @@ .menu-panel.dropdown-menu{"ng-if" => "ctrl.showMenu"} .section .header - %h4.title Note + %h4.title Note Options %menu-row{"title" => "ctrl.note.pinned ? 'Unpin' : 'Pin'", "ng-click" => "ctrl.selectedMenuItem($event); ctrl.togglePin()"} %menu-row{"title" => "ctrl.note.archived ? 'Unarchive' : 'Archive'", "ng-click" => "ctrl.selectedMenuItem($event); ctrl.toggleArchiveNote()"} %menu-row{"title" => "'Delete'", "ng-click" => "ctrl.selectedMenuItem($event); ctrl.deleteNote()"} diff --git a/app/assets/templates/frontend/footer.html.haml b/app/assets/templates/frontend/footer.html.haml index 4b772f60e..54634cdec 100644 --- a/app/assets/templates/frontend/footer.html.haml +++ b/app/assets/templates/frontend/footer.html.haml @@ -4,31 +4,38 @@ .item{"click-outside" => "ctrl.showAccountMenu = false;", "is-open" => "ctrl.showAccountMenu"} .column .circle.small.info - .column - .label.title{"ng-click" => "ctrl.accountMenuPressed()", "ng-class" => "{red: ctrl.error}"} Account + .column{"ng-click" => "ctrl.accountMenuPressed()"} + .label.title{"ng-class" => "{red: ctrl.error}"} Account %account-menu{"ng-if" => "ctrl.showAccountMenu", "on-successful-auth" => "ctrl.onAuthSuccess"} .item{"click-outside" => "ctrl.showExtensionsMenu = false;", "is-open" => "ctrl.showExtensionsMenu"} - .label.title{"ng-click" => "ctrl.toggleExtensions()"} Extensions + .column{"ng-click" => "ctrl.toggleExtensions()"} + .label.title Extensions %global-extensions-menu{"ng-if" => "ctrl.showExtensionsMenu"} .item .label.title{"href" => "https://standardnotes.org/help", "target" => "_blank"} Help - %room-bar#room-bar + .item.border + + .item{"ng-repeat" => "room in ctrl.rooms", "ng-click" => "ctrl.selectRoom(room)", "click-outside" => "ctrl.hideRoom(room)", "is-open" => "room.show && room.active"} + .label {{room.name}} + .sn-component + .panel-right.panel{"ng-if" => "room.show && room.active", "ng-attr-id" => "component-{{room.uuid}}"} + %iframe.room-iframe{"ng-src" => "{{ctrl.componentManager.urlForComponent(room) | trusted}}", "frameBorder" => "0", "sandbox" => "allow-scripts allow-top-navigation-by-user-activation allow-popups allow-popups-to-escape-sandbox allow-modals", "data-component-id" => "{{room.uuid}}"} + .right .item{"ng-if" => "ctrl.newUpdateAvailable", "ng-click" => "ctrl.clickedNewUpdateAnnouncement()"} %span.tinted.normal New update downloaded. Installs on app restart. - .item{"ng-if" => "ctrl.lastSyncDate"} - .label - %span{"ng-if" => "!ctrl.isRefreshing"} - Last refreshed {{ctrl.lastSyncDate | appDateTime}} - %span{"ng-if" => "ctrl.isRefreshing"} - .spinner + .item.no-pointer{"ng-if" => "ctrl.lastSyncDate && !ctrl.isRefreshing"} + .label.subtle + Last refreshed {{ctrl.lastSyncDate | appDateTime}} + .item{"ng-if" => "ctrl.lastSyncDate && ctrl.isRefreshing"} + .spinner.small .item{"ng-if" => "ctrl.offline"} .label Offline diff --git a/vendor/assets/stylesheets/stylekit.css b/vendor/assets/stylesheets/stylekit.css index 2a06681db..07729e74c 100644 --- a/vendor/assets/stylesheets/stylekit.css +++ b/vendor/assets/stylesheets/stylekit.css @@ -48,9 +48,6 @@ .sn-component .panel .content .panel-section.hero { text-align: center; } -.sn-component .panel .content .panel-section.hero .title { - margin-bottom: 1.1rem; -} .sn-component .panel .content .panel-section p:last-child { margin-bottom: 0; } @@ -67,16 +64,29 @@ margin-top: 2.1rem; margin-bottom: 15px; } -.sn-component .panel .content .panel-section .title { - margin-bottom: 12px; -} .sn-component .panel .content .panel-section .subtitle { - color: #086DD6; margin-top: -4px; } +.sn-component .panel .content .panel-section .subtitle.subtle { + font-weight: normal; + opacity: 0.6; +} .sn-component .panel .content .panel-section .panel-row { - display: block; - padding: 0.4rem 0; + display: flex; + justify-content: space-between; + align-items: center; + padding-top: 0.4rem; +} +.sn-component .panel .content .panel-section .panel-row:not(:last-child) { + padding-bottom: 0.4rem; +} +.sn-component .panel .content .panel-section .panel-row:not(:last-child).condensed { + padding-top: 0.2rem; + padding-bottom: 0.2rem; +} +.sn-component .panel .content .panel-section .panel-row p { + margin: 0; + padding: 0; } .sn-component .panel .content .panel-form { width: 100%; @@ -178,6 +188,9 @@ .sn-component a { cursor: pointer; } +.sn-component .wrap { + word-wrap: break-word; +} .sn-component *.info { color: #086DD6; } @@ -217,10 +230,11 @@ margin-right: 0.45rem; /* Space after checkbox */ } -.sn-component .input-group > * { +.sn-component .horizontal-group > *, .sn-component .input-group > * { display: inline-block; + vertical-align: middle; } -.sn-component .input-group > *:not(:first-child) { +.sn-component .horizontal-group > *:not(:first-child), .sn-component .input-group > *:not(:first-child) { margin-left: 0.9rem; } .sn-component .checkbox-group { @@ -241,6 +255,7 @@ } .sn-component .button-group.stretch { display: flex; + width: 100%; } .sn-component .button-group.stretch .button, .sn-component .button-group.stretch .box, .sn-component .button-group.stretch .circle { display: block; @@ -249,7 +264,6 @@ } .sn-component .button-group .button, .sn-component .button-group .box, .sn-component .button-group .circle { display: inline-block; - margin-bottom: 5px; } .sn-component .button-group .button:not(:last-child), .sn-component .button-group .box:not(:last-child), .sn-component .button-group .circle:not(:last-child) { margin-right: 5px; @@ -259,7 +273,6 @@ } .sn-component .box-group .box { display: inline-block; - margin-bottom: 5px; } .sn-component .box-group .box:not(:last-child) { margin-right: 5px; @@ -529,10 +542,21 @@ .sn-component .app-bar .item:not(:first-child) { margin-left: 1rem; } +.sn-component .app-bar .item.border { + border-left: 1px solid #DDDDDD; +} +.sn-component .app-bar .item > .column { + height: 100%; + display: flex; + align-items: center; +} .sn-component .app-bar .item > .column:not(:first-child) { margin-left: 0.5rem; } -.sn-component .app-bar .item:hover > .label, .sn-component .app-bar .panel .content .panel-section .item:hover > .subtitle, .sn-component .panel .content .panel-section .app-bar .item:hover > .subtitle, .sn-component .app-bar .item:hover > .sublabel, .sn-component .app-bar .item:hover > .column > .label, .sn-component .app-bar .panel .content .panel-section .item:hover > .column > .subtitle, .sn-component .panel .content .panel-section .app-bar .item:hover > .column > .subtitle, .sn-component .app-bar .item:hover > .column > .sublabel { +.sn-component .app-bar .item.no-pointer { + cursor: default; +} +.sn-component .app-bar .item:hover > .label:not(.subtle), .sn-component .app-bar .panel .content .panel-section .item:hover > .subtitle:not(.subtle), .sn-component .panel .content .panel-section .app-bar .item:hover > .subtitle:not(.subtle), .sn-component .app-bar .item:hover > .sublabel:not(.subtle), .sn-component .app-bar .item:hover > .column > .label:not(.subtle), .sn-component .app-bar .panel .content .panel-section .item:hover > .column > .subtitle:not(.subtle), .sn-component .panel .content .panel-section .app-bar .item:hover > .column > .subtitle:not(.subtle), .sn-component .app-bar .item:hover > .column > .sublabel:not(.subtle) { color: #086DD6; } .sn-component .app-bar .item > .label, .sn-component .app-bar .panel .content .panel-section .item > .subtitle, .sn-component .panel .content .panel-section .app-bar .item > .subtitle, .sn-component .app-bar .item > .column > .label, .sn-component .app-bar .panel .content .panel-section .item > .column > .subtitle, .sn-component .panel .content .panel-section .app-bar .item > .column > .subtitle { @@ -545,5 +569,9 @@ font-weight: normal; white-space: nowrap; } +.sn-component .app-bar .item .subtle { + font-weight: normal; + opacity: 0.6; +} /*# sourceMappingURL=stylekit.css.map */