diff --git a/css/dialogs.css b/css/dialogs.css index c221b3d9..ac7fa7d4 100644 --- a/css/dialogs.css +++ b/css/dialogs.css @@ -1126,7 +1126,8 @@ color: var(--color-text); height: auto; padding: 5px; - font-size: 0.94em + font-size: 0.94em; + word-break: break-word; } #action_selector ul > li { height: 30px; diff --git a/css/window.css b/css/window.css index 4f85ee74..b5f8373a 100644 --- a/css/window.css +++ b/css/window.css @@ -429,11 +429,18 @@ flex-direction: row; position: relative; white-space: nowrap; - overflow-x: auto; - overflow-y: hidden; padding-left: 4px; background: var(--color-frame); } + #tab_bar #tab_bar_list { + display: flex; + flex-direction: row; + position: relative; + white-space: nowrap; + overflow-x: auto; + overflow-y: hidden; + margin-right: auto; + } #tab_bar .project_tab { background-color: var(--color-back); cursor: pointer; @@ -515,10 +522,22 @@ text-align: center; cursor: pointer; padding-top: 4px; + flex-shrink: 0; } #new_tab_button:hover { color: var(--color-light); } + #search_tab_button { + height: 100%; + width: 32px; + text-align: center; + cursor: pointer; + padding-top: 4px; + flex-shrink: 0; + } + #search_tab_button:hover { + color: var(--color-light); + } #tab_bar .project_tab > label.project_tab_session_badge { display: flex; flex-grow: 0; diff --git a/index.html b/index.html index 9b76fc16..f71daf90 100644 --- a/index.html +++ b/index.html @@ -358,31 +358,36 @@
-
- - -
- {{ project.saved ? 'clear' : 'fiber_manual_record' }} +
+
+ + +
+ {{ project.saved ? 'clear' : 'fiber_manual_record' }} +
+
+
+ add
-
- add +
+ search
diff --git a/js/interface/actions.js b/js/interface/actions.js index 1f52e068..8ce6a33d 100644 --- a/js/interface/actions.js +++ b/js/interface/actions.js @@ -2226,33 +2226,82 @@ const BARS = { length: 0, list: [] }, - computed: { - actions() { + methods: { + updateSearch() { var search_input = this._data.search_input.toUpperCase() - var list = this._data.list.empty() - for (var i = 0; i < Keybinds.actions.length; i++) { - var item = Keybinds.actions[i]; - if ( - search_input.length == 0 || - item.name.toUpperCase().includes(search_input) || - item.id.toUpperCase().includes(search_input) - ) { - if (item instanceof Action && Condition(item.condition)) { - list.push(item) - if (list.length > ActionControl.max_length) break; + var type; + if (search_input.includes(':')) { + [type, search_input] = search_input.split(/:\s*(.*)/); + search_input = search_input || ''; + } + var list = this._data.list.empty(); + if (!type) { + for (var i = 0; i < Keybinds.actions.length; i++) { + var item = Keybinds.actions[i]; + if ( + search_input.length == 0 || + item.name.toUpperCase().includes(search_input) || + item.id.toUpperCase().includes(search_input) + ) { + if (item instanceof Action && Condition(item.condition)) { + list.push(item) + if (list.length > ActionControl.max_length) break; + } } } } - if (list.length <= ActionControl.max_length) { - for (let key in settings) { - let setting = settings[key]; - if ( - search_input.length == 0 || - setting.name.toUpperCase().includes(search_input) || - key.toUpperCase().includes(search_input) - ) { - if (Condition(setting.condition)) { - list.push(setting) + if (!type || type == 'SETTINGS') { + if (list.length <= ActionControl.max_length) { + for (let key in settings) { + let setting = settings[key]; + if ( + search_input.length == 0 || + setting.name.toUpperCase().includes(search_input) || + key.toUpperCase().includes(search_input) + ) { + if (Condition(setting.condition)) { + list.push(setting) + if (list.length > ActionControl.max_length) break; + } + } + } + } + } + if (isApp && type == 'RECENT') { + if (list.length <= ActionControl.max_length) { + for (let project of recent_projects) { + if ( + search_input.length == 0 || + project.path.toUpperCase().includes(search_input) + ) { + list.push({ + name: project.name, + icon: project.icon, + description: project.path, + keybind_label: StartScreen.vue.getDate(project), + type: 'recent_project' + }) + if (list.length > ActionControl.max_length) break; + } + } + } + } + if (isApp && type == 'TAB') { + if (list.length <= ActionControl.max_length) { + for (let project of ModelProject.all) { + if ( + search_input.length == 0 || + project.name.toUpperCase().includes(search_input) || + project.geometry_name.toUpperCase().includes(search_input) + ) { + list.push({ + name: project.name, + icon: project.format.icon, + description: project.path, + keybind_label: Modes.options[project.mode].name, + uuid: project.uuid, + type: 'project_tab' + }) if (list.length > ActionControl.max_length) break; } } @@ -2266,11 +2315,9 @@ const BARS = { this._data.index = list.length-1; } return list; - } - }, - methods: { + }, subtext() { - let action = this.actions[this.index]; + let action = this.list[this.index]; if (Pressing.alt) { if (action instanceof Setting) { if (action.type == 'select') { @@ -2286,20 +2333,29 @@ const BARS = { } } }, + watch: { + search_input() { + this.updateSearch(); + } + }, template: ` search
    -
  • + > +
    + {{ item.name }} + +
-
{{ subtext() }}
+
{{ subtext() }}
` @@ -2325,19 +2381,24 @@ const ActionControl = { set open(state) {ActionControl.vue._data.open = !!state}, type: 'action_selector', max_length: 32, - select() { + select(input) { ActionControl.open = true; open_interface = ActionControl; ActionControl.vue._data.index = 0; + ActionControl.vue.updateSearch(); + if (input) { + ActionControl.vue.search_input = input; + } Vue.nextTick(_ => { - $('#action_selector > input').focus().select(); + let element = $('#action_selector > input'); + element.trigger('focus'); + if (!input) element.trigger('select'); }) - // Update settings icons. Might need to be moved for (let key in settings) { let setting = settings[key]; if (setting.type == 'toggle') { - setting.menu_node.children[0].innerText = setting.value ? 'check_box' : 'check_box_outline_blank'; + setting.icon = setting.value ? 'check_box' : 'check_box_outline_blank'; } } }, @@ -2361,7 +2422,15 @@ const ActionControl = { $('body').effect('shake'); Blockbench.showQuickMessage('Congratulations! You have discovered recursion!', 3000) } - action.trigger(e); + if (action.type == 'recent_project') { + Blockbench.read([action.description], {}, files => { + loadModelFile(files[0]); + }) + } else if (action.type == 'project_tab') { + ModelProject.all.find(p => p.uuid == action.uuid).select(); + } else { + action.trigger(e); + } }, click(action, e) { ActionControl.trigger(action, e) diff --git a/js/interface/settings.js b/js/interface/settings.js index 99dde791..fa1d0792 100644 --- a/js/interface/settings.js +++ b/js/interface/settings.js @@ -58,29 +58,15 @@ class Setting { }) } - // Menu node for action control - this.menu_node = document.createElement('li'); - - var icon = this.icon; - if (!icon) { - if (this.type == 'toggle') icon = this.value ? 'check_box' : 'check_box_outline_blank'; - if (this.type == 'number') icon = 'tag'; - if (this.type == 'password') icon = 'password'; - if (this.type == 'text') icon = 'format_color_text'; - if (this.type == 'select') icon = 'list'; - if (!icon) icon = 'settings'; + if (!this.icon) { + if (this.type == 'toggle') this.icon = this.value ? 'check_box' : 'check_box_outline_blank'; + if (this.type == 'number') this.icon = 'tag'; + if (this.type == 'password') this.icon = 'password'; + if (this.type == 'text') this.icon = 'format_color_text'; + if (this.type == 'select') this.icon = 'list'; + if (!this.icon) this.icon = 'settings'; } - let icon_node = Blockbench.getIconNode(icon); - this.menu_node.append(icon_node); - - let span = document.createElement('span'); - span.innerText = this.name; - this.menu_node.append(span); - - let label = document.createElement('label'); - label.innerText = tl('data.setting'); - label.className = 'keybinding_label'; - this.menu_node.append(label); + this.keybind_label = tl('data.setting'); } delete() { if (settings[this.id]) { diff --git a/js/io/project.js b/js/io/project.js index 7b22249a..f4bb86e0 100644 --- a/js/io/project.js +++ b/js/io/project.js @@ -415,6 +415,7 @@ onVueSetup(() => { drag_target_index: null, drag_position_index: null, close_tab_label: tl('projects.close_tab'), + search_tabs_label: tl('generic.search'), new_tab: { name: tl('projects.new_tab'), saved: true, @@ -451,13 +452,18 @@ onVueSetup(() => { this.new_tab.select(); setStartScreen(true); }, + searchTabs() { + ActionControl.select('tab:'); + }, mouseDown(tab, e1) { convertTouchEvent(e1); + e1.preventDefault(); if (this.thumbnail) { this.thumbnail.remove(); delete this.thumbnail; } + if (e1.button == 1) return; let scope = this; let active = false; @@ -564,10 +570,10 @@ onVueSetup(() => { mouseLeave() { if (this.thumbnail) { this.thumbnail_timeout = setTimeout(() => { - this.thumbnail.remove(); + if (this.thumbnail) this.thumbnail.remove(); delete this.thumbnail; delete this.thumbnail_timeout; - }, 40) + }, 80) } } }