friendly fire and pvp at desert arenas!

This commit is contained in:
crabman 2024-03-25 21:55:50 +00:00
parent 4d67e808e1
commit c589bc5ca0
No known key found for this signature in database
9 changed files with 114 additions and 100 deletions

View File

@ -92,8 +92,7 @@ command-aura-spawn-new-entity = Spawned new aura
# Unreachable/untestable but added for consistency
command-player-info-unavailable = Cannot get player information for { $target }
command-unimplemented-waypoint-spawn = Waypoint spawning is not implemented
command-unimplemented-teleporter-spawn = Teleporter spawning is not implemented
command-unimplemented-spawn-special = Spawning special entities is not implemented
command-kit-inventory-unavailable = Could not get inventory
command-inventory-cant-fit-item = Can't fit item to inventory
# Emitted by /disconnect_all when you don't exist (?)

View File

@ -6,10 +6,9 @@ use crate::{
agent::Sound,
dialogue::Subject,
invite::{InviteKind, InviteResponse},
misc::PortalData,
DisconnectReason, LootOwner, Ori, Pos, UnresolvedChatMsg, Vel,
},
generation::EntityInfo,
generation::{EntityInfo, SpecialEntity},
lottery::LootSpec,
mounting::VolumePos,
outcome::Outcome,
@ -152,8 +151,10 @@ pub struct ChatEvent(pub UnresolvedChatMsg);
pub struct CommandEvent(pub EcsEntity, pub String, pub Vec<String>);
// Entity Creation
pub struct CreateWaypointEvent(pub Vec3<f32>);
pub struct CreateTeleporterEvent(pub Vec3<f32>, pub PortalData);
pub struct CreateSpecialEntityEvent {
pub pos: Vec3<f32>,
pub entity: SpecialEntity,
}
pub struct CreateNpcEvent {
pub pos: Pos,
@ -498,8 +499,7 @@ pub fn register_event_busses(ecs: &mut World) {
ecs.insert(EventBus::<ClientDisconnectWithoutPersistenceEvent>::default());
ecs.insert(EventBus::<ChatEvent>::default());
ecs.insert(EventBus::<CommandEvent>::default());
ecs.insert(EventBus::<CreateWaypointEvent>::default());
ecs.insert(EventBus::<CreateTeleporterEvent>::default());
ecs.insert(EventBus::<CreateSpecialEntityEvent>::default());
ecs.insert(EventBus::<CreateNpcEvent>::default());
ecs.insert(EventBus::<CreateShipEvent>::default());
ecs.insert(EventBus::<CreateItemDropEvent>::default());

View File

@ -177,10 +177,14 @@ pub fn try_all_entity_configs() -> Result<Vec<String>, Error> {
Ok(configs.read().ids().map(|id| id.to_string()).collect())
}
#[derive(Clone)]
#[derive(Clone, Debug)]
pub enum SpecialEntity {
Waypoint,
Teleporter(PortalData),
/// Totem with FriendlyFire and ForcePvP auras
ArenaTotem {
range: f32,
},
}
#[derive(Clone)]

View File

@ -42,10 +42,10 @@ use common::{
depot,
effect::Effect,
event::{
ClientDisconnectEvent, CreateNpcEvent, CreateWaypointEvent, EventBus, ExplosionEvent,
ClientDisconnectEvent, CreateNpcEvent, CreateSpecialEntityEvent, EventBus, ExplosionEvent,
GroupManipEvent, InitiateInviteEvent, TamePetEvent,
},
generation::{EntityConfig, EntityInfo},
generation::{EntityConfig, EntityInfo, SpecialEntity},
link::Is,
mounting::{Rider, Volume, VolumeRider},
npc::{self, get_npc_name},
@ -670,11 +670,8 @@ fn handle_into_npc(
TransformEntityError::EntityDead => {
Content::localized_with_args("command-entity-dead", [("entity", "target")])
},
TransformEntityError::UnexpectedNpcWaypoint => {
Content::localized("command-unimplemented-waypoint-spawn")
},
TransformEntityError::UnexpectedNpcTeleporter => {
Content::localized("command-unimplemented-teleporter-spawn")
TransformEntityError::UnexpectedSpecialEntity => {
Content::localized("command-unimplemented-spawn-special")
},
TransformEntityError::LoadingCharacter => {
Content::localized("command-transform-invalid-presence")
@ -731,11 +728,8 @@ fn handle_make_npc(
);
match SpawnEntityData::from_entity_info(entity_info) {
SpawnEntityData::Waypoint(_) => {
return Err(Content::localized("command-unimplemented-waypoint-spawn"));
},
SpawnEntityData::Teleporter(_, _) => {
return Err(Content::localized("command-unimplemented-teleporter-spawn"));
SpawnEntityData::Special(_, _) => {
return Err(Content::localized("command-unimplemented-spawn-special"));
},
SpawnEntityData::Npc(data) => {
let (npc_builder, _pos) = data.to_npc_builder();
@ -2000,8 +1994,11 @@ fn handle_spawn_campfire(
server
.state
.ecs()
.read_resource::<EventBus<CreateWaypointEvent>>()
.emit_now(CreateWaypointEvent(pos.0));
.read_resource::<EventBus<CreateSpecialEntityEvent>>()
.emit_now(CreateSpecialEntityEvent {
pos: pos.0,
entity: SpecialEntity::Waypoint,
});
server.notify_client(
client,

View File

@ -13,9 +13,10 @@ use common::{
},
event::{
CreateItemDropEvent, CreateNpcEvent, CreateObjectEvent, CreateShipEvent,
CreateTeleporterEvent, CreateWaypointEvent, EventBus, InitializeCharacterEvent,
InitializeSpectatorEvent, ShockwaveEvent, ShootEvent, UpdateCharacterDataEvent,
CreateSpecialEntityEvent, EventBus, InitializeCharacterEvent, InitializeSpectatorEvent,
ShockwaveEvent, ShootEvent, UpdateCharacterDataEvent,
},
generation::SpecialEntity,
mounting::{Mounting, Volume, VolumeMounting, VolumePos},
outcome::Outcome,
resources::{Secs, Time},
@ -388,53 +389,76 @@ pub fn handle_shockwave(server: &mut Server, ev: ShockwaveEvent) {
.build();
}
pub fn handle_create_waypoint(server: &mut Server, ev: CreateWaypointEvent) {
pub fn handle_create_special_entity(server: &mut Server, ev: CreateSpecialEntityEvent) {
let time = server.state.get_time();
server
.state
.create_object(Pos(ev.0), comp::object::Body::CampfireLit)
.with(LightEmitter {
col: Rgb::new(1.0, 0.3, 0.1),
strength: 5.0,
flicker: 1.0,
animated: true,
})
.with(WaypointArea::default())
.with(comp::Immovable)
.with(comp::Auras::new(vec![
Aura::new(
AuraKind::Buff {
kind: BuffKind::CampfireHeal,
data: BuffData::new(0.02, Some(Secs(1.0))),
category: BuffCategory::Natural,
source: BuffSource::World,
},
5.0,
None,
AuraTarget::All,
Time(time),
),
Aura::new(
AuraKind::Buff {
kind: BuffKind::Burning,
data: BuffData::new(2.0, Some(Secs(10.0))),
category: BuffCategory::Natural,
source: BuffSource::World,
},
0.7,
None,
AuraTarget::All,
Time(time),
),
]))
.build();
}
pub fn handle_create_teleporter(server: &mut Server, ev: CreateTeleporterEvent) {
server
.state
.create_teleporter(comp::Pos(ev.0), ev.1)
.build();
match ev.entity {
SpecialEntity::Waypoint => {
server
.state
.create_object(Pos(ev.pos), comp::object::Body::CampfireLit)
.with(LightEmitter {
col: Rgb::new(1.0, 0.3, 0.1),
strength: 5.0,
flicker: 1.0,
animated: true,
})
.with(WaypointArea::default())
.with(comp::Immovable)
.with(comp::EnteredAuras::default())
.with(comp::Auras::new(vec![
Aura::new(
AuraKind::Buff {
kind: BuffKind::CampfireHeal,
data: BuffData::new(0.02, Some(Secs(1.0))),
category: BuffCategory::Natural,
source: BuffSource::World,
},
5.0,
None,
AuraTarget::All,
Time(time),
),
Aura::new(
AuraKind::Buff {
kind: BuffKind::Burning,
data: BuffData::new(2.0, Some(Secs(10.0))),
category: BuffCategory::Natural,
source: BuffSource::World,
},
0.7,
None,
AuraTarget::All,
Time(time),
),
]))
.build();
},
SpecialEntity::Teleporter(portal) => {
server
.state
.create_teleporter(comp::Pos(ev.pos), portal)
.build();
},
SpecialEntity::ArenaTotem { range } => {
server
.state
.create_object(Pos(ev.pos), comp::object::Body::GnarlingTotemGreen)
.with(comp::Immovable)
.with(comp::EnteredAuras::default())
.with(comp::Auras::new(vec![
Aura::new(
AuraKind::FriendlyFire,
range,
None,
AuraTarget::All,
Time(time),
),
Aura::new(AuraKind::ForcePvP, range, None, AuraTarget::All, Time(time)),
]))
.build();
},
}
}
pub fn handle_create_item_drop(server: &mut Server, ev: CreateItemDropEvent) {

View File

@ -2165,8 +2165,7 @@ pub fn handle_transform(
#[derive(Debug)]
pub enum TransformEntityError {
EntityDead,
UnexpectedNpcWaypoint,
UnexpectedNpcTeleporter,
UnexpectedSpecialEntity,
LoadingCharacter,
EntityIsPlayer,
}
@ -2308,11 +2307,8 @@ pub fn transform_entity(
}
}
},
SpawnEntityData::Waypoint(_) => {
return Err(TransformEntityError::UnexpectedNpcWaypoint);
},
SpawnEntityData::Teleporter(_, _) => {
return Err(TransformEntityError::UnexpectedNpcTeleporter);
SpawnEntityData::Special(_, _) => {
return Err(TransformEntityError::UnexpectedSpecialEntity);
},
}

View File

@ -14,8 +14,8 @@ use specs::{
use self::{
entity_creation::{
handle_create_item_drop, handle_create_npc, handle_create_object, handle_create_ship,
handle_create_teleporter, handle_create_waypoint, handle_initialize_character,
handle_initialize_spectator, handle_loaded_character_data, handle_shockwave, handle_shoot,
handle_create_special_entity, handle_initialize_character, handle_initialize_spectator,
handle_loaded_character_data, handle_shockwave, handle_shoot,
},
entity_manipulation::{handle_delete, handle_transform},
interaction::handle_tame_pet,
@ -146,8 +146,7 @@ impl Server {
self.handle_serial_events(handle_create_ship);
self.handle_serial_events(handle_shoot);
self.handle_serial_events(handle_shockwave);
self.handle_serial_events(handle_create_waypoint);
self.handle_serial_events(handle_create_teleporter);
self.handle_serial_events(handle_create_special_entity);
self.handle_serial_events(handle_create_item_drop);
self.handle_serial_events(handle_create_object);
self.handle_serial_events(handle_delete);

View File

@ -13,12 +13,10 @@ use crate::{
use common::{
calendar::Calendar,
comp::{
self, agent, biped_small, bird_medium, misc::PortalData, BehaviorCapability, ForceUpdate,
Pos, Presence, Waypoint,
},
event::{
CreateNpcEvent, CreateTeleporterEvent, CreateWaypointEvent, EmitExt, EventBus, NpcBuilder,
self, agent, biped_small, bird_medium, BehaviorCapability, ForceUpdate, Pos, Presence,
Waypoint,
},
event::{CreateNpcEvent, CreateSpecialEntityEvent, EmitExt, EventBus, NpcBuilder},
event_emitters,
generation::{EntityInfo, SpecialEntity},
lottery::LootSpec,
@ -58,8 +56,7 @@ type RtSimData<'a> = ();
event_emitters! {
struct Events[Emitters] {
create_npc: CreateNpcEvent,
create_waypoint: CreateWaypointEvent,
create_teleporter: CreateTeleporterEvent,
create_waypoint: CreateSpecialEntityEvent,
}
}
@ -207,8 +204,8 @@ impl<'a> System<'a> for Sys {
let data = SpawnEntityData::from_entity_info(entity);
match data {
SpawnEntityData::Waypoint(pos) => {
emitters.emit(CreateWaypointEvent(pos));
SpawnEntityData::Special(pos, entity) => {
emitters.emit(CreateSpecialEntityEvent { pos, entity });
},
SpawnEntityData::Npc(data) => {
let (npc_builder, pos) = data.to_npc_builder();
@ -220,9 +217,6 @@ impl<'a> System<'a> for Sys {
rider: None,
});
},
SpawnEntityData::Teleporter(pos, teleporter) => {
emitters.emit(CreateTeleporterEvent(pos, teleporter));
},
}
}
}
@ -423,8 +417,7 @@ pub struct NpcData {
#[derive(Debug)]
pub enum SpawnEntityData {
Npc(NpcData),
Waypoint(Vec3<f32>),
Teleporter(Vec3<f32>, PortalData),
Special(Vec3<f32>, SpecialEntity),
}
impl SpawnEntityData {
@ -454,10 +447,7 @@ impl SpawnEntityData {
} = entity;
if let Some(special) = special_entity {
return match special {
SpecialEntity::Waypoint => Self::Waypoint(pos),
SpecialEntity::Teleporter(teleporter) => Self::Teleporter(pos, teleporter),
};
return Self::Special(pos, special);
}
let name = name.unwrap_or_else(|| "Unnamed".to_string());

View File

@ -1234,9 +1234,14 @@ impl Structure for DesertCityArena {
.fill(sandstone.clone());
// campfires & repair benches
painter.spawn(
EntityInfo::at((spire_pos - 2).with_z(base - 1).map(|e| e as f32))
EntityInfo::at((spire_pos - 2).with_z(base - 1).as_())
.into_special(SpecialEntity::Waypoint),
);
painter.spawn(EntityInfo::at(center.with_z(base).as_()).into_special(
SpecialEntity::ArenaTotem {
range: length as f32,
},
));
painter.sprite((spire_pos + 2).with_z(base - 1), SpriteKind::RepairBench);
// lamps