/
EntitySpawnSmartEvent.java
148 lines (119 loc) · 5.55 KB
/
EntitySpawnSmartEvent.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
package net.aufdemrand.denizen.events.core;
import net.aufdemrand.denizen.events.EventManager;
import net.aufdemrand.denizen.events.SmartEvent;
import net.aufdemrand.denizen.objects.*;
import net.aufdemrand.denizen.utilities.DenizenAPI;
import net.aufdemrand.denizen.utilities.debugging.dB;
import net.citizensnpcs.api.event.NPCSpawnEvent;
import org.bukkit.entity.LivingEntity;
import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener;
import org.bukkit.event.entity.CreatureSpawnEvent;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class EntitySpawnSmartEvent implements SmartEvent, Listener {
///////////////////
// SMARTEVENT METHODS
///////////////
@Override
public boolean shouldInitialize(Set<String> events) {
boolean should_register = false;
// Loop through event names from loaded world script events
for (String event : events) {
// Use a regex pattern to narrow down matches
// TODO: Cleaner regex?
Matcher m = Pattern.compile("on (\\w+) spawns(?: in (\\w+))?(?: because (\\w+))?", Pattern.CASE_INSENSITIVE)
.matcher(event);
if (m.matches()) {
// Check first group which contains entity name against dEntity's matches() method
if (!dEntity.matches(m.group(1)) && (!m.group(1).equalsIgnoreCase("entity") && !m.group(1).equalsIgnoreCase("npc"))) {
dB.echoError("Possible issue with '" + event + "' world event in script(s) " + EventManager.events.get(event)
+ ". Specified entity is not valid.");
}
// If registerable, we'll set should_register to true, but keep iterating through the matches
// to check them for errors, as caught above.
should_register = true;
}
}
return should_register;
}
@Override
public void _initialize() {
// Yipee! Register this class with Bukkit's EventListener
DenizenAPI.getCurrentInstance().getServer().getPluginManager()
.registerEvents(this, DenizenAPI.getCurrentInstance());
dB.log("Loaded Entity Spawn SmartEvent.");
}
@Override
public void breakDown() {
// Deregister CreatureSpawnEvent's ties to this SmartEvent
CreatureSpawnEvent.getHandlerList().unregister(this);
}
//////////////
// MECHANICS
///////////
// <--[event]
// @Events
// entity spawns
// entity spawns (in <notable cuboid>) (because <cause>)
// <entity> spawns
// <entity> spawns (in <notable cuboid>) (because <cause>)
//
// @Regex on (\w+) spawns(?: in (\w+))?(?: because (\w+))?
//
// @Warning This event may fire very rapidly.
//
// @Triggers when an entity spawns.
// @Context
// <context.entity> returns the dEntity that spawned.
// <context.reason> returns the reason the entity spawned.
// <context.location> returns the location the entity will spawn at.
// <context.cuboids> returns a list of cuboids that the entity spawned inside.
//
// @Determine
// "CANCELLED" to stop the entity from spawning.
//
// -->
@EventHandler
public void npcSpawn(NPCSpawnEvent event) {
if (event.getNPC().getEntity() instanceof LivingEntity)
creatureSpawn(new CreatureSpawnEvent((LivingEntity)event.getNPC().getEntity(),
CreatureSpawnEvent.SpawnReason.CUSTOM));
}
@EventHandler
public void creatureSpawn(CreatureSpawnEvent event) {
List<String> events = new ArrayList<String>();
Map<String, dObject> context = new HashMap<String, dObject>();
dEntity entity = new dEntity(event.getEntity());
String reason = event.getSpawnReason().name();
// Look for cuboids that contain the block's location
List<dCuboid> cuboids = dCuboid.getNotableCuboidsContaining(event.getLocation());
dList cuboid_context = new dList();
for (dCuboid cuboid : cuboids) {
events.add("entity spawns in " + cuboid.identifySimple());
events.add("entity spawns in " + cuboid.identifySimple() + " because " + reason);
events.add(entity.identifyType() + " spawns in " + cuboid.identifySimple());
events.add(entity.identifyType() + " spawns in " + cuboid.identifySimple() + " because " + reason);
events.add(entity.identifySimple() + " spawns in " + cuboid.identifySimple());
events.add(entity.identifySimple() + " spawns in " + cuboid.identifySimple() + " because " + reason);
}
// Add in cuboids context, with either the cuboids or an empty list
context.put("cuboids", cuboid_context);
// Add events to fire
events.add("entity spawns");
events.add("entity spawns because " + reason);
events.add(entity.identifyType() + " spawns");
events.add(entity.identifyType() + " spawns because " + reason);
events.add(entity.identifySimple() + " spawns");
events.add(entity.identifySimple() + " spawns because " + reason);
// Add in other contexts associated with this event
context.put("entity", entity);
context.put("reason", new Element(reason));
context.put("location", new dLocation(event.getLocation()));
String determination = EventManager.doEvents(events,
(entity.isNPC() ? entity.getDenizenNPC() : null), null, context, true);
if (determination.toUpperCase().startsWith("CANCELLED"))
event.setCancelled(true);
}
}