зеркало из https://github.com/mozilla/gecko-dev.git
Merge m-c to mozilla-inbound
This commit is contained in:
Коммит
76da7d9d6f
2
CLOBBER
2
CLOBBER
|
@ -22,4 +22,4 @@
|
|||
# changes to stick? As of bug 928195, this shouldn't be necessary! Please
|
||||
# don't change CLOBBER for WebIDL changes any more.
|
||||
|
||||
The backout of bug 994190 needed a clobber.
|
||||
Bug 1063304 moved IPDL PMobileConnection into its own namespace and needed a clobber.
|
||||
|
|
|
@ -246,6 +246,15 @@ pref("security.alternate_certificate_error_page", "certerror");
|
|||
|
||||
pref("security.warn_viewing_mixed", false); // Warning is disabled. See Bug 616712.
|
||||
|
||||
// 2 = strict certificate pinning checks.
|
||||
// This default preference is more strict than Firefox because B2G
|
||||
// currently does not have a way to install local root certificates.
|
||||
// Strict checking is effectively equivalent to non-strict checking as
|
||||
// long as that is true. If an ability to add local certificates is
|
||||
// added, there may be a need to change this pref.
|
||||
pref("security.cert_pinning.enforcement_level", 2);
|
||||
|
||||
|
||||
// Override some named colors to avoid inverse OS themes
|
||||
pref("ui.-moz-dialog", "#efebe7");
|
||||
pref("ui.-moz-dialogtext", "#101010");
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="fe92ddd450e03b38edb2d465de7897971d68ac68">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="891e5069c0ad330d8191bf8c7b879c814258c89f"/>
|
||||
|
|
|
@ -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="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="cd88d860656c31c7da7bb310d6a160d0011b0961"/>
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="562d357b72279a9e35d4af5aeecc8e1ffa2f44f1"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="f3e998242fb9a857cf50f5bf3a02304a530ea617"/>
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="fe92ddd450e03b38edb2d465de7897971d68ac68">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="891e5069c0ad330d8191bf8c7b879c814258c89f"/>
|
||||
|
|
|
@ -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="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="platform_hardware_ril" path="hardware/ril" remote="b2g" revision="cd88d860656c31c7da7bb310d6a160d0011b0961"/>
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
<project name="platform_build" path="build" remote="b2g" revision="fe92ddd450e03b38edb2d465de7897971d68ac68">
|
||||
<copyfile dest="Makefile" src="core/root.mk"/>
|
||||
</project>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="891e5069c0ad330d8191bf8c7b879c814258c89f"/>
|
||||
|
@ -135,10 +135,10 @@
|
|||
<project name="device-flame" path="device/t2m/flame" remote="b2g" revision="960533f716ce31dfad357e87fa2f1d9ee5e94674"/>
|
||||
<project name="codeaurora_kernel_msm" path="kernel" remote="b2g" revision="893238eb1215f8fd4f3747169170cc5e1cc33969"/>
|
||||
<project name="kernel_lk" path="bootable/bootloader/lk" remote="b2g" revision="fda40423ffa573dc6cafd3780515010cb2a086be"/>
|
||||
<project name="platform/external/bluetooth/bluedroid" path="external/bluetooth/bluedroid" revision="b2af89ae378a119819a9c86d9a12e573c7130459"/>
|
||||
<project name="platform/external/bluetooth/bluedroid" path="external/bluetooth/bluedroid" revision="30b96dfca99cb384bf520a16b81f3aba56f09907"/>
|
||||
<project name="platform/external/wpa_supplicant_8" path="external/wpa_supplicant_8" revision="5b71e40213f650459e95d35b6f14af7e88d8ab62"/>
|
||||
<project name="platform_external_libnfc-nci" path="external/libnfc-nci" remote="t2m" revision="4186bdecb4dae911b39a8202252cc2310d91b0be"/>
|
||||
<project name="platform/frameworks/av" path="frameworks/av" revision="c1814713bd2d07c2af0c236007badc8732a34324"/>
|
||||
<project name="platform/frameworks/av" path="frameworks/av" revision="ea2f399b3ca0a23524d2828f85f69902caefc22e"/>
|
||||
<project name="platform/frameworks/base" path="frameworks/base" revision="6b58ab45e3e56c1fc20708cc39fa2264c52558df"/>
|
||||
<project name="platform/frameworks/native" path="frameworks/native" revision="a46a9f1ac0ed5662d614c277cbb14eb3f332f365"/>
|
||||
<project name="platform/hardware/libhardware" path="hardware/libhardware" revision="7196881a0e9dd7bfbbcf0af64c8064e70f0fa094"/>
|
||||
|
@ -154,5 +154,5 @@
|
|||
<project name="platform_system_nfcd" path="system/nfcd" remote="b2g" revision="54a712b46fe937dacdaed9b1261c63847129a719"/>
|
||||
<project name="platform/system/qcom" path="system/qcom" revision="63e3f6f176caad587d42bba4c16b66d953fb23c2"/>
|
||||
<project name="platform/vendor/qcom-opensource/wlan/prima" path="vendor/qcom/opensource/wlan/prima" revision="d8952a42771045fca73ec600e2b42a4c7129d723"/>
|
||||
<project name="platform/vendor/qcom/msm8610" path="device/qcom/msm8610" revision="5d1dbc698de7294697373b436dd44e240f40e1ac"/>
|
||||
<project name="platform/vendor/qcom/msm8610" path="device/qcom/msm8610" revision="7704e16da545f4207812e593743d6743e1afb9c5"/>
|
||||
</manifest>
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
</project>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="891e5069c0ad330d8191bf8c7b879c814258c89f"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="562d357b72279a9e35d4af5aeecc8e1ffa2f44f1"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="f3e998242fb9a857cf50f5bf3a02304a530ea617"/>
|
||||
|
|
|
@ -4,6 +4,6 @@
|
|||
"remote": "",
|
||||
"branch": ""
|
||||
},
|
||||
"revision": "b5f6c10e258311d9f04ed759291bbe6af10a772b",
|
||||
"revision": "a491e07757d721d4bea7302cfbb2b18460a3820d",
|
||||
"repo_path": "/integration/gaia-central"
|
||||
}
|
||||
|
|
|
@ -17,7 +17,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="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="891e5069c0ad330d8191bf8c7b879c814258c89f"/>
|
||||
|
|
|
@ -15,7 +15,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="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="891e5069c0ad330d8191bf8c7b879c814258c89f"/>
|
||||
|
|
|
@ -17,7 +17,7 @@
|
|||
</project>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="fake-libdvm" path="dalvik" remote="b2g" revision="d50ae982b19f42f0b66d08b9eb306be81687869f"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="moztt" path="external/moztt" remote="b2g" revision="562d357b72279a9e35d4af5aeecc8e1ffa2f44f1"/>
|
||||
<project name="apitrace" path="external/apitrace" remote="apitrace" revision="f3e998242fb9a857cf50f5bf3a02304a530ea617"/>
|
||||
|
|
|
@ -17,7 +17,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="c7ef0bf06ce1c98cbe68aa52e2ecd862acb23e9c"/>
|
||||
<project name="gaia.git" path="gaia" remote="mozillaorg" revision="3802009e1ab6c3ddfc3eb15522e3140a96b33336"/>
|
||||
<project name="gonk-misc" path="gonk-misc" remote="b2g" revision="b81855b6b67f285d6f27a4f8c1cfe2e0387ea57c"/>
|
||||
<project name="rilproxy" path="rilproxy" remote="b2g" revision="827214fcf38d6569aeb5c6d6f31cb296d1f09272"/>
|
||||
<project name="librecovery" path="librecovery" remote="b2g" revision="891e5069c0ad330d8191bf8c7b879c814258c89f"/>
|
||||
|
|
|
@ -438,6 +438,8 @@
|
|||
#if defined(MOZ_WIDGET_GONK) && defined(MOZ_B2G_RIL)
|
||||
@BINPATH@/components/MmsService.js
|
||||
@BINPATH@/components/MmsService.manifest
|
||||
@BINPATH@/components/MobileConnectionService.js
|
||||
@BINPATH@/components/MobileConnectionService.manifest
|
||||
@BINPATH@/components/MobileMessageDatabaseService.js
|
||||
@BINPATH@/components/MobileMessageDatabaseService.manifest
|
||||
@BINPATH@/components/RadioInterfaceLayer.js
|
||||
|
@ -445,8 +447,6 @@
|
|||
@BINPATH@/components/RILContentHelper.js
|
||||
@BINPATH@/components/TelephonyService.js
|
||||
@BINPATH@/components/TelephonyService.manifest
|
||||
@BINPATH@/components/MobileConnectionGonkService.js
|
||||
@BINPATH@/components/MobileConnectionGonkService.manifest
|
||||
#endif // MOZ_WIDGET_GONK && MOZ_B2G_RIL
|
||||
|
||||
#ifndef MOZ_WIDGET_GONK
|
||||
|
|
|
@ -101,6 +101,7 @@ skip-if = os == "linux" # Bug 924307
|
|||
[browser_aboutHome.js]
|
||||
skip-if = e10s # Bug ?????? - no about:home support yet
|
||||
[browser_aboutSyncProgress.js]
|
||||
[browser_action_keyword.js]
|
||||
[browser_addKeywordSearch.js]
|
||||
skip-if = e10s
|
||||
[browser_alltabslistener.js]
|
||||
|
|
|
@ -0,0 +1,92 @@
|
|||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
let gOnSearchComplete = null;
|
||||
|
||||
function* promise_first_result(inputText) {
|
||||
gURLBar.focus();
|
||||
gURLBar.value = inputText.slice(0, -1);
|
||||
EventUtils.synthesizeKey(inputText.slice(-1) , {});
|
||||
yield promiseSearchComplete();
|
||||
// On Linux, the popup may or may not be open at this stage. So we need
|
||||
// additional checks to ensure we wait long enough.
|
||||
yield promisePopupShown(gURLBar.popup);
|
||||
|
||||
let firstResult = gURLBar.popup.richlistbox.firstChild;
|
||||
return firstResult;
|
||||
}
|
||||
|
||||
|
||||
add_task(function*() {
|
||||
// This test is only relevant if UnifiedComplete is enabled.
|
||||
if (!Services.prefs.getBoolPref("browser.urlbar.unifiedcomplete"))
|
||||
return;
|
||||
|
||||
let tab = gBrowser.selectedTab = gBrowser.addTab("about:mozilla");
|
||||
let tabs = [tab];
|
||||
registerCleanupFunction(() => {
|
||||
for (let tab of tabs)
|
||||
gBrowser.removeTab(tab);
|
||||
PlacesUtils.bookmarks.removeItem(itemId);
|
||||
});
|
||||
|
||||
yield promiseTabLoadEvent(tab);
|
||||
|
||||
let itemId =
|
||||
PlacesUtils.bookmarks.insertBookmark(PlacesUtils.unfiledBookmarksFolderId,
|
||||
NetUtil.newURI("http://example.com/?q=%s"),
|
||||
PlacesUtils.bookmarks.DEFAULT_INDEX,
|
||||
"test");
|
||||
PlacesUtils.bookmarks.setKeywordForBookmark(itemId, "keyword");
|
||||
|
||||
let result = yield promise_first_result("keyword something");
|
||||
isnot(result, null, "Expect a keyword result");
|
||||
|
||||
is(result.getAttribute("type"), "action keyword", "Expect correct `type` attribute");
|
||||
is(result.getAttribute("actiontype"), "keyword", "Expect correct `actiontype` attribute");
|
||||
is(result.getAttribute("title"), "test", "Expect correct title");
|
||||
|
||||
// We need to make a real URI out of this to ensure it's normalised for
|
||||
// comparison.
|
||||
let uri = NetUtil.newURI(result.getAttribute("url"));
|
||||
is(uri.spec, makeActionURI("keyword", {url: "http://example.com/?q=something", input: "keyword something"}).spec, "Expect correct url");
|
||||
|
||||
is_element_visible(result._title, "Title element should be visible");
|
||||
is(result._title.childNodes.length, 1, "Title element should have 1 child");
|
||||
is(result._title.childNodes[0].nodeName, "#text", "That child should be a text node");
|
||||
is(result._title.childNodes[0].data, "test", "Node should contain the name of the bookmark");
|
||||
|
||||
is_element_visible(result._extra, "Extra element should be visible");
|
||||
is(result._extra.childNodes.length, 1, "Title element should have 1 child");
|
||||
is(result._extra.childNodes[0].nodeName, "span", "That child should be a span node");
|
||||
let span = result._extra.childNodes[0];
|
||||
is(span.childNodes.length, 1, "span element should have 1 child");
|
||||
is(span.childNodes[0].nodeName, "#text", "That child should be a text node");
|
||||
is(span.childNodes[0].data, "something", "Node should contain the query for the keyword");
|
||||
|
||||
is_element_hidden(result._url, "URL element should be hidden");
|
||||
|
||||
// Click on the result
|
||||
info("Normal click on result");
|
||||
let tabPromise = promiseTabLoadEvent(tab);
|
||||
EventUtils.synthesizeMouseAtCenter(result, {});
|
||||
let loadEvent = yield tabPromise;
|
||||
is(loadEvent.target.location.href, "http://example.com/?q=something", "Tab should have loaded from clicking on result");
|
||||
|
||||
// Middle-click on the result
|
||||
info("Middle-click on result");
|
||||
result = yield promise_first_result("keyword somethingmore");
|
||||
isnot(result, null, "Expect a keyword result");
|
||||
// We need to make a real URI out of this to ensure it's normalised for
|
||||
// comparison.
|
||||
uri = NetUtil.newURI(result.getAttribute("url"));
|
||||
is(uri.spec, makeActionURI("keyword", {url: "http://example.com/?q=somethingmore", input: "keyword somethingmore"}).spec, "Expect correct url");
|
||||
|
||||
tabPromise = promiseWaitForEvent(gBrowser.tabContainer, "TabOpen");
|
||||
EventUtils.synthesizeMouseAtCenter(result, {button: 1});
|
||||
let tabOpenEvent = yield tabPromise;
|
||||
let newTab = tabOpenEvent.target;
|
||||
tabs.push(newTab);
|
||||
loadEvent = yield promiseTabLoadEvent(newTab);
|
||||
is(loadEvent.target.location.href, "http://example.com/?q=somethingmore", "Tab should have loaded from middle-clicking on result");
|
||||
});
|
|
@ -1,53 +1,11 @@
|
|||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
function promisePopupShown(popup) {
|
||||
if (popup.state = "open")
|
||||
return Promise.resolve();
|
||||
|
||||
let deferred = Promise.defer();
|
||||
popup.addEventListener("popupshown", function onPopupShown(event) {
|
||||
popup.removeEventListener("popupshown", onPopupShown);
|
||||
deferred.resolve();
|
||||
});
|
||||
|
||||
return deferred.promise;
|
||||
}
|
||||
|
||||
function promisePopupHidden(popup) {
|
||||
if (popup.state = "closed")
|
||||
return Promise.resolve();
|
||||
|
||||
let deferred = Promise.defer();
|
||||
popup.addEventListener("popuphidden", function onPopupHidden(event) {
|
||||
popup.removeEventListener("popuphidden", onPopupHidden);
|
||||
deferred.resolve();
|
||||
});
|
||||
|
||||
popup.closePopup();
|
||||
|
||||
return deferred.promise;
|
||||
}
|
||||
|
||||
|
||||
function* check_a11y_label(inputText, expectedLabel) {
|
||||
let searchDeferred = Promise.defer();
|
||||
|
||||
let onSearchComplete = gURLBar.onSearchComplete;
|
||||
registerCleanupFunction(() => {
|
||||
gURLBar.onSearchComplete = onSearchComplete;
|
||||
});
|
||||
gURLBar.onSearchComplete = function () {
|
||||
ok(gURLBar.popupOpen, "The autocomplete popup is correctly open");
|
||||
onSearchComplete.apply(gURLBar);
|
||||
gURLBar.onSearchComplete = onSearchComplete;
|
||||
searchDeferred.resolve();
|
||||
}
|
||||
|
||||
gURLBar.focus();
|
||||
gURLBar.value = inputText.slice(0, -1);
|
||||
EventUtils.synthesizeKey(inputText.slice(-1) , {});
|
||||
yield searchDeferred.promise;
|
||||
yield promiseSearchComplete();
|
||||
// On Linux, the popup may or may not be open at this stage. So we need
|
||||
// additional checks to ensure we wait long enough.
|
||||
yield promisePopupShown(gURLBar.popup);
|
||||
|
|
|
@ -670,3 +670,90 @@ function makeActionURI(action, params) {
|
|||
let url = "moz-action:" + action + "," + JSON.stringify(params);
|
||||
return NetUtil.newURI(url);
|
||||
}
|
||||
|
||||
function is_hidden(element) {
|
||||
var style = element.ownerDocument.defaultView.getComputedStyle(element, "");
|
||||
if (style.display == "none")
|
||||
return true;
|
||||
if (style.visibility != "visible")
|
||||
return true;
|
||||
if (style.display == "-moz-popup")
|
||||
return ["hiding","closed"].indexOf(element.state) != -1;
|
||||
|
||||
// Hiding a parent element will hide all its children
|
||||
if (element.parentNode != element.ownerDocument)
|
||||
return is_hidden(element.parentNode);
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
function is_visible(element) {
|
||||
var style = element.ownerDocument.defaultView.getComputedStyle(element, "");
|
||||
if (style.display == "none")
|
||||
return false;
|
||||
if (style.visibility != "visible")
|
||||
return false;
|
||||
if (style.display == "-moz-popup" && element.state != "open")
|
||||
return false;
|
||||
|
||||
// Hiding a parent element will hide all its children
|
||||
if (element.parentNode != element.ownerDocument)
|
||||
return is_visible(element.parentNode);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
function is_element_visible(element, msg) {
|
||||
isnot(element, null, "Element should not be null, when checking visibility");
|
||||
ok(is_visible(element), msg);
|
||||
}
|
||||
|
||||
function is_element_hidden(element, msg) {
|
||||
isnot(element, null, "Element should not be null, when checking visibility");
|
||||
ok(is_hidden(element), msg);
|
||||
}
|
||||
|
||||
function promisePopupEvent(popup, eventSuffix) {
|
||||
let endState = {shown: "open", hidden: "closed"}[eventSuffix];
|
||||
|
||||
if (popup.state = endState)
|
||||
return Promise.resolve();
|
||||
|
||||
let eventType = "popup" + eventSuffix;
|
||||
let deferred = Promise.defer();
|
||||
popup.addEventListener(eventType, function onPopupShown(event) {
|
||||
popup.removeEventListener(eventType, onPopupShown);
|
||||
deferred.resolve();
|
||||
});
|
||||
|
||||
return deferred.promise;
|
||||
}
|
||||
|
||||
function promisePopupShown(popup) {
|
||||
return promisePopupEvent(popup, "shown");
|
||||
}
|
||||
|
||||
function promisePopupHidden(popup) {
|
||||
return promisePopupEvent(popup, "hidden");
|
||||
}
|
||||
|
||||
let gURLBarOnSearchComplete = null;
|
||||
function promiseSearchComplete() {
|
||||
info("Waiting for onSearchComplete");
|
||||
let deferred = Promise.defer();
|
||||
|
||||
if (!gURLBarOnSearchComplete) {
|
||||
gURLBarOnSearchComplete = gURLBar.onSearchComplete;
|
||||
registerCleanupFunction(() => {
|
||||
gURLBar.onSearchComplete = gURLBarOnSearchComplete;
|
||||
});
|
||||
}
|
||||
|
||||
gURLBar.onSearchComplete = function () {
|
||||
ok(gURLBar.popupOpen, "The autocomplete popup is correctly open");
|
||||
gURLBarOnSearchComplete.apply(gURLBar);
|
||||
deferred.resolve();
|
||||
}
|
||||
|
||||
return deferred.promise;
|
||||
}
|
||||
|
|
|
@ -155,6 +155,10 @@
|
|||
returnValue = action.params.url;
|
||||
break;
|
||||
}
|
||||
case "keyword": {
|
||||
returnValue = action.params.input;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -313,8 +317,10 @@
|
|||
if (switchToTabHavingURI(url) &&
|
||||
isTabEmpty(prevTab))
|
||||
gBrowser.removeTab(prevTab);
|
||||
return;
|
||||
} else if (action.type == "keyword") {
|
||||
url = action.params.url;
|
||||
}
|
||||
return;
|
||||
}
|
||||
continueOperation.call(this);
|
||||
}
|
||||
|
@ -1005,10 +1011,18 @@
|
|||
// Check if this is meant to be an action
|
||||
let action = this.mInput._parseActionUrl(url);
|
||||
if (action) {
|
||||
if (action.type == "switchtab")
|
||||
url = action.param;
|
||||
else
|
||||
return;
|
||||
// TODO (bug 1054816): Centralise the implementation of actions
|
||||
// into a JS module.
|
||||
switch (action.type) {
|
||||
case "switchtab": //Fall through.
|
||||
case "keyword": {
|
||||
url = action.params.url;
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// respect the usual clicking subtleties
|
||||
|
|
|
@ -182,6 +182,21 @@ function injectLoopAPI(targetWindow) {
|
|||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Releases the callData for a specific loopCallId
|
||||
*
|
||||
* The result of this call will be a free call session slot.
|
||||
*
|
||||
* @param {int} loopCallId
|
||||
*/
|
||||
releaseCallData: {
|
||||
enumerable: true,
|
||||
writable: true,
|
||||
value: function(loopCallId) {
|
||||
MozLoopService.releaseCallData(loopCallId);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Returns the contacts API.
|
||||
*
|
||||
|
|
|
@ -81,6 +81,159 @@ let gFxAOAuthTokenData = null;
|
|||
let gFxAOAuthProfile = null;
|
||||
let gErrors = new Map();
|
||||
|
||||
/**
|
||||
* Attempts to open a websocket.
|
||||
*
|
||||
* A new websocket interface is used each time. If an onStop callback
|
||||
* was received, calling asyncOpen() on the same interface will
|
||||
* trigger a "alreay open socket" exception even though the channel
|
||||
* is logically closed.
|
||||
*/
|
||||
function CallProgressSocket(progressUrl, callId, token) {
|
||||
if (!progressUrl || !callId || !token) {
|
||||
throw new Error("missing required arguments");
|
||||
}
|
||||
|
||||
this._progressUrl = progressUrl;
|
||||
this._callId = callId;
|
||||
this._token = token;
|
||||
}
|
||||
|
||||
CallProgressSocket.prototype = {
|
||||
/**
|
||||
* Open websocket and run hello exchange.
|
||||
* Sends a hello message to the server.
|
||||
*
|
||||
* @param {function} Callback used after a successful handshake
|
||||
* over the progressUrl.
|
||||
* @param {function} Callback used if an error is encountered
|
||||
*/
|
||||
connect: function(onSuccess, onError) {
|
||||
this._onSuccess = onSuccess;
|
||||
this._onError = onError ||
|
||||
(reason => {console.warn("MozLoopService::callProgessSocket - ", reason);});
|
||||
|
||||
if (!onSuccess) {
|
||||
this._onError("missing onSuccess argument");
|
||||
return;
|
||||
}
|
||||
|
||||
let uri = Services.io.newURI(this._progressUrl, null, null);
|
||||
|
||||
// Allow _websocket to be set for testing.
|
||||
if (!this._websocket && !Services.io.offline) {
|
||||
this._websocket = Cc["@mozilla.org/network/protocol;1?name=" + uri.scheme]
|
||||
.createInstance(Ci.nsIWebSocketChannel);
|
||||
} else {
|
||||
this._onError("IO offline");
|
||||
return;
|
||||
}
|
||||
|
||||
this._websocket.asyncOpen(uri, this._progressUrl, this, null);
|
||||
},
|
||||
|
||||
/**
|
||||
* Listener method, handles the start of the websocket stream.
|
||||
* Sends a hello message to the server.
|
||||
*
|
||||
* @param {nsISupports} aContext Not used
|
||||
*/
|
||||
onStart: function() {
|
||||
let helloMsg = {
|
||||
messageType: "hello",
|
||||
callId: this._callId,
|
||||
auth: this._token,
|
||||
};
|
||||
try { // in case websocket has closed before this handler is run
|
||||
this._websocket.sendMsg(JSON.stringify(helloMsg));
|
||||
}
|
||||
catch (error) {
|
||||
this._onError(error);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Listener method, called when the websocket is closed.
|
||||
*
|
||||
* @param {nsISupports} aContext Not used
|
||||
* @param {nsresult} aStatusCode Reason for stopping (NS_OK = successful)
|
||||
*/
|
||||
onStop: function(aContext, aStatusCode) {
|
||||
if (!this._handshakeComplete) {
|
||||
this._onError("[" + aStatusCode + "]");
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Listener method, called when the websocket is closed by the server.
|
||||
* If there are errors, onStop may be called without ever calling this
|
||||
* method.
|
||||
*
|
||||
* @param {nsISupports} aContext Not used
|
||||
* @param {integer} aCode the websocket closing handshake close code
|
||||
* @param {String} aReason the websocket closing handshake close reason
|
||||
*/
|
||||
onServerClose: function(aContext, aCode, aReason) {
|
||||
if (!this._handshakeComplete) {
|
||||
this._onError("[" + aCode + "]" + aReason);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Listener method, called when the websocket receives a message.
|
||||
*
|
||||
* @param {nsISupports} aContext Not used
|
||||
* @param {String} aMsg The message data
|
||||
*/
|
||||
onMessageAvailable: function(aContext, aMsg) {
|
||||
let msg = {};
|
||||
try {
|
||||
msg = JSON.parse(aMsg);
|
||||
}
|
||||
catch (error) {
|
||||
console.error("MozLoopService: error parsing progress message - ", error);
|
||||
return;
|
||||
}
|
||||
|
||||
if (msg.messageType && msg.messageType === 'hello') {
|
||||
this._handshakeComplete = true;
|
||||
this._onSuccess();
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Create a JSON message payload and send on websocket.
|
||||
*
|
||||
* @param {Object} aMsg Message to send.
|
||||
*/
|
||||
_send: function(aMsg) {
|
||||
if (!this._handshakeComplete) {
|
||||
console.warn("MozLoopService::_send error - handshake not complete");
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
this._websocket.sendMsg(JSON.stringify(aMsg));
|
||||
}
|
||||
catch (error) {
|
||||
this._onError(error);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Notifies the server that the user has declined the call
|
||||
* with a reason of busy.
|
||||
*/
|
||||
sendBusy: function() {
|
||||
this._send({
|
||||
messageType: "action",
|
||||
event: "terminate",
|
||||
reason: "busy"
|
||||
});
|
||||
},
|
||||
};
|
||||
|
||||
/**
|
||||
* Internal helper methods and state
|
||||
*
|
||||
|
@ -89,7 +242,7 @@ let gErrors = new Map();
|
|||
* and register with the Loop server.
|
||||
*/
|
||||
let MozLoopServiceInternal = {
|
||||
callsData: {data: undefined},
|
||||
callsData: {inUse: false},
|
||||
|
||||
// The uri of the Loop server.
|
||||
get loopServerUri() Services.prefs.getCharPref("loop.server"),
|
||||
|
@ -243,10 +396,19 @@ let MozLoopServiceInternal = {
|
|||
2 * 32, true);
|
||||
}
|
||||
|
||||
return gHawkClient.request(path, method, credentials, payloadObj).catch(error => {
|
||||
console.error("Loop hawkRequest error:", error);
|
||||
throw error;
|
||||
});
|
||||
return gHawkClient.request(path, method, credentials, payloadObj);
|
||||
},
|
||||
|
||||
/**
|
||||
* Generic hawkRequest onError handler for the hawkRequest promise.
|
||||
*
|
||||
* @param {Object} error - error reporting object
|
||||
*
|
||||
*/
|
||||
|
||||
_hawkRequestError: function(error) {
|
||||
console.error("Loop hawkRequest error:", error);
|
||||
throw error;
|
||||
},
|
||||
|
||||
getSessionTokenPrefName: function(sessionType) {
|
||||
|
@ -422,23 +584,84 @@ let MozLoopServiceInternal = {
|
|||
// bug 1046039 for background.
|
||||
Services.prefs.setCharPref("loop.seenToS", "seen");
|
||||
|
||||
/* Request the information on the new call(s) associated with this version. */
|
||||
this.hawkRequest(LOOP_SESSION_TYPE.GUEST,
|
||||
"/calls?version=" + version, "GET").then(response => {
|
||||
try {
|
||||
let respData = JSON.parse(response.body);
|
||||
if (respData.calls && respData.calls[0]) {
|
||||
this.callsData.data = respData.calls[0];
|
||||
this.openChatWindow(null,
|
||||
this.localizedStrings["incoming_call_title2"].textContent,
|
||||
"about:loopconversation#incoming/" + version);
|
||||
} else {
|
||||
console.warn("Error: missing calls[] in response");
|
||||
}
|
||||
} catch (err) {
|
||||
console.warn("Error parsing calls info", err);
|
||||
// Request the information on the new call(s) associated with this version.
|
||||
// The registered FxA session is checked first, then the anonymous session.
|
||||
// Make the call to get the GUEST session regardless of whether the FXA
|
||||
// request fails.
|
||||
|
||||
this._getCalls(LOOP_SESSION_TYPE.FXA, version).catch(() => {});
|
||||
this._getCalls(LOOP_SESSION_TYPE.GUEST, version).catch(
|
||||
error => {this._hawkRequestError(error);});
|
||||
},
|
||||
|
||||
/**
|
||||
* Make a hawkRequest to GET/calls?=version for this session type.
|
||||
*
|
||||
* @param {LOOP_SESSION_TYPE} sessionType - type of hawk token used
|
||||
* for the GET operation.
|
||||
* @param {Object} version - LoopPushService notification version
|
||||
*
|
||||
* @returns {Promise}
|
||||
*
|
||||
*/
|
||||
|
||||
_getCalls: function(sessionType, version) {
|
||||
return this.hawkRequest(sessionType, "/calls?version=" + version, "GET").then(
|
||||
response => {this._processCalls(response, sessionType);}
|
||||
);
|
||||
},
|
||||
|
||||
/**
|
||||
* Process the calls array returned from a GET/calls?version request.
|
||||
* Only one active call is permitted at this time.
|
||||
*
|
||||
* @param {Object} response - response payload from GET
|
||||
*
|
||||
* @param {LOOP_SESSION_TYPE} sessionType - type of hawk token used
|
||||
* for the GET operation.
|
||||
*
|
||||
*/
|
||||
|
||||
_processCalls: function(response, sessionType) {
|
||||
try {
|
||||
let respData = JSON.parse(response.body);
|
||||
if (respData.calls && Array.isArray(respData.calls)) {
|
||||
respData.calls.forEach((callData) => {
|
||||
if (!this.callsData.inUse) {
|
||||
this.callsData.inUse = true;
|
||||
callData.sessionType = sessionType;
|
||||
this.callsData.data = callData;
|
||||
this.openChatWindow(
|
||||
null,
|
||||
this.localizedStrings["incoming_call_title2"].textContent,
|
||||
"about:loopconversation#incoming/" + callData.callId);
|
||||
} else {
|
||||
this._returnBusy(callData);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
console.warn("Error: missing calls[] in response");
|
||||
}
|
||||
});
|
||||
} catch (err) {
|
||||
console.warn("Error parsing calls info", err);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Open call progress websocket and terminate with a reason of busy
|
||||
* the server.
|
||||
*
|
||||
* @param {callData} Must contain the progressURL, callId and websocketToken
|
||||
* returned by the LoopService.
|
||||
*/
|
||||
_returnBusy: function(callData) {
|
||||
let callProgress = new CallProgressSocket(
|
||||
callData.progressURL,
|
||||
callData.callId,
|
||||
callData.websocketToken);
|
||||
// This instance of CallProgressSocket should stay alive until the underlying
|
||||
// websocket is closed since it is passed to the websocket as the nsIWebSocketListener.
|
||||
callProgress.connect(() => {callProgress.sendBusy();});
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -619,7 +842,8 @@ let MozLoopServiceInternal = {
|
|||
}
|
||||
|
||||
return JSON.parse(response.body);
|
||||
});
|
||||
},
|
||||
error => {this._hawkRequestError(error);});
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -697,7 +921,8 @@ let MozLoopServiceInternal = {
|
|||
};
|
||||
return this.hawkRequest(LOOP_SESSION_TYPE.FXA, "/fxa-oauth/token", "POST", payload).then(response => {
|
||||
return JSON.parse(response.body);
|
||||
});
|
||||
},
|
||||
error => {this._hawkRequestError(error);});
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -959,7 +1184,7 @@ this.MozLoopService = {
|
|||
},
|
||||
|
||||
/**
|
||||
* Returns the callData for a specific callDataId
|
||||
* Returns the callData for a specific loopCallId
|
||||
*
|
||||
* The data was retrieved from the LoopServer via a GET/calls/<version> request
|
||||
* triggered by an incoming message from the LoopPushServer.
|
||||
|
@ -968,7 +1193,27 @@ this.MozLoopService = {
|
|||
* @return {callData} The callData or undefined if error.
|
||||
*/
|
||||
getCallData: function(loopCallId) {
|
||||
return MozLoopServiceInternal.callsData.data;
|
||||
if (MozLoopServiceInternal.callsData.data &&
|
||||
MozLoopServiceInternal.callsData.data.callId == loopCallId) {
|
||||
return MozLoopServiceInternal.callsData.data;
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Releases the callData for a specific loopCallId
|
||||
*
|
||||
* The result of this call will be a free call session slot.
|
||||
*
|
||||
* @param {int} loopCallId
|
||||
*/
|
||||
releaseCallData: function(loopCallId) {
|
||||
if (MozLoopServiceInternal.callsData.data &&
|
||||
MozLoopServiceInternal.callsData.data.callId == loopCallId) {
|
||||
MozLoopServiceInternal.callsData.data = undefined;
|
||||
MozLoopServiceInternal.callsData.inUse = false;
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -1121,6 +1366,7 @@ this.MozLoopService = {
|
|||
* rejected with this JSON-parsed response.
|
||||
*/
|
||||
hawkRequest: function(sessionType, path, method, payloadObj) {
|
||||
return MozLoopServiceInternal.hawkRequest(sessionType, path, method, payloadObj);
|
||||
return MozLoopServiceInternal.hawkRequest(sessionType, path, method, payloadObj).catch(
|
||||
error => {this._hawkRequestError(error);});
|
||||
},
|
||||
};
|
||||
|
|
|
@ -215,6 +215,7 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
"call/decline": "decline",
|
||||
"call/ongoing": "conversation",
|
||||
"call/declineAndBlock": "declineAndBlock",
|
||||
"call/shutdown": "shutdown",
|
||||
"call/feedback": "feedback"
|
||||
},
|
||||
|
||||
|
@ -229,9 +230,14 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
* @override {loop.shared.router.BaseConversationRouter.endCall}
|
||||
*/
|
||||
endCall: function() {
|
||||
navigator.mozLoop.releaseCallData(this._conversation.get("callId"));
|
||||
this.navigate("call/feedback", {trigger: true});
|
||||
},
|
||||
|
||||
shutdown: function() {
|
||||
navigator.mozLoop.releaseCallData(this._conversation.get("callId"));
|
||||
},
|
||||
|
||||
/**
|
||||
* Incoming call route.
|
||||
*
|
||||
|
@ -348,6 +354,7 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
*/
|
||||
_declineCall: function() {
|
||||
this._websocket.decline();
|
||||
navigator.mozLoop.releaseCallData(this._conversation.get("callId"));
|
||||
// XXX Don't close the window straight away, but let any sends happen
|
||||
// first. Ideally we'd wait to close the window until after we have a
|
||||
// response from the server, to know that everything has completed
|
||||
|
@ -458,6 +465,12 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
{sdk: OT}), // Model dependencies
|
||||
notifications: new loop.shared.models.NotificationCollection()
|
||||
});
|
||||
|
||||
window.addEventListener("unload", (event) => {
|
||||
// Handle direct close of dialog box via [x] control.
|
||||
navigator.mozLoop.releaseCallData(router._conversation.get("callId"));
|
||||
});
|
||||
|
||||
Backbone.history.start();
|
||||
}
|
||||
|
||||
|
|
|
@ -215,6 +215,7 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
"call/decline": "decline",
|
||||
"call/ongoing": "conversation",
|
||||
"call/declineAndBlock": "declineAndBlock",
|
||||
"call/shutdown": "shutdown",
|
||||
"call/feedback": "feedback"
|
||||
},
|
||||
|
||||
|
@ -229,9 +230,14 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
* @override {loop.shared.router.BaseConversationRouter.endCall}
|
||||
*/
|
||||
endCall: function() {
|
||||
navigator.mozLoop.releaseCallData(this._conversation.get("callId"));
|
||||
this.navigate("call/feedback", {trigger: true});
|
||||
},
|
||||
|
||||
shutdown: function() {
|
||||
navigator.mozLoop.releaseCallData(this._conversation.get("callId"));
|
||||
},
|
||||
|
||||
/**
|
||||
* Incoming call route.
|
||||
*
|
||||
|
@ -348,6 +354,7 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
*/
|
||||
_declineCall: function() {
|
||||
this._websocket.decline();
|
||||
navigator.mozLoop.releaseCallData(this._conversation.get("callId"));
|
||||
// XXX Don't close the window straight away, but let any sends happen
|
||||
// first. Ideally we'd wait to close the window until after we have a
|
||||
// response from the server, to know that everything has completed
|
||||
|
@ -458,6 +465,12 @@ loop.conversation = (function(OT, mozL10n) {
|
|||
{sdk: OT}), // Model dependencies
|
||||
notifications: new loop.shared.models.NotificationCollection()
|
||||
});
|
||||
|
||||
window.addEventListener("unload", (event) => {
|
||||
// Handle direct close of dialog box via [x] control.
|
||||
navigator.mozLoop.releaseCallData(router._conversation.get("callId"));
|
||||
});
|
||||
|
||||
Backbone.history.start();
|
||||
}
|
||||
|
||||
|
|
|
@ -18,9 +18,9 @@ loop.shared.models = (function(l10n) {
|
|||
ongoing: false, // Ongoing call flag
|
||||
callerId: undefined, // Loop caller id
|
||||
loopToken: undefined, // Loop conversation token
|
||||
loopCallId: undefined, // LoopService id for incoming session
|
||||
sessionId: undefined, // OT session id
|
||||
sessionToken: undefined, // OT session token
|
||||
sessionType: undefined, // Hawk session type
|
||||
apiKey: undefined, // OT api key
|
||||
callId: undefined, // The callId on the server
|
||||
progressURL: undefined, // The websocket url to use for progress
|
||||
|
@ -139,6 +139,7 @@ loop.shared.models = (function(l10n) {
|
|||
this.set({
|
||||
sessionId: sessionData.sessionId,
|
||||
sessionToken: sessionData.sessionToken,
|
||||
sessionType: sessionData.sessionType,
|
||||
apiKey: sessionData.apiKey,
|
||||
callId: sessionData.callId,
|
||||
progressURL: sessionData.progressURL,
|
||||
|
|
|
@ -30,6 +30,7 @@ describe("loop.conversation", function() {
|
|||
getLoopCharPref: sandbox.stub(),
|
||||
getLoopBoolPref: sandbox.stub(),
|
||||
getCallData: sandbox.stub(),
|
||||
releaseCallData: function() {},
|
||||
startAlerting: function() {},
|
||||
stopAlerting: function() {},
|
||||
ensureRegistered: function() {},
|
||||
|
@ -461,6 +462,10 @@ describe("loop.conversation", function() {
|
|||
router._websocket = {
|
||||
decline: sandbox.spy()
|
||||
};
|
||||
conversation.setIncomingSessionData({
|
||||
callId: 8699,
|
||||
websocketToken: 123
|
||||
});
|
||||
});
|
||||
|
||||
it("should close the window", function() {
|
||||
|
@ -476,6 +481,14 @@ describe("loop.conversation", function() {
|
|||
|
||||
sinon.assert.calledOnce(navigator.mozLoop.stopAlerting);
|
||||
});
|
||||
|
||||
it("should release callData", function() {
|
||||
sandbox.stub(navigator.mozLoop, "releaseCallData");
|
||||
router.decline();
|
||||
|
||||
sinon.assert.calledOnce(navigator.mozLoop.releaseCallData);
|
||||
sinon.assert.calledWithExactly(navigator.mozLoop.releaseCallData, 8699);
|
||||
});
|
||||
});
|
||||
|
||||
describe("#feedback", function() {
|
||||
|
@ -546,8 +559,9 @@ describe("loop.conversation", function() {
|
|||
sandbox.stub(conversation, "get");
|
||||
router.declineAndBlock();
|
||||
|
||||
sinon.assert.calledOnce(conversation.get);
|
||||
sinon.assert.calledTwice(conversation.get);
|
||||
sinon.assert.calledWithExactly(conversation.get, "callToken");
|
||||
sinon.assert.calledWithExactly(conversation.get, "callId");
|
||||
});
|
||||
|
||||
it("should trigger error handling in case of error", function() {
|
||||
|
|
|
@ -372,11 +372,13 @@ this.PlacesUIUtils = {
|
|||
if (this.PLACES_FLAVORS.indexOf(aData.type) == -1)
|
||||
throw new Error (`itemGuid unexpectedly set on ${aData.type} data`);
|
||||
|
||||
let info = { GUID: aData.itemGuid
|
||||
, newParentGUID: aNewParentGuid
|
||||
let info = { guid: aData.itemGuid
|
||||
, newParentGuid: aNewParentGuid
|
||||
, newIndex: aIndex };
|
||||
if (aCopy)
|
||||
if (aCopy) {
|
||||
info.excludingAnnotation = "Places/SmartBookmark";
|
||||
return PlacesTransactions.Copy(info);
|
||||
}
|
||||
return PlacesTransactions.Move(info);
|
||||
}
|
||||
|
||||
|
@ -388,7 +390,7 @@ this.PlacesUIUtils = {
|
|||
throw new Error("Can't copy a container from a legacy-transactions build");
|
||||
|
||||
if (aData.type == PlacesUtils.TYPE_X_MOZ_PLACE_SEPARATOR) {
|
||||
return PlacesTransactions.NewSeparator({ parentGUID: aNewParentGuid
|
||||
return PlacesTransactions.NewSeparator({ parentGuid: aNewParentGuid
|
||||
, index: aIndex });
|
||||
}
|
||||
|
||||
|
@ -396,7 +398,7 @@ this.PlacesUIUtils = {
|
|||
: aData.uri;
|
||||
return PlacesTransactions.NewBookmark({ uri: NetUtil.newURI(aData.uri)
|
||||
, title: title
|
||||
, parentGUID: aNewParentGuid
|
||||
, parentGuid: aNewParentGuid
|
||||
, index: aIndex });
|
||||
},
|
||||
|
||||
|
|
|
@ -57,7 +57,7 @@ InsertionPoint.prototype = {
|
|||
return this._index = val;
|
||||
},
|
||||
|
||||
promiseGuid: function () PlacesUtils.promiseItemGUID(this.itemId),
|
||||
promiseGuid: function () PlacesUtils.promiseItemGuid(this.itemId),
|
||||
|
||||
get index() {
|
||||
if (this.dropNearItemId > 0) {
|
||||
|
@ -781,7 +781,7 @@ PlacesController.prototype = {
|
|||
return;
|
||||
}
|
||||
|
||||
let txn = PlacesTransactions.NewSeparator({ parentGUID: yield ip.promiseGuid()
|
||||
let txn = PlacesTransactions.NewSeparator({ parentGuid: yield ip.promiseGuid()
|
||||
, index: ip.index });
|
||||
let guid = yield PlacesTransactions.transact(txn);
|
||||
let itemId = yield PlacesUtils.promiseItemId(guid);
|
||||
|
@ -808,7 +808,7 @@ PlacesController.prototype = {
|
|||
PlacesUtils.transactionManager.doTransaction(txn);
|
||||
return;
|
||||
}
|
||||
let guid = yield PlacesUtils.promiseItemGUID(itemId);
|
||||
let guid = yield PlacesUtils.promiseItemGuid(itemId);
|
||||
yield PlacesTransactions.transact(PlacesTransactions.SortByName(guid));
|
||||
}),
|
||||
|
||||
|
|
|
@ -46,13 +46,13 @@ var gMoveBookmarksDialog = {
|
|||
}
|
||||
|
||||
PlacesTransactions.transact(function* () {
|
||||
let newParentGUID = yield PlacesUtils.promiseItemGUID(selectedFolderId);
|
||||
let newParentGuid = yield PlacesUtils.promiseItemGuid(selectedFolderId);
|
||||
for (let node of this._nodes) {
|
||||
// Nothing to do if the node is already under the selected folder.
|
||||
if (node.parent.itemId == selectedFolderId)
|
||||
continue;
|
||||
yield PlacesTransactions.Move({ GUID: node.bookmarkGuid
|
||||
, newParentGUID: newParentGUID });
|
||||
yield PlacesTransactions.Move({ guid: node.bookmarkGuid
|
||||
, newParentGuid: newParentGuid });
|
||||
}
|
||||
}.bind(this)).then(null, Components.utils.reportError);
|
||||
},
|
||||
|
|
|
@ -7,10 +7,9 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
|
||||
ok(target, "Should have a target available.");
|
||||
ok(debuggee, "Should have a debuggee available.");
|
||||
ok(panel, "Should have a panel available.");
|
||||
|
||||
yield teardown(panel);
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
* Tests if the shader editor works with bfcache.
|
||||
*/
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, $, EVENTS, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
// Attach frame scripts if in e10s to perform
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, ShadersEditorsView, EVENTS } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, EVENTS, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, EVENTS, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
try {
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, $ } = panel.panelWin;
|
||||
|
||||
is($("#reload-notice").hidden, false,
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, $, EVENTS, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, debuggee, panel } = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { gFront, EVENTS, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
once(panel.panelWin, EVENTS.SHADER_COMPILED).then(() => {
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(BLENDED_GEOMETRY_CANVAS_URL);
|
||||
let { target, debuggee, panel } = yield initShaderEditor(BLENDED_GEOMETRY_CANVAS_URL);
|
||||
let { gFront, EVENTS, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, debuggee, panel } = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { EVENTS, gFront, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, panel } = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { gFront, EVENTS, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
once(panel.panelWin, EVENTS.SHADER_COMPILED).then(() => {
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(BLENDED_GEOMETRY_CANVAS_URL);
|
||||
let { target, debuggee, panel } = yield initShaderEditor(BLENDED_GEOMETRY_CANVAS_URL);
|
||||
let { gFront, EVENTS, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, panel } = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { gFront, EVENTS, L10N, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
is(ShadersListView.itemCount, 0,
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, $, EVENTS, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { target, panel } = yield initShaderEditor(SIMPLE_CANVAS_URL);
|
||||
let { gFront, EVENTS, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, panel] = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, panel } = yield initShaderEditor(MULTIPLE_CONTEXTS_URL);
|
||||
let { gFront, EVENTS, ShadersListView, ShadersEditorsView } = panel.panelWin;
|
||||
|
||||
reload(target);
|
||||
|
|
|
@ -6,10 +6,9 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
|
||||
ok(target, "Should have a target available.");
|
||||
ok(debuggee, "Should have a debuggee available.");
|
||||
ok(front, "Should have a protocol front available.");
|
||||
|
||||
yield removeTab(target.tab);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
|
||||
once(front, "program-linked").then(() => {
|
||||
ok(false, "A 'program-linked' notification shouldn't have been sent!");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
|
||||
let navigated = once(target, "navigate");
|
||||
let linked = once(front, "program-linked");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let programActor = yield once(front, "program-linked");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let programActor = yield once(front, "program-linked");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let programActor = yield once(front, "program-linked");
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let programActor = yield once(front, "program-linked");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let programActor = yield once(front, "program-linked");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let programActor = yield once(front, "program-linked");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
|
||||
front.setup({ reload: true });
|
||||
yield testHighlighting((yield once(front, "program-linked")));
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
|
||||
let linked = once(front, "program-linked");
|
||||
front.setup({ reload: true });
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SHADER_ORDER_URL);
|
||||
let { target, front } = yield initBackend(SHADER_ORDER_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let programActor = yield once(front, "program-linked");
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, front } = yield initBackend(MULTIPLE_CONTEXTS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let [firstProgramActor, secondProgramActor] = yield getPrograms(front, 2);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, front } = yield initBackend(MULTIPLE_CONTEXTS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let [firstProgramActor, secondProgramActor] = yield getPrograms(front, 2);
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: false });
|
||||
|
||||
// Attach frame scripts if in e10s to perform
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(SIMPLE_CANVAS_URL);
|
||||
front.setup({ reload: false });
|
||||
|
||||
// Attach frame scripts if in e10s to perform
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(OVERLAPPING_GEOMETRY_CANVAS_URL);
|
||||
let { target, front } = yield initBackend(OVERLAPPING_GEOMETRY_CANVAS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
let [firstProgramActor, secondProgramActor] = yield getPrograms(front, 2);
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
function ifWebGLSupported() {
|
||||
let [target, debuggee, front] = yield initBackend(MULTIPLE_CONTEXTS_URL);
|
||||
let { target, front } = yield initBackend(MULTIPLE_CONTEXTS_URL);
|
||||
front.setup({ reload: true });
|
||||
|
||||
yield getPrograms(front, 2);
|
||||
|
|
|
@ -241,12 +241,11 @@ function initBackend(aUrl) {
|
|||
return Task.spawn(function*() {
|
||||
let tab = yield addTab(aUrl);
|
||||
let target = TargetFactory.forTab(tab);
|
||||
let debuggee = target.window.wrappedJSObject;
|
||||
|
||||
yield target.makeRemote();
|
||||
|
||||
let front = new WebGLFront(target.client, target.form);
|
||||
return [target, debuggee, front];
|
||||
return { target, front };
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -256,14 +255,13 @@ function initShaderEditor(aUrl) {
|
|||
return Task.spawn(function*() {
|
||||
let tab = yield addTab(aUrl);
|
||||
let target = TargetFactory.forTab(tab);
|
||||
let debuggee = target.window.wrappedJSObject;
|
||||
|
||||
yield target.makeRemote();
|
||||
|
||||
Services.prefs.setBoolPref("devtools.shadereditor.enabled", true);
|
||||
let toolbox = yield gDevTools.showToolbox(target, "shadereditor");
|
||||
let panel = toolbox.getCurrentPanel();
|
||||
return [target, debuggee, panel];
|
||||
return { target, panel };
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
[DEFAULT]
|
||||
skip-if = e10s # Bug 1065355 - devtools tests disabled with e10s
|
||||
subsuite = devtools
|
||||
support-files =
|
||||
doc_simple-test.html
|
||||
|
|
|
@ -7,10 +7,9 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
|
||||
ok(target, "Should have a target available.");
|
||||
ok(debuggee, "Should have a debuggee available.");
|
||||
ok(panel, "Should have a panel available.");
|
||||
|
||||
ok(panel.panelWin.gToolbox, "Should have a toolbox reference on the panel window.");
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { EVENTS, TimelineView, TimelineController } = panel.panelWin;
|
||||
let { OVERVIEW_INITIAL_SELECTION_RATIO: selectionRatio } = panel.panelWin;
|
||||
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { EVENTS, TimelineView, TimelineController } = panel.panelWin;
|
||||
let { OVERVIEW_INITIAL_SELECTION_RATIO: selectionRatio } = panel.panelWin;
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel("about:blank");
|
||||
let { target, panel } = yield initTimelinePanel("about:blank");
|
||||
let { EVENTS, TimelineView, TimelineController } = panel.panelWin;
|
||||
|
||||
yield DevToolsUtils.waitForTime(1000);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { $, EVENTS } = panel.panelWin;
|
||||
|
||||
is($("#record-button").hasAttribute("checked"), false,
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { gFront, TimelineController } = panel.panelWin;
|
||||
|
||||
is((yield gFront.isRecording()), false,
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { $, EVENTS, TimelineView, TimelineController } = panel.panelWin;
|
||||
|
||||
yield TimelineController.toggleRecording();
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { $, $$, EVENTS, TimelineController } = panel.panelWin;
|
||||
|
||||
yield TimelineController.toggleRecording();
|
||||
|
|
|
@ -16,7 +16,7 @@ var gRGB_TO_HSL = {
|
|||
};
|
||||
|
||||
let test = Task.async(function*() {
|
||||
let [target, debuggee, panel] = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { target, panel } = yield initTimelinePanel(SIMPLE_URL);
|
||||
let { TIMELINE_BLUEPRINT } = devtools.require("devtools/timeline/global");
|
||||
let { $, $$, EVENTS, TimelineController } = panel.panelWin;
|
||||
|
||||
|
|
|
@ -78,20 +78,19 @@ function removeTab(tab) {
|
|||
* The location of the new tab to spawn.
|
||||
* @return object
|
||||
* A promise resolved once the timeline is initialized, with the
|
||||
* [target, debuggee, panel] instances.
|
||||
* {target, panel} instances.
|
||||
*/
|
||||
function* initTimelinePanel(url) {
|
||||
info("Initializing a timeline pane.");
|
||||
|
||||
let tab = yield addTab(url);
|
||||
let target = TargetFactory.forTab(tab);
|
||||
let debuggee = target.window.wrappedJSObject;
|
||||
|
||||
yield target.makeRemote();
|
||||
|
||||
let toolbox = yield gDevTools.showToolbox(target, "timeline");
|
||||
let panel = toolbox.getCurrentPanel();
|
||||
return [target, debuggee, panel];
|
||||
return { target, panel };
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
This is the pdf.js project output, https://github.com/mozilla/pdf.js
|
||||
|
||||
Current extension version is: 1.0.712
|
||||
Current extension version is: 1.0.801
|
||||
|
||||
|
|
|
@ -42,6 +42,10 @@ XPCOMUtils.defineLazyServiceGetter(Svc, 'mime',
|
|||
XPCOMUtils.defineLazyServiceGetter(Svc, 'pluginHost',
|
||||
'@mozilla.org/plugin/host;1',
|
||||
'nsIPluginHost');
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PdfjsChromeUtils",
|
||||
"resource://pdf.js/PdfjsChromeUtils.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "PdfjsContentUtils",
|
||||
"resource://pdf.js/PdfjsContentUtils.jsm");
|
||||
|
||||
function getBoolPref(aPref, aDefaultValue) {
|
||||
try {
|
||||
|
@ -59,6 +63,13 @@ function getIntPref(aPref, aDefaultValue) {
|
|||
}
|
||||
}
|
||||
|
||||
function isDefaultHandler() {
|
||||
if (Services.appinfo.processType == Services.appinfo.PROCESS_TYPE_CONTENT) {
|
||||
return PdfjsContentUtils.isDefaultHandlerApp();
|
||||
}
|
||||
return PdfjsChromeUtils.isDefaultHandlerApp();
|
||||
}
|
||||
|
||||
function initializeDefaultPreferences() {
|
||||
|
||||
var DEFAULT_PREFERENCES = {
|
||||
|
@ -118,17 +129,30 @@ Factory.prototype = {
|
|||
let PdfJs = {
|
||||
QueryInterface: XPCOMUtils.generateQI([Ci.nsIObserver]),
|
||||
_registered: false,
|
||||
_initialized: false,
|
||||
|
||||
init: function init(remote) {
|
||||
if (Services.appinfo.processType != Services.appinfo.PROCESS_TYPE_DEFAULT) {
|
||||
throw new Error("PdfJs.init should only get called in the parent process.");
|
||||
}
|
||||
PdfjsChromeUtils.init();
|
||||
if (!remote) {
|
||||
PdfjsContentUtils.init();
|
||||
}
|
||||
this.initPrefs();
|
||||
this.updateRegistration();
|
||||
},
|
||||
|
||||
initPrefs: function initPrefs() {
|
||||
if (this._initialized) {
|
||||
return;
|
||||
}
|
||||
this._initialized = true;
|
||||
|
||||
init: function init() {
|
||||
if (!getBoolPref(PREF_DISABLED, true)) {
|
||||
this._migrate();
|
||||
}
|
||||
|
||||
if (this.enabled)
|
||||
this._ensureRegistered();
|
||||
else
|
||||
this._ensureUnregistered();
|
||||
|
||||
// Listen for when pdf.js is completely disabled or a different pdf handler
|
||||
// is chosen.
|
||||
Services.prefs.addObserver(PREF_DISABLED, this, false);
|
||||
|
@ -140,6 +164,26 @@ let PdfJs = {
|
|||
initializeDefaultPreferences();
|
||||
},
|
||||
|
||||
updateRegistration: function updateRegistration() {
|
||||
if (this.enabled) {
|
||||
this._ensureRegistered();
|
||||
} else {
|
||||
this._ensureUnregistered();
|
||||
}
|
||||
},
|
||||
|
||||
uninit: function uninit() {
|
||||
if (this._initialized) {
|
||||
Services.prefs.removeObserver(PREF_DISABLED, this, false);
|
||||
Services.prefs.removeObserver(PREF_DISABLED_PLUGIN_TYPES, this, false);
|
||||
Services.obs.removeObserver(this, TOPIC_PDFJS_HANDLER_CHANGED, false);
|
||||
Services.obs.removeObserver(this, TOPIC_PLUGINS_LIST_UPDATED, false);
|
||||
Services.obs.removeObserver(this, TOPIC_PLUGIN_INFO_UPDATED, false);
|
||||
this._initialized = false;
|
||||
}
|
||||
this._ensureUnregistered();
|
||||
},
|
||||
|
||||
_migrate: function migrate() {
|
||||
const VERSION = 2;
|
||||
var currentVersion = getIntPref(PREF_MIGRATION_VERSION, 0);
|
||||
|
@ -202,10 +246,12 @@ let PdfJs = {
|
|||
|
||||
// nsIObserver
|
||||
observe: function observe(aSubject, aTopic, aData) {
|
||||
if (this.enabled)
|
||||
this._ensureRegistered();
|
||||
else
|
||||
this._ensureUnregistered();
|
||||
this.updateRegistration();
|
||||
if (Services.appinfo.processType == Services.appinfo.PROCESS_TYPE_DEFAULT) {
|
||||
let jsm = "resource://pdf.js/PdfjsChromeUtils.jsm";
|
||||
let PdfjsChromeUtils = Components.utils.import(jsm, {}).PdfjsChromeUtils;
|
||||
PdfjsChromeUtils.notifyChildOfSettingsChange();
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -219,11 +265,8 @@ let PdfJs = {
|
|||
return false;
|
||||
}
|
||||
|
||||
// the 'application/pdf' handler is selected as internal?
|
||||
var handlerInfo = Svc.mime
|
||||
.getFromTypeAndExtension(PDF_CONTENT_TYPE, 'pdf');
|
||||
if (handlerInfo.alwaysAskBeforeHandling ||
|
||||
handlerInfo.preferredAction !== Ci.nsIHandlerInfo.handleInternally) {
|
||||
// Check if the 'application/pdf' preview handler is configured properly.
|
||||
if (!isDefaultHandler()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2013 Mozilla Foundation
|
||||
*
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
|
@ -48,6 +48,9 @@ XPCOMUtils.defineLazyModuleGetter(this, 'PrivateBrowsingUtils',
|
|||
XPCOMUtils.defineLazyModuleGetter(this, 'PdfJsTelemetry',
|
||||
'resource://pdf.js/PdfJsTelemetry.jsm');
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, 'PdfjsContentUtils',
|
||||
'resource://pdf.js/PdfjsContentUtils.jsm');
|
||||
|
||||
var Svc = {};
|
||||
XPCOMUtils.defineLazyServiceGetter(Svc, 'mime',
|
||||
'@mozilla.org/mime;1',
|
||||
|
@ -61,10 +64,16 @@ function getContainingBrowser(domWindow) {
|
|||
}
|
||||
|
||||
function getChromeWindow(domWindow) {
|
||||
if (PdfjsContentUtils.isRemote) {
|
||||
return PdfjsContentUtils.getChromeWindow(domWindow);
|
||||
}
|
||||
return getContainingBrowser(domWindow).ownerDocument.defaultView;
|
||||
}
|
||||
|
||||
function getFindBar(domWindow) {
|
||||
if (PdfjsContentUtils.isRemote) {
|
||||
return PdfjsContentUtils.getFindBar(domWindow);
|
||||
}
|
||||
var browser = getContainingBrowser(domWindow);
|
||||
try {
|
||||
var tabbrowser = browser.getTabBrowser();
|
||||
|
@ -77,10 +86,6 @@ function getFindBar(domWindow) {
|
|||
}
|
||||
}
|
||||
|
||||
function setBoolPref(pref, value) {
|
||||
Services.prefs.setBoolPref(pref, value);
|
||||
}
|
||||
|
||||
function getBoolPref(pref, def) {
|
||||
try {
|
||||
return Services.prefs.getBoolPref(pref);
|
||||
|
@ -89,10 +94,6 @@ function getBoolPref(pref, def) {
|
|||
}
|
||||
}
|
||||
|
||||
function setIntPref(pref, value) {
|
||||
Services.prefs.setIntPref(pref, value);
|
||||
}
|
||||
|
||||
function getIntPref(pref, def) {
|
||||
try {
|
||||
return Services.prefs.getIntPref(pref);
|
||||
|
@ -101,13 +102,6 @@ function getIntPref(pref, def) {
|
|||
}
|
||||
}
|
||||
|
||||
function setStringPref(pref, value) {
|
||||
var str = Cc['@mozilla.org/supports-string;1']
|
||||
.createInstance(Ci.nsISupportsString);
|
||||
str.data = value;
|
||||
Services.prefs.setComplexValue(pref, Ci.nsISupportsString, str);
|
||||
}
|
||||
|
||||
function getStringPref(pref, def) {
|
||||
try {
|
||||
return Services.prefs.getComplexValue(pref, Ci.nsISupportsString).data;
|
||||
|
@ -117,8 +111,9 @@ function getStringPref(pref, def) {
|
|||
}
|
||||
|
||||
function log(aMsg) {
|
||||
if (!getBoolPref(PREF_PREFIX + '.pdfBugEnabled', false))
|
||||
if (!getBoolPref(PREF_PREFIX + '.pdfBugEnabled', false)) {
|
||||
return;
|
||||
}
|
||||
var msg = 'PdfStreamConverter.js: ' + (aMsg.join ? aMsg.join('') : aMsg);
|
||||
Services.console.logStringMessage(msg);
|
||||
dump(msg + '\n');
|
||||
|
@ -423,53 +418,10 @@ ChromeActions.prototype = {
|
|||
} else {
|
||||
message = getLocalizedString(strings, 'unsupported_feature');
|
||||
}
|
||||
|
||||
PdfJsTelemetry.onFallback();
|
||||
|
||||
var notificationBox = null;
|
||||
try {
|
||||
// Based on MDN's "Working with windows in chrome code"
|
||||
var mainWindow = domWindow
|
||||
.QueryInterface(Components.interfaces.nsIInterfaceRequestor)
|
||||
.getInterface(Components.interfaces.nsIWebNavigation)
|
||||
.QueryInterface(Components.interfaces.nsIDocShellTreeItem)
|
||||
.rootTreeItem
|
||||
.QueryInterface(Components.interfaces.nsIInterfaceRequestor)
|
||||
.getInterface(Components.interfaces.nsIDOMWindow);
|
||||
var browser = mainWindow.gBrowser
|
||||
.getBrowserForDocument(domWindow.top.document);
|
||||
notificationBox = mainWindow.gBrowser.getNotificationBox(browser);
|
||||
} catch (e) {
|
||||
log('Unable to get a notification box for the fallback message');
|
||||
return;
|
||||
}
|
||||
|
||||
// Flag so we don't call the response callback twice, since if the user
|
||||
// clicks open with different viewer both the button callback and
|
||||
// eventCallback will be called.
|
||||
var sentResponse = false;
|
||||
var buttons = [{
|
||||
label: getLocalizedString(strings, 'open_with_different_viewer'),
|
||||
accessKey: getLocalizedString(strings, 'open_with_different_viewer',
|
||||
'accessKey'),
|
||||
callback: function() {
|
||||
sentResponse = true;
|
||||
sendResponse(true);
|
||||
}
|
||||
}];
|
||||
notificationBox.appendNotification(message, 'pdfjs-fallback', null,
|
||||
notificationBox.PRIORITY_INFO_LOW,
|
||||
buttons,
|
||||
function eventsCallback(eventType) {
|
||||
// Currently there is only one event "removed" but if there are any other
|
||||
// added in the future we still only care about removed at the moment.
|
||||
if (eventType !== 'removed')
|
||||
return;
|
||||
// Don't send a response again if we already responded when the button was
|
||||
// clicked.
|
||||
if (!sentResponse)
|
||||
sendResponse(false);
|
||||
});
|
||||
PdfjsContentUtils.displayWarning(domWindow, message, sendResponse,
|
||||
getLocalizedString(strings, 'open_with_different_viewer'),
|
||||
getLocalizedString(strings, 'open_with_different_viewer', 'accessKey'));
|
||||
},
|
||||
updateFindControlState: function(data) {
|
||||
if (!this.supportsIntegratedFind())
|
||||
|
@ -500,17 +452,17 @@ ChromeActions.prototype = {
|
|||
prefName = (PREF_PREFIX + '.' + key);
|
||||
switch (typeof prefValue) {
|
||||
case 'boolean':
|
||||
setBoolPref(prefName, prefValue);
|
||||
PdfjsContentUtils.setBoolPref(prefName, prefValue);
|
||||
break;
|
||||
case 'number':
|
||||
setIntPref(prefName, prefValue);
|
||||
PdfjsContentUtils.setIntPref(prefName, prefValue);
|
||||
break;
|
||||
case 'string':
|
||||
if (prefValue.length > MAX_STRING_PREF_LENGTH) {
|
||||
log('setPreferences - Exceeded the maximum allowed length ' +
|
||||
'for a string preference.');
|
||||
} else {
|
||||
setStringPref(prefName, prefValue);
|
||||
PdfjsContentUtils.setStringPref(prefName, prefValue);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
@ -793,7 +745,12 @@ FindEventManager.prototype.handleEvent = function(e) {
|
|||
detail = makeContentReadable(detail, contentWindow);
|
||||
var forward = contentWindow.document.createEvent('CustomEvent');
|
||||
forward.initCustomEvent(e.type, true, true, detail);
|
||||
contentWindow.dispatchEvent(forward);
|
||||
// Due to restrictions with cpow use, we can't dispatch
|
||||
// dom events with an urgent message on the stack. So bounce
|
||||
// this off the main thread to make it async.
|
||||
Services.tm.mainThread.dispatch(function () {
|
||||
contentWindow.dispatchEvent(forward);
|
||||
}, Ci.nsIThread.DISPATCH_NORMAL);
|
||||
e.preventDefault();
|
||||
}
|
||||
};
|
||||
|
@ -911,7 +868,6 @@ PdfStreamConverter.prototype = {
|
|||
PdfJsTelemetry.onViewerIsUsed();
|
||||
PdfJsTelemetry.onDocumentSize(aRequest.contentLength);
|
||||
|
||||
|
||||
// Creating storage for PDF data
|
||||
var contentLength = aRequest.contentLength;
|
||||
this.dataListener = new PdfDataListener(contentLength);
|
||||
|
|
|
@ -0,0 +1,328 @@
|
|||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
/*globals DEFAULT_PREFERENCES */
|
||||
|
||||
'use strict';
|
||||
|
||||
var EXPORTED_SYMBOLS = ['PdfjsChromeUtils'];
|
||||
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
const Cr = Components.results;
|
||||
const Cu = Components.utils;
|
||||
|
||||
const PREF_PREFIX = 'pdfjs';
|
||||
const PDF_CONTENT_TYPE = 'application/pdf';
|
||||
|
||||
Cu.import('resource://gre/modules/XPCOMUtils.jsm');
|
||||
Cu.import('resource://gre/modules/Services.jsm');
|
||||
|
||||
let Svc = {};
|
||||
XPCOMUtils.defineLazyServiceGetter(Svc, 'mime',
|
||||
'@mozilla.org/mime;1',
|
||||
'nsIMIMEService');
|
||||
|
||||
|
||||
var DEFAULT_PREFERENCES = {
|
||||
showPreviousViewOnLoad: true,
|
||||
defaultZoomValue: '',
|
||||
sidebarViewOnLoad: 0,
|
||||
enableHandToolOnLoad: false,
|
||||
enableWebGL: false,
|
||||
disableRange: false,
|
||||
disableAutoFetch: false,
|
||||
disableFontFace: false,
|
||||
disableTextLayer: false,
|
||||
useOnlyCssZoom: false
|
||||
};
|
||||
|
||||
|
||||
let PdfjsChromeUtils = {
|
||||
// For security purposes when running remote, we restrict preferences
|
||||
// content can access.
|
||||
_allowedPrefNames: Object.keys(DEFAULT_PREFERENCES),
|
||||
_ppmm: null,
|
||||
_mmg: null,
|
||||
|
||||
/*
|
||||
* Public API
|
||||
*/
|
||||
|
||||
init: function () {
|
||||
if (!this._ppmm) {
|
||||
// global parent process message manager (PPMM)
|
||||
this._ppmm = Cc["@mozilla.org/parentprocessmessagemanager;1"].getService(Ci.nsIMessageBroadcaster);
|
||||
this._ppmm.addMessageListener("PDFJS:Parent:clearUserPref", this);
|
||||
this._ppmm.addMessageListener("PDFJS:Parent:setIntPref", this);
|
||||
this._ppmm.addMessageListener("PDFJS:Parent:setBoolPref", this);
|
||||
this._ppmm.addMessageListener("PDFJS:Parent:setCharPref", this);
|
||||
this._ppmm.addMessageListener("PDFJS:Parent:setStringPref", this);
|
||||
this._ppmm.addMessageListener("PDFJS:Parent:isDefaultHandlerApp", this);
|
||||
|
||||
// global dom message manager (MMg)
|
||||
this._mmg = Cc["@mozilla.org/globalmessagemanager;1"].getService(Ci.nsIMessageListenerManager);
|
||||
this._mmg.addMessageListener("PDFJS:Parent:getChromeWindow", this);
|
||||
this._mmg.addMessageListener("PDFJS:Parent:getFindBar", this);
|
||||
this._mmg.addMessageListener("PDFJS:Parent:displayWarning", this);
|
||||
|
||||
// observer to handle shutdown
|
||||
Services.obs.addObserver(this, "quit-application", false);
|
||||
}
|
||||
},
|
||||
|
||||
uninit: function () {
|
||||
if (this._ppmm) {
|
||||
this._ppmm.removeMessageListener("PDFJS:Parent:clearUserPref", this);
|
||||
this._ppmm.removeMessageListener("PDFJS:Parent:setIntPref", this);
|
||||
this._ppmm.removeMessageListener("PDFJS:Parent:setBoolPref", this);
|
||||
this._ppmm.removeMessageListener("PDFJS:Parent:setCharPref", this);
|
||||
this._ppmm.removeMessageListener("PDFJS:Parent:setStringPref", this);
|
||||
this._ppmm.removeMessageListener("PDFJS:Parent:isDefaultHandlerApp", this);
|
||||
|
||||
this._mmg.removeMessageListener("PDFJS:Parent:getChromeWindow", this);
|
||||
this._mmg.removeMessageListener("PDFJS:Parent:getFindBar", this);
|
||||
this._mmg.removeMessageListener("PDFJS:Parent:displayWarning", this);
|
||||
|
||||
Services.obs.removeObserver(this, "quit-application", false);
|
||||
|
||||
this._mmg = null;
|
||||
this._ppmm = null;
|
||||
}
|
||||
},
|
||||
|
||||
/*
|
||||
* Called by the main module when preference changes are picked up
|
||||
* in the parent process. Observers don't propagate so we need to
|
||||
* instruct the child to refresh its configuration and (possibly)
|
||||
* the module's registration.
|
||||
*/
|
||||
notifyChildOfSettingsChange: function () {
|
||||
if (Services.appinfo.processType == Services.appinfo.PROCESS_TYPE_DEFAULT &&
|
||||
this._ppmm) {
|
||||
// XXX kinda bad, we want to get the parent process mm associated
|
||||
// with the content process. _ppmm is currently the global process
|
||||
// manager, which means this is going to fire to every child process
|
||||
// we have open. Unfortunately I can't find a way to get at that
|
||||
// process specific mm from js.
|
||||
this._ppmm.broadcastAsyncMessage("PDFJS:Child:refreshSettings", {});
|
||||
}
|
||||
},
|
||||
|
||||
/*
|
||||
* Events
|
||||
*/
|
||||
|
||||
observe: function(aSubject, aTopic, aData) {
|
||||
if (aTopic == "quit-application") {
|
||||
this.uninit();
|
||||
}
|
||||
},
|
||||
|
||||
receiveMessage: function (aMsg) {
|
||||
switch (aMsg.name) {
|
||||
case "PDFJS:Parent:clearUserPref":
|
||||
this._clearUserPref(aMsg.data.name);
|
||||
break;
|
||||
case "PDFJS:Parent:setIntPref":
|
||||
this._setIntPref(aMsg.data.name, aMsg.data.value);
|
||||
break;
|
||||
case "PDFJS:Parent:setBoolPref":
|
||||
this._setBoolPref(aMsg.data.name, aMsg.data.value);
|
||||
break;
|
||||
case "PDFJS:Parent:setCharPref":
|
||||
this._setCharPref(aMsg.data.name, aMsg.data.value);
|
||||
break;
|
||||
case "PDFJS:Parent:setStringPref":
|
||||
this._setStringPref(aMsg.data.name, aMsg.data.value);
|
||||
break;
|
||||
case "PDFJS:Parent:isDefaultHandlerApp":
|
||||
return this.isDefaultHandlerApp();
|
||||
case "PDFJS:Parent:displayWarning":
|
||||
this._displayWarning(aMsg);
|
||||
break;
|
||||
|
||||
// CPOW getters
|
||||
case "PDFJS:Parent:getChromeWindow":
|
||||
return this._getChromeWindow(aMsg);
|
||||
case "PDFJS:Parent:getFindBar":
|
||||
return this._getFindBar(aMsg);
|
||||
}
|
||||
},
|
||||
|
||||
/*
|
||||
* Internal
|
||||
*/
|
||||
|
||||
_getChromeWindow: function (aMsg) {
|
||||
// See the child module, our return result here can't be the element
|
||||
// since return results don't get auto CPOW'd.
|
||||
let browser = aMsg.target;
|
||||
let wrapper = new PdfjsWindowWrapper(browser);
|
||||
let suitcase = aMsg.objects.suitcase;
|
||||
suitcase.setChromeWindow(wrapper);
|
||||
return true;
|
||||
},
|
||||
|
||||
_getFindBar: function (aMsg) {
|
||||
// We send this over via the window's message manager, so target should
|
||||
// be the dom window.
|
||||
let browser = aMsg.target;
|
||||
let wrapper = new PdfjsFindbarWrapper(browser);
|
||||
let suitcase = aMsg.objects.suitcase;
|
||||
suitcase.setFindBar(wrapper);
|
||||
return true;
|
||||
},
|
||||
|
||||
_ensurePreferenceAllowed: function (aPrefName) {
|
||||
let unPrefixedName = aPrefName.split(PREF_PREFIX + '.');
|
||||
if (unPrefixedName[0] !== '' ||
|
||||
this._allowedPrefNames.indexOf(unPrefixedName[1]) === -1) {
|
||||
let msg = "'" + aPrefName + "' ";
|
||||
msg += "can't be accessed from content. See PdfjsChromeUtils."
|
||||
throw new Error(msg);
|
||||
}
|
||||
},
|
||||
|
||||
_clearUserPref: function (aPrefName) {
|
||||
this._ensurePreferenceAllowed(aPrefName);
|
||||
Services.prefs.clearUserPref(aPrefName);
|
||||
},
|
||||
|
||||
_setIntPref: function (aPrefName, aPrefValue) {
|
||||
this._ensurePreferenceAllowed(aPrefName);
|
||||
Services.prefs.setIntPref(aPrefName, aPrefValue);
|
||||
},
|
||||
|
||||
_setBoolPref: function (aPrefName, aPrefValue) {
|
||||
this._ensurePreferenceAllowed(aPrefName);
|
||||
Services.prefs.setBoolPref(aPrefName, aPrefValue);
|
||||
},
|
||||
|
||||
_setCharPref: function (aPrefName, aPrefValue) {
|
||||
this._ensurePreferenceAllowed(aPrefName);
|
||||
Services.prefs.setCharPref(aPrefName, aPrefValue);
|
||||
},
|
||||
|
||||
_setStringPref: function (aPrefName, aPrefValue) {
|
||||
this._ensurePreferenceAllowed(aPrefName);
|
||||
let str = Cc['@mozilla.org/supports-string;1']
|
||||
.createInstance(Ci.nsISupportsString);
|
||||
str.data = aPrefValue;
|
||||
Services.prefs.setComplexValue(aPrefName, Ci.nsISupportsString, str);
|
||||
},
|
||||
|
||||
/*
|
||||
* Svc.mime doesn't have profile information in the child, so
|
||||
* we bounce this pdfjs enabled configuration check over to the
|
||||
* parent.
|
||||
*/
|
||||
isDefaultHandlerApp: function () {
|
||||
var handlerInfo = Svc.mime.getFromTypeAndExtension(PDF_CONTENT_TYPE, 'pdf');
|
||||
return !handlerInfo.alwaysAskBeforeHandling &&
|
||||
handlerInfo.preferredAction == Ci.nsIHandlerInfo.handleInternally;
|
||||
},
|
||||
|
||||
/*
|
||||
* Display a notification warning when the renderer isn't sure
|
||||
* a pdf displayed correctly.
|
||||
*/
|
||||
_displayWarning: function (aMsg) {
|
||||
let json = aMsg.data;
|
||||
let browser = aMsg.target;
|
||||
let cpowCallback = aMsg.objects.callback;
|
||||
let tabbrowser = browser.getTabBrowser();
|
||||
let notificationBox = tabbrowser.getNotificationBox(browser);
|
||||
// Flag so we don't call the response callback twice, since if the user
|
||||
// clicks open with different viewer both the button callback and
|
||||
// eventCallback will be called.
|
||||
let responseSent = false;
|
||||
let buttons = [{
|
||||
label: json.label,
|
||||
accessKey: json.accessKey,
|
||||
callback: function() {
|
||||
responseSent = true;
|
||||
cpowCallback(true);
|
||||
}
|
||||
}];
|
||||
notificationBox.appendNotification(json.message, 'pdfjs-fallback', null,
|
||||
notificationBox.PRIORITY_INFO_LOW,
|
||||
buttons,
|
||||
function eventsCallback(eventType) {
|
||||
// Currently there is only one event "removed" but if there are any other
|
||||
// added in the future we still only care about removed at the moment.
|
||||
if (eventType !== 'removed') {
|
||||
return;
|
||||
}
|
||||
// Don't send a response again if we already responded when the button was
|
||||
// clicked.
|
||||
if (responseSent) {
|
||||
return;
|
||||
}
|
||||
cpowCallback(false);
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
/*
|
||||
* CPOW security features require chrome objects declare exposed
|
||||
* properties via __exposedProps__. We don't want to expose things
|
||||
* directly on the findbar, so we wrap the findbar in a smaller
|
||||
* object here that supports the features pdf.js needs.
|
||||
*/
|
||||
function PdfjsFindbarWrapper(aBrowser) {
|
||||
let tabbrowser = aBrowser.getTabBrowser();
|
||||
let tab = tabbrowser._getTabForBrowser(aBrowser);
|
||||
this._findbar = tabbrowser.getFindBar(tab);
|
||||
};
|
||||
|
||||
PdfjsFindbarWrapper.prototype = {
|
||||
__exposedProps__: {
|
||||
addEventListener: "r",
|
||||
removeEventListener: "r",
|
||||
updateControlState: "r",
|
||||
},
|
||||
_findbar: null,
|
||||
|
||||
updateControlState: function (aResult, aFindPrevious) {
|
||||
this._findbar.updateControlState(aResult, aFindPrevious);
|
||||
},
|
||||
|
||||
addEventListener: function (aType, aListener, aUseCapture, aWantsUntrusted) {
|
||||
this._findbar.addEventListener(aType, aListener, aUseCapture, aWantsUntrusted);
|
||||
},
|
||||
|
||||
removeEventListener: function (aType, aListener, aUseCapture) {
|
||||
this._findbar.removeEventListener(aType, aListener, aUseCapture);
|
||||
}
|
||||
};
|
||||
|
||||
function PdfjsWindowWrapper(aBrowser) {
|
||||
this._window = aBrowser.ownerDocument.defaultView;
|
||||
};
|
||||
|
||||
PdfjsWindowWrapper.prototype = {
|
||||
__exposedProps__: {
|
||||
valueOf: "r",
|
||||
},
|
||||
_window: null,
|
||||
|
||||
valueOf: function () {
|
||||
return this._window.valueOf();
|
||||
}
|
||||
};
|
||||
|
||||
|
|
@ -0,0 +1,193 @@
|
|||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
|
||||
var EXPORTED_SYMBOLS = ['PdfjsContentUtils'];
|
||||
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
const Cr = Components.results;
|
||||
const Cu = Components.utils;
|
||||
|
||||
Cu.import('resource://gre/modules/XPCOMUtils.jsm');
|
||||
Cu.import('resource://gre/modules/Services.jsm');
|
||||
|
||||
let PdfjsContentUtils = {
|
||||
_mm: null,
|
||||
|
||||
/*
|
||||
* Public API
|
||||
*/
|
||||
|
||||
get isRemote() {
|
||||
return Services.appinfo.processType == Services.appinfo.PROCESS_TYPE_CONTENT;
|
||||
},
|
||||
|
||||
init: function () {
|
||||
// child *process* mm, or when loaded into the parent for in-content
|
||||
// support the psuedo child process mm 'child PPMM'.
|
||||
if (!this._mm) {
|
||||
this._mm = Cc["@mozilla.org/childprocessmessagemanager;1"].getService(Ci.nsISyncMessageSender);
|
||||
this._mm.addMessageListener("PDFJS:Child:refreshSettings", this);
|
||||
Services.obs.addObserver(this, "quit-application", false);
|
||||
}
|
||||
},
|
||||
|
||||
uninit: function () {
|
||||
if (this._mm) {
|
||||
this._mm.removeMessageListener("PDFJS:Child:refreshSettings", this);
|
||||
Services.obs.removeObserver(this, "quit-application");
|
||||
}
|
||||
this._mm = null;
|
||||
},
|
||||
|
||||
/*
|
||||
* prefs utilities - the child does not have write access to prefs.
|
||||
* note, the pref names here are cross-checked against a list of
|
||||
* approved pdfjs prefs in chrome utils.
|
||||
*/
|
||||
|
||||
clearUserPref: function (aPrefName) {
|
||||
this._mm.sendSyncMessage("PDFJS:Parent:clearUserPref", {
|
||||
name: aPrefName
|
||||
});
|
||||
},
|
||||
|
||||
setIntPref: function (aPrefName, aPrefValue) {
|
||||
this._mm.sendSyncMessage("PDFJS:Parent:setIntPref", {
|
||||
name: aPrefName,
|
||||
value: aPrefValue
|
||||
});
|
||||
},
|
||||
|
||||
setBoolPref: function (aPrefName, aPrefValue) {
|
||||
this._mm.sendSyncMessage("PDFJS:Parent:setBoolPref", {
|
||||
name: aPrefName,
|
||||
value: aPrefValue
|
||||
});
|
||||
},
|
||||
|
||||
setCharPref: function (aPrefName, aPrefValue) {
|
||||
this._mm.sendSyncMessage("PDFJS:Parent:setCharPref", {
|
||||
name: aPrefName,
|
||||
value: aPrefValue
|
||||
});
|
||||
},
|
||||
|
||||
setStringPref: function (aPrefName, aPrefValue) {
|
||||
this._mm.sendSyncMessage("PDFJS:Parent:setStringPref", {
|
||||
name: aPrefName,
|
||||
value: aPrefValue
|
||||
});
|
||||
},
|
||||
|
||||
/*
|
||||
* Forwards default app query to the parent where we check various
|
||||
* handler app settings only available in the parent process.
|
||||
*/
|
||||
isDefaultHandlerApp: function () {
|
||||
return this._mm.sendSyncMessage("PDFJS:Parent:isDefaultHandlerApp")[0];
|
||||
},
|
||||
|
||||
/*
|
||||
* Request the display of a notification warning in the associated window
|
||||
* when the renderer isn't sure a pdf displayed correctly.
|
||||
*/
|
||||
displayWarning: function (aWindow, aMessage, aCallback, aLabel, accessKey) {
|
||||
// the child's dom frame mm associated with the window.
|
||||
let winmm = aWindow.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIDocShell)
|
||||
.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIContentFrameMessageManager);
|
||||
winmm.sendAsyncMessage("PDFJS:Parent:displayWarning", {
|
||||
message: aMessage,
|
||||
label: aLabel,
|
||||
accessKey: accessKey
|
||||
}, {
|
||||
callback: aCallback
|
||||
});
|
||||
},
|
||||
|
||||
/*
|
||||
* Events
|
||||
*/
|
||||
|
||||
observe: function(aSubject, aTopic, aData) {
|
||||
if (aTopic == "quit-application") {
|
||||
this.uninit();
|
||||
}
|
||||
},
|
||||
|
||||
receiveMessage: function (aMsg) {
|
||||
switch (aMsg.name) {
|
||||
case "PDFJS:Child:refreshSettings":
|
||||
// Only react to this if we are remote.
|
||||
if (Services.appinfo.processType == Services.appinfo.PROCESS_TYPE_CONTENT) {
|
||||
let jsm = "resource://pdf.js/PdfJs.jsm";
|
||||
let pdfjs = Components.utils.import(jsm, {}).PdfJs;
|
||||
pdfjs.updateRegistration();
|
||||
}
|
||||
break;
|
||||
}
|
||||
},
|
||||
|
||||
/*
|
||||
* CPOWs
|
||||
*/
|
||||
|
||||
getChromeWindow: function (aWindow) {
|
||||
let winmm = aWindow.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIDocShell)
|
||||
.sameTypeRootTreeItem
|
||||
.QueryInterface(Ci.nsIDocShell)
|
||||
.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIContentFrameMessageManager);
|
||||
// Sync calls don't support cpow wrapping of returned results, so we
|
||||
// send over a small container for the object we want.
|
||||
let suitcase = {
|
||||
_window: null,
|
||||
setChromeWindow: function (aObj) { this._window = aObj; }
|
||||
}
|
||||
if (!winmm.sendSyncMessage("PDFJS:Parent:getChromeWindow", {},
|
||||
{ suitcase: suitcase })[0]) {
|
||||
Cu.reportError("A request for a CPOW wrapped chrome window " +
|
||||
"failed for unknown reasons.");
|
||||
return null;
|
||||
}
|
||||
return suitcase._window;
|
||||
},
|
||||
|
||||
getFindBar: function (aWindow) {
|
||||
let winmm = aWindow.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIDocShell)
|
||||
.sameTypeRootTreeItem
|
||||
.QueryInterface(Ci.nsIDocShell)
|
||||
.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIContentFrameMessageManager);
|
||||
let suitcase = {
|
||||
_findbar: null,
|
||||
setFindBar: function (aObj) { this._findbar = aObj; }
|
||||
}
|
||||
if (!winmm.sendSyncMessage("PDFJS:Parent:getFindBar", {},
|
||||
{ suitcase: suitcase })[0]) {
|
||||
Cu.reportError("A request for a CPOW wrapped findbar " +
|
||||
"failed for unknown reasons.");
|
||||
return null;
|
||||
}
|
||||
return suitcase._findbar;
|
||||
}
|
||||
};
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
|
@ -22,8 +22,8 @@ if (typeof PDFJS === 'undefined') {
|
|||
(typeof window !== 'undefined' ? window : this).PDFJS = {};
|
||||
}
|
||||
|
||||
PDFJS.version = '1.0.712';
|
||||
PDFJS.build = '6969ed4';
|
||||
PDFJS.version = '1.0.801';
|
||||
PDFJS.build = 'e77e5c4';
|
||||
|
||||
(function pdfjsWrapper() {
|
||||
// Use strict in our context only - users might not want it
|
||||
|
@ -373,6 +373,7 @@ var PasswordException = (function PasswordExceptionClosure() {
|
|||
|
||||
return PasswordException;
|
||||
})();
|
||||
PDFJS.PasswordException = PasswordException;
|
||||
|
||||
var UnknownErrorException = (function UnknownErrorExceptionClosure() {
|
||||
function UnknownErrorException(msg, details) {
|
||||
|
@ -386,6 +387,7 @@ var UnknownErrorException = (function UnknownErrorExceptionClosure() {
|
|||
|
||||
return UnknownErrorException;
|
||||
})();
|
||||
PDFJS.UnknownErrorException = UnknownErrorException;
|
||||
|
||||
var InvalidPDFException = (function InvalidPDFExceptionClosure() {
|
||||
function InvalidPDFException(msg) {
|
||||
|
@ -398,6 +400,7 @@ var InvalidPDFException = (function InvalidPDFExceptionClosure() {
|
|||
|
||||
return InvalidPDFException;
|
||||
})();
|
||||
PDFJS.InvalidPDFException = InvalidPDFException;
|
||||
|
||||
var MissingPDFException = (function MissingPDFExceptionClosure() {
|
||||
function MissingPDFException(msg) {
|
||||
|
@ -410,6 +413,22 @@ var MissingPDFException = (function MissingPDFExceptionClosure() {
|
|||
|
||||
return MissingPDFException;
|
||||
})();
|
||||
PDFJS.MissingPDFException = MissingPDFException;
|
||||
|
||||
var UnexpectedResponseException =
|
||||
(function UnexpectedResponseExceptionClosure() {
|
||||
function UnexpectedResponseException(msg, status) {
|
||||
this.name = 'UnexpectedResponseException';
|
||||
this.message = msg;
|
||||
this.status = status;
|
||||
}
|
||||
|
||||
UnexpectedResponseException.prototype = new Error();
|
||||
UnexpectedResponseException.constructor = UnexpectedResponseException;
|
||||
|
||||
return UnexpectedResponseException;
|
||||
})();
|
||||
PDFJS.UnexpectedResponseException = UnexpectedResponseException;
|
||||
|
||||
var NotImplementedException = (function NotImplementedExceptionClosure() {
|
||||
function NotImplementedException(msg) {
|
||||
|
@ -1448,6 +1467,11 @@ PDFJS.maxCanvasPixels = (PDFJS.maxCanvasPixels === undefined ?
|
|||
* parameters: function that needs to be called with new password and reason
|
||||
* (see {PasswordResponses}).
|
||||
*
|
||||
* @param {function} progressCallback is optional. It is used to be able to
|
||||
* monitor the loading progress of the PDF file (necessary to implement e.g.
|
||||
* a loading bar). The callback receives an {Object} with the properties:
|
||||
* {number} loaded and {number} total.
|
||||
*
|
||||
* @return {Promise} A promise that is resolved with {@link PDFDocumentProxy}
|
||||
* object.
|
||||
*/
|
||||
|
@ -2107,36 +2131,46 @@ var WorkerTransport = (function WorkerTransportClosure() {
|
|||
this.workerReadyCapability.resolve(pdfDocument);
|
||||
}, this);
|
||||
|
||||
messageHandler.on('NeedPassword', function transportPassword(data) {
|
||||
messageHandler.on('NeedPassword',
|
||||
function transportNeedPassword(exception) {
|
||||
if (this.passwordCallback) {
|
||||
return this.passwordCallback(updatePassword,
|
||||
PasswordResponses.NEED_PASSWORD);
|
||||
}
|
||||
this.workerReadyCapability.reject(data.exception.message,
|
||||
data.exception);
|
||||
this.workerReadyCapability.reject(
|
||||
new PasswordException(exception.message, exception.code));
|
||||
}, this);
|
||||
|
||||
messageHandler.on('IncorrectPassword', function transportBadPass(data) {
|
||||
messageHandler.on('IncorrectPassword',
|
||||
function transportIncorrectPassword(exception) {
|
||||
if (this.passwordCallback) {
|
||||
return this.passwordCallback(updatePassword,
|
||||
PasswordResponses.INCORRECT_PASSWORD);
|
||||
}
|
||||
this.workerReadyCapability.reject(data.exception.message,
|
||||
data.exception);
|
||||
this.workerReadyCapability.reject(
|
||||
new PasswordException(exception.message, exception.code));
|
||||
}, this);
|
||||
|
||||
messageHandler.on('InvalidPDF', function transportInvalidPDF(data) {
|
||||
this.workerReadyCapability.reject(data.exception.name, data.exception);
|
||||
messageHandler.on('InvalidPDF', function transportInvalidPDF(exception) {
|
||||
this.workerReadyCapability.reject(
|
||||
new InvalidPDFException(exception.message));
|
||||
}, this);
|
||||
|
||||
messageHandler.on('MissingPDF', function transportMissingPDF(data) {
|
||||
this.workerReadyCapability.reject(data.exception.message,
|
||||
data.exception);
|
||||
messageHandler.on('MissingPDF', function transportMissingPDF(exception) {
|
||||
this.workerReadyCapability.reject(
|
||||
new MissingPDFException(exception.message));
|
||||
}, this);
|
||||
|
||||
messageHandler.on('UnknownError', function transportUnknownError(data) {
|
||||
this.workerReadyCapability.reject(data.exception.message,
|
||||
data.exception);
|
||||
messageHandler.on('UnexpectedResponse',
|
||||
function transportUnexpectedResponse(exception) {
|
||||
this.workerReadyCapability.reject(
|
||||
new UnexpectedResponseException(exception.message, exception.status));
|
||||
}, this);
|
||||
|
||||
messageHandler.on('UnknownError',
|
||||
function transportUnknownError(exception) {
|
||||
this.workerReadyCapability.reject(
|
||||
new UnknownErrorException(exception.message, exception.details));
|
||||
}, this);
|
||||
|
||||
messageHandler.on('DataLoaded', function transportPage(data) {
|
||||
|
@ -2232,10 +2266,6 @@ var WorkerTransport = (function WorkerTransportClosure() {
|
|||
}
|
||||
}, this);
|
||||
|
||||
messageHandler.on('DocError', function transportDocError(data) {
|
||||
this.workerReadyCapability.reject(data);
|
||||
}, this);
|
||||
|
||||
messageHandler.on('PageError', function transportError(data) {
|
||||
var page = this.pageCache[data.pageNum - 1];
|
||||
var intentState = page.intentStates[data.intent];
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
|
@ -22,8 +22,8 @@ if (typeof PDFJS === 'undefined') {
|
|||
(typeof window !== 'undefined' ? window : this).PDFJS = {};
|
||||
}
|
||||
|
||||
PDFJS.version = '1.0.712';
|
||||
PDFJS.build = '6969ed4';
|
||||
PDFJS.version = '1.0.801';
|
||||
PDFJS.build = 'e77e5c4';
|
||||
|
||||
(function pdfjsWrapper() {
|
||||
// Use strict in our context only - users might not want it
|
||||
|
@ -373,6 +373,7 @@ var PasswordException = (function PasswordExceptionClosure() {
|
|||
|
||||
return PasswordException;
|
||||
})();
|
||||
PDFJS.PasswordException = PasswordException;
|
||||
|
||||
var UnknownErrorException = (function UnknownErrorExceptionClosure() {
|
||||
function UnknownErrorException(msg, details) {
|
||||
|
@ -386,6 +387,7 @@ var UnknownErrorException = (function UnknownErrorExceptionClosure() {
|
|||
|
||||
return UnknownErrorException;
|
||||
})();
|
||||
PDFJS.UnknownErrorException = UnknownErrorException;
|
||||
|
||||
var InvalidPDFException = (function InvalidPDFExceptionClosure() {
|
||||
function InvalidPDFException(msg) {
|
||||
|
@ -398,6 +400,7 @@ var InvalidPDFException = (function InvalidPDFExceptionClosure() {
|
|||
|
||||
return InvalidPDFException;
|
||||
})();
|
||||
PDFJS.InvalidPDFException = InvalidPDFException;
|
||||
|
||||
var MissingPDFException = (function MissingPDFExceptionClosure() {
|
||||
function MissingPDFException(msg) {
|
||||
|
@ -410,6 +413,22 @@ var MissingPDFException = (function MissingPDFExceptionClosure() {
|
|||
|
||||
return MissingPDFException;
|
||||
})();
|
||||
PDFJS.MissingPDFException = MissingPDFException;
|
||||
|
||||
var UnexpectedResponseException =
|
||||
(function UnexpectedResponseExceptionClosure() {
|
||||
function UnexpectedResponseException(msg, status) {
|
||||
this.name = 'UnexpectedResponseException';
|
||||
this.message = msg;
|
||||
this.status = status;
|
||||
}
|
||||
|
||||
UnexpectedResponseException.prototype = new Error();
|
||||
UnexpectedResponseException.constructor = UnexpectedResponseException;
|
||||
|
||||
return UnexpectedResponseException;
|
||||
})();
|
||||
PDFJS.UnexpectedResponseException = UnexpectedResponseException;
|
||||
|
||||
var NotImplementedException = (function NotImplementedExceptionClosure() {
|
||||
function NotImplementedException(msg) {
|
||||
|
@ -1455,6 +1474,12 @@ var ChunkedStream = (function ChunkedStreamClosure() {
|
|||
return bytes.subarray(pos, end);
|
||||
},
|
||||
|
||||
peekByte: function ChunkedStream_peekByte() {
|
||||
var peekedByte = this.getByte();
|
||||
this.pos--;
|
||||
return peekedByte;
|
||||
},
|
||||
|
||||
peekBytes: function ChunkedStream_peekBytes(length) {
|
||||
var bytes = this.getBytes(length);
|
||||
this.pos -= bytes.length;
|
||||
|
@ -6863,20 +6888,21 @@ var CalRGBCS = (function CalRGBCSClosure() {
|
|||
convertToRgb(this, src, srcOffset, dest, destOffset, 1);
|
||||
},
|
||||
getRgbBuffer: function CalRGBCS_getRgbBuffer(src, srcOffset, count,
|
||||
dest, destOffset, bits) {
|
||||
dest, destOffset, bits,
|
||||
alpha01) {
|
||||
var scale = 1 / ((1 << bits) - 1);
|
||||
|
||||
for (var i = 0; i < count; ++i) {
|
||||
convertToRgb(this, src, srcOffset, dest, destOffset, scale);
|
||||
srcOffset += 3;
|
||||
destOffset += 3;
|
||||
destOffset += 3 + alpha01;
|
||||
}
|
||||
},
|
||||
getOutputLength: function CalRGBCS_getOutputLength(inputLength) {
|
||||
return inputLength;
|
||||
getOutputLength: function CalRGBCS_getOutputLength(inputLength, alpha01) {
|
||||
return (inputLength * (3 + alpha01) / 3) | 0;
|
||||
},
|
||||
isPassthrough: ColorSpace.prototype.isPassthrough,
|
||||
createRgbBuffer: ColorSpace.prototype.createRgbBuffer,
|
||||
fillRgb: ColorSpace.prototype.fillRgb,
|
||||
isDefaultDecode: function CalRGBCS_isDefaultDecode(decodeMap) {
|
||||
return ColorSpace.isDefaultDecode(decodeMap, this.numComps);
|
||||
},
|
||||
|
@ -11106,9 +11132,14 @@ var PartialEvaluator = (function PartialEvaluatorClosure() {
|
|||
// The Symbolic attribute can be misused for regular fonts
|
||||
// Heuristic: we have to check if the font is a standard one also
|
||||
if (!!(properties.flags & FontFlags.Symbolic)) {
|
||||
encoding = (!properties.file && /Symbol/i.test(properties.name) ?
|
||||
Encodings.SymbolSetEncoding :
|
||||
Encodings.MacRomanEncoding);
|
||||
encoding = Encodings.MacRomanEncoding;
|
||||
if (!properties.file) {
|
||||
if (/Symbol/i.test(properties.name)) {
|
||||
encoding = Encodings.SymbolSetEncoding;
|
||||
} else if (/Dingbats/i.test(properties.name)) {
|
||||
encoding = Encodings.ZapfDingbatsEncoding;
|
||||
}
|
||||
}
|
||||
}
|
||||
properties.defaultEncoding = encoding;
|
||||
}
|
||||
|
@ -13613,7 +13644,7 @@ var Encodings = {
|
|||
'parenrighttp', 'parenrightex', 'parenrightbt', 'bracketrighttp',
|
||||
'bracketrightex', 'bracketrightbt', 'bracerighttp', 'bracerightmid',
|
||||
'bracerightbt'],
|
||||
zapfDingbatsEncoding: ['', '', '', '', '', '', '', '', '', '', '', '', '', '',
|
||||
ZapfDingbatsEncoding: ['', '', '', '', '', '', '', '', '', '', '', '', '', '',
|
||||
'', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '',
|
||||
'space', 'a1', 'a2', 'a202', 'a3', 'a4', 'a5', 'a119', 'a118', 'a117',
|
||||
'a11', 'a12', 'a13', 'a14', 'a15', 'a16', 'a105', 'a17', 'a18', 'a19',
|
||||
|
@ -13624,19 +13655,19 @@ var Encodings = {
|
|||
'a57', 'a58', 'a59', 'a60', 'a61', 'a62', 'a63', 'a64', 'a65', 'a66',
|
||||
'a67', 'a68', 'a69', 'a70', 'a71', 'a72', 'a73', 'a74', 'a203', 'a75',
|
||||
'a204', 'a76', 'a77', 'a78', 'a79', 'a81', 'a82', 'a83', 'a84', 'a97',
|
||||
'a98', 'a99', 'a100', '', '', '', '', '', '', '', '', '', '', '', '', '',
|
||||
'', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '',
|
||||
'', '', 'a101', 'a102', 'a103', 'a104', 'a106', 'a107', 'a108', 'a112',
|
||||
'a111', 'a110', 'a109', 'a120', 'a121', 'a122', 'a123', 'a124', 'a125',
|
||||
'a126', 'a127', 'a128', 'a129', 'a130', 'a131', 'a132', 'a133', 'a134',
|
||||
'a135', 'a136', 'a137', 'a138', 'a139', 'a140', 'a141', 'a142', 'a143',
|
||||
'a144', 'a145', 'a146', 'a147', 'a148', 'a149', 'a150', 'a151', 'a152',
|
||||
'a153', 'a154', 'a155', 'a156', 'a157', 'a158', 'a159', 'a160', 'a161',
|
||||
'a163', 'a164', 'a196', 'a165', 'a192', 'a166', 'a167', 'a168', 'a169',
|
||||
'a170', 'a171', 'a172', 'a173', 'a162', 'a174', 'a175', 'a176', 'a177',
|
||||
'a178', 'a179', 'a193', 'a180', 'a199', 'a181', 'a200', 'a182', '', 'a201',
|
||||
'a183', 'a184', 'a197', 'a185', 'a194', 'a198', 'a186', 'a195', 'a187',
|
||||
'a188', 'a189', 'a190', 'a191']
|
||||
'a98', 'a99', 'a100', '', 'a89', 'a90', 'a93', 'a94', 'a91', 'a92', 'a205',
|
||||
'a85', 'a206', 'a86', 'a87', 'a88', 'a95', 'a96', '', '', '', '', '', '',
|
||||
'', '', '', '', '', '', '', '', '', '', '', '', '', 'a101', 'a102', 'a103',
|
||||
'a104', 'a106', 'a107', 'a108', 'a112', 'a111', 'a110', 'a109', 'a120',
|
||||
'a121', 'a122', 'a123', 'a124', 'a125', 'a126', 'a127', 'a128', 'a129',
|
||||
'a130', 'a131', 'a132', 'a133', 'a134', 'a135', 'a136', 'a137', 'a138',
|
||||
'a139', 'a140', 'a141', 'a142', 'a143', 'a144', 'a145', 'a146', 'a147',
|
||||
'a148', 'a149', 'a150', 'a151', 'a152', 'a153', 'a154', 'a155', 'a156',
|
||||
'a157', 'a158', 'a159', 'a160', 'a161', 'a163', 'a164', 'a196', 'a165',
|
||||
'a192', 'a166', 'a167', 'a168', 'a169', 'a170', 'a171', 'a172', 'a173',
|
||||
'a162', 'a174', 'a175', 'a176', 'a177', 'a178', 'a179', 'a193', 'a180',
|
||||
'a199', 'a181', 'a200', 'a182', '', 'a201', 'a183', 'a184', 'a197', 'a185',
|
||||
'a194', 'a198', 'a186', 'a195', 'a187', 'a188', 'a189', 'a190', 'a191']
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -13806,8 +13837,11 @@ var GlyphMapForStandardFonts = {
|
|||
'156': 8747, '157': 170, '158': 186, '159': 8486, '160': 230, '161': 248,
|
||||
'162': 191, '163': 161, '164': 172, '165': 8730, '166': 402, '167': 8776,
|
||||
'168': 8710, '169': 171, '170': 187, '171': 8230, '210': 218, '223': 711,
|
||||
'227': 353, '229': 382, '234': 253, '253': 268, '254': 269, '258': 258,
|
||||
'268': 283, '269': 313, '278': 328, '284': 345, '292': 367, '305': 963,
|
||||
'224': 321, '225': 322, '227': 353, '229': 382, '234': 253, '252': 263,
|
||||
'253': 268, '254': 269, '258': 258, '260': 260, '261': 261, '265': 280,
|
||||
'266': 281, '268': 283, '269': 313, '275': 323, '276': 324, '278': 328,
|
||||
'284': 345, '285': 346, '286': 347, '292': 367, '295': 377, '296': 378,
|
||||
'298': 380, '305': 963,
|
||||
'306': 964, '307': 966, '308': 8215, '309': 8252, '310': 8319, '311': 8359,
|
||||
'312': 8592, '313': 8593, '337': 9552, '493': 1039, '494': 1040, '705': 1524,
|
||||
'706': 8362, '710': 64288, '711': 64298, '759': 1617, '761': 1776,
|
||||
|
@ -13848,29 +13882,42 @@ var GlyphMapForStandardFonts = {
|
|||
'3316': 578, '3379': 42785, '3393': 1159, '3416': 8377
|
||||
};
|
||||
|
||||
// Some characters, e.g. copyrightserif, mapped to the private use area and
|
||||
// Some characters, e.g. copyrightserif, are mapped to the private use area and
|
||||
// might not be displayed using standard fonts. Mapping/hacking well-known chars
|
||||
// to the similar equivalents in the normal characters range.
|
||||
var SpecialPUASymbols = {
|
||||
'63721': 0x00A9, // copyrightsans (0xF8E9) => copyright
|
||||
'63193': 0x00A9, // copyrightserif (0xF6D9) => copyright
|
||||
'63720': 0x00AE, // registersans (0xF8E8) => registered
|
||||
'63194': 0x00AE, // registerserif (0xF6DA) => registered
|
||||
'63722': 0x2122, // trademarksans (0xF8EA) => trademark
|
||||
'63195': 0x2122, // trademarkserif (0xF6DB) => trademark
|
||||
'63729': 0x23A7, // bracelefttp (0xF8F1)
|
||||
'63730': 0x23A8, // braceleftmid (0xF8F2)
|
||||
'63731': 0x23A9, // braceleftbt (0xF8F3)
|
||||
'63740': 0x23AB, // bracerighttp (0xF8FC)
|
||||
'63741': 0x23AC, // bracerightmid (0xF8FD)
|
||||
'63742': 0x23AD, // bracerightmid (0xF8FE)
|
||||
'63726': 0x23A1, // bracketlefttp (0xF8EE)
|
||||
'63727': 0x23A2, // bracketleftex (0xF8EF)
|
||||
'63728': 0x23A3, // bracketleftbt (0xF8F0)
|
||||
'63737': 0x23A4, // bracketrighttp (0xF8F9)
|
||||
'63738': 0x23A5, // bracketrightex (0xF8FA)
|
||||
'63739': 0x23A6, // bracketrightbt (0xF8FB)
|
||||
'63723': 0x239B, // parenlefttp (0xF8EB)
|
||||
'63724': 0x239C, // parenleftex (0xF8EC)
|
||||
'63725': 0x239D, // parenleftbt (0xF8ED)
|
||||
'63734': 0x239E, // parenrighttp (0xF8F6)
|
||||
'63735': 0x239F, // parenrightex (0xF8F7)
|
||||
'63736': 0x23A0, // parenrightbt (0xF8F8)
|
||||
};
|
||||
function mapSpecialUnicodeValues(code) {
|
||||
if (code >= 0xFFF0 && code <= 0xFFFF) { // Specials unicode block.
|
||||
return 0;
|
||||
} else if (code >= 0xF600 && code <= 0xF8FF) {
|
||||
return (SpecialPUASymbols[code] || code);
|
||||
}
|
||||
switch (code) {
|
||||
case 0xF8E9: // copyrightsans
|
||||
case 0xF6D9: // copyrightserif
|
||||
return 0x00A9; // copyright
|
||||
|
||||
case 0xF8E8: // registersans
|
||||
case 0xF6DA: // registerserif
|
||||
return 0x00AE; // registered
|
||||
|
||||
case 0xF8EA: // trademarksans
|
||||
case 0xF6DB: // trademarkserif
|
||||
return 0x2122; // trademark
|
||||
|
||||
default:
|
||||
return code;
|
||||
}
|
||||
return code;
|
||||
}
|
||||
|
||||
var UnicodeRanges = [
|
||||
|
@ -15725,7 +15772,7 @@ var OpenTypeFileBuilder = (function OpenTypeFileBuilderClosure() {
|
|||
*/
|
||||
var Font = (function FontClosure() {
|
||||
function Font(name, file, properties) {
|
||||
var charCode, glyphName;
|
||||
var charCode, glyphName, fontChar;
|
||||
|
||||
this.name = name;
|
||||
this.loadedName = properties.loadedName;
|
||||
|
@ -15815,7 +15862,23 @@ var Font = (function FontClosure() {
|
|||
} else if (/Symbol/i.test(fontName)) {
|
||||
var symbols = Encodings.SymbolSetEncoding;
|
||||
for (charCode in symbols) {
|
||||
var fontChar = GlyphsUnicode[symbols[charCode]];
|
||||
fontChar = GlyphsUnicode[symbols[charCode]];
|
||||
if (!fontChar) {
|
||||
continue;
|
||||
}
|
||||
this.toFontChar[charCode] = fontChar;
|
||||
}
|
||||
} else if (/Dingbats/i.test(fontName)) {
|
||||
var dingbats = Encodings.ZapfDingbatsEncoding;
|
||||
for (charCode in dingbats) {
|
||||
fontChar = DingbatsGlyphsUnicode[dingbats[charCode]];
|
||||
if (!fontChar) {
|
||||
continue;
|
||||
}
|
||||
this.toFontChar[charCode] = fontChar;
|
||||
}
|
||||
for (charCode in properties.differences) {
|
||||
fontChar = DingbatsGlyphsUnicode[properties.differences[charCode]];
|
||||
if (!fontChar) {
|
||||
continue;
|
||||
}
|
||||
|
@ -16648,16 +16711,12 @@ var Font = (function FontClosure() {
|
|||
var numMissing = numOfSidebearings -
|
||||
((metrics.length - numOfMetrics * 4) >> 1);
|
||||
|
||||
var i, ii;
|
||||
if (numMissing > 0) {
|
||||
font.pos = (font.start ? font.start : 0) + metrics.offset;
|
||||
var entries = '';
|
||||
for (i = 0, ii = metrics.length; i < ii; i++) {
|
||||
entries += String.fromCharCode(font.getByte());
|
||||
}
|
||||
for (i = 0; i < numMissing; i++) {
|
||||
entries += '\x00\x00';
|
||||
}
|
||||
// For each missing glyph, we set both the width and lsb to 0 (zero).
|
||||
// Since we need to add two properties for each glyph, this explains
|
||||
// the use of |numMissing * 2| when initializing the typed array.
|
||||
var entries = new Uint8Array(metrics.length + numMissing * 2);
|
||||
entries.set(metrics.data);
|
||||
metrics.data = entries;
|
||||
}
|
||||
}
|
||||
|
@ -17389,7 +17448,15 @@ var Font = (function FontClosure() {
|
|||
// where the the font is symbolic and it has an encoding.
|
||||
if (hasEncoding &&
|
||||
(cmapPlatformId === 3 && cmapEncodingId === 1 ||
|
||||
cmapPlatformId === 1 && cmapEncodingId === 0)) {
|
||||
cmapPlatformId === 1 && cmapEncodingId === 0) ||
|
||||
(cmapPlatformId === -1 && cmapEncodingId === -1 && // Temporary hack
|
||||
!!Encodings[properties.baseEncodingName])) { // Temporary hack
|
||||
// When no preferred cmap table was found and |baseEncodingName| is
|
||||
// one of the predefined encodings, we seem to obtain a better
|
||||
// |charCodeToGlyphId| map from the code below (fixes bug 1057544).
|
||||
// TODO: Note that this is a hack which should be removed as soon as
|
||||
// we have proper support for more exotic cmap tables.
|
||||
|
||||
var baseEncoding = [];
|
||||
if (properties.baseEncodingName === 'MacRomanEncoding' ||
|
||||
properties.baseEncodingName === 'WinAnsiEncoding') {
|
||||
|
@ -25399,6 +25466,211 @@ var GlyphsUnicode = {
|
|||
'.notdef': 0x0000
|
||||
};
|
||||
|
||||
var DingbatsGlyphsUnicode = {
|
||||
space: 0x0020,
|
||||
a1: 0x2701,
|
||||
a2: 0x2702,
|
||||
a202: 0x2703,
|
||||
a3: 0x2704,
|
||||
a4: 0x260E,
|
||||
a5: 0x2706,
|
||||
a119: 0x2707,
|
||||
a118: 0x2708,
|
||||
a117: 0x2709,
|
||||
a11: 0x261B,
|
||||
a12: 0x261E,
|
||||
a13: 0x270C,
|
||||
a14: 0x270D,
|
||||
a15: 0x270E,
|
||||
a16: 0x270F,
|
||||
a105: 0x2710,
|
||||
a17: 0x2711,
|
||||
a18: 0x2712,
|
||||
a19: 0x2713,
|
||||
a20: 0x2714,
|
||||
a21: 0x2715,
|
||||
a22: 0x2716,
|
||||
a23: 0x2717,
|
||||
a24: 0x2718,
|
||||
a25: 0x2719,
|
||||
a26: 0x271A,
|
||||
a27: 0x271B,
|
||||
a28: 0x271C,
|
||||
a6: 0x271D,
|
||||
a7: 0x271E,
|
||||
a8: 0x271F,
|
||||
a9: 0x2720,
|
||||
a10: 0x2721,
|
||||
a29: 0x2722,
|
||||
a30: 0x2723,
|
||||
a31: 0x2724,
|
||||
a32: 0x2725,
|
||||
a33: 0x2726,
|
||||
a34: 0x2727,
|
||||
a35: 0x2605,
|
||||
a36: 0x2729,
|
||||
a37: 0x272A,
|
||||
a38: 0x272B,
|
||||
a39: 0x272C,
|
||||
a40: 0x272D,
|
||||
a41: 0x272E,
|
||||
a42: 0x272F,
|
||||
a43: 0x2730,
|
||||
a44: 0x2731,
|
||||
a45: 0x2732,
|
||||
a46: 0x2733,
|
||||
a47: 0x2734,
|
||||
a48: 0x2735,
|
||||
a49: 0x2736,
|
||||
a50: 0x2737,
|
||||
a51: 0x2738,
|
||||
a52: 0x2739,
|
||||
a53: 0x273A,
|
||||
a54: 0x273B,
|
||||
a55: 0x273C,
|
||||
a56: 0x273D,
|
||||
a57: 0x273E,
|
||||
a58: 0x273F,
|
||||
a59: 0x2740,
|
||||
a60: 0x2741,
|
||||
a61: 0x2742,
|
||||
a62: 0x2743,
|
||||
a63: 0x2744,
|
||||
a64: 0x2745,
|
||||
a65: 0x2746,
|
||||
a66: 0x2747,
|
||||
a67: 0x2748,
|
||||
a68: 0x2749,
|
||||
a69: 0x274A,
|
||||
a70: 0x274B,
|
||||
a71: 0x25CF,
|
||||
a72: 0x274D,
|
||||
a73: 0x25A0,
|
||||
a74: 0x274F,
|
||||
a203: 0x2750,
|
||||
a75: 0x2751,
|
||||
a204: 0x2752,
|
||||
a76: 0x25B2,
|
||||
a77: 0x25BC,
|
||||
a78: 0x25C6,
|
||||
a79: 0x2756,
|
||||
a81: 0x25D7,
|
||||
a82: 0x2758,
|
||||
a83: 0x2759,
|
||||
a84: 0x275A,
|
||||
a97: 0x275B,
|
||||
a98: 0x275C,
|
||||
a99: 0x275D,
|
||||
a100: 0x275E,
|
||||
a101: 0x2761,
|
||||
a102: 0x2762,
|
||||
a103: 0x2763,
|
||||
a104: 0x2764,
|
||||
a106: 0x2765,
|
||||
a107: 0x2766,
|
||||
a108: 0x2767,
|
||||
a112: 0x2663,
|
||||
a111: 0x2666,
|
||||
a110: 0x2665,
|
||||
a109: 0x2660,
|
||||
a120: 0x2460,
|
||||
a121: 0x2461,
|
||||
a122: 0x2462,
|
||||
a123: 0x2463,
|
||||
a124: 0x2464,
|
||||
a125: 0x2465,
|
||||
a126: 0x2466,
|
||||
a127: 0x2467,
|
||||
a128: 0x2468,
|
||||
a129: 0x2469,
|
||||
a130: 0x2776,
|
||||
a131: 0x2777,
|
||||
a132: 0x2778,
|
||||
a133: 0x2779,
|
||||
a134: 0x277A,
|
||||
a135: 0x277B,
|
||||
a136: 0x277C,
|
||||
a137: 0x277D,
|
||||
a138: 0x277E,
|
||||
a139: 0x277F,
|
||||
a140: 0x2780,
|
||||
a141: 0x2781,
|
||||
a142: 0x2782,
|
||||
a143: 0x2783,
|
||||
a144: 0x2784,
|
||||
a145: 0x2785,
|
||||
a146: 0x2786,
|
||||
a147: 0x2787,
|
||||
a148: 0x2788,
|
||||
a149: 0x2789,
|
||||
a150: 0x278A,
|
||||
a151: 0x278B,
|
||||
a152: 0x278C,
|
||||
a153: 0x278D,
|
||||
a154: 0x278E,
|
||||
a155: 0x278F,
|
||||
a156: 0x2790,
|
||||
a157: 0x2791,
|
||||
a158: 0x2792,
|
||||
a159: 0x2793,
|
||||
a160: 0x2794,
|
||||
a161: 0x2192,
|
||||
a163: 0x2194,
|
||||
a164: 0x2195,
|
||||
a196: 0x2798,
|
||||
a165: 0x2799,
|
||||
a192: 0x279A,
|
||||
a166: 0x279B,
|
||||
a167: 0x279C,
|
||||
a168: 0x279D,
|
||||
a169: 0x279E,
|
||||
a170: 0x279F,
|
||||
a171: 0x27A0,
|
||||
a172: 0x27A1,
|
||||
a173: 0x27A2,
|
||||
a162: 0x27A3,
|
||||
a174: 0x27A4,
|
||||
a175: 0x27A5,
|
||||
a176: 0x27A6,
|
||||
a177: 0x27A7,
|
||||
a178: 0x27A8,
|
||||
a179: 0x27A9,
|
||||
a193: 0x27AA,
|
||||
a180: 0x27AB,
|
||||
a199: 0x27AC,
|
||||
a181: 0x27AD,
|
||||
a200: 0x27AE,
|
||||
a182: 0x27AF,
|
||||
a201: 0x27B1,
|
||||
a183: 0x27B2,
|
||||
a184: 0x27B3,
|
||||
a197: 0x27B4,
|
||||
a185: 0x27B5,
|
||||
a194: 0x27B6,
|
||||
a198: 0x27B7,
|
||||
a186: 0x27B8,
|
||||
a195: 0x27B9,
|
||||
a187: 0x27BA,
|
||||
a188: 0x27BB,
|
||||
a189: 0x27BC,
|
||||
a190: 0x27BD,
|
||||
a191: 0x27BE,
|
||||
a89: 0x2768, // 0xF8D7
|
||||
a90: 0x2769, // 0xF8D8
|
||||
a93: 0x276A, // 0xF8D9
|
||||
a94: 0x276B, // 0xF8DA
|
||||
a91: 0x276C, // 0xF8DB
|
||||
a92: 0x276D, // 0xF8DC
|
||||
a205: 0x276E, // 0xF8DD
|
||||
a85: 0x276F, // 0xF8DE
|
||||
a206: 0x2770, // 0xF8DF
|
||||
a86: 0x2771, // 0xF8E0
|
||||
a87: 0x2772, // 0xF8E1
|
||||
a88: 0x2773, // 0xF8E2
|
||||
a95: 0x2774, // 0xF8E3
|
||||
a96: 0x2775, // 0xF8E4
|
||||
'.notdef': 0x0000
|
||||
};
|
||||
|
||||
|
||||
var PDFImage = (function PDFImageClosure() {
|
||||
|
@ -29318,6 +29590,9 @@ var Parser = (function ParserClosure() {
|
|||
return new NullStream(stream);
|
||||
}
|
||||
try {
|
||||
if (params) {
|
||||
params = this.fetchIfRef(params);
|
||||
}
|
||||
var xrefStreamStats = this.xref.stats.streamTypes;
|
||||
if (name === 'FlateDecode' || name === 'Fl') {
|
||||
xrefStreamStats[StreamType.FLATE] = true;
|
||||
|
@ -29341,6 +29616,22 @@ var Parser = (function ParserClosure() {
|
|||
return new LZWStream(stream, maybeLength, earlyChange);
|
||||
}
|
||||
if (name === 'DCTDecode' || name === 'DCT') {
|
||||
// According to the specification: for inline images, the ID operator
|
||||
// shall be followed by a single whitespace character (unless it uses
|
||||
// ASCII85Decode or ASCIIHexDecode filters).
|
||||
// In practice this only seems to be followed for inline JPEG images,
|
||||
// and generally ignoring the first byte of the stream if it is a
|
||||
// whitespace char can even *cause* issues (e.g. in the CCITTFaxDecode
|
||||
// filters used in issue2984.pdf).
|
||||
// Hence when the first byte of the stream of an inline JPEG image is
|
||||
// a whitespace character, we thus simply skip over it.
|
||||
if (isCmd(this.buf1, 'ID')) {
|
||||
var firstByte = stream.peekByte();
|
||||
if (firstByte === 0x0A /* LF */ || firstByte === 0x0D /* CR */ ||
|
||||
firstByte === 0x20 /* SPACE */) {
|
||||
stream.skip();
|
||||
}
|
||||
}
|
||||
xrefStreamStats[StreamType.DCT] = true;
|
||||
return new JpegStream(stream, maybeLength, stream.dict, this.xref);
|
||||
}
|
||||
|
@ -29447,7 +29738,7 @@ var Lexer = (function LexerClosure() {
|
|||
return (this.currentChar = this.stream.getByte());
|
||||
},
|
||||
peekChar: function Lexer_peekChar() {
|
||||
return this.stream.peekBytes(1)[0];
|
||||
return this.stream.peekByte();
|
||||
},
|
||||
getNumber: function Lexer_getNumber() {
|
||||
var ch = this.currentChar;
|
||||
|
@ -30104,6 +30395,11 @@ var Stream = (function StreamClosure() {
|
|||
this.pos = end;
|
||||
return bytes.subarray(pos, end);
|
||||
},
|
||||
peekByte: function Stream_peekByte() {
|
||||
var peekedByte = this.getByte();
|
||||
this.pos--;
|
||||
return peekedByte;
|
||||
},
|
||||
peekBytes: function Stream_peekBytes(length) {
|
||||
var bytes = this.getBytes(length);
|
||||
this.pos -= bytes.length;
|
||||
|
@ -30233,6 +30529,11 @@ var DecodeStream = (function DecodeStreamClosure() {
|
|||
this.pos = end;
|
||||
return this.buffer.subarray(pos, end);
|
||||
},
|
||||
peekByte: function DecodeStream_peekByte() {
|
||||
var peekedByte = this.getByte();
|
||||
this.pos--;
|
||||
return peekedByte;
|
||||
},
|
||||
peekBytes: function DecodeStream_peekBytes(length) {
|
||||
var bytes = this.getBytes(length);
|
||||
this.pos -= bytes.length;
|
||||
|
@ -30558,7 +30859,7 @@ var FlateStream = (function FlateStreamClosure() {
|
|||
var end = bufferLength + blockLen;
|
||||
this.bufferLength = end;
|
||||
if (blockLen === 0) {
|
||||
if (str.peekBytes(1).length === 0) {
|
||||
if (str.peekByte() === -1) {
|
||||
this.eof = true;
|
||||
}
|
||||
} else {
|
||||
|
@ -31064,7 +31365,8 @@ var Jbig2Stream = (function Jbig2StreamClosure() {
|
|||
|
||||
var jbig2Image = new Jbig2Image();
|
||||
|
||||
var chunks = [], decodeParams = this.dict.get('DecodeParms');
|
||||
var chunks = [], xref = this.dict.xref;
|
||||
var decodeParams = xref.fetchIfRef(this.dict.get('DecodeParms'));
|
||||
|
||||
// According to the PDF specification, DecodeParms can be either
|
||||
// a dictionary, or an array whose elements are dictionaries.
|
||||
|
@ -31073,7 +31375,7 @@ var Jbig2Stream = (function Jbig2StreamClosure() {
|
|||
warn('JBIG2 - \'DecodeParms\' array with multiple elements ' +
|
||||
'not supported.');
|
||||
}
|
||||
decodeParams = decodeParams[0];
|
||||
decodeParams = xref.fetchIfRef(decodeParams[0]);
|
||||
}
|
||||
if (decodeParams && decodeParams.has('JBIG2Globals')) {
|
||||
var globalsStream = decodeParams.get('JBIG2Globals');
|
||||
|
@ -32593,14 +32895,16 @@ var WorkerMessageHandler = PDFJS.WorkerMessageHandler = {
|
|||
},
|
||||
|
||||
onError: function onError(status) {
|
||||
var exception;
|
||||
if (status === 404) {
|
||||
var exception = new MissingPDFException('Missing PDF "' +
|
||||
source.url + '".');
|
||||
handler.send('MissingPDF', { exception: exception });
|
||||
exception = new MissingPDFException('Missing PDF "' +
|
||||
source.url + '".');
|
||||
handler.send('MissingPDF', exception);
|
||||
} else {
|
||||
handler.send('DocError', 'Unexpected server response (' +
|
||||
status + ') while retrieving PDF "' +
|
||||
source.url + '".');
|
||||
exception = new UnexpectedResponseException(
|
||||
'Unexpected server response (' + status +
|
||||
') while retrieving PDF "' + source.url + '".', status);
|
||||
handler.send('UnexpectedResponse', exception);
|
||||
}
|
||||
},
|
||||
|
||||
|
@ -32652,26 +32956,19 @@ var WorkerMessageHandler = PDFJS.WorkerMessageHandler = {
|
|||
var onFailure = function(e) {
|
||||
if (e instanceof PasswordException) {
|
||||
if (e.code === PasswordResponses.NEED_PASSWORD) {
|
||||
handler.send('NeedPassword', {
|
||||
exception: e
|
||||
});
|
||||
handler.send('NeedPassword', e);
|
||||
} else if (e.code === PasswordResponses.INCORRECT_PASSWORD) {
|
||||
handler.send('IncorrectPassword', {
|
||||
exception: e
|
||||
});
|
||||
handler.send('IncorrectPassword', e);
|
||||
}
|
||||
} else if (e instanceof InvalidPDFException) {
|
||||
handler.send('InvalidPDF', {
|
||||
exception: e
|
||||
});
|
||||
handler.send('InvalidPDF', e);
|
||||
} else if (e instanceof MissingPDFException) {
|
||||
handler.send('MissingPDF', {
|
||||
exception: e
|
||||
});
|
||||
handler.send('MissingPDF', e);
|
||||
} else if (e instanceof UnexpectedResponseException) {
|
||||
handler.send('UnexpectedResponse', e);
|
||||
} else {
|
||||
handler.send('UnknownError', {
|
||||
exception: new UnknownErrorException(e.message, e.toString())
|
||||
});
|
||||
handler.send('UnknownError',
|
||||
new UnknownErrorException(e.message, e.toString()));
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -34605,7 +34902,7 @@ var JpxImage = (function JpxImageClosure() {
|
|||
codeblockWidth: xcb_,
|
||||
codeblockHeight: ycb_,
|
||||
numcodeblockwide: cbx1 - cbx0 + 1,
|
||||
numcodeblockhigh: cby1 - cby1 + 1
|
||||
numcodeblockhigh: cby1 - cby0 + 1
|
||||
};
|
||||
subband.codeblocks = codeblocks;
|
||||
subband.precincts = precincts;
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
|
|
|
@ -0,0 +1,35 @@
|
|||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2014 Mozilla Foundation
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
/* jshint esnext:true */
|
||||
/* globals Components, PdfjsContentUtils, PdfJs */
|
||||
|
||||
'use strict';
|
||||
|
||||
/*
|
||||
* pdfjschildbootstrap.js loads into the content process to take care of
|
||||
* initializing our built-in version of pdfjs when running remote.
|
||||
*/
|
||||
|
||||
Components.utils.import('resource://pdf.js/PdfJs.jsm');
|
||||
Components.utils.import('resource://pdf.js/PdfjsContentUtils.jsm');
|
||||
|
||||
// init content utils shim pdfjs will use to access privileged apis.
|
||||
PdfjsContentUtils.init();
|
||||
|
||||
// register various pdfjs factories that hook us into content loading.
|
||||
PdfJs.updateRegistration();
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* globals FirefoxCom */
|
||||
|
||||
|
|
|
@ -345,6 +345,9 @@ html[dir='rtl'] .findbar {
|
|||
background-repeat: no-repeat;
|
||||
background-position: right;
|
||||
}
|
||||
html[dir='rtl'] #findInput[data-status="pending"] {
|
||||
background-position: left;
|
||||
}
|
||||
|
||||
.secondaryToolbar {
|
||||
padding: 6px;
|
||||
|
@ -940,7 +943,7 @@ html[dir='rtl'] .verticalToolbarSeparator {
|
|||
}
|
||||
|
||||
.horizontalToolbarSeparator {
|
||||
display: block;
|
||||
display: block;
|
||||
margin: 0 0 4px 0;
|
||||
height: 1px;
|
||||
width: 100%;
|
||||
|
@ -1208,8 +1211,6 @@ canvas {
|
|||
top: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
color: #000;
|
||||
font-family: sans-serif;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
|
@ -1218,6 +1219,8 @@ canvas {
|
|||
position: absolute;
|
||||
white-space: pre;
|
||||
cursor: text;
|
||||
-moz-transform-origin: 0% 0%;
|
||||
transform-origin: 0% 0%;
|
||||
}
|
||||
|
||||
.textLayer .highlight {
|
||||
|
@ -1386,7 +1389,7 @@ canvas {
|
|||
}
|
||||
|
||||
.dialog .separator {
|
||||
display: block;
|
||||
display: block;
|
||||
margin: 4px 0 4px 0;
|
||||
height: 1px;
|
||||
width: 100%;
|
||||
|
@ -1562,7 +1565,7 @@ html[dir='rtl'] #documentPropertiesOverlay .row > * {
|
|||
background: url(images/toolbarButton-menuArrows@2x.png) no-repeat;
|
||||
background-size: 7px 16px;
|
||||
}
|
||||
|
||||
|
||||
html[dir='ltr'] .toolbarButton#sidebarToggle::before {
|
||||
content: url(images/toolbarButton-sidebarToggle@2x.png);
|
||||
}
|
||||
|
@ -1852,4 +1855,3 @@ html[dir='rtl'] #documentPropertiesOverlay .row > * {
|
|||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
|
||||
/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
|
||||
/* Copyright 2012 Mozilla Foundation
|
||||
*
|
||||
|
@ -2034,6 +2034,11 @@ var GrabToPan = (function GrabToPanClosure() {
|
|||
event.preventDefault();
|
||||
event.stopPropagation();
|
||||
this.document.documentElement.classList.add(this.CSS_CLASS_GRABBING);
|
||||
|
||||
var focusedElement = document.activeElement;
|
||||
if (focusedElement && !focusedElement.contains(event.target)) {
|
||||
focusedElement.blur();
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
|
@ -2527,7 +2532,7 @@ var DocumentProperties = {
|
|||
minutes += offsetMinutes;
|
||||
} else if (utRel === '+') {
|
||||
hours -= offsetHours;
|
||||
minutes += offsetMinutes;
|
||||
minutes -= offsetMinutes;
|
||||
}
|
||||
|
||||
// Return the new date format from the user's locale.
|
||||
|
@ -2795,7 +2800,9 @@ var PDFView = {
|
|||
scale = Math.min(pageWidthScale, pageHeightScale);
|
||||
break;
|
||||
case 'auto':
|
||||
scale = Math.min(MAX_AUTO_SCALE, pageWidthScale);
|
||||
var isLandscape = (currentPage.width > currentPage.height);
|
||||
var horizontalScale = isLandscape ? pageHeightScale : pageWidthScale;
|
||||
scale = Math.min(MAX_AUTO_SCALE, horizontalScale);
|
||||
break;
|
||||
default:
|
||||
console.error('pdfViewSetScale: \'' + value +
|
||||
|
@ -3053,7 +3060,7 @@ var PDFView = {
|
|||
},
|
||||
|
||||
// TODO(mack): This function signature should really be pdfViewOpen(url, args)
|
||||
open: function pdfViewOpen(url, scale, password,
|
||||
open: function pdfViewOpen(file, scale, password,
|
||||
pdfDataRangeTransport, args) {
|
||||
if (this.pdfDocument) {
|
||||
// Reload the preferences if a document was previously opened.
|
||||
|
@ -3062,11 +3069,14 @@ var PDFView = {
|
|||
this.close();
|
||||
|
||||
var parameters = {password: password};
|
||||
if (typeof url === 'string') { // URL
|
||||
this.setTitleUsingUrl(url);
|
||||
parameters.url = url;
|
||||
} else if (url && 'byteLength' in url) { // ArrayBuffer
|
||||
parameters.data = url;
|
||||
if (typeof file === 'string') { // URL
|
||||
this.setTitleUsingUrl(file);
|
||||
parameters.url = file;
|
||||
} else if (file && 'byteLength' in file) { // ArrayBuffer
|
||||
parameters.data = file;
|
||||
} else if (file.url && file.originalUrl) {
|
||||
this.setTitleUsingUrl(file.originalUrl);
|
||||
parameters.url = file.url;
|
||||
}
|
||||
if (args) {
|
||||
for (var prop in args) {
|
||||
|
@ -3094,21 +3104,22 @@ var PDFView = {
|
|||
self.load(pdfDocument, scale);
|
||||
self.loading = false;
|
||||
},
|
||||
function getDocumentError(message, exception) {
|
||||
function getDocumentError(exception) {
|
||||
var message = exception && exception.message;
|
||||
var loadingErrorMessage = mozL10n.get('loading_error', null,
|
||||
'An error occurred while loading the PDF.');
|
||||
|
||||
if (exception && exception.name === 'InvalidPDFException') {
|
||||
if (exception instanceof PDFJS.InvalidPDFException) {
|
||||
// change error message also for other builds
|
||||
loadingErrorMessage = mozL10n.get('invalid_file_error', null,
|
||||
'Invalid or corrupted PDF file.');
|
||||
}
|
||||
|
||||
if (exception && exception.name === 'MissingPDFException') {
|
||||
'Invalid or corrupted PDF file.');
|
||||
} else if (exception instanceof PDFJS.MissingPDFException) {
|
||||
// special message for missing PDF's
|
||||
loadingErrorMessage = mozL10n.get('missing_file_error', null,
|
||||
'Missing PDF file.');
|
||||
|
||||
'Missing PDF file.');
|
||||
} else if (exception instanceof PDFJS.UnexpectedResponseException) {
|
||||
loadingErrorMessage = mozL10n.get('unexpected_response_error', null,
|
||||
'Unexpected server response.');
|
||||
}
|
||||
|
||||
var moreInfo = {
|
||||
|
@ -3528,7 +3539,11 @@ var PDFView = {
|
|||
|
||||
var pdfTitle;
|
||||
if (metadata && metadata.has('dc:title')) {
|
||||
pdfTitle = metadata.get('dc:title');
|
||||
var title = metadata.get('dc:title');
|
||||
// Ghostscript sometimes return 'Untitled', sets the title to 'Untitled'
|
||||
if (title !== 'Untitled') {
|
||||
pdfTitle = title;
|
||||
}
|
||||
}
|
||||
|
||||
if (!pdfTitle && info && info['Title']) {
|
||||
|
@ -3575,7 +3590,7 @@ var PDFView = {
|
|||
setInitialView: function pdfViewSetInitialView(storedHash, scale) {
|
||||
// Reset the current scale, as otherwise the page's scale might not get
|
||||
// updated if the zoom level stayed the same.
|
||||
this.currentScale = 0;
|
||||
this.currentScale = UNKNOWN_SCALE;
|
||||
this.currentScaleValue = null;
|
||||
// When opening a new file (when one is already loaded in the viewer):
|
||||
// Reset 'currentPageNumber', since otherwise the page's scale will be wrong
|
||||
|
@ -5074,15 +5089,21 @@ var TextLayerBuilder = (function TextLayerBuilderClosure() {
|
|||
var width = ctx.measureText(textDiv.textContent).width;
|
||||
if (width > 0) {
|
||||
textLayerFrag.appendChild(textDiv);
|
||||
// Dataset values come of type string.
|
||||
var textScale = textDiv.dataset.canvasWidth / width;
|
||||
var transform;
|
||||
if (textDiv.dataset.canvasWidth !== undefined) {
|
||||
// Dataset values come of type string.
|
||||
var textScale = textDiv.dataset.canvasWidth / width;
|
||||
transform = 'scaleX(' + textScale + ')';
|
||||
} else {
|
||||
transform = '';
|
||||
}
|
||||
var rotation = textDiv.dataset.angle;
|
||||
var transform = 'scale(' + textScale + ', 1)';
|
||||
if (rotation) {
|
||||
transform = 'rotate(' + rotation + 'deg) ' + transform;
|
||||
}
|
||||
CustomStyle.setProp('transform' , textDiv, transform);
|
||||
CustomStyle.setProp('transformOrigin' , textDiv, '0% 0%');
|
||||
if (transform) {
|
||||
CustomStyle.setProp('transform' , textDiv, transform);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -5157,10 +5178,15 @@ var TextLayerBuilder = (function TextLayerBuilderClosure() {
|
|||
if (angle !== 0) {
|
||||
textDiv.dataset.angle = angle * (180 / Math.PI);
|
||||
}
|
||||
if (style.vertical) {
|
||||
textDiv.dataset.canvasWidth = geom.height * this.viewport.scale;
|
||||
} else {
|
||||
textDiv.dataset.canvasWidth = geom.width * this.viewport.scale;
|
||||
// We don't bother scaling single-char text divs, because it has very
|
||||
// little effect on text highlighting. This makes scrolling on docs with
|
||||
// lots of such divs a lot faster.
|
||||
if (textDiv.textContent.length > 1) {
|
||||
if (style.vertical) {
|
||||
textDiv.dataset.canvasWidth = geom.height * this.viewport.scale;
|
||||
} else {
|
||||
textDiv.dataset.canvasWidth = geom.width * this.viewport.scale;
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
|
@ -5768,9 +5794,12 @@ window.addEventListener('localized', function localized(evt) {
|
|||
|
||||
PDFView.animationStartedPromise.then(function() {
|
||||
// Adjust the width of the zoom box to fit the content.
|
||||
// Note: This is only done if the zoom box is actually visible,
|
||||
// since otherwise element.clientWidth will return 0.
|
||||
// Note: If the window is narrow enough that the zoom box is not visible,
|
||||
// we temporarily show it to be able to adjust its width.
|
||||
var container = document.getElementById('scaleSelectContainer');
|
||||
if (container.clientWidth === 0) {
|
||||
container.setAttribute('style', 'display: inherit;');
|
||||
}
|
||||
if (container.clientWidth > 0) {
|
||||
var select = document.getElementById('scaleSelect');
|
||||
select.setAttribute('style', 'min-width: inherit;');
|
||||
|
|
|
@ -75,21 +75,15 @@ OrganizerQueryDownloads=Downloads
|
|||
OrganizerQueryAllBookmarks=All Bookmarks
|
||||
OrganizerQueryTags=Tags
|
||||
|
||||
# LOCALIZATION NOTE (tagResultLabel) :
|
||||
# LOCALIZATION NOTE (tagResultLabel, bookmarkResultLabel, switchtabResultLabel,
|
||||
# keywordResultLabel)
|
||||
# Noun used to describe the location bar autocomplete result type
|
||||
# to users with screen readers
|
||||
# See createResultLabel() in urlbarBindings.xml
|
||||
tagResultLabel=Tag
|
||||
# LOCALIZATION NOTE (bookmarkResultLabel) :
|
||||
# Noun used to describe the location bar autocomplete result type
|
||||
# to users with screen readers
|
||||
# See createResultLabel() in urlbarBindings.xml
|
||||
bookmarkResultLabel=Bookmark
|
||||
# LOCALIZATION NOTE (switchtabResultLabel) :
|
||||
# Noun used to describe the location bar autocomplete result type
|
||||
# to users with screen readers
|
||||
# See createResultLabel() in urlbarBindings.xml
|
||||
switchtabResultLabel=Tab
|
||||
keywordResultLabel=Keyword
|
||||
|
||||
# LOCALIZATION NOTE (lockPrompt.text)
|
||||
# %S will be replaced with the application name.
|
||||
|
|
|
@ -146,6 +146,7 @@ loading_error_indicator=Error
|
|||
loading_error=An error occurred while loading the PDF.
|
||||
invalid_file_error=Invalid or corrupted PDF file.
|
||||
missing_file_error=Missing PDF file.
|
||||
unexpected_response_error=Unexpected server response.
|
||||
|
||||
# LOCALIZATION NOTE (text_annotation_type.alt): This is used as a tooltip.
|
||||
# "{{type}}" will be replaced with an annotation type from a list defined in
|
||||
|
|
|
@ -134,19 +134,6 @@
|
|||
background-size: auto;
|
||||
}
|
||||
|
||||
/* Use a pseudo-element to overlay a gradient on the thumbnail */
|
||||
.newtab-site[type=history]:not(:hover) .newtab-thumbnail:first-child::after {
|
||||
background-image: linear-gradient(0deg, rgba(251, 251, 251, 0.8), rgba(251, 251, 251, 0) 33%);
|
||||
border-radius: inherit;
|
||||
bottom: 0;
|
||||
content: "";
|
||||
left: 0;
|
||||
pointer-events: none;
|
||||
position: absolute;
|
||||
right: 0;
|
||||
top: 0;
|
||||
}
|
||||
|
||||
/* TITLES */
|
||||
.newtab-title {
|
||||
color: #737373;
|
||||
|
|
|
@ -4,9 +4,6 @@
|
|||
|
||||
package org.mozilla.gecko.annotationProcessors.classloader;
|
||||
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.Iterator;
|
||||
|
||||
/**
|
||||
|
@ -46,37 +43,9 @@ public class JarClassIterator implements Iterator<ClassWithOptions> {
|
|||
if (canonicalName == null || "null".equals(canonicalName)) {
|
||||
// Anonymous inner class - unsupported.
|
||||
return next();
|
||||
} else {
|
||||
String generateName = null;
|
||||
for (Annotation annotation : ret.getAnnotations()) {
|
||||
Class<?> annotationType = annotation.annotationType();
|
||||
if (annotationType.getCanonicalName().equals("org.mozilla.gecko.mozglue.generatorannotations.GeneratorOptions")) {
|
||||
try {
|
||||
// Determine the explicitly-given name of the stub to generate, if any.
|
||||
final Method generateNameMethod = annotationType.getDeclaredMethod("generatedClassName");
|
||||
generateNameMethod.setAccessible(true);
|
||||
generateName = (String) generateNameMethod.invoke(annotation);
|
||||
break;
|
||||
} catch (NoSuchMethodException e) {
|
||||
System.err.println("Unable to find expected field on GeneratorOptions annotation. Did the signature change?");
|
||||
e.printStackTrace(System.err);
|
||||
System.exit(3);
|
||||
} catch (IllegalAccessException e) {
|
||||
System.err.println("IllegalAccessException reading fields on GeneratorOptions annotation. Seems the semantics of Reflection have changed...");
|
||||
e.printStackTrace(System.err);
|
||||
System.exit(4);
|
||||
} catch (InvocationTargetException e) {
|
||||
System.err.println("InvocationTargetException reading fields on GeneratorOptions annotation. This really shouldn't happen.");
|
||||
e.printStackTrace(System.err);
|
||||
System.exit(5);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (generateName == null) {
|
||||
generateName = ret.getSimpleName();
|
||||
}
|
||||
return new ClassWithOptions(ret, generateName);
|
||||
}
|
||||
|
||||
return new ClassWithOptions(ret, ret.getSimpleName());
|
||||
} catch (ClassNotFoundException e) {
|
||||
System.err.println("Unable to enumerate class: " + className + ". Corrupted jar file?");
|
||||
e.printStackTrace();
|
||||
|
|
|
@ -14,6 +14,22 @@ DEBUG_JARSIGNER=$(PYTHON) $(abspath $(topsrcdir)/mobile/android/debug_sign_tool.
|
|||
--jarsigner=$(JARSIGNER) \
|
||||
$(NULL)
|
||||
|
||||
# RELEASE_JARSIGNER release signs if possible.
|
||||
ifdef MOZ_SIGN_CMD
|
||||
RELEASE_JARSIGNER := $(MOZ_SIGN_CMD) -f jar
|
||||
else
|
||||
RELEASE_JARSIGNER := $(DEBUG_JARSIGNER)
|
||||
endif
|
||||
|
||||
# $(1) is the full path to input: foo-debug-unsigned-unaligned.apk.
|
||||
# $(2) is the full path to output: foo.apk.
|
||||
# Use this like: $(call RELEASE_SIGN_ANDROID_APK,foo-debug-unsigned-unaligned.apk,foo.apk)
|
||||
RELEASE_SIGN_ANDROID_APK = \
|
||||
cp $(1) $(2)-unaligned.apk && \
|
||||
$(RELEASE_JARSIGNER) $(2)-unaligned.apk && \
|
||||
$(ZIPALIGN) -f -v 4 $(2)-unaligned.apk $(2) && \
|
||||
$(RM) $(2)-unaligned.apk
|
||||
|
||||
# For Android, this defaults to $(ANDROID_SDK)/android.jar
|
||||
ifndef JAVA_BOOTCLASSPATH
|
||||
JAVA_BOOTCLASSPATH = $(ANDROID_SDK)/android.jar
|
||||
|
|
|
@ -0,0 +1,148 @@
|
|||
/* 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/. */
|
||||
|
||||
/* global Components, Services, dump */
|
||||
|
||||
"use strict";
|
||||
|
||||
const Cu = Components.utils;
|
||||
const Cc = Components.classes;
|
||||
const Ci = Components.interfaces;
|
||||
|
||||
this.EXPORTED_SYMBOLS = ["TrustedHostedAppsUtils"];
|
||||
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
// On Android, define the "debug" function as a binding of the "d" function
|
||||
// from the AndroidLog module so it gets the "debug" priority and a log tag.
|
||||
// We always report debug messages on Android because it's unnecessary
|
||||
// to restrict reporting, per bug 1003469.
|
||||
let debug = Cu
|
||||
.import("resource://gre/modules/AndroidLog.jsm", {})
|
||||
.AndroidLog.d.bind(null, "TrustedHostedAppsUtils");
|
||||
#else
|
||||
// Elsewhere, report debug messages only if dom.mozApps.debug is set to true.
|
||||
// The pref is only checked once, on startup, so restart after changing it.
|
||||
let debug = Services.prefs.getBoolPref("dom.mozApps.debug") ?
|
||||
aMsg => dump("-*- TrustedHostedAppsUtils.jsm : " + aMsg + "\n") :
|
||||
() => {};
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Verification functions for Trusted Hosted Apps.
|
||||
* (Manifest signature verification is in Webapps.jsm as part of
|
||||
* regular signature verification.)
|
||||
*/
|
||||
this.TrustedHostedAppsUtils = {
|
||||
|
||||
/**
|
||||
* Check if the given host is pinned in the CA pinning database.
|
||||
*/
|
||||
isHostPinned: function (aUrl) {
|
||||
let uri;
|
||||
try {
|
||||
uri = Services.io.newURI(aUrl, null, null);
|
||||
} catch(e) {
|
||||
debug("Host parsing failed: " + e);
|
||||
return false;
|
||||
}
|
||||
|
||||
// TODO: use nsSiteSecurityService.isSecureURI()
|
||||
if (!uri.host || "https" != uri.scheme) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Check certificate pinning
|
||||
let siteSecurityService;
|
||||
try {
|
||||
siteSecurityService = Cc["@mozilla.org/ssservice;1"]
|
||||
.getService(Ci.nsISiteSecurityService);
|
||||
} catch (e) {
|
||||
debug("nsISiteSecurityService error: " + e);
|
||||
// unrecoverable error, don't bug the user
|
||||
throw "CERTDB_ERROR";
|
||||
}
|
||||
|
||||
if (siteSecurityService.isSecureHost(Ci.nsISiteSecurityService.HEADER_HPKP, uri.host, 0)) {
|
||||
debug("\tvalid certificate pinning for host: " + uri.host + "\n");
|
||||
return true;
|
||||
}
|
||||
|
||||
debug("\tHost NOT pinned: " + uri.host + "\n");
|
||||
return false;
|
||||
},
|
||||
|
||||
/**
|
||||
* Take a CSP policy string as input and ensure that it contains at
|
||||
* least the directives that are required ('script-src' and
|
||||
* 'style-src'). If the CSP policy string is 'undefined' or does
|
||||
* not contain some of the required csp directives the function will
|
||||
* return empty list with status set to false. Otherwise a parsed
|
||||
* list of the unique sources listed from the required csp
|
||||
* directives is returned.
|
||||
*/
|
||||
getCSPWhiteList: function(aCsp) {
|
||||
let isValid = false;
|
||||
let whiteList = [];
|
||||
let requiredDirectives = [ "script-src", "style-src" ];
|
||||
|
||||
if (aCsp) {
|
||||
let validDirectives = [];
|
||||
let directives = aCsp.split(";");
|
||||
// TODO: Use nsIContentSecurityPolicy
|
||||
directives
|
||||
.map(aDirective => aDirective.trim().split(" "))
|
||||
.filter(aList => aList.length > 1)
|
||||
// we only restrict on requiredDirectives
|
||||
.filter(aList => (requiredDirectives.indexOf(aList[0]) != -1))
|
||||
.forEach(aList => {
|
||||
// aList[0] contains the directive name.
|
||||
// aList[1..n] contains sources.
|
||||
let directiveName = aList.shift()
|
||||
let sources = aList;
|
||||
|
||||
if ((-1 == validDirectives.indexOf(directiveName))) {
|
||||
validDirectives.push(directiveName);
|
||||
}
|
||||
whiteList.push(...sources.filter(
|
||||
// 'self' is checked separately during manifest check
|
||||
aSource => (aSource !="'self'" && whiteList.indexOf(aSource) == -1)
|
||||
));
|
||||
});
|
||||
|
||||
// Check if all required directives are present.
|
||||
isValid = requiredDirectives.length === validDirectives.length;
|
||||
|
||||
if (!isValid) {
|
||||
debug("White list doesn't contain all required directives!");
|
||||
whiteList = [];
|
||||
}
|
||||
}
|
||||
|
||||
debug("White list contains " + whiteList.length + " hosts");
|
||||
return { list: whiteList, valid: isValid };
|
||||
},
|
||||
|
||||
/**
|
||||
* Verify that the given csp is valid:
|
||||
* 1. contains required directives "script-src" and "style-src"
|
||||
* 2. required directives contain only "https" URLs
|
||||
* 3. domains of the restricted sources exist in the CA pinning database
|
||||
*/
|
||||
verifyCSPWhiteList: function(aCsp) {
|
||||
let domainWhitelist = this.getCSPWhiteList(aCsp);
|
||||
if (!domainWhitelist.valid) {
|
||||
debug("TRUSTED_APPLICATION_WHITELIST_PARSING_FAILED");
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!domainWhitelist.list.every(aUrl => this.isHostPinned(aUrl))) {
|
||||
debug("TRUSTED_APPLICATION_WHITELIST_VALIDATION_FAILED");
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
};
|
|
@ -64,6 +64,9 @@ XPCOMUtils.defineLazyModuleGetter(this, "NetUtil",
|
|||
XPCOMUtils.defineLazyModuleGetter(this, "ScriptPreloader",
|
||||
"resource://gre/modules/ScriptPreloader.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "TrustedHostedAppsUtils",
|
||||
"resource://gre/modules/TrustedHostedAppsUtils.jsm");
|
||||
|
||||
#ifdef MOZ_WIDGET_GONK
|
||||
XPCOMUtils.defineLazyGetter(this, "libcutils", function() {
|
||||
Cu.import("resource://gre/modules/systemlibs.js");
|
||||
|
@ -1411,6 +1414,24 @@ this.DOMApplicationRegistry = {
|
|||
return;
|
||||
}
|
||||
|
||||
// Check if launching trusted hosted app
|
||||
if (this.kTrustedHosted == app.kind) {
|
||||
debug("Launching Trusted Hosted App!");
|
||||
// sanity check on manifest host's CA
|
||||
// (proper CA check with pinning is done by regular networking code)
|
||||
if (!TrustedHostedAppsUtils.isHostPinned(aManifestURL)) {
|
||||
debug("Trusted App Host certificate Not OK");
|
||||
aOnFailure("TRUSTED_APPLICATION_HOST_CERTIFICATE_INVALID");
|
||||
return;
|
||||
}
|
||||
|
||||
debug("Trusted App Host pins exist");
|
||||
if (!TrustedHostedAppsUtils.verifyCSPWhiteList(app.csp)) {
|
||||
aOnFailure("TRUSTED_APPLICATION_WHITELIST_VALIDATION_FAILED");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// We have to clone the app object as nsIDOMApplication objects are
|
||||
// stringified as an empty object. (see bug 830376)
|
||||
let appClone = AppsUtils.cloneAppObject(app);
|
||||
|
@ -2295,6 +2316,23 @@ this.DOMApplicationRegistry = {
|
|||
// in which case we don't need to load it.
|
||||
if (app.manifest) {
|
||||
if (checkManifest()) {
|
||||
if (this.kTrustedHosted == this.appKind(app, app.manifest)) {
|
||||
// sanity check on manifest host's CA
|
||||
// (proper CA check with pinning is done by regular networking code)
|
||||
if (!TrustedHostedAppsUtils.isHostPinned(app.manifestURL)) {
|
||||
sendError("TRUSTED_APPLICATION_HOST_CERTIFICATE_INVALID");
|
||||
return;
|
||||
}
|
||||
|
||||
// Signature of the manifest should be verified here.
|
||||
// Bug 1059216.
|
||||
|
||||
if (!TrustedHostedAppsUtils.verifyCSPWhiteList(app.manifest.csp)) {
|
||||
sendError("TRUSTED_APPLICATION_WHITELIST_VALIDATION_FAILED");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
installApp();
|
||||
}
|
||||
return;
|
||||
|
@ -2319,6 +2357,19 @@ this.DOMApplicationRegistry = {
|
|||
app.manifest = xhr.response;
|
||||
if (checkManifest()) {
|
||||
app.etag = xhr.getResponseHeader("Etag");
|
||||
if (this.kTrustedHosted == this.appKind(app, app.manifest)) {
|
||||
// checking trusted host for pinning is not needed here, since
|
||||
// network code will have already done that
|
||||
|
||||
// Signature of the manifest should be verified here.
|
||||
// Bug 1059216.
|
||||
|
||||
if (!TrustedHostedAppsUtils.verifyCSPWhiteList(app.manifest.csp)) {
|
||||
sendError("TRUSTED_APPLICATION_WHITELIST_VALIDATION_FAILED");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
installApp();
|
||||
}
|
||||
} else {
|
||||
|
|
|
@ -44,6 +44,7 @@ EXTRA_PP_JS_MODULES += [
|
|||
'AppsUtils.jsm',
|
||||
'OperatorApps.jsm',
|
||||
'ScriptPreloader.jsm',
|
||||
'TrustedHostedAppsUtils.jsm',
|
||||
'Webapps.jsm',
|
||||
]
|
||||
|
||||
|
|
|
@ -7,6 +7,7 @@ support-files =
|
|||
[test_apps_service.xul]
|
||||
[test_bug_945152.html]
|
||||
run-if = os == 'linux'
|
||||
[test_tha_utils.html]
|
||||
[test_manifest_helper.xul]
|
||||
[test_operator_app_install.js]
|
||||
[test_operator_app_install.xul]
|
||||
|
|
Некоторые файлы не были показаны из-за слишком большого количества измененных файлов Показать больше
Загрузка…
Ссылка в новой задаче