Make it possible to add a title to context menu

This commit is contained in:
Paul Rouget 2020-03-31 09:40:57 +02:00
parent 687156ac90
commit 0b489a0135
9 changed files with 33 additions and 18 deletions

2
.gitignore vendored
View file

@ -53,7 +53,7 @@ support/hololens/ARM64/
support/hololens/ServoApp/x64/ support/hololens/ServoApp/x64/
support/hololens/ServoApp/ARM/ support/hololens/ServoApp/ARM/
support/hololens/ServoApp/ARM64/ support/hololens/ServoApp/ARM64/
support/hololens/ServoApp/Generated\ Files support/hololens/ServoApp/Generated Files/
support/hololens/ServoApp/BundleArtifacts/ support/hololens/ServoApp/BundleArtifacts/
support/hololens/ServoApp/support/ support/hololens/ServoApp/support/
support/hololens/ServoApp/Debug/ support/hololens/ServoApp/Debug/

View file

@ -157,7 +157,7 @@ pub enum EmbedderMsg {
/// Show dialog to user /// Show dialog to user
Prompt(PromptDefinition, PromptOrigin), Prompt(PromptDefinition, PromptOrigin),
/// Show a context menu to the user /// Show a context menu to the user
ShowContextMenu(IpcSender<ContextMenuResult>, Vec<String>), ShowContextMenu(IpcSender<ContextMenuResult>, Option<String>, Vec<String>),
/// Whether or not to allow a pipeline to load a url. /// Whether or not to allow a pipeline to load a url.
AllowNavigationRequest(PipelineId, ServoUrl), AllowNavigationRequest(PipelineId, ServoUrl),
/// Whether or not to allow script to open a new tab/browser /// Whether or not to allow script to open a new tab/browser

View file

@ -521,7 +521,7 @@ where
Err(()) => error!("Error running devtools server"), Err(()) => error!("Error running devtools server"),
} }
}, },
EmbedderMsg::ShowContextMenu(sender, _) => { EmbedderMsg::ShowContextMenu(sender, ..) => {
let _ = sender.send(ContextMenuResult::Ignored); let _ = sender.send(ContextMenuResult::Ignored);
} }
} }

View file

@ -105,7 +105,7 @@ pub trait HostTrait {
/// Ask for string /// Ask for string
fn prompt_input(&self, msg: String, default: String, trusted: bool) -> Option<String>; fn prompt_input(&self, msg: String, default: String, trusted: bool) -> Option<String>;
/// Show context menu /// Show context menu
fn show_context_menu(&self, items: Vec<String>); fn show_context_menu(&self, title: Option<String>, items: Vec<String>);
/// Page starts loading. /// Page starts loading.
/// "Reload button" should be disabled. /// "Reload button" should be disabled.
/// "Stop button" should be enabled. /// "Stop button" should be enabled.
@ -579,7 +579,7 @@ impl ServoGlue {
EmbedderMsg::AllowUnload(sender) => { EmbedderMsg::AllowUnload(sender) => {
let _ = sender.send(true); let _ = sender.send(true);
}, },
EmbedderMsg::ShowContextMenu(sender, items) => { EmbedderMsg::ShowContextMenu(sender, title, items) => {
if self.context_menu_sender.is_some() { if self.context_menu_sender.is_some() {
warn!( warn!(
"Trying to show a context menu when a context menu is already active" "Trying to show a context menu when a context menu is already active"
@ -587,7 +587,9 @@ impl ServoGlue {
let _ = sender.send(ContextMenuResult::Ignored); let _ = sender.send(ContextMenuResult::Ignored);
} else { } else {
self.context_menu_sender = Some(sender); self.context_menu_sender = Some(sender);
self.callbacks.host_callbacks.show_context_menu(items); self.callbacks
.host_callbacks
.show_context_menu(title, items);
} }
}, },
EmbedderMsg::Prompt(definition, origin) => { EmbedderMsg::Prompt(definition, origin) => {

View file

@ -230,7 +230,8 @@ pub struct CHostCallbacks {
trusted: bool, trusted: bool,
) -> *const c_char, ) -> *const c_char,
pub on_devtools_started: extern "C" fn(result: CDevtoolsServerState, port: c_uint), pub on_devtools_started: extern "C" fn(result: CDevtoolsServerState, port: c_uint),
pub show_context_menu: extern "C" fn(items_list: *const *const c_char, items_size: u32), pub show_context_menu:
extern "C" fn(title: *const c_char, items_list: *const *const c_char, items_size: u32),
} }
/// Servo options /// Servo options
@ -903,15 +904,19 @@ impl HostTrait for HostCallbacks {
} }
} }
fn show_context_menu(&self, items: Vec<String>) { fn show_context_menu(&self, title: Option<String>, items: Vec<String>) {
debug!("show_context_menu"); debug!("show_context_menu");
let size = items.len() as u32; let items_size = items.len() as u32;
let cstrs: Vec<CString> = items let cstrs: Vec<CString> = items
.into_iter() .into_iter()
.map(|i| CString::new(i).expect("Can't create string")) .map(|i| CString::new(i).expect("Can't create string"))
.collect(); .collect();
let ptrs: Vec<*const c_char> = cstrs.iter().map(|cstr| cstr.as_ptr()).collect(); let items: Vec<*const c_char> = cstrs.iter().map(|cstr| cstr.as_ptr()).collect();
(self.0.show_context_menu)(ptrs.as_ptr(), size); let title = title.map(|s| CString::new(s).expect("Can't create string"));
// let _ = cstrs; // Don't drop these too early let title_ptr = title
.as_ref()
.map(|cstr| cstr.as_ptr())
.unwrap_or(std::ptr::null());
(self.0.show_context_menu)(title_ptr, items.as_ptr(), items_size);
} }
} }

