mirror of
https://github.com/zen-browser/desktop.git
synced 2026-04-21 06:45:42 +00:00
Merge pull request #8243 from zen-browser/new-share-api
New share API and implementation
This commit is contained in:
@@ -5,7 +5,8 @@
|
||||
*/
|
||||
|
||||
.subviewbutton,
|
||||
#zen-welcome-start-button {
|
||||
#zen-welcome-start-button,
|
||||
.zen-toast button {
|
||||
-moz-context-properties: fill, fill-opacity !important;
|
||||
fill: currentColor !important;
|
||||
}
|
||||
@@ -425,7 +426,8 @@
|
||||
list-style-image: url('customize.svg') !important;
|
||||
}
|
||||
|
||||
#appmenu-zen-share-rice {
|
||||
#appmenu-zen-share-rice,
|
||||
#zen-copy-current-url-button {
|
||||
list-style-image: url('share.svg');
|
||||
}
|
||||
|
||||
|
||||
@@ -72,7 +72,25 @@ var gZenCommonActions = {
|
||||
transferable.addDataFlavor('text/plain');
|
||||
transferable.setTransferData('text/plain', str);
|
||||
Services.clipboard.setData(transferable, null, Ci.nsIClipboard.kGlobalClipboard);
|
||||
gZenUIManager.showToast('zen-copy-current-url-confirmation');
|
||||
let button;
|
||||
if (Services.zen.canShare()) {
|
||||
button = {
|
||||
id: 'zen-copy-current-url-button',
|
||||
command: (event) => {
|
||||
const buttonRect = event.target.getBoundingClientRect();
|
||||
Services.zen.share(
|
||||
Services.io.newURI(currentUrl),
|
||||
'',
|
||||
'',
|
||||
buttonRect.left,
|
||||
window.innerHeight - buttonRect.bottom,
|
||||
buttonRect.width,
|
||||
buttonRect.height
|
||||
);
|
||||
},
|
||||
};
|
||||
}
|
||||
gZenUIManager.showToast('zen-copy-current-url-confirmation', { button, timeout: 3000 });
|
||||
}
|
||||
},
|
||||
copyCurrentURLAsMarkdownToClipboard() {
|
||||
|
||||
@@ -422,6 +422,7 @@ var gZenUIManager = {
|
||||
return [child, true];
|
||||
}
|
||||
}
|
||||
const wrapper = document.createXULElement('hbox');
|
||||
const element = document.createXULElement('vbox');
|
||||
const label = document.createXULElement('label');
|
||||
document.l10n.setAttributes(label, messageId, options);
|
||||
@@ -432,26 +433,25 @@ var gZenUIManager = {
|
||||
document.l10n.setAttributes(description, options.descriptionId, options);
|
||||
element.appendChild(description);
|
||||
}
|
||||
element.classList.add('zen-toast');
|
||||
element._messageId = messageId;
|
||||
return [element, false];
|
||||
wrapper.appendChild(element);
|
||||
if (options.button) {
|
||||
const button = document.createXULElement('button');
|
||||
button.id = options.button.id;
|
||||
button.classList.add('footer-button');
|
||||
button.classList.add('primary');
|
||||
button.addEventListener('command', options.button.command);
|
||||
wrapper.appendChild(button);
|
||||
}
|
||||
wrapper.classList.add('zen-toast');
|
||||
wrapper._messageId = messageId;
|
||||
return [wrapper, false];
|
||||
},
|
||||
|
||||
async showToast(messageId, options = {}) {
|
||||
const [toast, reused] = this._createToastElement(messageId, options);
|
||||
this._toastContainer.removeAttribute('hidden');
|
||||
this._toastContainer.appendChild(toast);
|
||||
if (reused) {
|
||||
await this.motion.animate(toast, { scale: 0.2 }, { duration: 0.1, bounce: 0 });
|
||||
}
|
||||
if (!toast.style.hasOwnProperty('transform')) {
|
||||
toast.style.transform = 'scale(0)';
|
||||
}
|
||||
await this.motion.animate(toast, { scale: 1 }, { type: 'spring', bounce: 0.2, duration: 0.5 });
|
||||
if (this._toastTimeouts[messageId]) {
|
||||
clearTimeout(this._toastTimeouts[messageId]);
|
||||
}
|
||||
this._toastTimeouts[messageId] = setTimeout(() => {
|
||||
const timeoutFunction = () => {
|
||||
this.motion
|
||||
.animate(toast, { opacity: [1, 0], scale: [1, 0.5] }, { duration: 0.2, bounce: 0 })
|
||||
.then(() => {
|
||||
@@ -460,7 +460,30 @@ var gZenUIManager = {
|
||||
this._toastContainer.setAttribute('hidden', true);
|
||||
}
|
||||
});
|
||||
}, options.timeout || 2000);
|
||||
};
|
||||
if (reused) {
|
||||
await this.motion.animate(toast, { scale: 0.2 }, { duration: 0.1, bounce: 0 });
|
||||
} else {
|
||||
toast.addEventListener('mouseover', () => {
|
||||
if (this._toastTimeouts[messageId]) {
|
||||
clearTimeout(this._toastTimeouts[messageId]);
|
||||
}
|
||||
});
|
||||
toast.addEventListener('mouseout', () => {
|
||||
if (this._toastTimeouts[messageId]) {
|
||||
clearTimeout(this._toastTimeouts[messageId]);
|
||||
}
|
||||
this._toastTimeouts[messageId] = setTimeout(timeoutFunction, options.timeout || 2000);
|
||||
});
|
||||
}
|
||||
if (!toast.style.hasOwnProperty('transform')) {
|
||||
toast.style.transform = 'scale(0)';
|
||||
}
|
||||
await this.motion.animate(toast, { scale: 1 }, { type: 'spring', bounce: 0.2, duration: 0.5 });
|
||||
if (this._toastTimeouts[messageId]) {
|
||||
clearTimeout(this._toastTimeouts[messageId]);
|
||||
}
|
||||
this._toastTimeouts[messageId] = setTimeout(timeoutFunction, options.timeout || 2000);
|
||||
},
|
||||
|
||||
get panelUIPosition() {
|
||||
|
||||
@@ -363,8 +363,12 @@ menuitem {
|
||||
translate: 100%;
|
||||
}
|
||||
|
||||
gap: 10px;
|
||||
z-index: 1000;
|
||||
padding: 10px;
|
||||
@media (-moz-platform: windows) {
|
||||
padding: 6px;
|
||||
}
|
||||
border-radius: 12px;
|
||||
background: linear-gradient(
|
||||
170deg,
|
||||
@@ -376,7 +380,7 @@ menuitem {
|
||||
border: 1px solid rgba(0, 0, 0, 0.1);
|
||||
display: flex;
|
||||
font-weight: 600;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
width: max-content;
|
||||
font-size: small;
|
||||
position: absolute;
|
||||
@@ -386,6 +390,19 @@ menuitem {
|
||||
opacity: 0.6;
|
||||
font-size: smaller;
|
||||
}
|
||||
|
||||
& label {
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
& button {
|
||||
width: min-content;
|
||||
padding: 0 12px !important;
|
||||
min-width: unset !important;
|
||||
margin: 0px !important;
|
||||
border-radius: 8px !important;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -7,4 +7,5 @@ DIRS += [
|
||||
"glance",
|
||||
"mods",
|
||||
"tests",
|
||||
"toolkit",
|
||||
]
|
||||
|
||||
114
src/zen/toolkit/common/ZenCommonUtils.cpp
Normal file
114
src/zen/toolkit/common/ZenCommonUtils.cpp
Normal file
@@ -0,0 +1,114 @@
|
||||
/* 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 "ZenCommonUtils.h"
|
||||
#include "ZenShareInternal.h"
|
||||
|
||||
#include "nsGlobalWindowOuter.h"
|
||||
#include "nsQueryObject.h"
|
||||
#include "nsIWindowMediator.h"
|
||||
#include "nsServiceManagerUtils.h"
|
||||
#include "nsISharePicker.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)
|
||||
using WindowGlobalChild = mozilla::dom::WindowGlobalChild;
|
||||
|
||||
namespace {
|
||||
/**
|
||||
* @brief Helper function to fetch the most recent window proxy.
|
||||
* @param aWindow The window to query.
|
||||
* @returns The most recent window.
|
||||
*/
|
||||
static nsresult GetMostRecentWindowProxy(mozIDOMWindowProxy** aWindow) {
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIWindowMediator> med(
|
||||
do_GetService(NS_WINDOWMEDIATOR_CONTRACTID, &rv));
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
if (med) return med->GetMostRecentBrowserWindow(aWindow);
|
||||
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
/**
|
||||
* @brief Helper function to query and get a reference to the window.
|
||||
* @param aWindow The window to query.
|
||||
*/
|
||||
static nsCOMPtr<mozIDOMWindowProxy> GetMostRecentWindow() {
|
||||
nsCOMPtr<mozIDOMWindowProxy> aWindow;
|
||||
nsresult rv = GetMostRecentWindowProxy(getter_AddRefs(aWindow));
|
||||
if (NS_FAILED(rv) || !aWindow) {
|
||||
return nullptr;
|
||||
}
|
||||
return aWindow;
|
||||
}
|
||||
}
|
||||
|
||||
using mozilla::dom::WindowGlobalChild;
|
||||
|
||||
#define NS_ZEN_CAN_SHARE_FAILURE() \
|
||||
*canShare = false; \
|
||||
return NS_OK;
|
||||
|
||||
/*
|
||||
* @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(bool* canShare) {
|
||||
auto aWindow = GetMostRecentWindow();
|
||||
if (!aWindow) {
|
||||
NS_ZEN_CAN_SHARE_FAILURE();
|
||||
}
|
||||
*canShare = IsSharingSupported();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
ZenCommonUtils::Share(nsIURI* url, const nsACString& title, const nsACString& text,
|
||||
uint32_t aX, uint32_t aY, uint32_t aWidth, uint32_t aHeight) {
|
||||
auto aWindow = GetMostRecentWindow();
|
||||
if (!aWindow) {
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
if (!IsSharingSupported()) {
|
||||
return NS_OK; // We don't want to throw an error here
|
||||
}
|
||||
return ShareInternal(aWindow, url, title, text, aX, aY, aWidth, aHeight);
|
||||
}
|
||||
|
||||
nsresult ZenCommonUtils::ShareInternal(nsCOMPtr<mozIDOMWindowProxy>& aWindow, nsIURI* url,
|
||||
const nsACString& title, const nsACString& text, uint32_t aX, uint32_t aY,
|
||||
uint32_t aWidth, uint32_t aHeight) {
|
||||
// We shoud've had done pointer checks before, so we can assume
|
||||
// aWindow is valid.
|
||||
#ifdef NS_ZEN_CAN_SHARE_NATIVE
|
||||
return ::nsZenNativeShareInternal::ShowNativeDialog(
|
||||
aWindow, url, title, text,
|
||||
aX, aY, aWidth, aHeight
|
||||
);
|
||||
#else
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
#endif
|
||||
}
|
||||
|
||||
auto ZenCommonUtils::IsSharingSupported() -> bool {
|
||||
#if defined(XP_WIN) && !defined(__MINGW32__)
|
||||
// The first public build that supports ShareCanceled API
|
||||
return IsWindows10BuildOrLater(18956);
|
||||
#elif defined(NS_ZEN_CAN_SHARE_NATIVE)
|
||||
return NS_ZEN_CAN_SHARE_NATIVE;
|
||||
#else
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
} // namespace: zen
|
||||
50
src/zen/toolkit/common/ZenCommonUtils.h
Normal file
50
src/zen/toolkit/common/ZenCommonUtils.h
Normal file
@@ -0,0 +1,50 @@
|
||||
/* 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 "nsIZenCommonUtils.h"
|
||||
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsGlobalWindowOuter.h"
|
||||
#include "nsIURI.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;
|
||||
/**
|
||||
* @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;
|
||||
/**
|
||||
* @brief Helper function to share data via the native dialogs.
|
||||
* @param aWindow 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.
|
||||
*/
|
||||
static auto ShareInternal(nsCOMPtr<mozIDOMWindowProxy>& aWindow, nsIURI* url,
|
||||
const nsACString& title, const nsACString& text, uint32_t aX, uint32_t aY,
|
||||
uint32_t aWidth, uint32_t aHeight)
|
||||
-> nsresult;
|
||||
};
|
||||
|
||||
} // namespace zen
|
||||
|
||||
#endif
|
||||
41
src/zen/toolkit/common/ZenShareInternal.h
Normal file
41
src/zen/toolkit/common/ZenShareInternal.h
Normal file
@@ -0,0 +1,41 @@
|
||||
/* 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_nsZenShareInternal_h__
|
||||
#define mozilla_nsZenShareInternal_h__
|
||||
|
||||
#include "nsIZenCommonUtils.h"
|
||||
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsGlobalWindowOuter.h"
|
||||
#include "nsIURI.h"
|
||||
|
||||
#if defined(XP_WIN) || defined(XP_MACOSX)
|
||||
#define NS_ZEN_CAN_SHARE_NATIVE true
|
||||
|
||||
class nsZenNativeShareInternal final {
|
||||
public:
|
||||
/**
|
||||
* @brief Use the native share dialog. This only works on Windows and MacOS
|
||||
* since the native share dialog is not available on other platforms.
|
||||
* Macos does need pointer coordinates to show the share dialog while
|
||||
* Windows does not since it just displays a dialog on the middle of the
|
||||
* screen.
|
||||
* @param aWindow The window to use for the share dialog.
|
||||
* @param aUrl The URL to share.
|
||||
* @param aTitle The title of the share.
|
||||
* @param aText The text to share.
|
||||
* @returns void
|
||||
*/
|
||||
static auto ShowNativeDialog(nsCOMPtr<mozIDOMWindowProxy>& aWindow, nsIURI* aUrl,
|
||||
const nsACString& aTitle, const nsACString& aText, uint32_t aX = 0, uint32_t aY = 0,
|
||||
uint32_t aWidth = 0, uint32_t aHeight = 0)
|
||||
-> nsresult;
|
||||
|
||||
nsZenNativeShareInternal() = default;
|
||||
~nsZenNativeShareInternal() = default;
|
||||
};
|
||||
|
||||
#endif
|
||||
#endif
|
||||
78
src/zen/toolkit/common/cocoa/ZenShareInternal.mm
Normal file
78
src/zen/toolkit/common/cocoa/ZenShareInternal.mm
Normal file
@@ -0,0 +1,78 @@
|
||||
/* 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 "ZenShareInternal.h"
|
||||
#include "nsCocoaUtils.h"
|
||||
|
||||
#include "nsPIDOMWindow.h"
|
||||
#include "WidgetUtils.h"
|
||||
#include "nsIWidget.h"
|
||||
|
||||
extern mozilla::LazyLogModule gCocoaUtilsLog;
|
||||
#undef LOG
|
||||
#define LOG(...) MOZ_LOG(gCocoaUtilsLog, mozilla::LogLevel::Info, (__VA_ARGS__))
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
#import <AppKit/AppKit.h>
|
||||
|
||||
namespace zen {
|
||||
using ::mozilla::widget::WidgetUtils;
|
||||
|
||||
/**
|
||||
* Get the native NSWindow pointer from a DOM window.
|
||||
*
|
||||
* @param a_window The DOM window to get the native window from.
|
||||
* @param a_nativeWindow The pointer to the native NSWindow.
|
||||
* @return NS_OK on success, or an error code on failure.
|
||||
*/
|
||||
static nsresult GetNativeWindowPointerFromDOMWindow(mozIDOMWindowProxy* a_window,
|
||||
NSWindow** a_nativeWindow) {
|
||||
*a_nativeWindow = nil;
|
||||
if (!a_window) return NS_ERROR_INVALID_ARG;
|
||||
nsPIDOMWindowOuter* win = nsPIDOMWindowOuter::From(a_window);
|
||||
nsCOMPtr<nsIWidget> widget = WidgetUtils::DOMWindowToWidget(win);
|
||||
if (!widget) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
*a_nativeWindow = (NSWindow*)widget->GetNativeData(NS_NATIVE_WINDOW);
|
||||
return NS_OK;
|
||||
}
|
||||
}
|
||||
|
||||
auto nsZenNativeShareInternal::ShowNativeDialog(nsCOMPtr<mozIDOMWindowProxy>& aWindow,
|
||||
nsIURI* aUrl, const nsACString& aTitle, const nsACString& aText, uint32_t aX, uint32_t aY,
|
||||
uint32_t aWidth, uint32_t aHeight)
|
||||
-> nsresult {
|
||||
// Just use the URL since apple doesn't support sharing text
|
||||
// and title in the share dialog
|
||||
nsAutoCString pageUrlAsStringTemp;
|
||||
if (aUrl) {
|
||||
nsresult rv = aUrl->GetSpec(pageUrlAsStringTemp);
|
||||
MOZ_ASSERT(NS_SUCCEEDED(rv));
|
||||
mozilla::Unused << rv;
|
||||
} else {
|
||||
pageUrlAsStringTemp.SetIsVoid(true);
|
||||
}
|
||||
NSURL* pageUrl = nsCocoaUtils::ToNSURL(
|
||||
NS_ConvertUTF8toUTF16(pageUrlAsStringTemp)
|
||||
);
|
||||
if (!pageUrl || (![pageUrl.scheme isEqualToString:@"https"] &&
|
||||
![pageUrl.scheme isEqualToString:@"http"])) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
NSSharingServicePicker* sharingPicker =
|
||||
[[NSSharingServicePicker alloc] initWithItems:@[ pageUrl ]];
|
||||
NSWindow* cocoaMru = nil;
|
||||
zen::GetNativeWindowPointerFromDOMWindow(aWindow, &cocoaMru);
|
||||
if (!cocoaMru) {
|
||||
LOG("ERROR: failed to get native window pointer");
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
// Create a rect for the sharing picker
|
||||
NSRect rect = NSMakeRect(aX, aY, aWidth, aHeight);
|
||||
[sharingPicker showRelativeToRect:rect
|
||||
ofView:cocoaMru.contentView
|
||||
preferredEdge:NSMaxYEdge];
|
||||
return NS_OK;
|
||||
}
|
||||
12
src/zen/toolkit/common/cocoa/moz.build
Normal file
12
src/zen/toolkit/common/cocoa/moz.build
Normal file
@@ -0,0 +1,12 @@
|
||||
|
||||
FINAL_LIBRARY = "xul"
|
||||
SOURCES += [
|
||||
"ZenShareInternal.mm",
|
||||
]
|
||||
|
||||
LOCAL_INCLUDES += [
|
||||
"../",
|
||||
"/widget",
|
||||
"/widget/cocoa",
|
||||
"/xpcom/base",
|
||||
]
|
||||
11
src/zen/toolkit/common/components.conf
Normal file
11
src/zen/toolkit/common/components.conf
Normal file
@@ -0,0 +1,11 @@
|
||||
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': 'zen',
|
||||
'processes': ProcessSelector.MAIN_PROCESS_ONLY,
|
||||
},
|
||||
]
|
||||
26
src/zen/toolkit/common/moz.build
Normal file
26
src/zen/toolkit/common/moz.build
Normal file
@@ -0,0 +1,26 @@
|
||||
|
||||
XPIDL_SOURCES += [
|
||||
"nsIZenCommonUtils.idl",
|
||||
]
|
||||
|
||||
EXPORTS.mozilla += [
|
||||
"ZenCommonUtils.h",
|
||||
"ZenShareInternal.h",
|
||||
]
|
||||
|
||||
SOURCES += [
|
||||
"ZenCommonUtils.cpp",
|
||||
]
|
||||
|
||||
XPCOM_MANIFESTS += [
|
||||
"components.conf",
|
||||
]
|
||||
|
||||
if CONFIG["MOZ_WIDGET_TOOLKIT"] == "windows":
|
||||
DIRS += ["windows"]
|
||||
|
||||
if CONFIG["MOZ_WIDGET_TOOLKIT"] == "cocoa":
|
||||
DIRS += ["cocoa"]
|
||||
|
||||
FINAL_LIBRARY = "xul"
|
||||
XPIDL_MODULE = "zen"
|
||||
32
src/zen/toolkit/common/nsIZenCommonUtils.idl
Normal file
32
src/zen/toolkit/common/nsIZenCommonUtils.idl
Normal file
@@ -0,0 +1,32 @@
|
||||
/* 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 "nsIURI.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.
|
||||
* @param x The x coordinate of the share dialog.
|
||||
* @param y The y coordinate of the share dialog.
|
||||
* @returns A promise that resolves when the share is complete.
|
||||
*/
|
||||
void share(in nsIURI url, in ACString title, in ACString text,
|
||||
in uint32_t x, in uint32_t y, in uint32_t width, in uint32_t height);
|
||||
/*
|
||||
* @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();
|
||||
};
|
||||
|
||||
38
src/zen/toolkit/common/windows/ZenShareInternal.cpp
Normal file
38
src/zen/toolkit/common/windows/ZenShareInternal.cpp
Normal 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/. */
|
||||
|
||||
#include "ZenShareInternal.h"
|
||||
#include "WindowsUIUtils.h"
|
||||
|
||||
namespace zen {
|
||||
/**
|
||||
* @brief Helper function to convert UTF-8 to UTF-16.
|
||||
* @param aStr The UTF-8 string to convert.
|
||||
* @returns The converted UTF-16 string.
|
||||
*/
|
||||
inline NS_ConvertUTF8toUTF16 NS_ConvertUTF8toUTF16_MaybeVoid(
|
||||
const nsACString& aStr) {
|
||||
auto str = NS_ConvertUTF8toUTF16(aStr);
|
||||
str.SetIsVoid(aStr.IsVoid());
|
||||
return str;
|
||||
}
|
||||
} // namespace: zen
|
||||
|
||||
auto nsZenNativeShareInternal::ShowNativeDialog(
|
||||
nsCOMPtr<mozIDOMWindowProxy>& aWindow, nsIURI* aUrl, const nsACString& aTitle,
|
||||
const nsACString& aText, uint32_t aX, uint32_t aY, uint32_t aWidth, uint32_t aHeight)
|
||||
-> nsresult {
|
||||
nsAutoCString urlString;
|
||||
if (aUrl) {
|
||||
nsresult rv = aUrl->GetSpec(urlString);
|
||||
MOZ_ASSERT(NS_SUCCEEDED(rv));
|
||||
mozilla::Unused << rv;
|
||||
} else {
|
||||
urlString.SetIsVoid(true);
|
||||
}
|
||||
(void)WindowsUIUtils::Share(zen::NS_ConvertUTF8toUTF16_MaybeVoid(aTitle),
|
||||
zen::NS_ConvertUTF8toUTF16_MaybeVoid(aText),
|
||||
zen::NS_ConvertUTF8toUTF16_MaybeVoid(urlString));
|
||||
return NS_OK;
|
||||
}
|
||||
11
src/zen/toolkit/common/windows/moz.build
Normal file
11
src/zen/toolkit/common/windows/moz.build
Normal file
@@ -0,0 +1,11 @@
|
||||
|
||||
FINAL_LIBRARY = "xul"
|
||||
SOURCES += [
|
||||
"ZenShareInternal.cpp",
|
||||
]
|
||||
|
||||
LOCAL_INCLUDES += [
|
||||
"../",
|
||||
"/widget",
|
||||
"/widget/windows",
|
||||
]
|
||||
4
src/zen/toolkit/moz.build
Normal file
4
src/zen/toolkit/moz.build
Normal file
@@ -0,0 +1,4 @@
|
||||
|
||||
DIRS += [
|
||||
"common",
|
||||
]
|
||||
Reference in New Issue
Block a user