feat: Added priviledged window sharing API, b=(no-bug), c=common

This commit is contained in:
Mr. M
2025-05-12 00:50:01 +02:00
parent 1a2b527070
commit 1a7f9d9ee0
7 changed files with 196 additions and 0 deletions

View File

@@ -7,4 +7,5 @@ DIRS += [
"glance",
"mods",
"tests",
"toolkit",
]

View File

@@ -0,0 +1,96 @@
#include "ZenCommonUtils.h"
#if defined(XP_WIN)
# include "mozilla/WindowsVersion.h"
#endif
namespace zen {
// Use the macro to inject all of the definitions for nsISupports.
NS_IMPL_ISUPPORTS(ZenCommonUtils, nsIZenCommonUtils)
ZenCommonUtils::ZenCommonUtils(nsGlobalWindowOuter* aWindow) {
nsCOMPtr<nsISupports> supports = do_QueryObject(aWindow);
mWindow = do_GetWeakReference(supports);
}
/*
* @brief Check if the current context can share data.
* @param data The data to share.
* @returns True if the current context can share data, false otherwise.
*/
NS_IMETHODIMP
ZenCommonUtils::CanShare(const nsIDOMWindow& aWindow, bool* canShare) {
if (!aWindow || !aWindow->IsFullyActive()) {
*canShare = false;
return NS_OK;
}
*canShare = IsSharingSupported();
return NS_OK;
}
NS_IMETHODIMP
ZenCommonUtils::Share(const nsIDOMWindow& aWindow, const nsAString& url,
const nsAString& title, const nsAString& text,
mozilla::dom::Promise** _retval) {
if (!aWindow || !aWindow->IsFullyActive()) {
return NS_ERROR_NOT_AVAILABLE;
}
if (!IsSharingSupported()) {
return NS_ERROR_NOT_AVAILABLE;
}
if (url.IsEmpty()) {
return NS_ERROR_INVALID_ARG;
}
if (title.IsEmpty() && text.IsEmpty()) {
return NS_ERROR_INVALID_ARG;
}
if (aWindow->GetExtantDoc()) {
nsCOMPtr<nsIURI> uri;
nsresult rv = aWindow->GetExtantDoc()->ResolveWithBaseURI(url, getter_AddRefs(uri));
if (NS_FAILED(rv) || !uri) {
return NS_ERROR_INVALID_ARG;
}
}
if (mSharePromise) {
NS_WARNING("Only one share picker at a time per navigator instance");
return NS_ERROR_INVALID_STATE;
}
mSharePromise = Promise::Create(aWindow, __func__);
if (!mSharePromise) {
return NS_ERROR_FAILURE;
}
IPCWebShareData data(title, text, url);
auto wgc = aWindow->GetWindowGlobalChild();
if (!wgc) {
aRv.Throw(NS_ERROR_FAILURE);
return nullptr;
}
wgc->SendShare(data)->Then(
GetCurrentSerialEventTarget(), __func__,
[self = RefPtr{this}](
PWindowGlobalChild::SharePromise::ResolveOrRejectValue&& aResult) {
if (aResult.IsResolve()) {
if (NS_SUCCEEDED(aResult.ResolveValue())) {
self->mSharePromise->MaybeResolveWithUndefined();
} else {
self->mSharePromise->MaybeReject(aResult.ResolveValue());
}
} else if (self->mSharePromise) {
// IPC died
self->mSharePromise->MaybeReject(NS_BINDING_ABORTED);
}
self->mSharePromise = nullptr;
});
return NS_OK;
}
auto ZenCommonUtils::IsSharingSupported() -> bool {
#if defined(XP_WIN) && !defined(__MINGW32__)
// The first public build that supports ShareCanceled API
return IsWindows10BuildOrLater(18956);
#else
return true;
#endif
}
} // namespace: zen

View File

@@ -0,0 +1,38 @@
/* 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/. */
#ifndef mozilla_nsZenCommonUtils_h__
#define mozilla_nsZenCommonUtils_h__
#include "nsIDOMWindow.h"
#include "nsIZenCommonUtils.h"
namespace zen {
/**
* @brief Common utility functions for Zen.
*/
class ZenCommonUtils final : public nsIZenCommonUtils {
NS_DECL_ISUPPORTS
NS_DECL_NSIZENCOMMONUTILS
public:
explicit ZenCommonUtils() = default;
private:
~ZenCommonUtils() = default;
RefPtr<mozilla::dom::Promise> mSharePromise; // Web Share API related
/**
* @brief Check if the current context can share data.
* @param data The data to share.
* @returns True if the current context can share data, false otherwise.
*/
static auto IsSharingSupported() -> bool;
};
} // namespace zen
#endif

View File

@@ -0,0 +1,10 @@
Classes = [
{
'cid': '{d034642a-43b1-4814-be1c-8ad75e337c84}',
'interfaces': ['nsIZenCommonUtils'],
'contract_ids': ['@mozilla.org/zen/common-utils;1'],
'type': 'zen::ZenCommonUtils',
'headers': ['mozilla/ZenCommonUtils.h'],
'js_name': 'zenCommonUtils',
},
]

View File

@@ -0,0 +1,17 @@
XPIDL_MODULE = "zen"
XPIDL_SOURCES += [
"nsIZenCommonUtils.idl",
]
EXPORTS.mozilla += [
"ZenCommonUtils.h",
]
UNIFIED_SOURCES += [
"ZenCommonUtils.cpp",
]
XPCOM_MANIFESTS += [
"components.conf",
]

View File

@@ -0,0 +1,30 @@
/* 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/. */
#include "nsISupports.idl"
#include "nsIDOMWindow.idl"
/**
* @brief Common utility functions for Zen.
*/
[scriptable, uuid(d034642a-43b1-4814-be1c-8ad75e337c84)]
interface nsIZenCommonUtils : nsISupports {
/*
* @brief Share using the native share dialog.
* @param window The window to use for the share dialog.
* @param url The URL to share.
* @param title The title of the share.
* @param text The text to share.
* @returns A promise that resolves when the share is complete.
*/
Promise share(in nsIDOMWindow window, in AString url,
in AString title, in AString text);
/*
* @brief Check if the current context can share data.
* @param window The window to check.
* @returns True if the current context can share data, false otherwise.
*/
boolean canShare(in nsIDOMWindow window);
};

View File

@@ -0,0 +1,4 @@
DIRS += [
"common",
]