Checkpoint
This commit is contained in:
parent
03937a9f89
commit
a0634fa79e
2 changed files with 31 additions and 19 deletions
|
@ -238,7 +238,6 @@ impl AppContext {
|
||||||
});
|
});
|
||||||
|
|
||||||
if blur_window {
|
if blur_window {
|
||||||
cx.window.focus = None;
|
|
||||||
cx.blur();
|
cx.blur();
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
@ -263,12 +262,14 @@ impl AppContext {
|
||||||
self.update_window(window_id, |cx| {
|
self.update_window(window_id, |cx| {
|
||||||
if cx.window.focus == focused {
|
if cx.window.focus == focused {
|
||||||
let mut listeners = mem::take(&mut cx.window.focus_listeners);
|
let mut listeners = mem::take(&mut cx.window.focus_listeners);
|
||||||
let focused = focused.map(|id| FocusHandle::for_id(id, &cx.window.focus_handles));
|
let focused =
|
||||||
|
focused.map(|id| FocusHandle::for_id(id, &cx.window.focus_handles).unwrap());
|
||||||
let blurred = cx
|
let blurred = cx
|
||||||
.window
|
.window
|
||||||
.last_blur
|
.last_blur
|
||||||
|
.take()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.map(|id| FocusHandle::for_id(id, &cx.window.focus_handles));
|
.and_then(|id| FocusHandle::for_id(id, &cx.window.focus_handles));
|
||||||
let event = FocusEvent { focused, blurred };
|
let event = FocusEvent { focused, blurred };
|
||||||
for listener in &listeners {
|
for listener in &listeners {
|
||||||
listener(&event, cx);
|
listener(&event, cx);
|
||||||
|
|
|
@ -12,7 +12,7 @@ use crate::{
|
||||||
use anyhow::Result;
|
use anyhow::Result;
|
||||||
use collections::HashMap;
|
use collections::HashMap;
|
||||||
use derive_more::{Deref, DerefMut};
|
use derive_more::{Deref, DerefMut};
|
||||||
use parking_lot::{RwLock, RwLockUpgradableReadGuard};
|
use parking_lot::RwLock;
|
||||||
use slotmap::SlotMap;
|
use slotmap::SlotMap;
|
||||||
use smallvec::SmallVec;
|
use smallvec::SmallVec;
|
||||||
use std::{
|
use std::{
|
||||||
|
@ -24,7 +24,7 @@ use std::{
|
||||||
mem,
|
mem,
|
||||||
sync::{
|
sync::{
|
||||||
atomic::{AtomicUsize, Ordering::SeqCst},
|
atomic::{AtomicUsize, Ordering::SeqCst},
|
||||||
Arc, Weak,
|
Arc,
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
use util::ResultExt;
|
use util::ResultExt;
|
||||||
|
@ -57,10 +57,9 @@ type AnyKeyUpListener =
|
||||||
|
|
||||||
slotmap::new_key_type! { pub struct FocusId; }
|
slotmap::new_key_type! { pub struct FocusId; }
|
||||||
|
|
||||||
#[derive(Clone)]
|
|
||||||
pub struct FocusHandle {
|
pub struct FocusHandle {
|
||||||
pub(crate) id: FocusId,
|
pub(crate) id: FocusId,
|
||||||
handles: Weak<RwLock<SlotMap<FocusId, AtomicUsize>>>,
|
handles: Arc<RwLock<SlotMap<FocusId, AtomicUsize>>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl FocusHandle {
|
impl FocusHandle {
|
||||||
|
@ -68,20 +67,24 @@ impl FocusHandle {
|
||||||
let id = handles.write().insert(AtomicUsize::new(1));
|
let id = handles.write().insert(AtomicUsize::new(1));
|
||||||
Self {
|
Self {
|
||||||
id,
|
id,
|
||||||
handles: Arc::downgrade(handles),
|
handles: handles.clone(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn for_id(
|
pub(crate) fn for_id(
|
||||||
id: FocusId,
|
id: FocusId,
|
||||||
handles: &Arc<RwLock<SlotMap<FocusId, AtomicUsize>>>,
|
handles: &Arc<RwLock<SlotMap<FocusId, AtomicUsize>>>,
|
||||||
) -> Self {
|
) -> Option<Self> {
|
||||||
let lock = handles.upgradable_read();
|
let lock = handles.read();
|
||||||
let ref_count = lock.get(id).expect("all focus handles dropped for id");
|
let ref_count = lock.get(id)?;
|
||||||
ref_count.fetch_add(1, SeqCst);
|
if ref_count.load(SeqCst) == 0 {
|
||||||
Self {
|
None
|
||||||
id,
|
} else {
|
||||||
handles: Arc::downgrade(handles),
|
ref_count.fetch_add(1, SeqCst);
|
||||||
|
Some(Self {
|
||||||
|
id,
|
||||||
|
handles: handles.clone(),
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -112,6 +115,12 @@ impl FocusHandle {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Clone for FocusHandle {
|
||||||
|
fn clone(&self) -> Self {
|
||||||
|
Self::for_id(self.id, &self.handles).unwrap()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl PartialEq for FocusHandle {
|
impl PartialEq for FocusHandle {
|
||||||
fn eq(&self, other: &Self) -> bool {
|
fn eq(&self, other: &Self) -> bool {
|
||||||
self.id == other.id
|
self.id == other.id
|
||||||
|
@ -122,9 +131,11 @@ impl Eq for FocusHandle {}
|
||||||
|
|
||||||
impl Drop for FocusHandle {
|
impl Drop for FocusHandle {
|
||||||
fn drop(&mut self) {
|
fn drop(&mut self) {
|
||||||
if let Some(handles) = self.handles.upgrade() {
|
self.handles
|
||||||
handles.read().get(self.id).unwrap().fetch_sub(1, SeqCst);
|
.read()
|
||||||
}
|
.get(self.id)
|
||||||
|
.unwrap()
|
||||||
|
.fetch_sub(1, SeqCst);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -279,7 +290,7 @@ impl<'a, 'w> WindowContext<'a, 'w> {
|
||||||
pub fn focused(&self) -> Option<FocusHandle> {
|
pub fn focused(&self) -> Option<FocusHandle> {
|
||||||
self.window
|
self.window
|
||||||
.focus
|
.focus
|
||||||
.map(|id| FocusHandle::for_id(id, &self.window.focus_handles))
|
.and_then(|id| FocusHandle::for_id(id, &self.window.focus_handles))
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn focus(&mut self, handle: &FocusHandle) {
|
pub fn focus(&mut self, handle: &FocusHandle) {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue