feat: namespaced attributes
this commit adds namespaced attributes. This lets us support attribute groups, and thus, inline styles. This namespaced attribute stuff is only available for styles at the moment, though it theoretically could be enabled for any other attributes.
This commit is contained in:
1 parent
a4bf3d9862
commit
22e659c2bd
18 files changed
+612
-3129
No files matched your search
+63
-63
@@ -1326,69 +1326,69 @@ mod tests {
|
||||
use crate::util::DebugDom;
|
||||
use dioxus_core_macro::*;
|
||||
|
||||
#[test]
|
||||
fn test_child_iterator() {
|
||||
static App: FC<()> = |cx| {
|
||||
cx.render(rsx! {
|
||||
Fragment {
|
||||
div {}
|
||||
h1 {}
|
||||
h2 {}
|
||||
h3 {}
|
||||
Fragment {
|
||||
"internal node"
|
||||
div {
|
||||
"baller text shouldn't show up"
|
||||
}
|
||||
p {
|
||||
// #[test]
|
||||
// fn test_child_iterator() {
|
||||
// static App: FC<()> = |cx| {
|
||||
// cx.render(rsx! {
|
||||
// Fragment {
|
||||
// div {}
|
||||
// h1 {}
|
||||
// h2 {}
|
||||
// h3 {}
|
||||
// Fragment {
|
||||
// "internal node"
|
||||
// div {
|
||||
// "baller text shouldn't show up"
|
||||
// }
|
||||
// p {
|
||||
|
||||
}
|
||||
Fragment {
|
||||
Fragment {
|
||||
"wow you really like framgents"
|
||||
Fragment {
|
||||
"why are you like this"
|
||||
Fragment {
|
||||
"just stop now please"
|
||||
Fragment {
|
||||
"this hurts"
|
||||
Fragment {
|
||||
"who needs this many fragments?????"
|
||||
Fragment {
|
||||
"just... fine..."
|
||||
Fragment {
|
||||
"no"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
"my text node 1"
|
||||
"my text node 2"
|
||||
"my text node 3"
|
||||
"my text node 4"
|
||||
}
|
||||
})
|
||||
};
|
||||
let mut dom = VirtualDom::new(App);
|
||||
let mut renderer = DebugDom::new();
|
||||
dom.rebuild(&mut renderer).unwrap();
|
||||
let starter = dom.base_scope().root();
|
||||
let ite = RealChildIterator::new(starter, &dom.components);
|
||||
for child in ite {
|
||||
match child {
|
||||
VNode::Element(el) => println!("Found: Element {}", el.tag_name),
|
||||
VNode::Text(t) => println!("Found: Text {:?}", t.text),
|
||||
// }
|
||||
// Fragment {
|
||||
// Fragment {
|
||||
// "wow you really like framgents"
|
||||
// Fragment {
|
||||
// "why are you like this"
|
||||
// Fragment {
|
||||
// "just stop now please"
|
||||
// Fragment {
|
||||
// "this hurts"
|
||||
// Fragment {
|
||||
// "who needs this many fragments?????"
|
||||
// Fragment {
|
||||
// "just... fine..."
|
||||
// Fragment {
|
||||
// "no"
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// "my text node 1"
|
||||
// "my text node 2"
|
||||
// "my text node 3"
|
||||
// "my text node 4"
|
||||
// }
|
||||
// })
|
||||
// };
|
||||
// let mut dom = VirtualDom::new(App);
|
||||
// let mut renderer = DebugDom::new();
|
||||
// dom.rebuild(&mut renderer).unwrap();
|
||||
// let starter = dom.base_scope().root();
|
||||
// let ite = RealChildIterator::new(starter, &dom.components);
|
||||
// for child in ite {
|
||||
// match child {
|
||||
// VNode::Element(el) => println!("Found: Element {}", el.tag_name),
|
||||
// VNode::Text(t) => println!("Found: Text {:?}", t.text),
|
||||
|
||||
// These would represent failing cases.
|
||||
VNode::Fragment(_) => panic!("Found: Fragment"),
|
||||
VNode::Suspended { real } => panic!("Found: Suspended"),
|
||||
VNode::Component(_) => panic!("Found: Component"),
|
||||
}
|
||||
}
|
||||
}
|
||||
// // These would represent failing cases.
|
||||
// VNode::Fragment(_) => panic!("Found: Fragment"),
|
||||
// VNode::Suspended { real } => panic!("Found: Suspended"),
|
||||
// VNode::Component(_) => panic!("Found: Component"),
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
}
|
||||
+141
-28
@@ -123,10 +123,25 @@ pub mod on {
|
||||
use super::VirtualEvent;
|
||||
|
||||
macro_rules! event_directory {
|
||||
( $( $eventdata:ident($wrapper:ident): [ $( $name:ident )* ]; )* ) => {
|
||||
( $(
|
||||
$(
|
||||
#[$attr:meta]
|
||||
)*
|
||||
$eventdata:ident($wrapper:ident): [
|
||||
$(
|
||||
#[$method_attr:meta]
|
||||
)*
|
||||
$( $name:ident )*
|
||||
];
|
||||
)* ) => {
|
||||
$(
|
||||
$(#[$attr])*
|
||||
#[derive(Debug)]
|
||||
pub struct $wrapper(pub Rc<dyn $eventdata>);
|
||||
|
||||
// todo: derefing to the event is fine (and easy) but breaks some IDE stuff like (go to source)
|
||||
// going to source in fact takes you to the source of Rc which is... less than useful
|
||||
// Either we ask for this to be changed in Rust-analyzer or manually impkement the trait
|
||||
impl Deref for $wrapper {
|
||||
type Target = Rc<dyn $eventdata>;
|
||||
fn deref(&self) -> &Self::Target {
|
||||
@@ -134,6 +149,7 @@ pub mod on {
|
||||
}
|
||||
}
|
||||
|
||||
$(#[$method_attr])*
|
||||
$(
|
||||
pub fn $name<'a>(
|
||||
c: &'_ NodeFactory<'a>,
|
||||
@@ -155,17 +171,112 @@ pub mod on {
|
||||
};
|
||||
}
|
||||
|
||||
// The Dioxus Synthetic event system
|
||||
//
|
||||
//
|
||||
//
|
||||
//
|
||||
//
|
||||
//
|
||||
//
|
||||
//
|
||||
event_directory! {
|
||||
ClipboardEventInner(ClipboardEvent): [copy cut paste];
|
||||
CompositionEventInner(CompositionEvent): [compositionend compositionstart compositionupdate];
|
||||
KeyboardEventInner(KeyboardEvent): [keydown keypress keyup];
|
||||
FocusEventInner(FocusEvent): [focus blur];
|
||||
FormEventInner(FormEvent): [change input invalid reset submit];
|
||||
MouseEventInner(MouseEvent): [
|
||||
click contextmenu doubleclick drag dragend dragenter dragexit
|
||||
dragleave dragover dragstart drop mousedown mouseenter mouseleave
|
||||
mousemove mouseout mouseover mouseup
|
||||
|
||||
|
||||
|
||||
|
||||
ClipboardEventInner(ClipboardEvent): [
|
||||
/// Called when "copy"
|
||||
oncopy
|
||||
oncut
|
||||
onpaste
|
||||
];
|
||||
CompositionEventInner(CompositionEvent): [
|
||||
oncompositionend
|
||||
oncompositionstart
|
||||
oncompositionupdate
|
||||
];
|
||||
KeyboardEventInner(KeyboardEvent): [
|
||||
onkeydown
|
||||
onkeypress
|
||||
onkeyup
|
||||
];
|
||||
FocusEventInner(FocusEvent): [
|
||||
onfocus
|
||||
onblur
|
||||
];
|
||||
FormEventInner(FormEvent): [
|
||||
onchange
|
||||
oninput
|
||||
oninvalid
|
||||
onreset
|
||||
onsubmit
|
||||
];
|
||||
|
||||
|
||||
/// A synthetic event that wraps a web-style [`MouseEvent`](https://developer.mozilla.org/en-US/docs/Web/API/MouseEvent)
|
||||
///
|
||||
///
|
||||
/// The MouseEvent interface represents events that occur due to the user interacting with a pointing device (such as a mouse).
|
||||
///
|
||||
/// ## Trait implementation:
|
||||
/// ```rust
|
||||
/// fn alt_key(&self) -> bool;
|
||||
/// fn button(&self) -> i16;
|
||||
/// fn buttons(&self) -> u16;
|
||||
/// fn client_x(&self) -> i32;
|
||||
/// fn client_y(&self) -> i32;
|
||||
/// fn ctrl_key(&self) -> bool;
|
||||
/// fn meta_key(&self) -> bool;
|
||||
/// fn page_x(&self) -> i32;
|
||||
/// fn page_y(&self) -> i32;
|
||||
/// fn screen_x(&self) -> i32;
|
||||
/// fn screen_y(&self) -> i32;
|
||||
/// fn shift_key(&self) -> bool;
|
||||
/// fn get_modifier_state(&self, key_code: &str) -> bool;
|
||||
/// ```
|
||||
///
|
||||
/// ## Event Handlers
|
||||
/// - click
|
||||
/// - contextmenu
|
||||
/// - doubleclick
|
||||
/// - drag
|
||||
/// - dragend
|
||||
/// - dragenter
|
||||
/// - dragexit
|
||||
/// - dragleave
|
||||
/// - dragover
|
||||
/// - dragstart
|
||||
/// - drop
|
||||
/// - mousedown
|
||||
/// - mouseenter
|
||||
/// - mouseleave
|
||||
/// - mousemove
|
||||
/// - mouseout
|
||||
/// - mouseover
|
||||
/// - mouseup
|
||||
MouseEventInner(MouseEvent): [
|
||||
/// Onclick!
|
||||
onclick
|
||||
oncontextmenu
|
||||
ondoubleclick
|
||||
ondrag
|
||||
ondragend
|
||||
ondragenter
|
||||
ondragexit
|
||||
ondragleave
|
||||
ondragover
|
||||
ondragstart
|
||||
ondrop
|
||||
onmousedown
|
||||
onmouseenter
|
||||
onmouseleave
|
||||
onmousemove
|
||||
onmouseout
|
||||
onmouseover
|
||||
onmouseup
|
||||
];
|
||||
|
||||
PointerEventInner(PointerEvent): [
|
||||
pointerdown pointermove pointerup pointercancel gotpointercapture
|
||||
lostpointercapture pointerenter pointerleave pointerover pointerout
|
||||
@@ -293,6 +404,8 @@ pub mod on {
|
||||
fn alt_key(&self) -> bool;
|
||||
fn button(&self) -> i16;
|
||||
fn buttons(&self) -> u16;
|
||||
|
||||
/// Get the X coordinate of the mouse relative to the window
|
||||
fn client_x(&self) -> i32;
|
||||
fn client_y(&self) -> i32;
|
||||
fn ctrl_key(&self) -> bool;
|
||||
@@ -597,25 +710,25 @@ pub mod on {
|
||||
}
|
||||
}
|
||||
|
||||
mod tests {
|
||||
// mod tests {
|
||||
|
||||
use std::rc::Rc;
|
||||
// use std::rc::Rc;
|
||||
|
||||
use crate as dioxus;
|
||||
use crate::events::on::MouseEvent;
|
||||
use crate::prelude::*;
|
||||
// use crate as dioxus;
|
||||
// use crate::events::on::MouseEvent;
|
||||
// use crate::prelude::*;
|
||||
|
||||
fn autocomplete() {
|
||||
// let v = move |evt| {
|
||||
// let r = evt.alt_key();
|
||||
// };
|
||||
// fn autocomplete() {
|
||||
// // let v = move |evt| {
|
||||
// // let r = evt.alt_key();
|
||||
// // };
|
||||
|
||||
let g = rsx! {
|
||||
button {
|
||||
onclick: move |evt| {
|
||||
let r = evt.alt_key();
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
// let g = rsx! {
|
||||
// button {
|
||||
// onclick: move |evt| {
|
||||
// let r = evt.alt_key();
|
||||
// }
|
||||
// }
|
||||
// };
|
||||
// }
|
||||
// }
|
||||
@@ -13,6 +13,7 @@ pub mod serialize;
|
||||
|
||||
pub mod arena;
|
||||
pub mod component;
|
||||
pub mod styles;
|
||||
pub mod util; // Logic for extending FC
|
||||
|
||||
pub mod debug_renderer;
|
||||
@@ -54,6 +55,7 @@ pub(crate) mod innerlude {
|
||||
pub mod prelude {
|
||||
pub use crate::component::{fc_to_builder, Fragment, Properties};
|
||||
use crate::nodes;
|
||||
pub use crate::styles::{AsAttr, StyleBuilder};
|
||||
pub use crate::virtual_dom::Context;
|
||||
pub use crate::virtual_dom::Scoped;
|
||||
pub use nodes::*;
|
||||
@@ -61,7 +63,7 @@ pub mod prelude {
|
||||
pub use crate::nodebuilder::LazyNodes;
|
||||
|
||||
pub use crate::nodebuilder::ChildrenList;
|
||||
pub use crate::nodebuilder::NodeFactory;
|
||||
pub use crate::nodebuilder::{DioxusElement, NodeFactory};
|
||||
// pub use nodes::iterables::IterableNodes;
|
||||
/// This type alias is an internal way of abstracting over the static functions that represent components.
|
||||
pub use crate::innerlude::FC;
|
||||
|
||||
@@ -13,7 +13,7 @@ use bumpalo::Bump;
|
||||
|
||||
use crate::{
|
||||
events::VirtualEvent,
|
||||
innerlude::{Properties, VComponent, FC},
|
||||
innerlude::{Properties, VComponent, VText, FC},
|
||||
nodes::{Attribute, Listener, NodeKey, VNode},
|
||||
prelude::{VElement, VFragment},
|
||||
virtual_dom::{RealDomNode, Scope},
|
||||
@@ -34,7 +34,6 @@ where
|
||||
cx: &'b NodeFactory<'a>,
|
||||
key: NodeKey<'a>,
|
||||
tag_name: &'static str,
|
||||
// tag_name: &'a str,
|
||||
listeners: Listeners,
|
||||
attributes: Attributes,
|
||||
children: Children,
|
||||
@@ -422,7 +421,11 @@ where
|
||||
}
|
||||
};
|
||||
|
||||
self.attributes.push(Attribute { name, value });
|
||||
self.attributes.push(Attribute {
|
||||
name,
|
||||
value,
|
||||
namespace: None,
|
||||
});
|
||||
self
|
||||
}
|
||||
|
||||
@@ -455,7 +458,11 @@ where
|
||||
/// ```
|
||||
pub fn bool_attr(mut self, name: &'static str, should_add: bool) -> Self {
|
||||
if should_add {
|
||||
self.attributes.push(Attribute { name, value: "" });
|
||||
self.attributes.push(Attribute {
|
||||
name,
|
||||
value: "",
|
||||
namespace: None,
|
||||
});
|
||||
}
|
||||
self
|
||||
}
|
||||
@@ -659,13 +666,17 @@ pub fn text3<'a>(bump: &'a bumpalo::Bump, args: std::fmt::Arguments) -> VNode<'a
|
||||
// ```
|
||||
// div {"abc"}
|
||||
// ```
|
||||
VNode::text(raw_text(bump, args))
|
||||
}
|
||||
|
||||
pub fn raw_text<'a>(bump: &'a bumpalo::Bump, args: std::fmt::Arguments) -> &'a str {
|
||||
match args.as_str() {
|
||||
Some(static_str) => VNode::text(static_str),
|
||||
Some(static_str) => static_str,
|
||||
None => {
|
||||
use bumpalo::core_alloc::fmt::Write;
|
||||
let mut s = bumpalo::collections::String::new_in(bump);
|
||||
s.write_fmt(args).unwrap();
|
||||
VNode::text(s.into_bump_str())
|
||||
s.into_bump_str()
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -683,7 +694,11 @@ pub fn text3<'a>(bump: &'a bumpalo::Bump, args: std::fmt::Arguments) -> VNode<'a
|
||||
/// let my_id_attr = attr("id", "my-id");
|
||||
/// ```
|
||||
pub fn attr<'a>(name: &'static str, value: &'a str) -> Attribute<'a> {
|
||||
Attribute { name, value }
|
||||
Attribute {
|
||||
name,
|
||||
value,
|
||||
namespace: None,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn virtual_child<'a, T: Properties + 'a>(
|
||||
@@ -762,7 +777,7 @@ impl<'a> NodeFactory<'a> {
|
||||
/// Create an element builder
|
||||
pub fn element<'b>(
|
||||
&'b self,
|
||||
tag_name: &'static str,
|
||||
tag: impl DioxusElement,
|
||||
) -> ElementBuilder<
|
||||
'a,
|
||||
'b,
|
||||
@@ -770,7 +785,21 @@ impl<'a> NodeFactory<'a> {
|
||||
bumpalo::collections::Vec<'a, Attribute<'a>>,
|
||||
bumpalo::collections::Vec<'a, VNode<'a>>,
|
||||
> {
|
||||
ElementBuilder::new(self, tag_name)
|
||||
ElementBuilder::new(self, tag.tag_name())
|
||||
}
|
||||
|
||||
pub fn attr(
|
||||
&self,
|
||||
name: &'static str,
|
||||
val: Arguments<'a>,
|
||||
namespace: Option<&'static str>,
|
||||
) -> Attribute<'a> {
|
||||
let value = raw_text(self.bump(), val);
|
||||
Attribute {
|
||||
name,
|
||||
value,
|
||||
namespace,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn child_list(&self) -> ChildrenList {
|
||||
@@ -813,3 +842,11 @@ impl Debug for NodeFactory<'_> {
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
pub trait DioxusElement {
|
||||
const TAG_NAME: &'static str;
|
||||
const NAME_SPACE: Option<&'static str>;
|
||||
fn tag_name(&self) -> &'static str {
|
||||
Self::TAG_NAME
|
||||
}
|
||||
}
|
||||
@@ -216,6 +216,11 @@ pub struct VElement<'a> {
|
||||
pub struct Attribute<'a> {
|
||||
pub name: &'static str,
|
||||
pub value: &'a str,
|
||||
|
||||
/// If an attribute is "namespaced", then it belongs to a group
|
||||
/// The most common namespace is the "style" namespace
|
||||
// pub is_dynamic: bool,
|
||||
pub namespace: Option<&'static str>,
|
||||
}
|
||||
|
||||
impl<'a> Attribute<'a> {
|
||||
|
||||
+108
-72
@@ -1,6 +1,10 @@
|
||||
//! Dedicated styling system for Components
|
||||
//! ---------------------------------------
|
||||
//!
|
||||
//! In the future, we'd like to move this out of Dioxus core or build a better, more general abstraction. For now, dedicated
|
||||
//! styling is more-or-less hardcoded into Dioxus.
|
||||
//!
|
||||
//!
|
||||
//!
|
||||
//!
|
||||
//!
|
||||
@@ -8,76 +12,108 @@
|
||||
//!
|
||||
//!
|
||||
|
||||
enum Styles {
|
||||
background,
|
||||
backgroundAttachment,
|
||||
backgroundColor,
|
||||
backgroundImage,
|
||||
backgroundPosition,
|
||||
backgroundRepeat,
|
||||
border,
|
||||
borderBottom,
|
||||
borderBottomColor,
|
||||
borderBottomStyle,
|
||||
borderBottomWidth,
|
||||
borderColor,
|
||||
borderLeft,
|
||||
borderLeftColor,
|
||||
borderLeftStyle,
|
||||
borderLeftWidth,
|
||||
borderRight,
|
||||
borderRightColor,
|
||||
borderRightStyle,
|
||||
borderRightWidth,
|
||||
borderStyle,
|
||||
borderTop,
|
||||
borderTopColor,
|
||||
borderTopStyle,
|
||||
borderTopWidth,
|
||||
borderWidth,
|
||||
clear,
|
||||
clip,
|
||||
color,
|
||||
cursor,
|
||||
display,
|
||||
filter,
|
||||
cssFloat,
|
||||
font,
|
||||
fontFamily,
|
||||
fontSize,
|
||||
fontVariant,
|
||||
fontWeight,
|
||||
height,
|
||||
left,
|
||||
letterSpacing,
|
||||
lineHeight,
|
||||
listStyle,
|
||||
listStyleImage,
|
||||
listStylePosition,
|
||||
listStyleType,
|
||||
margin,
|
||||
marginBottom,
|
||||
marginLeft,
|
||||
marginRight,
|
||||
marginTop,
|
||||
overflow,
|
||||
padding,
|
||||
paddingBottom,
|
||||
paddingLeft,
|
||||
paddingRight,
|
||||
paddingTop,
|
||||
pageBreakAfter,
|
||||
pageBreakBefore,
|
||||
position,
|
||||
strokeDasharray,
|
||||
strokeDashoffset,
|
||||
textAlign,
|
||||
textDecoration,
|
||||
textIndent,
|
||||
textTransform,
|
||||
top,
|
||||
verticalAlign,
|
||||
visibility,
|
||||
width,
|
||||
zIndex,
|
||||
use crate::{
|
||||
innerlude::Attribute,
|
||||
nodebuilder::{text3, NodeFactory},
|
||||
};
|
||||
|
||||
pub struct StyleBuilder;
|
||||
pub trait AsAttr<'a> {
|
||||
fn to_attr(self, field: &'static str, fac: &NodeFactory<'a>) -> Attribute<'a>;
|
||||
}
|
||||
impl<'a> AsAttr<'a> for std::fmt::Arguments<'a> {
|
||||
fn to_attr(self, field: &'static str, fac: &NodeFactory<'a>) -> Attribute<'a> {
|
||||
fac.attr(field, self, Some("style"))
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! build_styles {
|
||||
($ ($name:ident: $lit:literal,)* ) => {
|
||||
impl StyleBuilder {
|
||||
$(
|
||||
pub fn $name<'a>(f: &NodeFactory<'a>, args: impl AsAttr<'a>) -> Attribute<'a> {
|
||||
args.to_attr($lit, f)
|
||||
}
|
||||
)*
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
build_styles! {
|
||||
background: "background",
|
||||
background_attachment: "background-attachment",
|
||||
background_color: "background-color",
|
||||
background_image: "background-image",
|
||||
background_position: "background-position",
|
||||
background_repeat: "background-repeat",
|
||||
border: "border",
|
||||
border_bottom: "border-bottom",
|
||||
border_bottom_color: "border-bottom-color",
|
||||
border_bottom_style: "border-bottom-style",
|
||||
border_bottom_width: "border-bottom-width",
|
||||
border_color: "border-color",
|
||||
border_left: "border-left",
|
||||
border_left_color: "border-left-color",
|
||||
border_left_style: "border-left-style",
|
||||
border_left_width: "border-left-width",
|
||||
border_right: "border-right",
|
||||
border_right_color: "border-right-color",
|
||||
border_right_style: "border-right-style",
|
||||
border_right_width: "border-right-width",
|
||||
border_style: "border-style",
|
||||
border_top: "border-top",
|
||||
border_top_color: "border-top-color",
|
||||
border_top_style: "border-top-style",
|
||||
border_top_width: "border-top-width",
|
||||
border_width: "border-width",
|
||||
clear: "clear",
|
||||
clip: "clip",
|
||||
color: "color",
|
||||
cursor: "cursor",
|
||||
display: "display",
|
||||
filter: "filter",
|
||||
css_float: "css-float",
|
||||
font: "font",
|
||||
font_family: "font-family",
|
||||
font_size: "font-size",
|
||||
font_variant: "font-variant",
|
||||
font_weight: "font-weight",
|
||||
height: "height",
|
||||
left: "left",
|
||||
letter_spacing: "letter-spacing",
|
||||
line_height: "line-height",
|
||||
list_style: "list-style",
|
||||
list_style_image: "list-style-image",
|
||||
list_style_position: "list-style-position",
|
||||
list_style_type: "list-style-type",
|
||||
margin: "margin",
|
||||
margin_bottom: "margin-bottom",
|
||||
margin_left: "margin-left",
|
||||
margin_right: "margin-right",
|
||||
margin_top: "margin-top",
|
||||
overflow: "overflow",
|
||||
padding: "padding",
|
||||
padding_bottom: "padding-bottom",
|
||||
padding_left: "padding-left",
|
||||
padding_right: "padding-right",
|
||||
padding_top: "padding-top",
|
||||
page_break_after: "page-break-after",
|
||||
page_break_before: "page-break-before",
|
||||
position: "position",
|
||||
stroke_dasharray: "stroke-dasharray",
|
||||
stroke_dashoffset: "stroke-dashoffset",
|
||||
text_align: "text-align",
|
||||
text_decoration: "text-decoration",
|
||||
text_indent: "text-indent",
|
||||
text_transform: "text-transform",
|
||||
top: "top",
|
||||
vertical_align: "vertical-align",
|
||||
visibility: "visibility",
|
||||
width: "width",
|
||||
z_index: "z-index",
|
||||
}
|
||||
|
||||
fn example(f: &NodeFactory) {
|
||||
let style_list = &[("width", "10"), ("text-decoration", "")];
|
||||
let styles = &[StyleBuilder::background(f, format_args!("10"))];
|
||||
}
|
||||
Reference in new issue
Block a user