From 9d81bf030d75bb65ae009bd94fd84604b7cc2ae7 Mon Sep 17 00:00:00 2001 From: zadam Date: Sun, 12 Jan 2020 19:05:09 +0100 Subject: [PATCH] tab row widgetizing --- config-sample.ini | 2 +- src/public/javascripts/desktop.js | 4 +- .../javascripts/services/app_context.js | 146 ++++++------ .../javascripts/services/note_detail.js | 2 - .../javascripts/services/tab_context.js | 118 +--------- src/public/javascripts/services/tab_row.js | 62 +++-- src/public/javascripts/widgets/note_title.js | 219 ++++++++++++++++++ .../{services => widgets}/note_type.js | 54 +++-- .../javascripts/widgets/tab_aware_widget.js | 19 ++ src/public/stylesheets/desktop.css | 15 -- src/public/stylesheets/style.css | 6 - src/views/center.ejs | 2 - src/views/desktop.ejs | 4 +- src/views/title.ejs | 71 ------ 14 files changed, 389 insertions(+), 335 deletions(-) create mode 100644 src/public/javascripts/widgets/note_title.js rename src/public/javascripts/{services => widgets}/note_type.js (75%) create mode 100644 src/public/javascripts/widgets/tab_aware_widget.js delete mode 100644 src/views/title.ejs diff --git a/config-sample.ini b/config-sample.ini index 36d546ebe..20c747197 100644 --- a/config-sample.ini +++ b/config-sample.ini @@ -8,7 +8,7 @@ instanceName= [Network] # host setting is relevant only for web deployments - set the host on which the server will listen # host=0.0.0.0 -# port setting is relevant only for web deployments, desktop builds run on random free port +# port setting is relevant only for web deployments, desktop builds run on a fixed port (changeable with TRILIUM_PORT environment variable) port=8080 # true for TLS/SSL/HTTPS (secure), false for HTTP (unsecure). https=false diff --git a/src/public/javascripts/desktop.js b/src/public/javascripts/desktop.js index ece9f9885..b93de56a6 100644 --- a/src/public/javascripts/desktop.js +++ b/src/public/javascripts/desktop.js @@ -3,7 +3,7 @@ import contextMenu from './services/tree_context_menu.js'; import link from './services/link.js'; import ws from './services/ws.js'; import noteDetailService from './services/note_detail.js'; -import noteType from './services/note_type.js'; +import noteType from './widgets/note_type.js'; import protectedSessionService from './services/protected_session.js'; import protectedSessionHolder from './services/protected_session_holder.js'; import searchNotesService from './services/search_notes.js'; @@ -21,7 +21,7 @@ import bundle from "./services/bundle.js"; import treeCache from "./services/tree_cache.js"; import libraryLoader from "./services/library_loader.js"; import hoistedNoteService from './services/hoisted_note.js'; -import noteTypeService from './services/note_type.js'; +import noteTypeService from './widgets/note_type.js'; import linkService from './services/link.js'; import noteAutocompleteService from './services/note_autocomplete.js'; import macInit from './services/mac_init.js'; diff --git a/src/public/javascripts/services/app_context.js b/src/public/javascripts/services/app_context.js index c24173698..336b0a357 100644 --- a/src/public/javascripts/services/app_context.js +++ b/src/public/javascripts/services/app_context.js @@ -2,13 +2,12 @@ import GlobalButtonsWidget from "../widgets/global_buttons.js"; import SearchBoxWidget from "../widgets/search_box.js"; import SearchResultsWidget from "../widgets/search_results.js"; import NoteTreeWidget from "../widgets/note_tree.js"; -import tabRow from "./tab_row.js"; import treeService from "./tree.js"; import noteDetailService from "./note_detail.js"; import TabContext from "./tab_context.js"; import server from "./server.js"; import keyboardActionService from "./keyboard_actions.js"; -import contextMenuService from "./context_menu.js"; +import TabRowWidget from "./tab_row.js"; class AppContext { constructor() { @@ -16,6 +15,30 @@ class AppContext { /** @type {TabContext[]} */ this.tabContexts = []; this.tabsChangedTaskId = null; + /** @type {TabRowWidget} */ + this.tabRow = null; + } + + showWidgets() { + const $leftPane = $("#left-pane"); + + this.tabRow = new TabRowWidget(this); + $("#tab-row-container").append(this.tabRow.render()); + + this.noteTreeWidget = new NoteTreeWidget(this); + + this.widgets = [ + new GlobalButtonsWidget(this), + new SearchBoxWidget(this), + new SearchResultsWidget(this), + this.noteTreeWidget + ]; + + for (const widget of this.widgets) { + const $widget = widget.render(); + + $leftPane.append($widget); + } } trigger(name, data) { @@ -31,7 +54,7 @@ class AppContext { /** @returns {TabContext} */ getActiveTabContext() { - const activeTabEl = tabRow.activeTabEl; + const activeTabEl = this.tabRow.activeTabEl; if (!activeTabEl) { return null; @@ -115,25 +138,6 @@ class AppContext { } } - showWidgets() { - const $leftPane = $("#left-pane"); - - this.noteTreeWidget = new NoteTreeWidget(this); - - this.widgets = [ - new GlobalButtonsWidget(this), - new SearchBoxWidget(this), - new SearchResultsWidget(this), - this.noteTreeWidget - ]; - - for (const widget of this.widgets) { - const $widget = widget.render(); - - $leftPane.append($widget); - } - } - /** * @return {NoteTreeWidget} */ @@ -144,7 +148,7 @@ class AppContext { getTab(newTab, state) { if (!this.getActiveTabContext() || newTab) { // if it's a new tab explicitly by user then it's in background - const ctx = new TabContext(tabRow, state); + const ctx = new TabContext(this.tabRow, state); this.tabContexts.push(ctx); return ctx; @@ -174,16 +178,16 @@ class AppContext { } async openEmptyTab() { - const ctx = new TabContext(tabRow); + const ctx = new TabContext(this.tabRow); this.tabContexts.push(ctx); - await tabRow.activateTab(ctx.$tab[0]); + await this.tabRow.activateTab(ctx.$tab[0]); } async filterTabs(noteId) { for (const tc of this.tabContexts) { if (tc.notePath && !tc.notePath.split("/").includes(noteId)) { - await tabRow.removeTab(tc.$tab[0]); + await this.tabRow.removeTab(tc.$tab[0]); } } @@ -197,7 +201,7 @@ class AppContext { async saveOpenTabs() { const openTabs = []; - for (const tabEl of tabRow.tabEls) { + for (const tabEl of this.tabRow.tabEls) { const tabId = tabEl.getAttribute('data-tab-id'); const tabContext = appContext.getTabContexts().find(tc => tc.tabId === tabId); @@ -229,81 +233,63 @@ class AppContext { this.tabsChangedTaskId = setTimeout(() => this.saveOpenTabs(), 1000); } + + newTabListener() { + this.openEmptyTab(); + } + + async activeTabChangedListener({tabEl}) { + const tabId = tabEl.getAttribute('data-tab-id'); + + await this.showTab(tabId); + } + + async tabRemoveListener({tabEl}) { + const tabId = tabEl.getAttribute('data-tab-id'); + + this.tabContexts.filter(nc => nc.tabId === tabId) + .forEach(tc => tc.remove()); + + this.tabContexts = this.tabContexts.filter(nc => nc.tabId !== tabId); + + if (this.tabContexts.length === 0) { + this.openEmptyTab(); + } + + this.openTabsChanged(); + } + + tabReorderListener() { + this.openTabsChanged(); + } } const appContext = new AppContext(); -tabRow.addListener('newTab', () => appContext.openEmptyTab()); - -tabRow.addListener('activeTabChange', async ({ detail }) => { - const tabId = detail.tabEl.getAttribute('data-tab-id'); - - await appContext.showTab(tabId); -}); - -tabRow.addListener('tabRemove', async ({ detail }) => { - const tabId = detail.tabEl.getAttribute('data-tab-id'); - - appContext.tabContexts.filter(nc => nc.tabId === tabId) - .forEach(tc => tc.remove()); - - appContext.tabContexts = appContext.tabContexts.filter(nc => nc.tabId !== tabId); - - if (appContext.tabContexts.length === 0) { - appContext.openEmptyTab(); - } -}); - -tabRow.addListener('activeTabChange', () => appContext.openTabsChanged()); -tabRow.addListener('tabRemove', () => appContext.openTabsChanged()); -tabRow.addListener('tabReorder', () => appContext.openTabsChanged()); - keyboardActionService.setGlobalActionHandler('OpenNewTab', () => { appContext.openEmptyTab(); }); keyboardActionService.setGlobalActionHandler('CloseActiveTab', () => { - if (tabRow.activeTabEl) { - tabRow.removeTab(tabRow.activeTabEl); + if (this.tabRow.activeTabEl) { + this.tabRow.removeTab(this.tabRow.activeTabEl); } }); keyboardActionService.setGlobalActionHandler('ActivateNextTab', () => { - const nextTab = tabRow.nextTabEl; + const nextTab = this.tabRow.nextTabEl; if (nextTab) { - tabRow.activateTab(nextTab); + this.tabRow.activateTab(nextTab); } }); keyboardActionService.setGlobalActionHandler('ActivatePreviousTab', () => { - const prevTab = tabRow.previousTabEl; + const prevTab = this.tabRow.previousTabEl; if (prevTab) { - tabRow.activateTab(prevTab); + this.tabRow.activateTab(prevTab); } }); -$(tabRow.el).on('contextmenu', '.note-tab', e => { - e.preventDefault(); - - const tab = $(e.target).closest(".note-tab"); - - contextMenuService.initContextMenu(e, { - getContextMenuItems: () => { - return [ - {title: "Close all tabs", cmd: "removeAllTabs", uiIcon: "empty"}, - {title: "Close all tabs except for this", cmd: "removeAllTabsExceptForThis", uiIcon: "empty"} - ]; - }, - selectContextMenuItem: (e, cmd) => { - if (cmd === 'removeAllTabs') { - tabRow.removeAllTabs(); - } else if (cmd === 'removeAllTabsExceptForThis') { - tabRow.removeAllTabsExceptForThis(tab[0]); - } - } - }); -}); - export default appContext; \ No newline at end of file diff --git a/src/public/javascripts/services/note_detail.js b/src/public/javascripts/services/note_detail.js index 4f7af4d60..4730492d3 100644 --- a/src/public/javascripts/services/note_detail.js +++ b/src/public/javascripts/services/note_detail.js @@ -4,10 +4,8 @@ import server from './server.js'; import ws from "./ws.js"; import treeCache from "./tree_cache.js"; import NoteFull from "../entities/note_full.js"; -import contextMenuService from "./context_menu.js"; import treeUtils from "./tree_utils.js"; import tabRow from "./tab_row.js"; -import keyboardActionService from "./keyboard_actions.js"; import appContext from "./app_context.js"; const $tabContentsContainer = $("#note-tab-container"); diff --git a/src/public/javascripts/services/tab_context.js b/src/public/javascripts/services/tab_context.js index 794e8f80a..8cee17575 100644 --- a/src/public/javascripts/services/tab_context.js +++ b/src/public/javascripts/services/tab_context.js @@ -3,13 +3,8 @@ import protectedSessionHolder from "./protected_session_holder.js"; import server from "./server.js"; import bundleService from "./bundle.js"; import Attributes from "./attributes.js"; -import treeUtils from "./tree_utils.js"; import utils from "./utils.js"; -import NoteTypeContext from "./note_type.js"; -import noteDetailService from "./note_detail.js"; -import protectedSessionService from "./protected_session.js"; import optionsService from "./options.js"; -import linkService from "./link.js"; import Sidebar from "./sidebar.js"; import appContext from "./app_context.js"; @@ -36,7 +31,7 @@ optionsService.addLoadListener(options => { class TabContext { /** - * @param {TabRow} tabRow + * @param {TabRowWidget} tabRow * @param {object} state */ constructor(tabRow, state = {}) { @@ -61,13 +56,8 @@ class TabContext { $tabContentsContainer.append(this.$tabContent); - this.$noteTitle = this.$tabContent.find(".note-title"); - this.$noteTitleRow = this.$tabContent.find(".note-title-row"); - this.$notePathList = this.$tabContent.find(".note-path-list"); - this.$notePathCount = this.$tabContent.find(".note-path-count"); this.$noteDetailComponents = this.$tabContent.find(".note-detail-component"); this.$scriptArea = this.$tabContent.find(".note-detail-script-area"); - this.$savedIndicator = this.$tabContent.find(".saved-indicator"); this.noteChangeDisabled = false; this.isNoteChanged = false; this.attributes = new Attributes(this); @@ -78,41 +68,10 @@ class TabContext { }; this.sidebar = new Sidebar(this, sidebarState); - this.noteType = new NoteTypeContext(this); } this.components = {}; - this.$noteTitle.on('input', () => { - if (!this.note) { - return; - } - - this.noteChanged(); - - this.note.title = this.$noteTitle.val(); - - this.tabRow.updateTab(this.$tab[0], {title: this.note.title}); - treeService.setNoteTitle(this.note.noteId, this.note.title); - - this.setTitleBar(); - }); - - if (utils.isDesktop()) { - // keyboard plugin is not loaded in mobile - utils.bindElShortcut(this.$noteTitle, 'return', () => { - this.getComponent().focus(); - - return false; // to not propagate the enter into the editor (causes issues with codemirror) - }); - } - - this.$protectButton = this.$tabContent.find(".protect-button"); - this.$protectButton.on('click', protectedSessionService.protectNoteAndSendToServer); - - this.$unprotectButton = this.$tabContent.find(".unprotect-button"); - this.$unprotectButton.on('click', protectedSessionService.unprotectNoteAndSendToServer); - await this.initComponent(); } @@ -156,8 +115,6 @@ class TabContext { this.noteChangeDisabled = true; try { - this.$noteTitle.val(this.note.title); - await this.renderComponent(); } finally { this.noteChangeDisabled = false; @@ -177,12 +134,6 @@ class TabContext { } }, 5000); - this.showPaths(); - - if (utils.isDesktop()) { - this.noteType.update(); - } - bundleService.executeRelationBundles(this.note, 'runOnNoteView', this); // after loading new note make sure editor is scrolled to the top @@ -281,12 +232,7 @@ class TabContext { this.$tabContent.addClass(utils.getNoteTypeClass(this.note.type)); this.$tabContent.addClass(utils.getMimeTypeClass(this.note.mime)); - this.$noteTitleRow.show(); // might be hidden from empty detail this.$tabContent.toggleClass("protected", this.note.isProtected); - this.$protectButton.toggleClass("active", this.note.isProtected); - this.$protectButton.prop("disabled", this.note.isProtected); - this.$unprotectButton.toggleClass("active", !this.note.isProtected); - this.$unprotectButton.prop("disabled", !this.note.isProtected || !protectedSessionHolder.isProtectedSessionAvailable()); } getComponent() { @@ -349,12 +295,11 @@ class TabContext { protectedSessionHolder.touchProtectedSession(); } - this.$savedIndicator.fadeIn(); + // FIXME trigger "noteSaved" event so that title indicator is triggered + this.eventReceived('noteSaved'); // run async bundleService.executeRelationBundles(this.note, 'runOnNoteChange', this); - - this.eventReceived('noteSaved'); } async saveNoteIfChanged() { @@ -372,65 +317,10 @@ class TabContext { this.isNoteChanged = true; + // FIMXE: trigger noteChanged event this.$savedIndicator.fadeOut(); } - async addPath(notePath, isCurrent) { - const title = await treeUtils.getNotePathTitle(notePath); - - const noteLink = await linkService.createNoteLink(notePath, {title}); - - noteLink - .addClass("no-tooltip-preview") - .addClass("dropdown-item"); - - if (isCurrent) { - noteLink.addClass("current"); - } - - this.$notePathList.append(noteLink); - } - - async showPaths() { - if (this.note.noteId === 'root') { - // root doesn't have any parent, but it's still technically 1 path - - this.$notePathCount.html("1 path"); - - this.$notePathList.empty(); - - await this.addPath('root', true); - } - else { - const parents = await this.note.getParentNotes(); - - this.$notePathCount.html(parents.length + " path" + (parents.length > 1 ? "s" : "")); - this.$notePathList.empty(); - - const pathSegments = this.notePath.split("/"); - const activeNoteParentNoteId = pathSegments[pathSegments.length - 2]; // we know this is not root so there must be a parent - - for (const parentNote of parents) { - const parentNotePath = await treeService.getSomeNotePath(parentNote); - // this is to avoid having root notes leading '/' - const notePath = parentNotePath ? (parentNotePath + '/' + this.note.noteId) : this.note.noteId; - const isCurrent = activeNoteParentNoteId === parentNote.noteId; - - await this.addPath(notePath, isCurrent); - } - - const cloneLink = $("
") - .addClass("dropdown-item") - .append( - $('
`; -class TabRow { - constructor(el) { +const TPL = ` +
+
+
`; + +export default class TabRowWidget extends BasicWidget { + async doRender($widget) { + $widget.append($(TPL)); + this.draggabillies = []; this.eventListeners = {}; - this.el = el; + this.el = $widget.find(".note-tab-row")[0]; this.setupStyleEl(); this.setupEvents(); @@ -46,17 +56,28 @@ class TabRow { this.setupFiller(); this.layoutTabs(); this.setVisibility(); - } - addListener(eventName, callback) { - this.eventListeners[eventName] = this.eventListeners[eventName] || []; - this.eventListeners[eventName].push(callback); - } + $(this.el).on('contextmenu', '.note-tab', e => { + e.preventDefault(); - async emit(eventName, data) { - for (const listener of this.eventListeners[eventName]) { - await listener({ detail: data }); - } + const tab = $(e.target).closest(".note-tab"); + + contextMenuService.initContextMenu(e, { + getContextMenuItems: () => { + return [ + {title: "Close all tabs", cmd: "removeAllTabs", uiIcon: "empty"}, + {title: "Close all tabs except for this", cmd: "removeAllTabsExceptForThis", uiIcon: "empty"} + ]; + }, + selectContextMenuItem: (e, cmd) => { + if (cmd === 'removeAllTabs') { + this.removeAllTabs(); + } else if (cmd === 'removeAllTabsExceptForThis') { + this.removeAllTabsExceptForThis(tab[0]); + } + } + }); + }) } setupStyleEl() { @@ -250,7 +271,7 @@ class TabRow { if (activeTabEl === tabEl) return; if (activeTabEl) activeTabEl.removeAttribute('active'); tabEl.setAttribute('active', ''); - await this.emit('activeTabChange', { tabEl }); + await this.trigger('activeTabChanged', { tabEl }); } async removeTab(tabEl) { @@ -262,7 +283,7 @@ class TabRow { } } tabEl.parentNode.removeChild(tabEl); - await this.emit('tabRemove', { tabEl }); + await this.trigger('tabRemove', { tabEl }); this.cleanUpPreviouslyDraggedTabs(); this.layoutTabs(); this.setupDraggabilly(); @@ -380,7 +401,7 @@ class TabRow { tabEl.parentNode.insertBefore(tabEl, beforeEl); } - await this.emit('tabReorder', { tabEl, originIndex, destinationIndex }); + await this.trigger('tabReorder', { tabEl, originIndex, destinationIndex }); this.layoutTabs(); } @@ -391,7 +412,7 @@ class TabRow { this.tabContentEl.appendChild(this.newTabEl); - this.newTabEl.addEventListener('click', _ => this.emit('newTab')); + this.newTabEl.addEventListener('click', _ => this.trigger('newTab')); } setupFiller() { @@ -415,9 +436,4 @@ class TabRow { return closestIndex; }; -} - -const noteTabRowEl = document.querySelector('.note-tab-row'); -const tabRow = new TabRow(noteTabRowEl); - -export default tabRow; \ No newline at end of file +} \ No newline at end of file diff --git a/src/public/javascripts/widgets/note_title.js b/src/public/javascripts/widgets/note_title.js new file mode 100644 index 000000000..ea7bb9392 --- /dev/null +++ b/src/public/javascripts/widgets/note_title.js @@ -0,0 +1,219 @@ +import TabAwareWidget from "./tab_aware_widget.js"; +import treeService from "../services/tree.js"; +import utils from "../services/utils.js"; +import protectedSessionService from "../services/protected_session.js"; +import treeUtils from "../services/tree_utils.js"; +import linkService from "../services/link.js"; +import protectedSessionHolder from "../services/protected_session_holder.js"; +import NoteTypeWidget from "./note_type.js"; + +const TPL = ` + + +
+
+ + + + + + +
+ + + + +
+ + + +
+ +     + +
+ + + +
+
+
+
`; + +export default class NoteTitleWidget extends TabAwareWidget { + constructor(appContext) { + super(appContext); + + this.tree = null; + } + + async doRender($widget) { + $widget.append($(TPL)); + + this.$noteTitle = this.$tabContent.find(".note-title"); + this.$noteTitleRow = this.$tabContent.find(".note-title-row"); + this.$notePathList = this.$tabContent.find(".note-path-list"); + this.$notePathCount = this.$tabContent.find(".note-path-count"); + + this.$protectButton = this.$tabContent.find(".protect-button"); + this.$protectButton.on('click', protectedSessionService.protectNoteAndSendToServer); + + this.$unprotectButton = this.$tabContent.find(".unprotect-button"); + this.$unprotectButton.on('click', protectedSessionService.unprotectNoteAndSendToServer); + + this.$savedIndicator = this.$tabContent.find(".saved-indicator"); + + this.noteType = new NoteTypeWidget(this); + + this.$noteTitle.on('input', () => { + if (!this.note) { + return; + } + + // FIXME event not used + this.trigger(`activeNoteChanged`); + + this.note.title = this.$noteTitle.val(); + + this.tabRow.updateTab(this.$tab[0], {title: this.note.title}); + treeService.setNoteTitle(this.note.noteId, this.note.title); + + this.setTitleBar(); + }); + + if (utils.isDesktop()) { + // keyboard plugin is not loaded in mobile + utils.bindElShortcut(this.$noteTitle, 'return', () => { + this.getComponent().focus(); + + return false; // to not propagate the enter into the editor (causes issues with codemirror) + }); + } + } + + async activeTabChanged() { + const note = this.tabContext.note; + + this.$noteTitle.val(this.note.title); + + this.$protectButton.toggleClass("active", note.isProtected); + this.$protectButton.prop("disabled", note.isProtected); + this.$unprotectButton.toggleClass("active", !note.isProtected); + this.$unprotectButton.prop("disabled", !note.isProtected || !protectedSessionHolder.isProtectedSessionAvailable()); + + await this.showPaths(); + } + + async showPaths() { + const note = this.tabContext.note; + + if (note.noteId === 'root') { + // root doesn't have any parent, but it's still technically 1 path + + this.$notePathCount.html("1 path"); + + this.$notePathList.empty(); + + await this.addPath('root', true); + } + else { + const parents = await note.getParentNotes(); + + this.$notePathCount.html(parents.length + " path" + (parents.length > 1 ? "s" : "")); + this.$notePathList.empty(); + + const pathSegments = this.notePath.split("/"); + const activeNoteParentNoteId = pathSegments[pathSegments.length - 2]; // we know this is not root so there must be a parent + + for (const parentNote of parents) { + const parentNotePath = await treeService.getSomeNotePath(parentNote); + // this is to avoid having root notes leading '/' + const notePath = parentNotePath ? (parentNotePath + '/' + note.noteId) : note.noteId; + const isCurrent = activeNoteParentNoteId === parentNote.noteId; + + await this.addPath(notePath, isCurrent); + } + + const cloneLink = $("
") + .addClass("dropdown-item") + .append( + $(' + +
+`; - this.$noteTypeDropdown = ctx.$tabContent.find(".note-type-dropdown"); - this.$noteTypeButton = ctx.$tabContent.find(".note-type-button"); - this.$noteTypeDesc = ctx.$tabContent.find(".note-type-desc"); - this.$executeScriptButton = ctx.$tabContent.find(".execute-script-button"); - this.$renderButton = ctx.$tabContent.find('.render-button'); +export default class NoteTypeWidget extends TabAwareWidget { + async doRender($widget) { + $widget.append($(TPL)); + + $widget.find('.note-type').on('show.bs.dropdown', () => this.renderDropdown()); + + this.$noteTypeDropdown = $widget.find(".note-type-dropdown"); + this.$noteTypeButton = $widget.find(".note-type-button"); + this.$noteTypeDesc = $widget.find(".note-type-desc"); + this.$executeScriptButton = $widget.find(".execute-script-button"); + this.$renderButton = $widget.find('.render-button'); + + return $widget; } async update() { @@ -41,6 +59,10 @@ export default class NoteTypeContext { this.$renderButton.toggle(this.ctx.note.type === 'render'); } + async activeTabChanged() { + this.update(); + } + /** actual body is rendered lazily on note-type button click */ async renderDropdown() { this.$noteTypeDropdown.empty(); diff --git a/src/public/javascripts/widgets/tab_aware_widget.js b/src/public/javascripts/widgets/tab_aware_widget.js new file mode 100644 index 000000000..c6d253067 --- /dev/null +++ b/src/public/javascripts/widgets/tab_aware_widget.js @@ -0,0 +1,19 @@ +import BasicWidget from "./basic_widget.js"; + +export default class TabAwareWidget extends BasicWidget { + constructor(appContext) { + super(appContext); + + /** @var {TabContext} */ + this.tabContext = null; + } + + // to override + activeTabChanged() {} + + activeTabChangedListener() { + this.tabContext = this.appContext.getActiveTabContext(); + + this.activeTabChanged(); + } +} \ No newline at end of file diff --git a/src/public/stylesheets/desktop.css b/src/public/stylesheets/desktop.css index 0545cb310..2e58b3cfb 100644 --- a/src/public/stylesheets/desktop.css +++ b/src/public/stylesheets/desktop.css @@ -175,21 +175,6 @@ body { border-color: var(--button-border-color); } -.note-title-row { - flex-grow: 0; - flex-shrink: 0; - padding-top: 2px; -} - -.note-title { - margin-left: 15px; - margin-right: 10px; - font-size: 150%; - border: 0; - width: 5em; - flex-grow: 100; -} - .note-tab-row { box-sizing: border-box; position: relative; diff --git a/src/public/stylesheets/style.css b/src/public/stylesheets/style.css index 44db06758..cfb68cd10 100644 --- a/src/public/stylesheets/style.css +++ b/src/public/stylesheets/style.css @@ -381,12 +381,6 @@ div.ui-tooltip { border-right: none; } -.note-type-dropdown { - max-height: 500px; - overflow-y: auto; - overflow-x: hidden; -} - .cm-matchhighlight { background-color: #eeeeee } diff --git a/src/views/center.ejs b/src/views/center.ejs index 97ade9a51..69cc9ed49 100644 --- a/src/views/center.ejs +++ b/src/views/center.ejs @@ -2,8 +2,6 @@
- <% include title.ejs %> -
diff --git a/src/views/desktop.ejs b/src/views/desktop.ejs index fdf8014aa..2a804379a 100644 --- a/src/views/desktop.ejs +++ b/src/views/desktop.ejs @@ -85,9 +85,7 @@
-
-
-
+