diff --git a/src/client/js/input.js b/src/client/js/input.js
index 1e542fbd..19ee59f4 100644
--- a/src/client/js/input.js
+++ b/src/client/js/input.js
@@ -60,6 +60,9 @@ define([
enabled: true,
+ blacklistedKeys: [],
+ whitelistedKeys: [],
+
init: function () {
$(window).on('keydown', this.events.keyboard.keyDown.bind(this));
$(window).on('keyup', this.events.keyboard.keyUp.bind(this));
@@ -78,6 +81,22 @@ define([
require(['plugins/shake.js'], this.onLoadShake.bind(this));
},
+ blacklistKeys: function (list) {
+ this.blacklistedKeys.push(...list);
+ },
+
+ unBlacklistKeys: function (list) {
+ this.blacklistedKeys.spliceWhere(d => list.includes(d));
+ },
+
+ whitelistKeys: function (list) {
+ this.whitelistedKeys.push(...list);
+ },
+
+ unWhitelistKeys: function (list) {
+ this.whitelistedKeys.spliceWhere(d => list.includes(d));
+ },
+
onLoadShake: function (shake) {
let shaker = new shake({
threshold: 5,
@@ -142,6 +161,7 @@ define([
events: {
keyboard: {
+ /* eslint-disable-next-line max-lines-per-function */
keyDown: function (e) {
if (!this.enabled)
return;
@@ -156,6 +176,18 @@ define([
if ((e.keyCode === 9) || (e.keyCode === 8) || (e.keyCode === 122))
e.preventDefault();
+ const allowKey = (
+ key.length > 1 ||
+ this.whitelistedKeys.includes(key) ||
+ (
+ !this.blacklistedKeys.includes(key) &&
+ !this.blacklistedKeys.includes('*')
+ )
+ );
+
+ if (!allowKey)
+ return;
+
if (this.keys.has(key))
this.keys[key] = 2;
else {
diff --git a/src/client/js/misc/physics.js b/src/client/js/misc/physics.js
index f3b49199..176a0251 100644
--- a/src/client/js/misc/physics.js
+++ b/src/client/js/misc/physics.js
@@ -76,6 +76,22 @@ define([
return inside;
},
+ //Helper function to check if a point is inside an area
+ // This function is optimized to check if the point is outside the rect first
+ // and if it is not, we do the more expensive isInPolygon check
+ isInArea: function (x, y, { x: ax, y: ay, width, height, area }) {
+ //Outside rect
+ if (
+ x < ax ||
+ x >= ax + width ||
+ y < ay ||
+ y >= ay + height
+ )
+ return false;
+
+ return this.isInPolygon(x, y, area);
+ },
+
distanceToPolygon: function (p, verts) {
return distanceToPolygon.calculate(p, verts);
}
diff --git a/src/client/js/objects/objects.js b/src/client/js/objects/objects.js
index 33ffbbd2..d155b6a9 100644
--- a/src/client/js/objects/objects.js
+++ b/src/client/js/objects/objects.js
@@ -167,7 +167,7 @@ define([
events.emit('onGetPlayer', obj);
window.player = obj;
- sound.unload(obj.zoneId);
+ sound.unload(obj.zoneName);
renderer.setPosition({
x: (obj.x - (renderer.width / (scale * 2))) * scale,
diff --git a/src/client/js/rendering/renderer.js b/src/client/js/rendering/renderer.js
index 71a567fa..93eeb14f 100644
--- a/src/client/js/rendering/renderer.js
+++ b/src/client/js/rendering/renderer.js
@@ -313,8 +313,13 @@ define([
return 0;
});
- if (this.zoneId !== null)
- events.emit('onRezone', this.zoneId);
+ if (this.zoneId !== null) {
+ events.emit('onRezone', {
+ oldZoneId: this.zoneId,
+ newZoneId: msg.zoneId
+ });
+ }
+
this.zoneId = msg.zoneId;
msg.clientObjects.forEach(c => {
@@ -384,60 +389,45 @@ define([
let foundVisibleLayer = null;
let foundHiddenLayer = null;
+ const fnTileInArea = physics.isInArea.bind(physics, x, y);
+ const fnPlayerInArea = physics.isInArea.bind(physics, px, py);
+
hiddenRooms.forEach(h => {
const { discovered, layer, interior } = h;
- const { x: hx, y: hy, width, height, area } = h;
-
- //Is the tile outside the hider
- if (
- x < hx ||
- x >= hx + width ||
- y < hy ||
- y >= hy + height
- ) {
- //If the hider is an interior, the tile should be hidden if the player is inside the hider
- if (interior) {
- if (physics.isInPolygon(px, py, area))
- foundHiddenLayer = layer;
- }
- return;
- }
+ const playerInHider = fnPlayerInArea(h);
+ const tileInHider = fnTileInArea(h);
- //Is the tile inside the hider
- if (!physics.isInPolygon(x, y, area))
- return;
+ if (playerInHider) {
+ if (interior && !tileInHider) {
+ foundHiddenLayer = layer;
- if (discovered) {
- foundVisibleLayer = layer;
+ return;
+ }
+ } else if (tileInHider && !discovered) {
+ foundHiddenLayer = layer;
return;
- }
-
- //Is the player outside the hider
- if (
- px < hx ||
- px >= hx + width ||
- py < hy ||
- py >= hy + height
- ) {
- foundHiddenLayer = layer;
+ } else if (discovered) {
+ foundVisibleLayer = layer;
return;
}
- //Is the player inside the hider
- if (!physics.isInPolygon(px, py, area)) {
- foundHiddenLayer = layer;
-
+ if (!tileInHider)
return;
- }
foundVisibleLayer = layer;
});
//We compare hider layers to cater for hiders inside hiders
- return (foundHiddenLayer > foundVisibleLayer) || (foundHiddenLayer === 0 && foundVisibleLayer === null);
+ return (
+ foundHiddenLayer > foundVisibleLayer ||
+ (
+ foundHiddenLayer === 0 &&
+ foundVisibleLayer === null
+ )
+ );
},
updateSprites: function () {
diff --git a/src/client/js/sound/sound.js b/src/client/js/sound/sound.js
index 022cff4c..53645558 100644
--- a/src/client/js/sound/sound.js
+++ b/src/client/js/sound/sound.js
@@ -52,7 +52,7 @@ define([
},
//Fired when a character rezones
- // 'scope' is the new zone name
+ // 'newScope' is the new zone name
unload: function (newScope) {
const { sounds } = this;
diff --git a/src/client/ui/templates/equipment/styles.css b/src/client/ui/templates/equipment/styles.css
index 31e8555d..78653759 100644
--- a/src/client/ui/templates/equipment/styles.css
+++ b/src/client/ui/templates/equipment/styles.css
@@ -1 +1 @@
-.uiEquipment{display:none;z-index:2;border:5px solid #3c3f4c;text-align:center;width:500px;height:712px}.uiEquipment>.heading{color:#fcfcfc;width:100%;height:36px;background-color:#3c3f4c}.uiEquipment>.heading .heading-text{padding-top:8px;margin:auto}.uiEquipment .content{width:100%;height:calc(100% - 36px);background-color:#373041;display:flex;flex-direction:column}.uiEquipment .content .tabs{width:100%;height:40px;padding:8px 8px 0 8px}.uiEquipment .content .tabs .tab{cursor:pointer;background-color:#3c3f4c;color:#fcfcfc;margin-right:8px;float:left;height:100%;padding-top:8px;padding-left:8px;padding-right:8px;width:calc((100% - 24px)/ 4)}.uiEquipment .content .tabs .tab:hover{background-color:#505360}.uiEquipment .content .tabs .tab.selected{background-color:#505360;color:#48edff}.uiEquipment .content .tabs .tab:last-child{margin-right:0}.uiEquipment .content .main{height:528px;display:flex;flex-direction:column;flex-wrap:wrap}.uiEquipment .content .main .left,.uiEquipment .content .main .right{width:96px;padding:8px}.uiEquipment .content .main .bottom,.uiEquipment .content .main .left,.uiEquipment .content .main .right,.uiEquipment .content .main .stats{height:528px}.uiEquipment .content .main .stats{height:calc(528px - 80px);width:calc(100% - (2 * 96px));padding:16px 8px 8px 8px}.uiEquipment .content .main .stats .stat{height:22px;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.uiEquipment .content .main .stats .stat.blueText>font{color:#3fa7dd}.uiEquipment .content .main .stats .stat.empty{height:22px}.uiEquipment .content .main .stats .stat.gold font{color:#faac45}.uiEquipment .content .main .quick{width:calc(100% - (2 * 96px));height:80px;padding:0;display:flex;justify-content:center}.uiEquipment .content .runes{display:flex;flex-direction:row;justify-content:space-between;width:100%;height:80px;padding:8px}.uiEquipment .content .runes .slot:last-child{margin-right:0}.uiEquipment .content .itemList .slot,.uiEquipment .content .left .slot,.uiEquipment .content .quick .slot,.uiEquipment .content .right .slot,.uiEquipment .content .runes .slot,.uiEquipment .content .tools .slot{width:80px;height:80px;background-color:#312136;margin-bottom:8px;cursor:pointer;padding:8px;position:relative}.uiEquipment .content .itemList .slot:last-child,.uiEquipment .content .left .slot:last-child,.uiEquipment .content .quick .slot:last-child,.uiEquipment .content .right .slot:last-child,.uiEquipment .content .runes .slot:last-child,.uiEquipment .content .tools .slot:last-child{margin-bottom:0}.uiEquipment .content .itemList .slot.show-default-icon .icon,.uiEquipment .content .left .slot.show-default-icon .icon,.uiEquipment .content .quick .slot.show-default-icon .icon,.uiEquipment .content .right .slot.show-default-icon .icon,.uiEquipment .content .runes .slot.show-default-icon .icon,.uiEquipment .content .tools .slot.show-default-icon .icon{opacity:.5;background-image:url(../../../images/uiIcons.png)!important}.uiEquipment .content .itemList .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=head] .icon{background-position:0 -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=neck] .icon{background-position:-64px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=chest] .icon{background-position:-128px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=hands] .icon{background-position:-192px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=finger-1] .icon{background-position:-256px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=finger-2] .icon{background-position:-256px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=waist] .icon{background-position:-320px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=legs] .icon{background-position:-384px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=feet] .icon{background-position:-448px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=trinket] .icon{background-position:-448px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=oneHanded] .icon{background-position:-384px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=offHand] .icon{background-position:-192px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=tool] .icon{background-position:-256px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .left .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .right .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot^=rune] .icon{background-position:-320px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .left .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .right .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot^=quick-0] .icon{background-position:-128px -384px}.uiEquipment .content .itemList .slot .icon,.uiEquipment .content .left .slot .icon,.uiEquipment .content .quick .slot .icon,.uiEquipment .content .right .slot .icon,.uiEquipment .content .runes .slot .icon,.uiEquipment .content .tools .slot .icon{height:100%}.uiEquipment .content .itemList .slot .info,.uiEquipment .content .left .slot .info,.uiEquipment .content .quick .slot .info,.uiEquipment .content .right .slot .info,.uiEquipment .content .runes .slot .info,.uiEquipment .content .tools .slot .info{left:6px;bottom:3px;position:absolute;color:#fcfcfc;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.uiEquipment .content .itemList .slot:hover .icon,.uiEquipment .content .left .slot:hover .icon,.uiEquipment .content .quick .slot:hover .icon,.uiEquipment .content .right .slot:hover .icon,.uiEquipment .content .runes .slot:hover .icon,.uiEquipment .content .tools .slot:hover .icon{filter:brightness(160%);-moz-filter:brightness(160%)}.uiEquipment .content .itemList .slot:hover.empty,.uiEquipment .content .left .slot:hover.empty,.uiEquipment .content .quick .slot:hover.empty,.uiEquipment .content .right .slot:hover.empty,.uiEquipment .content .runes .slot:hover.empty,.uiEquipment .content .tools .slot:hover.empty{background-color:rgba(72,237,255,.1)}.uiEquipment .content .itemList{display:none;position:absolute;left:0;top:0;width:100%;height:100%;background-color:#373041;padding:0;z-index:2;overflow-y:auto}.uiEquipment .content .itemList .slot{float:left;margin:8px 0 0 8px}.uiEquipment .content .itemList .slot .icon{position:relative}.uiEquipment .content .itemList .slot .icon.eq:before{content:'eq';left:-2px;bottom:-3px;position:absolute;color:#fcfcfc;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.uiEquipment .content .itemList .slot .icon.new:before{content:'new';left:-2px;bottom:-3px;position:absolute;color:#fcfcfc;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.mobile .uiEquipment{width:100%;height:100%;margin-left:5px;margin-top:5px}.mobile .uiEquipment .content{flex-direction:column;flex-wrap:wrap;position:relative}.mobile .uiEquipment .content .main{width:calc(100% - 8px);height:calc(100% - 130px);padding:8px 8px 0 8px;justify-content:space-between;position:relative}.mobile .uiEquipment .content .main .left,.mobile .uiEquipment .content .main .quick,.mobile .uiEquipment .content .main .right{display:flex;flex-direction:row;justify-content:space-between;width:70%;height:calc(100% / 3)}.mobile .uiEquipment .content .main .left .slot,.mobile .uiEquipment .content .main .quick .slot,.mobile .uiEquipment .content .main .right .slot{margin-bottom:0}.mobile .uiEquipment .content .main .stats{width:30%;height:calc(100% + 74px);overflow-y:auto;position:absolute;right:0}.mobile .uiEquipment .content .main .quick{order:3;justify-content:center;padding:0 8px 0 0}.mobile .uiEquipment .content .main .left{padding:0 8px 0 0}.mobile .uiEquipment .content .main .right{order:2;padding:0 8px 0 0}.mobile .uiEquipment .content .runes{flex-direction:row;width:calc((100% - 16px) * .7);position:absolute;left:1px;bottom:8px;padding:0 8px 0 8px}
\ No newline at end of file
+.uiEquipment{display:none;z-index:2;border:5px solid #3c3f4c;text-align:center;width:500px;height:712px}.uiEquipment>.heading{color:#fcfcfc;width:100%;height:36px;background-color:#3c3f4c}.uiEquipment>.heading .heading-text{padding-top:8px;margin:auto}.uiEquipment .content{width:100%;height:calc(100% - 36px);background-color:#373041;display:flex;flex-direction:column}.uiEquipment .content .tabs{width:100%;height:40px;padding:8px 8px 0 8px}.uiEquipment .content .tabs .tab{cursor:pointer;background-color:#3c3f4c;color:#fcfcfc;margin-right:8px;float:left;height:100%;padding-top:8px;padding-left:8px;padding-right:8px;width:calc((100% - 24px)/ 4)}.uiEquipment .content .tabs .tab:hover{background-color:#505360}.uiEquipment .content .tabs .tab.selected{background-color:#505360;color:#48edff}.uiEquipment .content .tabs .tab:last-child{margin-right:0}.uiEquipment .content .main{height:528px;display:flex;flex-direction:column;flex-wrap:wrap}.uiEquipment .content .main .left,.uiEquipment .content .main .right{width:96px;padding:8px}.uiEquipment .content .main .bottom,.uiEquipment .content .main .left,.uiEquipment .content .main .right,.uiEquipment .content .main .stats{height:528px}.uiEquipment .content .main .stats{height:calc(528px - 80px);width:calc(100% - (2 * 96px));padding:16px 8px 8px 8px}.uiEquipment .content .main .stats .stat{height:22px;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.uiEquipment .content .main .stats .stat.blueText>font{color:#3fa7dd}.uiEquipment .content .main .stats .stat.empty{height:22px}.uiEquipment .content .main .stats .stat.gold font{color:#faac45}.uiEquipment .content .main .quick{width:calc(100% - (2 * 96px));height:80px;padding:0;display:flex;justify-content:center}.uiEquipment .content .runes{display:flex;flex-direction:row;justify-content:space-between;width:100%;height:80px;padding:8px}.uiEquipment .content .runes .slot:last-child{margin-right:0}.uiEquipment .content .itemList .slot,.uiEquipment .content .left .slot,.uiEquipment .content .quick .slot,.uiEquipment .content .right .slot,.uiEquipment .content .runes .slot,.uiEquipment .content .tools .slot{width:80px;height:80px;background-color:#312136;margin-bottom:8px;cursor:pointer;padding:8px;position:relative}.uiEquipment .content .itemList .slot:last-child,.uiEquipment .content .left .slot:last-child,.uiEquipment .content .quick .slot:last-child,.uiEquipment .content .right .slot:last-child,.uiEquipment .content .runes .slot:last-child,.uiEquipment .content .tools .slot:last-child{margin-bottom:0}.uiEquipment .content .itemList .slot.show-default-icon .icon,.uiEquipment .content .left .slot.show-default-icon .icon,.uiEquipment .content .quick .slot.show-default-icon .icon,.uiEquipment .content .right .slot.show-default-icon .icon,.uiEquipment .content .runes .slot.show-default-icon .icon,.uiEquipment .content .tools .slot.show-default-icon .icon{opacity:.5;background-image:url(../../../images/uiIcons.png)!important}.uiEquipment .content .itemList .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=head] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=head] .icon{background-position:0 -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=neck] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=neck] .icon{background-position:-64px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=chest] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=chest] .icon{background-position:-128px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=hands] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=hands] .icon{background-position:-192px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=finger-1] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=finger-1] .icon{background-position:-256px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=finger-2] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=finger-2] .icon{background-position:-256px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=waist] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=waist] .icon{background-position:-320px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=legs] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=legs] .icon{background-position:-384px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=feet] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=feet] .icon{background-position:-448px -448px}.uiEquipment .content .itemList .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=trinket] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=trinket] .icon{background-position:-448px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=oneHanded] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=oneHanded] .icon{background-position:-384px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=offHand] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=offHand] .icon{background-position:-192px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .left .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .right .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot=tool] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot=tool] .icon{background-position:-256px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .left .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .right .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot^=rune] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot^=rune] .icon{background-position:-320px -384px}.uiEquipment .content .itemList .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .left .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .quick .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .right .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .runes .slot.show-default-icon[slot^=quick-0] .icon,.uiEquipment .content .tools .slot.show-default-icon[slot^=quick-0] .icon{background-position:-128px -384px}.uiEquipment .content .itemList .slot .icon,.uiEquipment .content .left .slot .icon,.uiEquipment .content .quick .slot .icon,.uiEquipment .content .right .slot .icon,.uiEquipment .content .runes .slot .icon,.uiEquipment .content .tools .slot .icon{height:100%}.uiEquipment .content .itemList .slot .info,.uiEquipment .content .left .slot .info,.uiEquipment .content .quick .slot .info,.uiEquipment .content .right .slot .info,.uiEquipment .content .runes .slot .info,.uiEquipment .content .tools .slot .info{left:6px;bottom:3px;position:absolute;color:#fcfcfc;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.uiEquipment .content .itemList .slot:hover .icon,.uiEquipment .content .left .slot:hover .icon,.uiEquipment .content .quick .slot:hover .icon,.uiEquipment .content .right .slot:hover .icon,.uiEquipment .content .runes .slot:hover .icon,.uiEquipment .content .tools .slot:hover .icon{filter:brightness(160%);-moz-filter:brightness(160%)}.uiEquipment .content .itemList .slot:hover.empty,.uiEquipment .content .left .slot:hover.empty,.uiEquipment .content .quick .slot:hover.empty,.uiEquipment .content .right .slot:hover.empty,.uiEquipment .content .runes .slot:hover.empty,.uiEquipment .content .tools .slot:hover.empty{background-color:rgba(72,237,255,.1)}.uiEquipment .content .itemList{display:none;position:absolute;left:0;top:0;width:100%;height:100%;background-color:#373041;padding:0;z-index:2;overflow-y:auto}.uiEquipment .content .itemList .slot{float:left;margin:8px 0 0 8px}.uiEquipment .content .itemList .slot .icon{position:relative}.uiEquipment .content .itemList .slot .icon.eq:before{content:'eq';left:-2px;bottom:-3px;position:absolute;color:#fcfcfc;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.uiEquipment .content .itemList .slot .icon.new:before{content:'new';left:-2px;bottom:-3px;position:absolute;color:#fcfcfc;filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136);-moz-filter:drop-shadow(0 -2px 0 #312136) drop-shadow(0 2px 0 #312136) drop-shadow(2px 0 0 #312136) drop-shadow(-2px 0 0 #312136)}.mobile .uiEquipment{width:calc(100% - 10px);height:calc(100% - 10px);margin-left:-5px;margin-top:-5px}.mobile .uiEquipment .content{flex-direction:column;flex-wrap:wrap;position:relative}.mobile .uiEquipment .content .main{width:calc(100% - 8px);height:calc(100% - 130px);padding:8px 8px 0 8px;justify-content:space-between;position:relative}.mobile .uiEquipment .content .main .left,.mobile .uiEquipment .content .main .quick,.mobile .uiEquipment .content .main .right{display:flex;flex-direction:row;justify-content:space-between;width:70%;height:calc(100% / 3)}.mobile .uiEquipment .content .main .left .slot,.mobile .uiEquipment .content .main .quick .slot,.mobile .uiEquipment .content .main .right .slot{margin-bottom:0}.mobile .uiEquipment .content .main .stats{width:30%;height:calc(100% + 74px);overflow-y:auto;position:absolute;right:0}.mobile .uiEquipment .content .main .quick{order:3;justify-content:center;padding:0 8px 0 0}.mobile .uiEquipment .content .main .left{padding:0 8px 0 0}.mobile .uiEquipment .content .main .right{order:2;padding:0 8px 0 0}.mobile .uiEquipment .content .runes{flex-direction:row;width:calc((100% - 16px) * .7);position:absolute;left:1px;bottom:8px;padding:0 8px 0 8px}
\ No newline at end of file
diff --git a/src/client/ui/templates/equipment/styles.less b/src/client/ui/templates/equipment/styles.less
index c6b01391..3998f425 100644
--- a/src/client/ui/templates/equipment/styles.less
+++ b/src/client/ui/templates/equipment/styles.less
@@ -337,10 +337,10 @@
}
.mobile .uiEquipment {
- width: 100%;
- height: 100%;
- margin-left: 5px;
- margin-top: 5px;
+ width: calc(100% - 10px);
+ height: calc(100% - 10px);
+ margin-left: -5px;
+ margin-top: -5px;
.content {
flex-direction: column;
diff --git a/src/client/ui/templates/party/party.js b/src/client/ui/templates/party/party.js
index ab07051d..15a06f17 100644
--- a/src/client/ui/templates/party/party.js
+++ b/src/client/ui/templates/party/party.js
@@ -39,7 +39,9 @@ define([
},
onGetConnectedPlayer: function (msg) {
- let party = this.party;
+ const { party } = this;
+ const { player: { serverId: playerId, zoneId: playerZone } } = window;
+
if (!party)
return;
@@ -47,25 +49,26 @@ define([
msg = [msg];
msg.forEach(m => {
+ const { id: mId, zoneId: mZone } = m;
+
if (party.indexOf(m.id) === -1)
return;
- let zone = m.zone;
- if (m.id === window.player.serverId) {
+ if (mId === playerId) {
party.forEach(p => {
- let player = globals.onlineList.find(o => o.id === p);
+ const mObj = globals.onlineList.find(o => o.id === p);
let el = this.find('.member[memberId="' + p + '"]');
el.removeClass('differentZone');
- if (player.zone !== zone)
+ if (mObj.mZone !== mZone)
el.addClass('differentZone');
});
} else {
let el = this.find('.member[memberId="' + m.id + '"]');
el.removeClass('differentZone');
- if (m.zone !== window.player.zone)
+ if (m.mZone !== playerZone)
el.addClass('differentZone');
el.find('.txtLevel').html('level: ' + m.level);
@@ -130,7 +133,7 @@ define([
.attr('memberId', p)
.on('contextmenu', this.showContext.bind(this, playerName, p));
- if (player.zone !== window.player.zone)
+ if (player.zoneId !== window.player.zoneId)
el.addClass('differentZone');
//Find stats
diff --git a/src/server/clientComponents/inventory.js b/src/server/clientComponents/inventory.js
index df681310..07adfade 100644
--- a/src/server/clientComponents/inventory.js
+++ b/src/server/clientComponents/inventory.js
@@ -56,7 +56,7 @@ define([
this.items.push.apply(this.items, blueprint.getItems || []);
- events.emit('onGetItems', this.items, rerender);
+ events.emit('onGetItems', this.items, rerender, blueprint.getItems);
}
},
diff --git a/src/server/clientComponents/sound.js b/src/server/clientComponents/sound.js
index 64edb170..28ee46f3 100644
--- a/src/server/clientComponents/sound.js
+++ b/src/server/clientComponents/sound.js
@@ -14,11 +14,11 @@ define([
init: function () {
const {
sound, volume, music, defaultMusic, loop = true,
- obj: { zoneId, x, y, width, height, area }
+ obj: { zoneName, x, y, width, height, area }
} = this;
const config = {
- scope: zoneId,
+ scope: zoneName,
file: sound,
volume,
x,
diff --git a/src/server/components/gatherer.js b/src/server/components/gatherer.js
index 11a5c7b1..e26061be 100644
--- a/src/server/components/gatherer.js
+++ b/src/server/components/gatherer.js
@@ -80,10 +80,10 @@ module.exports = {
}
if (this.gatheringTtl > 0) {
- if ((this.gatheringTtl === this.gatheringTtlMax) && (gathering.width)) {
- ['x', 'y', 'width', 'height'].forEach(function (p) {
+ if (this.gatheringTtl === this.gatheringTtlMax && gathering.width > 1) {
+ ['x', 'y', 'width', 'height'].forEach(p => {
this.obj.syncer.set(false, 'gatherer', p, gathering[p]);
- }, this);
+ });
}
this.gatheringTtl--;
@@ -124,7 +124,7 @@ module.exports = {
return;
}
- gatherResult.items.forEach(function (g) {
+ gatherResult.items.forEach(g => {
if (g.slot)
return;
@@ -150,7 +150,12 @@ module.exports = {
};
g.worth = ~~(weight * 10);
- }, this);
+ });
+ } else {
+ gatherResult.items.forEach(g => {
+ if (g.worth === undefined)
+ g.worth = 1;
+ });
}
if (isFish) {
diff --git a/src/server/components/mob.js b/src/server/components/mob.js
index 2f801faa..cd6e8285 100644
--- a/src/server/components/mob.js
+++ b/src/server/components/mob.js
@@ -126,7 +126,6 @@ module.exports = {
let distanceFromHome = Math.max(abs(this.originX - obj.x), abs(this.originY - obj.y));
if (!distanceFromHome) {
this.goHome = false;
-
if (!obj.spellbook) {
/* eslint-disable-next-line no-console */
console.log('MOB HAS NO SPELLBOOK BUT WANTS TO RESET ROTATION');
diff --git a/src/server/components/player.js b/src/server/components/player.js
index b441e523..3fe6331c 100644
--- a/src/server/components/player.js
+++ b/src/server/components/player.js
@@ -1,5 +1,4 @@
let classes = require('../config/spirits');
-let serverConfig = require('../config/serverConfig');
const eventEmitter = require('../misc/events');
module.exports = {
@@ -31,12 +30,12 @@ module.exports = {
skinId: character.skinId,
name: character.name,
class: character.class,
- zoneName: character.zoneName || serverConfig.defaultZone,
x: character.x,
y: character.y,
hidden: character.dead || null,
account: character.account,
- instanceId: character.instanceId || null
+ zoneName: character.zoneName || clientConfig.config.defaultZone,
+ zoneId: character.zoneId || null
});
character.components = character.components || [];
@@ -125,7 +124,7 @@ module.exports = {
let self = {
id: obj.id,
- zone: obj.zone,
+ zoneId: obj.zoneId,
name: obj.name,
level: obj.level,
class: obj.class
@@ -215,7 +214,7 @@ module.exports = {
};
obj.instance.eventEmitter.emit('onBeforePlayerRespawn', obj, spawnPos);
- if (!spawnPos.zone) {
+ if (!spawnPos.zoneName) {
obj.x = spawnPos.x;
obj.y = spawnPos.y;
@@ -251,7 +250,7 @@ module.exports = {
id: obj.serverId,
args: {
obj: simpleObj,
- newZone: spawnPos.zone
+ newZone: spawnPos.zoneName
}
});
}
diff --git a/src/server/components/trade.js b/src/server/components/trade.js
index e95a51d0..4697e747 100644
--- a/src/server/components/trade.js
+++ b/src/server/components/trade.js
@@ -275,7 +275,7 @@ module.exports = {
if (oldQuantity)
item.quantity = oldQuantity;
- let worth = ~~(item.worth * targetTrade.markup.buy);
+ let worth = ~~((item.quantity ?? 1) * item.worth * targetTrade.markup.buy);
this.gold += worth;
diff --git a/src/server/config/clientConfig.js b/src/server/config/clientConfig.js
index 6b6a2d47..07df4f00 100644
--- a/src/server/config/clientConfig.js
+++ b/src/server/config/clientConfig.js
@@ -203,7 +203,8 @@ const config = {
sounds: {
ui: []
},
- tos
+ tos,
+ defaultMap: 'fjolarok'
};
module.exports = {
diff --git a/src/server/config/maps/fjolarok/map.json b/src/server/config/maps/fjolarok/map.json
index 6d571c45..8c2ad5fc 100644
--- a/src/server/config/maps/fjolarok/map.json
+++ b/src/server/config/maps/fjolarok/map.json
@@ -497,140 +497,21 @@
"y":672
},
{
- "height":112,
+ "height":160,
"id":627,
"name":"",
"properties":[
{
"name":"cpnNotice",
"type":"string",
- "value":"{\"maxLevel\": 1, \"msg\": \"You open your eyes and cough. Saltwater burns your throat. You remember the storm, and the crash that left your ship in pieces.
You realize you need to find shelter. Use wasd<\/font> or the arrow keys<\/font> to move.\"}"
+ "value":"{ \"msg\": \"The Cape of Confusion\"}"
}],
"rotation":0,
"type":"",
"visible":true,
- "width":120,
- "x":704,
- "y":1096
- },
- {
- "height":32,
- "id":628,
- "name":"",
- "properties":[
- {
- "name":"cpnNotice",
- "type":"string",
- "value":"{\"maxLevel\": 1, \"msg\": \"You take a few steps, still weak from the ordeal. Through the glare of the sun, you see a creature to the north-east.
Press v<\/font> to toggle nameplates.\"}"
- }],
- "rotation":0,
- "type":"",
- "visible":true,
- "width":48,
- "x":840,
- "y":1096
- },
- {
- "height":80,
- "id":629,
- "name":"",
- "properties":[
- {
- "name":"cpnNotice",
- "type":"string",
- "value":"{\"maxLevel\": 1, \"msg\": \"You take a few steps, still weak from the ordeal. Through the glare of the sun, you see a creature to the north-east.
Press v<\/font> to toggle nameplates.\"}"
- }],
- "rotation":0,
- "type":"",
- "visible":true,
- "width":136,
- "x":824,
- "y":1128
- },
- {
- "height":40,
- "id":630,
- "name":"",
- "properties":[
- {
- "name":"cpnNotice",
- "type":"string",
- "value":"{\"maxLevel\": 1, \"msg\": \"The seagull's eyes are bloodshot and in its beak you see a glinting locket. It stole your family heirloom!
Click on it to target it then press space<\/font> to toggle auto-attack. Remember to stand close if you are using melee attacks.\"}"
- }],
- "rotation":0,
- "type":"",
- "visible":true,
- "width":8,
- "x":888,
- "y":1072
- },
- {
- "height":8,
- "id":631,
- "name":"",
- "properties":[
- {
- "name":"cpnNotice",
- "type":"string",
- "value":"{\"maxLevel\": 1, \"msg\": \"You take a few steps, still weak from the ordeal. Through the glare of the sun, you see a creature to the north-east.
Press v<\/font> to toggle nameplates.\"}"
- }],
- "rotation":0,
- "type":"",
- "visible":true,
- "width":8,
- "x":888,
- "y":1120
- },
- {
- "height":40,
- "id":632,
- "name":"",
- "properties":[
- {
- "name":"cpnNotice",
- "type":"string",
- "value":"{\"maxLevel\": 2, \"msg\": \"You can loot items by standing on them then open your inventory with i<\/font>.
To equip an item, simply right click the item in your inventory.\"}"
- }],
- "rotation":0,
- "type":"",
- "visible":true,
- "width":144,
- "x":888,
- "y":1032
- },
- {
- "height":32,
- "id":633,
- "name":"",
- "properties":[
- {
- "name":"cpnNotice",
- "type":"string",
- "value":"{\"maxLevel\": 2, \"msg\": \"Far to the north, you see a small shack. Civilization!
You can read more help by pressing h<\/font>.\"}"
- }],
- "rotation":0,
- "type":"",
- "visible":true,
- "width":144,
- "x":912,
- "y":1000
- },
- {
- "height":56,
- "id":634,
- "name":"",
- "properties":[
- {
- "name":"cpnNotice",
- "type":"string",
- "value":"{\"maxLevel\": 1, \"msg\": \"The seagull's eyes are bloodshot and in its beak you see a glinting locket. It stole your family heirloom!
Click on it to target it then press space<\/font> to toggle auto-attack. Remember to stand close if you are using melee attacks.\"}"
- }],
- "rotation":0,
- "type":"",
- "visible":true,
- "width":112,
- "x":896,
- "y":1072
+ "width":304,
+ "x":712,
+ "y":1048
},
{
"height":0,
@@ -2839,7 +2720,7 @@
{
"name":"spawn",
"type":"string",
- "value":"[{\"maxLevel\":1,\"x\":100,\"y\":150},{\"maxLevel\":999,\"x\":132,\"y\":82}]"
+ "value":"[{\"x\":132,\"y\":82}]"
}],
"renderorder":"right-down",
"tiledversion":"1.6.0",
diff --git a/src/server/config/maps/fjolarok/quests.js b/src/server/config/maps/fjolarok/quests.js
index a2ce18d4..fba99912 100644
--- a/src/server/config/maps/fjolarok/quests.js
+++ b/src/server/config/maps/fjolarok/quests.js
@@ -19,6 +19,6 @@ module.exports = {
name: 'Green Fingers',
type: 'gatherResource',
subType: 'herb',
- quantity: [5, 10]
+ quantity: [2, 5]
}]
};
diff --git a/src/server/config/maps/fjolarok/zone.js b/src/server/config/maps/fjolarok/zone.js
index 0a0a83d8..cd665a98 100644
--- a/src/server/config/maps/fjolarok/zone.js
+++ b/src/server/config/maps/fjolarok/zone.js
@@ -56,27 +56,7 @@ module.exports = {
},
'crazed seagull': {
level: 1,
-
- rare: {
- count: 0
- },
-
- regular: {
- drops: {
- rolls: 1,
- noRandom: true,
- blueprints: [{
- chance: 100,
- maxLevel: 2,
- name: 'Family Heirloom',
- quality: 1,
- slot: 'neck',
- type: 'Choker',
- noSalvage: true,
- stats: ['vit', 'regenMana']
- }]
- }
- }
+ attackable: false
},
seagull: {
level: 2,
diff --git a/src/server/config/quests/questBuilder.js b/src/server/config/quests/questBuilder.js
index 098a1075..9033ffd0 100644
--- a/src/server/config/quests/questBuilder.js
+++ b/src/server/config/quests/questBuilder.js
@@ -10,7 +10,7 @@ module.exports = {
},
obtain: function (obj, template) {
- let zoneName = template ? template.zoneName : obj.zoneName;
+ let zoneName = template?.zoneName ?? obj.zoneName;
let zone = mapList.mapList.find(m => m.name === zoneName);
//Zone doesn't exist any more. Probably been renamed
@@ -33,13 +33,18 @@ module.exports = {
zoneTemplate = globalQuests;
let config = extend({}, zoneTemplate);
- this.instance.eventEmitter.emit('onBeforeGetQuests', config);
+ this.instance.eventEmitter.emit('onBeforeGetQuests', {
+ obj,
+ config,
+ zoneName,
+ template
+ });
if (config.infini.length === 0)
return;
//Only check min level of quests when physically in the zone they belong to
if (obj.zoneName === zoneName) {
- const minPlayerLevel = ~~(obj.instance.map.zone.level[0] * 0.75);
+ const minPlayerLevel = ~~(obj.instance.zoneConfig.level[0] * 0.75);
if (obj.stats.values.level < minPlayerLevel)
return;
diff --git a/src/server/config/quests/templates/questGatherResource.js b/src/server/config/quests/templates/questGatherResource.js
index 4aa91839..78f8ada3 100644
--- a/src/server/config/quests/templates/questGatherResource.js
+++ b/src/server/config/quests/templates/questGatherResource.js
@@ -8,9 +8,11 @@ module.exports = {
build: function () {
if (!this.need) {
- this.need = 2 + ~~(Math.random() * 3);
+ const { quantity, subType } = this;
- this.gatherType = ['herb', 'fish'][~~(Math.random() * 2)];
+ this.need = quantity[0] + ~~(Math.random() * (quantity[1] - quantity[0]));
+
+ this.gatherType = subType ?? ['herb', 'fish'][~~(Math.random() * 2)];
if (this.gatherType === 'fish') {
this.name = 'Lure of the Sea';
diff --git a/src/server/config/quests/templates/questKillX.js b/src/server/config/quests/templates/questKillX.js
index 7a2a78ea..8b948b37 100644
--- a/src/server/config/quests/templates/questKillX.js
+++ b/src/server/config/quests/templates/questKillX.js
@@ -10,7 +10,7 @@ module.exports = {
//If we're not in the correct zone, don't do this check, it'll just crash the server
// since the mob won't be available (most likely) in the zoneFile
if (this.obj.zoneName === this.zoneName) {
- let mobTypes = this.obj.instance.spawners.zone.mobs;
+ let mobTypes = this.obj.instance.zoneConfig.mobs;
if (this.mobName) {
let mobType = mobTypes[this.mobName.toLowerCase()];
//Maybe the zoneFile changed in the meantime. If so, regenerate
diff --git a/src/server/config/quests/templates/questLootGen.js b/src/server/config/quests/templates/questLootGen.js
index 23521fbc..666dc33d 100644
--- a/src/server/config/quests/templates/questLootGen.js
+++ b/src/server/config/quests/templates/questLootGen.js
@@ -18,7 +18,7 @@ module.exports = {
//If we're not in the correct zone, don't do this check, it'll just crash the server
// since the mob won't be available (most likely) in the zoneFile
if (this.obj.zoneName === this.zoneName) {
- let mobTypes = this.obj.instance.spawners.zone.mobs;
+ let mobTypes = this.obj.instance.zoneConfig.mobs;
if (this.mobType && this.item) {
//Check if the zoneFile changed
diff --git a/src/server/config/quests/templates/questTemplate.js b/src/server/config/quests/templates/questTemplate.js
index 13867d90..f31a2584 100644
--- a/src/server/config/quests/templates/questTemplate.js
+++ b/src/server/config/quests/templates/questTemplate.js
@@ -6,7 +6,7 @@ module.exports = {
return false;
if (!this.xp) {
- let level = this.obj.instance.spawners.zone.level;
+ let level = this.obj.instance.zoneConfig.level;
level = level[0];
let xp = ~~(level * 22 * this.getXpMultiplier());
this.xp = xp;
diff --git a/src/server/config/serverConfig.js b/src/server/config/serverConfig.js
index 0ab213e6..5daf9883 100644
--- a/src/server/config/serverConfig.js
+++ b/src/server/config/serverConfig.js
@@ -2,7 +2,6 @@ module.exports = {
version: '0.10.6',
port: 4000,
startupMessage: 'Server: ready',
- defaultZone: 'fjolarok',
//Options:
// sqlite
diff --git a/src/server/mods/class-necromancer/index.js b/src/server/mods/class-necromancer/index.js
index db4823e2..f9e6b6f4 100644
--- a/src/server/mods/class-necromancer/index.js
+++ b/src/server/mods/class-necromancer/index.js
@@ -17,8 +17,8 @@ module.exports = {
this.events.on('onAfterGetZone', this.onAfterGetZone.bind(this));
},
- onAfterGetZone: function (zone, config) {
- if (zone !== 'fjolgard')
+ onAfterGetZone: function (zoneName, config) {
+ if (zoneName !== 'fjolgard')
return;
let newRunes = [{
diff --git a/src/server/objects/objBase.js b/src/server/objects/objBase.js
index eb824564..a0a09675 100644
--- a/src/server/objects/objBase.js
+++ b/src/server/objects/objBase.js
@@ -88,8 +88,6 @@ module.exports = {
getSimple: function (self, isSave, isTransfer) {
let s = this.simplify(null, self, isSave, isTransfer);
- if (this.instance)
- s.zoneId = this.instance.zoneId;
if (self && !isSave && this.syncer) {
this.syncer.oSelf.components
diff --git a/src/server/security/connections.js b/src/server/security/connections.js
index 2f628cbc..8ab275d3 100644
--- a/src/server/security/connections.js
+++ b/src/server/security/connections.js
@@ -104,8 +104,8 @@ module.exports = {
});
//If we don't do this, the atlas will try to remove it from the thread
- player.zoneName = null;
- player.name = null;
+ delete player.zoneName;
+ delete player.name;
//A hack to allow us to actually call methods again (like retrieve the player list)
player.dead = false;
@@ -151,7 +151,7 @@ module.exports = {
continue;
result.push({
- zone: p.zone,
+ zoneName: p.zoneName,
name: p.name,
level: p.level,
class: p.class,
@@ -164,7 +164,7 @@ module.exports = {
forceSaveAll: function () {
this.players
- .filter(p => p.zone)
+ .filter(p => p.zoneName !== undefined)
.forEach(p => {
atlas.performAction(p, {
cpn: 'auth',
diff --git a/src/server/security/connections/route.js b/src/server/security/connections/route.js
index c8a90eec..e4a908a4 100644
--- a/src/server/security/connections/route.js
+++ b/src/server/security/connections/route.js
@@ -27,7 +27,7 @@ const route = function (socket, msg) {
if (msg.callback)
msg.data.callbackId = atlas.registerCallback(msg.callback);
- atlas.send(source.zone, msg);
+ atlas.send(source.zoneId, msg);
return;
}
diff --git a/src/server/security/router.js b/src/server/security/router.js
index 8cbb225d..9c0dc02c 100644
--- a/src/server/security/router.js
+++ b/src/server/security/router.js
@@ -45,7 +45,7 @@ module.exports = {
keysCorrect: function (obj, keys) {
const foundIncorrect = keys.some(({ key, dataType, optional, spec }) => {
- if (!obj.hasOwnProperty(key)) {
+ if (!Object.hasOwnProperty.call(obj, key)) {
if (optional)
return false;
@@ -127,7 +127,7 @@ module.exports = {
return keysCorrect;
},
- isMsgValid: function (msg) {
+ isMsgValid: function (msg, source) {
let signature;
if (msg.module) {
@@ -152,8 +152,12 @@ module.exports = {
const result = this.signatureCorrect(msg, signature);
- if (!result || msg.cpn !== 'player' || msg.method !== 'performAction')
+ if (!result || msg.cpn !== 'player' || msg.method !== 'performAction') {
+ if (result && signature.allowWhenIngame === false && source.name !== undefined)
+ return false;
+
return result;
+ }
const signatureThreadMsg = signatures.threadCpnMethods[msg.data.cpn]?.[msg.data.method];
diff --git a/src/server/security/routerConfig.js b/src/server/security/routerConfig.js
index 19ef9d7a..c7723bd2 100644
--- a/src/server/security/routerConfig.js
+++ b/src/server/security/routerConfig.js
@@ -49,6 +49,7 @@ const routerConfig = {
auth: {
login: {
callback: true,
+ allowWhenIngame: false,
data: [
{
key: 'username',
@@ -62,6 +63,7 @@ const routerConfig = {
},
register: {
callback: true,
+ allowWhenIngame: false,
data: [
{
key: 'username',
@@ -75,6 +77,7 @@ const routerConfig = {
},
deleteCharacter: {
callback: true,
+ allowWhenIngame: false,
data: [
{
key: 'name',
@@ -88,6 +91,7 @@ const routerConfig = {
},
createCharacter: {
callback: true,
+ allowWhenIngame: false,
data: [
{
key: 'name',
@@ -109,10 +113,12 @@ const routerConfig = {
},
getCharacterList: {
callback: true,
+ allowWhenIngame: false,
data: []
},
getCharacter: {
callback: true,
+ allowWhenIngame: false,
data: [
{
key: 'name',
@@ -122,6 +128,7 @@ const routerConfig = {
},
play: {
callback: true,
+ allowWhenIngame: false,
data: [
{
key: 'name',
diff --git a/src/server/server/onConnection.js b/src/server/server/onConnection.js
index 90a0142e..3e796d63 100644
--- a/src/server/server/onConnection.js
+++ b/src/server/server/onConnection.js
@@ -16,7 +16,9 @@ const onRequest = (socket, msg, callback) => {
if (!msg.data)
msg.data = {};
- if (!router.isMsgValid(msg))
+ const source = cons.players.find(p => p.socket.id === socket.id);
+
+ if (!router.isMsgValid(msg, source))
return;
if (msg.cpn)
@@ -24,8 +26,6 @@ const onRequest = (socket, msg, callback) => {
else if (msg.threadModule)
cons.route(socket, msg);
else {
- const source = cons.players.find(p => p.socket.id === socket.id);
-
msg.socket = socket;
if (source)
diff --git a/src/server/world/atlas.js b/src/server/world/atlas.js
index 9a0a7c7a..b0909588 100644
--- a/src/server/world/atlas.js
+++ b/src/server/world/atlas.js
@@ -2,7 +2,6 @@ let childProcess = require('child_process');
let objects = require('../objects/objects');
let mapList = require('../config/maps/mapList');
let connections = require('../security/connections');
-let serverConfig = require('../config/serverConfig');
let events = require('../misc/events');
const listenersOnZoneIdle = [];
@@ -17,79 +16,120 @@ module.exports = {
this.getMapFiles();
},
- addObject: function (obj, keepPos, transfer) {
+ addObject: async function (obj, keepPos, transfer) {
+ const serverObj = objects.objects.find(o => o.id === obj.id);
+ if (!serverObj)
+ return;
+
events.emit('onBeforePlayerEnterWorld', obj);
- let thread = this.getThreadFromName(obj.zoneName);
+ let thread;
+
+ let map = mapList.mapList.find(m => m.name === obj.zoneName);
+
+ if (!map)
+ map = mapList.mapList.find(m => m.name === clientConfig.config.defaultZone);
- let instanceId = obj.instanceId;
- if ((!thread) || (obj.zoneName !== thread.name))
- instanceId = -1;
+ thread = this.threads.find(t => t.id === obj.zoneId && t.name === obj.zoneName);
if (!thread) {
- thread = this.getThreadFromName(serverConfig.defaultZone);
- obj.zoneName = thread.name;
+ if (map.instanced) {
+ delete obj.x;
+ delete obj.y;
+ thread = this.spawnMap(map);
+
+ await new Promise(res => setTimeout(res, 2000));
+ } else
+ thread = this.getThreadFromName(map.name);
}
- obj.zone = thread.id;
- this.send(obj.zone, {
+ obj.zoneName = thread.name;
+ obj.zoneId = thread.id;
+
+ serverObj.zoneId = thread.id;
+ serverObj.zoneName = thread.name;
+
+ const simpleObj = obj.getSimple ? obj.getSimple(true, true) : obj;
+
+ this.send(obj.zoneId, {
method: 'addObject',
args: {
keepPos: keepPos,
- obj: obj.getSimple ? obj.getSimple(true, true) : obj,
- instanceId: instanceId,
+ obj: simpleObj,
transfer: transfer
}
});
},
+
+ removeObjectFromInstancedZone: async function (thread, obj, callback) {
+ await new Promise(res => {
+ const cb = this.registerCallback(res);
+
+ thread.worker.send({
+ method: 'forceSavePlayer',
+ args: {
+ playerName: obj.name,
+ callbackId: cb
+ }
+ });
+ });
+
+ thread.worker.kill();
+ this.threads.spliceWhere(t => t === thread);
+
+ if (callback)
+ callback();
+ },
+
removeObject: function (obj, skipLocal, callback) {
if (!skipLocal)
objects.removeObject(obj);
- let thread = this.getThreadFromName(obj.zoneName);
- if (!thread)
+ let thread = this.findObjectThread(obj);
+ if (!thread)
+ return;
+
+ if (thread.instanced) {
+ this.removeObjectFromInstancedZone(thread, obj, callback);
+
return;
+ }
let callbackId = null;
if (callback)
callbackId = this.registerCallback(callback);
- obj.zone = thread.id;
- this.send(obj.zone, {
+ this.send(obj.zoneId, {
method: 'removeObject',
args: {
obj: obj.getSimple(true),
- instanceId: obj.instanceId,
callbackId: callbackId
}
});
},
updateObject: function (obj, msgObj) {
- this.send(obj.zone, {
+ this.send(obj.zoneId, {
method: 'updateObject',
args: {
id: obj.id,
- instanceId: obj.instanceId,
obj: msgObj
}
});
},
queueAction: function (obj, action) {
- this.send(obj.zone, {
+ this.send(obj.zoneId, {
method: 'queueAction',
args: {
id: obj.id,
- instanceId: obj.instanceId,
action: action
}
});
},
performAction: function (obj, action) {
- this.send(obj.zone, {
+ this.send(obj.zoneId, {
method: 'performAction',
args: {
id: obj.id,
- instanceId: obj.instanceId,
action: action
}
});
@@ -111,29 +151,34 @@ module.exports = {
callback.callback(msg.msg.result);
},
- send: function (zone, msg) {
- let thread = this.getThreadFromId(zone);
+ send: function (threadId, msg) {
+ const thread = this.threads.find(t => t.id === threadId);
if (thread)
thread.worker.send(msg);
},
- getThreadFromId: function (id) {
- return this.threads.find(t => t.id === id);
+ findObjectThread: function ({ zoneId }) {
+ return this.threads.find(t => t.id === zoneId);
},
getThreadFromName: function (name) {
return this.threads.find(t => t.name === name);
},
getMapFiles: function () {
- mapList.mapList.filter(m => !m.disabled).forEach(m => this.spawnMap(m));
+ mapList.mapList
+ .filter(m => !m.disabled && !m.instanced)
+ .forEach(m => this.spawnMap(m));
},
- spawnMap: function (map) {
- const worker = childProcess.fork('./world/worker', [map.name]);
+ spawnMap: function ({ name, path, instanced }) {
+ const worker = childProcess.fork('./world/worker', [name]);
+
+ const id = instanced ? _.getGuid() : name;
const thread = {
- id: this.nextId++,
- name: map.name,
- path: map.path,
+ id,
+ name,
+ instanced,
+ path,
worker
};
@@ -143,6 +188,8 @@ module.exports = {
});
this.threads.push(thread);
+
+ return thread;
},
onMessage: function (thread, message) {
if (message.module)
@@ -167,9 +214,9 @@ module.exports = {
thread.worker.send({
method: 'init',
args: {
- name: thread.name,
- path: thread.path,
- zoneId: thread.id
+ zoneName: thread.name,
+ zoneId: thread.id,
+ path: thread.path
}
});
},
@@ -209,31 +256,33 @@ module.exports = {
});
},
- rezone: function (thread, message) {
+ rezone: async function (thread, message) {
const { args: { obj, newZone, keepPos = true } } = message;
+ //When messages are sent from map threads, they have an id (id of the object in the map thread)
+ // as well as a serverId (id of the object in the main thread)
+ const serverId = obj.serverId;
+ obj.id = serverId;
obj.destroyed = false;
- obj.zoneName = newZone;
- obj.id = obj.serverId;
-
- let serverObj = objects.objects.find(o => o.id === obj.id);
- serverObj.zoneName = obj.zoneName;
- let newThread = this.getThreadFromName(obj.zoneName);
+ const serverObj = objects.objects.find(o => o.id === obj.id);
+ const mapExists = mapList.mapList.some(m => m.name === newZone);
- if (!newThread) {
- newThread = this.getThreadFromName(serverConfig.defaultZone);
- obj.zoneName = newThread.name;
- serverObj.zoneName = newThread.name;
+ if (mapExists) {
+ serverObj.zoneName = newZone;
+ obj.zoneName = newZone;
+ } else {
+ obj.zoneName = clientConfig.config.defaultZone;
+ serverObj.zoneName = clientConfig.config.defaultZone;
}
- serverObj.zone = newThread.id;
- obj.zone = newThread.id;
+ delete serverObj.zoneId;
+ delete obj.zoneId;
serverObj.player.broadcastSelf();
const isRezone = true;
- this.addObject(obj, keepPos, isRezone);
+ await this.addObject(obj, keepPos, isRezone);
},
onZoneIdle: function (thread) {
diff --git a/src/server/world/customMap.js b/src/server/world/customMap.js
index 8362d861..dc60cb11 100644
--- a/src/server/world/customMap.js
+++ b/src/server/world/customMap.js
@@ -7,7 +7,7 @@ module.exports = {
load: function (instance, objToAdd, callback) {
this.instance = instance;
- this.ent = instance.zone.name + '-' + objToAdd.components.find(c => c.type === 'auth').username;
+ this.ent = instance.mapName + '-' + objToAdd.components.find(c => c.type === 'auth').username;
io.get({
ent: this.ent,
diff --git a/src/server/world/instancer.js b/src/server/world/instancer.js
index 94ddbc13..44602496 100644
--- a/src/server/world/instancer.js
+++ b/src/server/world/instancer.js
@@ -27,7 +27,10 @@ module.exports = {
lastTime: 0,
init: function (args) {
- this.zoneId = args.zoneId;
+ const { zoneId, zoneName } = args;
+
+ this.zoneName = zoneName;
+ this.zoneId = zoneId;
spellCallbacks.init();
herbs.init();
@@ -37,15 +40,16 @@ module.exports = {
objects,
syncer,
physics,
- zoneId: this.zoneId,
+ zoneId,
+ zoneName,
spawners,
questBuilder,
events,
- zone: map.zone,
map,
scheduler,
eventEmitter,
- resourceSpawner
+ resourceSpawner,
+ zoneConfig: map.zoneConfig
};
this.instances.push(fakeInstance);
diff --git a/src/server/world/map.js b/src/server/world/map.js
index 776223e4..d6ead04e 100644
--- a/src/server/world/map.js
+++ b/src/server/world/map.js
@@ -68,18 +68,18 @@ module.exports = {
hiddenWalls: null,
hiddenTiles: null,
- zone: null,
+ zoneConfig: null,
- init: function (args) {
- this.name = args.name;
- this.path = args.path;
+ init: function ({ zoneName, path }) {
+ this.name = zoneName;
+ this.path = path;
try {
- this.zone = require('../' + this.path + '/' + this.name + '/zone');
+ this.zoneConfig = require('../' + this.path + '/' + this.name + '/zone');
} catch (e) {
- this.zone = globalZone;
+ this.zoneConfig = globalZone;
}
- events.emit('onAfterGetZone', this.name, this.zone);
+ events.emit('onAfterGetZone', this.name, this.zoneConfig);
let chats = null;
try {
@@ -87,10 +87,10 @@ module.exports = {
} catch (e) {}
if (chats) {
- if (this.zone.chats)
- extend(this.zone.chats, chats);
+ if (this.zoneConfig.chats)
+ extend(this.zoneConfig.chats, chats);
else
- this.zone.chats = chats;
+ this.zoneConfig.chats = chats;
}
let dialogues = null;
@@ -99,11 +99,11 @@ module.exports = {
} catch (e) {}
events.emit('onBeforeGetDialogue', this.name, dialogues);
if (dialogues)
- this.zone.dialogues = dialogues;
+ this.zoneConfig.dialogues = dialogues;
- this.zone = extend({}, globalZone, this.zone);
+ this.zoneConfig = extend({}, globalZone, this.zoneConfig);
- let resources = this.zone.resources || {};
+ let resources = this.zoneConfig.resources || {};
for (let r in resources)
resourceSpawner.register(r, resources[r]);
@@ -456,11 +456,11 @@ module.exports = {
if (objZoneName !== name)
blueprint.objZoneName = objZoneName;
- if (this.zone) {
- if ((this.zone.objects) && (this.zone.objects[objZoneName.toLowerCase()]))
- extend(blueprint, this.zone.objects[objZoneName.toLowerCase()]);
- else if ((this.zone.objects) && (this.zone.mobs[objZoneName.toLowerCase()]))
- extend(blueprint, this.zone.mobs[objZoneName.toLowerCase()]);
+ if (this.zoneConfig) {
+ if ((this.zoneConfig.objects) && (this.zoneConfig.objects[objZoneName.toLowerCase()]))
+ extend(blueprint, this.zoneConfig.objects[objZoneName.toLowerCase()]);
+ else if ((this.zoneConfig.objects) && (this.zoneConfig.mobs[objZoneName.toLowerCase()]))
+ extend(blueprint, this.zoneConfig.mobs[objZoneName.toLowerCase()]);
}
if (blueprint.blocking)
diff --git a/src/server/world/mobBuilder.js b/src/server/world/mobBuilder.js
index a5cb9bfa..816c6e2e 100644
--- a/src/server/world/mobBuilder.js
+++ b/src/server/world/mobBuilder.js
@@ -76,15 +76,15 @@ module.exports = {
mob.inventory.inventorySize = -1;
mob.inventory.dailyDrops = blueprint.dailyDrops;
- if (this.zone) {
- let chats = this.zone.chats;
+ if (this.zoneConfig) {
+ let chats = this.zoneConfig.chats;
if (chats && chats[mob.name.toLowerCase()]) {
mob.addComponent('chatter', {
chats: chats[mob.name.toLowerCase()]
});
}
- let dialogues = this.zone.dialogues;
+ let dialogues = this.zoneConfig.dialogues;
if (dialogues && dialogues[mob.name.toLowerCase()]) {
mob.addComponent('dialogue', {
config: dialogues[mob.name.toLowerCase()]
diff --git a/src/server/world/randomMap/spawnObjects.js b/src/server/world/randomMap/spawnObjects.js
index bc454b94..0b5d9083 100644
--- a/src/server/world/randomMap/spawnObjects.js
+++ b/src/server/world/randomMap/spawnObjects.js
@@ -1,6 +1,7 @@
+const spawners = require('../spawners');
+
const spawnObjects = (scope, instance, room) => {
let template = room.template;
- let spawners = instance.spawners;
let spawnCd = instance.map.mapFile.properties.spawnCd;
template.objects.forEach(o => {
diff --git a/src/server/world/resourceSpawner.js b/src/server/world/resourceSpawner.js
index 0449f784..09b5ff03 100644
--- a/src/server/world/resourceSpawner.js
+++ b/src/server/world/resourceSpawner.js
@@ -5,7 +5,7 @@ module.exports = {
objects: null,
syncer: null,
- zone: null,
+ zoneConfig: null,
physics: null,
map: null,
@@ -17,7 +17,7 @@ module.exports = {
syncer: instance.syncer,
physics: instance.physics,
map: instance.map,
- zone: instance.zone
+ zoneConfig: instance.zoneConfig
});
},
@@ -76,7 +76,7 @@ module.exports = {
let position = null;
- if (blueprint.type === 'herb') {
+ if (blueprint.type === 'herb' && !blueprint.positions) {
x = ~~(Math.random() * w);
y = ~~(Math.random() * h);
@@ -124,7 +124,7 @@ module.exports = {
if (blueprint.quantity)
quantity = blueprint.quantity[0] + ~~(Math.random() * (blueprint.quantity[1] - blueprint.quantity[0]));
- let zoneLevel = this.zone.level;
+ let zoneLevel = this.zoneConfig.level;
zoneLevel = ~~(zoneLevel[0] + ((zoneLevel[1] - zoneLevel[0]) / 2));
let objBlueprint = extend({}, blueprint, position);
diff --git a/src/server/world/rezoneManager.js b/src/server/world/rezoneManager.js
index 08bf8a97..dd1fdbca 100644
--- a/src/server/world/rezoneManager.js
+++ b/src/server/world/rezoneManager.js
@@ -35,7 +35,7 @@ const doRezone = stagedRezone => {
const clientAck = msg => {
const staged = stagedRezones.find(s => s.simplifiedObj.serverId === msg.sourceId);
- if (!staged)
+ if (!staged)
return;
stagedRezones.spliceWhere(s => s === staged);
diff --git a/src/server/world/spawners.js b/src/server/world/spawners.js
index 22fd59ca..ea611bef 100644
--- a/src/server/world/spawners.js
+++ b/src/server/world/spawners.js
@@ -9,9 +9,9 @@ module.exports = {
init: function (msg) {
this.objects = msg.objects;
this.syncer = msg.syncer;
- this.zone = msg.zone;
+ this.zoneConfig = msg.zoneConfig;
this.mobBuilder = extend({
- zone: this.zone
+ zoneConfig: this.zoneConfig
}, mobBuilder);
},
@@ -40,7 +40,7 @@ module.exports = {
else
this.mobTypes[name]++;
- spawner.zonePrint = extend({}, this.zone.mobs.default, this.zone.mobs[name] || {});
+ spawner.zonePrint = extend({}, this.zoneConfig.mobs.default, this.zoneConfig.mobs[name] || {});
},
spawn: function (spawner) {
@@ -162,7 +162,7 @@ module.exports = {
if (l.blueprint.layerName === 'mobs')
this.setupMob(mob, l.zonePrint);
else {
- const blueprint = extend({}, this.zone.objects.default, this.zone.objects[name] || {});
+ const blueprint = extend({}, this.zoneConfig.objects.default, this.zoneConfig.objects[name] || {});
this.setupObj(mob, blueprint);
}
@@ -194,7 +194,7 @@ module.exports = {
this.setupObj(mob, blueprint);
- this.mobBuilder.build(mob, blueprint, type, this.zone.name);
+ this.mobBuilder.build(mob, blueprint, type, this.zoneConfig.name);
},
setupObj: function (obj, blueprint) {