/* ***** BEGIN LICENSE BLOCK ***** * Distributed under the BSD license: * * Copyright (c) 2010, Ajax.org B.V. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * Neither the name of Ajax.org B.V. nor the * names of its contributors may be used to endorse or promote products * derived from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL AJAX.ORG B.V. BE LIABLE FOR ANY * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * * ***** END LICENSE BLOCK ***** */ define(function(require, exports, module) { "use strict"; require("ace/lib/fixoldbrowsers"); require("ace/config").init(); var env = {}; var dom = require("ace/lib/dom"); var net = require("ace/lib/net"); var lang = require("ace/lib/lang"); var useragent = require("ace/lib/useragent"); var event = require("ace/lib/event"); var theme = require("ace/theme/textmate"); var EditSession = require("ace/edit_session").EditSession; var UndoManager = require("ace/undomanager").UndoManager; var vim = require("ace/keyboard/vim").handler; var emacs = require("ace/keyboard/emacs").handler; var HashHandler = require("ace/keyboard/hash_handler").HashHandler; var Renderer = require("ace/virtual_renderer").VirtualRenderer; var Editor = require("ace/editor").Editor; var MultiSelect = require("ace/multi_select").MultiSelect; var doclist = require("./doclist"); var modelist = require("./modelist"); var layout = require("./layout"); var TokenTooltip = require("./token_tooltip").TokenTooltip; var util = require("./util"); var saveOption = util.saveOption; var fillDropdown = util.fillDropdown; var bindCheckbox = util.bindCheckbox; var bindDropdown = util.bindDropdown; /*********** create editor ***************************/ var container = document.getElementById("editor"); // Splitting. var Split = require("ace/split").Split; var split = new Split(container, theme, 1); env.editor = split.getEditor(0); split.on("focus", function(editor) { env.editor = editor; updateUIEditorOptions(); }); env.split = split; window.env = env; window.ace = env.editor; env.editor.setAnimatedScroll(true); // add multiple cursor support to editor require("ace/multi_select").MultiSelect(env.editor); var consoleEl = dom.createElement("div"); container.parentNode.appendChild(consoleEl); consoleEl.style.cssText = "position:fixed; bottom:1px; right:0;\ border:1px solid #baf; zIndex:100"; var cmdLine = new layout.singleLineEditor(consoleEl); cmdLine.editor = env.editor; env.editor.cmdLine = cmdLine; /** * This demonstrates how you can define commands and bind shortcuts to them. */ env.editor.commands.addCommands([{ name: "gotoline", bindKey: {win: "Ctrl-L", mac: "Command-L"}, exec: function(editor, line) { if (typeof line == "object") { var arg = this.name + " " + editor.getCursorPosition().row; editor.cmdLine.setValue(arg, 1); editor.cmdLine.focus(); return; } line = parseInt(line, 10); if (!isNaN(line)) editor.gotoLine(line); }, readOnly: true }, { name: "find", bindKey: {win: "Ctrl-F", mac: "Command-F"}, exec: function(editor, needle) { if (typeof needle == "object") { var arg = this.name + " " + editor.getCopyText(); editor.cmdLine.setValue(arg, 1); editor.cmdLine.focus(); return; } editor.find(needle); }, readOnly: true }, { name: "focusCommandLine", bindKey: "shift-esc", exec: function(editor, needle) { editor.cmdLine.focus(); }, readOnly: true }, { name: "execute", bindKey: "ctrl+enter", exec: function(editor) { try { var r = eval(editor.getCopyText()||editor.getValue()); } catch(e) { r = e; } editor.cmdLine.setValue(r + "") }, readOnly: true }]); cmdLine.commands.bindKeys({ "Shift-Return|Ctrl-Return|Alt-Return": function(cmdLine) { cmdLine.insert("\n"); }, "Esc|Shift-Esc": function(cmdLine){ cmdLine.editor.focus(); }, "Return": function(cmdLine){ var command = cmdLine.getValue().split(/\s+/); var editor = cmdLine.editor; editor.commands.exec(command[0], editor, command[1]); editor.focus(); } }); cmdLine.commands.removeCommands(["find", "gotoline", "findall", "replace", "replaceall"]); var commands = env.editor.commands; commands.addCommand({ name: "save", bindKey: {win: "Ctrl-S", mac: "Command-S"}, exec: function() {alert("Fake Save File");} }); var keybindings = { // Null = use "default" keymapping ace: null, vim: vim, emacs: emacs, // This is a way to define simple keyboard remappings custom: new HashHandler({ "gotoright": "Tab", "indent": "]", "outdent": "[", "gotolinestart": "^", "gotolineend": "$" }) }; /*********** manage layout ***************************/ var consoleHeight = 20; function onResize() { var left = env.split.$container.offsetLeft; var width = document.documentElement.clientWidth - left; container.style.width = width + "px"; container.style.height = document.documentElement.clientHeight - consoleHeight + "px"; env.split.resize(); consoleEl.style.width = width + "px"; cmdLine.resize(); } window.onresize = onResize; onResize(); /*********** options panel ***************************/ var docEl = document.getElementById("doc"); var modeEl = document.getElementById("mode"); var wrapModeEl = document.getElementById("soft_wrap"); var themeEl = document.getElementById("theme"); var foldingEl = document.getElementById("folding"); var selectStyleEl = document.getElementById("select_style"); var highlightActiveEl = document.getElementById("highlight_active"); var showHiddenEl = document.getElementById("show_hidden"); var showGutterEl = document.getElementById("show_gutter"); var showPrintMarginEl = document.getElementById("show_print_margin"); var highlightSelectedWordE = document.getElementById("highlight_selected_word"); var showHScrollEl = document.getElementById("show_hscroll"); var animateScrollEl = document.getElementById("animate_scroll"); var softTabEl = document.getElementById("soft_tab"); var behavioursEl = document.getElementById("enable_behaviours"); fillDropdown(docEl, doclist.all); fillDropdown(modeEl, modelist.modes); var modesByName = modelist.modesByName; bindDropdown("mode", function(value) { env.editor.session.setMode(modesByName[value].mode || modesByName.text.mode); env.editor.session.modeName = value; }); bindDropdown("doc", function(name) { doclist.loadDoc(name, function(session) { if (!session) return; session = env.split.setSession(session); updateUIEditorOptions(); env.editor.focus(); }); }); function updateUIEditorOptions() { var editor = env.editor; var session = editor.session; session.setFoldStyle(foldingEl.value); saveOption(docEl, session.name); saveOption(modeEl, session.modeName || "text"); saveOption(wrapModeEl, session.getUseWrapMode() ? session.getWrapLimitRange().min || "free" : "off"); saveOption(selectStyleEl, editor.getSelectionStyle() == "line"); saveOption(themeEl, editor.getTheme()); saveOption(highlightActiveEl, editor.getHighlightActiveLine()); saveOption(showHiddenEl, editor.getShowInvisibles()); saveOption(showGutterEl, editor.renderer.getShowGutter()); saveOption(showPrintMarginEl, editor.renderer.getShowPrintMargin()); saveOption(highlightSelectedWordE, editor.getHighlightSelectedWord()); saveOption(showHScrollEl, editor.renderer.getHScrollBarAlwaysVisible()); saveOption(animateScrollEl, editor.getAnimatedScroll()); saveOption(softTabEl, session.getUseSoftTabs()); saveOption(behavioursEl, editor.getBehavioursEnabled()); } event.addListener(themeEl, "mouseover", function(e){ this.desiredValue = e.target.value; if (!this.$timer) this.$timer = setTimeout(this.updateTheme); }); event.addListener(themeEl, "mouseout", function(e){ this.desiredValue = null; if (!this.$timer) this.$timer = setTimeout(this.updateTheme, 20); }); themeEl.updateTheme = function(){ env.split.setTheme(themeEl.desiredValue || themeEl.selectedValue); themeEl.$timer = null; }; bindDropdown("theme", function(value) { if (!value) return; env.editor.setTheme(value); themeEl.selectedValue = value; }); bindDropdown("keybinding", function(value) { env.editor.setKeyboardHandler(keybindings[value]); }); bindDropdown("fontsize", function(value) { env.split.setFontSize(value); }); bindDropdown("folding", function(value) { env.editor.session.setFoldStyle(value); env.editor.setShowFoldWidgets(value !== "manual"); }); bindDropdown("soft_wrap", function(value) { var session = env.editor.session; var renderer = env.editor.renderer; switch (value) { case "off": session.setUseWrapMode(false); renderer.setPrintMarginColumn(80); break; case "free": session.setUseWrapMode(true); session.setWrapLimitRange(null, null); renderer.setPrintMarginColumn(80); break; default: session.setUseWrapMode(true); var col = parseInt(value, 10); session.setWrapLimitRange(col, col); renderer.setPrintMarginColumn(col); } }); bindCheckbox("select_style", function(checked) { env.editor.setSelectionStyle(checked ? "line" : "text"); }); bindCheckbox("highlight_active", function(checked) { env.editor.setHighlightActiveLine(checked); }); bindCheckbox("show_hidden", function(checked) { env.editor.setShowInvisibles(checked); }); bindCheckbox("display_indent_guides", function(checked) { env.editor.setDisplayIndentGuides(checked); }); bindCheckbox("show_gutter", function(checked) { env.editor.renderer.setShowGutter(checked); }); bindCheckbox("show_print_margin", function(checked) { env.editor.renderer.setShowPrintMargin(checked); }); bindCheckbox("highlight_selected_word", function(checked) { env.editor.setHighlightSelectedWord(checked); }); bindCheckbox("show_hscroll", function(checked) { env.editor.renderer.setHScrollBarAlwaysVisible(checked); }); bindCheckbox("animate_scroll", function(checked) { env.editor.setAnimatedScroll(checked); }); bindCheckbox("soft_tab", function(checked) { env.editor.session.setUseSoftTabs(checked); }); bindCheckbox("enable_behaviours", function(checked) { env.editor.setBehavioursEnabled(checked); }); bindCheckbox("fade_fold_widgets", function(checked) { env.editor.setFadeFoldWidgets(checked); }); var secondSession = null; bindDropdown("split", function(value) { var sp = env.split; if (value == "none") { if (sp.getSplits() == 2) { secondSession = sp.getEditor(1).session; } sp.setSplits(1); } else { var newEditor = (sp.getSplits() == 1); if (value == "below") { sp.setOrientation(sp.BELOW); } else { sp.setOrientation(sp.BESIDE); } sp.setSplits(2); if (newEditor) { var session = secondSession || sp.getEditor(0).session; var newSession = sp.setSession(session, 1); newSession.name = session.name; } } }); bindCheckbox("highlight_token", function(checked) { var editor = env.editor; if (editor.tokenTooltip && !checked) { editor.tokenTooltip.destroy(); delete editor.tokenTooltip; } else if (checked) { editor.tokenTooltip = new TokenTooltip(editor); } }); /************** dragover ***************************/ event.addListener(container, "dragover", function(e) { return event.preventDefault(e); }); event.addListener(container, "drop", function(e) { var file; try { file = e.dataTransfer.files[0]; if (window.FileReader) { var reader = new FileReader(); reader.onload = function() { var mode = getModeFromPath(file.name); env.editor.session.doc.setValue(reader.result); modeEl.value = mode.name; env.editor.session.setMode(mode.mode); env.editor.session.modeName = mode.name; }; reader.readAsText(file); } return event.preventDefault(e); } catch(err) { return event.stopEvent(e); } }); var StatusBar = require("./statusbar").StatusBar; new StatusBar(env.editor, cmdLine.container); });