Merge m-c to f-t
|
@ -6,6 +6,10 @@ import imp
|
|||
import os
|
||||
from StringIO import StringIO
|
||||
import shlex
|
||||
import sys
|
||||
|
||||
old_bytecode = sys.dont_write_bytecode
|
||||
sys.dont_write_bytecode = True
|
||||
|
||||
path = os.path.join(os.path.dirname(__file__), 'mach')
|
||||
|
||||
|
@ -15,6 +19,8 @@ if not os.path.exists(path):
|
|||
path = os.path.join(config.topsrcdir, 'mach')
|
||||
mach_module = imp.load_module('_mach', open(path), path, ('', 'r', imp.PY_SOURCE))
|
||||
|
||||
sys.dont_write_bytecode = old_bytecode
|
||||
|
||||
def FlagsForFile(filename):
|
||||
mach = mach_module.get_mach()
|
||||
out = StringIO()
|
||||
|
|
|
@ -855,6 +855,13 @@ getIndexInParentCB(AtkObject* aAtkObj)
|
|||
{
|
||||
// We don't use Accessible::IndexInParent() because we don't include text
|
||||
// leaf nodes as children in ATK.
|
||||
if (ProxyAccessible* proxy = GetProxy(aAtkObj)) {
|
||||
if (ProxyAccessible* parent = proxy->Parent())
|
||||
return parent->IndexOfEmbeddedChild(proxy);
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
AccessibleWrap* accWrap = GetAccessibleWrap(aAtkObj);
|
||||
if (!accWrap) {
|
||||
return -1;
|
||||
|
@ -1053,6 +1060,9 @@ GetInterfacesForProxy(ProxyAccessible* aProxy, uint32_t aInterfaces)
|
|||
if (aInterfaces & Interfaces::IMAGE)
|
||||
interfaces |= MAI_INTERFACE_IMAGE;
|
||||
|
||||
if (aInterfaces & Interfaces::DOCUMENT)
|
||||
interfaces |= MAI_INTERFACE_DOCUMENT;
|
||||
|
||||
return interfaces;
|
||||
}
|
||||
|
||||
|
|
|
@ -16,7 +16,7 @@ static AtkHyperlink*
|
|||
getHyperlinkCB(AtkHyperlinkImpl* aImpl)
|
||||
{
|
||||
AccessibleWrap* accWrap = GetAccessibleWrap(ATK_OBJECT(aImpl));
|
||||
if (!accWrap || !GetProxy(ATK_OBJECT(aImpl)))
|
||||
if (!accWrap && !GetProxy(ATK_OBJECT(aImpl)))
|
||||
return nullptr;
|
||||
|
||||
if (accWrap)
|
||||
|
|
|
@ -39,6 +39,9 @@ InterfacesFor(Accessible* aAcc)
|
|||
if (aAcc->IsTableCell())
|
||||
interfaces |= Interfaces::TABLECELL;
|
||||
|
||||
if (aAcc->IsDoc())
|
||||
interfaces |= Interfaces::DOCUMENT;
|
||||
|
||||
return interfaces;
|
||||
}
|
||||
|
||||
|
@ -1615,6 +1618,22 @@ DocAccessibleChild::RecvTakeFocus(const uint64_t& aID)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
DocAccessibleChild::RecvIndexOfEmbeddedChild(const uint64_t& aID,
|
||||
const uint64_t& aChildID,
|
||||
uint32_t* aChildIdx)
|
||||
{
|
||||
*aChildIdx = 0;
|
||||
|
||||
Accessible* parent = IdToAccessible(aID);
|
||||
Accessible* child = IdToAccessible(aChildID);
|
||||
if (!parent || !child)
|
||||
return true;
|
||||
|
||||
*aChildIdx = parent->GetIndexOfEmbeddedChild(child);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
DocAccessibleChild::RecvChildAtPoint(const uint64_t& aID,
|
||||
const int32_t& aX,
|
||||
|
|
|
@ -393,6 +393,10 @@ public:
|
|||
|
||||
virtual bool RecvTakeFocus(const uint64_t& aID) override;
|
||||
|
||||
virtual bool RecvIndexOfEmbeddedChild(const uint64_t& aID,
|
||||
const uint64_t& aChildID,
|
||||
uint32_t* aChildIdx) override final;
|
||||
|
||||
virtual bool RecvChildAtPoint(const uint64_t& aID,
|
||||
const int32_t& aX,
|
||||
const int32_t& aY,
|
||||
|
|
|
@ -211,6 +211,8 @@ child:
|
|||
prio(high) sync Step(uint64_t aID) returns(double aStep);
|
||||
|
||||
prio(high) sync TakeFocus(uint64_t aID);
|
||||
prio(high) sync IndexOfEmbeddedChild(uint64_t aID, uint64_t aChildID)
|
||||
returns(uint32_t childIdx);
|
||||
prio(high) sync ChildAtPoint(uint64_t aID, int32_t aX, int32_t aY, uint32_t aWhich)
|
||||
returns(uint64_t aChild, bool aOk);
|
||||
prio(high) sync Bounds(uint64_t aID) returns(nsIntRect aRect);
|
||||
|
|
|
@ -903,6 +903,15 @@ ProxyAccessible::TakeFocus()
|
|||
unused << mDoc->SendTakeFocus(mID);
|
||||
}
|
||||
|
||||
int32_t
|
||||
ProxyAccessible::IndexOfEmbeddedChild(const ProxyAccessible* aChild)
|
||||
{
|
||||
uint64_t childID = aChild->mID;
|
||||
uint32_t childIdx;
|
||||
unused << mDoc->SendIndexOfEmbeddedChild(mID, childID, &childIdx);
|
||||
return childIdx;
|
||||
}
|
||||
|
||||
ProxyAccessible*
|
||||
ProxyAccessible::ChildAtPoint(int32_t aX, int32_t aY,
|
||||
Accessible::EWhichChildAtPoint aWhichChild)
|
||||
|
|
|
@ -47,6 +47,7 @@ public:
|
|||
|
||||
// XXX evaluate if this is fast enough.
|
||||
size_t IndexInParent() const { return mParent->mChildren.IndexOf(this); }
|
||||
int32_t IndexOfEmbeddedChild(const ProxyAccessible*);
|
||||
bool MustPruneChildren() const;
|
||||
|
||||
void Shutdown();
|
||||
|
@ -320,6 +321,7 @@ enum Interfaces
|
|||
VALUE = 8,
|
||||
TABLE = 16,
|
||||
TABLECELL = 32,
|
||||
DOCUMENT = 64,
|
||||
};
|
||||
|
||||
}
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="2eda36a4795012a5d1275b77ebb20ac377c8cd26">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
|
|
@ -19,7 +19,7 @@
|
|||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="9a9797062c6001d6346504161c51187a2968466b"/>
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="adb24954bf8068f21705b570450475d183336b2d"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="0627790166dccd8dd370fa7d9f434ed9fc027fb4"/>
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="2eda36a4795012a5d1275b77ebb20ac377c8cd26">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="61e82f99bb8bc78d52b5717e9a2481ec7267fa33">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
|
|
@ -19,7 +19,7 @@
|
|||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="fake-dalvik" path="dalvik" remote="b2g" revision="ca1f327d5acc198bb4be62fa51db2c039032c9ce"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="9a9797062c6001d6346504161c51187a2968466b"/>
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="2eda36a4795012a5d1275b77ebb20ac377c8cd26">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
</project>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="adb24954bf8068f21705b570450475d183336b2d"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="0627790166dccd8dd370fa7d9f434ed9fc027fb4"/>
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
{
|
||||
"git": {
|
||||
"git_revision": "3692ad2cf3a047cc66f58f655a56b6ec559ef253",
|
||||
"git_revision": "5b2a150f6f5d29bddfaac13fcbbf099376f2f275",
|
||||
"remote": "https://git.mozilla.org/releases/gaia.git",
|
||||
"branch": ""
|
||||
},
|
||||
"revision": "5cf33f632627cefff6e9809144064600fed4c088",
|
||||
"revision": "75e6c18c2cdd05073434a8d5e749c72a063a0521",
|
||||
"repo_path": "integration/gaia-central"
|
||||
}
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="5ef30994f4778b4052e58a4383dbe7890048c87e"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="adb24954bf8068f21705b570450475d183336b2d"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="0627790166dccd8dd370fa7d9f434ed9fc027fb4"/>
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="61e82f99bb8bc78d52b5717e9a2481ec7267fa33">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3692ad2cf3a047cc66f58f655a56b6ec559ef253"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="5b2a150f6f5d29bddfaac13fcbbf099376f2f275"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="d3868ff4bb3a4b81382795e2784258c210fe6cb8"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="1b3591a50ed352fc6ddb77462b7b35d0bfa555a3"/>
|
||||
|
|
|
@ -3029,6 +3029,21 @@
|
|||
</certItem>
|
||||
<certItem issuerName="MIGQMQswCQYDVQQGEwJHQjEbMBkGA1UECBMSR3JlYXRlciBNYW5jaGVzdGVyMRAwDgYDVQQHEwdTYWxmb3JkMRowGAYDVQQKExFDT01PRE8gQ0EgTGltaXRlZDE2MDQGA1UEAxMtQ09NT0RPIFJTQSBEb21haW4gVmFsaWRhdGlvbiBTZWN1cmUgU2VydmVyIENB">
|
||||
<serialNumber>UoRGnb96CUDTxIqVry6LBg==</serialNumber>
|
||||
</certItem>
|
||||
<certItem issuerName="MHExCzAJBgNVBAYTAkRFMRwwGgYDVQQKExNEZXV0c2NoZSBUZWxla29tIEFHMR8wHQYDVQQLExZULVRlbGVTZWMgVHJ1c3QgQ2VudGVyMSMwIQYDVQQDExpEZXV0c2NoZSBUZWxla29tIFJvb3QgQ0EgMg==">
|
||||
<serialNumber>ARQ=</serialNumber>
|
||||
</certItem>
|
||||
<certItem issuerName="MGcxCzAJBgNVBAYTAkRFMRMwEQYDVQQKEwpGcmF1bmhvZmVyMSEwHwYDVQQLExhGcmF1bmhvZmVyIENvcnBvcmF0ZSBQS0kxIDAeBgNVBAMTF0ZyYXVuaG9mZXIgUm9vdCBDQSAyMDA3">
|
||||
<serialNumber>YR3YYQAAAAAABA==</serialNumber>
|
||||
</certItem>
|
||||
<certItem issuerName="MGExCzAJBgNVBAYTAk5MMR4wHAYDVQQKDBVTdGFhdCBkZXIgTmVkZXJsYW5kZW4xMjAwBgNVBAMMKVN0YWF0IGRlciBOZWRlcmxhbmRlbiBPcmdhbmlzYXRpZSBDQSAtIEcy">
|
||||
<serialNumber>ATE0vw==</serialNumber>
|
||||
</certItem>
|
||||
<certItem issuerName="MFkxCzAJBgNVBAYTAk5MMR4wHAYDVQQKExVTdGFhdCBkZXIgTmVkZXJsYW5kZW4xKjAoBgNVBAMTIVN0YWF0IGRlciBOZWRlcmxhbmRlbiBPdmVyaGVpZCBDQQ">
|
||||
<serialNumber>ATFpsA==</serialNumber>
|
||||
</certItem>
|
||||
<certItem issuerName="MFkxCzAJBgNVBAYTAk5MMR4wHAYDVQQKExVTdGFhdCBkZXIgTmVkZXJsYW5kZW4xKjAoBgNVBAMTIVN0YWF0IGRlciBOZWRlcmxhbmRlbiBPdmVyaGVpZCBDQQ">
|
||||
<serialNumber>ATFEdg==</serialNumber>
|
||||
</certItem>
|
||||
</certItems>
|
||||
|
||||
|
|
|
@ -1567,6 +1567,21 @@ let BookmarkingUI = {
|
|||
|
||||
updatePocketItemVisibility: function BUI_updatePocketItemVisibility(prefix) {
|
||||
let hidden = !CustomizableUI.getPlacementOfWidget("pocket-button");
|
||||
if (!hidden) {
|
||||
let locale = Cc["@mozilla.org/chrome/chrome-registry;1"].
|
||||
getService(Ci.nsIXULChromeRegistry).
|
||||
getSelectedLocale("browser");
|
||||
let url = "chrome://browser/content/browser-pocket-" + locale + ".properties";
|
||||
let bundle = Services.strings.createBundle(url);
|
||||
let item = document.getElementById(prefix + "pocket");
|
||||
try {
|
||||
item.setAttribute("label", bundle.GetStringFromName("pocketMenuitem.label"));
|
||||
} catch (err) {
|
||||
// GetStringFromName throws when the bundle doesn't exist. In that
|
||||
// case, the item will retain the browser-pocket.dtd en-US string that
|
||||
// it has in the markup.
|
||||
}
|
||||
}
|
||||
document.getElementById(prefix + "pocket").hidden = hidden;
|
||||
document.getElementById(prefix + "pocketSeparator").hidden = hidden;
|
||||
},
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||
# License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
# This is a temporary file, later versions of Firefox will use
|
||||
# browser.properties in the usual L10N location.
|
||||
|
||||
pocket-button.label = Pocket
|
||||
pocket-button.tooltiptext = Bei Pocket speichern
|
||||
|
||||
# From browser-pocket.dtd
|
||||
saveToPocketCmd.label = Seite bei Pocket speichern
|
||||
saveToPocketCmd.accesskey = k
|
||||
pocketMenuitem.label = Pocket-Liste anzeigen
|
|
@ -0,0 +1,14 @@
|
|||
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||
# License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
# This is a temporary file, later versions of Firefox will use
|
||||
# browser.properties in the usual L10N location.
|
||||
|
||||
pocket-button.label = Pocket
|
||||
pocket-button.tooltiptext = Guardar en Pocket
|
||||
|
||||
# From browser-pocket.dtd
|
||||
saveToPocketCmd.label = Guardar página en Pocket
|
||||
saveToPocketCmd.accesskey = k
|
||||
pocketMenuitem.label = Ver lista de Pocket
|
|
@ -0,0 +1,14 @@
|
|||
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||
# License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
# This is a temporary file, later versions of Firefox will use
|
||||
# browser.properties in the usual L10N location.
|
||||
|
||||
pocket-button.label = Pocket
|
||||
pocket-button.tooltiptext = Pocket に保存
|
||||
|
||||
# From browser-pocket.dtd
|
||||
saveToPocketCmd.label = Pocket にページを保存
|
||||
saveToPocketCmd.accesskey = k
|
||||
pocketMenuitem.label = Pocket のマイリストを表示
|
|
@ -0,0 +1,14 @@
|
|||
# This Source Code Form is subject to the terms of the Mozilla Public
|
||||
# License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
# This is a temporary file, later versions of Firefox will use
|
||||
# browser.properties in the usual L10N location.
|
||||
|
||||
pocket-button.label = Pocket
|
||||
pocket-button.tooltiptext = Сохранить в Pocket
|
||||
|
||||
# From browser-pocket.dtd
|
||||
saveToPocketCmd.label = Сохранить страницу в Pocket
|
||||
saveToPocketCmd.accesskey = х
|
||||
pocketMenuitem.label = Показать список Pocket
|
|
@ -2,8 +2,8 @@
|
|||
# License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
|
||||
# This is a temporary file and not meant for localization; later versions
|
||||
# of Firefox include these strings in browser.properties
|
||||
# This is a temporary file, later versions of Firefox will use
|
||||
# browser.properties in the usual L10N location.
|
||||
|
||||
pocket-button.label = Pocket
|
||||
pocket-button.tooltiptext = Save to Pocket
|
||||
|
|
|
@ -186,6 +186,22 @@ nsContextMenu.prototype = {
|
|||
CustomizableUI.getPlacementOfWidget("pocket-button") &&
|
||||
(uri.schemeIs("http") || uri.schemeIs("https") ||
|
||||
(uri.schemeIs("about") && ReaderMode.getOriginalUrl(uri.spec)));
|
||||
if (canPocket) {
|
||||
let locale = Cc["@mozilla.org/chrome/chrome-registry;1"].
|
||||
getService(Ci.nsIXULChromeRegistry).
|
||||
getSelectedLocale("browser");
|
||||
let url = "chrome://browser/content/browser-pocket-" + locale + ".properties";
|
||||
let bundle = Services.strings.createBundle(url);
|
||||
let item = document.getElementById("context-pocket");
|
||||
try {
|
||||
item.setAttribute("label", bundle.GetStringFromName("saveToPocketCmd.label"));
|
||||
item.setAttribute("accesskey", bundle.GetStringFromName("saveToPocketCmd.accesskey"));
|
||||
} catch (err) {
|
||||
// GetStringFromName throws when the bundle doesn't exist. In that
|
||||
// case, the item will retain the browser-pocket.dtd en-US string that
|
||||
// it has in the markup.
|
||||
}
|
||||
}
|
||||
}
|
||||
this.showItem("context-pocket", canPocket && window.pktApi && window.pktApi.isUserLoggedIn());
|
||||
},
|
||||
|
|
|
@ -23,9 +23,6 @@ const EXPECTED_REFLOWS = [
|
|||
// Sometimes sessionstore collects data during this test, which causes a sync reflow
|
||||
// (https://bugzilla.mozilla.org/show_bug.cgi?id=892154 will fix this)
|
||||
"ssi_getWindowDimension@resource:///modules/sessionstore/SessionStore.jsm",
|
||||
|
||||
// We may get a resize event, see bug 1149555.
|
||||
"PreviewController.prototype.wasResizedSinceLastPreview@resource:///modules/WindowsPreviewPerTab.jsm"
|
||||
];
|
||||
|
||||
if (Services.appinfo.OS == "WINNT" || Services.appinfo.OS == "Darwin") {
|
||||
|
|
|
@ -72,8 +72,8 @@ var tests = {
|
|||
[chatWidth*2+popupWidth+2, 2, "big enough to fit 2 - nub remains visible as first is still hidden"],
|
||||
[chatWidth*3+popupWidth-2, 2, "one smaller than the size necessary to display all three - first still hidden"],
|
||||
[chatWidth*3+popupWidth+2, 3, "big enough to fit all - all exposed (which removes the nub)"],
|
||||
[chatWidth*3+4, 3, "now the nub is hidden we can resize back down to chatWidth*3 before overflow."],
|
||||
[chatWidth*3-4, 2, "4 pixels less and the first is again collapsed (and the nub re-appears)"],
|
||||
[chatWidth*3+2, 3, "now the nub is hidden we can resize back down to chatWidth*3 before overflow."],
|
||||
[chatWidth*3-2, 2, "2 pixels less and the first is again collapsed (and the nub re-appears)"],
|
||||
[chatWidth*2+popupWidth+2, 2, "back down to just big enough to fit 2"],
|
||||
[chatWidth*2+popupWidth-2, 1, "back down to just not enough to fit 2"],
|
||||
[chatWidth*3+popupWidth+2, 3, "now a large jump to make all 3 visible (ie, affects 2)"],
|
||||
|
|
|
@ -77,6 +77,10 @@ browser.jar:
|
|||
* content/browser/browser.xul (content/browser.xul)
|
||||
content/browser/browser-pocket.properties (content/browser-pocket.properties)
|
||||
content/browser/browser-pocket.dtd (content/browser-pocket.dtd)
|
||||
content/browser/browser-pocket-de.properties (content/browser-pocket-de.properties)
|
||||
content/browser/browser-pocket-es-ES.properties (content/browser-pocket-es-ES.properties)
|
||||
content/browser/browser-pocket-ja.properties (content/browser-pocket-ja.properties)
|
||||
content/browser/browser-pocket-ru.properties (content/browser-pocket-ru.properties)
|
||||
* content/browser/browser-tabPreviews.xml (content/browser-tabPreviews.xml)
|
||||
* content/browser/chatWindow.xul (content/chatWindow.xul)
|
||||
content/browser/tab-content.js (content/tab-content.js)
|
||||
|
|
|
@ -39,10 +39,6 @@ XPCOMUtils.defineLazyGetter(this, "BrandBundle", function() {
|
|||
const kBrandBundle = "chrome://branding/locale/brand.properties";
|
||||
return Services.strings.createBundle(kBrandBundle);
|
||||
});
|
||||
XPCOMUtils.defineLazyGetter(this, "PocketBundle", function() {
|
||||
const kPocketBundle = "chrome://browser/content/browser-pocket.properties";
|
||||
return Services.strings.createBundle(kPocketBundle);
|
||||
});
|
||||
|
||||
const kNSXUL = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
|
||||
const kPrefCustomizationDebug = "browser.uiCustomization.debug";
|
||||
|
@ -1069,10 +1065,11 @@ if (Services.prefs.getBoolPref("privacy.panicButton.enabled")) {
|
|||
|
||||
if (Services.prefs.getBoolPref("browser.pocket.enabled")) {
|
||||
let isEnabledForLocale = true;
|
||||
let browserLocale;
|
||||
if (Services.prefs.getBoolPref("browser.pocket.useLocaleList")) {
|
||||
let chromeRegistry = Cc["@mozilla.org/chrome/chrome-registry;1"]
|
||||
.getService(Ci.nsIXULChromeRegistry);
|
||||
let browserLocale = chromeRegistry.getSelectedLocale("browser");
|
||||
browserLocale = chromeRegistry.getSelectedLocale("browser");
|
||||
let enabledLocales = [];
|
||||
try {
|
||||
enabledLocales = Services.prefs.getCharPref("browser.pocket.enabledLocales").split(' ');
|
||||
|
@ -1083,14 +1080,30 @@ if (Services.prefs.getBoolPref("browser.pocket.enabled")) {
|
|||
}
|
||||
|
||||
if (isEnabledForLocale) {
|
||||
let url = "chrome://browser/content/browser-pocket-" + browserLocale + ".properties";
|
||||
let strings = Services.strings.createBundle(url);
|
||||
let label;
|
||||
let tooltiptext;
|
||||
try {
|
||||
label = strings.GetStringFromName("pocket-button.label");
|
||||
tooltiptext = strings.GetStringFromName("pocket-button.tooltiptext");
|
||||
} catch (err) {
|
||||
// GetStringFromName throws when the bundle doesn't exist. In that case,
|
||||
// fall back to the en-US browser-pocket.properties.
|
||||
url = "chrome://browser/content/browser-pocket.properties";
|
||||
strings = Services.strings.createBundle(url);
|
||||
label = strings.GetStringFromName("pocket-button.label");
|
||||
tooltiptext = strings.GetStringFromName("pocket-button.tooltiptext");
|
||||
}
|
||||
|
||||
let pocketButton = {
|
||||
id: "pocket-button",
|
||||
defaultArea: CustomizableUI.AREA_NAVBAR,
|
||||
introducedInVersion: "pref",
|
||||
type: "view",
|
||||
viewId: "PanelUI-pocketView",
|
||||
label: PocketBundle.GetStringFromName("pocket-button.label"),
|
||||
tooltiptext: PocketBundle.GetStringFromName("pocket-button.tooltiptext"),
|
||||
label: label,
|
||||
tooltiptext: tooltiptext,
|
||||
onViewShowing: Pocket.onPanelViewShowing,
|
||||
onViewHiding: Pocket.onPanelViewHiding,
|
||||
|
||||
|
|
|
@ -12,6 +12,8 @@ browser.jar:
|
|||
content/browser/pocket/panels/css/saved.css (panels/css/saved.css)
|
||||
content/browser/pocket/panels/css/signup.css (panels/css/signup.css)
|
||||
content/browser/pocket/panels/fonts/FiraSans-Regular.woff (panels/fonts/FiraSans-Regular.woff)
|
||||
content/browser/pocket/panels/img/pocketerror@1x.png (panels/img/pocketerror@1x.png)
|
||||
content/browser/pocket/panels/img/pocketerror@2x.png (panels/img/pocketerror@2x.png)
|
||||
content/browser/pocket/panels/img/pocketlogo@1x.png (panels/img/pocketlogo@1x.png)
|
||||
content/browser/pocket/panels/img/pocketlogo@2x.png (panels/img/pocketlogo@2x.png)
|
||||
content/browser/pocket/panels/img/pocketlogosolo@1x.png (panels/img/pocketlogosolo@1x.png)
|
||||
|
@ -40,6 +42,7 @@ browser.jar:
|
|||
content/browser/pocket/panels/js/vendor/jquery-2.1.1.min.js (panels/js/vendor/jquery-2.1.1.min.js)
|
||||
content/browser/pocket/panels/js/vendor/handlebars.runtime.js (panels/js/vendor/handlebars.runtime.js)
|
||||
content/browser/pocket/panels/js/vendor/jquery.tokeninput.min.js (panels/js/vendor/jquery.tokeninput.min.js)
|
||||
content/browser/pocket/panels/tmpl/saved_premiumextras.handlebars (panels/tmpl/saved_premiumextras.handlebars)
|
||||
content/browser/pocket/panels/tmpl/saved_premiumshell.handlebars (panels/tmpl/saved_premiumshell.handlebars)
|
||||
content/browser/pocket/panels/tmpl/saved_shell.handlebars (panels/tmpl/saved_shell.handlebars)
|
||||
content/browser/pocket/panels/tmpl/signup_shell.handlebars (panels/tmpl/signup_shell.handlebars)
|
||||
|
|
|
@ -49,13 +49,21 @@ var pktUI = (function() {
|
|||
|
||||
// -- Initialization (on startup and new windows) -- //
|
||||
var inited = false;
|
||||
var currentPanelDidShow, currentPanelDidHide;
|
||||
var _currentPanelDidShow;
|
||||
var _currentPanelDidHide;
|
||||
var _isHidden = false;
|
||||
|
||||
var _notificationTimeout;
|
||||
|
||||
var prefBranch = Services.prefs.getBranch("browser.pocket.settings.");
|
||||
|
||||
|
||||
// Init panel id at 0. The first actual panel id will have the number 1 so
|
||||
// in case at some point any panel has the id 0 we know there is something
|
||||
// wrong
|
||||
var _panelId = 0;
|
||||
|
||||
var prefBranch = Services.prefs.getBranch("browser.pocket.settings.");
|
||||
|
||||
var savePanelWidth = 350;
|
||||
var savePanelHeights = {collapsed: 153, expanded: 272};
|
||||
|
||||
/**
|
||||
* Initalizes Pocket UI and panels
|
||||
*/
|
||||
|
@ -162,15 +170,15 @@ var pktUI = (function() {
|
|||
}
|
||||
|
||||
function pocketPanelDidShow(event) {
|
||||
if (currentPanelDidShow) {
|
||||
currentPanelDidShow(event);
|
||||
if (_currentPanelDidShow) {
|
||||
_currentPanelDidShow(event);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
function pocketPanelDidHide(event) {
|
||||
if (currentPanelDidHide) {
|
||||
currentPanelDidHide(event);
|
||||
if (_currentPanelDidHide) {
|
||||
_currentPanelDidHide(event);
|
||||
}
|
||||
|
||||
// clear the panel
|
||||
|
@ -299,7 +307,7 @@ var pktUI = (function() {
|
|||
startheight = 436;
|
||||
}
|
||||
}
|
||||
showPanel("chrome://browser/content/pocket/panels/signup.html?pockethost=" + Services.prefs.getCharPref("browser.pocket.site") + "&fxasignedin=" + fxasignedin + "&variant=" + pktApi.getSignupAB(), {
|
||||
var panelId = showPanel("chrome://browser/content/pocket/panels/signup.html?pockethost=" + Services.prefs.getCharPref("browser.pocket.site") + "&fxasignedin=" + fxasignedin + "&variant=" + pktApi.getSignupAB(), {
|
||||
onShow: function() {
|
||||
},
|
||||
onHide: panelDidHide,
|
||||
|
@ -321,15 +329,30 @@ var pktUI = (function() {
|
|||
|
||||
var isValidURL = (typeof url !== 'undefined' && (url.startsWith("http") || url.startsWith('https')));
|
||||
|
||||
showPanel("chrome://browser/content/pocket/panels/saved.html?pockethost=" + Services.prefs.getCharPref("browser.pocket.site") + "&premiumStatus=" + (pktApi.isPremiumUser() ? '1' : '0'), {
|
||||
var panelId = showPanel("chrome://browser/content/pocket/panels/saved.html?pockethost=" + Services.prefs.getCharPref("browser.pocket.site") + "&premiumStatus=" + (pktApi.isPremiumUser() ? '1' : '0'), {
|
||||
onShow: function() {
|
||||
var saveLinkMessageId = 'saveLink';
|
||||
|
||||
// Send error message for invalid url
|
||||
if (!isValidURL) {
|
||||
var error = new Error('Only links can be saved');
|
||||
sendErrorMessage('saveLink', error);
|
||||
// TODO: Pass key for localized error in error object
|
||||
var error = {
|
||||
message: 'Only links can be saved',
|
||||
localizedKey: "onlylinkssaved"
|
||||
};
|
||||
pktUIMessaging.sendErrorMessageToPanel(panelId, saveLinkMessageId, error);
|
||||
return;
|
||||
}
|
||||
|
||||
// Check online state
|
||||
if (!navigator.onLine) {
|
||||
// TODO: Pass key for localized error in error object
|
||||
var error = {
|
||||
message: 'You must be connected to the Internet in order to save to Pocket. Please connect to the Internet and try again.'
|
||||
};
|
||||
pktUIMessaging.sendErrorMessageToPanel(panelId, saveLinkMessageId, error); return;
|
||||
}
|
||||
|
||||
// Add url
|
||||
var options = {
|
||||
success: function(data, request) {
|
||||
|
@ -338,7 +361,7 @@ var pktUI = (function() {
|
|||
status: "success",
|
||||
item: item
|
||||
};
|
||||
sendMessage('saveLink', successResponse);
|
||||
pktUIMessaging.sendMessageToPanel(panelId, saveLinkMessageId, successResponse);
|
||||
},
|
||||
error: function(error, request) {
|
||||
// If user is not authorized show singup page
|
||||
|
@ -347,8 +370,13 @@ var pktUI = (function() {
|
|||
return;
|
||||
}
|
||||
|
||||
// Send error message to panel
|
||||
sendErrorMessage('saveLink', error);
|
||||
// If there is no error message in the error use a
|
||||
// complete catch-all
|
||||
var errorMessage = error.message || "There was an error when trying to save to Pocket.";
|
||||
var panelError = { message: errorMessage}
|
||||
|
||||
// Send error message to panel
|
||||
pktUIMessaging.sendErrorMessageToPanel(panelId, saveLinkMessageId, panelError);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -361,8 +389,8 @@ var pktUI = (function() {
|
|||
pktApi.addLink(url, options);
|
||||
},
|
||||
onHide: panelDidHide,
|
||||
width: 350,
|
||||
height: 267
|
||||
width: savePanelWidth,
|
||||
height: pktApi.isPremiumUser() && isValidURL ? savePanelHeights.expanded : savePanelHeights.collapsed
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -370,6 +398,9 @@ var pktUI = (function() {
|
|||
* Open a generic panel
|
||||
*/
|
||||
function showPanel(url, options) {
|
||||
// Add new panel id
|
||||
_panelId += 1;
|
||||
url += ("&panelId=" + _panelId);
|
||||
|
||||
// We don't have to hide and show the panel again if it's already shown
|
||||
// as if the user tries to click again on the toolbar button the overlay
|
||||
|
@ -389,13 +420,15 @@ var pktUI = (function() {
|
|||
|
||||
// For some reason setting onpopupshown and onpopuphidden on the panel directly didn't work, so
|
||||
// do it this hacky way for now
|
||||
currentPanelDidShow = options.onShow;
|
||||
currentPanelDidHide = options.onHide;
|
||||
_currentPanelDidShow = options.onShow;
|
||||
_currentPanelDidHide = options.onHide;
|
||||
|
||||
resizePanel({
|
||||
width: options.width,
|
||||
height: options.height
|
||||
});
|
||||
|
||||
return _panelId;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -421,168 +454,132 @@ var pktUI = (function() {
|
|||
function panelDidHide() {
|
||||
}
|
||||
|
||||
// -- Communication to Panels -- //
|
||||
// https://developer.mozilla.org/en-US/Add-ons/Code_snippets/Interaction_between_privileged_and_non-privileged_pages
|
||||
|
||||
/**
|
||||
* Register a listener and callback for a specific messageId
|
||||
*/
|
||||
function addMessageListener(messageId, callback) {
|
||||
|
||||
document.addEventListener('PKT_'+messageId, function(e) {
|
||||
// ignore to ensure we do not pick up other events in the browser
|
||||
if (e.target.tagName !== 'PKTMESSAGEFROMPANELELEMENT') {
|
||||
return;
|
||||
}
|
||||
|
||||
// Send payload to callback
|
||||
callback(JSON.parse(e.target.getAttribute("payload"))[0]);
|
||||
|
||||
// Cleanup the element
|
||||
e.target.parentNode.removeChild(e.target);
|
||||
|
||||
}, false, true);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove a message listener
|
||||
*/
|
||||
function removeMessageListener(messageId, callback) {
|
||||
document.removeMessageListener('PKT_'+messageId, callback);
|
||||
}
|
||||
|
||||
/**
|
||||
* Send a message to the panel's iframe
|
||||
*/
|
||||
function sendMessage(messageId, payload) {
|
||||
|
||||
var doc = getPanelFrame().contentWindow.document;
|
||||
|
||||
var AnswerEvt = doc.createElement("PKTMessage");
|
||||
AnswerEvt.setAttribute("payload", JSON.stringify([payload]));
|
||||
|
||||
doc.documentElement.appendChild(AnswerEvt);
|
||||
|
||||
var event = doc.createEvent("HTMLEvents");
|
||||
event.initEvent('PKT_'+messageId, true, false);
|
||||
AnswerEvt.dispatchEvent(event);
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper function to package an error object and send it to the panel iframe as a message response
|
||||
*/
|
||||
function sendErrorMessage(messageId, error) {
|
||||
var errorResponse = {status: "error", error: error.message};
|
||||
sendMessage(messageId, errorResponse);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register all of the messages needed for the panels
|
||||
*/
|
||||
function registerEventMessages() {
|
||||
|
||||
// TODO : There are likely some possible race conditions possible here, for example if the user clicks the button quickly multiple times, due to the async property of the messages, a message may be picked up for an older panel. We should consider updating this to include some sort of panelId that changes per open.
|
||||
var iframe = getPanelFrame();
|
||||
|
||||
// Only register the messages once
|
||||
if (iframe.getAttribute('did_init') == 1) {
|
||||
return;
|
||||
var didInitAttributeKey = 'did_init';
|
||||
var didInitMessageListener = iframe.getAttribute(didInitAttributeKey);
|
||||
if (typeof didInitMessageListener !== "undefined" && didInitMessageListener == 1) {
|
||||
return;
|
||||
}
|
||||
|
||||
iframe.setAttribute('did_init', 1);
|
||||
iframe.setAttribute(didInitAttributeKey, 1);
|
||||
|
||||
// When the panel is displayed it generated an event called
|
||||
// "show": we will listen for that event and when it happens,
|
||||
// send our own "show" event to the panel's script, so the
|
||||
// script can prepare the panel for display.
|
||||
addMessageListener("show", function(payload) {
|
||||
var _showMessageId = "show";
|
||||
pktUIMessaging.addMessageListener(_showMessageId, function(panelId, data) {
|
||||
// Let panel know that it is ready
|
||||
sendMessage('show');
|
||||
pktUIMessaging.sendMessageToPanel(panelId, _showMessageId);
|
||||
});
|
||||
|
||||
// Open a new tab with a given url and activate if
|
||||
addMessageListener("openTabWithUrl", function(payload) {
|
||||
// Open a new tab with a given url and activate if
|
||||
var _openTabWithUrlMessageId = "openTabWithUrl";
|
||||
pktUIMessaging.addMessageListener(_openTabWithUrlMessageId, function(panelId, data) {
|
||||
|
||||
// Check if the tab should become active after opening
|
||||
var activate = true;
|
||||
if (typeof payload.activate !== "undefined") {
|
||||
activate = payload.activate;
|
||||
if (typeof data.activate !== "undefined") {
|
||||
activate = data.activate;
|
||||
}
|
||||
openTabWithUrl(payload.url, activate);
|
||||
sendMessage("openTabWithUrlResponse", payload.url);
|
||||
|
||||
var url = data.url;
|
||||
openTabWithUrl(url, activate);
|
||||
pktUIMessaging.sendResponseMessageToPanel(panelId, _openTabWithUrlMessageId, url);
|
||||
});
|
||||
|
||||
// Close the panel
|
||||
addMessageListener("close", function(payload) {
|
||||
var _closeMessageId = "close";
|
||||
pktUIMessaging.addMessageListener(_closeMessageId, function(panelId, data) {
|
||||
getPanel().hidePopup();
|
||||
});
|
||||
|
||||
// Send the current url to the panel
|
||||
addMessageListener("getCurrentURL", function(payload) {
|
||||
sendMessage('getCurrentURLResponse', getCurrentUrl());
|
||||
var _getCurrentURLMessageId = "getCurrentURL";
|
||||
pktUIMessaging.addMessageListener(_getCurrentURLMessageId, function(panelId, data) {
|
||||
pktUIMessaging.sendResponseMessageToPanel(panelId, _getCurrentURLMessageId, getCurrentUrl());
|
||||
});
|
||||
|
||||
var _resizePanelMessageId = "resizePanel";
|
||||
pktUIMessaging.addMessageListener(_resizePanelMessageId, function(panelId, data) {
|
||||
resizePanel(data);
|
||||
});
|
||||
|
||||
// Callback post initialization to tell background script that panel is "ready" for communication.
|
||||
addMessageListener("listenerReady", function(payload) {
|
||||
pktUIMessaging.addMessageListener("listenerReady", function(panelId, data) {
|
||||
|
||||
});
|
||||
|
||||
pktUIMessaging.addMessageListener("collapseSavePanel", function(panelId, data) {
|
||||
if (!pktApi.isPremiumUser())
|
||||
resizePanel({width:savePanelWidth, height:savePanelHeights.collapsed});
|
||||
});
|
||||
|
||||
addMessageListener("resizePanel", function(payload) {
|
||||
resizePanel(payload);
|
||||
pktUIMessaging.addMessageListener("expandSavePanel", function(panelId, data) {
|
||||
resizePanel({width:savePanelWidth, height:savePanelHeights.expanded});
|
||||
});
|
||||
|
||||
// Ask for recently accessed/used tags for auto complete
|
||||
addMessageListener("getTags", function(payload) {
|
||||
var _getTagsMessageId = "getTags";
|
||||
pktUIMessaging.addMessageListener(_getTagsMessageId, function(panelId, data) {
|
||||
pktApi.getTags(function(tags, usedTags) {
|
||||
sendMessage('getTagsResponse', {tags, usedTags});
|
||||
pktUIMessaging.sendResponseMessageToPanel(panelId, _getTagsMessageId, {
|
||||
tags: tags,
|
||||
usedTags: usedTags
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
// Ask for suggested tags based on passed url
|
||||
addMessageListener("getSuggestedTags", function(payload) {
|
||||
var responseMessageId = "getSuggestedTagsResponse";
|
||||
|
||||
pktApi.getSuggestedTagsForURL(payload.url, {
|
||||
var _getSuggestedTagsMessageId = "getSuggestedTags";
|
||||
pktUIMessaging.addMessageListener(_getSuggestedTagsMessageId, function(panelId, data) {
|
||||
pktApi.getSuggestedTagsForURL(data.url, {
|
||||
success: function(data, response) {
|
||||
var suggestedTags = data.suggested_tags;
|
||||
var successResponse = {
|
||||
status: "success",
|
||||
value: {
|
||||
"suggestedTags" : suggestedTags
|
||||
suggestedTags : suggestedTags
|
||||
}
|
||||
}
|
||||
sendMessage(responseMessageId, successResponse);
|
||||
pktUIMessaging.sendResponseMessageToPanel(panelId, _getSuggestedTagsMessageId, successResponse);
|
||||
},
|
||||
error: function(error, response) {
|
||||
sendErrorMessage(responseMessageId, error);
|
||||
pktUIMessaging.sendErrorResponseMessageToPanel(panelId, _getSuggestedTagsMessageId, error);
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
// Pass url and array list of tags, add to existing save item accordingly
|
||||
addMessageListener("addTags", function(payload) {
|
||||
var responseMessageId = "addTagsResponse";
|
||||
|
||||
pktApi.addTagsToURL(payload.url, payload.tags, {
|
||||
var _addTagsMessageId = "addTags";
|
||||
pktUIMessaging.addMessageListener(_addTagsMessageId, function(panelId, data) {
|
||||
pktApi.addTagsToURL(data.url, data.tags, {
|
||||
success: function(data, response) {
|
||||
var successResponse = {status: "success"};
|
||||
sendMessage(responseMessageId, successResponse);
|
||||
var successResponse = {status: "success"};
|
||||
pktUIMessaging.sendResponseMessageToPanel(panelId, _addTagsMessageId, successResponse);
|
||||
},
|
||||
error: function(error, response) {
|
||||
sendErrorMessage(responseMessageId, error);
|
||||
pktUIMessaging.sendErrorResponseMessageToPanel(panelId, _addTagsMessageId, error);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Based on clicking "remove page" CTA, and passed unique item id, remove the item
|
||||
addMessageListener("deleteItem", function(payload) {
|
||||
var responseMessageId = "deleteItemResponse";
|
||||
|
||||
pktApi.deleteItem(payload.itemId, {
|
||||
var _deleteItemMessageId = "deleteItem";
|
||||
pktUIMessaging.addMessageListener(_deleteItemMessageId, function(panelId, data) {
|
||||
pktApi.deleteItem(data.itemId, {
|
||||
success: function(data, response) {
|
||||
var successResponse = {status: "success"};
|
||||
sendMessage(responseMessageId, successResponse);
|
||||
var successResponse = {status: "success"};
|
||||
pktUIMessaging.sendResponseMessageToPanel(panelId, _deleteItemMessageId, successResponse);
|
||||
},
|
||||
error: function(error, response) {
|
||||
sendErrorMessage(responseMessageId, error);
|
||||
pktUIMessaging.sendErrorResponseMessageToPanel(panelId, _deleteItemMessageId, error);
|
||||
}
|
||||
})
|
||||
});
|
||||
|
@ -748,3 +745,149 @@ var pktUI = (function() {
|
|||
isHidden
|
||||
};
|
||||
}());
|
||||
|
||||
// -- Communication to Background -- //
|
||||
// https://developer.mozilla.org/en-US/Add-ons/Code_snippets/Interaction_between_privileged_and_non-privileged_pages
|
||||
var pktUIMessaging = (function() {
|
||||
|
||||
/**
|
||||
* Prefix message id for message listening
|
||||
*/
|
||||
function prefixedMessageId(messageId) {
|
||||
return 'PKT_' + messageId;
|
||||
}
|
||||
|
||||
/**
|
||||
* Register a listener and callback for a specific messageId
|
||||
*/
|
||||
function addMessageListener(messageId, callback) {
|
||||
document.addEventListener(prefixedMessageId(messageId), function(e) {
|
||||
// ignore to ensure we do not pick up other events in the browser
|
||||
if (e.target.tagName !== 'PKTMESSAGEFROMPANELELEMENT') {
|
||||
return;
|
||||
}
|
||||
|
||||
// Pass in information to callback
|
||||
var payload = JSON.parse(e.target.getAttribute("payload"))[0];
|
||||
var panelId = payload.panelId;
|
||||
var data = payload.data;
|
||||
callback(panelId, data);
|
||||
|
||||
// Cleanup the element
|
||||
e.target.parentNode.removeChild(e.target);
|
||||
|
||||
}, false, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove a message listener
|
||||
*/
|
||||
function removeMessageListener(messageId, callback) {
|
||||
document.removeEventListener(prefixedMessageId(messageId), callback);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Send a message to the panel's iframe
|
||||
*/
|
||||
function sendMessageToPanel(panelId, messageId, payload) {
|
||||
|
||||
if (!isPanelIdValid(panelId)) { return; };
|
||||
|
||||
var panelFrame = document.getElementById('pocket-panel-iframe');
|
||||
if (!isPocketPanelFrameValid(panelFrame)) { return; }
|
||||
|
||||
var doc = panelFrame.contentWindow.document;
|
||||
var documentElement = doc.documentElement;
|
||||
|
||||
// Send message to panel
|
||||
var panelMessageId = prefixedMessageId(panelId + '_' + messageId);
|
||||
|
||||
var AnswerEvt = doc.createElement("PKTMessage");
|
||||
AnswerEvt.setAttribute("payload", JSON.stringify([payload]));
|
||||
documentElement.appendChild(AnswerEvt);
|
||||
|
||||
var event = doc.createEvent("HTMLEvents");
|
||||
event.initEvent(panelMessageId, true, false);
|
||||
AnswerEvt.dispatchEvent(event);
|
||||
}
|
||||
|
||||
function sendResponseMessageToPanel(panelId, messageId, payload) {
|
||||
var responseMessageId = messageId + "Response";
|
||||
sendMessageToPanel(panelId, responseMessageId, payload);
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper function to package an error object and send it to the panel
|
||||
* iframe as a message response
|
||||
*/
|
||||
function sendErrorMessageToPanel(panelId, messageId, error) {
|
||||
var errorResponse = {status: "error", error: error};
|
||||
sendMessageToPanel(panelId, messageId, errorResponse);
|
||||
}
|
||||
|
||||
function sendErrorResponseMessageToPanel(panelId, messageId, error) {
|
||||
var errorResponse = {status: "error", error: error};
|
||||
sendResponseMessageToPanel(panelId, messageId, errorResponse);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validation
|
||||
*/
|
||||
|
||||
function isPanelIdValid(panelId) {
|
||||
// First check if panelId has a valid value > 0. We set the panelId to
|
||||
// 0 to start. But if for some reason the message is attempted to be
|
||||
// sent before the panel has a panelId, then it's going to send out
|
||||
// a message with panelId 0, which is never going to be heard. If this
|
||||
// happens, it means some race condition occurred where the panel was
|
||||
// trying to communicate before it should.
|
||||
if (panelId === 0) {
|
||||
console.warn("Tried to send message to panel with id 0.")
|
||||
return false;
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
function isPocketPanelFrameValid(panelFrame) {
|
||||
// Check if panel is available if not throw a warning and bailout.
|
||||
// We likely try to send to a panel that is not visible anymore
|
||||
if (typeof panelFrame === "undefined") {
|
||||
console.warn("Pocket panel frame is undefined");
|
||||
return false;
|
||||
}
|
||||
|
||||
var contentWindow = panelFrame.contentWindow;
|
||||
if (typeof contentWindow == "undefined") {
|
||||
console.warn("Pocket panel frame content window is undefined");
|
||||
return false;
|
||||
}
|
||||
|
||||
var doc = contentWindow.document;
|
||||
if (typeof doc === "undefined") {
|
||||
console.warn("Pocket panel frame content window document is undefined");
|
||||
return false;
|
||||
}
|
||||
|
||||
var documentElement = doc.documentElement;
|
||||
if (typeof documentElement === "undefined") {
|
||||
console.warn("Pocket panel frame content window document document element is undefined");
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Public
|
||||
*/
|
||||
return {
|
||||
addMessageListener: addMessageListener,
|
||||
removeMessageListener: removeMessageListener,
|
||||
sendMessageToPanel: sendMessageToPanel,
|
||||
sendResponseMessageToPanel: sendResponseMessageToPanel,
|
||||
sendErrorMessageToPanel: sendErrorMessageToPanel,
|
||||
sendErrorResponseMessageToPanel: sendErrorResponseMessageToPanel
|
||||
}
|
||||
}());
|
||||
|
|
|
@ -397,3 +397,28 @@ td,
|
|||
th {
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
/* Normalization for FF panel defauts
|
||||
========================================================================== */
|
||||
html {
|
||||
outline: none;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
a {
|
||||
color: #0095dd;
|
||||
margin: 0;
|
||||
outline: none;
|
||||
padding: 0;
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
a:hover,
|
||||
a:active {
|
||||
color: #008acb;
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
a:active {
|
||||
color: #006b9d;
|
||||
}
|
||||
|
|
|
@ -52,12 +52,15 @@
|
|||
.pkt_ext_containersaved .pkt_ext_loadingspinner {
|
||||
position: relative;
|
||||
display: inline-block;
|
||||
width: 2.5em;
|
||||
height: 2.5em;
|
||||
margin: 2em 0 0;
|
||||
left: 50%;
|
||||
margin: 2em 0 0 -1.25em;
|
||||
font-size: 10px;
|
||||
text-indent: 999em;
|
||||
position: absolute;
|
||||
top: 4em;
|
||||
overflow: hidden;
|
||||
width: 2.5em;
|
||||
animation: pkt_ext_spin 0.7s infinite steps(8);
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_loadingspinner:before,
|
||||
|
@ -96,7 +99,7 @@
|
|||
.pkt_ext_containersaved .pkt_ext_initload {
|
||||
left: 0;
|
||||
position: absolute;
|
||||
top: 1em;
|
||||
top: 0;
|
||||
width: 100%;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_detail {
|
||||
|
@ -106,7 +109,6 @@
|
|||
z-index: 10;
|
||||
}
|
||||
.pkt_ext_container_detailactive .pkt_ext_initload {
|
||||
transition: opacity 0.2s ease-out;
|
||||
opacity: 0;
|
||||
}
|
||||
.pkt_ext_container_detailactive .pkt_ext_initload .pkt_ext_loadingspinner,
|
||||
|
@ -116,7 +118,6 @@
|
|||
.pkt_ext_container_detailactive .pkt_ext_detail {
|
||||
max-height: 20em;
|
||||
opacity: 1;
|
||||
transition: opacity 0.2s ease-out;
|
||||
}
|
||||
.pkt_ext_container_finalstate .pkt_ext_edit_msg,
|
||||
.pkt_ext_container_finalstate .pkt_ext_tag_detail,
|
||||
|
@ -151,30 +152,9 @@
|
|||
@keyframes fade_in_out {
|
||||
0% {
|
||||
opacity: 1;
|
||||
top: 0;
|
||||
}
|
||||
50% {
|
||||
opacity: 0;
|
||||
top: 0;
|
||||
}
|
||||
51% {
|
||||
opacity: 0;
|
||||
top: 10px;
|
||||
}
|
||||
100% {
|
||||
opacity: 1;
|
||||
top: 10px;
|
||||
}
|
||||
}
|
||||
@keyframes fade_in_outalt {
|
||||
0% {
|
||||
opacity: 1;
|
||||
}
|
||||
50% {
|
||||
opacity: 0;
|
||||
}
|
||||
51% {
|
||||
opacity: 0;
|
||||
}
|
||||
100% {
|
||||
opacity: 1;
|
||||
|
@ -182,18 +162,17 @@
|
|||
}
|
||||
.pkt_ext_container_finalstate h2 {
|
||||
animation: fade_in_out 0.4s ease-out;
|
||||
top: 10px;
|
||||
}
|
||||
.pkt_ext_container_finalerrorstate h2 {
|
||||
animation: fade_int_outalt 0.4s ease-out;
|
||||
animation: none;
|
||||
color: #d74345;
|
||||
top: 0;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_errordetail {
|
||||
display: none;
|
||||
font-size: 12px;
|
||||
font-weight: normal;
|
||||
left: 6.4em;
|
||||
max-width: 21em;
|
||||
opacity: 0;
|
||||
position: absolute;
|
||||
top: 2.7em;
|
||||
|
@ -220,20 +199,33 @@
|
|||
background-size: 44px 40px;
|
||||
}
|
||||
}
|
||||
.pkt_ext_container_finalerrorstate .pkt_ext_logo {
|
||||
background-image: url(../img/pocketerror@1x.png);
|
||||
height: 44px;
|
||||
width: 44px;
|
||||
}
|
||||
@media (min-resolution: 1.1dppx) {
|
||||
.pkt_ext_container_finalerrorstate .pkt_ext_logo {
|
||||
background-image: url(../img/pocketerror@2x.png);
|
||||
background-size: 44px 44px;
|
||||
}
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_topdetail {
|
||||
float: left;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_edit_msg {
|
||||
box-sizing: border-box;
|
||||
display: none;
|
||||
font-size: 0.875em;
|
||||
font-size: 0.75em;
|
||||
left: auto;
|
||||
padding: 0 1.4em;
|
||||
position: absolute;
|
||||
text-align: center;
|
||||
top: 4.3em;
|
||||
text-align: left;
|
||||
top: 8.7em;
|
||||
width: 100%;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_edit_msg_error {
|
||||
color: #c10000;
|
||||
color: #d74345;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_edit_msg_active {
|
||||
display: block;
|
||||
|
@ -357,6 +349,9 @@
|
|||
padding: 0;
|
||||
display: flex;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_tag_error {
|
||||
border: none;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_tag_input_wrapper {
|
||||
box-sizing: border-box;
|
||||
flex: 1;
|
||||
|
@ -374,6 +369,9 @@
|
|||
padding-left: 0.5em;
|
||||
padding-right: 0.5em;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_tag_error .pkt_ext_tag_input_wrapper {
|
||||
border: 1px solid #d74345;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_tag_input_wrapper .token-input-list {
|
||||
display: block;
|
||||
left: 0;
|
||||
|
@ -418,6 +416,7 @@
|
|||
}
|
||||
.pkt_ext_containersaved .pkt_ext_btn {
|
||||
box-sizing: border-box;
|
||||
color: #333;
|
||||
float: none;
|
||||
font-size: 0.875em;
|
||||
font-size: 14px;
|
||||
|
@ -425,13 +424,27 @@
|
|||
height: 2.2em;
|
||||
min-width: 4em;
|
||||
padding: 0.5em 0;
|
||||
text-decoration: none;
|
||||
text-transform: none;
|
||||
width: auto;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_btn_disabled {
|
||||
background-color: #ededed;
|
||||
.pkt_ext_containersaved .pkt_ext_btn:hover {
|
||||
background-color: #ebebeb;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_btn:active {
|
||||
background-color: #dadada;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_btn_disabled,
|
||||
.pkt_ext_containersaved .pkt_ext_btn_disabled:hover,
|
||||
.pkt_ext_containersaved .pkt_ext_btn_disabled:active {
|
||||
background-color: transparent;
|
||||
cursor: default;
|
||||
opacity: 0.5;
|
||||
opacity: 0.4;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_tag_error .pkt_ext_btn {
|
||||
border: 1px solid #c3c3c3;
|
||||
border-width: 1px 1px 1px 0;
|
||||
height: 2.35em;
|
||||
}
|
||||
.pkt_ext_containersaved .autocomplete-suggestions {
|
||||
margin-top: 2.2em;
|
||||
|
@ -439,19 +452,27 @@
|
|||
|
||||
/*=Recent/suggested tags
|
||||
--------------------------------------------------------------------------------------- */
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detail {
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detail,
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detailshown {
|
||||
border-top: 1px solid #c1c1c1;
|
||||
bottom: 0;
|
||||
background: #ebebeb;
|
||||
clear: both;
|
||||
left: 0;
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
min-height: 110px;
|
||||
position: fixed;
|
||||
visibility: hidden;
|
||||
width: 100%;
|
||||
}
|
||||
.pkt_ext_container_detailactive .pkt_ext_suggestedtag_detail {
|
||||
.pkt_ext_container_detailactive .pkt_ext_suggestedtag_detail,
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detailshown {
|
||||
opacity: 1;
|
||||
transition: opacity 0.2s ease-out, visibility 0.2s ease-out;
|
||||
visibility: visible;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detailshown {
|
||||
padding: 4px 0;
|
||||
}
|
||||
.pkt_ext_container_finalstate .pkt_ext_suggestedtag_detail {
|
||||
opacity: 0;
|
||||
visibility: hidden;
|
||||
|
@ -488,6 +509,11 @@
|
|||
overflow: hidden;
|
||||
padding: 2px 0 0 0;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detail ul {
|
||||
height: auto;
|
||||
margin: 0 2em 0 0;
|
||||
padding-top: 6px;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_recenttag_detail li,
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detail li {
|
||||
background: none;
|
||||
|
@ -512,6 +538,9 @@
|
|||
text-align: left;
|
||||
top: 2em;
|
||||
}
|
||||
.pkt_ext_containersaved .pkt_ext_suggestedtag_detail .suggestedtag_msg {
|
||||
margin-right: 1.3em;
|
||||
}
|
||||
.pkt_ext_containersaved .token_tag {
|
||||
border-radius: 4px;
|
||||
background: #f7f7f7;
|
||||
|
@ -522,7 +551,7 @@
|
|||
font-weight: normal;
|
||||
letter-spacing: normal;
|
||||
margin-right: 0.5em;
|
||||
padding: 0.125em 0.3125em;
|
||||
padding: 0.125em 0.625em;
|
||||
text-decoration: none;
|
||||
text-transform: none;
|
||||
}
|
||||
|
@ -639,7 +668,7 @@
|
|||
border: 1px solid #c3c3c3;
|
||||
overflow: hidden;
|
||||
margin: 0;
|
||||
padding: 0 5px;
|
||||
padding: 0 8px;
|
||||
background-color: #f7f7f7;
|
||||
color: #000;
|
||||
font-weight: normal;
|
||||
|
@ -688,7 +717,7 @@
|
|||
cursor: pointer;
|
||||
display: inline-block;
|
||||
height: 8px;
|
||||
margin: 0 2px 0 8px;
|
||||
margin: 0 0 0 8px;
|
||||
overflow: hidden;
|
||||
width: 8px;
|
||||
text-indent: -99px;
|
||||
|
|
После Ширина: | Высота: | Размер: 1.4 KiB |
После Ширина: | Высота: | Размер: 3.1 KiB |
Двоичные данные
browser/components/pocket/panels/img/pocketsignup_devices@1x.png
До Ширина: | Высота: | Размер: 21 KiB После Ширина: | Высота: | Размер: 22 KiB |
Двоичные данные
browser/components/pocket/panels/img/pocketsignup_devices@2x.png
До Ширина: | Высота: | Размер: 66 KiB После Ширина: | Высота: | Размер: 72 KiB |
Двоичные данные
browser/components/pocket/panels/img/pocketsignup_hero@1x.png
До Ширина: | Высота: | Размер: 40 KiB После Ширина: | Высота: | Размер: 44 KiB |
Двоичные данные
browser/components/pocket/panels/img/pocketsignup_hero@2x.png
До Ширина: | Высота: | Размер: 130 KiB После Ширина: | Высота: | Размер: 145 KiB |
|
@ -3,10 +3,12 @@ Translations.en =
|
|||
{
|
||||
addtags: "Add Tags",
|
||||
alreadyhaveacct: "Already a Pocket user?",
|
||||
errorgeneric: "There was an error when trying to save to Pocket.",
|
||||
learnmore: "Learn More",
|
||||
loginnow: "Log in",
|
||||
maxtaglength: "Tags are limited to 25 characters",
|
||||
mustbeconnected: "You must be connected to the Internet in order to save to Pocket. Please check your connection and try again.",
|
||||
onlylinkssaved: "Only links can be saved",
|
||||
or: "or",
|
||||
pagenotsaved: "Page Not Saved",
|
||||
pageremoved: "Page Removed",
|
||||
pagesaved: "Saved to Pocket",
|
||||
|
@ -14,6 +16,7 @@ Translations.en =
|
|||
processingtags: "Adding tags...",
|
||||
removepage: "Remove Page",
|
||||
save: "Save",
|
||||
saving: "Saving...",
|
||||
signupemail: "Sign up with email",
|
||||
signuptosave: "Sign up for Pocket. It’s free.",
|
||||
suggestedtags: "Suggested Tags",
|
||||
|
|
|
@ -1,11 +1,27 @@
|
|||
// Documentation of methods used here are at:
|
||||
// https://developer.mozilla.org/en-US/Add-ons/Code_snippets/Interaction_between_privileged_and_non-privileged_pages
|
||||
|
||||
var Messaging = (function() {
|
||||
var pktPanelMessaging = (function() {
|
||||
|
||||
function addMessageListener(messageId, callback) {
|
||||
function panelIdFromURL(url) {
|
||||
var panelId = url.match(/panelId=([\w|\d|\.]*)&?/);
|
||||
if (panelId && panelId.length > 1) {
|
||||
return panelId[1];
|
||||
}
|
||||
|
||||
document.addEventListener('PKT_' + messageId, function(e) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
function prefixedMessageId(messageId) {
|
||||
return 'PKT_' + messageId;
|
||||
}
|
||||
|
||||
function panelPrefixedMessageId(panelId, messageId) {
|
||||
return prefixedMessageId(panelId + '_' + messageId);
|
||||
}
|
||||
|
||||
function addMessageListener(panelId, messageId, callback) {
|
||||
document.addEventListener(panelPrefixedMessageId(panelId, messageId), function(e) {
|
||||
|
||||
callback(JSON.parse(e.target.getAttribute("payload"))[0]);
|
||||
|
||||
|
@ -16,33 +32,36 @@ var Messaging = (function() {
|
|||
|
||||
}
|
||||
|
||||
function removeMessageListener(messageId, callback) {
|
||||
|
||||
document.removeEventListener('PKT_' + messageId, callback);
|
||||
|
||||
function removeMessageListener(panelId, messageId, callback) {
|
||||
document.removeEventListener(panelPrefixedMessageId(panelId, messageId), callback);
|
||||
}
|
||||
|
||||
function sendMessage(messageId, payload, callback) {
|
||||
function sendMessage(panelId, messageId, payload, callback) {
|
||||
// Payload needs to be an object in format:
|
||||
// { panelId: panelId, data: {} }
|
||||
var messagePayload = {
|
||||
panelId: panelId,
|
||||
data: (payload || {})
|
||||
};
|
||||
|
||||
// Create a callback to listen for a response
|
||||
if (callback) {
|
||||
// Message response id is messageId + "Response"
|
||||
var messageResponseId = messageId + "Response";
|
||||
var responseListener = function(responsePayload) {
|
||||
callback(responsePayload);
|
||||
removeMessageListener(messageResponseId, responseListener);
|
||||
removeMessageListener(panelId, messageResponseId, responseListener);
|
||||
}
|
||||
|
||||
addMessageListener(messageResponseId, responseListener);
|
||||
addMessageListener(panelId, messageResponseId, responseListener);
|
||||
}
|
||||
|
||||
// Send message
|
||||
var element = document.createElement("PKTMessageFromPanelElement");
|
||||
element.setAttribute("payload", JSON.stringify([payload]));
|
||||
element.setAttribute("payload", JSON.stringify([messagePayload]));
|
||||
document.documentElement.appendChild(element);
|
||||
|
||||
var evt = document.createEvent("Events");
|
||||
evt.initEvent('PKT_'+messageId, true, false);
|
||||
evt.initEvent(prefixedMessageId(messageId), true, false);
|
||||
element.dispatchEvent(evt);
|
||||
}
|
||||
|
||||
|
@ -51,6 +70,7 @@ var Messaging = (function() {
|
|||
* Public functions
|
||||
*/
|
||||
return {
|
||||
panelIdFromURL: panelIdFromURL,
|
||||
addMessageListener : addMessageListener,
|
||||
removeMessageListener : removeMessageListener,
|
||||
sendMessage: sendMessage
|
||||
|
|
|
@ -11,6 +11,7 @@ var PKT_SAVED_OVERLAY = function (options)
|
|||
this.savedItemId = 0;
|
||||
this.savedUrl = '';
|
||||
this.premiumStatus = false;
|
||||
this.panelId = 0;
|
||||
this.preventCloseTimerCancel = false;
|
||||
this.closeValid = true;
|
||||
this.mouseInside = false;
|
||||
|
@ -33,14 +34,8 @@ var PKT_SAVED_OVERLAY = function (options)
|
|||
var newtag = $('<li><a href="#" class="token_tag ' + tagclass + '">' + tags[i] + '</a></li>');
|
||||
container.append(newtag);
|
||||
var templeft = newtag.position().left;
|
||||
if (templeft > newtagleft) {
|
||||
this.cxt_suggested_available++;
|
||||
newtagleft = templeft;
|
||||
}
|
||||
else {
|
||||
newtag.remove();
|
||||
break;
|
||||
}
|
||||
this.cxt_suggested_available++;
|
||||
newtagleft = templeft;
|
||||
}
|
||||
};
|
||||
this.fillUserTags = function() {
|
||||
|
@ -190,9 +185,6 @@ var PKT_SAVED_OVERLAY = function (options)
|
|||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
returnlist.push({name:'blah'});
|
||||
}
|
||||
if (!$('.token-input-dropdown-tag').data('init')) {
|
||||
$('.token-input-dropdown-tag').css('width',inputwrapper.outerWidth()).data('init');
|
||||
inputwrapper.append($('.token-input-dropdown-tag'));
|
||||
|
@ -202,7 +194,7 @@ var PKT_SAVED_OVERLAY = function (options)
|
|||
textToData: function(text) {
|
||||
if($.trim(text).length > 25 || !$.trim(text).length) {
|
||||
if (text.length > 25) {
|
||||
$('.pkt_ext_edit_msg').addClass('pkt_ext_edit_msg_error pkt_ext_edit_msg_active').text(myself.dictJSON.invalidTags);
|
||||
myself.showTagsError(myself.dictJSON.maxtaglength);
|
||||
changestamp = Date.now();
|
||||
setTimeout(function() {
|
||||
$('.token-input-input-token input').val(text).focus();
|
||||
|
@ -211,7 +203,7 @@ var PKT_SAVED_OVERLAY = function (options)
|
|||
return null;
|
||||
}
|
||||
else {
|
||||
$('.pkt_ext_edit_msg').removeClass('pkt_ext_edit_msg_error pkt_ext_edit_msg_active').text('');
|
||||
myself.hideTagsError();
|
||||
return {name:myself.sanitizeText(text.toLowerCase())};
|
||||
}
|
||||
},
|
||||
|
@ -258,6 +250,12 @@ var PKT_SAVED_OVERLAY = function (options)
|
|||
changestamp = Date.now();
|
||||
myself.showActiveTags();
|
||||
myself.checkPlaceholderStatus();
|
||||
},
|
||||
onShowDropdown: function() {
|
||||
thePKT_SAVED.sendMessage("expandSavePanel");
|
||||
},
|
||||
onHideDropdown: function() {
|
||||
thePKT_SAVED.sendMessage("collapseSavePanel");
|
||||
}
|
||||
});
|
||||
$('body').on('keydown',function(e) {
|
||||
|
@ -364,6 +362,14 @@ var PKT_SAVED_OVERLAY = function (options)
|
|||
myself.closePopup();
|
||||
});
|
||||
};
|
||||
this.showTagsError = function(msg) {
|
||||
$('.pkt_ext_edit_msg').addClass('pkt_ext_edit_msg_error pkt_ext_edit_msg_active').text(msg);
|
||||
$('.pkt_ext_tag_detail').addClass('pkt_ext_tag_error');
|
||||
};
|
||||
this.hideTagsError = function(msg) {
|
||||
$('.pkt_ext_edit_msg').removeClass('pkt_ext_edit_msg_error pkt_ext_edit_msg_active').text('');
|
||||
$('.pkt_ext_tag_detail').removeClass('pkt_ext_tag_error');
|
||||
};
|
||||
this.showActiveTags = function() {
|
||||
if (!$('.pkt_ext_suggestedtag_detail').length) {
|
||||
return;
|
||||
|
@ -567,6 +573,7 @@ PKT_SAVED_OVERLAY.prototype = {
|
|||
if (this.premiumStatus && !$('.pkt_ext_suggestedtag_detail').length)
|
||||
{
|
||||
$('body').append(Handlebars.templates.saved_premiumshell(this.dictJSON));
|
||||
$('.pkt_ext_initload').append(Handlebars.templates.saved_premiumextras(this.dictJSON));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
@ -586,11 +593,11 @@ PKT_SAVED.prototype = {
|
|||
},
|
||||
|
||||
addMessageListener: function(messageId, callback) {
|
||||
Messaging.addMessageListener(messageId, callback);
|
||||
pktPanelMessaging.addMessageListener(this.overlay.panelId, messageId, callback);
|
||||
},
|
||||
|
||||
sendMessage: function(messageId, payload, callback) {
|
||||
Messaging.sendMessage(messageId, payload, callback);
|
||||
pktPanelMessaging.sendMessage(this.overlay.panelId, messageId, payload, callback);
|
||||
},
|
||||
|
||||
create: function() {
|
||||
|
@ -605,6 +612,9 @@ PKT_SAVED.prototype = {
|
|||
{
|
||||
myself.overlay.pockethost = host[1];
|
||||
}
|
||||
|
||||
myself.overlay.panelId = pktPanelMessaging.panelIdFromURL(window.location.href);
|
||||
|
||||
myself.overlay.create();
|
||||
|
||||
// tell back end we're ready
|
||||
|
@ -614,7 +624,21 @@ PKT_SAVED.prototype = {
|
|||
thePKT_SAVED.addMessageListener("saveLink",function(resp)
|
||||
{
|
||||
if (resp.status == 'error') {
|
||||
myself.overlay.showStateError(myself.overlay.dictJSON.pagenotsaved,myself.overlay.dictJSON.onlylinkssaved);
|
||||
if (typeof resp.error == 'object')
|
||||
{
|
||||
if (resp.error.localizedKey)
|
||||
{
|
||||
myself.overlay.showStateError(myself.overlay.dictJSON.pagenotsaved,myself.overlay.dictJSON[resp.error.localizedKey]);
|
||||
}
|
||||
else
|
||||
{
|
||||
myself.overlay.showStateError(myself.overlay.dictJSON.pagenotsaved,resp.error.message);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
myself.overlay.showStateError(myself.overlay.dictJSON.pagenotsaved,myself.overlay.dictJSON.errorgeneric);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -22,6 +22,7 @@ var PKT_SIGNUP_OVERLAY = function (options)
|
|||
this.variant = "";
|
||||
this.pockethost = "getpocket.com";
|
||||
this.fxasignedin = false;
|
||||
this.panelId = 0;
|
||||
this.dictJSON = {};
|
||||
this.initCloseTabEvents = function() {
|
||||
$('.btn,.pkt_ext_learnmore,.alreadyhave > a').click(function(e)
|
||||
|
@ -162,6 +163,8 @@ PKT_SIGNUP_OVERLAY.prototype = {
|
|||
this.pockethost = host[1];
|
||||
}
|
||||
|
||||
this.panelId = pktPanelMessaging.panelIdFromURL(window.location.href);
|
||||
|
||||
if (this.active)
|
||||
{
|
||||
return;
|
||||
|
@ -207,11 +210,11 @@ PKT_SIGNUP.prototype = {
|
|||
},
|
||||
|
||||
addMessageListener: function(messageId, callback) {
|
||||
Messaging.addMessageListener(messageId, callback);
|
||||
pktPanelMessaging.addMessageListener(this.overlay.panelId, messageId, callback);
|
||||
},
|
||||
|
||||
sendMessage: function(messageId, payload, callback) {
|
||||
Messaging.sendMessage(messageId, payload, callback);
|
||||
pktPanelMessaging.sendMessage(this.overlay.panelId, messageId, payload, callback);
|
||||
},
|
||||
|
||||
create: function() {
|
||||
|
|
|
@ -1,5 +1,8 @@
|
|||
(function() {
|
||||
var template = Handlebars.template, templates = Handlebars.templates = Handlebars.templates || {};
|
||||
templates['saved_premiumextras'] = template({"compiler":[6,">= 2.0.0-beta.1"],"main":function(depth0,helpers,partials,data) {
|
||||
return "<div class=\"pkt_ext_suggestedtag_detailshown\">\n</div>";
|
||||
},"useData":true});
|
||||
templates['saved_premiumshell'] = template({"compiler":[6,">= 2.0.0-beta.1"],"main":function(depth0,helpers,partials,data) {
|
||||
var helper, functionType="function", helperMissing=helpers.helperMissing, escapeExpression=this.escapeExpression;
|
||||
return "<div class=\"pkt_ext_suggestedtag_detail pkt_ext_suggestedtag_detail_loading\">\n <h4>"
|
||||
|
@ -8,19 +11,21 @@ templates['saved_premiumshell'] = template({"compiler":[6,">= 2.0.0-beta.1"],"ma
|
|||
},"useData":true});
|
||||
templates['saved_shell'] = template({"compiler":[6,">= 2.0.0-beta.1"],"main":function(depth0,helpers,partials,data) {
|
||||
var helper, functionType="function", helperMissing=helpers.helperMissing, escapeExpression=this.escapeExpression;
|
||||
return "<div class=\"pkt_ext_initload\"> \n <div class=\"pkt_ext_loadingspinner\"><div></div></div>\n</div> \n<div class=\"pkt_ext_detail\"> \n <div class=\"pkt_ext_logo\"></div>\n <div class=\"pkt_ext_topdetail\">\n <h2>"
|
||||
return "<div class=\"pkt_ext_initload\">\n <div class=\"pkt_ext_logo\"></div> \n <div class=\"pkt_ext_topdetail\">\n <h2>"
|
||||
+ escapeExpression(((helper = (helper = helpers.saving || (depth0 != null ? depth0.saving : depth0)) != null ? helper : helperMissing),(typeof helper === functionType ? helper.call(depth0, {"name":"saving","hash":{},"data":data}) : helper)))
|
||||
+ "</h2>\n </div> \n <div class=\"pkt_ext_loadingspinner\"><div></div></div>\n</div> \n<div class=\"pkt_ext_detail\"> \n <div class=\"pkt_ext_logo\"></div>\n <div class=\"pkt_ext_topdetail\">\n <h2>"
|
||||
+ escapeExpression(((helper = (helper = helpers.pagesaved || (depth0 != null ? depth0.pagesaved : depth0)) != null ? helper : helperMissing),(typeof helper === functionType ? helper.call(depth0, {"name":"pagesaved","hash":{},"data":data}) : helper)))
|
||||
+ "</h2>\n <h3 class=\"pkt_ext_errordetail\"></h3>\n <nav class=\"pkt_ext_item_actions pkt_ext_cf\">\n <ul>\n <li><a class=\"pkt_ext_removeitem\" href=\"#\">"
|
||||
+ escapeExpression(((helper = (helper = helpers.removepage || (depth0 != null ? depth0.removepage : depth0)) != null ? helper : helperMissing),(typeof helper === functionType ? helper.call(depth0, {"name":"removepage","hash":{},"data":data}) : helper)))
|
||||
+ "</a></li>\n <li class=\"pkt_ext_actions_separator\"></li> \n <li><a class=\"pkt_ext_openpocket\" href=\"http://"
|
||||
+ "</a></li>\n <li class=\"pkt_ext_actions_separator\"></li> \n <li><a class=\"pkt_ext_openpocket\" href=\"https://"
|
||||
+ escapeExpression(((helper = (helper = helpers.pockethost || (depth0 != null ? depth0.pockethost : depth0)) != null ? helper : helperMissing),(typeof helper === functionType ? helper.call(depth0, {"name":"pockethost","hash":{},"data":data}) : helper)))
|
||||
+ "/a?src=ff_ext_saved\" target=\"_blank\">"
|
||||
+ escapeExpression(((helper = (helper = helpers.viewlist || (depth0 != null ? depth0.viewlist : depth0)) != null ? helper : helperMissing),(typeof helper === functionType ? helper.call(depth0, {"name":"viewlist","hash":{},"data":data}) : helper)))
|
||||
+ "</a></li>\n </ul>\n </nav> \n </div>\n <p class=\"pkt_ext_edit_msg\"></p> \n <div class=\"pkt_ext_tag_detail pkt_ext_cf\">\n <div class=\"pkt_ext_tag_input_wrapper\">\n <div class=\"pkt_ext_tag_input_blocker\"></div>\n <input class=\"pkt_ext_tag_input\" type=\"text\" placeholder=\""
|
||||
+ "</a></li>\n </ul>\n </nav> \n </div>\n <div class=\"pkt_ext_tag_detail pkt_ext_cf\">\n <div class=\"pkt_ext_tag_input_wrapper\">\n <div class=\"pkt_ext_tag_input_blocker\"></div>\n <input class=\"pkt_ext_tag_input\" type=\"text\" placeholder=\""
|
||||
+ escapeExpression(((helper = (helper = helpers.addtags || (depth0 != null ? depth0.addtags : depth0)) != null ? helper : helperMissing),(typeof helper === functionType ? helper.call(depth0, {"name":"addtags","hash":{},"data":data}) : helper)))
|
||||
+ "\">\n </div>\n <a href=\"#\" class=\"pkt_ext_btn pkt_ext_btn_disabled\">"
|
||||
+ escapeExpression(((helper = (helper = helpers.save || (depth0 != null ? depth0.save : depth0)) != null ? helper : helperMissing),(typeof helper === functionType ? helper.call(depth0, {"name":"save","hash":{},"data":data}) : helper)))
|
||||
+ "</a>\n </div>\n</div>";
|
||||
+ "</a>\n </div>\n <p class=\"pkt_ext_edit_msg\"></p> \n</div>";
|
||||
},"useData":true});
|
||||
templates['signup_shell'] = template({"1":function(depth0,helpers,partials,data) {
|
||||
var helper, functionType="function", helperMissing=helpers.helperMissing, escapeExpression=this.escapeExpression;
|
||||
|
|
|
@ -0,0 +1,2 @@
|
|||
<div class="pkt_ext_suggestedtag_detailshown">
|
||||
</div>
|
|
@ -1,4 +1,8 @@
|
|||
<div class="pkt_ext_initload">
|
||||
<div class="pkt_ext_initload">
|
||||
<div class="pkt_ext_logo"></div>
|
||||
<div class="pkt_ext_topdetail">
|
||||
<h2>{{saving}}</h2>
|
||||
</div>
|
||||
<div class="pkt_ext_loadingspinner"><div></div></div>
|
||||
</div>
|
||||
<div class="pkt_ext_detail">
|
||||
|
@ -10,11 +14,10 @@
|
|||
<ul>
|
||||
<li><a class="pkt_ext_removeitem" href="#">{{removepage}}</a></li>
|
||||
<li class="pkt_ext_actions_separator"></li>
|
||||
<li><a class="pkt_ext_openpocket" href="http://{{pockethost}}/a?src=ff_ext_saved" target="_blank">{{viewlist}}</a></li>
|
||||
<li><a class="pkt_ext_openpocket" href="https://{{pockethost}}/a?src=ff_ext_saved" target="_blank">{{viewlist}}</a></li>
|
||||
</ul>
|
||||
</nav>
|
||||
</div>
|
||||
<p class="pkt_ext_edit_msg"></p>
|
||||
<div class="pkt_ext_tag_detail pkt_ext_cf">
|
||||
<div class="pkt_ext_tag_input_wrapper">
|
||||
<div class="pkt_ext_tag_input_blocker"></div>
|
||||
|
@ -22,4 +25,5 @@
|
|||
</div>
|
||||
<a href="#" class="pkt_ext_btn pkt_ext_btn_disabled">{{save}}</a>
|
||||
</div>
|
||||
<p class="pkt_ext_edit_msg"></p>
|
||||
</div>
|
|
@ -223,8 +223,6 @@ var pktApi = (function() {
|
|||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: Better error handling
|
||||
if (options.error) {
|
||||
// In case the user did revoke the access token or it's not
|
||||
// valid anymore clear the user data
|
||||
|
@ -232,15 +230,10 @@ var pktApi = (function() {
|
|||
clearUserData();
|
||||
}
|
||||
|
||||
// Check to handle Pocket error
|
||||
var errorMessage = request.getResponseHeader("X-Error");
|
||||
if (typeof errorMessage !== "undefined") {
|
||||
options.error(new Error(errorMessage), request);
|
||||
return;
|
||||
}
|
||||
|
||||
// Handle other error
|
||||
options.error(new Error(request.statusText), request);
|
||||
// Handle error message
|
||||
var errorMessage = request.getResponseHeader("X-Error") || request.statusText;
|
||||
var error = {message: errorMessage};
|
||||
options.error(error, request);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
|
|
@ -254,7 +254,10 @@ Section "-InstallStartCleanup"
|
|||
${CleanUpdateDirectories} "Mozilla\Firefox" "Mozilla\updates"
|
||||
|
||||
${RemoveDeprecatedFiles}
|
||||
${RemovePrecompleteEntries} "false"
|
||||
|
||||
StrCpy $R2 "false"
|
||||
StrCpy $R3 "false"
|
||||
${RemovePrecompleteEntries} "$R2" "$R3"
|
||||
|
||||
${If} ${FileExists} "$INSTDIR\defaults\pref\channel-prefs.js"
|
||||
Delete "$INSTDIR\defaults\pref\channel-prefs.js"
|
||||
|
|
|
@ -71,8 +71,6 @@ Var CanSetAsDefault
|
|||
Var InstallCounterStep
|
||||
Var InstallStepSize
|
||||
Var InstallTotalSteps
|
||||
Var ProgressCompleted
|
||||
Var ProgressTotal
|
||||
Var TmpVal
|
||||
|
||||
Var ExitCode
|
||||
|
@ -260,7 +258,6 @@ Var ControlRightPX
|
|||
!insertmacro IsUserAdmin
|
||||
!insertmacro RemovePrecompleteEntries
|
||||
!insertmacro SetBrandNameVars
|
||||
!insertmacro ITBL3Create
|
||||
!insertmacro UnloadUAC
|
||||
|
||||
VIAddVersionKey "FileDescription" "${BrandShortName} Stub Installer"
|
||||
|
@ -1296,9 +1293,6 @@ Function createInstall
|
|||
StrCpy $InstallTotalSteps ${InstallCleanTotalSteps}
|
||||
${EndIf}
|
||||
|
||||
${ITBL3Create}
|
||||
${ITBL3SetProgressState} "${TBPF_INDETERMINATE}"
|
||||
|
||||
${NSD_CreateTimer} StartDownload ${DownloadIntervalMS}
|
||||
|
||||
LockWindow off
|
||||
|
@ -1321,21 +1315,6 @@ Function StartDownload
|
|||
${EndIf}
|
||||
FunctionEnd
|
||||
|
||||
Function SetProgressBars
|
||||
SendMessage $Progressbar ${PBM_SETPOS} $ProgressCompleted 0
|
||||
${ITBL3SetProgressValue} "$ProgressCompleted" "$ProgressTotal"
|
||||
FunctionEnd
|
||||
|
||||
Function RemoveFileProgressCallback
|
||||
IntOp $InstallCounterStep $InstallCounterStep + 2
|
||||
System::Int64Op $ProgressCompleted + $InstallStepSize
|
||||
Pop $ProgressCompleted
|
||||
Call SetProgressBars
|
||||
System::Int64Op $ProgressCompleted + $InstallStepSize
|
||||
Pop $ProgressCompleted
|
||||
Call SetProgressBars
|
||||
FunctionEnd
|
||||
|
||||
Function OnDownload
|
||||
InetBgDL::GetStats
|
||||
# $0 = HTTP status code, 0=Completed
|
||||
|
@ -1354,7 +1333,6 @@ Function OnDownload
|
|||
${NSD_AddStyle} $Progressbar ${PBS_MARQUEE}
|
||||
SendMessage $Progressbar ${PBM_SETMARQUEE} 1 \
|
||||
$ProgressbarMarqueeIntervalMS ; start=1|stop=0 interval(ms)=+N
|
||||
${ITBL3SetProgressState} "${TBPF_INDETERMINATE}"
|
||||
${EndIf}
|
||||
InetBgDL::Get /RESET /END
|
||||
StrCpy $DownloadSizeBytes ""
|
||||
|
@ -1412,9 +1390,8 @@ Function OnDownload
|
|||
SendMessage $Progressbar ${PBM_SETMARQUEE} 0 0 ; start=1|stop=0 interval(ms)=+N
|
||||
${RemoveStyle} $Progressbar ${PBS_MARQUEE}
|
||||
System::Int64Op $HalfOfDownload + $DownloadSizeBytes
|
||||
Pop $ProgressTotal
|
||||
StrCpy $ProgressCompleted 0
|
||||
SendMessage $Progressbar ${PBM_SETRANGE32} $ProgressCompleted $ProgressTotal
|
||||
Pop $R9
|
||||
SendMessage $Progressbar ${PBM_SETRANGE32} 0 $R9
|
||||
${EndIf}
|
||||
|
||||
; Don't update the status until after the download starts
|
||||
|
@ -1471,13 +1448,12 @@ Function OnDownload
|
|||
LockWindow on
|
||||
; Update the progress bars first in the UI change so they take affect
|
||||
; before other UI changes.
|
||||
StrCpy $ProgressCompleted "$DownloadSizeBytes"
|
||||
Call SetProgressBars
|
||||
SendMessage $Progressbar ${PBM_SETPOS} $DownloadSizeBytes 0
|
||||
System::Int64Op $InstallStepSize * ${InstallProgressFirstStep}
|
||||
Pop $R9
|
||||
System::Int64Op $ProgressCompleted + $R9
|
||||
Pop $ProgressCompleted
|
||||
Call SetProgressBars
|
||||
SendMessage $Progressbar ${PBM_SETSTEP} $R9 0
|
||||
SendMessage $Progressbar ${PBM_STEPIT} 0 0
|
||||
SendMessage $Progressbar ${PBM_SETSTEP} $InstallStepSize 0
|
||||
ShowWindow $LabelDownloading ${SW_HIDE}
|
||||
ShowWindow $LabelInstalling ${SW_SHOW}
|
||||
ShowWindow $LabelBlurb2 ${SW_HIDE}
|
||||
|
@ -1564,8 +1540,7 @@ Function OnDownload
|
|||
WriteIniStr "$0" "TASKBAR" "Migrated" "true"
|
||||
${EndIf}
|
||||
|
||||
GetFunctionAddress $0 RemoveFileProgressCallback
|
||||
${RemovePrecompleteEntries} $0
|
||||
${RemovePrecompleteEntries} $Progressbar $InstallCounterStep
|
||||
|
||||
; Delete the install.log and let the full installer create it. When the
|
||||
; installer closes it we can detect that it has completed.
|
||||
|
@ -1594,8 +1569,7 @@ Function OnDownload
|
|||
LockWindow off
|
||||
${EndIf}
|
||||
StrCpy $DownloadedBytes "$3"
|
||||
StrCpy $ProgressCompleted "$DownloadedBytes"
|
||||
Call SetProgressBars
|
||||
SendMessage $Progressbar ${PBM_SETPOS} $3 0
|
||||
${EndIf}
|
||||
${EndIf}
|
||||
FunctionEnd
|
||||
|
@ -1634,9 +1608,7 @@ Function CheckInstall
|
|||
Return
|
||||
${EndIf}
|
||||
|
||||
System::Int64Op $ProgressCompleted + $InstallStepSize
|
||||
Pop $ProgressCompleted
|
||||
Call SetProgressBars
|
||||
SendMessage $Progressbar ${PBM_STEPIT} 0 0
|
||||
|
||||
${If} ${FileExists} "$INSTDIR\install.log"
|
||||
Delete "$INSTDIR\install.tmp"
|
||||
|
@ -1660,6 +1632,7 @@ Function CheckInstall
|
|||
Pop $EndInstallPhaseTickCount
|
||||
System::Int64Op $InstallStepSize * ${InstallProgressFinishStep}
|
||||
Pop $InstallStepSize
|
||||
SendMessage $Progressbar ${PBM_SETSTEP} $InstallStepSize 0
|
||||
${NSD_CreateTimer} FinishInstall ${InstallIntervalMS}
|
||||
${EndUnless}
|
||||
${EndIf}
|
||||
|
@ -1674,16 +1647,14 @@ Function FinishInstall
|
|||
${EndIf}
|
||||
|
||||
${If} $InstallTotalSteps != $InstallCounterStep
|
||||
System::Int64Op $ProgressCompleted + $InstallStepSize
|
||||
Pop $ProgressCompleted
|
||||
Call SetProgressBars
|
||||
SendMessage $Progressbar ${PBM_STEPIT} 0 0
|
||||
Return
|
||||
${EndIf}
|
||||
|
||||
${NSD_KillTimer} FinishInstall
|
||||
|
||||
StrCpy $ProgressCompleted "$ProgressTotal"
|
||||
Call SetProgressBars
|
||||
SendMessage $Progressbar ${PBM_GETRANGE} 0 0 $R9
|
||||
SendMessage $Progressbar ${PBM_SETPOS} $R9 0
|
||||
|
||||
${If} "$CheckboxSetAsDefault" == "1"
|
||||
${GetParameters} $0
|
||||
|
@ -1964,10 +1935,6 @@ FunctionEnd
|
|||
|
||||
Function DisplayDownloadError
|
||||
${NSD_KillTimer} DisplayDownloadError
|
||||
; To better display the error state on the taskbar set the progress completed
|
||||
; value to the total value.
|
||||
${ITBL3SetProgressValue} "100" "100"
|
||||
${ITBL3SetProgressState} "${TBPF_ERROR}"
|
||||
MessageBox MB_OKCANCEL|MB_ICONSTOP "$(ERROR_DOWNLOAD)" IDCANCEL +2 IDOK +1
|
||||
StrCpy $OpenedDownloadPage "1" ; Already initialized to 0
|
||||
|
||||
|
|
|
@ -397,7 +397,9 @@ Section "Uninstall"
|
|||
${UnregisterDLL} "$INSTDIR\AccessibleMarshal.dll"
|
||||
${EndIf}
|
||||
|
||||
${un.RemovePrecompleteEntries} "false"
|
||||
StrCpy $R2 "false"
|
||||
StrCpy $R3 "false"
|
||||
${un.RemovePrecompleteEntries} "$R2" "$R3"
|
||||
|
||||
${If} ${FileExists} "$INSTDIR\defaults\pref\channel-prefs.js"
|
||||
Delete /REBOOTOK "$INSTDIR\defaults\pref\channel-prefs.js"
|
||||
|
|
|
@ -647,7 +647,7 @@ IsOnFullDomainWhitelist(nsIURI* aURI)
|
|||
NS_LITERAL_CSTRING("touch.qunar.com"),
|
||||
NS_LITERAL_CSTRING("mjs.sinaimg.cn"), // for sina.cn
|
||||
NS_LITERAL_CSTRING("static.qiyi.com"), // for m.iqiyi.com
|
||||
NS_LITERAL_CSTRING("www.kuaidi100.com"), // for m.kuaidi100.com
|
||||
NS_LITERAL_CSTRING("cdn.kuaidi100.com"), // for m.kuaidi100.com
|
||||
NS_LITERAL_CSTRING("m.pc6.com"),
|
||||
NS_LITERAL_CSTRING("m.haosou.com"),
|
||||
NS_LITERAL_CSTRING("m.mi.com"),
|
||||
|
|
|
@ -244,8 +244,9 @@ CPPOBJS = $(notdir $(addsuffix .$(OBJ_SUFFIX),$(basename $(CPPSRCS))))
|
|||
CMOBJS = $(notdir $(CMSRCS:.m=.$(OBJ_SUFFIX)))
|
||||
CMMOBJS = $(notdir $(CMMSRCS:.mm=.$(OBJ_SUFFIX)))
|
||||
ASOBJS = $(notdir $(ASFILES:.$(ASM_SUFFIX)=.$(OBJ_SUFFIX)))
|
||||
RSOBJS = $(addprefix lib,$(notdir $(RSSRCS:.rs=.$(LIB_SUFFIX))))
|
||||
ifndef OBJS
|
||||
_OBJS = $(COBJS) $(SOBJS) $(CPPOBJS) $(CMOBJS) $(CMMOBJS) $(ASOBJS)
|
||||
_OBJS = $(COBJS) $(SOBJS) $(CPPOBJS) $(CMOBJS) $(CMMOBJS) $(ASOBJS) $(RSOBJS)
|
||||
OBJS = $(strip $(_OBJS))
|
||||
endif
|
||||
|
||||
|
@ -876,6 +877,11 @@ $(basename $2$(notdir $1)).$(OBJ_SUFFIX): $1 $$(call mkdir_deps,$$(MDDEPDIR))
|
|||
endef
|
||||
$(foreach f,$(CSRCS) $(SSRCS) $(CPPSRCS) $(CMSRCS) $(CMMSRCS) $(ASFILES),$(eval $(call src_objdep,$(f))))
|
||||
$(foreach f,$(HOST_CSRCS) $(HOST_CPPSRCS) $(HOST_CMSRCS) $(HOST_CMMSRCS),$(eval $(call src_objdep,$(f),host_)))
|
||||
# The rust compiler only outputs library objects, and so we need different
|
||||
# mangling to generate dependency rules for it.
|
||||
mk_libname = $(basename lib$(notdir $1)).$(LIB_SUFFIX)
|
||||
src_libdep = $(call mk_libname,$1): $1 $$(call mkdir_deps,$$(MDDEPDIR))
|
||||
$(foreach f,$(RSSRCS),$(eval $(call src_libdep,$(f))))
|
||||
|
||||
$(OBJS) $(HOST_OBJS) $(PROGOBJS) $(HOST_PROGOBJS): $(GLOBAL_DEPS)
|
||||
|
||||
|
@ -924,6 +930,14 @@ $(ASOBJS):
|
|||
$(AS) $(ASOUTOPTION)$@ $(ASFLAGS) $($(notdir $<)_FLAGS) $(AS_DASH_C_FLAG) $(_VPATH_SRCS)
|
||||
endif
|
||||
|
||||
ifdef MOZ_RUST
|
||||
# Assume any system libraries rustc links against are already
|
||||
# in the target's LIBS.
|
||||
$(RSOBJS):
|
||||
$(REPORT_BUILD)
|
||||
$(RUSTC) --crate-type staticlib -o $(call mk_libname,$<) $(_VPATH_SRCS)
|
||||
endif
|
||||
|
||||
$(SOBJS):
|
||||
$(REPORT_BUILD)
|
||||
$(AS) -o $@ $(ASFLAGS) $($(notdir $<)_FLAGS) $(LOCAL_INCLUDES) $(TARGET_LOCAL_INCLUDES) -c $<
|
||||
|
|
12
configure.in
|
@ -429,6 +429,18 @@ MOZ_TOOL_VARIABLES
|
|||
|
||||
MOZ_CHECK_COMPILER_WRAPPER
|
||||
|
||||
MOZ_PATH_PROG(RUSTC, rustc)
|
||||
MOZ_ARG_ENABLE_BOOL([rust],
|
||||
[ --enable-rust Include rust language sources],
|
||||
[MOZ_RUST=1],
|
||||
[MOZ_RUST= ])
|
||||
if test -z "$RUSTC" -a -n "$MOZ_RUST"; then
|
||||
AC_MSG_ERROR([Rust compiler not found.
|
||||
To compile rust language sources, you must have 'rustc' in your path.
|
||||
See http://www.rust-lang.org/ for more information.])
|
||||
fi
|
||||
AC_SUBST(MOZ_RUST)
|
||||
|
||||
dnl ========================================================
|
||||
dnl Check for MacOS deployment target version
|
||||
dnl ========================================================
|
||||
|
|
|
@ -506,7 +506,7 @@ private:
|
|||
nsINode* oldTextNode = static_cast<Element*>(aData);
|
||||
Element* rootNode = aEntry->GetKey();
|
||||
nsINode* newTextNode = nullptr;
|
||||
if (oldTextNode && rootNode->HasDirAuto()) {
|
||||
if (rootNode->GetParentNode() && rootNode->HasDirAuto()) {
|
||||
newTextNode = WalkDescendantsSetDirectionFromText(rootNode, true,
|
||||
oldTextNode);
|
||||
}
|
||||
|
@ -533,11 +533,6 @@ public:
|
|||
mElements.EnumerateEntries(SetNodeDirection, &aDir);
|
||||
}
|
||||
|
||||
void ClearAutoDirection()
|
||||
{
|
||||
mElements.EnumerateEntries(ResetNodeDirection, nullptr);
|
||||
}
|
||||
|
||||
void ResetAutoDirection(nsINode* aTextNode)
|
||||
{
|
||||
mElements.EnumerateEntries(ResetNodeDirection, aTextNode);
|
||||
|
@ -574,13 +569,6 @@ public:
|
|||
GetDirectionalityMap(aTextNode)->UpdateAutoDirection(aDir);
|
||||
}
|
||||
|
||||
static void ClearTextNodeDirection(nsINode* aTextNode)
|
||||
{
|
||||
MOZ_ASSERT(aTextNode->HasTextNodeDirectionalityMap(),
|
||||
"Map missing in ResetTextNodeDirection");
|
||||
GetDirectionalityMap(aTextNode)->ClearAutoDirection();
|
||||
}
|
||||
|
||||
static void ResetTextNodeDirection(nsINode* aTextNode)
|
||||
{
|
||||
MOZ_ASSERT(aTextNode->HasTextNodeDirectionalityMap(),
|
||||
|
@ -888,7 +876,7 @@ SetDirectionFromNewTextNode(nsIContent* aTextNode)
|
|||
}
|
||||
|
||||
void
|
||||
ResetDirectionSetByTextNode(nsTextNode* aTextNode, bool aNullParent)
|
||||
ResetDirectionSetByTextNode(nsTextNode* aTextNode)
|
||||
{
|
||||
if (!NodeAffectsDirAutoAncestor(aTextNode)) {
|
||||
nsTextNodeDirectionalityMap::EnsureMapIsClearFor(aTextNode);
|
||||
|
@ -897,11 +885,7 @@ ResetDirectionSetByTextNode(nsTextNode* aTextNode, bool aNullParent)
|
|||
|
||||
Directionality dir = GetDirectionFromText(aTextNode->GetText());
|
||||
if (dir != eDir_NotSet && aTextNode->HasTextNodeDirectionalityMap()) {
|
||||
if (aNullParent) {
|
||||
nsTextNodeDirectionalityMap::ClearTextNodeDirection(aTextNode);
|
||||
} else {
|
||||
nsTextNodeDirectionalityMap::ResetTextNodeDirection(aTextNode);
|
||||
}
|
||||
nsTextNodeDirectionalityMap::ResetTextNodeDirection(aTextNode);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -103,10 +103,8 @@ void SetDirectionFromNewTextNode(nsIContent* aTextNode);
|
|||
* directionality it determined and redetermine their directionality
|
||||
*
|
||||
* @param aTextNode the text node
|
||||
* @param aNullParent whether the the parent is also being removed
|
||||
* (passed from UnbindFromTree)
|
||||
*/
|
||||
void ResetDirectionSetByTextNode(nsTextNode* aTextNode, bool aNullParent);
|
||||
void ResetDirectionSetByTextNode(nsTextNode* aTextNode);
|
||||
|
||||
/**
|
||||
* Set the directionality of an element according to the directionality of the
|
||||
|
|
|
@ -15,13 +15,13 @@
|
|||
#include "nsTArray.h"
|
||||
#include "mozilla/ErrorResult.h"
|
||||
#include "mozilla/dom/BindingDeclarations.h"
|
||||
#include "mozilla/dom/File.h"
|
||||
#include "mozilla/dom/FormDataBinding.h"
|
||||
|
||||
namespace mozilla {
|
||||
class ErrorResult;
|
||||
|
||||
namespace dom {
|
||||
class File;
|
||||
class HTMLFormElement;
|
||||
class GlobalObject;
|
||||
} // namespace dom
|
||||
|
|
|
@ -574,10 +574,7 @@ nsObjectLoadingContent::QueueCheckPluginStopEvent()
|
|||
nsCOMPtr<nsIRunnable> event = new CheckPluginStopEvent(this);
|
||||
mPendingCheckPluginStopEvent = event;
|
||||
|
||||
nsCOMPtr<nsIAppShell> appShell = do_GetService(kAppShellCID);
|
||||
if (appShell) {
|
||||
appShell->RunInStableState(event);
|
||||
}
|
||||
NS_DispatchToCurrentThread(event);
|
||||
}
|
||||
|
||||
// Tedious syntax to create a plugin stream listener with checks and put it in
|
||||
|
|
|
@ -400,7 +400,8 @@ NS_IMPL_CYCLE_COLLECTION_CLASS(nsPerformance)
|
|||
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(nsPerformance, DOMEventTargetHelper)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK(mWindow, mTiming,
|
||||
mNavigation, mEntries,
|
||||
mNavigation, mUserEntries,
|
||||
mResourceEntries,
|
||||
mParentPerformance)
|
||||
tmp->mMozMemory = nullptr;
|
||||
mozilla::DropJSObjects(this);
|
||||
|
@ -408,7 +409,8 @@ NS_IMPL_CYCLE_COLLECTION_UNLINK_END
|
|||
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(nsPerformance, DOMEventTargetHelper)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mWindow, mTiming,
|
||||
mNavigation, mEntries,
|
||||
mNavigation, mUserEntries,
|
||||
mResourceEntries,
|
||||
mParentPerformance)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_SCRIPT_OBJECTS
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||
|
@ -429,7 +431,7 @@ nsPerformance::nsPerformance(nsPIDOMWindow* aWindow,
|
|||
mDOMTiming(aDOMTiming),
|
||||
mChannel(aChannel),
|
||||
mParentPerformance(aParentPerformance),
|
||||
mPrimaryBufferSize(kDefaultBufferSize)
|
||||
mResourceTimingBufferSize(kDefaultResourceTimingBufferSize)
|
||||
{
|
||||
MOZ_ASSERT(aWindow, "Parent window object should be provided");
|
||||
}
|
||||
|
@ -509,24 +511,30 @@ nsPerformance::WrapObject(JSContext *cx, JS::Handle<JSObject*> aGivenProto)
|
|||
}
|
||||
|
||||
void
|
||||
nsPerformance::GetEntries(nsTArray<nsRefPtr<PerformanceEntry> >& retval)
|
||||
nsPerformance::GetEntries(nsTArray<nsRefPtr<PerformanceEntry>>& retval)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
retval = mEntries;
|
||||
retval = mResourceEntries;
|
||||
retval.AppendElements(mUserEntries);
|
||||
retval.Sort(PerformanceEntryComparator());
|
||||
}
|
||||
|
||||
void
|
||||
nsPerformance::GetEntriesByType(const nsAString& entryType,
|
||||
nsTArray<nsRefPtr<PerformanceEntry> >& retval)
|
||||
nsTArray<nsRefPtr<PerformanceEntry>>& retval)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
retval.Clear();
|
||||
uint32_t count = mEntries.Length();
|
||||
for (uint32_t i = 0 ; i < count; i++) {
|
||||
if (mEntries[i]->GetEntryType().Equals(entryType)) {
|
||||
retval.AppendElement(mEntries[i]);
|
||||
if (entryType.EqualsLiteral("resource")) {
|
||||
retval = mResourceEntries;
|
||||
} else if (entryType.EqualsLiteral("mark") ||
|
||||
entryType.EqualsLiteral("measure")) {
|
||||
for (PerformanceEntry* entry : mUserEntries) {
|
||||
if (entry->GetEntryType().Equals(entryType)) {
|
||||
retval.AppendElement(entry);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -534,31 +542,38 @@ nsPerformance::GetEntriesByType(const nsAString& entryType,
|
|||
void
|
||||
nsPerformance::GetEntriesByName(const nsAString& name,
|
||||
const Optional<nsAString>& entryType,
|
||||
nsTArray<nsRefPtr<PerformanceEntry> >& retval)
|
||||
nsTArray<nsRefPtr<PerformanceEntry>>& retval)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
|
||||
retval.Clear();
|
||||
uint32_t count = mEntries.Length();
|
||||
for (uint32_t i = 0 ; i < count; i++) {
|
||||
if (mEntries[i]->GetName().Equals(name) &&
|
||||
for (PerformanceEntry* entry : mResourceEntries) {
|
||||
if (entry->GetName().Equals(name) &&
|
||||
(!entryType.WasPassed() ||
|
||||
mEntries[i]->GetEntryType().Equals(entryType.Value()))) {
|
||||
retval.AppendElement(mEntries[i]);
|
||||
entry->GetEntryType().Equals(entryType.Value()))) {
|
||||
retval.AppendElement(entry);
|
||||
}
|
||||
}
|
||||
for (PerformanceEntry* entry : mUserEntries) {
|
||||
if (entry->GetName().Equals(name) &&
|
||||
(!entryType.WasPassed() ||
|
||||
entry->GetEntryType().Equals(entryType.Value()))) {
|
||||
retval.AppendElement(entry);
|
||||
}
|
||||
}
|
||||
retval.Sort(PerformanceEntryComparator());
|
||||
}
|
||||
|
||||
void
|
||||
nsPerformance::ClearEntries(const Optional<nsAString>& aEntryName,
|
||||
const nsAString& aEntryType)
|
||||
nsPerformance::ClearUserEntries(const Optional<nsAString>& aEntryName,
|
||||
const nsAString& aEntryType)
|
||||
{
|
||||
for (uint32_t i = 0; i < mEntries.Length();) {
|
||||
for (uint32_t i = 0; i < mUserEntries.Length();) {
|
||||
if ((!aEntryName.WasPassed() ||
|
||||
mEntries[i]->GetName().Equals(aEntryName.Value())) &&
|
||||
mUserEntries[i]->GetName().Equals(aEntryName.Value())) &&
|
||||
(aEntryType.IsEmpty() ||
|
||||
mEntries[i]->GetEntryType().Equals(aEntryType))) {
|
||||
mEntries.RemoveElementAt(i);
|
||||
mUserEntries[i]->GetEntryType().Equals(aEntryType))) {
|
||||
mUserEntries.RemoveElementAt(i);
|
||||
} else {
|
||||
++i;
|
||||
}
|
||||
|
@ -569,15 +584,14 @@ void
|
|||
nsPerformance::ClearResourceTimings()
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
ClearEntries(Optional<nsAString>(),
|
||||
NS_LITERAL_STRING("resource"));
|
||||
mResourceEntries.Clear();
|
||||
}
|
||||
|
||||
void
|
||||
nsPerformance::SetResourceTimingBufferSize(uint64_t maxSize)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
mPrimaryBufferSize = maxSize;
|
||||
mResourceTimingBufferSize = maxSize;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -595,7 +609,7 @@ nsPerformance::AddEntry(nsIHttpChannel* channel,
|
|||
}
|
||||
|
||||
// Don't add the entry if the buffer is full
|
||||
if (mEntries.Length() >= mPrimaryBufferSize) {
|
||||
if (mResourceEntries.Length() >= mResourceTimingBufferSize) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -634,7 +648,7 @@ nsPerformance::AddEntry(nsIHttpChannel* channel,
|
|||
initiatorType = NS_LITERAL_STRING("other");
|
||||
}
|
||||
performanceEntry->SetInitiatorType(initiatorType);
|
||||
InsertPerformanceEntry(performanceEntry, false);
|
||||
InsertResourceEntry(performanceEntry);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -659,16 +673,25 @@ nsPerformance::PerformanceEntryComparator::LessThan(
|
|||
}
|
||||
|
||||
void
|
||||
nsPerformance::InsertPerformanceEntry(PerformanceEntry* aEntry,
|
||||
bool aShouldPrint)
|
||||
nsPerformance::InsertResourceEntry(PerformanceEntry* aEntry)
|
||||
{
|
||||
MOZ_ASSERT(aEntry);
|
||||
MOZ_ASSERT(mEntries.Length() < mPrimaryBufferSize);
|
||||
if (mEntries.Length() == mPrimaryBufferSize) {
|
||||
NS_WARNING("Performance Entry buffer size maximum reached!");
|
||||
MOZ_ASSERT(mResourceEntries.Length() < mResourceTimingBufferSize);
|
||||
if (mResourceEntries.Length() >= mResourceTimingBufferSize) {
|
||||
return;
|
||||
}
|
||||
if (aShouldPrint && nsContentUtils::IsUserTimingLoggingEnabled()) {
|
||||
mResourceEntries.InsertElementSorted(aEntry,
|
||||
PerformanceEntryComparator());
|
||||
if (mResourceEntries.Length() == mResourceTimingBufferSize) {
|
||||
// call onresourcetimingbufferfull
|
||||
DispatchBufferFullEvent();
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
nsPerformance::InsertUserEntry(PerformanceEntry* aEntry)
|
||||
{
|
||||
if (nsContentUtils::IsUserTimingLoggingEnabled()) {
|
||||
nsAutoCString uri;
|
||||
nsresult rv = mWindow->GetDocumentURI()->GetHost(uri);
|
||||
if(NS_FAILED(rv)) {
|
||||
|
@ -683,21 +706,16 @@ nsPerformance::InsertPerformanceEntry(PerformanceEntry* aEntry,
|
|||
aEntry->Duration(),
|
||||
static_cast<uint64_t>(PR_Now() / PR_USEC_PER_MSEC));
|
||||
}
|
||||
mEntries.InsertElementSorted(aEntry,
|
||||
PerformanceEntryComparator());
|
||||
if (mEntries.Length() == mPrimaryBufferSize) {
|
||||
// call onresourcetimingbufferfull
|
||||
DispatchBufferFullEvent();
|
||||
}
|
||||
mUserEntries.InsertElementSorted(aEntry,
|
||||
PerformanceEntryComparator());
|
||||
}
|
||||
|
||||
void
|
||||
nsPerformance::Mark(const nsAString& aName, ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
// Don't add the entry if the buffer is full
|
||||
if (mEntries.Length() >= mPrimaryBufferSize) {
|
||||
NS_WARNING("Performance Entry buffer size maximum reached!");
|
||||
// Don't add the entry if the buffer is full. XXX should be removed by bug 1159003.
|
||||
if (mUserEntries.Length() >= mResourceTimingBufferSize) {
|
||||
return;
|
||||
}
|
||||
if (IsPerformanceTimingAttribute(aName)) {
|
||||
|
@ -706,14 +724,14 @@ nsPerformance::Mark(const nsAString& aName, ErrorResult& aRv)
|
|||
}
|
||||
nsRefPtr<PerformanceMark> performanceMark =
|
||||
new PerformanceMark(this, aName);
|
||||
InsertPerformanceEntry(performanceMark, true);
|
||||
InsertUserEntry(performanceMark);
|
||||
}
|
||||
|
||||
void
|
||||
nsPerformance::ClearMarks(const Optional<nsAString>& aName)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
ClearEntries(aName, NS_LITERAL_STRING("mark"));
|
||||
ClearUserEntries(aName, NS_LITERAL_STRING("mark"));
|
||||
}
|
||||
|
||||
DOMHighResTimeStamp
|
||||
|
@ -749,9 +767,8 @@ nsPerformance::Measure(const nsAString& aName,
|
|||
ErrorResult& aRv)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
// Don't add the entry if the buffer is full
|
||||
if (mEntries.Length() >= mPrimaryBufferSize) {
|
||||
NS_WARNING("Performance Entry buffer size maximum reached!");
|
||||
// Don't add the entry if the buffer is full. XXX should be removed by bug 1159003.
|
||||
if (mUserEntries.Length() >= mResourceTimingBufferSize) {
|
||||
return;
|
||||
}
|
||||
DOMHighResTimeStamp startTime;
|
||||
|
@ -783,14 +800,14 @@ nsPerformance::Measure(const nsAString& aName,
|
|||
}
|
||||
nsRefPtr<PerformanceMeasure> performanceMeasure =
|
||||
new PerformanceMeasure(this, aName, startTime, endTime);
|
||||
InsertPerformanceEntry(performanceMeasure, true);
|
||||
InsertUserEntry(performanceMeasure);
|
||||
}
|
||||
|
||||
void
|
||||
nsPerformance::ClearMeasures(const Optional<nsAString>& aName)
|
||||
{
|
||||
MOZ_ASSERT(NS_IsMainThread());
|
||||
ClearEntries(aName, NS_LITERAL_STRING("measure"));
|
||||
ClearUserEntries(aName, NS_LITERAL_STRING("measure"));
|
||||
}
|
||||
|
||||
DOMHighResTimeStamp
|
||||
|
|
|
@ -328,12 +328,12 @@ public:
|
|||
nsPerformanceTiming* Timing();
|
||||
nsPerformanceNavigation* Navigation();
|
||||
|
||||
void GetEntries(nsTArray<nsRefPtr<PerformanceEntry> >& retval);
|
||||
void GetEntries(nsTArray<nsRefPtr<PerformanceEntry>>& retval);
|
||||
void GetEntriesByType(const nsAString& entryType,
|
||||
nsTArray<nsRefPtr<PerformanceEntry> >& retval);
|
||||
nsTArray<nsRefPtr<PerformanceEntry>>& retval);
|
||||
void GetEntriesByName(const nsAString& name,
|
||||
const mozilla::dom::Optional< nsAString >& entryType,
|
||||
nsTArray<nsRefPtr<PerformanceEntry> >& retval);
|
||||
nsTArray<nsRefPtr<PerformanceEntry>>& retval);
|
||||
void AddEntry(nsIHttpChannel* channel,
|
||||
nsITimedChannel* timedChannel);
|
||||
void ClearResourceTimings();
|
||||
|
@ -357,20 +357,22 @@ private:
|
|||
DOMTimeMilliSec GetPerformanceTimingFromString(const nsAString& aTimingName);
|
||||
DOMHighResTimeStamp ConvertDOMMilliSecToHighRes(const DOMTimeMilliSec aTime);
|
||||
void DispatchBufferFullEvent();
|
||||
void InsertPerformanceEntry(PerformanceEntry* aEntry, bool aShouldPrint);
|
||||
void ClearEntries(const mozilla::dom::Optional<nsAString>& aEntryName,
|
||||
const nsAString& aEntryType);
|
||||
void InsertUserEntry(PerformanceEntry* aEntry);
|
||||
void ClearUserEntries(const mozilla::dom::Optional<nsAString>& aEntryName,
|
||||
const nsAString& aEntryType);
|
||||
void InsertResourceEntry(PerformanceEntry* aEntry);
|
||||
nsCOMPtr<nsPIDOMWindow> mWindow;
|
||||
nsRefPtr<nsDOMNavigationTiming> mDOMTiming;
|
||||
nsCOMPtr<nsITimedChannel> mChannel;
|
||||
nsRefPtr<nsPerformanceTiming> mTiming;
|
||||
nsRefPtr<nsPerformanceNavigation> mNavigation;
|
||||
nsTArray<nsRefPtr<PerformanceEntry> > mEntries;
|
||||
nsTArray<nsRefPtr<PerformanceEntry>> mResourceEntries;
|
||||
nsTArray<nsRefPtr<PerformanceEntry>> mUserEntries;
|
||||
nsRefPtr<nsPerformance> mParentPerformance;
|
||||
uint64_t mPrimaryBufferSize;
|
||||
uint64_t mResourceTimingBufferSize;
|
||||
JS::Heap<JSObject*> mMozMemory;
|
||||
|
||||
static const uint64_t kDefaultBufferSize = 150;
|
||||
static const uint64_t kDefaultResourceTimingBufferSize = 150;
|
||||
|
||||
// Helper classes
|
||||
class PerformanceEntryComparator {
|
||||
|
|
|
@ -150,7 +150,7 @@ nsTextNode::BindToTree(nsIDocument* aDocument, nsIContent* aParent,
|
|||
|
||||
void nsTextNode::UnbindFromTree(bool aDeep, bool aNullParent)
|
||||
{
|
||||
ResetDirectionSetByTextNode(this, aNullParent);
|
||||
ResetDirectionSetByTextNode(this);
|
||||
|
||||
nsGenericDOMDataNode::UnbindFromTree(aDeep, aNullParent);
|
||||
}
|
||||
|
|
|
@ -48,11 +48,12 @@ addLoadEvent(function() {
|
|||
|
||||
// Now flush out layout on the subdocument, to trigger the resize handler
|
||||
is(bod.getBoundingClientRect().width, 50, "Width of body should still be 50px");
|
||||
window.requestAnimationFrame(function() {
|
||||
is(resizeHandlerRan, true, "Resize handler should have run");
|
||||
win.removeEventListener("resize", handleResize, false);
|
||||
SimpleTest.finish();
|
||||
});
|
||||
|
||||
is(resizeHandlerRan, true, "Resize handler should have run");
|
||||
|
||||
win.removeEventListener("resize", handleResize, false);
|
||||
|
||||
SimpleTest.finish();
|
||||
});
|
||||
</script>
|
||||
</pre>
|
||||
|
|
|
@ -35,7 +35,7 @@ function setupTestMultipleEntries(headers) {
|
|||
return new Promise(function(resolve, reject) {
|
||||
var response, responseText, cache;
|
||||
Promise.all(headers.map(function(h) {
|
||||
return fetch(new Request(requestURL, {headers: h}));
|
||||
return fetch(requestURL, {headers: h});
|
||||
})).then(function(r) {
|
||||
response = r;
|
||||
return Promise.all(response.map(function(r) {
|
||||
|
@ -59,20 +59,20 @@ function setupTestMultipleEntries(headers) {
|
|||
|
||||
function testBasics() {
|
||||
var test;
|
||||
return setupTest({"WhatToVary": "Cookie"})
|
||||
return setupTest({"WhatToVary": "Custom"})
|
||||
.then(function(t) {
|
||||
test = t;
|
||||
// Ensure that searching without specifying a Cookie header succeeds.
|
||||
// Ensure that searching without specifying a Custom header succeeds.
|
||||
return test.cache.match(requestURL);
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
}).then(function() {
|
||||
// Ensure that searching with a non-matching value for the Cookie header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Cookie": "foo=bar"}}));
|
||||
// Ensure that searching with a non-matching value for the Custom header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom": "foo=bar"}}));
|
||||
}).then(function(r) {
|
||||
is(typeof r, "undefined", "Searching for a request with an unknown Vary header should not succeed");
|
||||
// Ensure that searching with a non-matching value for the Cookie header but with ignoreVary set succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Cookie": "foo=bar"}}),
|
||||
// Ensure that searching with a non-matching value for the Custom header but with ignoreVary set succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom": "foo=bar"}}),
|
||||
{ignoreVary: true});
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
|
@ -83,23 +83,23 @@ function testBasicKeys() {
|
|||
function checkRequest(reqs) {
|
||||
is(reqs.length, 1, "One request expected");
|
||||
ok(reqs[0].url.indexOf(requestURL) >= 0, "The correct request expected");
|
||||
ok(reqs[0].headers.get("WhatToVary"), "Cookie", "The correct request headers expected");
|
||||
ok(reqs[0].headers.get("WhatToVary"), "Custom", "The correct request headers expected");
|
||||
}
|
||||
var test;
|
||||
return setupTest({"WhatToVary": "Cookie"})
|
||||
return setupTest({"WhatToVary": "Custom"})
|
||||
.then(function(t) {
|
||||
test = t;
|
||||
// Ensure that searching without specifying a Cookie header succeeds.
|
||||
// Ensure that searching without specifying a Custom header succeeds.
|
||||
return test.cache.keys(requestURL);
|
||||
}).then(function(r) {
|
||||
return checkRequest(r);
|
||||
}).then(function() {
|
||||
// Ensure that searching with a non-matching value for the Cookie header fails.
|
||||
return test.cache.keys(new Request(requestURL, {headers: {"Cookie": "foo=bar"}}));
|
||||
// Ensure that searching with a non-matching value for the Custom header fails.
|
||||
return test.cache.keys(new Request(requestURL, {headers: {"Custom": "foo=bar"}}));
|
||||
}).then(function(r) {
|
||||
is(r.length, 0, "Searching for a request with an unknown Vary header should not succeed");
|
||||
// Ensure that searching with a non-matching value for the Cookie header but with ignoreVary set succeeds.
|
||||
return test.cache.keys(new Request(requestURL, {headers: {"Cookie": "foo=bar"}}),
|
||||
// Ensure that searching with a non-matching value for the Custom header but with ignoreVary set succeeds.
|
||||
return test.cache.keys(new Request(requestURL, {headers: {"Custom": "foo=bar"}}),
|
||||
{ignoreVary: true});
|
||||
}).then(function(r) {
|
||||
return checkRequest(r);
|
||||
|
@ -164,15 +164,15 @@ function testStar() {
|
|||
|
||||
function testMatch() {
|
||||
var test;
|
||||
return setupTest({"WhatToVary": "Cookie", "Cookie": "foo=bar"})
|
||||
return setupTest({"WhatToVary": "Custom", "Custom": "foo=bar"})
|
||||
.then(function(t) {
|
||||
test = t;
|
||||
// Ensure that searching with a different Cookie header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Cookie": "bar=baz"}}));
|
||||
// Ensure that searching with a different Custom header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom": "bar=baz"}}));
|
||||
}).then(function(r) {
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Cookie header should not succeed");
|
||||
// Ensure that searching with the same Cookie header succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Cookie": "foo=bar"}}));
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Custom header should not succeed");
|
||||
// Ensure that searching with the same Custom header succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom": "foo=bar"}}));
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
});
|
||||
|
@ -180,15 +180,15 @@ function testMatch() {
|
|||
|
||||
function testInvalidHeaderName() {
|
||||
var test;
|
||||
return setupTest({"WhatToVary": "Foo/Bar, User-Agent"})
|
||||
return setupTest({"WhatToVary": "Foo/Bar, Custom-User-Agent"})
|
||||
.then(function(t) {
|
||||
test = t;
|
||||
// Ensure that searching with a different User-Agent header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"User-Agent": "MyUA"}}));
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-User-Agent": "MyUA"}}));
|
||||
}).then(function(r) {
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching User-Agent header should not succeed");
|
||||
// Ensure that searching with a different User-Agent header but with ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"User-Agent": "MyUA"}}),
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Custom-User-Agent header should not succeed");
|
||||
// Ensure that searching with a different Custom-User-Agent header but with ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-User-Agent": "MyUA"}}),
|
||||
{ignoreVary: true});
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
|
@ -202,47 +202,47 @@ function testInvalidHeaderName() {
|
|||
|
||||
function testMultipleHeaders() {
|
||||
var test;
|
||||
return setupTest({"WhatToVary": "Referer,\tAccept-Encoding"})
|
||||
return setupTest({"WhatToVary": "Custom-Referer,\tCustom-Accept-Encoding"})
|
||||
.then(function(t) {
|
||||
test = t;
|
||||
// Ensure that searching with a different Referer header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Referer": "https://somesite.com/"}}));
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Referer": "https://somesite.com/"}}));
|
||||
}).then(function(r) {
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Referer header should not succeed");
|
||||
// Ensure that searching with a different Referer header but with ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Referer": "https://somesite.com/"}}),
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Custom-Referer header should not succeed");
|
||||
// Ensure that searching with a different Custom-Referer header but with ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Referer": "https://somesite.com/"}}),
|
||||
{ignoreVary: true});
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
}).then(function() {
|
||||
// Ensure that searching with a different Accept-Encoding header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Accept-Encoding": "myencoding"}}));
|
||||
// Ensure that searching with a different Custom-Accept-Encoding header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Accept-Encoding": "myencoding"}}));
|
||||
}).then(function(r) {
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Accept-Encoding header should not succeed");
|
||||
// Ensure that searching with a different Accept-Encoding header but with ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Accept-Encoding": "myencoding"}}),
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Custom-Accept-Encoding header should not succeed");
|
||||
// Ensure that searching with a different Custom-Accept-Encoding header but with ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Accept-Encoding": "myencoding"}}),
|
||||
{ignoreVary: true});
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
}).then(function() {
|
||||
// Ensure that searching with an empty Referer header succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Referer": ""}}));
|
||||
// Ensure that searching with an empty Custom-Referer header succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Referer": ""}}));
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
}).then(function() {
|
||||
// Ensure that searching with an empty Accept-Encoding header succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Accept-Encoding": ""}}));
|
||||
// Ensure that searching with an empty Custom-Accept-Encoding header succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Accept-Encoding": ""}}));
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
}).then(function() {
|
||||
// Ensure that searching with an empty Referer header but with a different Accept-Encoding header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Referer": "",
|
||||
"Accept-Encoding": "myencoding"}}));
|
||||
// Ensure that searching with an empty Custom-Referer header but with a different Custom-Accept-Encoding header fails.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Referer": "",
|
||||
"Custom-Accept-Encoding": "myencoding"}}));
|
||||
}).then(function(r) {
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Accept-Encoding header should not succeed");
|
||||
// Ensure that searching with an empty Referer header but with a different Accept-Encoding header and ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Referer": "",
|
||||
"Accept-Encoding": "myencoding"}}),
|
||||
is(typeof r, "undefined", "Searching for a request with a non-matching Custom-Accept-Encoding header should not succeed");
|
||||
// Ensure that searching with an empty Custom-Referer header but with a different Custom-Accept-Encoding header and ignoreVary succeeds.
|
||||
return test.cache.match(new Request(requestURL, {headers: {"Custom-Referer": "",
|
||||
"Custom-Accept-Encoding": "myencoding"}}),
|
||||
{ignoreVary: true});
|
||||
}).then(function(r) {
|
||||
return checkResponse(r, test.response, test.responseText);
|
||||
|
|
|
@ -13,30 +13,34 @@
|
|||
Cu.import('resource://gre/modules/Services.jsm');
|
||||
SimpleTest.waitForExplicitFinish();
|
||||
|
||||
// attach to a different origin's CacheStorage
|
||||
var url = 'http://example.com/';
|
||||
var uri = Services.io.newURI(url, null, null);
|
||||
var principal = Services.scriptSecurityManager.getNoAppCodebasePrincipal(uri);
|
||||
var storage = new CacheStorage('content', principal);
|
||||
SpecialPowers.pushPrefEnv({
|
||||
"set": [["dom.caches.enabled", true]],
|
||||
}, function() {
|
||||
// attach to a different origin's CacheStorage
|
||||
var url = 'http://example.com/';
|
||||
var uri = Services.io.newURI(url, null, null);
|
||||
var principal = Services.scriptSecurityManager.getNoAppCodebasePrincipal(uri);
|
||||
var storage = new CacheStorage('content', principal);
|
||||
|
||||
// verify we can use the other origin's CacheStorage as normal
|
||||
var req = new Request('http://example.com/index.html');
|
||||
var res = new Response('hello world');
|
||||
var cache;
|
||||
storage.open('foo').then(function(c) {
|
||||
cache = c;
|
||||
ok(cache, 'storage should create cache');
|
||||
return cache.put(req, res.clone());
|
||||
}).then(function() {
|
||||
return cache.match(req);
|
||||
}).then(function(foundResponse) {
|
||||
return Promise.all([res.text(), foundResponse.text()]);
|
||||
}).then(function(results) {
|
||||
is(results[0], results[1], 'cache should contain response');
|
||||
return storage.delete('foo');
|
||||
}).then(function(deleted) {
|
||||
ok(deleted, 'storage should delete cache');
|
||||
SimpleTest.finish();
|
||||
// verify we can use the other origin's CacheStorage as normal
|
||||
var req = new Request('http://example.com/index.html');
|
||||
var res = new Response('hello world');
|
||||
var cache;
|
||||
storage.open('foo').then(function(c) {
|
||||
cache = c;
|
||||
ok(cache, 'storage should create cache');
|
||||
return cache.put(req, res.clone());
|
||||
}).then(function() {
|
||||
return cache.match(req);
|
||||
}).then(function(foundResponse) {
|
||||
return Promise.all([res.text(), foundResponse.text()]);
|
||||
}).then(function(results) {
|
||||
is(results[0], results[1], 'cache should contain response');
|
||||
return storage.delete('foo');
|
||||
}).then(function(deleted) {
|
||||
ok(deleted, 'storage should delete cache');
|
||||
SimpleTest.finish();
|
||||
});
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
|
|
|
@ -1448,7 +1448,7 @@ nsDOMCameraControl::OnUserError(CameraControlListener::UserContext aContext, nsr
|
|||
break;
|
||||
|
||||
case CameraControlListener::kInSetConfiguration:
|
||||
if (mSetInitialConfig) {
|
||||
if (mSetInitialConfig && mCameraControl) {
|
||||
// If the SetConfiguration() call in the constructor fails, there
|
||||
// is nothing we can do except release the camera hardware. This
|
||||
// will trigger a hardware state change, and when the flag that
|
||||
|
|
|
@ -263,6 +263,10 @@ Request::Constructor(const GlobalObject& aGlobal,
|
|||
}
|
||||
|
||||
requestHeaders->Clear();
|
||||
// From "Let r be a new Request object associated with request and a new
|
||||
// Headers object whose guard is "request"."
|
||||
requestHeaders->SetGuard(HeadersGuardEnum::Request, aRv);
|
||||
MOZ_ASSERT(!aRv.Failed());
|
||||
|
||||
if (request->Mode() == RequestMode::No_cors) {
|
||||
if (!request->HasSimpleMethod()) {
|
||||
|
|
|
@ -878,7 +878,8 @@ void HTMLMediaElement::SelectResource()
|
|||
|
||||
mLoadingSrc = uri;
|
||||
UpdatePreloadAction();
|
||||
if (mPreloadAction == HTMLMediaElement::PRELOAD_NONE) {
|
||||
if (mPreloadAction == HTMLMediaElement::PRELOAD_NONE &&
|
||||
!IsMediaStreamURI(mLoadingSrc)) {
|
||||
// preload:none media, suspend the load here before we make any
|
||||
// network requests.
|
||||
SuspendLoad();
|
||||
|
@ -1016,7 +1017,8 @@ void HTMLMediaElement::LoadFromSourceChildren()
|
|||
NS_ASSERTION(mNetworkState == nsIDOMHTMLMediaElement::NETWORK_LOADING,
|
||||
"Network state should be loading");
|
||||
|
||||
if (mPreloadAction == HTMLMediaElement::PRELOAD_NONE) {
|
||||
if (mPreloadAction == HTMLMediaElement::PRELOAD_NONE &&
|
||||
!IsMediaStreamURI(mLoadingSrc)) {
|
||||
// preload:none media, suspend the load here before we make any
|
||||
// network requests.
|
||||
SuspendLoad();
|
||||
|
|
|
@ -9,11 +9,11 @@
|
|||
#include "mozilla/Attributes.h"
|
||||
#include "nsString.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIContent.h"
|
||||
|
||||
class nsIURI;
|
||||
class nsIInputStream;
|
||||
class nsGenericHTMLElement;
|
||||
class nsIContent;
|
||||
class nsISaveAsCharset;
|
||||
class nsIMultiplexInputStream;
|
||||
|
||||
|
|
|
@ -3,5 +3,6 @@
|
|||
"WeakMap.prototype.delete.length": true,
|
||||
"WeakMap.prototype.get.length": true,
|
||||
"WeakMap.prototype.has.length": true,
|
||||
"WeakMap.prototype.set.length": true
|
||||
"WeakMap.prototype.set.length": true,
|
||||
"WeakMap.prototype.@@toStringTag": true
|
||||
}
|
||||
|
|
|
@ -0,0 +1,109 @@
|
|||
/**
|
||||
* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/
|
||||
*/
|
||||
|
||||
var testGenerator = testSteps();
|
||||
|
||||
function testSteps()
|
||||
{
|
||||
const openParams = [
|
||||
// This one lives in storage/permanent/chrome
|
||||
{ dbName: "dbA",
|
||||
dbOptions: { version: 1, storage: "persistent" } },
|
||||
|
||||
// This one lives in storage/temporary/http+++localhost
|
||||
{ url: "http://localhost", dbName: "dbB",
|
||||
dbOptions: { version: 1, storage: "temporary" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+81
|
||||
{ url: "http://localhost:81", dbName: "dbC",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+82
|
||||
{ url: "http://localhost:82", dbName: "dbD",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+83
|
||||
{ url: "http://localhost:83", dbName: "dbE",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+84
|
||||
{ url: "http://localhost:84", dbName: "dbF",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+85
|
||||
{ url: "http://localhost:85", dbName: "dbG",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+86
|
||||
{ url: "http://localhost:86", dbName: "dbH",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+87
|
||||
{ url: "http://localhost:87", dbName: "dbI",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+88
|
||||
{ url: "http://localhost:88", dbName: "dbJ",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+89
|
||||
{ url: "http://localhost:89", dbName: "dbK",
|
||||
dbOptions: { version: 1, storage: "default" } },
|
||||
|
||||
// This one lives in storage/default/http+++localhost+90
|
||||
{ url: "http://localhost:90", dbName: "dbL",
|
||||
dbOptions: { version: 1, storage: "default" } }
|
||||
];
|
||||
|
||||
let ios = SpecialPowers.Cc["@mozilla.org/network/io-service;1"]
|
||||
.getService(SpecialPowers.Ci.nsIIOService);
|
||||
|
||||
let ssm = SpecialPowers.Cc["@mozilla.org/scriptsecuritymanager;1"]
|
||||
.getService(SpecialPowers.Ci.nsIScriptSecurityManager);
|
||||
|
||||
function openDatabase(params) {
|
||||
let request;
|
||||
if ("url" in params) {
|
||||
let uri = ios.newURI(params.url, null, null);
|
||||
let principal = ssm.getNoAppCodebasePrincipal(uri);
|
||||
request = indexedDB.openForPrincipal(principal, params.dbName,
|
||||
params.dbOptions);
|
||||
} else {
|
||||
request = indexedDB.open(params.dbName, params.dbOptions);
|
||||
}
|
||||
return request;
|
||||
}
|
||||
|
||||
clearAllDatabases(continueToNextStepSync);
|
||||
yield undefined;
|
||||
|
||||
installPackagedProfile("metadataRestore_profile");
|
||||
|
||||
for (let params of openParams) {
|
||||
let request = openDatabase(params);
|
||||
request.onerror = errorHandler;
|
||||
request.onupgradeneeded = unexpectedSuccessHandler;
|
||||
request.onsuccess = grabEventAndContinueHandler;
|
||||
let event = yield undefined;
|
||||
|
||||
is(event.type, "success", "Correct event type");
|
||||
}
|
||||
|
||||
resetAllDatabases(continueToNextStepSync);
|
||||
yield undefined;
|
||||
|
||||
for (let params of openParams) {
|
||||
let request = openDatabase(params);
|
||||
request.onerror = errorHandler;
|
||||
request.onupgradeneeded = unexpectedSuccessHandler;
|
||||
request.onsuccess = grabEventAndContinueHandler;
|
||||
let event = yield undefined;
|
||||
|
||||
is(event.type, "success", "Correct event type");
|
||||
}
|
||||
|
||||
finishTest();
|
||||
yield undefined;
|
||||
}
|
|
@ -15,6 +15,7 @@ support-files =
|
|||
GlobalObjectsComponent.manifest
|
||||
GlobalObjectsModule.jsm
|
||||
GlobalObjectsSandbox.js
|
||||
metadataRestore_profile.zip
|
||||
schema18upgrade_profile.zip
|
||||
xpcshell-shared.ini
|
||||
|
||||
|
@ -29,6 +30,7 @@ skip-if = toolkit == 'android'
|
|||
# disabled for the moment.
|
||||
skip-if = true
|
||||
[test_lowDiskSpace.js]
|
||||
[test_metadataRestore.js]
|
||||
[test_readwriteflush_disabled.js]
|
||||
[test_schema18upgrade.js]
|
||||
[test_temporary_storage.js]
|
||||
|
|
|
@ -424,7 +424,7 @@ public:
|
|||
|
||||
private:
|
||||
const uint32_t mGeneration;
|
||||
// Non-null if we haven't yet called EndChildReport() on it.
|
||||
// Non-null if we haven't yet called EndProcessReport() on it.
|
||||
nsRefPtr<nsMemoryReporterManager> mReporterManager;
|
||||
|
||||
ContentParent* Owner()
|
||||
|
@ -464,7 +464,7 @@ void
|
|||
MemoryReportRequestParent::ActorDestroy(ActorDestroyReason aWhy)
|
||||
{
|
||||
if (mReporterManager) {
|
||||
mReporterManager->EndChildReport(mGeneration, aWhy == Deletion);
|
||||
mReporterManager->EndProcessReport(mGeneration, aWhy == Deletion);
|
||||
mReporterManager = nullptr;
|
||||
}
|
||||
}
|
||||
|
@ -648,7 +648,6 @@ static const char* sObserverTopics[] = {
|
|||
"profile-before-change",
|
||||
NS_IPC_IOSERVICE_SET_OFFLINE_TOPIC,
|
||||
NS_IPC_IOSERVICE_SET_CONNECTIVITY_TOPIC,
|
||||
"child-memory-reporter-request",
|
||||
"memory-pressure",
|
||||
"child-gc-request",
|
||||
"child-cc-request",
|
||||
|
@ -1976,18 +1975,6 @@ ContentParent::ActorDestroy(ActorDestroyReason why)
|
|||
}
|
||||
}
|
||||
|
||||
// Tell the memory reporter manager that this ContentParent is going away.
|
||||
nsRefPtr<nsMemoryReporterManager> mgr =
|
||||
nsMemoryReporterManager::GetOrCreate();
|
||||
#ifdef MOZ_NUWA_PROCESS
|
||||
bool isMemoryChild = !IsNuwaProcess();
|
||||
#else
|
||||
bool isMemoryChild = true;
|
||||
#endif
|
||||
if (mgr && isMemoryChild) {
|
||||
mgr->DecrementNumChildProcesses();
|
||||
}
|
||||
|
||||
// remove the global remote preferences observers
|
||||
Preferences::RemoveObserver(this, "");
|
||||
|
||||
|
@ -2261,15 +2248,6 @@ ContentParent::ContentParent(mozIApplication* aApp,
|
|||
|
||||
IToplevelProtocol::SetTransport(mSubprocess->GetChannel());
|
||||
|
||||
if (!aIsNuwaProcess) {
|
||||
// Tell the memory reporter manager that this ContentParent exists.
|
||||
nsRefPtr<nsMemoryReporterManager> mgr =
|
||||
nsMemoryReporterManager::GetOrCreate();
|
||||
if (mgr) {
|
||||
mgr->IncrementNumChildProcesses();
|
||||
}
|
||||
}
|
||||
|
||||
std::vector<std::string> extraArgs;
|
||||
if (aIsNuwaProcess) {
|
||||
extraArgs.push_back("-nuwa");
|
||||
|
@ -2334,13 +2312,6 @@ ContentParent::ContentParent(ContentParent* aTemplate,
|
|||
aPid,
|
||||
*fd);
|
||||
|
||||
// Tell the memory reporter manager that this ContentParent exists.
|
||||
nsRefPtr<nsMemoryReporterManager> mgr =
|
||||
nsMemoryReporterManager::GetOrCreate();
|
||||
if (mgr) {
|
||||
mgr->IncrementNumChildProcesses();
|
||||
}
|
||||
|
||||
mSubprocess->LaunchAndWaitForProcessHandle();
|
||||
|
||||
// Clone actors routed by aTemplate for this instance.
|
||||
|
@ -3062,46 +3033,6 @@ ContentParent::Observe(nsISupports* aSubject,
|
|||
nsDependentString(aData)))
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
else if (!strcmp(aTopic, "child-memory-reporter-request")) {
|
||||
bool isNuwa = false;
|
||||
#ifdef MOZ_NUWA_PROCESS
|
||||
isNuwa = IsNuwaProcess();
|
||||
#endif
|
||||
if (!isNuwa) {
|
||||
unsigned generation;
|
||||
int anonymize, minimize, identOffset = -1;
|
||||
nsDependentString msg(aData);
|
||||
NS_ConvertUTF16toUTF8 cmsg(msg);
|
||||
|
||||
if (sscanf(cmsg.get(),
|
||||
"generation=%x anonymize=%d minimize=%d DMDident=%n",
|
||||
&generation, &anonymize, &minimize, &identOffset) < 3
|
||||
|| identOffset < 0) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
// The pre-%n part of the string should be all ASCII, so the byte
|
||||
// offset in identOffset should be correct as a char offset.
|
||||
MOZ_ASSERT(cmsg[identOffset - 1] == '=');
|
||||
MaybeFileDesc dmdFileDesc = void_t();
|
||||
#ifdef MOZ_DMD
|
||||
nsAutoString dmdIdent(Substring(msg, identOffset));
|
||||
if (!dmdIdent.IsEmpty()) {
|
||||
FILE *dmdFile = nullptr;
|
||||
nsresult rv = nsMemoryInfoDumper::OpenDMDFile(dmdIdent, Pid(), &dmdFile);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
// Proceed with the memory report as if DMD were disabled.
|
||||
dmdFile = nullptr;
|
||||
}
|
||||
if (dmdFile) {
|
||||
dmdFileDesc = FILEToFileDescriptor(dmdFile);
|
||||
fclose(dmdFile);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
unused << SendPMemoryReportRequestConstructor(
|
||||
generation, anonymize, minimize, dmdFileDesc);
|
||||
}
|
||||
}
|
||||
else if (!strcmp(aTopic, "child-gc-request")){
|
||||
unused << SendGarbageCollect();
|
||||
}
|
||||
|
|
|
@ -77,6 +77,8 @@
|
|||
#include "mozilla/WindowsVersion.h"
|
||||
#endif
|
||||
|
||||
#include <map>
|
||||
|
||||
// GetCurrentTime is defined in winbase.h as zero argument macro forwarding to
|
||||
// GetTickCount() and conflicts with MediaStream::GetCurrentTime.
|
||||
#ifdef GetCurrentTime
|
||||
|
@ -530,22 +532,31 @@ uint32_t
|
|||
VideoDevice::GetBestFitnessDistance(
|
||||
const nsTArray<const MediaTrackConstraintSet*>& aConstraintSets)
|
||||
{
|
||||
// TODO: Minimal kludge to fix plain and ideal facingMode regression, for
|
||||
// smooth landing and uplift. Proper cleanup is forthcoming (1037389).
|
||||
uint64_t distance = 0;
|
||||
|
||||
// Interrogate device-inherent properties first.
|
||||
for (size_t i = 0; i < aConstraintSets.Length(); i++) {
|
||||
auto& c = *aConstraintSets[i];
|
||||
if (!c.mFacingMode.IsConstrainDOMStringParameters() ||
|
||||
c.mFacingMode.GetAsConstrainDOMStringParameters().mIdeal.WasPassed() ||
|
||||
c.mFacingMode.GetAsConstrainDOMStringParameters().mExact.WasPassed()) {
|
||||
nsString deviceFacingMode;
|
||||
GetFacingMode(deviceFacingMode);
|
||||
if (c.mFacingMode.IsString()) {
|
||||
if (c.mFacingMode.GetAsString() != deviceFacingMode) {
|
||||
return UINT32_MAX;
|
||||
if (i == 0) {
|
||||
distance = 1000;
|
||||
}
|
||||
}
|
||||
} else if (c.mFacingMode.IsStringSequence()) {
|
||||
if (!c.mFacingMode.GetAsStringSequence().Contains(deviceFacingMode)) {
|
||||
return UINT32_MAX;
|
||||
if (i == 0) {
|
||||
distance = 1000;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
} else if (c.mFacingMode.GetAsConstrainDOMStringParameters().mExact.WasPassed()) {
|
||||
auto& exact = c.mFacingMode.GetAsConstrainDOMStringParameters().mExact.Value();
|
||||
if (exact.IsString()) {
|
||||
if (exact.GetAsString() != deviceFacingMode) {
|
||||
|
@ -554,6 +565,19 @@ VideoDevice::GetBestFitnessDistance(
|
|||
} else if (!exact.GetAsStringSequence().Contains(deviceFacingMode)) {
|
||||
return UINT32_MAX;
|
||||
}
|
||||
} else if (c.mFacingMode.GetAsConstrainDOMStringParameters().mIdeal.WasPassed()) {
|
||||
auto& ideal = c.mFacingMode.GetAsConstrainDOMStringParameters().mIdeal.Value();
|
||||
if (ideal.IsString()) {
|
||||
if (ideal.GetAsString() != deviceFacingMode) {
|
||||
if (i == 0) {
|
||||
distance = 1000;
|
||||
}
|
||||
}
|
||||
} else if (!ideal.GetAsStringSequence().Contains(deviceFacingMode)) {
|
||||
if (i == 0) {
|
||||
distance = 1000;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
nsString s;
|
||||
|
@ -563,7 +587,8 @@ VideoDevice::GetBestFitnessDistance(
|
|||
}
|
||||
}
|
||||
// Forward request to underlying object to interrogate per-mode capabilities.
|
||||
return GetSource()->GetBestFitnessDistance(aConstraintSets);
|
||||
distance += uint64_t(GetSource()->GetBestFitnessDistance(aConstraintSets));
|
||||
return uint32_t(std::min(distance, uint64_t(UINT32_MAX)));
|
||||
}
|
||||
|
||||
AudioDevice::AudioDevice(MediaEngineAudioSource* aSource)
|
||||
|
@ -1122,13 +1147,23 @@ static void
|
|||
nsTArray<const MediaTrackConstraintSet*> aggregateConstraints;
|
||||
aggregateConstraints.AppendElement(&c);
|
||||
|
||||
std::multimap<uint32_t, nsRefPtr<DeviceType>> ordered;
|
||||
|
||||
for (uint32_t i = 0; i < candidateSet.Length();) {
|
||||
if (candidateSet[i]->GetBestFitnessDistance(aggregateConstraints) == UINT32_MAX) {
|
||||
uint32_t distance = candidateSet[i]->GetBestFitnessDistance(aggregateConstraints);
|
||||
if (distance == UINT32_MAX) {
|
||||
candidateSet.RemoveElementAt(i);
|
||||
} else {
|
||||
ordered.insert(std::pair<uint32_t, nsRefPtr<DeviceType>>(distance,
|
||||
candidateSet[i]));
|
||||
++i;
|
||||
}
|
||||
}
|
||||
// Order devices by shortest distance
|
||||
for (auto& ordinal : ordered) {
|
||||
candidateSet.RemoveElement(ordinal.second);
|
||||
candidateSet.AppendElement(ordinal.second);
|
||||
}
|
||||
|
||||
// Then apply advanced constraints.
|
||||
|
||||
|
@ -1318,6 +1353,11 @@ public:
|
|||
{
|
||||
MOZ_ASSERT(mOnSuccess);
|
||||
MOZ_ASSERT(mOnFailure);
|
||||
|
||||
if (!IsOn(mConstraints.mVideo) && !IsOn(mConstraints.mAudio)) {
|
||||
Fail(NS_LITERAL_STRING("NotSupportedError"));
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
if (IsOn(mConstraints.mVideo)) {
|
||||
nsTArray<nsRefPtr<VideoDevice>> sources;
|
||||
GetSources(backend, GetInvariant(mConstraints.mVideo),
|
||||
|
@ -1343,6 +1383,11 @@ public:
|
|||
LOG(("Selected audio device"));
|
||||
}
|
||||
|
||||
if (!mAudioDevice && !mVideoDevice) {
|
||||
Fail(NS_LITERAL_STRING("NotFoundError"));
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
|
|
@ -27,6 +27,9 @@ BaseMediaMgrError::BaseMediaMgrError(const nsAString& aName,
|
|||
"accessed due to a hardware error (e.g. lock from another process).");
|
||||
} else if (mName.EqualsLiteral("InternalError")) {
|
||||
mMessage.AssignLiteral("Internal error.");
|
||||
} else if (mName.EqualsLiteral("NotSupportedError")) {
|
||||
mMessage.AssignLiteral("Constraints with no audio or video in it are not "
|
||||
"supported");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,8 @@
|
|||
#include <stdint.h>
|
||||
|
||||
extern "C" uint8_t* test_rust();
|
||||
|
||||
TEST(rust, CallFromCpp) {
|
||||
auto greeting = test_rust();
|
||||
EXPECT_STREQ(reinterpret_cast<char*>(greeting), "hello from rust.");
|
||||
}
|
|
@ -0,0 +1,6 @@
|
|||
#[no_mangle]
|
||||
pub extern fn test_rust() -> *const u8 {
|
||||
// NB: rust &str aren't null terminated.
|
||||
let greeting = "hello from rust.\0";
|
||||
greeting.as_ptr()
|
||||
}
|
|
@ -29,6 +29,11 @@ if CONFIG['MOZ_WEBM_ENCODER']:
|
|||
'TestWebMWriter.cpp',
|
||||
]
|
||||
|
||||
if CONFIG['MOZ_RUST']:
|
||||
SOURCES += ['hello.rs',]
|
||||
UNIFIED_SOURCES += ['TestRust.cpp',]
|
||||
|
||||
|
||||
TEST_HARNESS_FILES.gtest += [
|
||||
'../test/gizmo-frag.mp4',
|
||||
'../test/gizmo.mp4',
|
||||
|
|
|
@ -50,6 +50,9 @@ var tests = [
|
|||
{ message: "unknown mediaSource fails",
|
||||
constraints: { video: { mediaSource: 'uncle' } },
|
||||
error: "NotFoundError" },
|
||||
{ message: "emtpy constraint fails",
|
||||
constraints: { },
|
||||
error: "NotSupportedError" },
|
||||
{ message: "Success-path: optional video facingMode + audio ignoring facingMode",
|
||||
constraints: { fake: true,
|
||||
audio: { mediaSource: 'microphone',
|
||||
|
|
|
@ -84,28 +84,27 @@ MediaEngineCameraVideoSource::FitnessDistance(ValueType n,
|
|||
|
||||
// Binding code doesn't templatize well...
|
||||
|
||||
template<>
|
||||
/* static */ uint32_t
|
||||
/*static*/ uint32_t
|
||||
MediaEngineCameraVideoSource::FitnessDistance(int32_t n,
|
||||
const OwningLongOrConstrainLongRange& aConstraint)
|
||||
const OwningLongOrConstrainLongRange& aConstraint, bool aAdvanced)
|
||||
{
|
||||
if (aConstraint.IsLong()) {
|
||||
ConstrainLongRange range;
|
||||
range.mIdeal.Construct(aConstraint.GetAsLong());
|
||||
(aAdvanced ? range.mExact : range.mIdeal).Construct(aConstraint.GetAsLong());
|
||||
return FitnessDistance(n, range);
|
||||
} else {
|
||||
return FitnessDistance(n, aConstraint.GetAsConstrainLongRange());
|
||||
}
|
||||
}
|
||||
|
||||
template<>
|
||||
/* static */ uint32_t
|
||||
/*static*/ uint32_t
|
||||
MediaEngineCameraVideoSource::FitnessDistance(double n,
|
||||
const OwningDoubleOrConstrainDoubleRange& aConstraint)
|
||||
const OwningDoubleOrConstrainDoubleRange& aConstraint,
|
||||
bool aAdvanced)
|
||||
{
|
||||
if (aConstraint.IsDouble()) {
|
||||
ConstrainDoubleRange range;
|
||||
range.mIdeal.Construct(aConstraint.GetAsDouble());
|
||||
(aAdvanced ? range.mExact : range.mIdeal).Construct(aConstraint.GetAsDouble());
|
||||
return FitnessDistance(n, range);
|
||||
} else {
|
||||
return FitnessDistance(n, aConstraint.GetAsConstrainDoubleRange());
|
||||
|
@ -114,18 +113,22 @@ MediaEngineCameraVideoSource::FitnessDistance(double n,
|
|||
|
||||
/*static*/ uint32_t
|
||||
MediaEngineCameraVideoSource::GetFitnessDistance(const webrtc::CaptureCapability& aCandidate,
|
||||
const MediaTrackConstraintSet &aConstraints)
|
||||
const MediaTrackConstraintSet &aConstraints,
|
||||
bool aAdvanced)
|
||||
{
|
||||
// Treat width|height|frameRate == 0 on capability as "can do any".
|
||||
// This allows for orthogonal capabilities that are not in discrete steps.
|
||||
|
||||
uint64_t distance =
|
||||
uint64_t(aCandidate.width? FitnessDistance(int32_t(aCandidate.width),
|
||||
aConstraints.mWidth) : 0) +
|
||||
aConstraints.mWidth,
|
||||
aAdvanced) : 0) +
|
||||
uint64_t(aCandidate.height? FitnessDistance(int32_t(aCandidate.height),
|
||||
aConstraints.mHeight) : 0) +
|
||||
aConstraints.mHeight,
|
||||
aAdvanced) : 0) +
|
||||
uint64_t(aCandidate.maxFPS? FitnessDistance(double(aCandidate.maxFPS),
|
||||
aConstraints.mFrameRate) : 0);
|
||||
aConstraints.mFrameRate,
|
||||
aAdvanced) : 0);
|
||||
return uint32_t(std::min(distance, uint64_t(UINT32_MAX)));
|
||||
}
|
||||
|
||||
|
@ -152,6 +155,8 @@ MediaEngineCameraVideoSource::TrimLessFitCandidates(CapabilitySet& set) {
|
|||
// GetBestFitnessDistance returns the best distance the capture device can offer
|
||||
// as a whole, given an accumulated number of ConstraintSets.
|
||||
// Ideal values are considered in the first ConstraintSet only.
|
||||
// Plain values are treated as Ideal in the first ConstraintSet.
|
||||
// Plain values are treated as Exact in subsequent ConstraintSets.
|
||||
// Infinity = UINT32_MAX e.g. device cannot satisfy accumulated ConstraintSets.
|
||||
// A finite result may be used to calculate this device's ranking as a choice.
|
||||
|
||||
|
@ -172,7 +177,7 @@ MediaEngineCameraVideoSource::GetBestFitnessDistance(
|
|||
auto& candidate = candidateSet[i];
|
||||
webrtc::CaptureCapability cap;
|
||||
GetCapability(candidate.mIndex, cap);
|
||||
uint32_t distance = GetFitnessDistance(cap, *cs);
|
||||
uint32_t distance = GetFitnessDistance(cap, *cs, !first);
|
||||
if (distance == UINT32_MAX) {
|
||||
candidateSet.RemoveElementAt(i);
|
||||
} else {
|
||||
|
@ -246,7 +251,7 @@ MediaEngineCameraVideoSource::ChooseCapability(
|
|||
auto& candidate = candidateSet[i];
|
||||
webrtc::CaptureCapability cap;
|
||||
GetCapability(candidate.mIndex, cap);
|
||||
candidate.mDistance = GetFitnessDistance(cap, aConstraints);
|
||||
candidate.mDistance = GetFitnessDistance(cap, aConstraints, false);
|
||||
if (candidate.mDistance == UINT32_MAX) {
|
||||
candidateSet.RemoveElementAt(i);
|
||||
} else {
|
||||
|
@ -263,7 +268,7 @@ MediaEngineCameraVideoSource::ChooseCapability(
|
|||
auto& candidate = candidateSet[i];
|
||||
webrtc::CaptureCapability cap;
|
||||
GetCapability(candidate.mIndex, cap);
|
||||
if (GetFitnessDistance(cap, cs) == UINT32_MAX) {
|
||||
if (GetFitnessDistance(cap, cs, true) == UINT32_MAX) {
|
||||
rejects.AppendElement(candidate);
|
||||
candidateSet.RemoveElementAt(i);
|
||||
} else {
|
||||
|
@ -295,7 +300,7 @@ MediaEngineCameraVideoSource::ChooseCapability(
|
|||
for (auto& candidate : candidateSet) {
|
||||
webrtc::CaptureCapability cap;
|
||||
GetCapability(candidate.mIndex, cap);
|
||||
candidate.mDistance = GetFitnessDistance(cap, prefs);
|
||||
candidate.mDistance = GetFitnessDistance(cap, prefs, false);
|
||||
}
|
||||
TrimLessFitCandidates(candidateSet);
|
||||
}
|
||||
|
|
|
@ -80,8 +80,14 @@ protected:
|
|||
StreamTime delta);
|
||||
template<class ValueType, class ConstrainRange>
|
||||
static uint32_t FitnessDistance(ValueType n, const ConstrainRange& aRange);
|
||||
static uint32_t FitnessDistance(int32_t n,
|
||||
const dom::OwningLongOrConstrainLongRange& aConstraint, bool aAdvanced);
|
||||
static uint32_t FitnessDistance(double n,
|
||||
const dom::OwningDoubleOrConstrainDoubleRange& aConstraint, bool aAdvanced);
|
||||
|
||||
static uint32_t GetFitnessDistance(const webrtc::CaptureCapability& aCandidate,
|
||||
const dom::MediaTrackConstraintSet &aConstraints);
|
||||
const dom::MediaTrackConstraintSet &aConstraints,
|
||||
bool aAdvanced);
|
||||
static void TrimLessFitCandidates(CapabilitySet& set);
|
||||
static void LogConstraints(const dom::MediaTrackConstraintSet& aConstraints,
|
||||
bool aAdvanced);
|
||||
|
|
|
@ -37,13 +37,23 @@ i.addEventListener("load", function loadfunc() {
|
|||
// Navigate the frame to cause the document with the plugin to go inactive
|
||||
i.removeEventListener("load", loadfunc);
|
||||
i.src = "about:blank";
|
||||
SimpleTest.executeSoon(function() {
|
||||
// Ensure this event doesn't race with CheckPluginStopEvent
|
||||
SimpleTest.executeSoon(function() {
|
||||
|
||||
const MAX_ATTEMPTS = 5;
|
||||
var attempts = 0;
|
||||
function checkPluginDestroyRan() {
|
||||
// We may need to retry a few times until the plugin stop event makes
|
||||
// its way through the event queue.
|
||||
if (attempts < MAX_ATTEMPTS && !destroyran) {
|
||||
++attempts;
|
||||
SimpleTest.executeSoon(checkPluginDestroyRan);
|
||||
} else {
|
||||
info("Number of retry attempts: " + attempts);
|
||||
ok(destroyran, "OnDestroy callback ran and did not crash");
|
||||
SimpleTest.finish();
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
SimpleTest.executeSoon(checkPluginDestroyRan);
|
||||
});
|
||||
document.body.appendChild(i);
|
||||
|
||||
|
|
|
@ -12,14 +12,24 @@
|
|||
SimpleTest.waitForExplicitFinish();
|
||||
setTestPluginEnabledState(SpecialPowers.Ci.nsIPluginTag.STATE_ENABLED);
|
||||
|
||||
const MAX_ATTEMPTS = 5;
|
||||
var attempts = 0;
|
||||
var destroyed = false;
|
||||
function onDestroy() {
|
||||
destroyed = true;
|
||||
}
|
||||
|
||||
function checkPluginAlreadyDestroyed() {
|
||||
is(destroyed, true, "Plugin instance should have been destroyed.");
|
||||
SimpleTest.finish();
|
||||
// We may need to retry a few times until the plugin stop event makes
|
||||
// its way through the event queue.
|
||||
if (attempts < MAX_ATTEMPTS && !destroyed) {
|
||||
++attempts;
|
||||
SimpleTest.executeSoon(checkPluginAlreadyDestroyed);
|
||||
} else {
|
||||
info("Number of retry attempts: " + attempts);
|
||||
is(destroyed, true, "Plugin instance should have been destroyed.");
|
||||
SimpleTest.finish();
|
||||
}
|
||||
}
|
||||
|
||||
function startTest() {
|
||||
|
@ -27,10 +37,8 @@
|
|||
var d1 = document.getElementById('div1');
|
||||
|
||||
p1.callOnDestroy(onDestroy);
|
||||
|
||||
setTimeout(checkPluginAlreadyDestroyed, 0);
|
||||
|
||||
d1.removeChild(p1);
|
||||
SimpleTest.executeSoon(checkPluginAlreadyDestroyed);
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
@ -12,14 +12,24 @@
|
|||
SimpleTest.waitForExplicitFinish();
|
||||
setTestPluginEnabledState(SpecialPowers.Ci.nsIPluginTag.STATE_ENABLED);
|
||||
|
||||
const MAX_ATTEMPTS = 5;
|
||||
var attempts = 0;
|
||||
var destroyed = false;
|
||||
function onDestroy() {
|
||||
destroyed = true;
|
||||
}
|
||||
|
||||
function checkPluginAlreadyDestroyed() {
|
||||
is(destroyed, true, "Plugin instance should have been destroyed.");
|
||||
SimpleTest.finish();
|
||||
// We may need to retry a few times until the plugin stop event makes
|
||||
// its way through the event queue.
|
||||
if (attempts < MAX_ATTEMPTS && !destroyed) {
|
||||
++attempts;
|
||||
SimpleTest.executeSoon(checkPluginAlreadyDestroyed);
|
||||
} else {
|
||||
info("Number of retry attempts: " + attempts);
|
||||
is(destroyed, true, "Plugin instance should have been destroyed.");
|
||||
SimpleTest.finish();
|
||||
}
|
||||
}
|
||||
|
||||
function startTest() {
|
||||
|
@ -28,12 +38,12 @@
|
|||
|
||||
p1.callOnDestroy(onDestroy);
|
||||
|
||||
setTimeout(checkPluginAlreadyDestroyed, 0);
|
||||
|
||||
// Get two parent check events to run.
|
||||
d1.removeChild(p1);
|
||||
d1.appendChild(p1);
|
||||
d1.removeChild(p1);
|
||||
|
||||
SimpleTest.executeSoon(checkPluginAlreadyDestroyed);
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
@ -12,14 +12,24 @@
|
|||
SimpleTest.waitForExplicitFinish();
|
||||
setTestPluginEnabledState(SpecialPowers.Ci.nsIPluginTag.STATE_ENABLED);
|
||||
|
||||
const MAX_ATTEMPTS = 5;
|
||||
var attempts = 0;
|
||||
var destroyed = false;
|
||||
function onDestroy() {
|
||||
destroyed = true;
|
||||
}
|
||||
|
||||
function checkPluginAlreadyDestroyed() {
|
||||
is(destroyed, true, "Plugin instance should have been destroyed.");
|
||||
SimpleTest.finish();
|
||||
// We may need to retry a few times until the plugin stop event makes
|
||||
// its way through the event queue.
|
||||
if (attempts < MAX_ATTEMPTS && !destroyed) {
|
||||
++attempts;
|
||||
SimpleTest.executeSoon(checkPluginAlreadyDestroyed);
|
||||
} else {
|
||||
info("Number of retry attempts: " + attempts);
|
||||
is(destroyed, true, "Plugin instance should have been destroyed.");
|
||||
SimpleTest.finish();
|
||||
}
|
||||
}
|
||||
|
||||
function startTest() {
|
||||
|
@ -28,10 +38,8 @@
|
|||
var d2 = document.getElementById('div2');
|
||||
|
||||
p1.callOnDestroy(onDestroy);
|
||||
|
||||
setTimeout(checkPluginAlreadyDestroyed, 0);
|
||||
|
||||
d1.removeChild(d2);
|
||||
SimpleTest.executeSoon(checkPluginAlreadyDestroyed);
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
|
@ -573,7 +573,8 @@ class StorageDirectoryHelper final
|
|||
mozilla::Mutex mMutex;
|
||||
mozilla::CondVar mCondVar;
|
||||
nsresult mMainThreadResultCode;
|
||||
bool mPersistent;
|
||||
const bool mPersistent;
|
||||
bool mCreate;
|
||||
bool mWaiting;
|
||||
|
||||
public:
|
||||
|
@ -584,18 +585,28 @@ public:
|
|||
, mCondVar(mMutex, "StorageDirectoryHelper::mCondVar")
|
||||
, mMainThreadResultCode(NS_OK)
|
||||
, mPersistent(aPersistent)
|
||||
, mCreate(true)
|
||||
, mWaiting(true)
|
||||
{
|
||||
AssertIsOnIOThread();
|
||||
}
|
||||
|
||||
nsresult
|
||||
CreateOrUpgradeMetadataFiles();
|
||||
CreateOrUpgradeMetadataFiles(bool aCreate);
|
||||
|
||||
nsresult
|
||||
RestoreMetadataFile();
|
||||
|
||||
private:
|
||||
~StorageDirectoryHelper()
|
||||
{ }
|
||||
|
||||
nsresult
|
||||
AddOriginDirectory(nsIFile* aDirectory);
|
||||
|
||||
nsresult
|
||||
ProcessOriginDirectories(bool aMove);
|
||||
|
||||
nsresult
|
||||
RunOnMainThread();
|
||||
|
||||
|
@ -1050,6 +1061,20 @@ CreateDirectoryMetadata(nsIFile* aDirectory, int64_t aTimestamp,
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
RestoreDirectoryMetadata(nsIFile* aDirectory, bool aPersistent)
|
||||
{
|
||||
nsRefPtr<StorageDirectoryHelper> helper =
|
||||
new StorageDirectoryHelper(aDirectory, aPersistent);
|
||||
|
||||
nsresult rv = helper->RestoreMetadataFile();
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
GetDirectoryMetadataInputStream(nsIFile* aDirectory,
|
||||
nsIBinaryInputStream** aStream)
|
||||
|
@ -1129,6 +1154,83 @@ GetDirectoryMetadata(nsIFile* aDirectory,
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
GetDirectoryMetadataWithRestore(nsIFile* aDirectory,
|
||||
bool aPersistent,
|
||||
int64_t* aTimestamp,
|
||||
nsACString& aGroup,
|
||||
nsACString& aOrigin,
|
||||
bool* aIsApp)
|
||||
{
|
||||
nsresult rv = GetDirectoryMetadata(aDirectory,
|
||||
aTimestamp,
|
||||
aGroup,
|
||||
aOrigin,
|
||||
aIsApp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
rv = RestoreDirectoryMetadata(aDirectory, aPersistent);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = GetDirectoryMetadata(aDirectory,
|
||||
aTimestamp,
|
||||
aGroup,
|
||||
aOrigin,
|
||||
aIsApp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
GetDirectoryMetadata(nsIFile* aDirectory, int64_t* aTimestamp)
|
||||
{
|
||||
AssertIsOnIOThread();
|
||||
MOZ_ASSERT(aDirectory);
|
||||
MOZ_ASSERT(aTimestamp);
|
||||
|
||||
nsCOMPtr<nsIBinaryInputStream> binaryStream;
|
||||
nsresult rv =
|
||||
GetDirectoryMetadataInputStream(aDirectory, getter_AddRefs(binaryStream));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
uint64_t timestamp;
|
||||
rv = binaryStream->Read64(×tamp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
*aTimestamp = timestamp;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
GetDirectoryMetadataWithRestore(nsIFile* aDirectory,
|
||||
bool aPersistent,
|
||||
int64_t* aTimestamp)
|
||||
{
|
||||
nsresult rv = GetDirectoryMetadata(aDirectory, aTimestamp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
rv = RestoreDirectoryMetadata(aDirectory, aPersistent);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = GetDirectoryMetadata(aDirectory, aTimestamp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
MaybeUpgradeOriginDirectory(nsIFile* aDirectory)
|
||||
{
|
||||
|
@ -1822,6 +1924,9 @@ QuotaManager::GetDirectoryForOrigin(PersistenceType aPersistenceType,
|
|||
nsresult
|
||||
QuotaManager::InitializeRepository(PersistenceType aPersistenceType)
|
||||
{
|
||||
MOZ_ASSERT(aPersistenceType == PERSISTENCE_TYPE_TEMPORARY ||
|
||||
aPersistenceType == PERSISTENCE_TYPE_DEFAULT);
|
||||
|
||||
nsresult rv;
|
||||
|
||||
nsCOMPtr<nsIFile> directory =
|
||||
|
@ -1885,8 +1990,12 @@ QuotaManager::InitializeRepository(PersistenceType aPersistenceType)
|
|||
nsCString group;
|
||||
nsCString origin;
|
||||
bool isApp;
|
||||
rv = GetDirectoryMetadata(childDirectory, ×tamp, group, origin,
|
||||
&isApp);
|
||||
rv = GetDirectoryMetadataWithRestore(childDirectory,
|
||||
/* aPersistent */ false,
|
||||
×tamp,
|
||||
group,
|
||||
origin,
|
||||
&isApp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
@ -2123,7 +2232,7 @@ QuotaManager::MaybeUpgradePersistentStorageDirectory()
|
|||
nsRefPtr<StorageDirectoryHelper> helper =
|
||||
new StorageDirectoryHelper(persistentStorageDir, /* aPersistent */ true);
|
||||
|
||||
rv = helper->CreateOrUpgradeMetadataFiles();
|
||||
rv = helper->CreateOrUpgradeMetadataFiles(/* aCreate */ true);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
@ -2159,7 +2268,7 @@ QuotaManager::MaybeUpgradePersistentStorageDirectory()
|
|||
helper = new StorageDirectoryHelper(temporaryStorageDir,
|
||||
/* aPersistent */ false);
|
||||
|
||||
rv = helper->CreateOrUpgradeMetadataFiles();
|
||||
rv = helper->CreateOrUpgradeMetadataFiles(/* aCreate */ false);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
@ -2278,15 +2387,13 @@ QuotaManager::EnsureOriginIsInitialized(PersistenceType aPersistenceType,
|
|||
aIsApp);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
} else {
|
||||
nsCOMPtr<nsIBinaryInputStream> stream;
|
||||
rv = GetDirectoryMetadataInputStream(directory, getter_AddRefs(stream));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
uint64_t ts;
|
||||
rv = stream->Read64(&ts);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
timestamp = ts;
|
||||
bool persistent = aPersistenceType == PERSISTENCE_TYPE_PERSISTENT;
|
||||
rv = GetDirectoryMetadataWithRestore(directory,
|
||||
persistent,
|
||||
×tamp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
MOZ_ASSERT(timestamp <= PR_Now());
|
||||
}
|
||||
|
@ -3775,11 +3882,18 @@ OriginClearRunnable::DeleteFiles(QuotaManager* aQuotaManager,
|
|||
continue;
|
||||
}
|
||||
|
||||
bool persistent = aPersistenceType == PERSISTENCE_TYPE_PERSISTENT;
|
||||
|
||||
int64_t timestamp;
|
||||
nsCString group;
|
||||
nsCString origin;
|
||||
bool isApp;
|
||||
rv = GetDirectoryMetadata(file, ×tamp, group, origin, &isApp);
|
||||
rv = GetDirectoryMetadataWithRestore(file,
|
||||
persistent,
|
||||
×tamp,
|
||||
group,
|
||||
origin,
|
||||
&isApp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return;
|
||||
}
|
||||
|
@ -4369,14 +4483,15 @@ SaveOriginAccessTimeRunnable::Run()
|
|||
}
|
||||
|
||||
nsresult
|
||||
StorageDirectoryHelper::CreateOrUpgradeMetadataFiles()
|
||||
StorageDirectoryHelper::CreateOrUpgradeMetadataFiles(bool aCreate)
|
||||
{
|
||||
AssertIsOnIOThread();
|
||||
MOZ_ASSERT_IF(mPersistent, aCreate);
|
||||
|
||||
nsresult rv;
|
||||
mCreate = aCreate;
|
||||
|
||||
nsCOMPtr<nsISimpleEnumerator> entries;
|
||||
rv = mDirectory->GetDirectoryEntries(getter_AddRefs(entries));
|
||||
nsresult rv = mDirectory->GetDirectoryEntries(getter_AddRefs(entries));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
@ -4392,61 +4507,27 @@ StorageDirectoryHelper::CreateOrUpgradeMetadataFiles()
|
|||
nsCOMPtr<nsIFile> originDir = do_QueryInterface(entry);
|
||||
MOZ_ASSERT(originDir);
|
||||
|
||||
nsString leafName;
|
||||
rv = originDir->GetLeafName(leafName);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
bool isDirectory;
|
||||
rv = originDir->IsDirectory(&isDirectory);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
if (!isDirectory) {
|
||||
nsString leafName;
|
||||
rv = originDir->GetLeafName(leafName);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (!leafName.EqualsLiteral(DSSTORE_FILE_NAME)) {
|
||||
NS_WARNING("Something in the storage directory that doesn't belong!");
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
if (mPersistent) {
|
||||
rv = MaybeUpgradeOriginDirectory(originDir);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
|
||||
if (leafName.EqualsLiteral(kChromeOrigin)) {
|
||||
OriginProps* originProps = mOriginProps.AppendElement();
|
||||
originProps->mDirectory = originDir;
|
||||
originProps->mSpec = kChromeOrigin;
|
||||
originProps->mType = OriginProps::eChrome;
|
||||
} else {
|
||||
nsCString spec;
|
||||
uint32_t appId;
|
||||
bool inMozBrowser;
|
||||
if (NS_WARN_IF(!OriginParser::ParseOrigin(NS_ConvertUTF16toUTF8(leafName),
|
||||
&appId, &inMozBrowser, spec))) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
OriginProps* originProps = mOriginProps.AppendElement();
|
||||
originProps->mDirectory = originDir;
|
||||
originProps->mSpec = spec;
|
||||
originProps->mAppId = appId;
|
||||
originProps->mType = OriginProps::eContent;
|
||||
originProps->mInMozBrowser = inMozBrowser;
|
||||
|
||||
if (mPersistent) {
|
||||
int64_t timestamp = INT64_MIN;
|
||||
rv = GetLastModifiedTime(originDir, ×tamp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
originProps->mTimestamp = timestamp;
|
||||
}
|
||||
rv = AddOriginDirectory(originDir);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4454,6 +4535,94 @@ StorageDirectoryHelper::CreateOrUpgradeMetadataFiles()
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
rv = ProcessOriginDirectories(/* aMove */ true);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
StorageDirectoryHelper::RestoreMetadataFile()
|
||||
{
|
||||
AssertIsOnIOThread();
|
||||
MOZ_ASSERT(mCreate);
|
||||
|
||||
nsresult rv = AddOriginDirectory(mDirectory);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
rv = ProcessOriginDirectories(/* aMove */ false);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
StorageDirectoryHelper::AddOriginDirectory(nsIFile* aDirectory)
|
||||
{
|
||||
MOZ_ASSERT(aDirectory);
|
||||
|
||||
nsresult rv;
|
||||
|
||||
if (mPersistent) {
|
||||
rv = MaybeUpgradeOriginDirectory(aDirectory);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
}
|
||||
|
||||
nsString leafName;
|
||||
rv = aDirectory->GetLeafName(leafName);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (leafName.EqualsLiteral(kChromeOrigin)) {
|
||||
OriginProps* originProps = mOriginProps.AppendElement();
|
||||
originProps->mDirectory = aDirectory;
|
||||
originProps->mSpec = kChromeOrigin;
|
||||
originProps->mType = OriginProps::eChrome;
|
||||
} else {
|
||||
nsCString spec;
|
||||
uint32_t appId;
|
||||
bool inMozBrowser;
|
||||
if (NS_WARN_IF(!OriginParser::ParseOrigin(NS_ConvertUTF16toUTF8(leafName),
|
||||
&appId, &inMozBrowser, spec))) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
OriginProps* originProps = mOriginProps.AppendElement();
|
||||
originProps->mDirectory = aDirectory;
|
||||
originProps->mSpec = spec;
|
||||
originProps->mAppId = appId;
|
||||
originProps->mType = OriginProps::eContent;
|
||||
originProps->mInMozBrowser = inMozBrowser;
|
||||
|
||||
if (mCreate) {
|
||||
int64_t timestamp = INT64_MIN;
|
||||
rv = GetLastModifiedTime(aDirectory, ×tamp);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
originProps->mTimestamp = timestamp;
|
||||
}
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
StorageDirectoryHelper::ProcessOriginDirectories(bool aMove)
|
||||
{
|
||||
AssertIsOnIOThread();
|
||||
MOZ_ASSERT(!mOriginProps.IsEmpty());
|
||||
|
||||
MOZ_ALWAYS_TRUE(NS_SUCCEEDED(NS_DispatchToMainThread(this)));
|
||||
|
||||
{
|
||||
|
@ -4473,6 +4642,8 @@ StorageDirectoryHelper::CreateOrUpgradeMetadataFiles()
|
|||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsresult rv;
|
||||
|
||||
nsCOMPtr<nsIFile> permanentStorageDir;
|
||||
|
||||
for (uint32_t count = mOriginProps.Length(), index = 0;
|
||||
|
@ -4480,7 +4651,7 @@ StorageDirectoryHelper::CreateOrUpgradeMetadataFiles()
|
|||
index++) {
|
||||
OriginProps& originProps = mOriginProps[index];
|
||||
|
||||
if (mPersistent) {
|
||||
if (mCreate) {
|
||||
rv = CreateDirectoryMetadata(originProps.mDirectory,
|
||||
originProps.mTimestamp,
|
||||
originProps.mGroup,
|
||||
|
@ -4491,7 +4662,9 @@ StorageDirectoryHelper::CreateOrUpgradeMetadataFiles()
|
|||
}
|
||||
|
||||
// Move whitelisted origins to new persistent storage.
|
||||
if (QuotaManager::IsOriginWhitelistedForPersistentStorage(
|
||||
if (mPersistent &&
|
||||
aMove &&
|
||||
QuotaManager::IsOriginWhitelistedForPersistentStorage(
|
||||
originProps.mSpec)) {
|
||||
if (!permanentStorageDir) {
|
||||
permanentStorageDir =
|
||||
|
@ -4586,7 +4759,7 @@ StorageDirectoryHelper::RunOnMainThread()
|
|||
return rv;
|
||||
}
|
||||
|
||||
if (mPersistent) {
|
||||
if (mCreate) {
|
||||
rv = QuotaManager::GetInfoFromPrincipal(principal,
|
||||
&originProps.mGroup,
|
||||
&originProps.mOrigin,
|
||||
|
|
|
@ -37,21 +37,23 @@ var innerWidthMax = (isWin8 ? 125 : 100);
|
|||
|
||||
function test() {
|
||||
var w = window.open('data:text/html,null', null, 'width=300,height=300');
|
||||
var nbResize = 0;
|
||||
|
||||
SimpleTest.waitForFocus(function() {
|
||||
w.onresize = function() {
|
||||
if (!(w.innerWidth + epsilon >= innerWidthMin &&
|
||||
w.innerWidth - epsilon <= innerWidthMax)) {
|
||||
// We need still another resize event.
|
||||
nbResize++;
|
||||
|
||||
if (nbResize == 1) {
|
||||
return;
|
||||
}
|
||||
if (!(w.innerHeight + epsilon >= 100 &&
|
||||
w.innerHeight - epsilon <= 100)) {
|
||||
// ditto
|
||||
return;
|
||||
}
|
||||
ok(true, "innerWidth should be between " + innerWidthMin + " and " + innerWidthMax);
|
||||
ok(true, "innerHeight should be around 100");
|
||||
|
||||
ok(w.innerWidth + epsilon >= innerWidthMin && w.innerWidth - epsilon <= innerWidthMax,
|
||||
"innerWidth should be between " + innerWidthMin + " and " + innerWidthMax);
|
||||
ok(w.innerHeight + epsilon >= 100 && w.innerHeight - epsilon <= 100,
|
||||
"innerHeight should be around 100");
|
||||
|
||||
// It's not clear why 2 events are coming...
|
||||
is(nbResize, 2, "We should get 2 events.");
|
||||
|
||||
w.close();
|
||||
|
||||
|
|
|
@ -23,7 +23,7 @@ function testDefaultCtor() {
|
|||
function testClone() {
|
||||
var orig = new Request("./cloned_request.txt", {
|
||||
method: 'POST',
|
||||
headers: { "Content-Length": 5 },
|
||||
headers: { "Sample-Header": "5" },
|
||||
body: "Sample body",
|
||||
mode: "same-origin",
|
||||
credentials: "same-origin",
|
||||
|
@ -33,9 +33,9 @@ function testClone() {
|
|||
ok(clone.method === "POST", "Request method is POST");
|
||||
ok(clone.headers instanceof Headers, "Request should have non-null Headers object");
|
||||
|
||||
is(clone.headers.get('content-length'), "5", "Response content-length should be 5.");
|
||||
orig.headers.set('content-length', 6);
|
||||
is(clone.headers.get('content-length'), "5", "Request content-length should be 5.");
|
||||
is(clone.headers.get('sample-header'), "5", "Request sample-header should be 5.");
|
||||
orig.headers.set('sample-header', 6);
|
||||
is(clone.headers.get('sample-header'), "5", "Cloned Request sample-header should continue to be 5.");
|
||||
|
||||
ok(clone.url === (new URL("./cloned_request.txt", self.location.href)).href,
|
||||
"URL should be resolved with entry settings object's API base URL");
|
||||
|
@ -124,6 +124,20 @@ function testBug1109574() {
|
|||
var r3 = new Request(r1);
|
||||
}
|
||||
|
||||
function testHeaderGuard() {
|
||||
var headers = {
|
||||
"Cookie": "Custom cookie",
|
||||
"Non-Simple-Header": "value",
|
||||
};
|
||||
var r1 = new Request("", { headers: headers });
|
||||
ok(!r1.headers.has("Cookie"), "Default Request header should have guard request and prevent setting forbidden header.");
|
||||
ok(r1.headers.has("Non-Simple-Header"), "Default Request header should have guard request and allow setting non-simple header.");
|
||||
|
||||
var r2 = new Request("", { mode: "no-cors", headers: headers });
|
||||
ok(!r2.headers.has("Cookie"), "no-cors Request header should have guard request-no-cors and prevent setting non-simple header.");
|
||||
ok(!r2.headers.has("Non-Simple-Header"), "no-cors Request header should have guard request-no-cors and prevent setting non-simple header.");
|
||||
}
|
||||
|
||||
function testMethod() {
|
||||
// These get normalized.
|
||||
var allowed = ["delete", "get", "head", "options", "post", "put" ];
|
||||
|
@ -434,6 +448,7 @@ function runTest() {
|
|||
testUrlFragment();
|
||||
testMethod();
|
||||
testBug1109574();
|
||||
testHeaderGuard();
|
||||
testModeCorsPreflightEnumValue();
|
||||
|
||||
return Promise.resolve()
|
||||
|
|
|
@ -14,6 +14,7 @@ support-files =
|
|||
image_50.png
|
||||
image_100.png
|
||||
image_200.png
|
||||
performance_timeline_main_test.html
|
||||
resource_timing_iframe.html
|
||||
resource_timing_main_test.html
|
||||
resource_timing_cross_origin.html
|
||||
|
@ -79,8 +80,10 @@ support-files = test_offsets.js
|
|||
skip-if = buildapp == 'mulet'
|
||||
[test_paste_selection.html]
|
||||
skip-if = buildapp == 'mulet'
|
||||
[test_performance_timeline.html]
|
||||
[test_picture_mutations.html]
|
||||
[test_picture_pref.html]
|
||||
skip-if = buildapp == 'b2g' || buildapp == 'mulet'
|
||||
[test_resource_timing.html]
|
||||
skip-if = buildapp == 'b2g' || buildapp == 'mulet'
|
||||
[test_resource_timing_cross_origin.html]
|
||||
|
|
|
@ -0,0 +1,100 @@
|
|||
<!--
|
||||
Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/
|
||||
-->
|
||||
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||
<script type="application/javascript">
|
||||
|
||||
function ok(cond, message) {
|
||||
window.opener.ok(cond, message)
|
||||
}
|
||||
|
||||
function is(received, expected, message) {
|
||||
window.opener.is(received, expected, message);
|
||||
}
|
||||
|
||||
function isnot(received, notExpected, message) {
|
||||
window.opener.isnot(received, notExpected, message);
|
||||
}
|
||||
|
||||
var receivedBufferFullEvents = 0;
|
||||
window.performance.onresourcetimingbufferfull = () => {
|
||||
receivedBufferFullEvents++;
|
||||
}
|
||||
|
||||
window.onload = () => {
|
||||
// Here, we should have 4 entries (1 css, 3 png) since the image was loaded.
|
||||
is(window.performance.getEntries().length, 4, "Performance.getEntries() returned wrong number of entries.");
|
||||
|
||||
window.performance.setResourceTimingBufferSize(5);
|
||||
window.performance.mark("test-start");
|
||||
window.performance.mark("test-end");
|
||||
|
||||
// The URI should be the address of a resource will be loaded later to be used on getEntriesByName.
|
||||
window.performance.measure("http://mochi.test:8888/tests/dom/tests/mochitest/general/test-data2.json",
|
||||
"test-start", "test-end");
|
||||
|
||||
is(window.performance.getEntries().length, 7, "User Timing APIs should never be affected by setResourceTimingBufferSize.");
|
||||
is(window.performance.getEntriesByType("resource").length, 4, "The number of PerformanceResourceTiming should be 4.");
|
||||
is(window.performance.getEntriesByType("mark").length, 2, "The number of PerformanceMark entries should be 2.");
|
||||
is(window.performance.getEntriesByType("measure").length, 1, "The number of PerformanceMeasure entries should be 1.");
|
||||
|
||||
is(receivedBufferFullEvents, 0, "onresourcetimingbufferfull should never be called.");
|
||||
|
||||
makeXhr("test-data2.json", firstCheck);
|
||||
}
|
||||
|
||||
function makeXhr(aUrl, aCallback) {
|
||||
var xmlhttp = new XMLHttpRequest();
|
||||
xmlhttp.onload = aCallback;
|
||||
xmlhttp.open("get", aUrl, true);
|
||||
xmlhttp.send();
|
||||
}
|
||||
|
||||
function firstCheck() {
|
||||
is(window.performance.getEntriesByType("resource").length, 5, "The number of PerformanceResourceTiming should be 5.");
|
||||
is(receivedBufferFullEvents, 1, "onresourcetimingbufferfull should be called once.");
|
||||
makeXhr("test-data2.json", secondCheck);
|
||||
}
|
||||
|
||||
function secondCheck() {
|
||||
is(window.performance.getEntriesByType("resource").length, 5, "The number of PerformanceResourceTiming should be 5.");
|
||||
is(receivedBufferFullEvents, 1, "onresourcetimingbufferfull should never be called since the last call.");
|
||||
checkOrder(window.performance.getEntries(), "All PerformanceEntry");
|
||||
checkOrder(window.performance.getEntriesByType("resource"), "PerformanceResourceTiming");
|
||||
checkOrder(window.performance.getEntriesByType("mark"), "PerformanceMark");
|
||||
checkOrder(window.performance.getEntriesByType("measure"), "PerformanceMeasure");
|
||||
|
||||
is(window.performance.getEntriesByName("http://mochi.test:8888/tests/dom/tests/mochitest/general/test-data2.json").length, 2,
|
||||
"Both PerformanceMeasure and XMLHttpRequest resource should be included.");
|
||||
checkOrder(window.performance.getEntriesByName("http://mochi.test:8888/tests/dom/tests/mochitest/general/test-data2.json"),
|
||||
"Entry with performance.getEntrieByName()");
|
||||
window.opener.finishTests();
|
||||
}
|
||||
|
||||
function checkOrder(entries, name) {
|
||||
for (var i = 0; i < entries.length - 1; i++) {
|
||||
ok(entries[i].startTime <= entries[i + 1].startTime, name + " should be sorted by startTime.");
|
||||
}
|
||||
}
|
||||
|
||||
</script>
|
||||
</head>
|
||||
<body>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=1158731"
|
||||
title="Buffer for Performance APIs (Resource Timing, User Timing) should be separeted">
|
||||
Bug #1158731 - Buffer for Performance APIs (Resource Timing, User Timing) should be separeted
|
||||
</a>
|
||||
<p id="display"></p>
|
||||
<div id="content">
|
||||
<img src="http://mochi.test:8888/tests/image/test/mochitest/over.png">
|
||||
<object data="http://mochi.test:8888/tests/image/test/mochitest/clear.png" type="image/png"/>
|
||||
<embed src="http://mochi.test:8888/tests/image/test/mochitest/green.png" type="image/png"/>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
|
@ -76,7 +76,7 @@ window.onload = function() {
|
|||
bufferFullCounter += 1;
|
||||
}
|
||||
|
||||
// Here, we should have 6 entries (1 css, 3 png, 1 html) since the image was loaded.
|
||||
// Here, we should have 5 entries (1 css, 3 png, 1 html) since the image was loaded.
|
||||
is(window.performance.getEntries().length, 5, "Performance.getEntries() returned wrong number of entries.");
|
||||
|
||||
checkStringify(window.performance.getEntries()[0]);
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
<!--
|
||||
Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/
|
||||
-->
|
||||
|
||||
<!DOCTYPE HTML>
|
||||
<html>
|
||||
<head>
|
||||
<script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<pre id="test">
|
||||
<script type="application/javascript">
|
||||
|
||||
SimpleTest.waitForExplicitFinish();
|
||||
|
||||
// Resource timing is prefed off by default, so we had to use this workaround
|
||||
SpecialPowers.pushPrefEnv({"set": [["dom.enable_resource_timing", true],
|
||||
["dom.enable_user_timing", true]]}, start);
|
||||
var subwindow = null;
|
||||
|
||||
function start() {
|
||||
subwindow = window.open("performance_timeline_main_test.html");
|
||||
}
|
||||
|
||||
function finishTests() {
|
||||
subwindow.close();
|
||||
SimpleTest.finish();
|
||||
}
|
||||
</script>
|
||||
</pre>
|
||||
|
||||
</body>
|
||||
</html>
|
|
@ -62,6 +62,7 @@
|
|||
|
||||
SimpleTest.waitForExplicitFinish();
|
||||
SpecialPowers.pushPrefEnv({"set": [
|
||||
["dom.serviceWorkers.exemptFromPerDomainMax", true],
|
||||
["dom.serviceWorkers.enabled", true],
|
||||
["dom.serviceWorkers.testing.enabled", true]
|
||||
]}, runTest);
|
||||
|
|
|
@ -74,6 +74,12 @@ skip-if(B2G||Mulet) fails-if(Android) needs-focus != spellcheck-hyphen-invalid.h
|
|||
skip-if(B2G||Mulet) fails-if(Android) needs-focus != spellcheck-hyphen-multiple-invalid.html spellcheck-hyphen-multiple-invalid-ref.html # Initial mulet triage: parity with B2G/B2G Desktop
|
||||
== spellcheck-dotafterquote-valid.html spellcheck-dotafterquote-valid-ref.html
|
||||
== spellcheck-url-valid.html spellcheck-url-valid-ref.html
|
||||
needs-focus == spellcheck-non-latin-arabic.html spellcheck-non-latin-arabic-ref.html
|
||||
needs-focus == spellcheck-non-latin-chinese-simplified.html spellcheck-non-latin-chinese-simplified-ref.html
|
||||
needs-focus == spellcheck-non-latin-chinese-traditional.html spellcheck-non-latin-chinese-traditional-ref.html
|
||||
needs-focus == spellcheck-non-latin-hebrew.html spellcheck-non-latin-hebrew-ref.html
|
||||
needs-focus == spellcheck-non-latin-japanese.html spellcheck-non-latin-japanese-ref.html
|
||||
needs-focus == spellcheck-non-latin-korean.html spellcheck-non-latin-korean-ref.html
|
||||
== unneeded_scroll.html unneeded_scroll-ref.html
|
||||
skip-if(B2G||Mulet) == caret_on_presshell_reinit.html caret_on_presshell_reinit-ref.html # Initial mulet triage: parity with B2G/B2G Desktop
|
||||
skip-if(B2G||Mulet) == caret_on_presshell_reinit-2.html caret_on_presshell_reinit-ref.html # Initial mulet triage: parity with B2G/B2G Desktop
|
||||
|
|
|
@ -0,0 +1,9 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
</head>
|
||||
<body>
|
||||
<textarea autofocus spellcheck="false">سلام</textarea>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,9 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
</head>
|
||||
<body>
|
||||
<textarea autofocus>سلام</textarea>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,9 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
</head>
|
||||
<body>
|
||||
<textarea autofocus spellcheck="false">你好</textarea>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,9 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
</head>
|
||||
<body>
|
||||
<textarea autofocus>你好</textarea>
|
||||
</body>
|
||||
</html>
|