mirror of
https://github.com/mat-1/azalea.git
synced 2025-08-02 23:44:38 +00:00
improve docs
This commit is contained in:
parent
f747e6df0c
commit
e0cb50fea0
10 changed files with 113 additions and 16 deletions
|
@ -126,8 +126,6 @@ impl Client {
|
|||
|
||||
/// Send a message in chat.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// # use azalea::prelude::*;
|
||||
/// # use parking_lot::Mutex;
|
||||
|
|
|
@ -351,7 +351,7 @@ impl Client {
|
|||
Ok(())
|
||||
}
|
||||
|
||||
/// Disconnect from the server, ending all tasks.
|
||||
/// Disconnect this client from the server, ending all tasks.
|
||||
pub async fn disconnect(&self) -> Result<(), std::io::Error> {
|
||||
if let Err(e) = self.write_conn.lock().await.shutdown().await {
|
||||
warn!(
|
||||
|
@ -1111,6 +1111,14 @@ impl Client {
|
|||
|
||||
/// Tell the server we changed our game options (i.e. render distance, main hand).
|
||||
/// If this is not set before the login packet, the default will be sent.
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// bot.set_client_information(ClientInformation {
|
||||
/// view_distance: 2,
|
||||
/// ..Default::default()
|
||||
/// })
|
||||
/// .await?;
|
||||
/// ```
|
||||
pub async fn set_client_information(
|
||||
&self,
|
||||
client_information: ServerboundClientInformationPacket,
|
||||
|
|
|
@ -262,6 +262,10 @@ impl Client {
|
|||
/// Start walking in the given direction. To sprint, use
|
||||
/// [`Client::sprint`]. To stop walking, call walk with
|
||||
/// `WalkDirection::None`.
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// bot.walk(WalkDirection::Forward);
|
||||
/// ```
|
||||
pub fn walk(&mut self, direction: WalkDirection) {
|
||||
{
|
||||
let mut physics_state = self.physics_state.lock();
|
||||
|
|
|
@ -43,7 +43,7 @@ pub struct WeakChunkStorage {
|
|||
}
|
||||
|
||||
/// A storage of potentially infinite chunks in a world. Chunks are stored as
|
||||
/// an Arc<Mutex> so they can be shared across threads.
|
||||
/// an `Arc<Mutex>` so they can be shared across threads.
|
||||
pub struct ChunkStorage {
|
||||
pub height: u32,
|
||||
pub min_y: i32,
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
//! https://minecraft.fandom.com/wiki/Attribute
|
||||
//! <https://minecraft.fandom.com/wiki/Attribute>
|
||||
|
||||
use std::{
|
||||
collections::HashMap,
|
||||
|
|
|
@ -119,7 +119,7 @@ impl PartialEntityStorage {
|
|||
/// Whether the entity with the given id is in the shared storage (i.e.
|
||||
/// it's possible we don't see the entity but something else in the shared
|
||||
/// storage does). To check whether the entity is being loaded by this
|
||||
/// storage, use [`EntityStorage::limited_contains_id`].
|
||||
/// storage, use [`PartialEntityStorage::limited_contains_id`].
|
||||
#[inline]
|
||||
pub fn contains_id(&self, id: &u32) -> bool {
|
||||
self.shared.read().data_by_id.contains_key(id)
|
||||
|
@ -345,6 +345,12 @@ impl WeakEntityStorage {
|
|||
pub fn entities(&self) -> std::collections::hash_map::Values<'_, u32, Weak<EntityData>> {
|
||||
self.data_by_id.values()
|
||||
}
|
||||
|
||||
/// Whether the entity with the given id is in the shared storage.
|
||||
#[inline]
|
||||
pub fn contains_id(&self, id: &u32) -> bool {
|
||||
self.data_by_id.contains_key(id)
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
|
|
@ -15,7 +15,7 @@ async fn main() {
|
|||
account,
|
||||
address: "localhost",
|
||||
state: State::default(),
|
||||
plugins: plugins![autoeat::Plugin::default(), pathfinder::Plugin::default(),],
|
||||
plugins: plugins![autoeat::Plugin, pathfinder::Plugin],
|
||||
handle,
|
||||
})
|
||||
.await
|
||||
|
|
|
@ -15,7 +15,7 @@ async fn main() {
|
|||
swarm_state: State::default(),
|
||||
state: State::default(),
|
||||
|
||||
swarm_plugins: plugins![pathfinder::Plugin::default()],
|
||||
swarm_plugins: plugins![pathfinder::Plugin],
|
||||
plugins: plugins![],
|
||||
|
||||
handle: Box::new(handle),
|
||||
|
|
|
@ -8,8 +8,10 @@ use thiserror::Error;
|
|||
/// that implement [`Plugin`].
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// plugins![azalea_pathfinder::Plugin::default()];
|
||||
/// plugins![azalea_pathfinder::Plugin];
|
||||
/// ```
|
||||
///
|
||||
/// [`Plugin`]: crate::Plugin
|
||||
#[macro_export]
|
||||
macro_rules! plugins {
|
||||
($($plugin:expr),*) => {
|
||||
|
@ -25,7 +27,7 @@ macro_rules! plugins {
|
|||
|
||||
/// The options that are passed to [`azalea::start`].
|
||||
///
|
||||
/// [`azalea::start`]: crate::start
|
||||
/// [`azalea::start`]: crate::start()
|
||||
pub struct Options<S, A, Fut>
|
||||
where
|
||||
A: TryInto<ServerAddress>,
|
||||
|
@ -44,7 +46,7 @@ where
|
|||
/// for this field.
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// plugins![azalea_pathfinder::Plugin::default()]
|
||||
/// plugins![azalea_pathfinder::Plugin]
|
||||
/// ```
|
||||
pub plugins: Plugins,
|
||||
/// A struct that contains the data that you want your bot to remember
|
||||
|
@ -94,7 +96,7 @@ pub enum StartError {
|
|||
/// account,
|
||||
/// address: "localhost",
|
||||
/// state: State::default(),
|
||||
/// plugins: plugins![azalea_pathfinder::Plugin::default()],
|
||||
/// plugins: plugins![azalea_pathfinder::Plugin],
|
||||
/// handle,
|
||||
/// }).await;
|
||||
/// ```
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
/// Swarms are a way to conveniently control many bots.
|
||||
mod chat;
|
||||
mod plugins;
|
||||
|
||||
|
@ -17,11 +18,11 @@ use std::{future::Future, net::SocketAddr, sync::Arc, time::Duration};
|
|||
use thiserror::Error;
|
||||
use tokio::sync::mpsc::{self, UnboundedSender};
|
||||
|
||||
/// A helper macro that generates a [`Plugins`] struct from a list of objects
|
||||
/// that implement [`Plugin`].
|
||||
/// A helper macro that generates a [`SwarmPlugins`] struct from a list of objects
|
||||
/// that implement [`SwarmPlugin`].
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// plugins![azalea_pathfinder::Plugin::default()];
|
||||
/// swarm_plugins![azalea_pathfinder::Plugin];
|
||||
/// ```
|
||||
#[macro_export]
|
||||
macro_rules! swarm_plugins {
|
||||
|
@ -41,6 +42,74 @@ macro_rules! swarm_plugins {
|
|||
///
|
||||
/// The `S` type parameter is the type of the state for individual bots.
|
||||
/// It's used to make the [`Swarm::add`] function work.
|
||||
///
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// use azalea::{prelude::*, Swarm, SwarmEvent};
|
||||
/// use azalea::{Account, Client, Event};
|
||||
/// use std::time::Duration;
|
||||
///
|
||||
/// #[derive(Default, Clone)]
|
||||
/// struct State {}
|
||||
///
|
||||
/// #[derive(Default, Clone)]
|
||||
/// struct SwarmState {}
|
||||
///
|
||||
/// #[tokio::main]
|
||||
/// async fn main() -> anyhow::Result<()> {
|
||||
/// let mut accounts = Vec::new();
|
||||
/// let mut states = Vec::new();
|
||||
///
|
||||
/// for i in 0..10 {
|
||||
/// accounts.push(Account::offline(&format!("bot{}", i)));
|
||||
/// states.push(State::default());
|
||||
/// }
|
||||
///
|
||||
/// loop {
|
||||
/// let e = azalea::start_swarm(azalea::SwarmOptions {
|
||||
/// accounts: accounts.clone(),
|
||||
/// address: "localhost",
|
||||
///
|
||||
/// states: states.clone(),
|
||||
/// swarm_state: SwarmState::default(),
|
||||
///
|
||||
/// plugins: plugins![],
|
||||
/// swarm_plugins: swarm_plugins![],
|
||||
///
|
||||
/// handle,
|
||||
/// swarm_handle,
|
||||
///
|
||||
/// join_delay: Some(Duration::from_millis(1000)),
|
||||
/// })
|
||||
/// .await;
|
||||
/// println!("{e:?}");
|
||||
/// }
|
||||
/// }
|
||||
///
|
||||
/// async fn handle(bot: Client, event: Event, _state: State) -> anyhow::Result<()> {
|
||||
/// match &event {
|
||||
/// _ => {}
|
||||
/// }
|
||||
/// Ok(())
|
||||
/// }
|
||||
///
|
||||
/// async fn swarm_handle(
|
||||
/// mut swarm: Swarm<State>,
|
||||
/// event: SwarmEvent,
|
||||
/// _state: SwarmState,
|
||||
/// ) -> anyhow::Result<()> {
|
||||
/// match &event {
|
||||
/// SwarmEvent::Disconnect(account) => {
|
||||
/// tokio::time::sleep(Duration::from_secs(5)).await;
|
||||
/// swarm.add(account, State::default()).await?;
|
||||
/// }
|
||||
/// SwarmEvent::Chat(m) => {
|
||||
/// println!("{}", m.message().to_ansi(None));
|
||||
/// }
|
||||
/// _ => {}
|
||||
/// }
|
||||
/// Ok(())
|
||||
/// }
|
||||
#[derive(Clone)]
|
||||
pub struct Swarm<S> {
|
||||
bot_datas: Arc<Mutex<Vec<(Client, S)>>>,
|
||||
|
@ -76,7 +145,7 @@ pub type SwarmHandleFn<Fut, S, SS> = fn(Swarm<S>, SwarmEvent, SS) -> Fut;
|
|||
|
||||
/// The options that are passed to [`azalea::start_swarm`].
|
||||
///
|
||||
/// [`azalea::start`]: crate::start_swarm
|
||||
/// [`azalea::start_swarm`]: crate::start_swarm()
|
||||
pub struct SwarmOptions<S, SS, A, Fut, SwarmFut>
|
||||
where
|
||||
A: TryInto<ServerAddress>,
|
||||
|
@ -309,6 +378,9 @@ where
|
|||
|
||||
/// Add a new account to the swarm, retrying if it couldn't join. This will
|
||||
/// run forever until the bot joins or the task is aborted.
|
||||
///
|
||||
/// Exponential backoff means if it fails joining it will initially wait 10
|
||||
/// seconds, then 20, then 40, up to 2 minutes.
|
||||
pub async fn add_with_exponential_backoff(&mut self, account: &Account, state: S) -> Client {
|
||||
let mut disconnects = 0;
|
||||
loop {
|
||||
|
@ -334,6 +406,13 @@ where
|
|||
type Item = (Client, S);
|
||||
type IntoIter = std::vec::IntoIter<Self::Item>;
|
||||
|
||||
/// Iterate over the bots and their states in this swarm.
|
||||
///
|
||||
/// ```rust,no_run
|
||||
/// for (bot, state) in swarm {
|
||||
/// // ...
|
||||
/// }
|
||||
/// ```
|
||||
fn into_iter(self) -> Self::IntoIter {
|
||||
self.bot_datas.lock().clone().into_iter()
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue