[Laszlo-checkins] r14405 - openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml
max@openlaszlo.org
max at openlaszlo.org
Wed Jul 29 15:38:20 PDT 2009
Author: max
Date: 2009-07-29 15:38:19 -0700 (Wed, 29 Jul 2009)
New Revision: 14405
Modified:
openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzInputTextSprite.js
openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzMouseKernel.js
openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzSprite.js
Log:
Change 20090727-maxcarlson-U by maxcarlson at Bank.local on 2009-07-27 16:21:22 PDT
in /Users/maxcarlson/openlaszlo/trunk-clean
for http://svn.openlaszlo.org/openlaszlo/trunk
Summary: UPDATED AGAIN AGAIN: Don't re-parent input text to click tree
Bugs Fixed: LPP-5447 DHTML: inputtext and clickable
Technical Reviewer: ptw (pending)
QA Reviewer: a.bargull at intensis.de (pending)
Details:
This is based on Tucker's change (http://svn.openlaszlo.org/openlaszlo/patches/20090722-ptw-k.tar). I turned off the dom_breaks_focus quirk for firefox, cleaned up LzMouseKernel to not attempt to re-focus inputtexts when showing the click tree again. I had to resort to the istextsprite hack - ! this instanceof LzTextSprite wasn't working - not sure why :(. Finally, I test the target of global onmousemove events, and if it's not an inputtext and one's showing, I hide it so mouse events work.
The rest of this is ptw's original change note:
This is just a first pass. It doesn't reparent the input text
sprite into the click tree, and it turns off the click tree when
you mouse over in input element. The test case works in Safari,
and Firefox. I have not tested IE.
LzSprite: Correct fencepost error in __isMouseOver.
LzInputTextSprite: Add documentation from Max. Fix init clauses
that were causing the schema-generator to warn. Remove
reparenting code, replace with hiding/showing the click tree. Now
we can just turn the whole click tree on and off, since we are not
reparenting, which should be much more efficient. Only re-enable
click tree when we _actually_ leave the bounding box of the input
element.
Tests:
Test case from LPP-8334. Also see lpp-5447.lzx attached to the bug and
Modified: openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzInputTextSprite.js
===================================================================
--- openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzInputTextSprite.js 2009-07-29 18:29:44 UTC (rev 14404)
+++ openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzInputTextSprite.js 2009-07-29 22:38:19 UTC (rev 14405)
@@ -38,11 +38,36 @@
LzInputTextSprite.prototype._dbg_typename = 'LzInputTextSprite';
}
+/**
+ * __lastshown tracks the last inputtext to be shown by __show(), and
+ * is used to hide the currently showing inputtext.
+ *
+ * @access private
+ */
LzInputTextSprite.prototype.__lastshown = null;
+/**
+ * __focusedSprite tracks the last inputtext to be focused, and is
+ * used to work around bugs in firefox's focus management and prevent
+ * spurious/extra onfocus/blur events from being sent.
+ *
+ * @access private
+ */
LzInputTextSprite.prototype.__focusedSprite = null;
+/**
+ * __lastfocus holds a reference to the last inputtext to be selected
+ * - by select() or setSelection(). It's used as a callback (see
+ * setTimout()) to work around a bug in IE where a field can't be
+ * selected immediately after it's focused.
+ *
+ * @access private
+ */
LzInputTextSprite.prototype.__lastfocus = null;
-LzInputTextSprite.prototype._cancelfocus = LzInputTextSprite.prototype._cancelblur = false;
+/** @access private */
+LzInputTextSprite.prototype._cancelfocus = false;
+/** @access private */
+LzInputTextSprite.prototype._cancelblur = false;
+/** @access private */
LzInputTextSprite.prototype.____crregexp = new RegExp('\\r\\n', 'g');
LzInputTextSprite.prototype.__createInputText = function(t) {
@@ -182,18 +207,18 @@
// called from the scope of __LZinputclickdiv
LzInputTextSprite.prototype.__handlemouse = function(e) {
- if (this.owner.selectable != true) return;
- LzInputTextSprite.prototype.__setglobalclickable(false);
- if (this.owner.__fix_inputtext_with_parent_resource) {
+ var sprite = this.owner;
+ if (sprite.selectable != true) return;
+ if (sprite.__fix_inputtext_with_parent_resource) {
//if (!e) e = window.event;
//Debug.warn(e.type);
if (! this.__shown) {
- this.owner.setClickable(true);
- //this.owner.__show();
- this.owner.select();
+ sprite.setClickable(true);
+ //sprite.__show();
+ sprite.select();
}
} else {
- this.owner.__show();
+ sprite.__show();
}
}
@@ -232,8 +257,6 @@
this.__hideIfNotFocused();
LzInputTextSprite.prototype.__lastshown = this;
this.__shown = true;
- // bring to front of click divs
- this.__LzInputDiv = this.__LZdiv.removeChild(this.__LzInputDiv);
if (this.quirks['inputtext_parents_cannot_contain_clip']) {
var sprites = this.__findParents('clip');
@@ -252,12 +275,8 @@
}
}
}
- if (this.quirks.fix_ie_clickable) {
- this.__LZclickcontainerdiv.appendChild(this.__LzInputDiv);
- this.__setglobalclickable(false);
- } else {
- this.__LZinputclickdiv.appendChild(this.__LzInputDiv);
- }
+ // Hide the clickdivs, so we can interact with the mouse
+ LzMouseKernel.setGlobalClickable(false);
//Debug.warn('__show', this.owner);
// turn on text selection in IE
// can't use lz.embed.attachEventHandler because we need to cancel events selectively
@@ -277,14 +296,14 @@
// track mouse position for inputtext when global clickable is false
if (lzinppr.__globalclickable == false && lzinppr.__focusedSprite && target) {
if (target.owner != lzinppr.__focusedSprite) {
- lzinppr.__setglobalclickable(true);
+ LzMouseKernel.setGlobalClickable(true);
} else {
- lzinppr.__setglobalclickable(false);
+ LzMouseKernel.setGlobalClickable(false);
}
}
return;
} else if (eventname != null && lzinppr.__globalclickable == true) {
- lzinppr.__setglobalclickable(false);
+ LzMouseKernel.setGlobalClickable(false);
}
if (quirks.textgrabsinputtextfocus) {
var s = window.event;
@@ -302,14 +321,6 @@
}
}
-LzInputTextSprite.prototype.__setglobalclickable = function(c) {
- if (! LzSprite.prototype.quirks.fix_ie_clickable) return;
- if (c != LzInputTextSprite.prototype.__globalclickable) {
- LzInputTextSprite.prototype.__globalclickable = c;
- LzInputTextSprite.prototype.__setCSSClassProperty('.lzclickdiv', 'display', c ? '' : 'none');
- }
-}
-
LzInputTextSprite.prototype.__hide = function(ignore) {
if (this.__shown != true || this.disabled == true) return;
if (LzInputTextSprite.prototype.__lastshown == this) {
@@ -327,26 +338,9 @@
this._shownclippedsprites = null;
}
}
- // send to __LZdiv
- if (this.quirks.fix_ie_clickable) {
- // [TODO ptw 1-18-2007] rather than twiddling the style or style sheet you could just have a rule
- // like (assuming you used multiple classes): .lzdiv + .lzclick { display: none; }
- // and make the click be displayed or not by whether it is before or after the (input) div?
- // [max 1-18-2007] IE requires different nesting rules for inputtext. Also, if there are _any_
- // clickable divs behind the inputtext they'll grab clicks. This is the reason I temporarily
- // hide all clickable divs when the inputtext is selected - and the reason the inputtext can't
- // be a child of the clickable view.
-
- this.__setglobalclickable(true);
- if (this.__LzInputDiv.parentNode == this.__LZclickcontainerdiv) {
- this.__LzInputDiv = this.__LZclickcontainerdiv.removeChild(this.__LzInputDiv);
- }
- } else {
- if (this.__LzInputDiv.parentNode == this.__LZinputclickdiv) {
- this.__LzInputDiv = this.__LZinputclickdiv.removeChild(this.__LzInputDiv);
- }
- }
- this.__LZdiv.appendChild(this.__LzInputDiv);
+ // Put the clickdivs back in place, we are done interacting with
+ // the mouse
+ LzMouseKernel.setGlobalClickable(true);
//Debug.warn('__hide', this.owner);
if (this.__fix_inputtext_with_parent_resource) {
//Debug.write('forcing blur', this.__LzInputDiv);
@@ -354,8 +348,8 @@
this.setClickable(false);
//good.sprite.gotFocus();
/* none of these seem to allow mousedown events, so we show onmouseenter
- this.__setglobalclickable(false);
- this.__setglobalclickable(true);
+ LzMouseKernel.setGlobalClickable(false);
+ LzMouseKernel.setGlobalClickable(true);
this.__dummyinputtext.style.display = '';
this.__dummyinputtext.focus();
this.__dummyinputtext.blur();
@@ -597,7 +591,7 @@
var nextFocus = null;
if (eventname == 'onfocus' || eventname == 'onmousedown') {
if (eventname == 'onfocus') {
- LzInputTextSprite.prototype.__setglobalclickable(false);
+ LzMouseKernel.setGlobalClickable(false);
}
LzInputTextSprite.prototype.__focusedSprite = sprite;
sprite.__show();
@@ -636,7 +630,16 @@
return;
}
} else if (eventname == 'onmouseout') {
- sprite.__setglobalclickable(true);
+ // Only re-enable clickable if the mouse actually leaves our
+ // bounding box (i.e., not just because it enters another sprite
+ // that overlaps us)
+// if ($debug) {
+// var m = sprite.getMouse(null);
+// Debug.info("%w: 0 <= %d < %d; 0 <= %d < %d", sprite, m.x, sprite.width, m.y, sprite.height);
+// }
+ if (! sprite.__isMouseOver()) {
+ sprite.__hide();
+ }
} else if (eventname == 'onmousemove') {
if (quirks.autoscroll_textarea && sprite.dragging) {
// Simulate mouse scrolling naer the top and bottom (LPP-8277)
Modified: openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzMouseKernel.js
===================================================================
--- openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzMouseKernel.js 2009-07-29 18:29:44 UTC (rev 14404)
+++ openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzMouseKernel.js 2009-07-29 22:38:19 UTC (rev 14405)
@@ -43,6 +43,14 @@
if (eventname == 'onmousemove') {
LzMouseKernel.__sendMouseMove(e);
+ // hide any active inputtexts to allow clickable to work - see LPP-5447...
+ if (lzinputproto && lzinputproto.__lastshown != null) {
+ if (! (targ.owner instanceof LzInputTextSprite)) {
+ if (! lzinputproto.__lastshown.__isMouseOver()) {
+ lzinputproto.__lastshown.__hide();
+ }
+ }
+ }
} else if (eventname == 'oncontextmenu' || (e.button == 2 && eventname == 'onmouseup') ) {
if (targ) {
// update mouse position, required for Safari
@@ -197,29 +205,8 @@
}
,__cachedSelection: null
,setGlobalClickable: function (isclickable){
- //Debug.error('setGlobalClickable', isclickable, LzInputTextSprite.prototype.__lastfocus, LzInputTextSprite.prototype.__focusedSprite, LzInputTextSprite.prototype.__lastshown);
- if (! isclickable) {
- // reset any inputtexts that are showing so they don't disappear - see LPP-7190
- var lzinputproto = LzInputTextSprite.prototype;
- var lastshown = lzinputproto.__lastshown;
- if (lastshown) {
- LzMouseKernel.__cachedSelection = {s: lastshown, st: lastshown.getSelectionPosition(), sz: lastshown.getSelectionSize()};
- lastshown.__hide();
- lzinputproto.__lastshown = null;
- }
- var focused = lzinputproto.__focusedSprite;
- if (focused) {
- focused.deselect();
- lzinputproto.__focusedSprite = null;
- }
- var lastfocus = lzinputproto.__lastfocus;
- if (lastfocus) {
- lastfocus.deselect();
- lzinputproto.__lastfocus = null;
- }
- }
var el = document.getElementById('lzcanvasclickdiv');
- el.style.display = isclickable ? 'block' : 'none';
+ el.style.display = isclickable ? '' : 'none';
}
,__sendMouseMove: function(e, offsetx, offsety) {
// see http://www.quirksmode.org/js/events_properties.html#position
Modified: openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzSprite.js
===================================================================
--- openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzSprite.js 2009-07-29 18:29:44 UTC (rev 14404)
+++ openlaszlo/trunk/WEB-INF/lps/lfc/kernel/dhtml/LzSprite.js 2009-07-29 22:38:19 UTC (rev 14405)
@@ -164,7 +164,7 @@
}
if (mousein) {
if (quirks.fix_ie_clickable) {
- LzInputTextSprite.prototype.__setglobalclickable(true);
+ LzMouseKernel.setGlobalClickable(true);
}
if (quirks.focus_on_mouseover) {
if (LzInputTextSprite.prototype.__lastshown == null) {
@@ -736,7 +736,7 @@
} else if (browser.isFirefox) {
// DOM operations on blurring element break focus (LPP-7786)
// https://bugzilla.mozilla.org/show_bug.cgi?id=481468
- quirks['dom_breaks_focus'] = true;
+ //quirks['dom_breaks_focus'] = true;
// anonymous div bug on input-elements (LPP-7796)
// see https://bugzilla.mozilla.org/show_bug.cgi?id=208427
quirks['inputtext_anonymous_div'] = true;
@@ -1359,7 +1359,8 @@
LzSprite.prototype.__isMouseOver = function ( e ){
var p = this.getMouse();
- return p.x >= 0 && p.y >= 0 && p.x <= this.width && p.y <= this.height;
+ // Note pixels are 0-based, so width and height are exclusive limits
+ return p.x >= 0 && p.y >= 0 && p.x < this.width && p.y < this.height;
}
/**
@@ -1405,7 +1406,7 @@
var size = w;
// set size to zero if we don't have either of these
if (this.quirks.size_blank_to_zero) {
- if (this.bgcolor == null && this.source == null && ! this instanceof LzTextSprite) {
+ if (this.bgcolor == null && this.source == null && ! (this instanceof LzTextSprite)) {
this.__sizedtozero = true;
size = '0px';
}
@@ -1448,7 +1449,7 @@
var size = h;
// set size to zero if we don't have either of these
if (this.quirks.size_blank_to_zero) {
- if (this.bgcolor == null && this.source == null && ! this instanceof LzTextSprite) {
+ if (this.bgcolor == null && this.source == null && ! (this instanceof LzTextSprite)) {
this.__sizedtozero = true;
size = '0px';
}
More information about the Laszlo-checkins
mailing list