View file

@ -67,12 +67,17 @@ void prompt_alert(const char *message, bool trusted) {
sServo->Delegate().OnServoPromptAlert(char2hstring(message), trusted); sServo->Delegate().OnServoPromptAlert(char2hstring(message), trusted);
} }
void show_context_menu(const char *const *items_list, uint32_t items_size) { void show_context_menu(const char *title, const char *const *items_list,
uint32_t items_size) {
std::optional<hstring> opt_title = {};
if (title != nullptr) {
opt_title = char2hstring(title);
}
std::vector<winrt::hstring> items; std::vector<winrt::hstring> items;
for (uint32_t i = 0; i < items_size; i++) { for (uint32_t i = 0; i < items_size; i++) {
items.push_back(char2hstring(items_list[i])); items.push_back(char2hstring(items_list[i]));
} }
sServo->Delegate().OnServoShowContextMenu(items); sServo->Delegate().OnServoShowContextMenu(opt_title, items);
} }
void on_devtools_started(Servo::DevtoolsServerState result, void on_devtools_started(Servo::DevtoolsServerState result,

View file

@ -105,7 +105,8 @@ public:
virtual void OnServoMediaSessionMetadata(hstring, hstring, hstring) = 0; virtual void OnServoMediaSessionMetadata(hstring, hstring, hstring) = 0;
virtual void OnServoMediaSessionPlaybackStateChange(int) = 0; virtual void OnServoMediaSessionPlaybackStateChange(int) = 0;
virtual void OnServoPromptAlert(hstring, bool) = 0; virtual void OnServoPromptAlert(hstring, bool) = 0;
virtual void OnServoShowContextMenu(std::vector<hstring>) = 0; virtual void OnServoShowContextMenu(std::optional<hstring>,
std::vector<hstring>) = 0;
virtual Servo::PromptResult OnServoPromptOkCancel(hstring, bool) = 0; virtual Servo::PromptResult OnServoPromptOkCancel(hstring, bool) = 0;
virtual Servo::PromptResult OnServoPromptYesNo(hstring, bool) = 0; virtual Servo::PromptResult OnServoPromptYesNo(hstring, bool) = 0;
virtual std::optional<hstring> OnServoPromptInput(hstring, hstring, bool) = 0; virtual std::optional<hstring> OnServoPromptInput(hstring, hstring, bool) = 0;

View file

@ -564,9 +564,10 @@ void ServoControl::OnServoDevtoolsStarted(bool success,
}); });
} }
void ServoControl::OnServoShowContextMenu(std::vector<winrt::hstring> items) { void ServoControl::OnServoShowContextMenu(std::optional<hstring> title,
std::vector<winrt::hstring> items) {
RunOnUIThread([=] { RunOnUIThread([=] {
MessageDialog msg{L"Menu"}; MessageDialog msg{title.value_or(L"Menu")};
for (auto i = 0; i < items.size(); i++) { for (auto i = 0; i < items.size(); i++) {
UICommand cmd{items[i], [=](auto) { UICommand cmd{items[i], [=](auto) {
RunOnGLThread([=] { RunOnGLThread([=] {

View file

@ -117,7 +117,8 @@ struct ServoControl : ServoControlT<ServoControl>, public servo::ServoDelegate {
winrt::hstring); winrt::hstring);
virtual void OnServoMediaSessionPlaybackStateChange(int); virtual void OnServoMediaSessionPlaybackStateChange(int);
virtual void OnServoPromptAlert(winrt::hstring, bool); virtual void OnServoPromptAlert(winrt::hstring, bool);
virtual void OnServoShowContextMenu(std::vector<winrt::hstring>); virtual void OnServoShowContextMenu(std::optional<winrt::hstring>,
std::vector<winrt::hstring>);
virtual servo::Servo::PromptResult OnServoPromptOkCancel(winrt::hstring, virtual servo::Servo::PromptResult OnServoPromptOkCancel(winrt::hstring,
bool); bool);
virtual servo::Servo::PromptResult OnServoPromptYesNo(winrt::hstring, bool); virtual servo::Servo::PromptResult OnServoPromptYesNo(winrt::hstring, bool);