Add OS file drop event handler
Co-Authored-By: Nathan Sobo <nathan@zed.dev>
This commit is contained in:
parent
5b04f965fa
commit
a01b507ef4
9 changed files with 141 additions and 85 deletions
|
@ -821,7 +821,7 @@ impl<G: 'static> DerefMut for GlobalLease<G> {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) struct AnyDrag {
|
pub(crate) struct AnyDrag {
|
||||||
pub drag_handle_view: AnyView,
|
pub drag_handle_view: Option<AnyView>,
|
||||||
pub cursor_offset: Point<Pixels>,
|
pub cursor_offset: Point<Pixels>,
|
||||||
pub state: AnyBox,
|
pub state: AnyBox,
|
||||||
pub state_type: TypeId,
|
pub state_type: TypeId,
|
||||||
|
|
|
@ -374,10 +374,12 @@ pub trait StatefulInteractive: StatelessInteractive {
|
||||||
Some(Arc::new(move |view_state, cursor_offset, cx| {
|
Some(Arc::new(move |view_state, cursor_offset, cx| {
|
||||||
let drag = listener(view_state, cx);
|
let drag = listener(view_state, cx);
|
||||||
let view_handle = cx.handle().upgrade().unwrap();
|
let view_handle = cx.handle().upgrade().unwrap();
|
||||||
let drag_handle_view = view(view_handle, move |view_state, cx| {
|
let drag_handle_view = Some(
|
||||||
(drag.render_drag_handle)(view_state, cx)
|
view(view_handle, move |view_state, cx| {
|
||||||
})
|
(drag.render_drag_handle)(view_state, cx)
|
||||||
.into_any();
|
})
|
||||||
|
.into_any(),
|
||||||
|
);
|
||||||
AnyDrag {
|
AnyDrag {
|
||||||
drag_handle_view,
|
drag_handle_view,
|
||||||
cursor_offset,
|
cursor_offset,
|
||||||
|
@ -780,11 +782,7 @@ impl GroupBounds {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn pop(name: &SharedString, cx: &mut AppContext) {
|
pub fn pop(name: &SharedString, cx: &mut AppContext) {
|
||||||
cx.default_global::<Self>()
|
cx.default_global::<Self>().0.get_mut(name).unwrap().pop();
|
||||||
.0
|
|
||||||
.get_mut(name)
|
|
||||||
.unwrap()
|
|
||||||
.pop();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1035,16 +1033,21 @@ impl Deref for MouseExitEvent {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone, Default)]
|
#[derive(Debug, Clone, Default)]
|
||||||
|
pub struct DroppedFiles(pub(crate) SmallVec<[PathBuf; 2]>);
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
pub enum FileDropEvent {
|
pub enum FileDropEvent {
|
||||||
#[default]
|
Entered {
|
||||||
End,
|
position: Point<Pixels>,
|
||||||
|
files: DroppedFiles,
|
||||||
|
},
|
||||||
Pending {
|
Pending {
|
||||||
position: Point<Pixels>,
|
position: Point<Pixels>,
|
||||||
},
|
},
|
||||||
Submit {
|
Submit {
|
||||||
position: Point<Pixels>,
|
position: Point<Pixels>,
|
||||||
paths: Vec<PathBuf>,
|
|
||||||
},
|
},
|
||||||
|
Exited,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
@ -1054,7 +1057,7 @@ pub enum InputEvent {
|
||||||
ModifiersChanged(ModifiersChangedEvent),
|
ModifiersChanged(ModifiersChangedEvent),
|
||||||
MouseDown(MouseDownEvent),
|
MouseDown(MouseDownEvent),
|
||||||
MouseUp(MouseUpEvent),
|
MouseUp(MouseUpEvent),
|
||||||
MouseMoved(MouseMoveEvent),
|
MouseMove(MouseMoveEvent),
|
||||||
MouseExited(MouseExitEvent),
|
MouseExited(MouseExitEvent),
|
||||||
ScrollWheel(ScrollWheelEvent),
|
ScrollWheel(ScrollWheelEvent),
|
||||||
FileDrop(FileDropEvent),
|
FileDrop(FileDropEvent),
|
||||||
|
@ -1068,12 +1071,14 @@ impl InputEvent {
|
||||||
InputEvent::ModifiersChanged { .. } => None,
|
InputEvent::ModifiersChanged { .. } => None,
|
||||||
InputEvent::MouseDown(event) => Some(event.position),
|
InputEvent::MouseDown(event) => Some(event.position),
|
||||||
InputEvent::MouseUp(event) => Some(event.position),
|
InputEvent::MouseUp(event) => Some(event.position),
|
||||||
InputEvent::MouseMoved(event) => Some(event.position),
|
InputEvent::MouseMove(event) => Some(event.position),
|
||||||
InputEvent::MouseExited(event) => Some(event.position),
|
InputEvent::MouseExited(event) => Some(event.position),
|
||||||
InputEvent::ScrollWheel(event) => Some(event.position),
|
InputEvent::ScrollWheel(event) => Some(event.position),
|
||||||
InputEvent::FileDrop(FileDropEvent::End) => None,
|
InputEvent::FileDrop(FileDropEvent::Exited) => None,
|
||||||
InputEvent::FileDrop(
|
InputEvent::FileDrop(
|
||||||
FileDropEvent::Pending { position } | FileDropEvent::Submit { position, .. },
|
FileDropEvent::Entered { position, .. }
|
||||||
|
| FileDropEvent::Pending { position, .. }
|
||||||
|
| FileDropEvent::Submit { position, .. },
|
||||||
) => Some(*position),
|
) => Some(*position),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1085,7 +1090,7 @@ impl InputEvent {
|
||||||
InputEvent::ModifiersChanged { .. } => None,
|
InputEvent::ModifiersChanged { .. } => None,
|
||||||
InputEvent::MouseDown(event) => Some(event),
|
InputEvent::MouseDown(event) => Some(event),
|
||||||
InputEvent::MouseUp(event) => Some(event),
|
InputEvent::MouseUp(event) => Some(event),
|
||||||
InputEvent::MouseMoved(event) => Some(event),
|
InputEvent::MouseMove(event) => Some(event),
|
||||||
InputEvent::MouseExited(event) => Some(event),
|
InputEvent::MouseExited(event) => Some(event),
|
||||||
InputEvent::ScrollWheel(event) => Some(event),
|
InputEvent::ScrollWheel(event) => Some(event),
|
||||||
InputEvent::FileDrop(event) => Some(event),
|
InputEvent::FileDrop(event) => Some(event),
|
||||||
|
@ -1099,7 +1104,7 @@ impl InputEvent {
|
||||||
InputEvent::ModifiersChanged(event) => Some(event),
|
InputEvent::ModifiersChanged(event) => Some(event),
|
||||||
InputEvent::MouseDown(_) => None,
|
InputEvent::MouseDown(_) => None,
|
||||||
InputEvent::MouseUp(_) => None,
|
InputEvent::MouseUp(_) => None,
|
||||||
InputEvent::MouseMoved(_) => None,
|
InputEvent::MouseMove(_) => None,
|
||||||
InputEvent::MouseExited(_) => None,
|
InputEvent::MouseExited(_) => None,
|
||||||
InputEvent::ScrollWheel(_) => None,
|
InputEvent::ScrollWheel(_) => None,
|
||||||
InputEvent::FileDrop(_) => None,
|
InputEvent::FileDrop(_) => None,
|
||||||
|
|
|
@ -202,7 +202,7 @@ impl InputEvent {
|
||||||
};
|
};
|
||||||
|
|
||||||
window_height.map(|window_height| {
|
window_height.map(|window_height| {
|
||||||
Self::MouseMoved(MouseMoveEvent {
|
Self::MouseMove(MouseMoveEvent {
|
||||||
pressed_button: Some(pressed_button),
|
pressed_button: Some(pressed_button),
|
||||||
position: point(
|
position: point(
|
||||||
px(native_event.locationInWindow().x as f32),
|
px(native_event.locationInWindow().x as f32),
|
||||||
|
@ -213,7 +213,7 @@ impl InputEvent {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
NSEventType::NSMouseMoved => window_height.map(|window_height| {
|
NSEventType::NSMouseMoved => window_height.map(|window_height| {
|
||||||
Self::MouseMoved(MouseMoveEvent {
|
Self::MouseMove(MouseMoveEvent {
|
||||||
position: point(
|
position: point(
|
||||||
px(native_event.locationInWindow().x as f32),
|
px(native_event.locationInWindow().x as f32),
|
||||||
window_height - px(native_event.locationInWindow().y as f32),
|
window_height - px(native_event.locationInWindow().y as f32),
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
use super::{display_bounds_from_native, ns_string, MacDisplay, MetalRenderer, NSRange};
|
use super::{display_bounds_from_native, ns_string, MacDisplay, MetalRenderer, NSRange};
|
||||||
use crate::{
|
use crate::{
|
||||||
display_bounds_to_native, point, px, size, AnyWindowHandle, Bounds, Executor, FileDropEvent,
|
display_bounds_to_native, point, px, size, AnyWindowHandle, Bounds, DroppedFiles, Executor,
|
||||||
GlobalPixels, InputEvent, KeyDownEvent, Keystroke, Modifiers, ModifiersChangedEvent,
|
FileDropEvent, GlobalPixels, InputEvent, KeyDownEvent, Keystroke, Modifiers,
|
||||||
MouseButton, MouseDownEvent, MouseMoveEvent, MouseUpEvent, Pixels, PlatformAtlas,
|
ModifiersChangedEvent, MouseButton, MouseDownEvent, MouseMoveEvent, MouseUpEvent, Pixels,
|
||||||
PlatformDisplay, PlatformInputHandler, PlatformWindow, Point, Scene, Size, Timer,
|
PlatformAtlas, PlatformDisplay, PlatformInputHandler, PlatformWindow, Point, Scene, Size,
|
||||||
WindowAppearance, WindowBounds, WindowKind, WindowOptions, WindowPromptLevel,
|
Timer, WindowAppearance, WindowBounds, WindowKind, WindowOptions, WindowPromptLevel,
|
||||||
};
|
};
|
||||||
use block::ConcreteBlock;
|
use block::ConcreteBlock;
|
||||||
use cocoa::{
|
use cocoa::{
|
||||||
|
@ -31,6 +31,7 @@ use objc::{
|
||||||
sel, sel_impl,
|
sel, sel_impl,
|
||||||
};
|
};
|
||||||
use parking_lot::Mutex;
|
use parking_lot::Mutex;
|
||||||
|
use smallvec::SmallVec;
|
||||||
use std::{
|
use std::{
|
||||||
any::Any,
|
any::Any,
|
||||||
cell::{Cell, RefCell},
|
cell::{Cell, RefCell},
|
||||||
|
@ -1177,7 +1178,7 @@ extern "C" fn handle_view_event(this: &Object, _: Sel, native_event: id) {
|
||||||
};
|
};
|
||||||
|
|
||||||
match &event {
|
match &event {
|
||||||
InputEvent::MouseMoved(
|
InputEvent::MouseMove(
|
||||||
event @ MouseMoveEvent {
|
event @ MouseMoveEvent {
|
||||||
pressed_button: Some(_),
|
pressed_button: Some(_),
|
||||||
..
|
..
|
||||||
|
@ -1194,7 +1195,7 @@ extern "C" fn handle_view_event(this: &Object, _: Sel, native_event: id) {
|
||||||
.detach();
|
.detach();
|
||||||
}
|
}
|
||||||
|
|
||||||
InputEvent::MouseMoved(_) if !(is_active || lock.kind == WindowKind::PopUp) => return,
|
InputEvent::MouseMove(_) if !(is_active || lock.kind == WindowKind::PopUp) => return,
|
||||||
|
|
||||||
InputEvent::MouseUp(MouseUpEvent {
|
InputEvent::MouseUp(MouseUpEvent {
|
||||||
button: MouseButton::Left,
|
button: MouseButton::Left,
|
||||||
|
@ -1633,11 +1634,14 @@ extern "C" fn accepts_first_mouse(this: &Object, _: Sel, _: id) -> BOOL {
|
||||||
|
|
||||||
extern "C" fn dragging_entered(this: &Object, _: Sel, dragging_info: id) -> NSDragOperation {
|
extern "C" fn dragging_entered(this: &Object, _: Sel, dragging_info: id) -> NSDragOperation {
|
||||||
let window_state = unsafe { get_window_state(this) };
|
let window_state = unsafe { get_window_state(this) };
|
||||||
let position = drag_event_position(&window_state, dragging_info);
|
if send_new_event(&window_state, {
|
||||||
if send_new_event(
|
let position = drag_event_position(&window_state, dragging_info);
|
||||||
&window_state,
|
let paths = external_paths_from_event(dragging_info);
|
||||||
InputEvent::FileDrop(FileDropEvent::Pending { position }),
|
InputEvent::FileDrop(FileDropEvent::Entered {
|
||||||
) {
|
position,
|
||||||
|
files: paths,
|
||||||
|
})
|
||||||
|
}) {
|
||||||
NSDragOperationCopy
|
NSDragOperationCopy
|
||||||
} else {
|
} else {
|
||||||
NSDragOperationNone
|
NSDragOperationNone
|
||||||
|
@ -1659,26 +1663,17 @@ extern "C" fn dragging_updated(this: &Object, _: Sel, dragging_info: id) -> NSDr
|
||||||
|
|
||||||
extern "C" fn dragging_exited(this: &Object, _: Sel, _: id) {
|
extern "C" fn dragging_exited(this: &Object, _: Sel, _: id) {
|
||||||
let window_state = unsafe { get_window_state(this) };
|
let window_state = unsafe { get_window_state(this) };
|
||||||
send_new_event(&window_state, InputEvent::FileDrop(FileDropEvent::End));
|
send_new_event(&window_state, InputEvent::FileDrop(FileDropEvent::Exited));
|
||||||
}
|
}
|
||||||
|
|
||||||
extern "C" fn perform_drag_operation(this: &Object, _: Sel, dragging_info: id) -> BOOL {
|
extern "C" fn perform_drag_operation(this: &Object, _: Sel, dragging_info: id) -> BOOL {
|
||||||
let mut paths = Vec::new();
|
let files = external_paths_from_event(dragging_info);
|
||||||
let pb: id = unsafe { msg_send![dragging_info, draggingPasteboard] };
|
|
||||||
let filenames = unsafe { NSPasteboard::propertyListForType(pb, NSFilenamesPboardType) };
|
|
||||||
for file in unsafe { filenames.iter() } {
|
|
||||||
let path = unsafe {
|
|
||||||
let f = NSString::UTF8String(file);
|
|
||||||
CStr::from_ptr(f).to_string_lossy().into_owned()
|
|
||||||
};
|
|
||||||
paths.push(PathBuf::from(path))
|
|
||||||
}
|
|
||||||
|
|
||||||
let window_state = unsafe { get_window_state(this) };
|
let window_state = unsafe { get_window_state(this) };
|
||||||
let position = drag_event_position(&window_state, dragging_info);
|
let position = drag_event_position(&window_state, dragging_info);
|
||||||
if send_new_event(
|
if send_new_event(
|
||||||
&window_state,
|
&window_state,
|
||||||
InputEvent::FileDrop(FileDropEvent::Submit { position, paths }),
|
InputEvent::FileDrop(FileDropEvent::Submit { position }),
|
||||||
) {
|
) {
|
||||||
YES
|
YES
|
||||||
} else {
|
} else {
|
||||||
|
@ -1686,9 +1681,23 @@ extern "C" fn perform_drag_operation(this: &Object, _: Sel, dragging_info: id) -
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn external_paths_from_event(dragging_info: *mut Object) -> DroppedFiles {
|
||||||
|
let mut paths = SmallVec::new();
|
||||||
|
let pasteboard: id = unsafe { msg_send![dragging_info, draggingPasteboard] };
|
||||||
|
let filenames = unsafe { NSPasteboard::propertyListForType(pasteboard, NSFilenamesPboardType) };
|
||||||
|
for file in unsafe { filenames.iter() } {
|
||||||
|
let path = unsafe {
|
||||||
|
let f = NSString::UTF8String(file);
|
||||||
|
CStr::from_ptr(f).to_string_lossy().into_owned()
|
||||||
|
};
|
||||||
|
paths.push(PathBuf::from(path))
|
||||||
|
}
|
||||||
|
DroppedFiles(paths)
|
||||||
|
}
|
||||||
|
|
||||||
extern "C" fn conclude_drag_operation(this: &Object, _: Sel, _: id) {
|
extern "C" fn conclude_drag_operation(this: &Object, _: Sel, _: id) {
|
||||||
let window_state = unsafe { get_window_state(this) };
|
let window_state = unsafe { get_window_state(this) };
|
||||||
send_new_event(&window_state, InputEvent::FileDrop(FileDropEvent::End));
|
send_new_event(&window_state, InputEvent::FileDrop(FileDropEvent::Exited));
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn synthetic_drag(
|
async fn synthetic_drag(
|
||||||
|
@ -1703,7 +1712,7 @@ async fn synthetic_drag(
|
||||||
if lock.synthetic_drag_counter == drag_id {
|
if lock.synthetic_drag_counter == drag_id {
|
||||||
if let Some(mut callback) = lock.event_callback.take() {
|
if let Some(mut callback) = lock.event_callback.take() {
|
||||||
drop(lock);
|
drop(lock);
|
||||||
callback(InputEvent::MouseMoved(event.clone()));
|
callback(InputEvent::MouseMove(event.clone()));
|
||||||
window_state.lock().event_callback = Some(callback);
|
window_state.lock().event_callback = Some(callback);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -1,13 +1,14 @@
|
||||||
use crate::{
|
use crate::{
|
||||||
px, size, Action, AnyBox, AnyView, AppContext, AsyncWindowContext, AvailableSpace, Bounds,
|
px, size, Action, AnyBox, AnyDrag, AnyView, AppContext, AsyncWindowContext, AvailableSpace,
|
||||||
BoxShadow, Context, Corners, DevicePixels, DispatchContext, DisplayId, Edges, Effect, Element,
|
Bounds, BoxShadow, Context, Corners, DevicePixels, DispatchContext, DisplayId, DroppedFiles,
|
||||||
EntityId, EventEmitter, FileDropEvent, FocusEvent, FontId, GlobalElementId, GlyphId, Handle,
|
Edges, Effect, Element, EntityId, EventEmitter, FileDropEvent, FocusEvent, FontId,
|
||||||
Hsla, ImageData, InputEvent, IsZero, KeyListener, KeyMatch, KeyMatcher, Keystroke, LayoutId,
|
GlobalElementId, GlyphId, Handle, Hsla, ImageData, InputEvent, IsZero, KeyListener, KeyMatch,
|
||||||
MainThread, MainThreadOnly, MonochromeSprite, MouseMoveEvent, MouseUpEvent, Path, Pixels,
|
KeyMatcher, Keystroke, LayoutId, MainThread, MainThreadOnly, Modifiers, MonochromeSprite,
|
||||||
PlatformAtlas, PlatformWindow, Point, PolychromeSprite, Quad, Reference, RenderGlyphParams,
|
MouseButton, MouseDownEvent, MouseMoveEvent, MouseUpEvent, Path, Pixels, PlatformAtlas,
|
||||||
RenderImageParams, RenderSvgParams, ScaledPixels, SceneBuilder, Shadow, SharedString, Size,
|
PlatformWindow, Point, PolychromeSprite, Quad, Reference, RenderGlyphParams, RenderImageParams,
|
||||||
Style, Subscription, TaffyLayoutEngine, Task, Underline, UnderlineStyle, WeakHandle,
|
RenderSvgParams, ScaledPixels, SceneBuilder, Shadow, SharedString, Size, Style, Subscription,
|
||||||
WindowOptions, SUBPIXEL_VARIANTS,
|
TaffyLayoutEngine, Task, Underline, UnderlineStyle, WeakHandle, WindowOptions,
|
||||||
|
SUBPIXEL_VARIANTS,
|
||||||
};
|
};
|
||||||
use anyhow::Result;
|
use anyhow::Result;
|
||||||
use collections::HashMap;
|
use collections::HashMap;
|
||||||
|
@ -816,7 +817,9 @@ impl<'a, 'w> WindowContext<'a, 'w> {
|
||||||
cx.with_element_offset(Some(offset), |cx| {
|
cx.with_element_offset(Some(offset), |cx| {
|
||||||
let available_space =
|
let available_space =
|
||||||
size(AvailableSpace::MinContent, AvailableSpace::MinContent);
|
size(AvailableSpace::MinContent, AvailableSpace::MinContent);
|
||||||
draw_any_view(&mut active_drag.drag_handle_view, available_space, cx);
|
if let Some(drag_handle_view) = &mut active_drag.drag_handle_view {
|
||||||
|
draw_any_view(drag_handle_view, available_space, cx);
|
||||||
|
}
|
||||||
cx.active_drag = Some(active_drag);
|
cx.active_drag = Some(active_drag);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -889,27 +892,48 @@ impl<'a, 'w> WindowContext<'a, 'w> {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn dispatch_event(&mut self, event: InputEvent) -> bool {
|
fn dispatch_event(&mut self, event: InputEvent) -> bool {
|
||||||
|
let event = match event {
|
||||||
|
InputEvent::MouseMove(mouse_move) => {
|
||||||
|
self.window.mouse_position = mouse_move.position;
|
||||||
|
InputEvent::MouseMove(mouse_move)
|
||||||
|
}
|
||||||
|
InputEvent::FileDrop(file_drop) => match file_drop {
|
||||||
|
FileDropEvent::Entered { position, files } => {
|
||||||
|
self.active_drag.get_or_insert_with(|| AnyDrag {
|
||||||
|
drag_handle_view: None,
|
||||||
|
cursor_offset: position,
|
||||||
|
state: Box::new(files),
|
||||||
|
state_type: TypeId::of::<DroppedFiles>(),
|
||||||
|
});
|
||||||
|
InputEvent::MouseDown(MouseDownEvent {
|
||||||
|
position,
|
||||||
|
button: MouseButton::Left,
|
||||||
|
click_count: 1,
|
||||||
|
modifiers: Modifiers::default(),
|
||||||
|
})
|
||||||
|
}
|
||||||
|
FileDropEvent::Pending { position } => InputEvent::MouseMove(MouseMoveEvent {
|
||||||
|
position,
|
||||||
|
pressed_button: Some(MouseButton::Left),
|
||||||
|
modifiers: Modifiers::default(),
|
||||||
|
}),
|
||||||
|
FileDropEvent::Submit { position } => InputEvent::MouseUp(MouseUpEvent {
|
||||||
|
button: MouseButton::Left,
|
||||||
|
position,
|
||||||
|
modifiers: Modifiers::default(),
|
||||||
|
click_count: 1,
|
||||||
|
}),
|
||||||
|
FileDropEvent::Exited => InputEvent::MouseUp(MouseUpEvent {
|
||||||
|
button: MouseButton::Left,
|
||||||
|
position: Point::default(),
|
||||||
|
modifiers: Modifiers::default(),
|
||||||
|
click_count: 1,
|
||||||
|
}),
|
||||||
|
},
|
||||||
|
_ => event,
|
||||||
|
};
|
||||||
|
|
||||||
if let Some(any_mouse_event) = event.mouse_event() {
|
if let Some(any_mouse_event) = event.mouse_event() {
|
||||||
if let Some(MouseMoveEvent { position, .. }) = any_mouse_event.downcast_ref() {
|
|
||||||
self.window.mouse_position = *position;
|
|
||||||
}
|
|
||||||
|
|
||||||
match any_mouse_event.downcast_ref() {
|
|
||||||
Some(FileDropEvent::Pending { position }) => {
|
|
||||||
dbg!("FileDropEvent::Pending", position);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
Some(FileDropEvent::Submit { position, paths }) => {
|
|
||||||
dbg!("FileDropEvent::Submit", position, paths);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
Some(FileDropEvent::End) => {
|
|
||||||
self.active_drag = None;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
_ => {}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Handlers may set this to false by calling `stop_propagation`
|
// Handlers may set this to false by calling `stop_propagation`
|
||||||
self.app.propagate_event = true;
|
self.app.propagate_event = true;
|
||||||
self.window.default_prevented = false;
|
self.window.default_prevented = false;
|
||||||
|
|
|
@ -305,7 +305,18 @@ fn box_prefixes() -> Vec<(&'static str, bool, Vec<TokenStream2>, &'static str)>
|
||||||
vec![quote! { padding.right }],
|
vec![quote! { padding.right }],
|
||||||
"Sets the right padding of the element. [Docs](https://tailwindcss.com/docs/padding#add-padding-to-a-single-side)"
|
"Sets the right padding of the element. [Docs](https://tailwindcss.com/docs/padding#add-padding-to-a-single-side)"
|
||||||
),
|
),
|
||||||
("top", true, vec![quote! { inset.top }], "Sets the top value of a positioned element. [Docs](https://tailwindcss.com/docs/top-right-bottom-left)",),
|
(
|
||||||
|
"inset",
|
||||||
|
true,
|
||||||
|
vec![quote! { inset.top }, quote! { inset.right }, quote! { inset.bottom }, quote! { inset.left }],
|
||||||
|
"Sets the top, right, bottom, and left values of a positioned element. [Docs](https://tailwindcss.com/docs/top-right-bottom-left)",
|
||||||
|
),
|
||||||
|
(
|
||||||
|
"top",
|
||||||
|
true,
|
||||||
|
vec![quote! { inset.top }],
|
||||||
|
"Sets the top value of a positioned element. [Docs](https://tailwindcss.com/docs/top-right-bottom-left)",
|
||||||
|
),
|
||||||
(
|
(
|
||||||
"bottom",
|
"bottom",
|
||||||
true,
|
true,
|
||||||
|
|
|
@ -159,8 +159,6 @@ pub struct ThemeColor {
|
||||||
|
|
||||||
impl std::fmt::Debug for ThemeColor {
|
impl std::fmt::Debug for ThemeColor {
|
||||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||||
dbg!("ThemeColor debug");
|
|
||||||
|
|
||||||
f.debug_struct("ThemeColor")
|
f.debug_struct("ThemeColor")
|
||||||
.field("transparent", &self.transparent.to_rgb().to_hex())
|
.field("transparent", &self.transparent.to_rgb().to_hex())
|
||||||
.field(
|
.field(
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
use std::marker::PhantomData;
|
use std::marker::PhantomData;
|
||||||
|
|
||||||
use gpui2::{hsla, AnyElement, ElementId, Hsla, Length, Size};
|
use gpui2::{hsla, red, AnyElement, DroppedFiles, ElementId, Hsla, Length, Size};
|
||||||
use smallvec::SmallVec;
|
use smallvec::SmallVec;
|
||||||
|
|
||||||
use crate::prelude::*;
|
use crate::prelude::*;
|
||||||
|
@ -50,8 +50,19 @@ impl<S: 'static + Send + Sync> Pane<S> {
|
||||||
.bg(self.fill)
|
.bg(self.fill)
|
||||||
.w(self.size.width)
|
.w(self.size.width)
|
||||||
.h(self.size.height)
|
.h(self.size.height)
|
||||||
.overflow_y_scroll()
|
.relative()
|
||||||
.children(self.children.drain(..))
|
.children(cx.stack(0, |_| self.children.drain(..)))
|
||||||
|
.child(cx.stack(1, |_| {
|
||||||
|
// TODO kb! Figure out why we can't we see the red background when we drag a file over this div.
|
||||||
|
div()
|
||||||
|
.id("drag-target")
|
||||||
|
.drag_over::<DroppedFiles>(|d| d.bg(red()))
|
||||||
|
.on_drop(|_, files: DroppedFiles, _| {
|
||||||
|
dbg!("dropped files!", files);
|
||||||
|
})
|
||||||
|
.absolute()
|
||||||
|
.inset_0()
|
||||||
|
}))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -179,8 +179,6 @@ impl Workspace {
|
||||||
|
|
||||||
let color = ThemeColor::new(cx);
|
let color = ThemeColor::new(cx);
|
||||||
|
|
||||||
dbg!(color);
|
|
||||||
|
|
||||||
// HACK: This should happen inside of `debug_toggle_user_settings`, but
|
// HACK: This should happen inside of `debug_toggle_user_settings`, but
|
||||||
// we don't have `cx.global::<FakeSettings>()` in event handlers at the moment.
|
// we don't have `cx.global::<FakeSettings>()` in event handlers at the moment.
|
||||||
// Need to talk with Nathan/Antonio about this.
|
// Need to talk with Nathan/Antonio about this.
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue