diff --git a/COMBOS.md b/COMBOS.md index f0e082b0..4cd2063f 100644 --- a/COMBOS.md +++ b/COMBOS.md @@ -1,4 +1,4 @@ -# vbox_info -> +# item_info -> combos [strike, [R R Attack]] specs [spec [bonus amount, [r g b]] diff --git a/client/src/actions.jsx b/client/src/actions.jsx index 01ca414c..bf584a5f 100644 --- a/client/src/actions.jsx +++ b/client/src/actions.jsx @@ -4,8 +4,8 @@ export const setAccount = value => ({ type: SET_ACCOUNT, value }); export const SET_CRYPS = 'SET_CRYPS'; export const setCryps = value => ({ type: SET_CRYPS, value }); -export const SET_VBOX_INFO = 'SET_VBOX_INFO'; -export const setVboxInfo = value => ({ type: SET_VBOX_INFO, value }); +export const SET_ITEM_INFO = 'SET_ITEM_INFO'; +export const setItemInfo = value => ({ type: SET_ITEM_INFO, value }); export const SET_SKIP = 'SET_SKIP'; export const setSkip = value => ({ type: SET_SKIP, value }); diff --git a/client/src/components/info.component.jsx b/client/src/components/info.component.jsx index bb1175b1..27b0e95e 100644 --- a/client/src/components/info.component.jsx +++ b/client/src/components/info.component.jsx @@ -15,7 +15,7 @@ function Info(args) { sendUnequip, instance, player, - vboxInfo, + itemInfo, vboxHidden, } = args; @@ -166,7 +166,7 @@ function Info(args) { if (!player) return false; if (!(combiner.every(u => u === null))) { - const filteredCombos = vboxInfo.combos + const filteredCombos = itemInfo.combos .filter(combo => combiner.every(u => u === null || combo.units.includes(player.vbox.bound[u]))); if (filteredCombos.length > 6) return false; @@ -183,7 +183,7 @@ function Info(args) { ); } - const vboxCombos = vboxInfo.combos.filter(c => c.units.includes(info[1])); + const vboxCombos = itemInfo.combos.filter(c => c.units.includes(info[1])); if (vboxCombos.length > 6) return false; return ( diff --git a/client/src/components/info.container.jsx b/client/src/components/info.container.jsx index 9acd039a..bf1cd941 100644 --- a/client/src/components/info.container.jsx +++ b/client/src/components/info.container.jsx @@ -11,7 +11,7 @@ const addState = connect( info, ws, instance, - vboxInfo, + itemInfo, vboxHidden, player, } = state; @@ -27,7 +27,7 @@ const addState = connect( sendUnequip, instance, player, - vboxInfo, + itemInfo, vboxHidden, }; }, diff --git a/client/src/components/info.cryp.jsx b/client/src/components/info.cryp.jsx index 230864dc..5b2e2bba 100644 --- a/client/src/components/info.cryp.jsx +++ b/client/src/components/info.cryp.jsx @@ -8,8 +8,8 @@ const shapes = require('./shapes'); const addState = connect( function receiveState(state) { - const { activeCryp, player, vboxInfo } = state; - return { activeCryp, player, vboxInfo }; + const { activeCryp, player, itemInfo } = state; + return { activeCryp, player, itemInfo }; }, function receiveDispatch(dispatch) { @@ -38,7 +38,7 @@ function InfoCryp(args) { const { activeCryp, player, - vboxInfo, + itemInfo, setVboxHidden, setInfo, @@ -52,8 +52,8 @@ function InfoCryp(args) { if (!cryp) return false; function setHighlight(type) { - if (type === 'skill') return setVboxHighlight(vboxInfo.items.filter(v => v.skill).map(v => v.v)); - if (type === 'spec') return setVboxHighlight(vboxInfo.items.filter(v => v.spec).map(v => v.v)); + if (type === 'skill') return setVboxHighlight(itemInfo.items.filter(v => v.skill).map(v => v.v)); + if (type === 'spec') return setVboxHighlight(itemInfo.items.filter(v => v.spec).map(v => v.v)); return false; } diff --git a/client/src/components/instance.cryps.jsx b/client/src/components/instance.cryps.jsx index 95dae84d..f2aabd96 100644 --- a/client/src/components/instance.cryps.jsx +++ b/client/src/components/instance.cryps.jsx @@ -8,7 +8,7 @@ const actions = require('../actions'); const addState = connect( function receiveState(state) { - const { ws, instance, player, account, vboxHidden, vboxInfo, activeItem, activeCryp } = state; + const { ws, instance, player, account, vboxHidden, itemInfo, activeItem, activeCryp } = state; function sendInstanceReady() { return ws.sendInstanceReady(instance.id); @@ -18,7 +18,7 @@ const addState = connect( return ws.sendVboxApply(instance.id, crypId, i); } - return { instance, player, account, sendInstanceReady, sendVboxApply, vboxHidden, vboxInfo, activeItem, activeCryp }; + return { instance, player, account, sendInstanceReady, sendVboxApply, vboxHidden, itemInfo, activeItem, activeCryp }; }, function receiveDispatch(dispatch) { @@ -57,12 +57,12 @@ function Cryp(props) { setInfo, setActiveCryp, setVboxHighlight, - vboxInfo, + itemInfo, } = props; function setHighlight(type) { - if (type === 'skill') return setVboxHighlight(vboxInfo.items.filter(v => v.skill).map(v => v.v)); - if (type === 'spec') return setVboxHighlight(vboxInfo.items.filter(v => v.spec).map(v => v.v)); + if (type === 'skill') return setVboxHighlight(itemInfo.items.filter(v => v.skill).map(v => v.v)); + if (type === 'spec') return setVboxHighlight(itemInfo.items.filter(v => v.spec).map(v => v.v)); return false; } @@ -74,8 +74,8 @@ function Cryp(props) { } const { vbox } = player; - const skillList = vboxInfo.items.filter(v => v.skill).map(v => v.v); - const specList = vboxInfo.items.filter(v => v.spec).map(v => v.v); + const skillList = itemInfo.items.filter(v => v.skill).map(v => v.v); + const specList = itemInfo.items.filter(v => v.spec).map(v => v.v); const skills = range(0, 3).map(i => { const skill = cryp.skills[i]; @@ -194,7 +194,7 @@ function InstanceCryps(props) { sendVboxApply, vboxHidden, - vboxInfo, + itemInfo, setVboxHighlight, } = props; @@ -202,7 +202,7 @@ function InstanceCryps(props) { if (instance.phase === 'Lobby') return false; const cryps = player.cryps.map((c, i) => Cryp({ - activeCryp, activeItem, cryp: c, player, sendVboxApply, setInfo, setActiveCryp, vboxInfo, setVboxHighlight, + activeCryp, activeItem, cryp: c, player, sendVboxApply, setInfo, setActiveCryp, itemInfo, setVboxHighlight, })); const classes = `cryp-list ${vboxHidden ? '' : 'hidden'}`; diff --git a/client/src/components/instance.equip.jsx b/client/src/components/instance.equip.jsx index a45ca744..636c75c1 100644 --- a/client/src/components/instance.equip.jsx +++ b/client/src/components/instance.equip.jsx @@ -7,13 +7,13 @@ const { convertItem, SPECS } = require('./../utils'); const addState = connect( function receiveState(state) { - const { player, vboxInfo, info, ws, instance } = state; + const { player, itemInfo, info, ws, instance } = state; function sendUnequip(crypId, item) { return ws.sendVboxUnequip(instance.id, crypId, item); } - return { player, vboxInfo, info, sendUnequip }; + return { player, itemInfo, info, sendUnequip }; }, function receiveDispatch(dispatch) { @@ -38,7 +38,7 @@ function Equipment(props) { const { player, info, - vboxInfo, + itemInfo, sendUnequip, setInfo, setActiveItem, @@ -70,8 +70,8 @@ function Equipment(props) { const specClass = infoType === 'spec' ? 'specs highlight' : 'specs'; // const classes = `right ${skill ? '' : 'action'}`; - const skillList = vboxInfo.items.filter(v => v.skill).map(v => v.v); - const specList = vboxInfo.items.filter(v => v.spec).map(v => v.v); + const skillList = itemInfo.items.filter(v => v.skill).map(v => v.v); + const specList = itemInfo.items.filter(v => v.spec).map(v => v.v); const skills = range(0, 9).map(i => { diff --git a/client/src/components/vbox.component.jsx b/client/src/components/vbox.component.jsx index 63b02f29..3b01595f 100644 --- a/client/src/components/vbox.component.jsx +++ b/client/src/components/vbox.component.jsx @@ -26,7 +26,7 @@ function Vbox(args) { vboxHidden, vboxHighlight, setVboxHighlight, - vboxInfo, + itemInfo, } = args; if (!player) return false; @@ -39,10 +39,10 @@ function Vbox(args) { const combinerValues = newCombiner.map(cv => player.vbox.bound[cv]).filter(cv => cv); - const filteredCombos = vboxInfo.combos + const filteredCombos = itemInfo.combos .filter(combo => combinerValues.every(u => combo.units.includes(u))); - const comboValues = vboxInfo.items.filter(v => { + const comboValues = itemInfo.items.filter(v => { if (!filteredCombos.some(c => c.units.includes(v.v))) return false; if (!['Red', 'Green', 'Blue'].includes(v.v) && combinerValues.includes(v.v)) return false; return true; diff --git a/client/src/components/vbox.container.jsx b/client/src/components/vbox.container.jsx index 19fa5413..c61fbfe4 100644 --- a/client/src/components/vbox.container.jsx +++ b/client/src/components/vbox.container.jsx @@ -17,7 +17,7 @@ const addState = connect( info, vboxHidden, vboxHighlight, - vboxInfo, + itemInfo, } = state; function sendVboxApply(i) { @@ -48,7 +48,7 @@ const addState = connect( activeItem, activeCryp, info, - vboxInfo, + itemInfo, vboxHidden, vboxHighlight, sendVboxAccept, diff --git a/client/src/events.jsx b/client/src/events.jsx index 1caed41c..98260585 100644 --- a/client/src/events.jsx +++ b/client/src/events.jsx @@ -37,7 +37,7 @@ function registerEvents(store) { crypAnimations(); function setPing(ping) { - store.dispatch(actions.setPing(ping)); + store.dispatch(actions.setPing(ping)); } function setCryps(cryps) { @@ -158,8 +158,8 @@ function registerEvents(store) { console.log('EVENT ->', 'crypStatusUpdate', { id, skill, target }); } - function setVboxInfo(v) { - return store.dispatch(actions.setVboxInfo(v)); + function setItemInfo(v) { + return store.dispatch(actions.setItemInfo(v)); } // events.on('SET_PLAYER', setInstance); @@ -220,7 +220,7 @@ function registerEvents(store) { setZone, setPing, setScores, - setVboxInfo, + setItemInfo, }; } diff --git a/client/src/reducers.jsx b/client/src/reducers.jsx index 5d6fbb93..10097444 100644 --- a/client/src/reducers.jsx +++ b/client/src/reducers.jsx @@ -33,6 +33,6 @@ module.exports = { showLog: createReducer(false, actions.SET_SHOW_LOG), vboxHidden: createReducer(false, actions.SET_VBOX_HIDDEN), vboxHighlight: createReducer([], actions.SET_VBOX_HIGHLIGHT), - vboxInfo: createReducer({ combos: [], items: [] }, actions.SET_VBOX_INFO), + itemInfo: createReducer({ combos: [], items: [] }, actions.SET_VBOX_INFO), ws: createReducer(null, actions.SET_WS), }; diff --git a/client/src/socket.jsx b/client/src/socket.jsx index 72b27bf6..793b3d0f 100644 --- a/client/src/socket.jsx +++ b/client/src/socket.jsx @@ -114,8 +114,8 @@ function createSocket(events) { send({ method: 'player_vbox_reclaim', params: { instance_id: instanceId, index } }); } - function sendVboxInfo() { - send({ method: 'vbox_info', params: {} }); + function sendItemInfo() { + send({ method: 'item_info', params: {} }); } function sendGameSkill(gameId, crypId, targetCrypId, skill) { @@ -177,7 +177,7 @@ function createSocket(events) { function accountInstanceList(res) { const [struct, playerList] = res; - sendVboxInfo(); + sendItemInfo(); events.setInstanceList(playerList); } @@ -228,9 +228,9 @@ function createSocket(events) { clearTimeout(instanceStateTimeout); } - function vboxInfo(response) { + function itemInfo(response) { const [structName, info] = response; - events.setVboxInfo(info); + events.setItemInfo(info); } function pong() { @@ -255,7 +255,7 @@ function createSocket(events) { zone_state: zoneState, zone_close: res => console.log(res), instance_state: instanceState, - vbox_info: vboxInfo, + item_info: itemInfo, pong, }; @@ -367,7 +367,7 @@ function createSocket(events) { sendVboxCombine, sendVboxDiscard, sendVboxUnequip, - sendVboxInfo, + sendItemInfo, startInstanceStateTimeout, startGameStateTimeout, connect, diff --git a/server/src/cryp.rs b/server/src/cryp.rs index b4701fce..0ccc6f3e 100644 --- a/server/src/cryp.rs +++ b/server/src/cryp.rs @@ -11,7 +11,7 @@ use account::{Account}; use rpc::{CrypSpawnParams}; use skill::{Skill, Cooldown, Effect, Cast, Category, Immunity, Disable, Event}; use spec::{Spec}; -use vbox::Item; +use item::{Item}; #[derive(Debug,Clone,Serialize,Deserialize)] pub struct Colours { diff --git a/server/src/instance.rs b/server/src/instance.rs index aac7d318..a35192bf 100644 --- a/server/src/instance.rs +++ b/server/src/instance.rs @@ -18,8 +18,8 @@ use account::Account; use player::{Player, player_create, player_get, player_global_update}; use cryp::{Cryp, cryp_get}; use mob::{instance_mobs}; -use game::{Game, Phase, game_get, game_write, game_instance_new}; -use vbox::{Item}; +use game::{Game, Phase, game_get, game_write}; +use item::{Item}; use rpc::{RpcResult}; use names::{name}; diff --git a/server/src/item.rs b/server/src/item.rs index 4daf83bd..830f5f9f 100644 --- a/server/src/item.rs +++ b/server/src/item.rs @@ -1,266 +1,446 @@ -use serde_cbor::{from_slice, to_vec}; -use uuid::Uuid; +use skill::{Skill}; +use spec::{Spec}; +use cryp::{Colours}; -use postgres::transaction::Transaction; -use failure::Error; +#[derive(Debug,Copy,Clone,Serialize,Deserialize,PartialEq,PartialOrd,Ord,Eq)] +pub enum Item { + // colours + Blue, + Green, + Red, -// drops -use rand::prelude::*; -use rand::{thread_rng}; -use rand::distributions::{LogNormal,WeightedIndex}; + // base skills + Attack, + Block, + Stun, + Buff, + Debuff, -use account::Account; -use rpc::{ItemUseParams}; -use cryp::{Stat, cryp_get, cryp_write}; -use game::{GameMode}; -use spec::{Spec, SpecType}; + // specs + // Base + Damage, + Life, + Speed, -#[derive(Debug,Clone,Copy,PartialEq,Serialize,Deserialize)] -pub enum ItemAction { - RerollRedDamage, - RerollBlueDamage, - RerollSpeed, - RerollGreenLife, - RerollRedLife, - RerollBlueLife, - RerollEvasion, + // Lifes Upgrades + GreenLifeI, + RedLifeI, + BlueLifeI, + GRLI, + GBLI, + RBLI, - SpecRedDamage5, - SpecBlueDamage5, - SpecRedLife5, - SpecBlueLife5, - SpecBlueEvasion5, + // Damage Upgrades + RedDamageI, + BlueDamageI, + GreenDamageI, + GRDI, + GBDI, + RBDI, + + // Speed Upgrades + RedSpeedI, + BlueSpeedI, + GreenSpeedI, + GRSpeedI, + GBSpeedI, + RBSpeedI, + + Amplify, + Banish, + Blast, + Chaos, + Clutch, + Corrupt, + Curse, + Decay, + Hostility, + Haste, + Heal, + Hex, + Impurity, + Invert, + Parry, + Purge, + Purify, + Reflect, + Recharge, + Ruin, + Scatter, + Silence, + Slay, + Sleep, + Snare, + Strangle, + Strike, + StrikeII, + StrikeIII, + Siphon, + Taunt, + Throw, + Triage, + + + TestTouch, + TestStun, + TestBlock, + TestParry, + TestSiphon, } -#[derive(Debug,Clone,Copy,PartialEq,Serialize,Deserialize)] -pub struct Item { - // mods: Vec, - id: Uuid, - account: Uuid, - action: ItemAction, +pub enum ItemEffect { + Skill, + Spec, } impl Item { - pub fn new(action: ItemAction, account_id: Uuid) -> Item { - let id = Uuid::new_v4(); - return Item { - id, - account: account_id, - action, - }; + pub fn colours(&self, count: &mut Colours) { + let combos = get_combos(); + let combo = combos.iter().find(|c| c.item == *self); + match combo { + Some(c) => c.units.iter().for_each(|unit| match unit { + Item::Red => count.red += 1, + Item::Blue => count.blue += 1, + Item::Green => count.green += 1, + _ => { + let mut combo_count = Colours::new(); + unit.colours(&mut combo_count); + count.red += combo_count.red; + count.blue += combo_count.blue; + count.green += combo_count.green; + } + }), + None => (), + } } - fn apply(&mut self, tx: &mut Transaction, target: Uuid) -> Result<(), Error> { - match self.action { - ItemAction::RerollGreenLife => reroll(self, tx, target, Stat::GreenLife), - ItemAction::RerollRedDamage => reroll(self, tx, target, Stat::RedDamage), - ItemAction::RerollBlueDamage => reroll(self, tx, target, Stat::BlueDamage), - ItemAction::RerollSpeed => reroll(self, tx, target, Stat::Speed), - ItemAction::RerollRedLife => reroll(self, tx, target, Stat::RedLife), - ItemAction::RerollBlueLife => reroll(self, tx, target, Stat::BlueLife), - ItemAction::RerollEvasion => reroll(self, tx, target, Stat::Evasion), + pub fn cost(&self) -> u16 { + match self { + Item::Red => 1, + Item::Green => 1, + Item::Blue => 1, - ItemAction::SpecRedDamage5 => spec_add(self, tx, target, SpecType::RedDamage5), - ItemAction::SpecBlueDamage5 => spec_add(self, tx, target, SpecType::BlueDamage5), - _ => unimplemented!(), + Item::Attack => 2, + Item::Block => 2, + Item::Buff => 2, + Item::Debuff => 2, + Item::Stun => 2, + + Item::Damage => 3, + Item::Life => 3, + Item::Speed => 3, + + _ => { + let combos = get_combos(); + let combo = combos.iter().find(|c| c.item == *self) + .unwrap_or_else(|| panic!("unable to find components for {:?}", self)); + return combo.units.iter().fold(0, |acc, c| acc + c.cost()); + }, + } + } + + pub fn speed(&self) -> u8 { + match self { + Item::Red => 3, + Item::Green => 2, + Item::Blue => 1, + + Item::Attack => 1, + Item::Stun => 2, + Item::Block => 3, + Item::Buff => 4, + Item::Debuff => 4, + + _ => { + let combos = get_combos(); + let combo = combos.iter().find(|c| c.item == *self) + .unwrap_or_else(|| panic!("unable to find components for {:?}", self)); + return combo.units.iter().fold(0, |acc, c| acc + c.speed()); + }, + } + } + + pub fn effect(&self) -> Option { + if let Some(_skill) = self.into_skill() { + return Some(ItemEffect::Skill); + } + if let Some(_spec) = self.into_spec() { + return Some(ItemEffect::Spec); + } + return None; + } + + pub fn into_skill(&self) -> Option { + match self { + Item::Attack => Some(Skill::Attack), + Item::Amplify => Some(Skill::Amplify), + Item::Banish => Some(Skill::Banish), + Item::Blast => Some(Skill::Blast), + Item::Block => Some(Skill::Block), + Item::Chaos => Some(Skill::Chaos), + Item::Curse => Some(Skill::Curse), + Item::Debuff => Some(Skill::Debuff), + Item::Decay => Some(Skill::Decay), + Item::Haste => Some(Skill::Haste), + Item::Heal => Some(Skill::Heal), + Item::Hex => Some(Skill::Hex), + Item::Hostility => Some(Skill::Hostility), + Item::Impurity => Some(Skill::Impurity), + Item::Invert => Some(Skill::Invert), + Item::Parry => Some(Skill::Parry), + Item::Purge => Some(Skill::Purge), + Item::Purify => Some(Skill::Purify), + Item::Recharge => Some(Skill::Recharge), + Item::Reflect => Some(Skill::Reflect), + Item::Ruin => Some(Skill::Ruin), + Item::Scatter => Some(Skill::Scatter), + Item::Silence => Some(Skill::Silence), + Item::Slay => Some(Skill::Slay), + Item::Sleep => Some(Skill::Sleep), + Item::Siphon => Some(Skill::Siphon), + Item::Snare => Some(Skill::Snare), + Item::Strangle => Some(Skill::Strangle), + Item::Stun => Some(Skill::Stun), + Item::Strike => Some(Skill::Strike), + Item::StrikeII => Some(Skill::StrikeII), + Item::StrikeIII => Some(Skill::StrikeIII), + Item::Clutch => Some(Skill::Clutch), + Item::Taunt => Some(Skill::Taunt), + Item::Throw => Some(Skill::Throw), + Item::Corrupt => Some(Skill::Corrupt), + Item::Triage => Some(Skill::Triage), + _ => None, + } + } + + pub fn into_spec(&self) -> Option { + match *self { + Item::Speed => Some(Spec::Speed), + Item::RedSpeedI => Some(Spec::RedSpeedI), + Item::BlueSpeedI => Some(Spec::BlueSpeedI), + Item::GreenSpeedI => Some(Spec::GreenSpeedI), + Item::GRSpeedI => Some(Spec::GRSpeedI), + Item::GBSpeedI => Some(Spec::GBSpeedI), + Item::RBSpeedI => Some(Spec::RBSpeedI), + + Item::Damage => Some(Spec::Damage), + Item::RedDamageI => Some(Spec::RedDamageI), + Item::BlueDamageI => Some(Spec::BlueDamageI), + Item::GreenDamageI => Some(Spec::GreenDamageI), + Item::GRDI => Some(Spec::GRDI), + Item::GBDI => Some(Spec::GBDI), + Item::RBDI => Some(Spec::RBDI), + + Item::Life => Some(Spec::Life), + Item::GRLI => Some(Spec::GRLI), + Item::GBLI => Some(Spec::GBLI), + Item::RBLI => Some(Spec::RBLI), + Item::GreenLifeI => Some(Spec::GreenLifeI), + Item::RedLifeI => Some(Spec::RedLifeI), + Item::BlueLifeI => Some(Spec::BlueLifeI), + + _ => None, } } } -fn spec_add(item: &mut Item, tx: &mut Transaction, target: Uuid, spec_type: SpecType) -> Result<(), Error> { - let mut cryp = cryp_get(tx, target, item.account)?; - let spec = Spec::new(spec_type); - cryp.spec_add(spec)?; - cryp_write(cryp, tx)?; - return Ok(()); -} +impl From for Item { + fn from(skill: Skill) -> Item { + match skill { + Skill::Amplify => Item::Amplify, + Skill::Attack => Item::Attack, + Skill::Banish => Item::Banish, + Skill::Blast => Item::Blast, + Skill::Block => Item::Block, + Skill::Chaos => Item::Chaos, + Skill::Curse => Item::Curse, + Skill::Clutch => Item::Clutch, + Skill::Decay => Item::Decay, + Skill::Debuff => Item::Debuff, + Skill::Haste => Item::Haste, + Skill::Hostility => Item::Hostility, + Skill::Heal => Item::Heal, + Skill::Hex => Item::Hex, + Skill::Impurity => Item::Impurity, + Skill::Invert => Item::Invert, + Skill::Parry => Item::Parry, + Skill::Purge => Item::Purge, + Skill::Purify => Item::Purify, + Skill::Recharge => Item::Recharge, + Skill::Reflect => Item::Reflect, + Skill::Ruin => Item::Ruin, + Skill::Scatter => Item::Scatter, + Skill::Silence => Item::Silence, + Skill::Siphon => Item::Siphon, + Skill::Slay => Item::Slay, + Skill::Sleep => Item::Sleep, + Skill::Snare => Item::Snare, + Skill::Strangle => Item::Strangle, + Skill::Strike => Item::Strike, + Skill::StrikeII => Item::StrikeII, + Skill::StrikeIII => Item::StrikeIII, + Skill::Stun => Item::Stun, + Skill::Taunt => Item::Taunt, + Skill::Throw => Item::Throw, + Skill::Triage => Item::Triage, + Skill::Corrupt => Item::Corrupt, -fn reroll(item: &mut Item, tx: &mut Transaction, target: Uuid, stat: Stat) -> Result<(), Error> { - let mut cryp = cryp_get(tx, target, item.account)?; - cryp.roll_stat(stat); - cryp_write(cryp, tx)?; - return Ok(()); -} - -fn mode_drops(mode: GameMode) -> Vec<(ItemAction, usize)> { - match mode { - GameMode::Normal => vec![ - (ItemAction::RerollGreenLife, 1), - (ItemAction::RerollRedDamage, 1), - (ItemAction::RerollBlueDamage, 1), - ], - GameMode::Pvp => vec![ - (ItemAction::RerollSpeed, 1), - ], - GameMode::Zone3v2Attack | - GameMode::Zone2v2Caster | - GameMode::Zone3v3MeleeMiniboss => vec![ - (ItemAction::RerollEvasion, 1), - (ItemAction::RerollRedLife, 1), - (ItemAction::RerollBlueLife, 1), - ], - GameMode::Zone3v3HealerBoss => vec![ - (ItemAction::RerollSpeed, 1), - ], - // _ => vec![ - // (ItemAction::RerollGreenLife, 1), - // (ItemAction::RerollRedDamage, 1), - // (ItemAction::RerollBlueDamage, 1), - // (ItemAction::RerollSpeed, 1), - // (ItemAction::RerollRedLife, 1), - // (ItemAction::RerollBlueLife, 1), - // (ItemAction::RerollEvasion, 1), - // ], + Skill::TestTouch => Item::TestTouch, + Skill::TestStun => Item::TestStun, + Skill::TestBlock => Item::TestBlock, + Skill::TestParry => Item::TestParry, + Skill::TestSiphon => Item::TestSiphon, + _ => panic!("{:?} not implemented as a item", skill), + } } } -pub fn item_drop(tx: &mut Transaction, account_id: Uuid, mode: GameMode) -> Result<(), Error> { - let mut rng = thread_rng(); +impl From for Item { + fn from(spec: Spec) -> Item { + match spec { + Spec::Speed => Item::Speed, + Spec::RedSpeedI => Item::RedSpeedI, + Spec::BlueSpeedI => Item::BlueSpeedI, + Spec::GreenSpeedI => Item::GreenSpeedI, + Spec::GRSpeedI => Item::GRSpeedI, + Spec::GBSpeedI => Item::GBSpeedI, + Spec::RBSpeedI => Item::RBSpeedI, - let log_normal = LogNormal::new(1.0, 1.0); - let num_drops = log_normal.sample(&mut rng).floor() as u16; + Spec::Damage => Item::Damage, + Spec::RedDamageI => Item::RedDamageI, + Spec::BlueDamageI => Item::BlueDamageI, + Spec::GreenDamageI => Item::GreenDamageI, + Spec::GRDI => Item::GRDI, + Spec::GBDI => Item::GBDI, + Spec::RBDI => Item::RBDI, - let actions = mode_drops(mode); - info!("{:?} drops", num_drops); - - for _i in 0..num_drops { - let dist = WeightedIndex::new(actions.iter().map(|item| item.1)).unwrap(); - let kind = actions[dist.sample(&mut rng)].0; - let item = Item::new(kind, account_id); - - info!("{:?} dropped {:?}", account_id, item); - item_create(item, tx, account_id)?; + Spec::Life => Item::Life, + Spec::GRLI => Item::GRLI, + Spec::GBLI => Item::GBLI, + Spec::RBLI => Item::RBLI, + Spec::GreenLifeI => Item::GreenLifeI, + Spec::RedLifeI => Item::RedLifeI, + Spec::BlueLifeI => Item::BlueLifeI, + // _ => panic!("{:?} not implemented as a item", spec), + } } - - Ok(()) } -pub fn item_create(item: Item, tx: &mut Transaction, account_id: Uuid) -> Result { - let item_bytes = to_vec(&item)?; - - let query = " - INSERT INTO items (id, account, data) - VALUES ($1, $2, $3) - RETURNING id, account, data; - "; - - let result = tx - .query(query, &[&item.id, &account_id, &item_bytes])?; - - result.iter().next().expect("no row returned"); - - return Ok(item); +#[derive(Debug,Clone,Serialize,Deserialize)] +pub struct Combo { + pub item: Item, + pub units: Vec, } -pub fn item_use(params: ItemUseParams, tx: &mut Transaction, account: &Account) -> Result<(), Error> { - let query = " - SELECT data - FROM items - WHERE id = $1 - AND account = $2 - FOR UPDATE; - "; +pub fn get_combos() -> Vec { + let mut combinations = vec![ + Combo { units: vec![Item::Buff, Item::Red, Item::Red], item: Item::Taunt }, + Combo { units: vec![Item::Buff, Item::Green, Item::Green], item: Item::Triage }, + Combo { units: vec![Item::Buff, Item::Blue, Item::Blue], item: Item::Scatter }, //To be impl + Combo { units: vec![Item::Buff, Item::Red, Item::Green], item: Item::Haste }, + Combo { units: vec![Item::Buff, Item::Green, Item::Blue], item: Item::Impurity }, + Combo { units: vec![Item::Buff, Item::Red, Item::Blue], item: Item::Amplify }, // Some flavour - let result = tx - .query(query, &[¶ms.item, &account.id])?; + Combo { units: vec![Item::Debuff, Item::Red, Item::Red], item: Item::Snare }, + Combo { units: vec![Item::Debuff, Item::Green, Item::Green], item: Item::Purge }, // Needs flavour + Combo { units: vec![Item::Debuff, Item::Blue, Item::Blue], item: Item::Silence }, + Combo { units: vec![Item::Debuff, Item::Red, Item::Green], item: Item::Curse }, // To be reworked + Combo { units: vec![Item::Debuff, Item::Green, Item::Blue], item: Item::Decay }, + Combo { units: vec![Item::Debuff, Item::Red, Item::Blue], item: Item::Invert }, - let returned = result.iter().next().expect("no row returned"); + Combo { units: vec![Item::Block, Item::Red, Item::Red], item: Item::Parry }, // Add red recharge + Combo { units: vec![Item::Block, Item::Green, Item::Green], item: Item::Purify }, + Combo { units: vec![Item::Block, Item::Blue, Item::Blue], item: Item::Corrupt }, + Combo { units: vec![Item::Block, Item::Red, Item::Green], item: Item::Clutch }, + Combo { units: vec![Item::Block, Item::Green, Item::Blue], item: Item::Reflect }, + Combo { units: vec![Item::Block, Item::Red, Item::Blue], item: Item::Recharge }, - let item_bytes: Vec = returned.get(0); - let mut item = from_slice::(&item_bytes)?; + Combo { units: vec![Item::Stun, Item::Red, Item::Red], item: Item::Strangle }, + Combo { units: vec![Item::Stun, Item::Green, Item::Green], item: Item::Sleep }, + Combo { units: vec![Item::Stun, Item::Blue, Item::Blue], item: Item::Ruin }, + Combo { units: vec![Item::Stun, Item::Red, Item::Green], item: Item::Throw }, + Combo { units: vec![Item::Stun, Item::Green, Item::Blue], item: Item::Hex }, + Combo { units: vec![Item::Stun, Item::Red, Item::Blue], item: Item::Banish }, - item.apply(tx, params.target)?; - item_delete(tx, params.item)?; + Combo { units: vec![Item::Attack, Item::Red, Item::Red], item: Item::Strike }, + Combo { units: vec![Item::Strike, Item::Strike, Item::Strike], item: Item::StrikeII }, + Combo { units: vec![Item::StrikeII, Item::StrikeII, Item::StrikeII], item: Item::StrikeIII }, - return Ok(()); + Combo { units: vec![Item::Attack, Item::Green, Item::Green], item: Item::Heal }, + Combo { units: vec![Item::Attack, Item::Blue, Item::Blue], item: Item::Blast }, + Combo { units: vec![Item::Attack, Item::Red, Item::Green], item: Item::Slay }, + Combo { units: vec![Item::Attack, Item::Green, Item::Blue], item: Item::Siphon }, + Combo { units: vec![Item::Attack, Item::Red, Item::Blue], item: Item::Chaos }, + + Combo { units: vec![Item::Damage, Item::Red, Item::Red], item: Item::RedDamageI }, + Combo { units: vec![Item::Damage, Item::Green, Item::Green], item: Item::GreenDamageI }, + Combo { units: vec![Item::Damage, Item::Blue, Item::Blue], item: Item::BlueDamageI }, + Combo { units: vec![Item::Damage, Item::Red, Item::Green], item: Item::GRDI }, + Combo { units: vec![Item::Damage, Item::Green, Item::Blue], item: Item::GBDI }, + Combo { units: vec![Item::Damage, Item::Red, Item::Blue], item: Item::RBDI }, + + Combo { units: vec![Item::Life, Item::Red, Item::Red], item: Item::RedLifeI }, + Combo { units: vec![Item::Life, Item::Green, Item::Green], item: Item::GreenLifeI }, + Combo { units: vec![Item::Life, Item::Blue, Item::Blue], item: Item::BlueLifeI }, + Combo { units: vec![Item::Life, Item::Red, Item::Green], item: Item::GRLI }, + Combo { units: vec![Item::Life, Item::Green, Item::Blue], item: Item::GBLI }, + Combo { units: vec![Item::Life, Item::Red, Item::Blue], item: Item::RBLI }, + + Combo { units: vec![Item::Speed, Item::Red, Item::Red], item: Item::RedSpeedI }, + Combo { units: vec![Item::Speed, Item::Green, Item::Green], item: Item::GreenSpeedI }, + Combo { units: vec![Item::Speed, Item::Blue, Item::Blue], item: Item::BlueSpeedI }, + Combo { units: vec![Item::Speed, Item::Red, Item::Green], item: Item::GRSpeedI }, + Combo { units: vec![Item::Speed, Item::Green, Item::Blue], item: Item::GBSpeedI }, + Combo { units: vec![Item::Speed, Item::Red, Item::Blue], item: Item::RBSpeedI }, + + ]; + + combinations.iter_mut().for_each(|set| set.units.sort_unstable()); + + return combinations; } -pub fn item_delete(tx: &mut Transaction, id: Uuid) -> Result<(), Error> { - let query = " - DELETE - FROM items - WHERE id = $1; - "; - - let result = tx - .execute(query, &[&id])?; - - if result != 1 { - return Err(format_err!("unable to delete item {:?}", id)); - } - - // info!("item deleted {:?}", id); - - return Ok(()); +#[derive(Debug,Clone,Serialize,Deserialize)] +pub struct ItemInfo { + pub v: Item, + pub spec: bool, + pub skill: bool, } -pub fn items_list(tx: &mut Transaction, account: &Account) -> Result, Error> { - let query = " - SELECT data, id - FROM items - WHERE account = $1; - "; - let result = tx - .query(query, &[&account.id])?; - - let mut items = vec![]; - - for row in result.into_iter() { - let item_bytes: Vec = row.get(0); - let id = row.get(1); - - match from_slice::(&item_bytes) { - Ok(i) => items.push(i), - Err(_e) => { - item_delete(tx, id)?; - } - }; - } - - return Ok(items); +#[derive(Debug,Clone,Serialize,Deserialize)] +pub struct ItemInfoCtr { + pub combos: Vec, + pub items: Vec, } -// # max damage potion -// name +pub fn item_info() -> ItemInfoCtr { + let combos = get_combos(); + let mut items = combos + .into_iter() + .flat_map(|mut c| { + c.units.push(c.item); + c.units + }) + .collect::>(); -// "MapMonstersCurseEffectOnSelfFinal3": { -// "adds_tags": [], -// "domain": "area", -// "generation_type": "prefix", -// "generation_weights": [], -// "grants_buff": {}, -// "grants_effect": {}, -// "group": "MapHexproof", -// "is_essence_only": false, -// "name": "Hexwarded", -// "required_level": 1, -// "spawn_weights": [ -// { -// "tag": "top_tier_map", -// "weight": 0 -// }, -// { -// "tag": "default", -// "weight": 0 -// } -// ], -// "stats": [ -// { -// "id": "map_item_drop_quantity_+%", -// "max": 15, -// "min": 15 -// }, -// { -// "id": "map_item_drop_rarity_+%", -// "max": 8, -// "min": 8 -// }, -// { -// "id": "map_monsters_curse_effect_on_self_+%_final", -// "max": -60, -// "min": -60 -// } -// ] -// }, + items.sort_unstable(); + items.dedup(); + + let items = items + .into_iter() + .map(|v| ItemInfo { + v, + spec: v.into_spec().is_some(), + skill: v.into_skill().is_some(), + }) + .collect::>(); + + let combos = get_combos(); + + return ItemInfoCtr { + combos, + items, + }; +} diff --git a/server/src/main.rs b/server/src/main.rs index 4ea70575..39e51e00 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -17,17 +17,18 @@ extern crate serde_cbor; extern crate fern; #[macro_use] extern crate log; +mod account; mod cryp; mod game; +mod instance; +mod item; +mod mob; +mod names; mod net; +mod player; +mod rpc; mod skill; mod spec; -mod names; -mod rpc; -mod account; -mod instance; -mod player; -mod mob; mod util; mod vbox; mod warden; diff --git a/server/src/player.rs b/server/src/player.rs index 3f0e67ed..11a753fd 100644 --- a/server/src/player.rs +++ b/server/src/player.rs @@ -10,9 +10,10 @@ use failure::err_msg; use account::Account; use cryp::{Cryp, Colours, cryp_get}; -use vbox::{Vbox, Item, ItemEffect}; +use vbox::{Vbox}; +use item::{Item, ItemEffect}; use rpc::{PlayerCrypsSetParams}; -use instance::{Instance, instance_get, instance_update}; +use instance::{Instance}; use skill::{Effect}; const DISCARD_COST: u16 = 5; diff --git a/server/src/rpc.rs b/server/src/rpc.rs index dac72479..78756910 100644 --- a/server/src/rpc.rs +++ b/server/src/rpc.rs @@ -19,11 +19,11 @@ use cryp::{Cryp, cryp_spawn}; use game::{Game, game_state, game_skill, game_ready}; use account::{Account, account_create, account_login, account_from_token, account_cryps, account_instances}; use skill::{Skill}; -// use zone::{Zone, zone_create, zone_join, zone_close}; use spec::{Spec}; use player::{Score, player_mm_cryps_set}; use instance::{Instance, instance_state, instance_new, instance_ready, instance_join}; -use vbox::{Item, VboxInfo, vbox_accept, vbox_apply, vbox_discard, vbox_combine, vbox_reclaim, vbox_unequip, vbox_info}; +use vbox::{vbox_accept, vbox_apply, vbox_discard, vbox_combine, vbox_reclaim, vbox_unequip}; +use item::{Item, ItemInfoCtr, item_info}; pub struct Rpc; @@ -97,7 +97,7 @@ impl Rpc { "player_vbox_reclaim" => Rpc::player_vbox_reclaim(data, &mut tx, account.unwrap(), client), "player_vbox_unequip" => Rpc::player_vbox_unequip(data, &mut tx, account.unwrap(), client), - "vbox_info" => Ok(RpcResponse { method: "vbox_info".to_string(), params: RpcResult::VboxInfo(vbox_info()) }), + "item_info" => Ok(RpcResponse { method: "item_info".to_string(), params: RpcResult::ItemInfo(item_info()) }), _ => Err(format_err!("unknown method - {:?}", v.method)), }; @@ -405,7 +405,7 @@ pub enum RpcResult { Account(Account), CrypList(Vec), GameState(Game), - VboxInfo(VboxInfo), + ItemInfo(ItemInfoCtr), InstanceScores(Vec<(String, Score)>), // ZoneState(Zone), // ZoneClose(()), diff --git a/server/src/skill.rs b/server/src/skill.rs index 6d29aeac..45756bcd 100644 --- a/server/src/skill.rs +++ b/server/src/skill.rs @@ -3,7 +3,7 @@ use uuid::Uuid; use util::{IntPct}; use cryp::{Cryp, CrypEffect, EffectMeta, Stat}; -use vbox::{Item}; +use item::{Item}; use game::{Game}; diff --git a/server/src/vbox.rs b/server/src/vbox.rs index c371107a..309ebc16 100644 --- a/server/src/vbox.rs +++ b/server/src/vbox.rs @@ -1,5 +1,4 @@ use std::iter; -use uuid::Uuid; // reclaims use rand::prelude::*; @@ -13,453 +12,10 @@ use failure::err_msg; use account::Account; use rpc::{VboxAcceptParams, VboxDiscardParams, VboxCombineParams, VboxApplyParams, VboxReclaimParams, VboxUnequipParams}; -use skill::{Skill}; -use spec::{Spec}; use instance::{Instance, instance_get, instance_update}; use cryp::{Colours}; -#[derive(Debug,Copy,Clone,Serialize,Deserialize,PartialEq,PartialOrd,Ord,Eq)] -pub enum Item { - // colours - Blue, - Green, - Red, - - // base skills - Attack, - Block, - Stun, - Buff, - Debuff, - - // specs - // Base - Damage, - Life, - Speed, - - // Lifes Upgrades - GreenLifeI, - RedLifeI, - BlueLifeI, - GRLI, - GBLI, - RBLI, - - // Damage Upgrades - RedDamageI, - BlueDamageI, - GreenDamageI, - GRDI, - GBDI, - RBDI, - - // Speed Upgrades - RedSpeedI, - BlueSpeedI, - GreenSpeedI, - GRSpeedI, - GBSpeedI, - RBSpeedI, - - Amplify, - Banish, - Blast, - Chaos, - Clutch, - Corrupt, - Curse, - Decay, - Hostility, - Haste, - Heal, - Hex, - Impurity, - Invert, - Parry, - Purge, - Purify, - Reflect, - Recharge, - Ruin, - Scatter, - Silence, - Slay, - Sleep, - Snare, - Strangle, - Strike, - StrikeII, - StrikeIII, - Siphon, - Taunt, - Throw, - Triage, - - - TestTouch, - TestStun, - TestBlock, - TestParry, - TestSiphon, -} - -pub enum ItemEffect { - Skill, - Spec, -} - -impl Item { - pub fn colours(&self, count: &mut Colours) { - let combos = get_combos(); - let combo = combos.iter().find(|c| c.item == *self); - match combo { - Some(c) => c.units.iter().for_each(|unit| match unit { - Item::Red => count.red += 1, - Item::Blue => count.blue += 1, - Item::Green => count.green += 1, - _ => { - let mut combo_count = Colours::new(); - unit.colours(&mut combo_count); - count.red += combo_count.red; - count.blue += combo_count.blue; - count.green += combo_count.green; - } - }), - None => (), - } - } - - fn cost(&self) -> u16 { - match self { - Item::Red => 1, - Item::Green => 1, - Item::Blue => 1, - - Item::Attack => 2, - Item::Block => 2, - Item::Buff => 2, - Item::Debuff => 2, - Item::Stun => 2, - - Item::Damage => 3, - Item::Life => 3, - Item::Speed => 3, - - _ => { - let combos = get_combos(); - let combo = combos.iter().find(|c| c.item == *self) - .unwrap_or_else(|| panic!("unable to find components for {:?}", self)); - return combo.units.iter().fold(0, |acc, c| acc + c.cost()); - }, - } - } - - pub fn speed(&self) -> u8 { - match self { - Item::Red => 3, - Item::Green => 2, - Item::Blue => 1, - - Item::Attack => 1, - Item::Stun => 2, - Item::Block => 3, - Item::Buff => 4, - Item::Debuff => 4, - - _ => { - let combos = get_combos(); - let combo = combos.iter().find(|c| c.item == *self) - .unwrap_or_else(|| panic!("unable to find components for {:?}", self)); - return combo.units.iter().fold(0, |acc, c| acc + c.speed()); - }, - } - } - - pub fn effect(&self) -> Option { - if let Some(_skill) = self.into_skill() { - return Some(ItemEffect::Skill); - } - if let Some(_spec) = self.into_spec() { - return Some(ItemEffect::Spec); - } - return None; - } - - pub fn into_skill(&self) -> Option { - match self { - Item::Attack => Some(Skill::Attack), - Item::Amplify => Some(Skill::Amplify), - Item::Banish => Some(Skill::Banish), - Item::Blast => Some(Skill::Blast), - Item::Block => Some(Skill::Block), - Item::Chaos => Some(Skill::Chaos), - Item::Curse => Some(Skill::Curse), - Item::Debuff => Some(Skill::Debuff), - Item::Decay => Some(Skill::Decay), - Item::Haste => Some(Skill::Haste), - Item::Heal => Some(Skill::Heal), - Item::Hex => Some(Skill::Hex), - Item::Hostility => Some(Skill::Hostility), - Item::Impurity => Some(Skill::Impurity), - Item::Invert => Some(Skill::Invert), - Item::Parry => Some(Skill::Parry), - Item::Purge => Some(Skill::Purge), - Item::Purify => Some(Skill::Purify), - Item::Recharge => Some(Skill::Recharge), - Item::Reflect => Some(Skill::Reflect), - Item::Ruin => Some(Skill::Ruin), - Item::Scatter => Some(Skill::Scatter), - Item::Silence => Some(Skill::Silence), - Item::Slay => Some(Skill::Slay), - Item::Sleep => Some(Skill::Sleep), - Item::Siphon => Some(Skill::Siphon), - Item::Snare => Some(Skill::Snare), - Item::Strangle => Some(Skill::Strangle), - Item::Stun => Some(Skill::Stun), - Item::Strike => Some(Skill::Strike), - Item::StrikeII => Some(Skill::StrikeII), - Item::StrikeIII => Some(Skill::StrikeIII), - Item::Clutch => Some(Skill::Clutch), - Item::Taunt => Some(Skill::Taunt), - Item::Throw => Some(Skill::Throw), - Item::Corrupt => Some(Skill::Corrupt), - Item::Triage => Some(Skill::Triage), - _ => None, - } - } - - pub fn into_spec(&self) -> Option { - match *self { - Item::Speed => Some(Spec::Speed), - Item::RedSpeedI => Some(Spec::RedSpeedI), - Item::BlueSpeedI => Some(Spec::BlueSpeedI), - Item::GreenSpeedI => Some(Spec::GreenSpeedI), - Item::GRSpeedI => Some(Spec::GRSpeedI), - Item::GBSpeedI => Some(Spec::GBSpeedI), - Item::RBSpeedI => Some(Spec::RBSpeedI), - - Item::Damage => Some(Spec::Damage), - Item::RedDamageI => Some(Spec::RedDamageI), - Item::BlueDamageI => Some(Spec::BlueDamageI), - Item::GreenDamageI => Some(Spec::GreenDamageI), - Item::GRDI => Some(Spec::GRDI), - Item::GBDI => Some(Spec::GBDI), - Item::RBDI => Some(Spec::RBDI), - - Item::Life => Some(Spec::Life), - Item::GRLI => Some(Spec::GRLI), - Item::GBLI => Some(Spec::GBLI), - Item::RBLI => Some(Spec::RBLI), - Item::GreenLifeI => Some(Spec::GreenLifeI), - Item::RedLifeI => Some(Spec::RedLifeI), - Item::BlueLifeI => Some(Spec::BlueLifeI), - - _ => None, - } - } -} - -impl From for Item { - fn from(skill: Skill) -> Item { - match skill { - Skill::Amplify => Item::Amplify, - Skill::Attack => Item::Attack, - Skill::Banish => Item::Banish, - Skill::Blast => Item::Blast, - Skill::Block => Item::Block, - Skill::Chaos => Item::Chaos, - Skill::Curse => Item::Curse, - Skill::Clutch => Item::Clutch, - Skill::Decay => Item::Decay, - Skill::Debuff => Item::Debuff, - Skill::Haste => Item::Haste, - Skill::Hostility => Item::Hostility, - Skill::Heal => Item::Heal, - Skill::Hex => Item::Hex, - Skill::Impurity => Item::Impurity, - Skill::Invert => Item::Invert, - Skill::Parry => Item::Parry, - Skill::Purge => Item::Purge, - Skill::Purify => Item::Purify, - Skill::Recharge => Item::Recharge, - Skill::Reflect => Item::Reflect, - Skill::Ruin => Item::Ruin, - Skill::Scatter => Item::Scatter, - Skill::Silence => Item::Silence, - Skill::Siphon => Item::Siphon, - Skill::Slay => Item::Slay, - Skill::Sleep => Item::Sleep, - Skill::Snare => Item::Snare, - Skill::Strangle => Item::Strangle, - Skill::Strike => Item::Strike, - Skill::StrikeII => Item::StrikeII, - Skill::StrikeIII => Item::StrikeIII, - Skill::Stun => Item::Stun, - Skill::Taunt => Item::Taunt, - Skill::Throw => Item::Throw, - Skill::Triage => Item::Triage, - Skill::Corrupt => Item::Corrupt, - - Skill::TestTouch => Item::TestTouch, - Skill::TestStun => Item::TestStun, - Skill::TestBlock => Item::TestBlock, - Skill::TestParry => Item::TestParry, - Skill::TestSiphon => Item::TestSiphon, - _ => panic!("{:?} not implemented as a item", skill), - } - } -} - -impl From for Item { - fn from(spec: Spec) -> Item { - match spec { - Spec::Speed => Item::Speed, - Spec::RedSpeedI => Item::RedSpeedI, - Spec::BlueSpeedI => Item::BlueSpeedI, - Spec::GreenSpeedI => Item::GreenSpeedI, - Spec::GRSpeedI => Item::GRSpeedI, - Spec::GBSpeedI => Item::GBSpeedI, - Spec::RBSpeedI => Item::RBSpeedI, - - Spec::Damage => Item::Damage, - Spec::RedDamageI => Item::RedDamageI, - Spec::BlueDamageI => Item::BlueDamageI, - Spec::GreenDamageI => Item::GreenDamageI, - Spec::GRDI => Item::GRDI, - Spec::GBDI => Item::GBDI, - Spec::RBDI => Item::RBDI, - - Spec::Life => Item::Life, - Spec::GRLI => Item::GRLI, - Spec::GBLI => Item::GBLI, - Spec::RBLI => Item::RBLI, - Spec::GreenLifeI => Item::GreenLifeI, - Spec::RedLifeI => Item::RedLifeI, - Spec::BlueLifeI => Item::BlueLifeI, - // _ => panic!("{:?} not implemented as a item", spec), - } - } -} - - -#[derive(Debug,Clone,Serialize,Deserialize)] -pub struct Combo { - item: Item, - units: Vec, -} - -fn get_combos() -> Vec { - let mut combinations = vec![ - Combo { units: vec![Item::Buff, Item::Red, Item::Red], item: Item::Taunt }, - Combo { units: vec![Item::Buff, Item::Green, Item::Green], item: Item::Triage }, - Combo { units: vec![Item::Buff, Item::Blue, Item::Blue], item: Item::Scatter }, //To be impl - Combo { units: vec![Item::Buff, Item::Red, Item::Green], item: Item::Haste }, - Combo { units: vec![Item::Buff, Item::Green, Item::Blue], item: Item::Impurity }, - Combo { units: vec![Item::Buff, Item::Red, Item::Blue], item: Item::Amplify }, // Some flavour - - Combo { units: vec![Item::Debuff, Item::Red, Item::Red], item: Item::Snare }, - Combo { units: vec![Item::Debuff, Item::Green, Item::Green], item: Item::Purge }, // Needs flavour - Combo { units: vec![Item::Debuff, Item::Blue, Item::Blue], item: Item::Silence }, - Combo { units: vec![Item::Debuff, Item::Red, Item::Green], item: Item::Curse }, // To be reworked - Combo { units: vec![Item::Debuff, Item::Green, Item::Blue], item: Item::Decay }, - Combo { units: vec![Item::Debuff, Item::Red, Item::Blue], item: Item::Invert }, - - Combo { units: vec![Item::Block, Item::Red, Item::Red], item: Item::Parry }, // Add red recharge - Combo { units: vec![Item::Block, Item::Green, Item::Green], item: Item::Purify }, - Combo { units: vec![Item::Block, Item::Blue, Item::Blue], item: Item::Corrupt }, - Combo { units: vec![Item::Block, Item::Red, Item::Green], item: Item::Clutch }, - Combo { units: vec![Item::Block, Item::Green, Item::Blue], item: Item::Reflect }, - Combo { units: vec![Item::Block, Item::Red, Item::Blue], item: Item::Recharge }, - - Combo { units: vec![Item::Stun, Item::Red, Item::Red], item: Item::Strangle }, - Combo { units: vec![Item::Stun, Item::Green, Item::Green], item: Item::Sleep }, - Combo { units: vec![Item::Stun, Item::Blue, Item::Blue], item: Item::Ruin }, - Combo { units: vec![Item::Stun, Item::Red, Item::Green], item: Item::Throw }, - Combo { units: vec![Item::Stun, Item::Green, Item::Blue], item: Item::Hex }, - Combo { units: vec![Item::Stun, Item::Red, Item::Blue], item: Item::Banish }, - - Combo { units: vec![Item::Attack, Item::Red, Item::Red], item: Item::Strike }, - Combo { units: vec![Item::Strike, Item::Strike, Item::Strike], item: Item::StrikeII }, - Combo { units: vec![Item::StrikeII, Item::StrikeII, Item::StrikeII], item: Item::StrikeIII }, - - Combo { units: vec![Item::Attack, Item::Green, Item::Green], item: Item::Heal }, - Combo { units: vec![Item::Attack, Item::Blue, Item::Blue], item: Item::Blast }, - Combo { units: vec![Item::Attack, Item::Red, Item::Green], item: Item::Slay }, - Combo { units: vec![Item::Attack, Item::Green, Item::Blue], item: Item::Siphon }, - Combo { units: vec![Item::Attack, Item::Red, Item::Blue], item: Item::Chaos }, - - Combo { units: vec![Item::Damage, Item::Red, Item::Red], item: Item::RedDamageI }, - Combo { units: vec![Item::Damage, Item::Green, Item::Green], item: Item::GreenDamageI }, - Combo { units: vec![Item::Damage, Item::Blue, Item::Blue], item: Item::BlueDamageI }, - Combo { units: vec![Item::Damage, Item::Red, Item::Green], item: Item::GRDI }, - Combo { units: vec![Item::Damage, Item::Green, Item::Blue], item: Item::GBDI }, - Combo { units: vec![Item::Damage, Item::Red, Item::Blue], item: Item::RBDI }, - - Combo { units: vec![Item::Life, Item::Red, Item::Red], item: Item::RedLifeI }, - Combo { units: vec![Item::Life, Item::Green, Item::Green], item: Item::GreenLifeI }, - Combo { units: vec![Item::Life, Item::Blue, Item::Blue], item: Item::BlueLifeI }, - Combo { units: vec![Item::Life, Item::Red, Item::Green], item: Item::GRLI }, - Combo { units: vec![Item::Life, Item::Green, Item::Blue], item: Item::GBLI }, - Combo { units: vec![Item::Life, Item::Red, Item::Blue], item: Item::RBLI }, - - Combo { units: vec![Item::Speed, Item::Red, Item::Red], item: Item::RedSpeedI }, - Combo { units: vec![Item::Speed, Item::Green, Item::Green], item: Item::GreenSpeedI }, - Combo { units: vec![Item::Speed, Item::Blue, Item::Blue], item: Item::BlueSpeedI }, - Combo { units: vec![Item::Speed, Item::Red, Item::Green], item: Item::GRSpeedI }, - Combo { units: vec![Item::Speed, Item::Green, Item::Blue], item: Item::GBSpeedI }, - Combo { units: vec![Item::Speed, Item::Red, Item::Blue], item: Item::RBSpeedI }, - - ]; - - combinations.iter_mut().for_each(|set| set.units.sort_unstable()); - - return combinations; -} - -#[derive(Debug,Clone,Serialize,Deserialize)] -pub struct ItemInfo { - pub v: Item, - pub spec: bool, - pub skill: bool, -} - - -#[derive(Debug,Clone,Serialize,Deserialize)] -pub struct VboxInfo { - pub combos: Vec, - pub items: Vec, -} - -pub fn vbox_info() -> VboxInfo { - let combos = get_combos(); - let mut items = combos - .into_iter() - .flat_map(|mut c| { - c.units.push(c.item); - c.units - }) - .collect::>(); - - items.sort_unstable(); - items.dedup(); - - let items = items - .into_iter() - .map(|v| ItemInfo { - v, - spec: v.into_spec().is_some(), - skill: v.into_skill().is_some(), - }) - .collect::>(); - - let combos = get_combos(); - - return VboxInfo { - combos, - items, - }; -} +use item::*; #[derive(Debug,Clone,Serialize,Deserialize)] pub struct Vbox { @@ -677,7 +233,7 @@ mod tests { } // #[test] - // fn vbox_info_test() { - // info!("{:#?}", vbox_info()); + // fn item_info_test() { + // info!("{:#?}", item_info()); // } } \ No newline at end of file