Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Cleanup
  • Loading branch information
DanielleHuisman committed May 11, 2025
commit 585175bf9721783faf81324f048c1571c121748e
13 changes: 2 additions & 11 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

112 changes: 44 additions & 68 deletions book/src/primitives/components/aspect-ratio.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,146 +2,122 @@

Displays content within a desired ratio.

{{#tabs global="framework"}}
{{#tab name="Leptos"}}
{{#tabs global="framework" }}
{{#tab name="Leptos" }}

```toml,trunk
package = "radix-leptos-book-primitives"
features = ["aspect-ratio"]
files = ["src/aspect_ratio.rs"]
```

{{#endtab}}
{{#tab name="Yew"}}
{{#endtab }}
{{#tab name="Yew" }}

```toml,trunk
package = "radix-yew-book-primitives"
features = ["aspect-ratio"]
files = ["src/aspect_ratio.rs"]
```

{{#endtab}}
{{#endtabs}}
{{#endtab }}
{{#endtabs }}

## Features

- Accepts any custom ratio.
- Accepts any custom ratio.

## Installation

Install the component from your command line.

{{#tabs global="framework"}}
{{#tab name="Leptos"}}
{{#tabs global="framework" }}
{{#tab name="Leptos" }}

```shell
cargo add radix-leptos-aspect-ratio
```

- [View on crates.io](https://crates.io/crates/radix-leptos-aspect-ratio)
- [View on docs.rs](https://docs.rs/radix-leptos-aspect-ratio/latest/radix_leptos_aspect_ratio/)
- [View source](https://github.com/RustForWeb/radix/tree/main/packages/primitives/leptos/aspect-ratio)
- [View on crates.io](https://crates.io/crates/radix-leptos-aspect-ratio)
- [View on docs.rs](https://docs.rs/radix-leptos-aspect-ratio/latest/radix_leptos_aspect_ratio/)
- [View source](https://github.com/RustForWeb/radix/tree/main/packages/primitives/leptos/aspect-ratio)

{{#endtab}}
{{#tab name="Yew"}}
{{#endtab }}
{{#tab name="Yew" }}

```shell
cargo add radix-yew-aspect-ratio
```

- [View on crates.io](https://crates.io/crates/radix-yew-aspect-ratio)
- [View on docs.rs](https://docs.rs/radix-yew-aspect-ratio/latest/radix_yew_aspect_ratio/)
- [View source](https://github.com/RustForWeb/radix/tree/main/packages/primitives/yew/aspect-ratio)
- [View on crates.io](https://crates.io/crates/radix-yew-aspect-ratio)
- [View on docs.rs](https://docs.rs/radix-yew-aspect-ratio/latest/radix_yew_aspect_ratio/)
- [View source](https://github.com/RustForWeb/radix/tree/main/packages/primitives/yew/aspect-ratio)

{{#endtab}}
{{#endtabs}}
{{#endtab }}
{{#endtabs }}

## Anatomy

{{#tabs global="framework"}}
{{#tab name="Leptos"}}
Import the component.

{{#tabs global="framework" }}
{{#tab name="Leptos" }}

```rust,ignore
use leptos::*;
use radix_leptos_aspect_ratio as AspectRatio;
use radix_leptos_aspect_ratio::*;

#[component]
fn Anatomy() -> impl IntoView {
view! {
<AspectRatio::Root ratio=16.0/9.0>
<div>"Constrained within the 16:9 ratio!"</div>
</AspectRatio::Root>
<AspectRatio />
}
}
```

{{#endtab}}
{{#tab name="Yew"}}
{{#endtab }}
{{#tab name="Yew" }}

```rust,ignore
use radix_yew_aspect_ratio::*;
use yew::prelude::*;
use yew::prelude::::*;

#[function_component]
fn Anatomy() -> Html {
html! {
<AspectRatio>
{"Constrained within the desired ratio!"}
</AspectRatio>
<AspectRatio />
}
}
```

{{#endtab}}
{{#endtabs}}
{{#endtab }}
{{#endtabs }}

## API Reference

### Root

Contains the content you want to constrain to a given ratio.

{{#tabs global="framework"}}
{{#tab name="Leptos"}}
{{#tabs global="framework" }}
{{#tab name="Leptos" }}

| Prop | Type | Default |
|------------|-------------------|---------|
| ---------- | ----------------- | ------- |
| `as_child` | `MaybeProp<bool>` | `false` |
| `ratio` | `MaybeProp<f64>` | `1.0` |
| `node_ref` | `AnyNodeRef` | - |

### Usage

To use the `Root` alias for the `AspectRatio` component, import it and use `AspectRatio::Root` in your view.

```rust,ignore
use leptos::*;
use radix_leptos_aspect_ratio as AspectRatio;

#[component]
fn Example() -> impl IntoView {
view! {
<AspectRatio::Root ratio=4.0/3.0>
<img src="path/to/image.jpg" alt="Example Image" />
</AspectRatio::Root>
}
}
```

{{#endtab}}
{{#tab name="Yew"}}
| `ratio` | `Signal<f64>` | `1.0` |

<!-- TODO: Add or update Yew-specific props if needed -->
{{#endtab }}
{{#tab name="Yew" }}

| Prop | Type | Default |
|---------|-------|---------|
| `ratio` | `f64` | `1.0` |
| Prop | Type | Default |
| ---------- | ----------------------------------------------- | ------- |
| `as_child` | `Option<Callback<AspectRatioChildProps, Html>>` | - |
| `ratio` | `f64` | `1.0` |

{{#endtab}}
{{#endtabs}}
{{#endtab }}
{{#endtabs }}

## See Also

- [Radix documentation](https://www.radix-ui.com/primitives/docs/components/aspect-ratio)

```
- [Radix documentation](https://www.radix-ui.com/primitives/docs/components/aspect-ratio)
2 changes: 1 addition & 1 deletion packages/primitives/leptos/aspect-ratio/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -12,4 +12,4 @@ version.workspace = true
[dependencies]
leptos.workspace = true
leptos-node-ref.workspace = true
radix-leptos-primitive.workspace = true
radix-leptos-primitive = { path = "../primitive", version = "0.0.2" }
73 changes: 17 additions & 56 deletions packages/primitives/leptos/aspect-ratio/src/aspect_ratio.rs
Original file line number Diff line number Diff line change
@@ -1,80 +1,41 @@
use leptos::{prelude::*, html, attribute_interceptor::AttributeInterceptor};
use radix_leptos_primitive::Primitive;
use leptos::{attribute_interceptor::AttributeInterceptor, html, prelude::*};
use leptos_node_ref::AnyNodeRef;

const DEFAULT_RATIO: f64 = 1.0;

/* -------------------------------------------------------------------------------------------------
* AspectRatio
* -----------------------------------------------------------------------------------------------*/

const NAME: &'static str = "AspectRatio";
use radix_leptos_primitive::Primitive;

#[component]
#[allow(non_snake_case)]
pub fn AspectRatio(
/// Children passed to the AspectRatio component
#[prop(into, optional, default = 1.0.into())] ratio: Signal<f64>,
#[prop(into, optional)] as_child: MaybeProp<bool>,
#[prop(optional)] node_ref: AnyNodeRef,
children: TypedChildrenFn<impl IntoView + 'static>,
/// Change the default rendered element for the one passed as a child
#[prop(into, optional, default = false.into())]
as_child: MaybeProp<bool>,
/// The desired ratio when rendering the content (e.g., 16/9). Defaults to 1.0 if not specified.
#[prop(into, optional, default = DEFAULT_RATIO.into())]
ratio: MaybeProp<f64>,
/// Reference to the underlying DOM node
#[prop(into, optional)]
node_ref: AnyNodeRef,
) -> impl IntoView {
// attribute interceptor incurs this requirement
let children = StoredValue::new(children.into_inner());

// calculates the percent-based padding for the aspect ratio
let padding_bottom = Signal::derive(move || {
100.0
/ ratio
.get()
.unwrap_or(DEFAULT_RATIO)
.clamp(f64::EPSILON, f64::MAX)
});

#[cfg(debug_assertions)]
Effect::new(move |_| {
leptos::logging::log!("[{NAME}] ratio: {:?}", ratio.get());
leptos::logging::log!("[{NAME}] as_child: {:?}", as_child.get());
leptos::logging::log!("[{NAME}] node_ref: {:?}", node_ref.get());
leptos::logging::log!("[{NAME}] padding_bottom: {:?}", padding_bottom.get());
});

view! {
// replicate the radix react spread props
<AttributeInterceptor let:attrs>
// ensures inner element is contained
<div
// Ensures inner element is contained
style:position="relative"
// ensures padding bottom trick works
// Ensures padding bottom trick maths works
style:width="100%"
style:padding-bottom=move || format!("{}%", padding_bottom.get())
style:padding-bottom=move || format!("{}%", 100.0 / ratio.get())
data-radix-aspect-ratio-wrapper=""
>
<Primitive
// ensures children expand to fill the ratio
element={html::div}
as_child={as_child}
node_ref={node_ref}
{..attrs}
element=html::div
as_child=as_child
node_ref=node_ref
// Ensures children expand in ratio
style:position="absolute"
style:top="0"
style:right="0"
style:bottom="0"
style:left="0"
style:top="0px"
style:right="0px"
style:bottom="0px"
style:left="0px"
{..attrs}
>
{children.with_value(|children| children())}
</Primitive>
</div>
</AttributeInterceptor>
}
}

/* -----------------------------------------------------------------------------------------------*/

pub use AspectRatio as Root;