pub struct Linear<D, N = f64>{ /* private fields */ }Expand description
Linear scale: affine mapping between a numeric domain and normalized [0, 1] range.
Linear provides a straightforward linear mapping between data values and
a normalized [0, 1] range. This is the most common scale type for charting.
§Type Parameters
D: Domain type (the data values, typicallyf32orf64)N: Normalized type (typicallyf32orf64, represents[0, 1]range)
§Features
- Bidirectional mapping: Convert between domain and normalized values
- Pan and zoom: Interactively adjust the visible domain
- Tick generation: Automatically generate “nice” tick marks for axes
- Reversed axes: Support both increasing and decreasing domains
- No clamping: Out-of-range values map beyond [0, 1]
§Domain Ordering
Domain values are kept exactly as set (no implicit sorting), so both normal and reversed axes are supported:
- Normal:
new(0.0, 100.0)- larger values at the right/top - Reversed:
new(100.0, 0.0)- larger values at the left/bottom
§Examples
§Basic Usage
use aksel::{Scale, scale::Linear};
let scale = Linear::<f64, f64>::new(0.0, 100.0);
// Normalize to [0, 1]
assert_eq!(scale.normalize(&0.0), 0.0);
assert_eq!(scale.normalize(&50.0), 0.5);
assert_eq!(scale.normalize(&100.0), 1.0);
// Denormalize back to domain
assert_eq!(scale.denormalize(0.0), 0.0);
assert_eq!(scale.denormalize(0.5), 50.0);
assert_eq!(scale.denormalize(1.0), 100.0);§Mixed Type Precision
use aksel::{Scale, scale::Linear};
// f64 domain, f32 normalized (common for GPU rendering)
let scale = Linear::<f64, f32>::new(0.0, 100.0);
let normalized: f32 = scale.normalize(&50.0);
assert_eq!(normalized, 0.5f32);§Pan and Zoom
use aksel::{Scale, scale::Linear};
let mut scale = Linear::<f64, f64>::new(0.0, 100.0);
// Pan by 20% of the range
scale.pan(0.2);
assert_eq!(scale.domain(), (&20.0, &120.0));
// Zoom in 2x around the center
let mut scale = Linear::<f64, f64>::new(0.0, 100.0);
scale.zoom(2.0, Some(0.5));
assert_eq!(scale.domain(), (&25.0, &75.0));
// Zoom in 2x around the left edge (25% position)
let mut scale = Linear::<f64, f64>::new(0.0, 100.0);
scale.zoom(2.0, Some(0.25));
assert_eq!(scale.domain(), (&12.5, &62.5));§Reversed Axis
use aksel::{Scale, scale::Linear};
// Create a reversed scale (useful for Y-axes that go down)
let scale = Linear::<f64, f64>::new(100.0, 0.0);
assert_eq!(scale.normalize(&100.0), 0.0);
assert_eq!(scale.normalize(&0.0), 1.0);§Custom Tick Generation
use aksel::{Scale, scale::{Linear, Tick}};
// Create a scale with custom ticks
let scale = Linear::<f64, f64>::new_with_tick_fn(0.0, 100.0, |_scale| {
vec![
Tick { value: 0.0, level: 0 },
Tick { value: 50.0, level: 0 },
Tick { value: 100.0, level: 0 },
]
});
assert_eq!(scale.ticks().len(), 3);§Out-of-Range Values
use aksel::{Scale, scale::Linear};
let scale = Linear::<f64, f64>::new(0.0, 100.0);
// Values outside domain are not clamped
assert_eq!(scale.normalize(&150.0), 1.5);
assert_eq!(scale.normalize(&-50.0), -0.5);Implementations§
Source§impl<D, N> Linear<D, N>
impl<D, N> Linear<D, N>
Sourcepub fn new(min: D, max: D) -> Self
pub fn new(min: D, max: D) -> Self
Creates a new linear scale with the given domain range.
Uses the default tick generator which creates “nice” tick marks at round numbers (e.g., 0, 10, 20, 50, 100).
§Arguments
min- The minimum value of the domainmax- The maximum value of the domain
§Examples
use aksel::{Scale, scale::Linear};
let scale = Linear::<f64, f64>::new(0.0, 100.0);
assert_eq!(scale.domain(), (&0.0, &100.0));Sourcepub fn new_with_tick_generator<F>(min: D, max: D, tick_generator: F) -> Self
pub fn new_with_tick_generator<F>(min: D, max: D, tick_generator: F) -> Self
Creates a new linear scale with a custom tick generator.
The tick generator is a function that takes a reference to the scale
and returns a TickIter that generates tick marks.
§Arguments
min- The minimum value of the domainmax- The maximum value of the domaintick_generator- A function that generates ticks for this scale
§Examples
use aksel::{Scale, scale::{Linear, TickIter}};
let scale = Linear::<f64, f64>::new_with_tick_generator(0.0, 100.0, |_scale| {
TickIter::empty()
});
assert!(scale.ticks().is_empty());Sourcepub fn new_with_tick_fn<F>(min: D, max: D, tick_fn: F) -> Self
pub fn new_with_tick_fn<F>(min: D, max: D, tick_fn: F) -> Self
Creates a new linear scale with a custom tick function.
This is a convenience method that wraps a function returning Vec<Tick<D>>
into a tick generator. Use this when you want to provide a simple list
of ticks rather than implementing an iterator.
§Arguments
min- The minimum value of the domainmax- The maximum value of the domaintick_fn- A function that generates a vector of ticks
§Examples
use aksel::{Scale, scale::{Linear, Tick}};
let scale = Linear::<f64, f64>::new_with_tick_fn(0.0, 100.0, |_scale| {
vec![
Tick { value: 0.0, level: 0 },
Tick { value: 50.0, level: 0 },
Tick { value: 100.0, level: 0 },
]
});
assert_eq!(scale.ticks().len(), 3);Trait Implementations§
Source§impl<D, N> Scale for Linear<D, N>
impl<D, N> Scale for Linear<D, N>
Source§type Normalized = N
type Normalized = N
[0, 1] values (e.g., f32, f64).Source§fn set_domain(&mut self, min: D, max: D)
fn set_domain(&mut self, min: D, max: D)
min and max values.