From 9fbf91db06a6d4f4b5cd8bb45389a731bb86bf22 Mon Sep 17 00:00:00 2001 From: Richard Date: Sun, 13 Apr 2025 18:48:02 +0100 Subject: initial --- site/app/twist/twist_ui.js | 674 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 674 insertions(+) create mode 100644 site/app/twist/twist_ui.js (limited to 'site/app/twist/twist_ui.js') diff --git a/site/app/twist/twist_ui.js b/site/app/twist/twist_ui.js new file mode 100644 index 0000000..08e5fe1 --- /dev/null +++ b/site/app/twist/twist_ui.js @@ -0,0 +1,674 @@ +var twistTopMenuData = [ + {name: "File", contents: [ + {name: "New", disableOnPlay: true, shortcut: {name: "Ctrl N", ctrlKey: true, key: "n"}, click: function(twist) { + twist.createNewInstance(); + }, condition: function(twist) { + return (!twist.twine); + }}, + {name: "Save", disableOnPlay: true, shortcut: {name: "Ctrl S", ctrlKey: true, key: "s"}, click: function(twist) { + twist.saveFile(); + }}, + {name: "Close", disableOnPlay: true, shortcut: {name: "Ctrl W", ctrlKey: true, key: "w"}, click: function(twist) { + twist.closeInstance(); + }, condition: function(twist) { + return (!twist.twine && twist.waveforms.length != 1); + }}, + {name: "Edit in twigs", click: function(twist) { + twist.editInTwigs(); + }, condition: function(twist) { + return window.hasOwnProperty("Twigs"); + }} + ]}, + {name: "Edit", contents: [ + {name: "Undo", disableOnPlay: true, shortcut: {name: "Ctrl Z", ctrlKey: true, key: "z"}, click: function(twist) { + twist.undo(); + }, condition: function(twist) { + return (twist.storage.maxundo > 0 && twist.undoLevel > 0); + }}, + {preset: "divider"}, + {name: "Copy", disableOnPlay: true, shortcut: {name: "Ctrl C", ctrlKey: true, key: "c"}, click: function(twist) { + twist.copy(); + }}, + {name: "Cut", disableOnPlay: true, shortcut: {name: "Ctrl X", ctrlKey: true, key: "x"}, click: function(twist) { + twist.cut(); + }}, + {name: "Paste", disableOnPlay: true, shortcut: {name: "Ctrl V", ctrlKey: true, key: "v"}, click: function(twist) { + twist.paste(); + }, condition: function(twist) { + return twist.hasClipboard; + }}, + {name: "Paste special", disableOnPlay: true, shortcut: {name: "Ctrl shift V", ctrlKey: true, shiftKey: true, key: "v"}, click: function() { + twist.pasteSpecial(); + }, condition: function(twist) { + return twist.hasClipboard; + }}, + {name: "Trim", disableOnPlay: true, shortcut: {name: "T", key: "t"}, click: function() { + twist.trim(); + }}, + {name: "Delete", disableOnPlay: true, shortcut: {name: "Del", key: "delete"}, keyCondition: function(twist) { + return !twist.ui.deleteSupressed; + }, click: function(twist) { + twist.delete(); + }}, + {preset: "divider"}, + {name: "Select all", shortcut: {name: "Ctrl A", ctrlKey: true, key: "a"}, click: function(twist) { + twist.selectAll(); + }}, + {name: "Select to end", shortcut: {name: "W", key: "w"}, click: function(twist) { + twist.selectToEnd(); + }}, + {name: "Select from start", shortcut: {name: "Q", key: "q"}, click: function(twist) { + twist.selectFromStart(); + }}, + {name: "Select none", shortcut: {name: "Ctrl M", ctrlKey: true, key: "m"}, click: function(twist) { + twist.selectNone(); + }}, + {name: "Move to next transient", shortcut: {name: "[",key: "["}, click: function(twist) { + twist.moveToNextTransient(); + }}, + {name: "Select to next transient", shortcut: {name: "]",key: "]"}, click: function(twist) { + twist.selectToNextTransient(); + }} + ]}, + {name: "View", contents: [ + {name: "Zoom selection", shortcut: {name: "Z", key: "z"}, click: function(twist) { + twist.waveform.zoomSelection(); + }}, + {name: "Zoom in", shortcut: {name: "+", key: "+"}, click: function(twist) { + twist.waveform.zoomIn(); + }}, + {name: "Zoom out", shortcut: {name: "-", key: "-"}, click: function(twist) { + twist.waveform.zoomOut(); + }}, + {name: "Show all", shortcut: {name: "0", key: "0"}, click: function(twist) { + twist.waveform.setRegion(0, 1); + }}, + {preset: "divider"}, + {name: "Toggle analysis", click: function(twist){ + twist.ui.toggleScope(); + }}, + {name: "Toggle layout", shortcut: {name: "L", key: "l"}, click: function(twist){ + twist.ui.toggleLayout(); + }}, + ]}, + {name: "Action", contents: [ + {name: "Play/stop", shortcut: {name: "Space", key: " "}, click: function(twist) { + if (twist.isPlaying()) { + twist.stop(); + } else { + twist.play(); + } + }}, + {name: "Audition", disableOnPlay: true, shortcut: {name: "Enter", key: "enter"}, click: function(twist) { + twist.audition(); + }}, + {name: "Commit", disableOnPlay: true, shortcut: {name: "Alt enter", altKey: true, key: "enter"}, click: function(twist) { + twist.commit(); + }}, + {name: "Record", disableOnPlay: true, shortcut: {name: "R", key: "r"}, click: function(twist) { + twist.record(); + }}, + {preset: "divider"}, + {name: "Scripting", shortcut: {name: "Ctrl K", ctrlKey: true, key: "k"}, click: function(twist) { + twist.ui.scriptEdit(); + }}, + {name: "Developer", shortcut: {name: "Ctrl L", ctrlKey: true, key: "l"}, click: function(twist) { + twist.ui.developerConsole(); + }}, + + ]}, + {name: "Transform", contents: [ + {name: "Randomise", shortcut: {name: "Z", key: "z"}, click: function(twist) { + twist.currentTransform.randomise(); + }, condition: function(twist) { + return (twist.currentTransform) ? true : false; + }}, + {name: "Reset", shortcut: {name: "R", key: "r"}, click: function(twist) { + twist.currentTransform.reset(); + }, condition: function(twist) { + return (twist.currentTransform) ? true : false; + }}, + {name: "Hide automation", shortcut: {name: "H", key: "h"}, click: function(twist) { + twist.currentTransform.hideAllAutomation(); + }, condition: function(twist) { + return (twist.currentTransform) ? true : false; + }} + ]}, + {name: "Options", contents: [ + {name: "Settings", click: function(twist) { + twist.ui.showSettings(); + }} + ]}, + {name: "Help", contents: [ + {name: "Help", click: function(twist){ + $("#twist_documentation")[0].click(); + }}, + {name: "Developer reference", click: function(twist){ + $("#twist_developer_documentation")[0].click(); + }}, + {name: "Report bug", click: function(twist){ + $("#twist_reportbug")[0].click(); + }}, + {name: "Contact owner", click: function(twist){ + $("#twist_contact")[0].click(); + }}, + {name: "Submit transform code", click: function(twist){ + $("#twist_developer_submit")[0].click(); + }}, + {name: "About", click: function(twist) { + twist.ui.showAbout(); + }}, + ]}, +]; + + +var TwistUI = function(twist) { + var self = this; + var scope; + var elCrossfades = []; + var topMenu = new twirl.TopMenu(twist, twistTopMenuData, $("#twist_menubar")); + this.deleteSupressed = false; + + this.setPlaying = function(state) { + if (scope) { + scope.setPlaying(state); + } + if (state) { + $(".twist_scriptbutton").hide(); + $("#twist_scriptstop").show(); + } else { + $(".twist_scriptbutton").show(); + $("#twist_scriptstop").hide(); + } + }; + + this.getCrossFadeValues = function() { + return [elCrossfades[0].val(), elCrossfades[1].val()]; + }; + + + var contractedWaveform = false; + function setLayout() { + var elViews = $("#twist_views"); + var elWave = $("#twist_waveforms"); + var elSpline = $("#twist_splines"); + var elScope = $("#twist_analyser"); + var elControls = $("#twist_controls"); + + if (contractedWaveform) { + elViews.css({height: "20%"}); + elControls.css({top: "20%"}); + } else { + elViews.css({height: "50%"}); + elControls.css({top: "50%"}); + } + + if (scope) { + elScope.css({height: "40%", top: "0px"}); + elWave.css({top: "40%"}); + elSpline.css({top: elWave.css("top")}); + } else { + elWave.css({top: "0px"}); + elSpline.css({top: "0px"}); + } + + twist.redraw(); + } + + this.toggleLayout = function() { + contractedWaveform = !contractedWaveform; + setLayout(); + }; + + this.toggleScope = function(noSaveState) { + var state; + if (!scope) { + state = true; + var elScope = $("
").addClass("twist_scope").appendTo($("#twist_analyser")); + var type = (twist.storage.scopeType) ? twist.storage.scopeType : 0; + scope = new Analyser( + type, twist, elScope, app + ); + $("#twist_analyser").show(); + } else { + $("#twist_analyser").hide(); + state = false; + scope.remove(); + delete scope; + scope = null; + } + + if (!noSaveState) { + twist.storage.showScope = state; + twist.saveStorage(); + } + setLayout(); + }; + + + this.tooltip = twirl.tooltip; + + this.boot = function() { + if (twist.storage.hasOwnProperty("showShortcuts")) { + if (twist.storage.showShortcuts) { + $("#twist_wavecontrols_inner").show(); + } else { + $("#twist_wavecontrols_inner").hide(); + } + } + + if (twist.storage.develop) { + if (twist.storage.develop.csound) { + $("#twist_devcsound").val(twist.storage.develop.csound); + } + if (twist.storage.develop.json) { + $("#twist_devjson").val(twist.storage.develop.json); + } + } + $("#loading_background").css("opacity", 1).animate({opacity: 0.2}, 1000); + }; + + this.postBoot = function() { + self.setLoadingStatus(false); + + if (!twist.storage.hasOwnProperty("firstLoadDone")) { + twist.storage.firstLoadDone = true; + twist.saveStorage(); + self.showPrompt($("#twist_welcome").detach().show(), twist.createNewInstance); + } else { + twist.createNewInstance(); + } + + if (twist.storage.showScope) { + self.toggleScope(true); + } + }; + + this.hidePrompt = function() { + twirl.prompt.hide(); + }; + + this.showPrompt = function(text, oncomplete, noButton) { + twirl.prompt.show(text, oncomplete, noButton); + if (twist.playheadInterval) { + twist.waveform.movePlayhead(0); + clearInterval(twist.playheadInterval); + } + if (self.waveform) { + self.waveform.cover(false); + } + }; + + + this.showLoadNewPrompt = function() { + var elNewFile = $("
").css({"font-size": "var(--fontSizeDefault)"}); + if (twist.hasClipboard) { + $("