mirror of
https://github.com/danbulant/flying-squid
synced 2026-06-13 03:21:03 +00:00
Lots and lots and lots of changes... Plugins begin again!
This commit is contained in:
parent
808b5a0149
commit
cb88a5cbbb
15 changed files with 195 additions and 54 deletions
4
.gitignore
vendored
4
.gitignore
vendored
|
|
@ -2,4 +2,6 @@ node_modules
|
|||
dist/
|
||||
modpePlugins/
|
||||
config/settings.json
|
||||
logs/
|
||||
logs/
|
||||
src/plugins/*
|
||||
!src/plugins/README.md
|
||||
|
|
|
|||
3
app.js
3
app.js
|
|
@ -21,7 +21,8 @@ var options = {
|
|||
generation:settings.generation,
|
||||
'modpe': settings.modpe,
|
||||
kickTimeout: settings.kickTimeout ? settings.kickTimeout : 10*1000,
|
||||
regionFolder: settings.regionFolder
|
||||
regionFolder: settings.regionFolder,
|
||||
plugins: settings.plugins
|
||||
};
|
||||
|
||||
module.exports=mcServer.createMCServer(options);
|
||||
|
|
|
|||
|
|
@ -10,6 +10,9 @@
|
|||
"options":{
|
||||
"worldHeight":80
|
||||
}
|
||||
},
|
||||
"plugins": {
|
||||
|
||||
},
|
||||
"modpe": false
|
||||
}
|
||||
|
|
|
|||
|
|
@ -32,5 +32,6 @@ class MCServer extends EventEmitter {
|
|||
if(options.logging == true) this.createLog();
|
||||
this._server.on('error', error => this.emit('error',error));
|
||||
this._server.on('listening', () => this.emit('listening',this._server.socketServer.address().port));
|
||||
this.emit('asap');
|
||||
}
|
||||
}
|
||||
|
|
@ -1,16 +1,21 @@
|
|||
module.exports = (obj) => {
|
||||
return (eventName, data, func, opt) => {
|
||||
return async (eventName, data, func, opt) => {
|
||||
var hiddenCancelled = false;
|
||||
var cancelled = false;
|
||||
var cancelCount = 0;
|
||||
var cancel = (hidden) => { // Hidden shouldn't be used often but it's not hard to implement so meh
|
||||
if (hidden) hiddenCancelled = true;
|
||||
else cancelled = true;
|
||||
else {
|
||||
cancelled = true;
|
||||
cancelCount++;
|
||||
}
|
||||
}
|
||||
obj.emit(eventName + '_cancel', data, cancel);
|
||||
obj.emit(eventName, data, cancelled);
|
||||
|
||||
await obj.emit(eventName + '_cancel', data, cancel);
|
||||
await obj.emit(eventName, data, cancelled, cancelCount);
|
||||
|
||||
if (!hiddenCancelled && !cancelled) func(data);
|
||||
if (!hiddenCancelled && !cancelled) await func(data);
|
||||
|
||||
obj.emit(eventName + '_done', data, cancelled);
|
||||
await obj.emit(eventName + '_done', data, cancelled);
|
||||
}
|
||||
}
|
||||
|
|
@ -24,7 +24,7 @@ class Command {
|
|||
return res;
|
||||
}
|
||||
|
||||
use(command) {
|
||||
async use(command) {
|
||||
var res = this.find(command);
|
||||
|
||||
if(res) {
|
||||
|
|
@ -42,7 +42,7 @@ class Command {
|
|||
res[1].shift();
|
||||
}
|
||||
|
||||
res = res[0].params.action(res[1]);
|
||||
res = await res[0].params.action(res[1]);
|
||||
if(res) return '' + res;
|
||||
} else {
|
||||
return 'Command not found';
|
||||
|
|
|
|||
9
src/lib/plugins/behavior.js
Normal file
9
src/lib/plugins/behavior.js
Normal file
|
|
@ -0,0 +1,9 @@
|
|||
var Behavior = require('../behavior');
|
||||
|
||||
module.exports.server = function(serv) {
|
||||
serv.behavior = new Behavior(serv);
|
||||
}
|
||||
|
||||
module.exports.entity = function(entity, serv) {
|
||||
entity.behavior = new Behavior(entity);
|
||||
}
|
||||
|
|
@ -75,7 +75,6 @@ module.exports.player=function(player) {
|
|||
|
||||
|
||||
player.handleCommand = (str) => {
|
||||
var res = player.commands.use(str);
|
||||
if(res) player.chat('' + res);
|
||||
player.commands.use(str);
|
||||
};
|
||||
};
|
||||
|
|
|
|||
|
|
@ -6,18 +6,45 @@ module.exports.player=function(player,serv)
|
|||
var pos=new Vec3(location.x,location.y,location.z);
|
||||
player.world.getBlock(pos)
|
||||
.then(block => {
|
||||
currentlyDugBlock=block;
|
||||
if(currentlyDugBlock.type==0) return;
|
||||
if(status==0 && player.gameMode!=1)
|
||||
startDigging(pos);
|
||||
else if(status==2)
|
||||
completeDigging(pos);
|
||||
else if(status==1)
|
||||
cancelDigging(pos);
|
||||
else if(status==0 && player.gameMode==1)
|
||||
creativeDigging(pos);
|
||||
})
|
||||
.catch((err)=> setTimeout(() => {throw err;},0));
|
||||
player.behavior('digPacket', {
|
||||
position: pos,
|
||||
status: status,
|
||||
block: block
|
||||
}, ({position,status,block}) => {
|
||||
currentlyDugBlock=block;
|
||||
if(currentlyDugBlock.type==0) return;
|
||||
if(status==0 && player.gameMode!=1)
|
||||
player.behavior('dig', { // Start dig survival
|
||||
position: position,
|
||||
block: block
|
||||
}, ({position}) => {
|
||||
return startDigging(position);
|
||||
});
|
||||
else if(status==2)
|
||||
player.behavior('finishDig', { // Finish dig survival
|
||||
position: position,
|
||||
block: block
|
||||
}, ({position}) => {
|
||||
return completeDigging(position);
|
||||
});
|
||||
else if(status==1)
|
||||
player.behavior('cancelDig', { // Cancel dig survival
|
||||
position: position,
|
||||
block: block
|
||||
}, ({position}) => {
|
||||
return cancelDigging(position);
|
||||
});
|
||||
else if(status==0 && player.gameMode==1)
|
||||
player.behavior('dig', { // Start/finish dig creative
|
||||
position: position,
|
||||
block: block
|
||||
}, ({position}) => {
|
||||
return creativeDigging(position);
|
||||
});
|
||||
}
|
||||
)}
|
||||
)
|
||||
.catch((err)=> setTimeout(() => {throw err;},0))
|
||||
});
|
||||
|
||||
function diggingTime(location)
|
||||
|
|
|
|||
62
src/lib/plugins/external.js
Normal file
62
src/lib/plugins/external.js
Normal file
|
|
@ -0,0 +1,62 @@
|
|||
module.exports.server = function(serv, settings) {
|
||||
serv.plugins = {};
|
||||
serv.pluginCount = 0;
|
||||
serv.externalPluginsLoaded = false;
|
||||
|
||||
serv.addPlugin = (name, plugin, set) => {
|
||||
if (!name || !plugin) throw new Error('You need a name and object for your plugin!');
|
||||
serv.plugins[name] = {
|
||||
id: serv.pluginCount,
|
||||
name: name,
|
||||
player: plugin.player,
|
||||
entity: plugin.entity,
|
||||
server: plugin.server,
|
||||
settings: set,
|
||||
enabled: true
|
||||
};
|
||||
serv.pluginCount++;
|
||||
if (serv.externalPluginsLoaded && plugin.server) serv.plugins[name].server.call(p, serv, settings);
|
||||
}
|
||||
|
||||
for (var p in settings.plugins) {
|
||||
try {
|
||||
serv.addPlugin(p, require(p), settings.plugins[p]);
|
||||
} catch (err) {
|
||||
try {
|
||||
serv.addPlugin(p, require('../../plugins/' + p), settings.plugins[p]);
|
||||
} catch (err) {
|
||||
throw new Error('Cannot find plugin "' + p + '"');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (var p in serv.plugins) {
|
||||
if (serv.plugins[p].server) serv.plugins[p].server.call(serv.plugins[p], serv, settings);
|
||||
}
|
||||
serv.externalPluginsLoaded = true;
|
||||
};
|
||||
|
||||
module.exports.player = function(player, serv) {
|
||||
Object.keys(serv.plugins).forEach(p => {
|
||||
var plugin = serv.plugins[p];
|
||||
if (plugin.player) plugin.player.call(plugin, player, serv);
|
||||
});
|
||||
};
|
||||
|
||||
module.exports.entity = function(entity, serv) {
|
||||
entity.pluginData = {};
|
||||
|
||||
Object.keys(serv.plugins).forEach(p => {
|
||||
entity.pluginData[p] = {};
|
||||
});
|
||||
|
||||
entity.getData = (pluginName) => {
|
||||
if (typeof pluginName == 'object') pluginName = pluginName.name;
|
||||
return entity.pluginData[pluginName] || null;
|
||||
}
|
||||
|
||||
Object.keys(serv.plugins).forEach(p => {
|
||||
var plugin = serv.plugins[p];
|
||||
if (plugin.entity) plugin.entity.call(plugin, entity, serv);
|
||||
});
|
||||
}
|
||||
|
|
@ -12,15 +12,16 @@ module.exports.server=function(serv,options)
|
|||
client.on('error',error => serv.emit('clientError',client,error)));
|
||||
|
||||
serv._server.on('login', async (client) => {
|
||||
var player = serv.initEntity('player', null, serv.overworld, new Vec3(0,0,0));
|
||||
player._client=client;
|
||||
player.commands = new Command({});
|
||||
Object.keys(plugins)
|
||||
.filter(pluginName => plugins[pluginName].player!=undefined)
|
||||
.forEach(pluginName => plugins[pluginName].player(player, serv, options));
|
||||
|
||||
serv.emit("newPlayer",player);
|
||||
try {
|
||||
var player = serv.initEntity('player', null, serv.overworld, new Vec3(0,0,0));
|
||||
player._client=client;
|
||||
player.commands = new Command({});
|
||||
Object.keys(plugins)
|
||||
.filter(pluginName => plugins[pluginName].player!=undefined)
|
||||
.forEach(pluginName => plugins[pluginName].player(player, serv, options));
|
||||
|
||||
serv.emit("newPlayer",player);
|
||||
player.emit('asap');
|
||||
await player.login();
|
||||
}
|
||||
catch(err){
|
||||
|
|
|
|||
|
|
@ -1,13 +1,12 @@
|
|||
var Vec3 = require("vec3").Vec3;
|
||||
|
||||
module.exports.server=function(serv) {
|
||||
serv.emitParticle = (particle, world, position, {whitelist,blacklist=[],radius=32*32,longDistance=true,size,count=1}={}) => {
|
||||
serv.emitParticle = (particle, world, position, {whitelist,blacklist=[],radius=32*32,longDistance=true,size=new Vec3(1, 1, 1),count=1}={}) => {
|
||||
var players = (typeof whitelist != 'undefined' ? (typeof whitelist == 'array' ? whitelist : [whitelist]) : serv.getNearby({
|
||||
world: world,
|
||||
position: position.scaled(32).floored(),
|
||||
radius: radius // 32 blocks, fixed position
|
||||
}));
|
||||
if (!size) size = new Vec3(1.0, 1.0, 1.0);
|
||||
|
||||
serv._writeArray('world_particles', {
|
||||
particleId: particle,
|
||||
|
|
|
|||
|
|
@ -18,26 +18,35 @@ module.exports.player=function(player,serv)
|
|||
var referencePosition=new Vec3(location.x,location.y,location.z);
|
||||
var directionVector=directionToVector[direction];
|
||||
var placedPosition=referencePosition.plus(directionVector);
|
||||
player.world.getBlockType(referencePosition).then((id) => {
|
||||
if([25].indexOf(id) != -1) return;
|
||||
var sound = 'dig.' + (materialToSound[blocks[heldItem.blockId].material] || 'stone');
|
||||
serv.playSound(sound, player.world, placedPosition.clone().add(new Vec3(0.5, 0.5, 0.5)), {
|
||||
pitch: 0.8
|
||||
});
|
||||
player.behavior('placeBlock', {
|
||||
direction: directionVector,
|
||||
heldItem: heldItem,
|
||||
id: heldItem.blockId,
|
||||
damage: heldItem.itemDamage,
|
||||
position: placedPosition,
|
||||
reference: referencePosition,
|
||||
playSound: true,
|
||||
sound: 'dig.' + (materialToSound[blocks[heldItem.blockId].material] || 'stone')
|
||||
}, ({direction, heldItem, position, reference, playSound, sound}) => {
|
||||
if (playSound) {
|
||||
serv.playSound(sound, player.world, placedPosition.clone().add(new Vec3(0.5, 0.5, 0.5)), {
|
||||
pitch: 0.8
|
||||
});
|
||||
}
|
||||
if(heldItem.blockId!=323){
|
||||
player.changeBlock(placedPosition,heldItem.blockId,heldItem.itemDamage);
|
||||
player.changeBlock(position,heldItem.blockId,heldItem.itemDamage);
|
||||
}else if(direction==1){
|
||||
player.setBlock(placedPosition, 63, 0);
|
||||
player.setBlock(position, 63, 0);
|
||||
player._client.write('open_sign_entity', {
|
||||
location:placedPosition
|
||||
location:position
|
||||
});
|
||||
}else{
|
||||
player.setBlock(placedPosition, 68, 0);
|
||||
player.setBlock(position, 68, 0);
|
||||
player._client.write('open_sign_entity', {
|
||||
location:placedPosition
|
||||
location:position
|
||||
});
|
||||
}
|
||||
}).catch((err)=> setTimeout(() => {throw err;},0));
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -21,12 +21,14 @@ module.exports.server=function(serv) {
|
|||
});
|
||||
};
|
||||
|
||||
serv.playNoteBlock = (world, position, pitch) => {
|
||||
serv.emitParticle(23, world, position.clone().add(new Vec3(0.5, 1.5, 0.5)), {
|
||||
count: 1,
|
||||
size: new Vec3(0, 0, 0)
|
||||
});
|
||||
serv.playSound('note.harp', world, position, { pitch: serv.getNote(pitch) });
|
||||
serv.playNoteBlock = (pitch, world, position, {instrument='harp', particle=true}={}) => {
|
||||
if (particle) {
|
||||
serv.emitParticle(23, world, position.clone().add(new Vec3(0.5, 1.5, 0.5)), {
|
||||
count: 1,
|
||||
size: new Vec3(0, 0, 0)
|
||||
});
|
||||
}
|
||||
serv.playSound('note.' + instrument, world, position, { pitch: serv.getNote(pitch) });
|
||||
};
|
||||
|
||||
serv.getNote = note => 0.5 * Math.pow(Math.pow(2, 1/12), note);
|
||||
|
|
@ -48,7 +50,7 @@ module.exports.player=function(player,serv) {
|
|||
if (typeof data.note == 'undefined') data.note = -1;
|
||||
data.note++;
|
||||
data.note %= 25;
|
||||
serv.playNoteBlock(player.world, pos, data.note);
|
||||
serv.playNoteBlock(data.note, player.world, pos);
|
||||
}).catch((err)=> setTimeout(() => {throw err;},0));
|
||||
});
|
||||
|
||||
|
|
@ -60,7 +62,7 @@ module.exports.player=function(player,serv) {
|
|||
if (!player.world.blockEntityData[pos.toString()]) player.world.blockEntityData[pos.toString()] = {};
|
||||
var data = player.world.blockEntityData[pos.toString()];
|
||||
if (typeof data.note == 'undefined') data.note = 0;
|
||||
serv.playNoteBlock(player.world, pos, data.note);
|
||||
serv.playNoteBlock(data.not,player.world, pos, data.note);
|
||||
}).catch((err)=> setTimeout(() => {throw err;},0));
|
||||
});
|
||||
|
||||
|
|
|
|||
21
src/plugins/README.md
Normal file
21
src/plugins/README.md
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
## Usage
|
||||
|
||||
Drag plugins in this folder.
|
||||
|
||||
## Creating Plugin
|
||||
|
||||
1) Create folder.
|
||||
|
||||
2) Create your index.js inside the folder.
|
||||
|
||||
3) `cd` to the folder and type `npm init` and follow instructions.
|
||||
|
||||
4) index.js should return in module.exports. player, server, or entity. All are optional.
|
||||
|
||||
5.1) If you don't have config/settings.json, create it and copy everything from config/default-settings.json inside.
|
||||
|
||||
5.2) Add into plugins `"plugin_name": {}`. Add any options you'd like.
|
||||
|
||||
## Publish plugin
|
||||
|
||||
Use `npm publish` and follow instructions.
|
||||
Loading…
Reference in a new issue