Add Summon Command
Also refactor some things: - Remove cmd_ prefix from commands - Remove arg_ prefix from arguments
This commit is contained in:
parent
69cb3bb4f0
commit
2fdf0777f6
@ -40,8 +40,20 @@ pub(crate) fn build() -> TokenStream {
|
|||||||
})
|
})
|
||||||
.collect::<TokenStream>();
|
.collect::<TokenStream>();
|
||||||
|
|
||||||
|
let type_from_name = json
|
||||||
|
.iter()
|
||||||
|
.map(|sound| {
|
||||||
|
let id = &sound.0;
|
||||||
|
let name = ident(sound.0.to_pascal_case());
|
||||||
|
|
||||||
quote! {
|
quote! {
|
||||||
#[derive(Clone, Copy)]
|
#id => Some(Self::#name),
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.collect::<TokenStream>();
|
||||||
|
|
||||||
|
quote! {
|
||||||
|
#[derive(Clone, Copy, Debug)]
|
||||||
#[repr(u8)]
|
#[repr(u8)]
|
||||||
pub enum EntityType {
|
pub enum EntityType {
|
||||||
#variants
|
#variants
|
||||||
@ -54,6 +66,13 @@ pub(crate) fn build() -> TokenStream {
|
|||||||
_ => None
|
_ => None
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn from_name(name: &str) -> Option<Self> {
|
||||||
|
match name {
|
||||||
|
#type_from_name
|
||||||
|
_ => None
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -76,7 +76,6 @@ async-trait = "0.1.83"
|
|||||||
|
|
||||||
# plugins
|
# plugins
|
||||||
libloading = "0.8.5"
|
libloading = "0.8.5"
|
||||||
oneshot = "0.1.8"
|
|
||||||
[build-dependencies]
|
[build-dependencies]
|
||||||
git-version = "0.3.9"
|
git-version = "0.3.9"
|
||||||
# This makes it so the entire project doesn't recompile on each build on linux.
|
# This makes it so the entire project doesn't recompile on each build on linux.
|
||||||
|
|||||||
@ -49,8 +49,8 @@ impl ArgumentConsumer for BlockArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for BlockArgumentConsumer {
|
impl DefaultNameArgConsumer for BlockArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"block".to_string()
|
"block"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -62,8 +62,8 @@ impl ArgumentConsumer for BossbarColorArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for BossbarColorArgumentConsumer {
|
impl DefaultNameArgConsumer for BossbarColorArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"color".to_string()
|
"color"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -66,8 +66,8 @@ impl ArgumentConsumer for BossbarStyleArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for BossbarStyleArgumentConsumer {
|
impl DefaultNameArgConsumer for BossbarStyleArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"style".to_string()
|
"style"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -238,8 +238,8 @@ impl<T: ToFromNumber> DefaultNameArgConsumer for BoundedNumArgumentConsumer<T>
|
|||||||
where
|
where
|
||||||
Self: ArgumentConsumer,
|
Self: ArgumentConsumer,
|
||||||
{
|
{
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
// setting a single default name for all BoundedNumArgumentConsumer variants is probably a bad idea since it would lead to confusion
|
// setting a single default name for all BoundedNumArgumentConsumer variants is probably a bad idea since it would lead to confusion
|
||||||
self.name.expect("Only use *_default variants of methods with a BoundedNumArgumentConsumer that has a name.").to_string()
|
self.name.expect("Only use *_default variants of methods with a BoundedNumArgumentConsumer that has a name.")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -65,8 +65,8 @@ impl ArgumentConsumer for CommandTreeArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for CommandTreeArgumentConsumer {
|
impl DefaultNameArgConsumer for CommandTreeArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"cmd".to_string()
|
"cmd"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -10,7 +10,7 @@ use crate::entity::player::Player;
|
|||||||
use crate::server::Server;
|
use crate::server::Server;
|
||||||
|
|
||||||
use super::super::args::ArgumentConsumer;
|
use super::super::args::ArgumentConsumer;
|
||||||
use super::arg_players::PlayersArgumentConsumer;
|
use super::players::PlayersArgumentConsumer;
|
||||||
use super::{Arg, DefaultNameArgConsumer, FindArg, GetClientSideArgParser};
|
use super::{Arg, DefaultNameArgConsumer, FindArg, GetClientSideArgParser};
|
||||||
|
|
||||||
/// todo: implement (currently just calls [`super::arg_player::PlayerArgumentConsumer`])
|
/// todo: implement (currently just calls [`super::arg_player::PlayerArgumentConsumer`])
|
||||||
@ -55,8 +55,8 @@ impl ArgumentConsumer for EntitiesArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for EntitiesArgumentConsumer {
|
impl DefaultNameArgConsumer for EntitiesArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"targets".to_string()
|
"targets"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -77,8 +77,8 @@ impl ArgumentConsumer for EntityArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for EntityArgumentConsumer {
|
impl DefaultNameArgConsumer for EntityArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"target".to_string()
|
"target"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -57,8 +57,8 @@ impl ArgumentConsumer for GamemodeArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for GamemodeArgumentConsumer {
|
impl DefaultNameArgConsumer for GamemodeArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"gamemode".to_string()
|
"gamemode"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -47,8 +47,8 @@ impl ArgumentConsumer for ItemArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for ItemArgumentConsumer {
|
impl DefaultNameArgConsumer for ItemArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"item".to_string()
|
"item"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -55,8 +55,8 @@ impl ArgumentConsumer for MsgArgConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for MsgArgConsumer {
|
impl DefaultNameArgConsumer for MsgArgConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"msg".to_string()
|
"msg"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1,7 +1,7 @@
|
|||||||
use std::{collections::HashMap, hash::Hash, sync::Arc};
|
use std::{collections::HashMap, hash::Hash, sync::Arc};
|
||||||
|
|
||||||
use arg_bounded_num::{NotInBounds, Number};
|
|
||||||
use async_trait::async_trait;
|
use async_trait::async_trait;
|
||||||
|
use bounded_num::{NotInBounds, Number};
|
||||||
use pumpkin_protocol::client::play::{ArgumentType, CommandSuggestion, SuggestionProviders};
|
use pumpkin_protocol::client::play::{ArgumentType, CommandSuggestion, SuggestionProviders};
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
use pumpkin_util::{
|
use pumpkin_util::{
|
||||||
@ -17,27 +17,28 @@ use super::{
|
|||||||
use crate::world::bossbar::{BossbarColor, BossbarDivisions};
|
use crate::world::bossbar::{BossbarColor, BossbarDivisions};
|
||||||
use crate::{entity::player::Player, server::Server};
|
use crate::{entity::player::Player, server::Server};
|
||||||
|
|
||||||
pub mod arg_block;
|
pub mod block;
|
||||||
pub mod arg_bool;
|
pub mod bool;
|
||||||
pub mod arg_bossbar_color;
|
pub mod bossbar_color;
|
||||||
pub mod arg_bossbar_style;
|
pub mod bossbar_style;
|
||||||
pub mod arg_bounded_num;
|
pub mod bounded_num;
|
||||||
pub mod arg_command;
|
pub mod command;
|
||||||
pub mod arg_entities;
|
|
||||||
pub mod arg_entity;
|
|
||||||
pub mod arg_gamemode;
|
|
||||||
pub mod arg_item;
|
|
||||||
pub mod arg_message;
|
|
||||||
pub mod arg_players;
|
|
||||||
pub mod arg_position_2d;
|
|
||||||
pub mod arg_position_3d;
|
|
||||||
pub mod arg_position_block;
|
|
||||||
pub mod arg_resource_location;
|
|
||||||
pub mod arg_rotation;
|
|
||||||
pub mod arg_simple;
|
|
||||||
pub mod arg_sound;
|
|
||||||
pub mod arg_textcomponent;
|
|
||||||
mod coordinate;
|
mod coordinate;
|
||||||
|
pub mod entities;
|
||||||
|
pub mod entity;
|
||||||
|
pub mod gamemode;
|
||||||
|
pub mod item;
|
||||||
|
pub mod message;
|
||||||
|
pub mod players;
|
||||||
|
pub mod position_2d;
|
||||||
|
pub mod position_3d;
|
||||||
|
pub mod position_block;
|
||||||
|
pub mod resource_location;
|
||||||
|
pub mod rotation;
|
||||||
|
pub mod simple;
|
||||||
|
pub mod sound;
|
||||||
|
pub mod summonable_entities;
|
||||||
|
pub mod textcomponent;
|
||||||
|
|
||||||
/// see [`crate::commands::tree_builder::argument`]
|
/// see [`crate::commands::tree_builder::argument`]
|
||||||
#[async_trait]
|
#[async_trait]
|
||||||
@ -68,7 +69,7 @@ pub trait GetClientSideArgParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub trait DefaultNameArgConsumer: ArgumentConsumer {
|
pub trait DefaultNameArgConsumer: ArgumentConsumer {
|
||||||
fn default_name(&self) -> String;
|
fn default_name(&self) -> &str;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
@ -120,7 +121,7 @@ pub(crate) trait FindArgDefaultName<'a, T> {
|
|||||||
|
|
||||||
impl<'a, T, C: FindArg<'a, Data = T> + DefaultNameArgConsumer> FindArgDefaultName<'a, T> for C {
|
impl<'a, T, C: FindArg<'a, Data = T> + DefaultNameArgConsumer> FindArgDefaultName<'a, T> for C {
|
||||||
fn find_arg_default_name(&self, args: &'a ConsumedArgs) -> Result<T, CommandError> {
|
fn find_arg_default_name(&self, args: &'a ConsumedArgs) -> Result<T, CommandError> {
|
||||||
C::find_arg(args, &self.default_name())
|
C::find_arg(args, self.default_name())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -71,8 +71,8 @@ impl ArgumentConsumer for PlayersArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for PlayersArgumentConsumer {
|
impl DefaultNameArgConsumer for PlayersArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"player".to_string()
|
"player"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -71,8 +71,8 @@ impl MaybeRelativePosition2D {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for Position2DArgumentConsumer {
|
impl DefaultNameArgConsumer for Position2DArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"pos2d".to_string()
|
"pos"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -74,8 +74,8 @@ impl MaybeRelativePosition3D {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for Position3DArgumentConsumer {
|
impl DefaultNameArgConsumer for Position3DArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"pos".to_string()
|
"pos"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -75,8 +75,8 @@ impl MaybeRelativeBlockPos {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for BlockPosArgumentConsumer {
|
impl DefaultNameArgConsumer for BlockPosArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"block_pos".to_string()
|
"block_pos"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -58,8 +58,8 @@ impl ArgumentConsumer for ResourceLocationArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for ResourceLocationArgumentConsumer {
|
impl DefaultNameArgConsumer for ResourceLocationArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"id".to_string()
|
"id"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -59,8 +59,8 @@ impl ArgumentConsumer for RotationArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for RotationArgumentConsumer {
|
impl DefaultNameArgConsumer for RotationArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"rotation".to_string()
|
"rotation"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -47,8 +47,8 @@ impl ArgumentConsumer for SoundArgumentConsumer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultNameArgConsumer for SoundArgumentConsumer {
|
impl DefaultNameArgConsumer for SoundArgumentConsumer {
|
||||||
fn default_name(&self) -> String {
|
fn default_name(&self) -> &'static str {
|
||||||
"available_sounds".to_string()
|
"available_sounds"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
72
pumpkin/src/command/args/summonable_entities.rs
Normal file
72
pumpkin/src/command/args/summonable_entities.rs
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
use async_trait::async_trait;
|
||||||
|
use pumpkin_data::entity::EntityType;
|
||||||
|
use pumpkin_protocol::client::play::{ArgumentType, CommandSuggestion, SuggestionProviders};
|
||||||
|
|
||||||
|
use crate::{command::dispatcher::CommandError, server::Server};
|
||||||
|
|
||||||
|
use super::{
|
||||||
|
super::{
|
||||||
|
args::{ArgumentConsumer, RawArgs},
|
||||||
|
CommandSender,
|
||||||
|
},
|
||||||
|
Arg, DefaultNameArgConsumer, FindArg, GetClientSideArgParser,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub(crate) struct SummonableEntitiesArgumentConsumer;
|
||||||
|
|
||||||
|
impl GetClientSideArgParser for SummonableEntitiesArgumentConsumer {
|
||||||
|
fn get_client_side_parser(&self) -> ArgumentType {
|
||||||
|
ArgumentType::ResourceLocation
|
||||||
|
}
|
||||||
|
|
||||||
|
fn get_client_side_suggestion_type_override(&self) -> Option<SuggestionProviders> {
|
||||||
|
Some(SuggestionProviders::SummonableEntities)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[async_trait]
|
||||||
|
impl ArgumentConsumer for SummonableEntitiesArgumentConsumer {
|
||||||
|
async fn consume<'a>(
|
||||||
|
&'a self,
|
||||||
|
_sender: &CommandSender<'a>,
|
||||||
|
_server: &'a Server,
|
||||||
|
args: &mut RawArgs<'a>,
|
||||||
|
) -> Option<Arg<'a>> {
|
||||||
|
let s = args.pop()?;
|
||||||
|
Some(Arg::Block(s))
|
||||||
|
}
|
||||||
|
|
||||||
|
async fn suggest<'a>(
|
||||||
|
&'a self,
|
||||||
|
_sender: &CommandSender<'a>,
|
||||||
|
_server: &'a Server,
|
||||||
|
_input: &'a str,
|
||||||
|
) -> Result<Option<Vec<CommandSuggestion>>, CommandError> {
|
||||||
|
Ok(None)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl DefaultNameArgConsumer for SummonableEntitiesArgumentConsumer {
|
||||||
|
fn default_name(&self) -> &'static str {
|
||||||
|
"summonable_entities"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> FindArg<'a> for SummonableEntitiesArgumentConsumer {
|
||||||
|
type Data = EntityType;
|
||||||
|
|
||||||
|
fn find_arg(args: &'a super::ConsumedArgs, name: &str) -> Result<Self::Data, CommandError> {
|
||||||
|
match args.get(name) {
|
||||||
|
Some(Arg::Block(name)) => EntityType::from_name(&name.replace("minecraft:", ""))
|
||||||
|
.map_or_else(
|
||||||
|
|| {
|
||||||
|
Err(CommandError::GeneralCommandIssue(format!(
|
||||||
|
"Entity {name} does not exist."
|
||||||
|
)))
|
||||||
|
},
|
||||||
|
Result::Ok,
|
||||||
|
),
|
||||||
|
_ => Err(CommandError::InvalidConsumption(Some(name.to_string()))),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -1,14 +1,14 @@
|
|||||||
use crate::command::args::arg_bool::BoolArgConsumer;
|
use crate::command::args::bool::BoolArgConsumer;
|
||||||
use crate::command::args::arg_bossbar_color::BossbarColorArgumentConsumer;
|
use crate::command::args::bossbar_color::BossbarColorArgumentConsumer;
|
||||||
use crate::command::args::arg_bossbar_style::BossbarStyleArgumentConsumer;
|
use crate::command::args::bossbar_style::BossbarStyleArgumentConsumer;
|
||||||
use crate::command::args::arg_bounded_num::BoundedNumArgumentConsumer;
|
use crate::command::args::bounded_num::BoundedNumArgumentConsumer;
|
||||||
use crate::command::args::arg_players::PlayersArgumentConsumer;
|
use crate::command::args::players::PlayersArgumentConsumer;
|
||||||
use crate::command::args::arg_resource_location::ResourceLocationArgumentConsumer;
|
use crate::command::args::resource_location::ResourceLocationArgumentConsumer;
|
||||||
|
|
||||||
use crate::command::args::{ConsumedArgs, DefaultNameArgConsumer, FindArg, FindArgDefaultName};
|
use crate::command::args::{ConsumedArgs, DefaultNameArgConsumer, FindArg, FindArgDefaultName};
|
||||||
use crate::command::dispatcher::CommandError;
|
use crate::command::dispatcher::CommandError;
|
||||||
|
|
||||||
use crate::command::args::arg_textcomponent::TextComponentArgConsumer;
|
use crate::command::args::textcomponent::TextComponentArgConsumer;
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
use crate::command::tree_builder::{argument, argument_default_name, literal};
|
use crate::command::tree_builder::{argument, argument_default_name, literal};
|
||||||
use crate::command::{CommandExecutor, CommandSender};
|
use crate::command::{CommandExecutor, CommandSender};
|
||||||
@ -5,7 +5,7 @@ use pumpkin_inventory::Container;
|
|||||||
use pumpkin_util::text::color::NamedColor;
|
use pumpkin_util::text::color::NamedColor;
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_entities::EntitiesArgumentConsumer;
|
use crate::command::args::entities::EntitiesArgumentConsumer;
|
||||||
use crate::command::args::{Arg, ConsumedArgs};
|
use crate::command::args::{Arg, ConsumedArgs};
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
use crate::command::tree_builder::{argument, require};
|
use crate::command::tree_builder::{argument, require};
|
||||||
@ -1,6 +1,6 @@
|
|||||||
use crate::{
|
use crate::{
|
||||||
command::{
|
command::{
|
||||||
args::{arg_players::PlayersArgumentConsumer, Arg, ConsumedArgs},
|
args::{players::PlayersArgumentConsumer, Arg, ConsumedArgs},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
tree_builder::argument,
|
tree_builder::argument,
|
||||||
CommandError, CommandExecutor, CommandSender,
|
CommandError, CommandExecutor, CommandSender,
|
||||||
@ -1,5 +1,5 @@
|
|||||||
use crate::command::args::arg_block::BlockArgumentConsumer;
|
use crate::command::args::block::BlockArgumentConsumer;
|
||||||
use crate::command::args::arg_position_block::BlockPosArgumentConsumer;
|
use crate::command::args::position_block::BlockPosArgumentConsumer;
|
||||||
use crate::command::args::{ConsumedArgs, FindArg};
|
use crate::command::args::{ConsumedArgs, FindArg};
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
use crate::command::tree_builder::{argument, literal};
|
use crate::command::tree_builder::{argument, literal};
|
||||||
@ -1,11 +1,11 @@
|
|||||||
use async_trait::async_trait;
|
use async_trait::async_trait;
|
||||||
|
|
||||||
use crate::command::args::arg_gamemode::GamemodeArgumentConsumer;
|
use crate::command::args::gamemode::GamemodeArgumentConsumer;
|
||||||
use crate::command::args::GetCloned;
|
use crate::command::args::GetCloned;
|
||||||
|
|
||||||
use crate::TextComponent;
|
use crate::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_players::PlayersArgumentConsumer;
|
use crate::command::args::players::PlayersArgumentConsumer;
|
||||||
|
|
||||||
use crate::command::args::{Arg, ConsumedArgs};
|
use crate::command::args::{Arg, ConsumedArgs};
|
||||||
use crate::command::dispatcher::CommandError;
|
use crate::command::dispatcher::CommandError;
|
||||||
@ -2,9 +2,9 @@ use async_trait::async_trait;
|
|||||||
use pumpkin_util::text::color::{Color, NamedColor};
|
use pumpkin_util::text::color::{Color, NamedColor};
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_bounded_num::BoundedNumArgumentConsumer;
|
use crate::command::args::bounded_num::BoundedNumArgumentConsumer;
|
||||||
use crate::command::args::arg_item::ItemArgumentConsumer;
|
use crate::command::args::item::ItemArgumentConsumer;
|
||||||
use crate::command::args::arg_players::PlayersArgumentConsumer;
|
use crate::command::args::players::PlayersArgumentConsumer;
|
||||||
use crate::command::args::{ConsumedArgs, FindArg, FindArgDefaultName};
|
use crate::command::args::{ConsumedArgs, FindArg, FindArgDefaultName};
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
use crate::command::tree_builder::{argument, argument_default_name};
|
use crate::command::tree_builder::{argument, argument_default_name};
|
||||||
@ -3,8 +3,8 @@ use pumpkin_util::text::click::ClickEvent;
|
|||||||
use pumpkin_util::text::color::{Color, NamedColor};
|
use pumpkin_util::text::color::{Color, NamedColor};
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_bounded_num::BoundedNumArgumentConsumer;
|
use crate::command::args::bounded_num::BoundedNumArgumentConsumer;
|
||||||
use crate::command::args::arg_command::CommandTreeArgumentConsumer;
|
use crate::command::args::command::CommandTreeArgumentConsumer;
|
||||||
use crate::command::args::{Arg, ConsumedArgs, FindArgDefaultName};
|
use crate::command::args::{Arg, ConsumedArgs, FindArgDefaultName};
|
||||||
use crate::command::dispatcher::CommandError;
|
use crate::command::dispatcher::CommandError;
|
||||||
use crate::command::dispatcher::CommandError::InvalidConsumption;
|
use crate::command::dispatcher::CommandError::InvalidConsumption;
|
||||||
@ -2,8 +2,8 @@ use async_trait::async_trait;
|
|||||||
use pumpkin_util::text::color::NamedColor;
|
use pumpkin_util::text::color::NamedColor;
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_message::MsgArgConsumer;
|
use crate::command::args::message::MsgArgConsumer;
|
||||||
use crate::command::args::arg_players::PlayersArgumentConsumer;
|
use crate::command::args::players::PlayersArgumentConsumer;
|
||||||
use crate::command::args::{Arg, ConsumedArgs};
|
use crate::command::args::{Arg, ConsumedArgs};
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
use crate::command::tree_builder::argument;
|
use crate::command::tree_builder::argument;
|
||||||
@ -2,7 +2,7 @@ use async_trait::async_trait;
|
|||||||
use pumpkin_util::text::color::NamedColor;
|
use pumpkin_util::text::color::NamedColor;
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_entities::EntitiesArgumentConsumer;
|
use crate::command::args::entities::EntitiesArgumentConsumer;
|
||||||
use crate::command::args::{Arg, ConsumedArgs};
|
use crate::command::args::{Arg, ConsumedArgs};
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
use crate::command::tree_builder::{argument, require};
|
use crate::command::tree_builder::{argument, require};
|
||||||
@ -3,7 +3,7 @@ use pumpkin_data::world::EMOTE_COMMAND;
|
|||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::{
|
use crate::command::{
|
||||||
args::{arg_message::MsgArgConsumer, Arg, ConsumedArgs},
|
args::{message::MsgArgConsumer, Arg, ConsumedArgs},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
tree_builder::argument,
|
tree_builder::argument,
|
||||||
CommandError, CommandExecutor, CommandSender,
|
CommandError, CommandExecutor, CommandSender,
|
||||||
@ -1,25 +1,26 @@
|
|||||||
pub mod cmd_bossbar;
|
pub mod bossbar;
|
||||||
pub mod cmd_clear;
|
pub mod clear;
|
||||||
pub mod cmd_deop;
|
pub mod deop;
|
||||||
pub mod cmd_fill;
|
pub mod fill;
|
||||||
pub mod cmd_gamemode;
|
pub mod gamemode;
|
||||||
pub mod cmd_give;
|
pub mod give;
|
||||||
pub mod cmd_help;
|
pub mod help;
|
||||||
pub mod cmd_kick;
|
pub mod kick;
|
||||||
pub mod cmd_kill;
|
pub mod kill;
|
||||||
pub mod cmd_list;
|
pub mod list;
|
||||||
pub mod cmd_me;
|
pub mod me;
|
||||||
pub mod cmd_op;
|
pub mod op;
|
||||||
pub mod cmd_playsound;
|
pub mod playsound;
|
||||||
pub mod cmd_plugin;
|
pub mod plugin;
|
||||||
pub mod cmd_plugins;
|
pub mod plugins;
|
||||||
pub mod cmd_pumpkin;
|
pub mod pumpkin;
|
||||||
pub mod cmd_say;
|
pub mod say;
|
||||||
pub mod cmd_seed;
|
pub mod seed;
|
||||||
pub mod cmd_setblock;
|
pub mod setblock;
|
||||||
pub mod cmd_stop;
|
pub mod stop;
|
||||||
pub mod cmd_teleport;
|
pub mod summon;
|
||||||
pub mod cmd_time;
|
pub mod teleport;
|
||||||
pub mod cmd_title;
|
pub mod time;
|
||||||
pub mod cmd_transfer;
|
pub mod title;
|
||||||
pub mod cmd_worldborder;
|
pub mod transfer;
|
||||||
|
pub mod worldborder;
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
use crate::{
|
use crate::{
|
||||||
command::{
|
command::{
|
||||||
args::{arg_players::PlayersArgumentConsumer, Arg, ConsumedArgs},
|
args::{players::PlayersArgumentConsumer, Arg, ConsumedArgs},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
tree_builder::argument,
|
tree_builder::argument,
|
||||||
CommandError, CommandExecutor, CommandSender,
|
CommandError, CommandExecutor, CommandSender,
|
||||||
@ -3,7 +3,7 @@ use pumpkin_data::sound::SoundCategory;
|
|||||||
use rand::{thread_rng, Rng};
|
use rand::{thread_rng, Rng};
|
||||||
|
|
||||||
use crate::command::{
|
use crate::command::{
|
||||||
args::{arg_sound::SoundArgumentConsumer, ConsumedArgs, FindArg},
|
args::{sound::SoundArgumentConsumer, ConsumedArgs, FindArg},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
tree_builder::argument,
|
tree_builder::argument,
|
||||||
CommandError, CommandExecutor, CommandSender,
|
CommandError, CommandExecutor, CommandSender,
|
||||||
@ -6,7 +6,7 @@ use pumpkin_util::{
|
|||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
command::{
|
command::{
|
||||||
args::{arg_simple::SimpleArgConsumer, Arg, ConsumedArgs},
|
args::{simple::SimpleArgConsumer, Arg, ConsumedArgs},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
tree_builder::{argument, literal, require},
|
tree_builder::{argument, literal, require},
|
||||||
CommandError, CommandExecutor, CommandSender,
|
CommandError, CommandExecutor, CommandSender,
|
||||||
@ -3,7 +3,7 @@ use pumpkin_data::world::SAY_COMMAND;
|
|||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::{
|
use crate::command::{
|
||||||
args::{arg_message::MsgArgConsumer, Arg, ConsumedArgs},
|
args::{message::MsgArgConsumer, Arg, ConsumedArgs},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
tree_builder::argument,
|
tree_builder::argument,
|
||||||
CommandError, CommandExecutor, CommandSender,
|
CommandError, CommandExecutor, CommandSender,
|
||||||
@ -36,19 +36,17 @@ impl CommandExecutor for PumpkinExecutor {
|
|||||||
let seed = (seed as i64).to_string();
|
let seed = (seed as i64).to_string();
|
||||||
|
|
||||||
sender
|
sender
|
||||||
.send_message(
|
.send_message(TextComponent::translate(
|
||||||
TextComponent::text("Seed: [")
|
"commands.seed.success",
|
||||||
.add_child(
|
[TextComponent::text(seed.clone())
|
||||||
TextComponent::text(seed.clone())
|
|
||||||
.hover_event(HoverEvent::show_text(TextComponent::translate(
|
.hover_event(HoverEvent::show_text(TextComponent::translate(
|
||||||
Cow::from("chat.copy.click"),
|
Cow::from("chat.copy.click"),
|
||||||
vec![],
|
vec![],
|
||||||
)))
|
)))
|
||||||
.click_event(ClickEvent::CopyToClipboard(Cow::from(seed)))
|
.click_event(ClickEvent::CopyToClipboard(Cow::from(seed)))
|
||||||
.color_named(NamedColor::Green),
|
.color_named(NamedColor::Green)]
|
||||||
)
|
.into(),
|
||||||
.add_child(TextComponent::text("]")),
|
))
|
||||||
)
|
|
||||||
.await;
|
.await;
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
@ -1,8 +1,8 @@
|
|||||||
use async_trait::async_trait;
|
use async_trait::async_trait;
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_block::BlockArgumentConsumer;
|
use crate::command::args::block::BlockArgumentConsumer;
|
||||||
use crate::command::args::arg_position_block::BlockPosArgumentConsumer;
|
use crate::command::args::position_block::BlockPosArgumentConsumer;
|
||||||
use crate::command::args::{ConsumedArgs, FindArg};
|
use crate::command::args::{ConsumedArgs, FindArg};
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
use crate::command::tree_builder::{argument, literal};
|
use crate::command::tree_builder::{argument, literal};
|
||||||
64
pumpkin/src/command/commands/summon.rs
Normal file
64
pumpkin/src/command/commands/summon.rs
Normal file
@ -0,0 +1,64 @@
|
|||||||
|
use async_trait::async_trait;
|
||||||
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
command::{
|
||||||
|
args::{
|
||||||
|
position_3d::Position3DArgumentConsumer,
|
||||||
|
summonable_entities::SummonableEntitiesArgumentConsumer, ConsumedArgs, FindArg,
|
||||||
|
},
|
||||||
|
tree::CommandTree,
|
||||||
|
tree_builder::argument,
|
||||||
|
CommandError, CommandExecutor, CommandSender,
|
||||||
|
},
|
||||||
|
entity::mob,
|
||||||
|
};
|
||||||
|
const NAMES: [&str; 1] = ["summon"];
|
||||||
|
|
||||||
|
const DESCRIPTION: &str = "Spawns a Entity at position.";
|
||||||
|
|
||||||
|
const ARG_ENTITY: &str = "entity";
|
||||||
|
|
||||||
|
const ARG_POS: &str = "pos";
|
||||||
|
|
||||||
|
struct SummonExecutor;
|
||||||
|
|
||||||
|
#[async_trait]
|
||||||
|
impl CommandExecutor for SummonExecutor {
|
||||||
|
async fn execute<'a>(
|
||||||
|
&self,
|
||||||
|
sender: &mut CommandSender<'a>,
|
||||||
|
server: &crate::server::Server,
|
||||||
|
args: &ConsumedArgs<'a>,
|
||||||
|
) -> Result<(), CommandError> {
|
||||||
|
let entity = SummonableEntitiesArgumentConsumer::find_arg(args, ARG_ENTITY)?;
|
||||||
|
let pos = Position3DArgumentConsumer::find_arg(args, ARG_POS);
|
||||||
|
|
||||||
|
// TODO: Make this work in console
|
||||||
|
if let Some(player) = sender.as_player() {
|
||||||
|
let pos = pos.unwrap_or(player.living_entity.entity.pos.load());
|
||||||
|
let (mob, uuid) = mob::from_type(entity, server, pos, player.world()).await;
|
||||||
|
player
|
||||||
|
.world()
|
||||||
|
.broadcast_packet_all(&mob.living_entity.entity.create_spawn_packet(uuid))
|
||||||
|
.await;
|
||||||
|
sender
|
||||||
|
.send_message(TextComponent::translate(
|
||||||
|
"commands.summon.success",
|
||||||
|
[TextComponent::text(format!("{entity:?}"))].into(),
|
||||||
|
))
|
||||||
|
.await;
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn init_command_tree() -> CommandTree {
|
||||||
|
CommandTree::new(NAMES, DESCRIPTION).then(
|
||||||
|
argument(ARG_ENTITY, SummonableEntitiesArgumentConsumer)
|
||||||
|
.execute(SummonExecutor)
|
||||||
|
.then(argument(ARG_POS, Position3DArgumentConsumer).execute(SummonExecutor)),
|
||||||
|
// TODO: Add NBT
|
||||||
|
)
|
||||||
|
}
|
||||||
@ -2,10 +2,10 @@ use async_trait::async_trait;
|
|||||||
use pumpkin_util::math::vector3::Vector3;
|
use pumpkin_util::math::vector3::Vector3;
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_entities::EntitiesArgumentConsumer;
|
use crate::command::args::entities::EntitiesArgumentConsumer;
|
||||||
use crate::command::args::arg_entity::EntityArgumentConsumer;
|
use crate::command::args::entity::EntityArgumentConsumer;
|
||||||
use crate::command::args::arg_position_3d::Position3DArgumentConsumer;
|
use crate::command::args::position_3d::Position3DArgumentConsumer;
|
||||||
use crate::command::args::arg_rotation::RotationArgumentConsumer;
|
use crate::command::args::rotation::RotationArgumentConsumer;
|
||||||
use crate::command::args::ConsumedArgs;
|
use crate::command::args::ConsumedArgs;
|
||||||
use crate::command::args::FindArg;
|
use crate::command::args::FindArg;
|
||||||
use crate::command::tree::CommandTree;
|
use crate::command::tree::CommandTree;
|
||||||
@ -2,7 +2,7 @@ use async_trait::async_trait;
|
|||||||
use pumpkin_util::text::color::{Color, NamedColor};
|
use pumpkin_util::text::color::{Color, NamedColor};
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_bounded_num::BoundedNumArgumentConsumer;
|
use crate::command::args::bounded_num::BoundedNumArgumentConsumer;
|
||||||
use crate::command::args::FindArgDefaultName;
|
use crate::command::args::FindArgDefaultName;
|
||||||
use crate::command::tree_builder::{argument_default_name, literal};
|
use crate::command::tree_builder::{argument_default_name, literal};
|
||||||
use crate::command::{
|
use crate::command::{
|
||||||
@ -5,7 +5,7 @@ use pumpkin_util::text::TextComponent;
|
|||||||
use crate::{
|
use crate::{
|
||||||
command::{
|
command::{
|
||||||
args::{
|
args::{
|
||||||
arg_players::PlayersArgumentConsumer, arg_textcomponent::TextComponentArgConsumer, Arg,
|
players::PlayersArgumentConsumer, textcomponent::TextComponentArgConsumer, Arg,
|
||||||
ConsumedArgs, FindArg,
|
ConsumedArgs, FindArg,
|
||||||
},
|
},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
@ -4,9 +4,9 @@ use pumpkin_protocol::codec::var_int::VarInt;
|
|||||||
use pumpkin_util::text::color::{Color, NamedColor};
|
use pumpkin_util::text::color::{Color, NamedColor};
|
||||||
use pumpkin_util::text::TextComponent;
|
use pumpkin_util::text::TextComponent;
|
||||||
|
|
||||||
use crate::command::args::arg_bounded_num::BoundedNumArgumentConsumer;
|
use crate::command::args::bounded_num::BoundedNumArgumentConsumer;
|
||||||
use crate::command::args::arg_players::PlayersArgumentConsumer;
|
use crate::command::args::players::PlayersArgumentConsumer;
|
||||||
use crate::command::args::arg_simple::SimpleArgConsumer;
|
use crate::command::args::simple::SimpleArgConsumer;
|
||||||
use crate::command::args::{Arg, FindArgDefaultName};
|
use crate::command::args::{Arg, FindArgDefaultName};
|
||||||
use crate::command::dispatcher::CommandError::{InvalidConsumption, InvalidRequirement};
|
use crate::command::dispatcher::CommandError::{InvalidConsumption, InvalidRequirement};
|
||||||
use crate::command::tree_builder::{argument, argument_default_name, require};
|
use crate::command::tree_builder::{argument, argument_default_name, require};
|
||||||
@ -10,9 +10,8 @@ use pumpkin_util::{
|
|||||||
use crate::{
|
use crate::{
|
||||||
command::{
|
command::{
|
||||||
args::{
|
args::{
|
||||||
arg_bounded_num::BoundedNumArgumentConsumer,
|
bounded_num::BoundedNumArgumentConsumer, position_2d::Position2DArgumentConsumer,
|
||||||
arg_position_2d::Position2DArgumentConsumer, ConsumedArgs, DefaultNameArgConsumer,
|
ConsumedArgs, DefaultNameArgConsumer, FindArgDefaultName,
|
||||||
FindArgDefaultName,
|
|
||||||
},
|
},
|
||||||
tree::CommandTree,
|
tree::CommandTree,
|
||||||
tree_builder::{argument_default_name, literal},
|
tree_builder::{argument_default_name, literal},
|
||||||
@ -1,8 +1,8 @@
|
|||||||
use std::fmt;
|
use std::fmt;
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
|
||||||
use crate::command::commands::cmd_seed;
|
use crate::command::commands::seed;
|
||||||
use crate::command::commands::{cmd_bossbar, cmd_transfer};
|
use crate::command::commands::{bossbar, transfer};
|
||||||
use crate::command::dispatcher::CommandDispatcher;
|
use crate::command::dispatcher::CommandDispatcher;
|
||||||
use crate::entity::player::Player;
|
use crate::entity::player::Player;
|
||||||
use crate::server::Server;
|
use crate::server::Server;
|
||||||
@ -10,9 +10,8 @@ use crate::world::World;
|
|||||||
use args::ConsumedArgs;
|
use args::ConsumedArgs;
|
||||||
use async_trait::async_trait;
|
use async_trait::async_trait;
|
||||||
use commands::{
|
use commands::{
|
||||||
cmd_clear, cmd_deop, cmd_fill, cmd_gamemode, cmd_give, cmd_help, cmd_kick, cmd_kill, cmd_list,
|
clear, deop, fill, gamemode, give, help, kick, kill, list, me, op, playsound, plugin, plugins,
|
||||||
cmd_me, cmd_op, cmd_playsound, cmd_plugin, cmd_plugins, cmd_pumpkin, cmd_say, cmd_setblock,
|
pumpkin, say, setblock, stop, summon, teleport, time, title, worldborder,
|
||||||
cmd_stop, cmd_teleport, cmd_time, cmd_title, cmd_worldborder,
|
|
||||||
};
|
};
|
||||||
use dispatcher::CommandError;
|
use dispatcher::CommandError;
|
||||||
use pumpkin_util::math::vector3::Vector3;
|
use pumpkin_util::math::vector3::Vector3;
|
||||||
@ -112,31 +111,32 @@ impl CommandSender<'_> {
|
|||||||
pub fn default_dispatcher() -> CommandDispatcher {
|
pub fn default_dispatcher() -> CommandDispatcher {
|
||||||
let mut dispatcher = CommandDispatcher::default();
|
let mut dispatcher = CommandDispatcher::default();
|
||||||
|
|
||||||
dispatcher.register(cmd_pumpkin::init_command_tree(), PermissionLvl::Zero);
|
dispatcher.register(pumpkin::init_command_tree(), PermissionLvl::Zero);
|
||||||
dispatcher.register(cmd_bossbar::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(bossbar::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_say::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(say::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_gamemode::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(gamemode::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_stop::init_command_tree(), PermissionLvl::Four);
|
dispatcher.register(stop::init_command_tree(), PermissionLvl::Four);
|
||||||
dispatcher.register(cmd_help::init_command_tree(), PermissionLvl::Zero);
|
dispatcher.register(help::init_command_tree(), PermissionLvl::Zero);
|
||||||
dispatcher.register(cmd_kill::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(kill::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_kick::init_command_tree(), PermissionLvl::Three);
|
dispatcher.register(kick::init_command_tree(), PermissionLvl::Three);
|
||||||
dispatcher.register(cmd_plugin::init_command_tree(), PermissionLvl::Three);
|
dispatcher.register(plugin::init_command_tree(), PermissionLvl::Three);
|
||||||
dispatcher.register(cmd_plugins::init_command_tree(), PermissionLvl::Three);
|
dispatcher.register(plugins::init_command_tree(), PermissionLvl::Three);
|
||||||
dispatcher.register(cmd_worldborder::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(worldborder::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_teleport::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(teleport::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_time::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(time::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_give::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(give::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_list::init_command_tree(), PermissionLvl::Zero);
|
dispatcher.register(list::init_command_tree(), PermissionLvl::Zero);
|
||||||
dispatcher.register(cmd_clear::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(clear::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_setblock::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(setblock::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_seed::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(seed::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_transfer::init_command_tree(), PermissionLvl::Zero);
|
dispatcher.register(transfer::init_command_tree(), PermissionLvl::Zero);
|
||||||
dispatcher.register(cmd_fill::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(fill::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_op::init_command_tree(), PermissionLvl::Three);
|
dispatcher.register(op::init_command_tree(), PermissionLvl::Three);
|
||||||
dispatcher.register(cmd_deop::init_command_tree(), PermissionLvl::Three);
|
dispatcher.register(deop::init_command_tree(), PermissionLvl::Three);
|
||||||
dispatcher.register(cmd_me::init_command_tree(), PermissionLvl::Zero);
|
dispatcher.register(me::init_command_tree(), PermissionLvl::Zero);
|
||||||
dispatcher.register(cmd_playsound::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(playsound::init_command_tree(), PermissionLvl::Two);
|
||||||
dispatcher.register(cmd_title::init_command_tree(), PermissionLvl::Two);
|
dispatcher.register(title::init_command_tree(), PermissionLvl::Two);
|
||||||
|
dispatcher.register(summon::init_command_tree(), PermissionLvl::Two);
|
||||||
|
|
||||||
dispatcher
|
dispatcher
|
||||||
}
|
}
|
||||||
|
|||||||
@ -168,7 +168,7 @@ pub fn argument_default_name(
|
|||||||
) -> NonLeafNodeBuilder {
|
) -> NonLeafNodeBuilder {
|
||||||
NonLeafNodeBuilder {
|
NonLeafNodeBuilder {
|
||||||
node_type: NodeType::Argument {
|
node_type: NodeType::Argument {
|
||||||
name: consumer.default_name(),
|
name: consumer.default_name().to_string(),
|
||||||
consumer: Arc::new(consumer),
|
consumer: Arc::new(consumer),
|
||||||
},
|
},
|
||||||
child_nodes: Vec::new(),
|
child_nodes: Vec::new(),
|
||||||
|
|||||||
@ -1,7 +1,6 @@
|
|||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
|
||||||
use pumpkin_data::entity::EntityType;
|
use pumpkin_data::entity::EntityType;
|
||||||
use pumpkin_protocol::{client::play::CSpawnEntity, codec::var_int::VarInt};
|
|
||||||
use pumpkin_util::math::vector3::Vector3;
|
use pumpkin_util::math::vector3::Vector3;
|
||||||
use tokio::sync::Mutex;
|
use tokio::sync::Mutex;
|
||||||
use uuid::Uuid;
|
use uuid::Uuid;
|
||||||
@ -61,25 +60,4 @@ impl MobEntity {
|
|||||||
pub async fn goal<T: Goal + 'static>(&self, goal: T) {
|
pub async fn goal<T: Goal + 'static>(&self, goal: T) {
|
||||||
self.goals.lock().await.push((Arc::new(goal), false));
|
self.goals.lock().await.push((Arc::new(goal), false));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn create_spawn_entity_packet(&self, uuid: Uuid) -> CSpawnEntity {
|
|
||||||
let e = &self.living_entity.entity;
|
|
||||||
let entity_loc = e.pos.load();
|
|
||||||
let entity_vel = e.velocity.load();
|
|
||||||
CSpawnEntity::new(
|
|
||||||
VarInt(e.entity_id),
|
|
||||||
uuid,
|
|
||||||
VarInt((e.entity_type) as i32),
|
|
||||||
entity_loc.x,
|
|
||||||
entity_loc.y,
|
|
||||||
entity_loc.z,
|
|
||||||
e.pitch.load(),
|
|
||||||
e.yaw.load(),
|
|
||||||
e.yaw.load(), // todo: head_yaw and yaw are swapped, find out why
|
|
||||||
0.into(),
|
|
||||||
entity_vel.x as f32,
|
|
||||||
entity_vel.y as f32,
|
|
||||||
entity_vel.z as f32,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -6,7 +6,9 @@ use crossbeam::atomic::AtomicCell;
|
|||||||
use pumpkin_data::entity::{EntityPose, EntityType};
|
use pumpkin_data::entity::{EntityPose, EntityType};
|
||||||
use pumpkin_nbt::{compound::NbtCompound, tag::NbtTag};
|
use pumpkin_nbt::{compound::NbtCompound, tag::NbtTag};
|
||||||
use pumpkin_protocol::{
|
use pumpkin_protocol::{
|
||||||
client::play::{CHeadRot, CSetEntityMetadata, CTeleportEntity, CUpdateEntityRot, Metadata},
|
client::play::{
|
||||||
|
CHeadRot, CSetEntityMetadata, CSpawnEntity, CTeleportEntity, CUpdateEntityRot, Metadata,
|
||||||
|
},
|
||||||
codec::var_int::VarInt,
|
codec::var_int::VarInt,
|
||||||
};
|
};
|
||||||
use pumpkin_util::math::{
|
use pumpkin_util::math::{
|
||||||
@ -17,6 +19,7 @@ use pumpkin_util::math::{
|
|||||||
vector3::Vector3,
|
vector3::Vector3,
|
||||||
wrap_degrees,
|
wrap_degrees,
|
||||||
};
|
};
|
||||||
|
use uuid::Uuid;
|
||||||
|
|
||||||
use crate::world::World;
|
use crate::world::World;
|
||||||
|
|
||||||
@ -206,6 +209,26 @@ impl Entity {
|
|||||||
self.world.remove_entity(self).await;
|
self.world.remove_entity(self).await;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn create_spawn_packet(&self, uuid: Uuid) -> CSpawnEntity {
|
||||||
|
let entity_loc = self.pos.load();
|
||||||
|
let entity_vel = self.velocity.load();
|
||||||
|
CSpawnEntity::new(
|
||||||
|
VarInt(self.entity_id),
|
||||||
|
uuid,
|
||||||
|
VarInt((self.entity_type) as i32),
|
||||||
|
entity_loc.x,
|
||||||
|
entity_loc.y,
|
||||||
|
entity_loc.z,
|
||||||
|
self.pitch.load(),
|
||||||
|
self.yaw.load(),
|
||||||
|
self.head_yaw.load(), // todo: head_yaw and yaw are swapped, find out why
|
||||||
|
0.into(),
|
||||||
|
entity_vel.x as f32,
|
||||||
|
entity_vel.y as f32,
|
||||||
|
entity_vel.z as f32,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
/// Applies knockback to the entity, following vanilla Minecraft's mechanics.
|
/// Applies knockback to the entity, following vanilla Minecraft's mechanics.
|
||||||
///
|
///
|
||||||
/// This function calculates the entity's new velocity based on the specified knockback strength and direction.
|
/// This function calculates the entity's new velocity based on the specified knockback strength and direction.
|
||||||
|
|||||||
@ -538,7 +538,7 @@ impl Player {
|
|||||||
let mobs = world.current_living_mobs.lock().await.clone();
|
let mobs = world.current_living_mobs.lock().await.clone();
|
||||||
for (uuid, mob) in mobs {
|
for (uuid, mob) in mobs {
|
||||||
self.client
|
self.client
|
||||||
.send_packet(&mob.create_spawn_entity_packet(uuid))
|
.send_packet(&mob.living_entity.entity.create_spawn_packet(uuid))
|
||||||
.await;
|
.await;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1095,12 +1095,13 @@ impl Player {
|
|||||||
// create rotation like Vanilla
|
// create rotation like Vanilla
|
||||||
let yaw = wrap_degrees(rand::random::<f32>() * 360.0) % 360.0;
|
let yaw = wrap_degrees(rand::random::<f32>() * 360.0) % 360.0;
|
||||||
|
|
||||||
|
let world = self.world();
|
||||||
// create new mob and uuid based on spawn egg id
|
// create new mob and uuid based on spawn egg id
|
||||||
let (mob, uuid) = mob::from_type(
|
let (mob, uuid) = mob::from_type(
|
||||||
EntityType::from_raw(*spawn_item_id).unwrap(),
|
EntityType::from_raw(*spawn_item_id).unwrap(),
|
||||||
server,
|
server,
|
||||||
pos,
|
pos,
|
||||||
self.world(),
|
world,
|
||||||
)
|
)
|
||||||
.await;
|
.await;
|
||||||
|
|
||||||
@ -1108,8 +1109,8 @@ impl Player {
|
|||||||
mob.living_entity.entity.set_rotation(yaw, 0.0);
|
mob.living_entity.entity.set_rotation(yaw, 0.0);
|
||||||
|
|
||||||
// broadcast new mob to all players
|
// broadcast new mob to all players
|
||||||
server
|
world
|
||||||
.broadcast_packet_all(&mob.create_spawn_entity_packet(uuid))
|
.broadcast_packet_all(&mob.living_entity.entity.create_spawn_packet(uuid))
|
||||||
.await;
|
.await;
|
||||||
|
|
||||||
// TODO: send/configure additional commands/data based on type of entity (horse, slime, etc)
|
// TODO: send/configure additional commands/data based on type of entity (horse, slime, etc)
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user