WIP
This commit is contained in:
@@ -47,8 +47,8 @@ trait ElementObject<S> {
|
||||
fn layout(&mut self, state: &mut S, cx: &mut ViewContext<S>) -> Result<LayoutId>;
|
||||
fn paint(
|
||||
&mut self,
|
||||
parent_origin: super::Point<Pixels>,
|
||||
state: &mut S,
|
||||
offset: Option<Point<Pixels>>,
|
||||
cx: &mut ViewContext<S>,
|
||||
) -> Result<()>;
|
||||
}
|
||||
@@ -96,8 +96,8 @@ impl<E: Element> ElementObject<E::State> for RenderedElement<E> {
|
||||
|
||||
fn paint(
|
||||
&mut self,
|
||||
parent_origin: Point<Pixels>,
|
||||
state: &mut E::State,
|
||||
offset: Option<Point<Pixels>>,
|
||||
cx: &mut ViewContext<E::State>,
|
||||
) -> Result<()> {
|
||||
self.phase = match std::mem::take(&mut self.phase) {
|
||||
@@ -107,8 +107,8 @@ impl<E: Element> ElementObject<E::State> for RenderedElement<E> {
|
||||
layout_id,
|
||||
mut frame_state,
|
||||
} => {
|
||||
let mut layout = cx.layout(layout_id)?;
|
||||
layout.bounds.origin += parent_origin;
|
||||
let mut layout = cx.layout(layout_id)?.clone();
|
||||
offset.map(|offset| layout.bounds.origin += offset);
|
||||
self.element
|
||||
.paint(layout.clone(), state, &mut frame_state, cx)?;
|
||||
ElementRenderPhase::Painted {
|
||||
@@ -143,11 +143,11 @@ impl<S> AnyElement<S> {
|
||||
|
||||
pub fn paint(
|
||||
&mut self,
|
||||
parent_origin: Point<Pixels>,
|
||||
state: &mut S,
|
||||
offset: Option<Point<Pixels>>,
|
||||
cx: &mut ViewContext<S>,
|
||||
) -> Result<()> {
|
||||
self.0.paint(parent_origin, state, cx)
|
||||
self.0.paint(state, offset, cx)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -215,9 +215,8 @@ impl<S: 'static> Element for View<S> {
|
||||
element: &mut Self::FrameState,
|
||||
cx: &mut ViewContext<Self::State>,
|
||||
) -> Result<()> {
|
||||
self.state.update(cx, |state, cx| {
|
||||
element.paint(layout.bounds.origin, state, cx)
|
||||
})
|
||||
self.state
|
||||
.update(cx, |state, cx| element.paint(state, None, cx))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -251,7 +250,7 @@ impl<S: 'static> ViewObject for View<S> {
|
||||
element
|
||||
.downcast_mut::<AnyElement<S>>()
|
||||
.unwrap()
|
||||
.paint(layout.bounds.origin, state, cx)
|
||||
.paint(state, None, cx)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -67,8 +67,6 @@ impl<S: 'static> Element for Div<S> {
|
||||
style.paint_background(bounds, cx);
|
||||
// self.interaction_handlers().paint(order, bounds, cx);
|
||||
|
||||
let scrolled_origin = bounds.origin - self.scroll_offset(&style.overflow);
|
||||
|
||||
// // TODO: Support only one dimension being hidden
|
||||
// let mut pop_layer = false;
|
||||
// if style.overflow.y != Overflow::Visible || style.overflow.x != Overflow::Visible {
|
||||
@@ -76,8 +74,9 @@ impl<S: 'static> Element for Div<S> {
|
||||
// pop_layer = true;
|
||||
// }
|
||||
|
||||
let scroll_offset = self.scroll_offset(&style.overflow);
|
||||
for child in &mut self.children {
|
||||
child.paint(scrolled_origin, state, cx)?;
|
||||
child.paint(state, Some(scroll_offset), cx)?;
|
||||
}
|
||||
|
||||
// if pop_layer {
|
||||
|
||||
@@ -2,7 +2,7 @@ use bytemuck::{Pod, Zeroable};
|
||||
use core::fmt::Debug;
|
||||
use derive_more::{Add, AddAssign, Div, Mul, Sub, SubAssign};
|
||||
use refineable::Refineable;
|
||||
use std::ops::{Add, Mul, Sub, SubAssign};
|
||||
use std::ops::{Add, AddAssign, Mul, Sub, SubAssign};
|
||||
|
||||
#[derive(
|
||||
Refineable, Default, Add, AddAssign, Sub, SubAssign, Mul, Div, Copy, Debug, PartialEq, Eq, Hash,
|
||||
@@ -38,6 +38,13 @@ impl<T: Clone + Debug + Sub<Output = T>> SubAssign<Size<T>> for Point<T> {
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: Clone + Debug + Add<Output = T> + Copy> AddAssign<T> for Point<T> {
|
||||
fn add_assign(&mut self, rhs: T) {
|
||||
self.x = self.x.clone() + rhs;
|
||||
self.y = self.y.clone() + rhs;
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: Clone + Debug + std::cmp::PartialOrd> Point<T> {
|
||||
pub fn max(&self, other: &Self) -> Self {
|
||||
Point {
|
||||
|
||||
@@ -15,13 +15,14 @@ mod text_system;
|
||||
mod util;
|
||||
mod window;
|
||||
|
||||
use anyhow::Result;
|
||||
pub use anyhow::Result;
|
||||
pub use app::*;
|
||||
pub use color::*;
|
||||
pub use element::*;
|
||||
pub use elements::*;
|
||||
pub use executor::*;
|
||||
pub use geometry::*;
|
||||
pub use gpui3_macros::*;
|
||||
pub use platform::*;
|
||||
pub use refineable::*;
|
||||
pub use scene::*;
|
||||
|
||||
@@ -996,7 +996,7 @@ extern "C" fn open_urls(this: &mut Object, _: Sel, _: id, urls: id) {
|
||||
}
|
||||
}
|
||||
|
||||
extern "C" fn handle_menu_item(this: &mut Object, _: Sel, item: id) {
|
||||
extern "C" fn handle_menu_item(__this: &mut Object, _: Sel, __item: id) {
|
||||
todo!()
|
||||
// unsafe {
|
||||
// let platform = get_foreground_platform(this);
|
||||
@@ -1012,7 +1012,7 @@ extern "C" fn handle_menu_item(this: &mut Object, _: Sel, item: id) {
|
||||
// }
|
||||
}
|
||||
|
||||
extern "C" fn validate_menu_item(this: &mut Object, _: Sel, item: id) -> bool {
|
||||
extern "C" fn validate_menu_item(__this: &mut Object, _: Sel, __item: id) -> bool {
|
||||
todo!()
|
||||
// unsafe {
|
||||
// let mut result = false;
|
||||
|
||||
@@ -1378,7 +1378,7 @@ extern "C" fn set_frame_size(this: &Object, _: Sel, size: NSSize) {
|
||||
};
|
||||
}
|
||||
|
||||
extern "C" fn display_layer(this: &Object, _: Sel, _: id) {
|
||||
extern "C" fn display_layer(_this: &Object, _: Sel, _: id) {
|
||||
// unsafe {
|
||||
// let window_state = get_window_state(this);
|
||||
// let mut window_state = window_state.as_ref().borrow_mut();
|
||||
|
||||
@@ -17,7 +17,7 @@ impl Platform for TestPlatform {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn run(&self, on_finish_launching: Box<dyn FnOnce()>) {
|
||||
fn run(&self, _on_finish_launching: Box<dyn FnOnce()>) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ impl Platform for TestPlatform {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn activate(&self, ignoring_other_apps: bool) {
|
||||
fn activate(&self, _ignoring_other_apps: bool) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
@@ -49,7 +49,7 @@ impl Platform for TestPlatform {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn screen_by_id(&self, id: uuid::Uuid) -> Option<std::rc::Rc<dyn crate::PlatformScreen>> {
|
||||
fn screen_by_id(&self, _id: uuid::Uuid) -> Option<std::rc::Rc<dyn crate::PlatformScreen>> {
|
||||
todo!()
|
||||
}
|
||||
|
||||
@@ -59,55 +59,55 @@ impl Platform for TestPlatform {
|
||||
|
||||
fn open_window(
|
||||
&self,
|
||||
handle: crate::AnyWindowHandle,
|
||||
options: crate::WindowOptions,
|
||||
_handle: crate::AnyWindowHandle,
|
||||
_options: crate::WindowOptions,
|
||||
) -> Box<dyn crate::PlatformWindow> {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn open_url(&self, url: &str) {
|
||||
fn open_url(&self, _url: &str) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn on_open_urls(&self, callback: Box<dyn FnMut(Vec<String>)>) {
|
||||
fn on_open_urls(&self, _callback: Box<dyn FnMut(Vec<String>)>) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn prompt_for_paths(
|
||||
&self,
|
||||
options: crate::PathPromptOptions,
|
||||
_options: crate::PathPromptOptions,
|
||||
) -> futures::channel::oneshot::Receiver<Option<Vec<std::path::PathBuf>>> {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn prompt_for_new_path(
|
||||
&self,
|
||||
directory: &std::path::Path,
|
||||
_directory: &std::path::Path,
|
||||
) -> futures::channel::oneshot::Receiver<Option<std::path::PathBuf>> {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn reveal_path(&self, path: &std::path::Path) {
|
||||
fn reveal_path(&self, _path: &std::path::Path) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn on_become_active(&self, callback: Box<dyn FnMut()>) {
|
||||
fn on_become_active(&self, _callback: Box<dyn FnMut()>) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn on_resign_active(&self, callback: Box<dyn FnMut()>) {
|
||||
fn on_resign_active(&self, _callback: Box<dyn FnMut()>) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn on_quit(&self, callback: Box<dyn FnMut()>) {
|
||||
fn on_quit(&self, _callback: Box<dyn FnMut()>) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn on_reopen(&self, callback: Box<dyn FnMut()>) {
|
||||
fn on_reopen(&self, _callback: Box<dyn FnMut()>) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn on_event(&self, callback: Box<dyn FnMut(crate::Event) -> bool>) {
|
||||
fn on_event(&self, _callback: Box<dyn FnMut(crate::Event) -> bool>) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
@@ -131,11 +131,11 @@ impl Platform for TestPlatform {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn path_for_auxiliary_executable(&self, name: &str) -> anyhow::Result<std::path::PathBuf> {
|
||||
fn path_for_auxiliary_executable(&self, _name: &str) -> anyhow::Result<std::path::PathBuf> {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn set_cursor_style(&self, style: crate::CursorStyle) {
|
||||
fn set_cursor_style(&self, _style: crate::CursorStyle) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
@@ -143,7 +143,7 @@ impl Platform for TestPlatform {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn write_to_clipboard(&self, item: crate::ClipboardItem) {
|
||||
fn write_to_clipboard(&self, _item: crate::ClipboardItem) {
|
||||
todo!()
|
||||
}
|
||||
|
||||
@@ -151,15 +151,20 @@ impl Platform for TestPlatform {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn write_credentials(&self, url: &str, username: &str, password: &[u8]) -> anyhow::Result<()> {
|
||||
fn write_credentials(
|
||||
&self,
|
||||
_url: &str,
|
||||
_username: &str,
|
||||
_password: &[u8],
|
||||
) -> anyhow::Result<()> {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn read_credentials(&self, url: &str) -> anyhow::Result<Option<(String, Vec<u8>)>> {
|
||||
fn read_credentials(&self, _url: &str) -> anyhow::Result<Option<(String, Vec<u8>)>> {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn delete_credentials(&self, url: &str) -> anyhow::Result<()> {
|
||||
fn delete_credentials(&self, _url: &str) -> anyhow::Result<()> {
|
||||
todo!()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
use crate::{
|
||||
self as gpui2, relative, rems, AlignItems, Display, Fill, FlexDirection, Hsla, JustifyContent,
|
||||
self as gpui3, relative, rems, AlignItems, Display, Fill, FlexDirection, Hsla, JustifyContent,
|
||||
Length, Position, SharedString, Style, Styled,
|
||||
};
|
||||
|
||||
|
||||
+68
-17
@@ -2,29 +2,28 @@ use super::{
|
||||
AbsoluteLength, Bounds, DefiniteLength, Edges, Layout, Length, Pixels, Point, Result, Size,
|
||||
Style,
|
||||
};
|
||||
use collections::HashMap;
|
||||
use std::fmt::Debug;
|
||||
pub use taffy::tree::NodeId as LayoutId;
|
||||
use taffy::{
|
||||
geometry::Size as TaffySize,
|
||||
style::AvailableSpace as TaffyAvailableSpace,
|
||||
tree::{Measurable, MeasureFunc},
|
||||
tree::{Measurable, MeasureFunc, NodeId},
|
||||
Taffy,
|
||||
};
|
||||
pub struct TaffyLayoutEngine(Taffy);
|
||||
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
pub enum AvailableSpace {
|
||||
/// The amount of space available is the specified number of pixels
|
||||
Definite(Pixels),
|
||||
/// The amount of space available is indefinite and the node should be laid out under a min-content constraint
|
||||
MinContent,
|
||||
/// The amount of space available is indefinite and the node should be laid out under a max-content constraint
|
||||
MaxContent,
|
||||
pub struct TaffyLayoutEngine {
|
||||
taffy: Taffy,
|
||||
children_to_parents: HashMap<LayoutId, LayoutId>,
|
||||
absolute_layouts: HashMap<LayoutId, Layout>,
|
||||
}
|
||||
|
||||
impl TaffyLayoutEngine {
|
||||
pub fn new() -> Self {
|
||||
TaffyLayoutEngine(Taffy::new())
|
||||
TaffyLayoutEngine {
|
||||
taffy: Taffy::new(),
|
||||
children_to_parents: HashMap::default(),
|
||||
absolute_layouts: HashMap::default(),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn request_layout(
|
||||
@@ -35,9 +34,17 @@ impl TaffyLayoutEngine {
|
||||
) -> Result<LayoutId> {
|
||||
let style = style.to_taffy(rem_size);
|
||||
if children.is_empty() {
|
||||
Ok(self.0.new_leaf(style)?)
|
||||
Ok(self.taffy.new_leaf(style)?.into())
|
||||
} else {
|
||||
Ok(self.0.new_with_children(style, children)?)
|
||||
let parent_id = self
|
||||
.taffy
|
||||
// This is safe because LayoutId is repr(transparent) to taffy::tree::NodeId.
|
||||
.new_with_children(style, unsafe { std::mem::transmute(children) })?
|
||||
.into();
|
||||
for child_id in children {
|
||||
self.children_to_parents.insert(*child_id, parent_id);
|
||||
}
|
||||
Ok(parent_id)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -54,15 +61,59 @@ impl TaffyLayoutEngine {
|
||||
|
||||
let measurable = Box::new(Measureable(measure)) as Box<dyn Measurable>;
|
||||
Ok(self
|
||||
.0
|
||||
.new_leaf_with_measure(style, MeasureFunc::Boxed(measurable))?)
|
||||
.taffy
|
||||
.new_leaf_with_measure(style, MeasureFunc::Boxed(measurable))?
|
||||
.into())
|
||||
}
|
||||
|
||||
pub fn layout(&mut self, id: LayoutId) -> Result<Layout> {
|
||||
Ok(self.0.layout(id).map(Into::into)?)
|
||||
if let Some(layout) = self.absolute_layouts.get(&id).cloned() {
|
||||
return Ok(layout);
|
||||
}
|
||||
|
||||
let mut relative_layout: Layout = self.taffy.layout(id.into()).map(Into::into)?;
|
||||
if let Some(parent_id) = self.children_to_parents.get(&id).copied() {
|
||||
let parent_layout = self.layout(parent_id)?;
|
||||
relative_layout.bounds.origin += parent_layout.bounds.origin;
|
||||
}
|
||||
self.absolute_layouts.insert(id, relative_layout.clone());
|
||||
|
||||
Ok(relative_layout)
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Eq, PartialEq, Debug)]
|
||||
#[repr(transparent)]
|
||||
pub struct LayoutId(NodeId);
|
||||
|
||||
impl std::hash::Hash for LayoutId {
|
||||
fn hash<H: std::hash::Hasher>(&self, state: &mut H) {
|
||||
u64::from(self.0).hash(state);
|
||||
}
|
||||
}
|
||||
|
||||
impl From<NodeId> for LayoutId {
|
||||
fn from(node_id: NodeId) -> Self {
|
||||
Self(node_id)
|
||||
}
|
||||
}
|
||||
|
||||
impl From<LayoutId> for NodeId {
|
||||
fn from(layout_id: LayoutId) -> NodeId {
|
||||
layout_id.0
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
pub enum AvailableSpace {
|
||||
/// The amount of space available is the specified number of pixels
|
||||
Definite(Pixels),
|
||||
/// The amount of space available is indefinite and the node should be laid out under a min-content constraint
|
||||
MinContent,
|
||||
/// The amount of space available is indefinite and the node should be laid out under a max-content constraint
|
||||
MaxContent,
|
||||
}
|
||||
|
||||
struct Measureable<F>(F);
|
||||
|
||||
impl<F> taffy::tree::Measurable for Measureable<F>
|
||||
|
||||
@@ -1,92 +1,49 @@
|
||||
use proc_macro::TokenStream;
|
||||
use proc_macro2::Ident;
|
||||
use quote::quote;
|
||||
use syn::{parse_macro_input, parse_quote, DeriveInput, GenericParam, Generics};
|
||||
|
||||
use crate::derive_into_element::impl_into_element;
|
||||
use syn::{parse_macro_input, parse_quote, DeriveInput, GenericParam};
|
||||
|
||||
pub fn derive_element(input: TokenStream) -> TokenStream {
|
||||
let ast = parse_macro_input!(input as DeriveInput);
|
||||
let type_name = ast.ident;
|
||||
let placeholder_view_generics: Generics = parse_quote! { <V: 'static> };
|
||||
let mut state_type: Option<Ident> = None;
|
||||
|
||||
let (impl_generics, type_generics, where_clause, view_type_name, lifetimes) =
|
||||
if let Some(first_type_param) = ast.generics.params.iter().find_map(|param| {
|
||||
if let GenericParam::Type(type_param) = param {
|
||||
Some(type_param.ident.clone())
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}) {
|
||||
let mut lifetimes = vec![];
|
||||
for param in ast.generics.params.iter() {
|
||||
if let GenericParam::Lifetime(lifetime_def) = param {
|
||||
lifetimes.push(lifetime_def.lifetime.clone());
|
||||
}
|
||||
}
|
||||
let generics = ast.generics.split_for_impl();
|
||||
(
|
||||
generics.0,
|
||||
Some(generics.1),
|
||||
generics.2,
|
||||
first_type_param,
|
||||
lifetimes,
|
||||
)
|
||||
} else {
|
||||
let generics = placeholder_view_generics.split_for_impl();
|
||||
let placeholder_view_type_name: Ident = parse_quote! { V };
|
||||
(
|
||||
generics.0,
|
||||
None,
|
||||
generics.2,
|
||||
placeholder_view_type_name,
|
||||
vec![],
|
||||
)
|
||||
};
|
||||
for param in ast.generics.params.iter() {
|
||||
if let GenericParam::Type(type_param) = param {
|
||||
state_type = Some(type_param.ident.clone())
|
||||
}
|
||||
}
|
||||
|
||||
let lifetimes = if !lifetimes.is_empty() {
|
||||
quote! { <#(#lifetimes),*> }
|
||||
} else {
|
||||
quote! {}
|
||||
};
|
||||
|
||||
let impl_into_element = impl_into_element(
|
||||
&impl_generics,
|
||||
&view_type_name,
|
||||
&type_name,
|
||||
&type_generics,
|
||||
&where_clause,
|
||||
);
|
||||
let state_type_name = state_type.unwrap_or_else(|| parse_quote! { () });
|
||||
let (impl_generics, ty_generics, where_clause) = ast.generics.split_for_impl();
|
||||
|
||||
let gen = quote! {
|
||||
impl #impl_generics gpui2::element::Element<#view_type_name> for #type_name #type_generics
|
||||
impl #impl_generics gpui3::Element for #type_name #ty_generics
|
||||
#where_clause
|
||||
{
|
||||
type PaintState = gpui2::element::AnyElement<#view_type_name #lifetimes>;
|
||||
type State = #state_type_name;
|
||||
type FrameState = gpui3::AnyElement<#state_type_name>;
|
||||
|
||||
fn layout(
|
||||
&mut self,
|
||||
view: &mut V,
|
||||
cx: &mut gpui2::ViewContext<V>,
|
||||
) -> anyhow::Result<(gpui2::element::LayoutId, Self::PaintState)> {
|
||||
let mut rendered_element = self.render(view, cx).into_element().into_any();
|
||||
let layout_id = rendered_element.layout(view, cx)?;
|
||||
state: &mut #state_type_name,
|
||||
cx: &mut gpui3::ViewContext<V>,
|
||||
) -> anyhow::Result<(gpui3::LayoutId, Self::FrameState)> {
|
||||
let mut rendered_element = self.render(state, cx).into_element().into_any();
|
||||
let layout_id = rendered_element.layout(state, cx)?;
|
||||
Ok((layout_id, rendered_element))
|
||||
}
|
||||
|
||||
fn paint(
|
||||
&mut self,
|
||||
view: &mut V,
|
||||
parent_origin: gpui2::Vector2F,
|
||||
_: &gpui2::element::Layout,
|
||||
rendered_element: &mut Self::PaintState,
|
||||
cx: &mut gpui2::ViewContext<V>,
|
||||
layout: &gpui3::Layout,
|
||||
state: &mut #state_type_name,
|
||||
rendered_element: &mut Self::FrameState,
|
||||
cx: &mut gpui3::ViewContext<V>,
|
||||
) {
|
||||
rendered_element.paint(view, parent_origin, cx);
|
||||
rendered_element.paint(layout.origin, state, cx);
|
||||
}
|
||||
}
|
||||
|
||||
#impl_into_element
|
||||
};
|
||||
|
||||
gen.into()
|
||||
|
||||
@@ -1,69 +0,0 @@
|
||||
use proc_macro::TokenStream;
|
||||
use quote::quote;
|
||||
use syn::{
|
||||
parse_macro_input, parse_quote, DeriveInput, GenericParam, Generics, Ident, WhereClause,
|
||||
};
|
||||
|
||||
pub fn derive_into_element(input: TokenStream) -> TokenStream {
|
||||
let ast = parse_macro_input!(input as DeriveInput);
|
||||
let type_name = ast.ident;
|
||||
|
||||
let placeholder_view_generics: Generics = parse_quote! { <V: 'static> };
|
||||
let placeholder_view_type_name: Ident = parse_quote! { V };
|
||||
let view_type_name: Ident;
|
||||
let impl_generics: syn::ImplGenerics<'_>;
|
||||
let type_generics: Option<syn::TypeGenerics<'_>>;
|
||||
let where_clause: Option<&'_ WhereClause>;
|
||||
|
||||
match ast.generics.params.iter().find_map(|param| {
|
||||
if let GenericParam::Type(type_param) = param {
|
||||
Some(type_param.ident.clone())
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}) {
|
||||
Some(type_name) => {
|
||||
view_type_name = type_name;
|
||||
let generics = ast.generics.split_for_impl();
|
||||
impl_generics = generics.0;
|
||||
type_generics = Some(generics.1);
|
||||
where_clause = generics.2;
|
||||
}
|
||||
_ => {
|
||||
view_type_name = placeholder_view_type_name;
|
||||
let generics = placeholder_view_generics.split_for_impl();
|
||||
impl_generics = generics.0;
|
||||
type_generics = None;
|
||||
where_clause = generics.2;
|
||||
}
|
||||
}
|
||||
|
||||
impl_into_element(
|
||||
&impl_generics,
|
||||
&view_type_name,
|
||||
&type_name,
|
||||
&type_generics,
|
||||
&where_clause,
|
||||
)
|
||||
.into()
|
||||
}
|
||||
|
||||
pub fn impl_into_element(
|
||||
impl_generics: &syn::ImplGenerics<'_>,
|
||||
view_type_name: &Ident,
|
||||
type_name: &Ident,
|
||||
type_generics: &Option<syn::TypeGenerics<'_>>,
|
||||
where_clause: &Option<&WhereClause>,
|
||||
) -> proc_macro2::TokenStream {
|
||||
quote! {
|
||||
impl #impl_generics gpui2::element::IntoElement<#view_type_name> for #type_name #type_generics
|
||||
#where_clause
|
||||
{
|
||||
type Element = Self;
|
||||
|
||||
fn into_element(self) -> Self {
|
||||
self
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,7 +1,6 @@
|
||||
use proc_macro::TokenStream;
|
||||
|
||||
mod derive_element;
|
||||
mod derive_into_element;
|
||||
mod style_helpers;
|
||||
|
||||
#[proc_macro]
|
||||
@@ -13,8 +12,3 @@ pub fn style_helpers(args: TokenStream) -> TokenStream {
|
||||
pub fn derive_element(input: TokenStream) -> TokenStream {
|
||||
derive_element::derive_element(input)
|
||||
}
|
||||
|
||||
#[proc_macro_derive(IntoElement, attributes(element_crate))]
|
||||
pub fn derive_into_element(input: TokenStream) -> TokenStream {
|
||||
derive_into_element::derive_into_element(input)
|
||||
}
|
||||
|
||||
@@ -17,15 +17,9 @@ impl Parse for StyleableMacroInput {
|
||||
pub fn style_helpers(input: TokenStream) -> TokenStream {
|
||||
let _ = parse_macro_input!(input as StyleableMacroInput);
|
||||
let methods = generate_methods();
|
||||
|
||||
for method in &methods {
|
||||
println!("method: {}", method);
|
||||
}
|
||||
|
||||
let output = quote! {
|
||||
#(#methods)*
|
||||
};
|
||||
|
||||
output.into()
|
||||
}
|
||||
|
||||
@@ -74,7 +68,7 @@ fn generate_method(
|
||||
.iter()
|
||||
.map(|field_tokens| {
|
||||
quote! {
|
||||
style.#field_tokens = Some(gpui2::#length_tokens.into());
|
||||
style.#field_tokens = Some(gpui3::#length_tokens.into());
|
||||
}
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
use gpui3::{Element, Hsla, Layout, LayoutId, ViewContext, WindowContext};
|
||||
use gpui3::{Element, Hsla, Layout, LayoutId, Result, ViewContext, WindowContext};
|
||||
use serde::{de::Visitor, Deserialize, Deserializer};
|
||||
use std::{collections::HashMap, fmt};
|
||||
|
||||
@@ -156,13 +156,15 @@ impl<E: Element> Element for Themed<E> {
|
||||
state: &mut Self::State,
|
||||
frame_state: &mut Self::FrameState,
|
||||
cx: &mut ViewContext<Self::State>,
|
||||
) where
|
||||
) -> Result<()>
|
||||
where
|
||||
Self: Sized,
|
||||
{
|
||||
// todo!
|
||||
// cx.push_theme(self.theme.clone());
|
||||
self.child.paint(layout, state, frame_state, cx);
|
||||
// cx.pop_theme();
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
use crate::{collab_panel::collab_panel, theme::theme};
|
||||
use gpui3::{div, img, svg, Element, ParentElement, ScrollState, StyleHelpers, ViewContext};
|
||||
|
||||
#[derive(Default)]
|
||||
#[derive(Element, Default)]
|
||||
struct WorkspaceElement {
|
||||
left_scroll_state: ScrollState,
|
||||
right_scroll_state: ScrollState,
|
||||
|
||||
Reference in New Issue
Block a user