diff --git a/lib/ace/css/editor.css b/lib/ace/css/editor.css index 5a544076..58d1e7e6 100644 --- a/lib/ace/css/editor.css +++ b/lib/ace/css/editor.css @@ -94,8 +94,8 @@ .ace_editor textarea { position: fixed; z-index: 0; - width: 10px; - height: 30px; + width: 0.5em; + height: 1em; opacity: 0; background: transparent; appearance: none; diff --git a/lib/ace/editor.js b/lib/ace/editor.js index 53295878..1feebf68 100644 --- a/lib/ace/editor.js +++ b/lib/ace/editor.js @@ -80,6 +80,7 @@ var Editor = function(renderer, session) { this.commands = new CommandManager(useragent.isMac ? "mac" : "win", defaultCommands); this.textInput = new TextInput(renderer.getTextAreaContainer(), this); + this.renderer.textarea = this.textInput.getElement(); this.keyBinding = new KeyBinding(this); // TODO detect touch event support @@ -385,11 +386,7 @@ var Editor = function(renderer, session) { this.$cursorChange = function() { this.renderer.updateCursor(); - - // move text input over the cursor - // this is required for iOS and IME - this.renderer.moveTextAreaToCursor(this.textInput.getElement()); - } + }; /** * Editor@onDocumentChange(e) diff --git a/lib/ace/keyboard/textinput.js b/lib/ace/keyboard/textinput.js index 10f12865..fa570e66 100644 --- a/lib/ace/keyboard/textinput.js +++ b/lib/ace/keyboard/textinput.js @@ -49,7 +49,9 @@ var TextInput = function(parentNode, host) { var text = dom.createElement("textarea"); if (useragent.isTouchPad) text.setAttribute("x-palm-disable-auto-cap", true); - + + text.setAttribute("wrap", "off"); + text.style.left = "-10000px"; text.style.position = "fixed"; parentNode.insertBefore(text, parentNode.firstChild); diff --git a/lib/ace/layer/cursor.js b/lib/ace/layer/cursor.js index 1c55d7a8..f43b36b7 100644 --- a/lib/ace/layer/cursor.js +++ b/lib/ace/layer/cursor.js @@ -175,6 +175,9 @@ var Cursor = function(parentEl) { if (overwrite != this.overwrite) this.$setOverite(overwrite); + // cache for textarea and gutter highlight + this.$pixelPos = pixelPos; + this.restartTimer(); }; diff --git a/lib/ace/virtual_renderer.js b/lib/ace/virtual_renderer.js index 0c2c0880..fc477c58 100644 --- a/lib/ace/virtual_renderer.js +++ b/lib/ace/virtual_renderer.js @@ -82,6 +82,9 @@ var VirtualRenderer = function(container, theme) { // TODO: this breaks rendering in Cloud9 with multiple ace instances // // Imports CSS once per DOM document ('ace_editor' serves as an identifier). // dom.importCssString(editorCss, "ace_editor", container.ownerDocument); + + // in IE <= 9 the native cursor always shines through + this.$keepTextAreaAtCursor = !useragent.isIE; dom.addCssClass(container, "ace_editor"); @@ -496,30 +499,22 @@ var VirtualRenderer = function(container, theme) { return this.container; }; - /** - * VirtualRenderer.moveTextAreaToCursor(textarea) -> Void - * - textarea (DOMElement): A text area to work with - * - * Changes the position of `textarea` to where the cursor is pointing. - **/ - this.moveTextAreaToCursor = function(textarea) { - // in IE the native cursor always shines through - // this persists in IE9 - if (useragent.isIE) + // move text input over the cursor + // this is required for iOS and IME + this.$moveTextAreaToCursor = function() { + if (!this.$keepTextAreaAtCursor) return; - if (this.layerConfig.lastRow === 0) + var pos = this.$cursorLayer.$pixelPos; + pos.top -= this.layerConfig.offset; + + if (pos.top < 0 || pos.top > this.layerConfig.height) return; - var pos = this.$cursorLayer.getPixelPosition(); - if (!pos) - return; - - var bounds = this.content.getBoundingClientRect(); - var offset = this.layerConfig.offset; - - textarea.style.left = (bounds.left + pos.left) + "px"; - textarea.style.top = (bounds.top + pos.top - this.scrollTop + offset) + "px"; + pos.left += (this.showGutter ? this.$gutterLayer.gutterWidth : 0) - this.scrollLeft; + var bounds = this.container.getBoundingClientRect(); + this.textarea.style.left = (bounds.left + pos.left) + "px"; + this.textarea.style.top = (bounds.top + pos.top) + "px"; }; /** @@ -640,6 +635,7 @@ var VirtualRenderer = function(container, theme) { this.$markerBack.update(this.layerConfig); this.$markerFront.update(this.layerConfig); this.$cursorLayer.update(this.layerConfig); + this.$moveTextAreaToCursor(); return; } @@ -656,6 +652,7 @@ var VirtualRenderer = function(container, theme) { this.$markerBack.update(this.layerConfig); this.$markerFront.update(this.layerConfig); this.$cursorLayer.update(this.layerConfig); + this.$moveTextAreaToCursor(); return; } @@ -675,8 +672,10 @@ var VirtualRenderer = function(container, theme) { this.$gutterLayer.update(this.layerConfig); } - if (changes & this.CHANGE_CURSOR) + if (changes & this.CHANGE_CURSOR) { this.$cursorLayer.update(this.layerConfig); + this.$moveTextAreaToCursor(); + } if (changes & (this.CHANGE_MARKER | this.CHANGE_MARKER_FRONT)) { this.$markerFront.update(this.layerConfig);