Skip to content

Commit 8e864fd

Browse files
committed
can specify an anchor for a sprite (#3463)
# Objective - Fixes #1616, fixes #2225 - Let user specify an anchor for a sprite ## Solution - Add an enum for an anchor point for most common values, with a variant for a custom point - Defaults to Center to not change current behaviour Co-authored-by: François <[email protected]>
1 parent dba7790 commit 8e864fd

File tree

4 files changed

+53
-3
lines changed

4 files changed

+53
-3
lines changed

crates/bevy_sprite/src/render/mod.rs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -184,6 +184,7 @@ pub struct ExtractedSprite {
184184
pub image_handle_id: HandleId,
185185
pub flip_x: bool,
186186
pub flip_y: bool,
187+
pub anchor: Vec2,
187188
}
188189

189190
#[derive(Default)]
@@ -248,6 +249,7 @@ pub fn extract_sprites(
248249
flip_x: sprite.flip_x,
249250
flip_y: sprite.flip_y,
250251
image_handle_id: handle.id,
252+
anchor: sprite.anchor.as_vec(),
251253
});
252254
}
253255
for (visibility, atlas_sprite, transform, texture_atlas_handle) in atlas_query.iter() {
@@ -266,6 +268,7 @@ pub fn extract_sprites(
266268
flip_x: atlas_sprite.flip_x,
267269
flip_y: atlas_sprite.flip_y,
268270
image_handle_id: texture_atlas.texture.id,
271+
anchor: atlas_sprite.anchor.as_vec(),
269272
});
270273
}
271274
}
@@ -489,7 +492,7 @@ pub fn queue_sprites(
489492
let positions = QUAD_VERTEX_POSITIONS.map(|quad_pos| {
490493
extracted_sprite
491494
.transform
492-
.mul_vec3((quad_pos * quad_size).extend(0.))
495+
.mul_vec3(((quad_pos - extracted_sprite.anchor) * quad_size).extend(0.))
493496
.into()
494497
});
495498

crates/bevy_sprite/src/sprite.rs

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,4 +15,48 @@ pub struct Sprite {
1515
/// An optional custom size for the sprite that will be used when rendering, instead of the size
1616
/// of the sprite's image
1717
pub custom_size: Option<Vec2>,
18+
/// [`Anchor`] point of the sprite in the world
19+
pub anchor: Anchor,
20+
}
21+
22+
/// How a sprite is positioned relative to its [`Transform`](bevy_transform::components::Transform).
23+
/// It defaults to `Anchor::Center`.
24+
#[derive(Debug, Clone, Reflect)]
25+
#[doc(alias = "pivot")]
26+
pub enum Anchor {
27+
Center,
28+
BottomLeft,
29+
BottomCenter,
30+
BottomRight,
31+
CenterLeft,
32+
CenterRight,
33+
TopLeft,
34+
TopCenter,
35+
TopRight,
36+
/// Custom anchor point. Top left is `(-0.5, 0.5)`, center is `(0.0, 0.0)`. The value will
37+
/// be scaled with the sprite size.
38+
Custom(Vec2),
39+
}
40+
41+
impl Default for Anchor {
42+
fn default() -> Self {
43+
Anchor::Center
44+
}
45+
}
46+
47+
impl Anchor {
48+
pub fn as_vec(&self) -> Vec2 {
49+
match self {
50+
Anchor::Center => Vec2::ZERO,
51+
Anchor::BottomLeft => Vec2::new(-0.5, -0.5),
52+
Anchor::BottomCenter => Vec2::new(0.0, -0.5),
53+
Anchor::BottomRight => Vec2::new(0.5, -0.5),
54+
Anchor::CenterLeft => Vec2::new(-0.5, 0.0),
55+
Anchor::CenterRight => Vec2::new(0.5, 0.0),
56+
Anchor::TopLeft => Vec2::new(-0.5, 0.5),
57+
Anchor::TopCenter => Vec2::new(0.0, 0.5),
58+
Anchor::TopRight => Vec2::new(0.5, 0.5),
59+
Anchor::Custom(point) => *point,
60+
}
61+
}
1862
}

crates/bevy_sprite/src/texture_atlas.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use crate::Rect;
1+
use crate::{Anchor, Rect};
22
use bevy_asset::Handle;
33
use bevy_ecs::component::Component;
44
use bevy_math::Vec2;
@@ -30,6 +30,7 @@ pub struct TextureAtlasSprite {
3030
/// An optional custom size for the sprite that will be used when rendering, instead of the size
3131
/// of the sprite's image in the atlas
3232
pub custom_size: Option<Vec2>,
33+
pub anchor: Anchor,
3334
}
3435

3536
impl Default for TextureAtlasSprite {
@@ -40,6 +41,7 @@ impl Default for TextureAtlasSprite {
4041
flip_x: false,
4142
flip_y: false,
4243
custom_size: None,
44+
anchor: Anchor::default(),
4345
}
4446
}
4547
}

crates/bevy_text/src/text2d.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ use bevy_ecs::{
1010
use bevy_math::{Size, Vec3};
1111
use bevy_reflect::Reflect;
1212
use bevy_render::{texture::Image, view::Visibility, RenderWorld};
13-
use bevy_sprite::{ExtractedSprite, ExtractedSprites, TextureAtlas};
13+
use bevy_sprite::{Anchor, ExtractedSprite, ExtractedSprites, TextureAtlas};
1414
use bevy_transform::prelude::{GlobalTransform, Transform};
1515
use bevy_window::{WindowId, Windows};
1616

@@ -116,6 +116,7 @@ pub fn extract_text2d_sprite(
116116
image_handle_id: handle.id,
117117
flip_x: false,
118118
flip_y: false,
119+
anchor: Anchor::Center.as_vec(),
119120
});
120121
}
121122
}

0 commit comments

Comments
 (0)