Old ngn4 website
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

256 lines
6.5 KiB

var fs = require('fs');
var path = require('path');
var data = require('./data/combatant.json')
var list = {
uses: 0,
content: []
}
var weaponLists = null;
function getSpeciesList(set, category, species) {
if(typeof(species) !== 'undefined') {
var spList = species.split(',');
var selections = [];
for(var i = 0; i < spList.length; ++i) {
var spName = category + '/' + spList[i];
var gen = set.getGenerator(spName);
if(gen != null) {
selections.push(gen);
}
}
if(selections.length > 0) {
return selections;
}
}
if(--list.uses >= 0) {
return list.content;
}
list.content = [];
var keys = Object.keys(set.generators);
for(var i = 0; i < keys.length; ++i) {
var key = keys[i];
if(key.indexOf(category + '/') == 0) {
var enabled = set.getMeta(key, 'combatant.enabled', false)
var chance = set.getMeta(key, 'combatant.chance', 1.00);
if(enabled == false) {
continue;
}
if(chance <= 0.999 && Math.random() >= chance) {
continue;
}
list.content.push(set.getGenerator(key));
}
}
if(list.content.length > 0) {
list.uses = 32;
return list.content;
} else {
return null;
}
}
function getWeapons(set, fullId) {
var weapons = data[fullId.split('/')[0]].weapons;
var types = Object.keys(weapons);
var hasWeapon = false;
var result = {};
if(weaponLists == null) {
weaponLists = {};
for(var i = 0; i < types.length; ++i) {
var type = types[i];
var weaponNames = Object.keys(weapons[type]);
var entry = {total: 0, items: []};
for(var j = 0; j < weaponNames.length; ++j) {
entry.total += weapons[type][weaponNames[j]].chance;
entry.items.push({name: weaponNames[j], data: weapons[type][weaponNames[j]]});
}
weaponLists[type] = entry;
}
}
while(!hasWeapon) {
for(var i = 0; i < types.length; ++i) {
var type = types[i];
var chance = set.getMeta(fullId, 'combatant.weapon.' + type + '.chance', 0.5);
var weightList = weaponLists[type];
result[type] = null;
if(Math.random() < chance) {
var r = Math.random() * weightList.total;
for(var j = 0; j < weightList.items.length; ++j) {
var item = weightList.items[j];
r -= item.data.chance;
if(r <= 0) {
result[type] = item;
hasWeapon = true;
break;
}
}
}
}
}
return result;
}
function getItems(category)
{
var items = data[category].items;
var keys = Object.keys(items);
var result = [];
for(var i = 0; i < keys.length; ++i) {
var key = keys[i];
var item = items[key];
var amount = 0;
if(Math.random() < item.chance) {
amount = 1;
while(amount < item.max) {
if(Math.random() < item.more) {
++amount;
} else {
break;
}
}
}
if(amount > 0) {
result.push({name: key, amount: amount});
}
}
return result;
}
function getAbiltiies(set, fullId) {
var abilities = data[fullId.split('/')[0]].abilities;
var abilityTypes = Object.keys(abilities);
var sentinelPenalty = set.getMeta(fullId, 'combatant.ability.penalty.sentinel', 0.10);
var sentinel = false;
var result = [];
for(var i = 0; i < abilityTypes.length; ++i) {
var abilityType = abilityTypes[i];
var abilityChances = abilities[abilityType];
if(Math.random() > set.getMeta(fullId, 'combatant.ability.chance.' + abilityType, 0.10)) {
continue;
}
var initialPenalty = set.getMeta(fullId, 'combatant.ability.penalty.initial.' + abilityType, 0.10);
var incrementalPenalty = set.getMeta(fullId, 'combatant.ability.penalty.increment.' + abilityType, 0.10);
var keys = Object.keys(abilityChances);
for(var j = 0; j < keys.length; ++j) {
var key = keys[j];
var penalty = initialPenalty + (incrementalPenalty * result.length) + (sentinel ? sentinelPenalty : 0)
if(Math.random() < abilityChances[key] - penalty) {
result.push(key);
}
}
sentinel = true;
}
return result;
}
function makeSoldier(req, res, set) {
var category = req.params.cat;
var species = req.params.species;
var agent = req.headers['user-agent'];
var selections = [];
var result = {};
// Validate input
if(!data.hasOwnProperty(req.params.cat)) {
res.status(404);
res.send('ERROR 404: No combatant-generator data available for this category!\n');
return;
}
// Get generator to use
var spList = getSpeciesList(set, category, species);
if(spList == null || spList.length == 0) {
res.status(500);
res.send('ERROR 500: Somehow ended up with no species to pick from. That is not supposed to happen. D:\n');
return;
}
var gen = spList[Math.floor(Math.random() * spList.length)];
// Determine gender randomly. If it discrimates, blame Math.random!
if(gen.genders.length > 1) {
result.gender = gen.genders[Math.floor(Math.random() * gen.genders.length)];
} else {
result.gender = null;
}
result.name = gen.generate('full_name', result.gender);
result.species = gen.name;
result.weapons = getWeapons(set, category + '/' + gen.id, req.query.hasOwnProperty('v'));
result.abilities = getAbiltiies(set, category + '/' + gen.id, req.query.hasOwnProperty('v'));
result.items = getItems(category);
if(agent.indexOf('curl/') != -1 || req.query.hasOwnProperty('t')) {
var text = result.name + " - " + result.species;
if(result.gender != null) {
text += ' ' + result.gender;
}
if(result.abilities.length > 0) {
text += '\n\t' + result.abilities.join(', ');
}
if(result.weapons.primary != null) {
var wp = result.weapons.primary;
text += '\n\t' + wp.name + ' ' + wp.data.ammo + '/' + wp.data.ammo;
}
if(result.weapons.secondary != null) {
var wp = result.weapons.secondary;
text += '\n\t' + wp.name + ' ' + wp.data.ammo + '/' + wp.data.ammo;
}
for(var i = 0; i < result.items.length; ++i) {
text += '\n\t' + result.items[i].name + ' x' + result.items[i].amount;
}
res.status(200);
res.header("Content-Type", "text/plain; charset=utf-8");
res.end(text + '\n');
} else {
res.status(200);
res.header("Content-Type", "application/json; charset=utf-8");
res.end(JSON.stringify(result));
}
}
module.exports = function(set, app, data, scriptMethods) {
app.get('/c/:cat', function(req, res) {makeSoldier(req, res, set)});
app.get('/c/:cat/:species', function(req, res) {makeSoldier(req, res, set)});
}