diff options
Diffstat (limited to 'components/compositing/webview.rs')
-rw-r--r-- | components/compositing/webview.rs | 236 |
1 files changed, 1 insertions, 235 deletions
diff --git a/components/compositing/webview.rs b/components/compositing/webview.rs index 58fda6d20e5..a3140425563 100644 --- a/components/compositing/webview.rs +++ b/components/compositing/webview.rs @@ -4,7 +4,7 @@ use std::cell::RefCell; use std::collections::HashMap; -use std::collections::hash_map::{Entry, Keys, Values, ValuesMut}; +use std::collections::hash_map::Keys; use std::rc::Rc; use base::id::{PipelineId, WebViewId}; @@ -845,240 +845,6 @@ impl WebView { .push(ScrollZoomEvent::PinchZoom(magnification)); } } -#[derive(Debug)] -pub struct WebViewManager<WebView> { - /// Our top-level browsing contexts. In the WebRender scene, their pipelines are the children of - /// a single root pipeline that also applies any pinch zoom transformation. - webviews: HashMap<WebViewId, WebView>, - - /// The order to paint them in, topmost last. - pub(crate) painting_order: Vec<WebViewId>, -} #[derive(Clone, Copy, Debug, PartialEq)] pub struct UnknownWebView(pub WebViewId); - -impl<WebView> Default for WebViewManager<WebView> { - fn default() -> Self { - Self { - webviews: Default::default(), - painting_order: Default::default(), - } - } -} - -impl<WebView> WebViewManager<WebView> { - pub fn remove(&mut self, webview_id: WebViewId) -> Result<WebView, UnknownWebView> { - self.painting_order.retain(|b| *b != webview_id); - self.webviews - .remove(&webview_id) - .ok_or(UnknownWebView(webview_id)) - } - - pub fn get(&self, webview_id: WebViewId) -> Option<&WebView> { - self.webviews.get(&webview_id) - } - - pub fn get_mut(&mut self, webview_id: WebViewId) -> Option<&mut WebView> { - self.webviews.get_mut(&webview_id) - } - - /// Returns true iff the painting order actually changed. - pub fn show(&mut self, webview_id: WebViewId) -> Result<bool, UnknownWebView> { - if !self.webviews.contains_key(&webview_id) { - return Err(UnknownWebView(webview_id)); - } - if !self.painting_order.contains(&webview_id) { - self.painting_order.push(webview_id); - return Ok(true); - } - Ok(false) - } - - /// Returns true iff the painting order actually changed. - pub fn hide(&mut self, webview_id: WebViewId) -> Result<bool, UnknownWebView> { - if !self.webviews.contains_key(&webview_id) { - return Err(UnknownWebView(webview_id)); - } - if self.painting_order.contains(&webview_id) { - self.painting_order.retain(|b| *b != webview_id); - return Ok(true); - } - Ok(false) - } - - /// Returns true iff the painting order actually changed. - pub fn hide_all(&mut self) -> bool { - if !self.painting_order.is_empty() { - self.painting_order.clear(); - return true; - } - false - } - - /// Returns true iff the painting order actually changed. - pub fn raise_to_top(&mut self, webview_id: WebViewId) -> Result<bool, UnknownWebView> { - if !self.webviews.contains_key(&webview_id) { - return Err(UnknownWebView(webview_id)); - } - if self.painting_order.last() != Some(&webview_id) { - self.hide(webview_id)?; - self.show(webview_id)?; - return Ok(true); - } - Ok(false) - } - - pub fn painting_order(&self) -> impl Iterator<Item = (&WebViewId, &WebView)> { - self.painting_order - .iter() - .flat_map(move |webview_id| self.get(*webview_id).map(|b| (webview_id, b))) - } - - pub fn entry(&mut self, webview_id: WebViewId) -> Entry<'_, WebViewId, WebView> { - self.webviews.entry(webview_id) - } - - pub fn iter(&self) -> Values<'_, WebViewId, WebView> { - self.webviews.values() - } - - pub fn iter_mut(&mut self) -> ValuesMut<'_, WebViewId, WebView> { - self.webviews.values_mut() - } -} - -#[cfg(test)] -mod test { - use std::num::NonZeroU32; - - use base::id::{ - BrowsingContextId, BrowsingContextIndex, PipelineNamespace, PipelineNamespaceId, WebViewId, - }; - - use crate::webview::{UnknownWebView, WebViewManager}; - - fn top_level_id(namespace_id: u32, index: u32) -> WebViewId { - WebViewId(BrowsingContextId { - namespace_id: PipelineNamespaceId(namespace_id), - index: BrowsingContextIndex(NonZeroU32::new(index).unwrap()), - }) - } - - fn webviews_sorted<WebView: Clone>( - webviews: &WebViewManager<WebView>, - ) -> Vec<(WebViewId, WebView)> { - let mut keys = webviews.webviews.keys().collect::<Vec<_>>(); - keys.sort(); - keys.iter() - .map(|&id| (*id, webviews.webviews.get(id).cloned().unwrap())) - .collect() - } - - #[test] - fn test() { - PipelineNamespace::install(PipelineNamespaceId(0)); - let mut webviews = WebViewManager::default(); - - // entry() adds the webview to the map, but not the painting order. - webviews.entry(WebViewId::new()).or_insert('a'); - webviews.entry(WebViewId::new()).or_insert('b'); - webviews.entry(WebViewId::new()).or_insert('c'); - assert!(webviews.get(top_level_id(0, 1)).is_some()); - assert!(webviews.get(top_level_id(0, 2)).is_some()); - assert!(webviews.get(top_level_id(0, 3)).is_some()); - assert_eq!( - webviews_sorted(&webviews), - vec![ - (top_level_id(0, 1), 'a'), - (top_level_id(0, 2), 'b'), - (top_level_id(0, 3), 'c'), - ] - ); - assert!(webviews.painting_order.is_empty()); - - // add() returns WebViewAlreadyExists if the webview id already exists. - webviews.entry(top_level_id(0, 3)).or_insert('d'); - assert!(webviews.get(top_level_id(0, 3)).is_some()); - - // Other methods return UnknownWebView or None if the webview id doesn’t exist. - assert_eq!( - webviews.remove(top_level_id(1, 1)), - Err(UnknownWebView(top_level_id(1, 1))) - ); - assert_eq!(webviews.get(top_level_id(1, 1)), None); - assert_eq!(webviews.get_mut(top_level_id(1, 1)), None); - assert_eq!( - webviews.show(top_level_id(1, 1)), - Err(UnknownWebView(top_level_id(1, 1))) - ); - assert_eq!( - webviews.hide(top_level_id(1, 1)), - Err(UnknownWebView(top_level_id(1, 1))) - ); - assert_eq!( - webviews.raise_to_top(top_level_id(1, 1)), - Err(UnknownWebView(top_level_id(1, 1))) - ); - - // For webviews not yet visible, both show() and raise_to_top() add the given webview on top. - assert_eq!(webviews.show(top_level_id(0, 2)), Ok(true)); - assert_eq!(webviews.show(top_level_id(0, 2)), Ok(false)); - assert_eq!(webviews.painting_order, vec![top_level_id(0, 2)]); - assert_eq!(webviews.raise_to_top(top_level_id(0, 1)), Ok(true)); - assert_eq!(webviews.raise_to_top(top_level_id(0, 1)), Ok(false)); - assert_eq!( - webviews.painting_order, - vec![top_level_id(0, 2), top_level_id(0, 1)] - ); - assert_eq!(webviews.show(top_level_id(0, 3)), Ok(true)); - assert_eq!(webviews.show(top_level_id(0, 3)), Ok(false)); - assert_eq!( - webviews.painting_order, - vec![top_level_id(0, 2), top_level_id(0, 1), top_level_id(0, 3)] - ); - - // For webviews already visible, show() does nothing, while raise_to_top() makes it on top. - assert_eq!(webviews.show(top_level_id(0, 1)), Ok(false)); - assert_eq!( - webviews.painting_order, - vec![top_level_id(0, 2), top_level_id(0, 1), top_level_id(0, 3)] - ); - assert_eq!(webviews.raise_to_top(top_level_id(0, 1)), Ok(true)); - assert_eq!(webviews.raise_to_top(top_level_id(0, 1)), Ok(false)); - assert_eq!( - webviews.painting_order, - vec![top_level_id(0, 2), top_level_id(0, 3), top_level_id(0, 1)] - ); - - // hide() removes the webview from the painting order, but not the map. - assert_eq!(webviews.hide(top_level_id(0, 3)), Ok(true)); - assert_eq!(webviews.hide(top_level_id(0, 3)), Ok(false)); - assert_eq!( - webviews.painting_order, - vec![top_level_id(0, 2), top_level_id(0, 1)] - ); - assert_eq!( - webviews_sorted(&webviews), - vec![ - (top_level_id(0, 1), 'a'), - (top_level_id(0, 2), 'b'), - (top_level_id(0, 3), 'c'), - ] - ); - - // painting_order() returns only the visible webviews, in painting order. - let mut painting_order = webviews.painting_order(); - assert_eq!(painting_order.next(), Some((&top_level_id(0, 2), &'b'))); - assert_eq!(painting_order.next(), Some((&top_level_id(0, 1), &'a'))); - assert_eq!(painting_order.next(), None); - drop(painting_order); - - // remove() removes the given webview from both the map and the painting order. - assert!(webviews.remove(top_level_id(0, 1)).is_ok()); - assert!(webviews.remove(top_level_id(0, 2)).is_ok()); - assert!(webviews.remove(top_level_id(0, 3)).is_ok()); - assert!(webviews_sorted(&webviews).is_empty()); - assert!(webviews.painting_order.is_empty()); - } -} |