pub struct LookDirection { /* private fields */ }Expand description
The direction that an entity is looking, in degrees.
To avoid flagging anticheats, consider using Self::update when updating
the values of this struct.
Implementations§
Source§impl LookDirection
impl LookDirection
Sourcepub fn new(y_rot: f32, x_rot: f32) -> Self
pub fn new(y_rot: f32, x_rot: f32) -> Self
Create a new look direction and clamp the x_rot to the allowed values.
Sourcepub fn y_rot(&self) -> f32
pub fn y_rot(&self) -> f32
Returns yaw (left and right) in degrees.
Minecraft allows this to go outside of ±360°, so it won’t necessarily be in any range.
Examples found in repository?
26pub fn register(commands: &mut CommandDispatcher<Mutex<CommandSource>>) {
27 commands.register(literal("ping").executes(|ctx: &Ctx| {
28 let source = ctx.source.lock();
29 source.reply("pong!");
30 1
31 }));
32
33 commands.register(literal("disconnect").executes(|ctx: &Ctx| {
34 let source = ctx.source.lock();
35 source.bot.disconnect();
36 1
37 }));
38
39 commands.register(literal("whereami").executes(|ctx: &Ctx| {
40 let source = ctx.source.lock();
41 let Some(entity) = source.entity() else {
42 source.reply("You aren't in render distance!");
43 return 0;
44 };
45 let position = entity.position();
46 source.reply(format!(
47 "You are at {}, {}, {}",
48 position.x, position.y, position.z
49 ));
50 1
51 }));
52
53 commands.register(literal("entityid").executes(|ctx: &Ctx| {
54 let source = ctx.source.lock();
55 let Some(entity) = source.entity() else {
56 source.reply("You aren't in render distance!");
57 return 0;
58 };
59 let entity_id = entity.minecraft_id();
60 source.reply(format!(
61 "Your Minecraft ID is {} and your ECS ID is {entity:?}",
62 *entity_id
63 ));
64 1
65 }));
66
67 let whereareyou = |ctx: &Ctx| {
68 let source = ctx.source.lock();
69 let position = source.bot.position();
70 source.reply(format!(
71 "I'm at {}, {}, {}",
72 position.x, position.y, position.z
73 ));
74 1
75 };
76 commands.register(literal("whereareyou").executes(whereareyou));
77 commands.register(literal("pos").executes(whereareyou));
78
79 commands.register(literal("whoareyou").executes(|ctx: &Ctx| {
80 let source = ctx.source.lock();
81 source.reply(format!(
82 "I am {} ({}, {})",
83 source.bot.username(),
84 source.bot.uuid(),
85 source.bot.entity
86 ));
87 1
88 }));
89
90 commands.register(literal("getdirection").executes(|ctx: &Ctx| {
91 let source = ctx.source.lock();
92 let direction = source.bot.direction();
93 source.reply(format!(
94 "I'm looking at {}, {}",
95 direction.y_rot(),
96 direction.x_rot()
97 ));
98 1
99 }));
100
101 commands.register(literal("health").executes(|ctx: &Ctx| {
102 let source = ctx.source.lock();
103
104 let health = source.bot.health();
105 source.reply(format!("I have {health} health"));
106 1
107 }));
108
109 commands.register(literal("lookingat").executes(|ctx: &Ctx| {
110 let source = ctx.source.lock();
111
112 let hit_result = source.bot.hit_result();
113
114 match &hit_result {
115 HitResult::Block(r) => {
116 if r.miss {
117 source.reply("I'm not looking at anything");
118 return 0;
119 }
120 let block_pos = r.block_pos;
121 let block = source.bot.world().read().get_block_state(block_pos);
122 source.reply(format!("I'm looking at {block:?} at {block_pos:?}"));
123 }
124 HitResult::Entity(r) => {
125 let entity_kind = **source.bot.entity_component::<EntityKindComponent>(r.entity);
126 source.reply(format!(
127 "I'm looking at {entity_kind} ({:?}) at {}",
128 r.entity, r.location
129 ));
130 }
131 }
132
133 1
134 }));
135
136 commands.register(literal("getblock").then(argument("x", integer()).then(
137 argument("y", integer()).then(argument("z", integer()).executes(|ctx: &Ctx| {
138 let source = ctx.source.lock();
139 let x = get_integer(ctx, "x").unwrap();
140 let y = get_integer(ctx, "y").unwrap();
141 let z = get_integer(ctx, "z").unwrap();
142 println!("getblock xyz {x} {y} {z}");
143 let block_pos = BlockPos::new(x, y, z);
144 let block = source.bot.world().read().get_block_state(block_pos);
145 source.reply(format!("BlockKind at {block_pos} is {block:?}"));
146 1
147 })),
148 )));
149 commands.register(literal("getfluid").then(argument("x", integer()).then(
150 argument("y", integer()).then(argument("z", integer()).executes(|ctx: &Ctx| {
151 let source = ctx.source.lock();
152 let x = get_integer(ctx, "x").unwrap();
153 let y = get_integer(ctx, "y").unwrap();
154 let z = get_integer(ctx, "z").unwrap();
155 println!("getfluid xyz {x} {y} {z}");
156 let block_pos = BlockPos::new(x, y, z);
157 let block = source.bot.world().read().get_fluid_state(block_pos);
158 source.reply(format!("Fluid at {block_pos} is {block:?}"));
159 1
160 })),
161 )));
162
163 commands.register(literal("pathfinderstate").executes(|ctx: &Ctx| {
164 let source = ctx.source.lock();
165 let pathfinder = source.bot.get_component::<Pathfinder>();
166 let Some(pathfinder) = pathfinder else {
167 source.reply("I don't have the Pathfinder component");
168 return 1;
169 };
170 source.reply(format!(
171 "pathfinder.is_calculating: {}",
172 pathfinder.is_calculating
173 ));
174
175 let executing_path = source.bot.get_component::<ExecutingPath>();
176 let Some(executing_path) = executing_path else {
177 source.reply("I'm not executing a path");
178 return 1;
179 };
180 source.reply(format!(
181 "is_path_partial: {}, path.len: {}, queued_path.len: {}",
182 executing_path.is_path_partial,
183 executing_path.path.len(),
184 if let Some(queued) = &executing_path.queued_path {
185 queued.len().to_string()
186 } else {
187 "n/a".to_owned()
188 },
189 ));
190 1
191 }));
192 commands.register(literal("pathfindermoves").executes(|ctx: &Ctx| {
193 let source = ctx.source.lock();
194
195 let Some(entity) = source.entity() else {
196 source.reply("You aren't in render distance!");
197 return 0;
198 };
199 let position = entity.position();
200 let position = BlockPos::from(position);
201
202 let mut edges = Vec::new();
203 let cached_world = CachedWorld::new(source.bot.world(), position);
204 let mining_cache = MiningCache::new(Some(Menu::Player(inventory::Player::default())));
205 let custom_state = CustomPathfinderStateRef::default();
206
207 azalea::pathfinder::moves::default_move(
208 &mut MovesCtx {
209 edges: &mut edges,
210 world: &cached_world,
211 mining_cache: &mining_cache,
212 custom_state: &custom_state,
213 },
214 RelBlockPos::from_origin(position, position),
215 );
216
217 if edges.is_empty() {
218 source.reply("No possible moves.");
219 } else {
220 source.reply("Moves:");
221 for (i, edge) in edges.iter().enumerate() {
222 source.reply(format!("{}) {edge:?}", i + 1));
223 }
224 }
225
226 1
227 }));
228
229 commands.register(literal("startuseitem").executes(|ctx: &Ctx| {
230 let source = ctx.source.lock();
231 source.bot.start_use_item();
232 source.reply("Ok!");
233 1
234 }));
235 commands.register(literal("maxstacksize").executes(|ctx: &Ctx| {
236 let source = ctx.source.lock();
237 let max_stack_size = source
238 .bot
239 .get_held_item()
240 .get_component::<MaxStackSize>()
241 .map_or(-1, |s| s.count);
242 source.reply(format!("{max_stack_size}"));
243 1
244 }));
245
246 commands.register(literal("dimensions").executes(|ctx: &Ctx| {
247 let source = ctx.source.lock();
248 let bot_dimensions = source.bot.dimensions();
249 source.reply(format!("{bot_dimensions:?}"));
250 1
251 }));
252
253 commands.register(literal("players").executes(|ctx: &Ctx| {
254 let source = ctx.source.lock();
255 let player_entities = source
256 .bot
257 .nearest_entities_by::<(), With<metadata::Player>>(|_: ()| true);
258 let tab_list = source.bot.tab_list();
259 for player_entity in player_entities {
260 let uuid = player_entity.uuid();
261 source.reply(format!(
262 "{} - {} ({:?})",
263 player_entity.id(),
264 tab_list.get(&uuid).map_or("?", |p| p.profile.name.as_str()),
265 uuid
266 ));
267 }
268 1
269 }));
270
271 commands.register(literal("enchants").executes(|ctx: &Ctx| {
272 let source = ctx.source.lock();
273 source.bot.with_registry_holder(|r| {
274 let enchants = &r.enchantment;
275 println!("enchants: {enchants:?}");
276 });
277 1
278 }));
279
280 commands.register(literal("attributes").executes(|ctx: &Ctx| {
281 let source = ctx.source.lock();
282 let attributes = source.bot.attributes();
283 println!("attributes: {attributes:?}");
284 1
285 }));
286
287 commands.register(literal("debugecsleak").executes(|ctx: &Ctx| {
288 let source = ctx.source.lock();
289
290 source.reply("Ok!");
291
292
293
294 source.bot.disconnect();
295
296 let ecs = source.bot.ecs.clone();
297 thread::spawn(move || {
298 thread::sleep(Duration::from_secs(1));
299 // dump the ecs
300
301 let mut ecs = ecs.write();
302
303 let report_path = env::temp_dir().join("azalea-ecs-leak-report.txt");
304 let mut report = File::create(&report_path).unwrap();
305
306 let mut query = ecs.query::<EntityRef>();
307 for entity in query.iter(& ecs) {
308 writeln!(report, "Entity: {}", entity.id()).unwrap();
309 let archetype = entity.archetype();
310 let component_count = archetype.component_count();
311
312 let component_names = archetype
313 .components()
314 .iter()
315 .map(|c| ecs.components().get_info(*c).unwrap().name().to_string())
316 .collect::<Vec<_>>();
317 writeln!(
318 report,
319 "- {component_count} components: {}",
320 component_names.join(", ")
321 )
322 .unwrap();
323 }
324
325 writeln!(report).unwrap();
326
327
328 for (info, _) in ecs.iter_resources() {
329 let name = info.name().to_string();
330 writeln!(report, "Resource: {name}").unwrap();
331 // writeln!(report, "- Size: {} bytes",
332 // info.layout().size()).unwrap();
333
334 match name.as_ref() {
335 "azalea_world::container::Worlds" => {
336 let worlds = ecs.resource::<Worlds>();
337
338 for (world_name, world) in &worlds.map {
339 writeln!(report, "- Name: {world_name}").unwrap();
340 writeln!(report, "- Reference count: {}", world.strong_count())
341 .unwrap();
342 if let Some(world) = world.upgrade() {
343 let world = world.read();
344 let strong_chunks = world
345 .chunks
346 .map
347 .iter()
348 .filter(|(_, v)| v.strong_count() > 0)
349 .count();
350 writeln!(
351 report,
352 "- Chunks: {} strongly referenced, {} in map",
353 strong_chunks,
354 world.chunks.map.len()
355 )
356 .unwrap();
357 writeln!(
358 report,
359 "- Entities: {}",
360 world.entities_by_chunk.len()
361 )
362 .unwrap();
363 }
364 }
365 }
366 "bevy_ecs::message::Messages<azalea_client::packet::game::ReceivePacketEvent>" => {
367 let events = ecs.resource::<Messages<game::ReceiveGamePacketEvent>>();
368 writeln!(report, "- Event count: {}", events.len()).unwrap();
369 }
370 "bevy_ecs::message::Messages<azalea_client::chunks::ReceiveChunkEvent>" => {
371 let events = ecs.resource::<Messages<ReceiveChunkEvent>>();
372 writeln!(report, "- Event count: {}", events.len()).unwrap();
373 }
374
375 _ => {}
376 }
377 }
378
379 println!("\x1b[1mWrote report to {}\x1b[m", report_path.display());
380 });
381
382 1
383 }));
384
385 commands.register(literal("exit").executes(|ctx: &Ctx| {
386 let source = ctx.source.lock();
387 source.reply("bye!");
388
389 source.bot.disconnect();
390
391 let source = ctx.source.clone();
392 thread::spawn(move || {
393 thread::sleep(Duration::from_secs(1));
394
395 source
396 .lock()
397 .bot
398 .ecs
399 .write()
400 .write_message(AppExit::Success);
401 });
402
403 1
404 }));
405}Sourcepub fn x_rot(&self) -> f32
pub fn x_rot(&self) -> f32
Returns pitch (up and down) in degrees.
Clamped to ±90°.
Examples found in repository?
26pub fn register(commands: &mut CommandDispatcher<Mutex<CommandSource>>) {
27 commands.register(literal("ping").executes(|ctx: &Ctx| {
28 let source = ctx.source.lock();
29 source.reply("pong!");
30 1
31 }));
32
33 commands.register(literal("disconnect").executes(|ctx: &Ctx| {
34 let source = ctx.source.lock();
35 source.bot.disconnect();
36 1
37 }));
38
39 commands.register(literal("whereami").executes(|ctx: &Ctx| {
40 let source = ctx.source.lock();
41 let Some(entity) = source.entity() else {
42 source.reply("You aren't in render distance!");
43 return 0;
44 };
45 let position = entity.position();
46 source.reply(format!(
47 "You are at {}, {}, {}",
48 position.x, position.y, position.z
49 ));
50 1
51 }));
52
53 commands.register(literal("entityid").executes(|ctx: &Ctx| {
54 let source = ctx.source.lock();
55 let Some(entity) = source.entity() else {
56 source.reply("You aren't in render distance!");
57 return 0;
58 };
59 let entity_id = entity.minecraft_id();
60 source.reply(format!(
61 "Your Minecraft ID is {} and your ECS ID is {entity:?}",
62 *entity_id
63 ));
64 1
65 }));
66
67 let whereareyou = |ctx: &Ctx| {
68 let source = ctx.source.lock();
69 let position = source.bot.position();
70 source.reply(format!(
71 "I'm at {}, {}, {}",
72 position.x, position.y, position.z
73 ));
74 1
75 };
76 commands.register(literal("whereareyou").executes(whereareyou));
77 commands.register(literal("pos").executes(whereareyou));
78
79 commands.register(literal("whoareyou").executes(|ctx: &Ctx| {
80 let source = ctx.source.lock();
81 source.reply(format!(
82 "I am {} ({}, {})",
83 source.bot.username(),
84 source.bot.uuid(),
85 source.bot.entity
86 ));
87 1
88 }));
89
90 commands.register(literal("getdirection").executes(|ctx: &Ctx| {
91 let source = ctx.source.lock();
92 let direction = source.bot.direction();
93 source.reply(format!(
94 "I'm looking at {}, {}",
95 direction.y_rot(),
96 direction.x_rot()
97 ));
98 1
99 }));
100
101 commands.register(literal("health").executes(|ctx: &Ctx| {
102 let source = ctx.source.lock();
103
104 let health = source.bot.health();
105 source.reply(format!("I have {health} health"));
106 1
107 }));
108
109 commands.register(literal("lookingat").executes(|ctx: &Ctx| {
110 let source = ctx.source.lock();
111
112 let hit_result = source.bot.hit_result();
113
114 match &hit_result {
115 HitResult::Block(r) => {
116 if r.miss {
117 source.reply("I'm not looking at anything");
118 return 0;
119 }
120 let block_pos = r.block_pos;
121 let block = source.bot.world().read().get_block_state(block_pos);
122 source.reply(format!("I'm looking at {block:?} at {block_pos:?}"));
123 }
124 HitResult::Entity(r) => {
125 let entity_kind = **source.bot.entity_component::<EntityKindComponent>(r.entity);
126 source.reply(format!(
127 "I'm looking at {entity_kind} ({:?}) at {}",
128 r.entity, r.location
129 ));
130 }
131 }
132
133 1
134 }));
135
136 commands.register(literal("getblock").then(argument("x", integer()).then(
137 argument("y", integer()).then(argument("z", integer()).executes(|ctx: &Ctx| {
138 let source = ctx.source.lock();
139 let x = get_integer(ctx, "x").unwrap();
140 let y = get_integer(ctx, "y").unwrap();
141 let z = get_integer(ctx, "z").unwrap();
142 println!("getblock xyz {x} {y} {z}");
143 let block_pos = BlockPos::new(x, y, z);
144 let block = source.bot.world().read().get_block_state(block_pos);
145 source.reply(format!("BlockKind at {block_pos} is {block:?}"));
146 1
147 })),
148 )));
149 commands.register(literal("getfluid").then(argument("x", integer()).then(
150 argument("y", integer()).then(argument("z", integer()).executes(|ctx: &Ctx| {
151 let source = ctx.source.lock();
152 let x = get_integer(ctx, "x").unwrap();
153 let y = get_integer(ctx, "y").unwrap();
154 let z = get_integer(ctx, "z").unwrap();
155 println!("getfluid xyz {x} {y} {z}");
156 let block_pos = BlockPos::new(x, y, z);
157 let block = source.bot.world().read().get_fluid_state(block_pos);
158 source.reply(format!("Fluid at {block_pos} is {block:?}"));
159 1
160 })),
161 )));
162
163 commands.register(literal("pathfinderstate").executes(|ctx: &Ctx| {
164 let source = ctx.source.lock();
165 let pathfinder = source.bot.get_component::<Pathfinder>();
166 let Some(pathfinder) = pathfinder else {
167 source.reply("I don't have the Pathfinder component");
168 return 1;
169 };
170 source.reply(format!(
171 "pathfinder.is_calculating: {}",
172 pathfinder.is_calculating
173 ));
174
175 let executing_path = source.bot.get_component::<ExecutingPath>();
176 let Some(executing_path) = executing_path else {
177 source.reply("I'm not executing a path");
178 return 1;
179 };
180 source.reply(format!(
181 "is_path_partial: {}, path.len: {}, queued_path.len: {}",
182 executing_path.is_path_partial,
183 executing_path.path.len(),
184 if let Some(queued) = &executing_path.queued_path {
185 queued.len().to_string()
186 } else {
187 "n/a".to_owned()
188 },
189 ));
190 1
191 }));
192 commands.register(literal("pathfindermoves").executes(|ctx: &Ctx| {
193 let source = ctx.source.lock();
194
195 let Some(entity) = source.entity() else {
196 source.reply("You aren't in render distance!");
197 return 0;
198 };
199 let position = entity.position();
200 let position = BlockPos::from(position);
201
202 let mut edges = Vec::new();
203 let cached_world = CachedWorld::new(source.bot.world(), position);
204 let mining_cache = MiningCache::new(Some(Menu::Player(inventory::Player::default())));
205 let custom_state = CustomPathfinderStateRef::default();
206
207 azalea::pathfinder::moves::default_move(
208 &mut MovesCtx {
209 edges: &mut edges,
210 world: &cached_world,
211 mining_cache: &mining_cache,
212 custom_state: &custom_state,
213 },
214 RelBlockPos::from_origin(position, position),
215 );
216
217 if edges.is_empty() {
218 source.reply("No possible moves.");
219 } else {
220 source.reply("Moves:");
221 for (i, edge) in edges.iter().enumerate() {
222 source.reply(format!("{}) {edge:?}", i + 1));
223 }
224 }
225
226 1
227 }));
228
229 commands.register(literal("startuseitem").executes(|ctx: &Ctx| {
230 let source = ctx.source.lock();
231 source.bot.start_use_item();
232 source.reply("Ok!");
233 1
234 }));
235 commands.register(literal("maxstacksize").executes(|ctx: &Ctx| {
236 let source = ctx.source.lock();
237 let max_stack_size = source
238 .bot
239 .get_held_item()
240 .get_component::<MaxStackSize>()
241 .map_or(-1, |s| s.count);
242 source.reply(format!("{max_stack_size}"));
243 1
244 }));
245
246 commands.register(literal("dimensions").executes(|ctx: &Ctx| {
247 let source = ctx.source.lock();
248 let bot_dimensions = source.bot.dimensions();
249 source.reply(format!("{bot_dimensions:?}"));
250 1
251 }));
252
253 commands.register(literal("players").executes(|ctx: &Ctx| {
254 let source = ctx.source.lock();
255 let player_entities = source
256 .bot
257 .nearest_entities_by::<(), With<metadata::Player>>(|_: ()| true);
258 let tab_list = source.bot.tab_list();
259 for player_entity in player_entities {
260 let uuid = player_entity.uuid();
261 source.reply(format!(
262 "{} - {} ({:?})",
263 player_entity.id(),
264 tab_list.get(&uuid).map_or("?", |p| p.profile.name.as_str()),
265 uuid
266 ));
267 }
268 1
269 }));
270
271 commands.register(literal("enchants").executes(|ctx: &Ctx| {
272 let source = ctx.source.lock();
273 source.bot.with_registry_holder(|r| {
274 let enchants = &r.enchantment;
275 println!("enchants: {enchants:?}");
276 });
277 1
278 }));
279
280 commands.register(literal("attributes").executes(|ctx: &Ctx| {
281 let source = ctx.source.lock();
282 let attributes = source.bot.attributes();
283 println!("attributes: {attributes:?}");
284 1
285 }));
286
287 commands.register(literal("debugecsleak").executes(|ctx: &Ctx| {
288 let source = ctx.source.lock();
289
290 source.reply("Ok!");
291
292
293
294 source.bot.disconnect();
295
296 let ecs = source.bot.ecs.clone();
297 thread::spawn(move || {
298 thread::sleep(Duration::from_secs(1));
299 // dump the ecs
300
301 let mut ecs = ecs.write();
302
303 let report_path = env::temp_dir().join("azalea-ecs-leak-report.txt");
304 let mut report = File::create(&report_path).unwrap();
305
306 let mut query = ecs.query::<EntityRef>();
307 for entity in query.iter(& ecs) {
308 writeln!(report, "Entity: {}", entity.id()).unwrap();
309 let archetype = entity.archetype();
310 let component_count = archetype.component_count();
311
312 let component_names = archetype
313 .components()
314 .iter()
315 .map(|c| ecs.components().get_info(*c).unwrap().name().to_string())
316 .collect::<Vec<_>>();
317 writeln!(
318 report,
319 "- {component_count} components: {}",
320 component_names.join(", ")
321 )
322 .unwrap();
323 }
324
325 writeln!(report).unwrap();
326
327
328 for (info, _) in ecs.iter_resources() {
329 let name = info.name().to_string();
330 writeln!(report, "Resource: {name}").unwrap();
331 // writeln!(report, "- Size: {} bytes",
332 // info.layout().size()).unwrap();
333
334 match name.as_ref() {
335 "azalea_world::container::Worlds" => {
336 let worlds = ecs.resource::<Worlds>();
337
338 for (world_name, world) in &worlds.map {
339 writeln!(report, "- Name: {world_name}").unwrap();
340 writeln!(report, "- Reference count: {}", world.strong_count())
341 .unwrap();
342 if let Some(world) = world.upgrade() {
343 let world = world.read();
344 let strong_chunks = world
345 .chunks
346 .map
347 .iter()
348 .filter(|(_, v)| v.strong_count() > 0)
349 .count();
350 writeln!(
351 report,
352 "- Chunks: {} strongly referenced, {} in map",
353 strong_chunks,
354 world.chunks.map.len()
355 )
356 .unwrap();
357 writeln!(
358 report,
359 "- Entities: {}",
360 world.entities_by_chunk.len()
361 )
362 .unwrap();
363 }
364 }
365 }
366 "bevy_ecs::message::Messages<azalea_client::packet::game::ReceivePacketEvent>" => {
367 let events = ecs.resource::<Messages<game::ReceiveGamePacketEvent>>();
368 writeln!(report, "- Event count: {}", events.len()).unwrap();
369 }
370 "bevy_ecs::message::Messages<azalea_client::chunks::ReceiveChunkEvent>" => {
371 let events = ecs.resource::<Messages<ReceiveChunkEvent>>();
372 writeln!(report, "- Event count: {}", events.len()).unwrap();
373 }
374
375 _ => {}
376 }
377 }
378
379 println!("\x1b[1mWrote report to {}\x1b[m", report_path.display());
380 });
381
382 1
383 }));
384
385 commands.register(literal("exit").executes(|ctx: &Ctx| {
386 let source = ctx.source.lock();
387 source.reply("bye!");
388
389 source.bot.disconnect();
390
391 let source = ctx.source.clone();
392 thread::spawn(move || {
393 thread::sleep(Duration::from_secs(1));
394
395 source
396 .lock()
397 .bot
398 .ecs
399 .write()
400 .write_message(AppExit::Success);
401 });
402
403 1
404 }));
405}Sourcepub fn update(&mut self, new: LookDirection)
pub fn update(&mut self, new: LookDirection)
Update this look direction to the new value.
This handles relative rotations correctly and with the default Minecraft sensitivity to avoid triggering anticheats.
Sourcepub fn update_y_rot(&mut self, new_y_rot: f32)
pub fn update_y_rot(&mut self, new_y_rot: f32)
Update the y_rot (yaw) to the given value, in degrees.
This is a shortcut for Self::update while keeping the x_rot the
same.
Sourcepub fn update_x_rot(&mut self, new_x_rot: f32)
pub fn update_x_rot(&mut self, new_x_rot: f32)
Update the x_rot (pitch) to the given value, in degrees.
This is a shortcut for Self::update while keeping the y_rot the
same.
Sourcepub fn update_with_sensitivity(&mut self, new: LookDirection, sensitivity: f32)
pub fn update_with_sensitivity(&mut self, new: LookDirection, sensitivity: f32)
Update this look direction to the new value, using the given sensitivity value.
Consider using Self::update instead, which uses 1.0 as the
sensitivity (equivalent to 100% sensitivity in Minecraft).
Sourcepub fn clamped(self) -> Self
pub fn clamped(self) -> Self
Force the Self::x_rot to be between -90 and 90 degrees, and return
the new look direction.
Trait Implementations§
Source§impl AzBuf for LookDirection
impl AzBuf for LookDirection
fn azalea_write(&self, buf: &mut impl Write) -> Result<(), Error>
fn azalea_read(buf: &mut Cursor<&[u8]>) -> Result<Self, BufReadError>
Source§impl Clone for LookDirection
impl Clone for LookDirection
Source§fn clone(&self) -> LookDirection
fn clone(&self) -> LookDirection
1.0.0 · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
source. Read moreSource§impl Component for LookDirection
impl Component for LookDirection
Source§const STORAGE_TYPE: StorageType = bevy_ecs::component::StorageType::Table
const STORAGE_TYPE: StorageType = bevy_ecs::component::StorageType::Table
Source§type Mutability = Mutable
type Mutability = Mutable
Component<Mutability = Mutable>],
while immutable components will instead have [Component<Mutability = Immutable>]. Read moreSource§fn register_required_components(
_requiree: ComponentId,
required_components: &mut RequiredComponentsRegistrator<'_, '_>,
)
fn register_required_components( _requiree: ComponentId, required_components: &mut RequiredComponentsRegistrator<'_, '_>, )
Source§fn clone_behavior() -> ComponentCloneBehavior
fn clone_behavior() -> ComponentCloneBehavior
Source§fn relationship_accessor() -> Option<ComponentRelationshipAccessor<Self>>
fn relationship_accessor() -> Option<ComponentRelationshipAccessor<Self>>
ComponentRelationshipAccessor] required for working with relationships in dynamic contexts. Read more§fn on_add() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
fn on_add() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
on_add [ComponentHook] for this [Component] if one is defined.§fn on_insert() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
fn on_insert() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
on_insert [ComponentHook] for this [Component] if one is defined.§fn on_replace() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
fn on_replace() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
on_replace [ComponentHook] for this [Component] if one is defined.§fn on_remove() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
fn on_remove() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
on_remove [ComponentHook] for this [Component] if one is defined.§fn on_despawn() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
fn on_despawn() -> Option<for<'w> fn(DeferredWorld<'w>, HookContext)>
on_despawn [ComponentHook] for this [Component] if one is defined.§fn map_entities<E>(_this: &mut Self, _mapper: &mut E)where
E: EntityMapper,
fn map_entities<E>(_this: &mut Self, _mapper: &mut E)where
E: EntityMapper,
EntityMapper]. This is used to remap entities in contexts like scenes and entity cloning.
When deriving [Component], this is populated by annotating fields containing entities with #[entities] Read moreSource§impl Debug for LookDirection
impl Debug for LookDirection
Source§impl Default for LookDirection
impl Default for LookDirection
Source§fn default() -> LookDirection
fn default() -> LookDirection
Source§impl From<LookDirection> for (f32, f32)
impl From<LookDirection> for (f32, f32)
Source§fn from(value: LookDirection) -> Self
fn from(value: LookDirection) -> Self
Source§impl Hash for LookDirection
impl Hash for LookDirection
Source§impl PartialEq for LookDirection
impl PartialEq for LookDirection
impl Copy for LookDirection
impl Eq for LookDirection
impl StructuralPartialEq for LookDirection
Auto Trait Implementations§
impl Freeze for LookDirection
impl RefUnwindSafe for LookDirection
impl Send for LookDirection
impl Sync for LookDirection
impl Unpin for LookDirection
impl UnwindSafe for LookDirection
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
§impl<C> Bundle for Cwhere
C: Component,
impl<C> Bundle for Cwhere
C: Component,
fn component_ids( components: &mut ComponentsRegistrator<'_>, ) -> impl Iterator<Item = ComponentId> + use<C>
§fn get_component_ids(
components: &Components,
) -> impl Iterator<Item = Option<ComponentId>>
fn get_component_ids( components: &Components, ) -> impl Iterator<Item = Option<ComponentId>>
Bundle]’s component ids. This will be None if the component has not been registered.§impl<C> BundleFromComponents for Cwhere
C: Component,
impl<C> BundleFromComponents for Cwhere
C: Component,
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
§impl<T> Downcast for Twhere
T: Any,
impl<T> Downcast for Twhere
T: Any,
§fn into_any(self: Box<T>) -> Box<dyn Any>
fn into_any(self: Box<T>) -> Box<dyn Any>
Box<dyn Trait> (where Trait: Downcast) to Box<dyn Any>, which can then be
downcast into Box<dyn ConcreteType> where ConcreteType implements Trait.§fn into_any_rc(self: Rc<T>) -> Rc<dyn Any>
fn into_any_rc(self: Rc<T>) -> Rc<dyn Any>
Rc<Trait> (where Trait: Downcast) to Rc<Any>, which can then be further
downcast into Rc<ConcreteType> where ConcreteType implements Trait.§fn as_any(&self) -> &(dyn Any + 'static)
fn as_any(&self) -> &(dyn Any + 'static)
&Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot
generate &Any’s vtable from &Trait’s.§fn as_any_mut(&mut self) -> &mut (dyn Any + 'static)
fn as_any_mut(&mut self) -> &mut (dyn Any + 'static)
&mut Trait (where Trait: Downcast) to &Any. This is needed since Rust cannot
generate &mut Any’s vtable from &mut Trait’s.§impl<T> DowncastSend for T
impl<T> DowncastSend for T
§impl<T> DynEq for T
impl<T> DynEq for T
§impl<C> DynamicBundle for Cwhere
C: Component,
impl<C> DynamicBundle for Cwhere
C: Component,
§unsafe fn get_components(
ptr: MovingPtr<'_, C>,
func: &mut impl FnMut(StorageType, OwningPtr<'_>),
) -> <C as DynamicBundle>::Effect
unsafe fn get_components( ptr: MovingPtr<'_, C>, func: &mut impl FnMut(StorageType, OwningPtr<'_>), ) -> <C as DynamicBundle>::Effect
§unsafe fn apply_effect(
_ptr: MovingPtr<'_, MaybeUninit<C>>,
_entity: &mut EntityWorldMut<'_>,
)
unsafe fn apply_effect( _ptr: MovingPtr<'_, MaybeUninit<C>>, _entity: &mut EntityWorldMut<'_>, )
§impl<Q, K> Equivalent<K> for Q
impl<Q, K> Equivalent<K> for Q
§fn equivalent(&self, key: &K) -> bool
fn equivalent(&self, key: &K) -> bool
key and return true if they are equal.§impl<T> FromWorld for Twhere
T: Default,
impl<T> FromWorld for Twhere
T: Default,
§fn from_world(_world: &mut World) -> T
fn from_world(_world: &mut World) -> T
Creates Self using default().