Bug 1157236 - In-content dialogs: Port bug 1043612, bug 1148923 and bug 1141031 to TB. r=mkmelin
This commit is contained in:
Родитель
03ab024449
Коммит
0477f5cf9e
|
@ -19,6 +19,7 @@ let gSubDialog = {
|
|||
|
||||
// Store the original instantApply pref for restoring after closing the dialog
|
||||
_instantApplyOrig: Services.prefs.getBoolPref("browser.preferences.instantApply"),
|
||||
_resizeObserver: null,
|
||||
|
||||
init: function() {
|
||||
this._frame = document.getElementById("dialogFrame");
|
||||
|
@ -180,44 +181,100 @@ let gSubDialog = {
|
|||
parseFloat(getComputedStyle(groupBoxTitle).borderBottomWidth);
|
||||
|
||||
let groupBoxBody = document.getAnonymousElementByAttribute(this._box, "class", "groupbox-body");
|
||||
// These are deduced from styles which we don't change, so it's safe to get them now:
|
||||
let boxVerticalPadding = 2 * parseFloat(getComputedStyle(groupBoxBody).paddingTop);
|
||||
let boxHorizontalPadding = 2 * parseFloat(getComputedStyle(groupBoxBody).paddingLeft);
|
||||
let frameWidth = docEl.style.width || docEl.scrollWidth + "px";
|
||||
let frameHeight = docEl.style.height || docEl.scrollHeight + "px";
|
||||
let boxVerticalBorder = 2 * parseFloat(getComputedStyle(this._box).borderTopWidth);
|
||||
let boxHorizontalBorder = 2 * parseFloat(getComputedStyle(this._box).borderLeftWidth);
|
||||
let boxVerticalBorder = 2 * parseFloat(getComputedStyle(this._box).borderTopWidth);
|
||||
|
||||
let frameRect = this._frame.getBoundingClientRect();
|
||||
// The difference between the frame and box shouldn't change, either:
|
||||
let boxRect = this._box.getBoundingClientRect();
|
||||
let frameRect = this._frame.getBoundingClientRect();
|
||||
let frameSizeDifference = (frameRect.top - boxRect.top) + (boxRect.bottom - frameRect.bottom);
|
||||
|
||||
// Then determine and set a bunch of width stuff:
|
||||
let frameMinWidth = docEl.style.width || docEl.scrollWidth + "px";
|
||||
let frameWidth = docEl.getAttribute("width") ? docEl.getAttribute("width") + "px" :
|
||||
frameMinWidth;
|
||||
this._frame.style.width = frameWidth;
|
||||
this._box.style.minWidth = "calc(" +
|
||||
(boxHorizontalBorder + boxHorizontalPadding) +
|
||||
"px + " + frameMinWidth + ")";
|
||||
|
||||
// Now do the same but for the height. We need to do this afterwards because otherwise
|
||||
// XUL assumes we'll optimize for height and gives us "wrong" values which then are no
|
||||
// longer correct after we set the width:
|
||||
let frameMinHeight = docEl.style.height || docEl.scrollHeight + "px";
|
||||
let frameHeight = docEl.getAttribute("height") ? docEl.getAttribute("height") + "px" :
|
||||
frameMinHeight;
|
||||
|
||||
// Now check if the frame height we calculated is possible at this window size,
|
||||
// accounting for titlebar, padding/border and some spacing.
|
||||
let maxHeight = window.innerHeight - frameSizeDifference - 30;
|
||||
if (frameHeight > maxHeight) {
|
||||
// If not, we should probably let the dialog scroll:
|
||||
frameHeight = maxHeight;
|
||||
// Do this with a frame height in pixels...
|
||||
let comparisonFrameHeight;
|
||||
if (frameHeight.endsWith("em")) {
|
||||
let fontSize = parseFloat(getComputedStyle(this._frame).fontSize);
|
||||
comparisonFrameHeight = parseFloat(frameHeight, 10) * fontSize;
|
||||
} else if (frameHeight.endsWith("px")) {
|
||||
comparisonFrameHeight = parseFloat(frameHeight, 10);
|
||||
} else {
|
||||
Cu.reportError("This dialog (" + this._frame.contentWindow.location.href + ") " +
|
||||
"set a height in non-px-non-em units ('" + frameHeight + "'), " +
|
||||
"which is likely to lead to bad sizing in in-content preferences. " +
|
||||
"Please consider changing this.");
|
||||
comparisonFrameHeight = parseFloat(frameHeight);
|
||||
}
|
||||
|
||||
if (comparisonFrameHeight > maxHeight) {
|
||||
// If the height is bigger than that of the window, we should let the contents scroll:
|
||||
frameHeight = maxHeight + "px";
|
||||
frameMinHeight = maxHeight + "px";
|
||||
let containers = this._frame.contentDocument.querySelectorAll('.largeDialogContainer');
|
||||
for (let container of containers) {
|
||||
container.classList.add("doScroll");
|
||||
}
|
||||
}
|
||||
|
||||
this._frame.style.width = frameWidth;
|
||||
this._frame.style.height = frameHeight;
|
||||
this._box.style.minHeight = "calc(" +
|
||||
(boxVerticalBorder + groupBoxTitleHeight + boxVerticalPadding) +
|
||||
"px + " + frameHeight + ")";
|
||||
this._box.style.minWidth = "calc(" +
|
||||
(boxHorizontalBorder + boxHorizontalPadding) +
|
||||
"px + " + frameWidth + ")";
|
||||
"px + " + frameMinHeight + ")";
|
||||
|
||||
this._overlay.style.visibility = "visible";
|
||||
this._overlay.style.opacity = ""; // XXX: focus hack continued from _onContentLoaded
|
||||
|
||||
this._resizeObserver = new MutationObserver(this._onResize);
|
||||
this._resizeObserver.observe(this._box, {attributes: true});
|
||||
|
||||
this._trapFocus();
|
||||
},
|
||||
|
||||
_onResize: function(mutations) {
|
||||
let frame = gSubDialog._frame;
|
||||
// The width and height styles are needed for the initial
|
||||
// layout of the frame, but afterward they need to be removed
|
||||
// or their presence will restrict the contents of the <browser>
|
||||
// from resizing to a smaller size.
|
||||
frame.style.removeProperty("width");
|
||||
frame.style.removeProperty("height");
|
||||
|
||||
let docEl = frame.contentDocument.documentElement;
|
||||
let persistedAttributes = docEl.getAttribute("persist");
|
||||
if (!persistedAttributes.contains("width") &&
|
||||
!persistedAttributes.contains("height")) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (let mutation of mutations) {
|
||||
if (mutation.attributeName == "width") {
|
||||
docEl.setAttribute("width", docEl.scrollWidth);
|
||||
} else if (mutation.attributeName == "height") {
|
||||
docEl.setAttribute("height", docEl.scrollHeight);
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
_onDialogClosing: function(aEvent) {
|
||||
this._frame.contentWindow.removeEventListener("dialogclosing", this);
|
||||
this._closingEvent = aEvent;
|
||||
|
@ -302,6 +359,10 @@ let gSubDialog = {
|
|||
this._frame.removeEventListener("load", this);
|
||||
this._frame.contentWindow.removeEventListener("dialogclosing", this);
|
||||
window.removeEventListener("keydown", this, true);
|
||||
if (this._resizeObserver) {
|
||||
this._resizeObserver.disconnect();
|
||||
this._resizeObserver = null;
|
||||
}
|
||||
this._untrapFocus();
|
||||
},
|
||||
|
||||
|
|
|
@ -228,6 +228,17 @@ tabs {
|
|||
-moz-margin-end: 4px !important;
|
||||
}
|
||||
|
||||
/**
|
||||
* Font dialog menulist fixes
|
||||
*/
|
||||
|
||||
#defaultFontType,
|
||||
#serif,
|
||||
#sans-serif,
|
||||
#monospace {
|
||||
min-width: 30ch;
|
||||
}
|
||||
|
||||
/**
|
||||
* Dialog
|
||||
*/
|
||||
|
|
Загрузка…
Ссылка в новой задаче