diff --git a/client/assets/styles/instance.less b/client/assets/styles/instance.less
index 055ee56e..2ebd9f12 100644
--- a/client/assets/styles/instance.less
+++ b/client/assets/styles/instance.less
@@ -5,114 +5,17 @@
.instance {
overflow: hidden;
display: grid;
- grid-template-columns: 1fr minmax(min-content, 1fr);
grid-template-rows: min-content 1fr;
grid-template-areas:
- "vbox info"
- "constructs constructs";
-
- .info {
- h2 {
- text-transform: uppercase;
- }
- svg {
- display: inline;
- height: 1em;
- }
- figure {
- display: inline;
- height: 0.5em;
- svg {
- margin-right: 0.5em;
- }
- }
- figcaption {
- font-size: 1em;
- display: inline-block;
- vertical-align: middle;
- }
- margin-left: 1em;
- grid-area: info;
- display: grid;
- grid-template-columns: 1fr min-content;
- grid-template-areas:
- "item combos";
-
- .info-item {
- grid-area: item;
- }
- .combos {
- display: grid;
- grid-area: combos;
- margin-left: 0.5em;
- grid-template-rows: min-content min-content;
- grid-template-areas:
- "comboHeader"
- "comboList";
- .combo-header {
- text-align: center;
- }
-
- .combo-list {
- display: grid;
- grid-template-rows: min-content min-content min-content;
- grid-template-columns: min-content min-content;
- grid-gap: 0.5em;
- margin-top: 0.5em;
- width: 15.5em;
-
- .table-button {
- display: grid;
- text-align: center;
- align-content: center;
- grid-template-areas:
- "item"
- "ingr";
-
- cursor: pointer;
- &:hover {
- color: whitesmoke;
- background-color: @gray;
- }
-
- .item {
- border-top: 2px solid #222;
- border-bottom: 2px solid #222;
- flex: 1;
- grid-area: item;
- font-weight: bold;
- div {
- width: 5em;
- }
- }
-
-
- div {
- border-left: 2px solid #222;
- border-right: 2px solid #222;
- height: 1.75em;
- width: 7.5em;
- svg {
- vertical-align: middle;
- }
- &:last-child {
- border-bottom: 2px solid #222;
- }
- }
- }
- }
- }
- }
+ "vbox"
+ "constructs";
.constructs {
grid-area: constructs;
}
}
-
-
-
@keyframes action {
0% {
color: palegoldenrod;
diff --git a/client/assets/styles/vbox.less b/client/assets/styles/vbox.less
index 6b51f9de..05dd9867 100644
--- a/client/assets/styles/vbox.less
+++ b/client/assets/styles/vbox.less
@@ -3,10 +3,10 @@
grid-area: vbox;
display: grid;
grid-template-rows: 3fr 2fr;
- grid-template-columns: 1fr 4fr 1fr;
+ grid-template-columns: 1fr 4fr 6fr;
grid-template-areas:
- "store-hdr store combiner"
- "stash-hdr stash combiner";
+ "store-hdr store info"
+ "stash-hdr stash info";
margin-bottom: 1em;
line-height: 0;
@@ -46,38 +46,6 @@
}
}
- .combiner {
- grid-area: combiner;
- display: flex;
- flex-direction: column;
- line-height: 1.3;
-
- padding: 0;
-
- .vbox-padding {
- margin-right: 0em;
- margin-bottom: 0em;
- }
-
- button {
- line-height: 1.3;
- font-size: 1.25em;
-
- letter-spacing: 0.1em;
- background-color: @yellow;
- color: black;
- border-radius: 0;
- border: 0;
- &[disabled] {
- border: 0.1em solid @gray;
- border-left: 0;
- color: @gray-exists;
- };
-
- transition-property: 0;
- }
- }
-
.stash {
grid-area: stash;
display: grid;
@@ -210,6 +178,126 @@
line-height: initial;
}
}
+
+ .info {
+ line-height: 1.6;
+
+ h2 {
+ text-transform: uppercase;
+ }
+ svg {
+ display: inline;
+ height: 1em;
+ }
+ figure {
+ display: inline;
+ height: 0.5em;
+ svg {
+ margin-right: 0.5em;
+ }
+ }
+ figcaption {
+ font-size: 1em;
+ display: inline-block;
+ vertical-align: middle;
+ }
+ margin-left: 1em;
+ grid-area: info;
+ display: grid;
+ grid-template-rows: min-content min-content;
+ grid-template-columns: 1fr min-content;
+ grid-template-areas:
+ "item combos"
+ "combiner combos";
+
+ .combiner {
+ grid-area: combiner;
+ button {
+ margin-top: 1em;
+ line-height: 1.3;
+ font-size: 1.25em;
+
+
+ letter-spacing: 0.1em;
+ background-color: @yellow;
+ color: black;
+ border-radius: 0;
+ border: 0;
+ &[disabled] {
+ border: 0.1em solid @gray;
+ border-left: 0;
+ color: @gray-exists;
+ };
+ transition-property: 0;
+ }
+ }
+
+
+ .info-item {
+ grid-area: item;
+ }
+ .combos {
+ display: grid;
+ grid-area: combos;
+ margin-left: 0.5em;
+ grid-template-rows: min-content min-content;
+ grid-template-areas:
+ "comboHeader"
+ "comboList";
+ .combo-header {
+ text-align: center;
+ }
+
+ .combo-list {
+ display: grid;
+ grid-template-rows: min-content min-content min-content;
+ grid-template-columns: min-content min-content;
+ grid-gap: 0.5em;
+ margin-top: 0.5em;
+ width: 15.5em;
+
+ .table-button {
+ display: grid;
+ text-align: center;
+ align-content: center;
+ grid-template-areas:
+ "item"
+ "ingr";
+
+ cursor: pointer;
+ &:hover {
+ color: whitesmoke;
+ background-color: @gray;
+ }
+
+ .item {
+ border-top: 2px solid #222;
+ border-bottom: 2px solid #222;
+ flex: 1;
+ grid-area: item;
+ font-weight: bold;
+ div {
+ width: 5em;
+ }
+ }
+
+
+ div {
+ border-left: 2px solid #222;
+ border-right: 2px solid #222;
+ height: 1.75em;
+ width: 7.5em;
+ svg {
+ vertical-align: middle;
+ }
+ &:last-child {
+ border-bottom: 2px solid #222;
+ }
+ }
+ }
+ }
+ }
+ }
}
@media (min-width: 2000px) {
diff --git a/client/src/components/info.component.jsx b/client/src/components/info.component.jsx
index eec7b710..4b59e4d3 100644
--- a/client/src/components/info.component.jsx
+++ b/client/src/components/info.component.jsx
@@ -7,9 +7,12 @@ const { convertItem, removeTier } = require('../utils');
const { tutorialStage } = require('../tutorial.utils');
const shapes = require('./shapes');
+const Combiner = require('./vbox.combiner');
+
class InfoComponent extends preact.Component {
shouldComponentUpdate(newProps, newState) {
+ if (newProps.vboxHighlight !== this.props.vboxHighlight) return true;
if (newProps.tutorial !== this.props.tutorial) return true;
// We don't care about info during tutorial
if (newProps.tutorial && this.props.instance.time_control === 'Practice'
@@ -30,6 +33,7 @@ class InfoComponent extends preact.Component {
// Variables that will change
info,
tutorial,
+ vboxHighlight,
// Static
player, // Only used for colour calcs which will be update if info changes
@@ -37,7 +41,6 @@ class InfoComponent extends preact.Component {
itemInfo,
instance, // Only used for instance id
// functions
- setInfo,
setTutorialNull,
} = args;
const { comboItem } = this.state;
@@ -181,6 +184,7 @@ class InfoComponent extends preact.Component {
this.setState({ comboItem: null })}>
+
diff --git a/client/src/components/instance.component.jsx b/client/src/components/instance.component.jsx
index a8abcac0..d0d34345 100644
--- a/client/src/components/instance.component.jsx
+++ b/client/src/components/instance.component.jsx
@@ -2,7 +2,6 @@ const preact = require('preact');
const { connect } = require('preact-redux');
const Vbox = require('./vbox.component');
-const InfoContainer = require('./info.container');
const InstanceConstructsContainer = require('./instance.constructs');
const Faceoff = require('./faceoff');
@@ -63,7 +62,6 @@ function Instance(args) {
return (
-
);
diff --git a/client/src/components/vbox.combiner.jsx b/client/src/components/vbox.combiner.jsx
index 5b02b88e..1ffd6797 100644
--- a/client/src/components/vbox.combiner.jsx
+++ b/client/src/components/vbox.combiner.jsx
@@ -1,66 +1,123 @@
const preact = require('preact');
+const { connect } = require('preact-redux');
const countBy = require('lodash/countBy');
-function combinerBtn(props) {
- const {
- itemInfo,
- sendVboxCombine,
- setInfo,
- stashSelect,
- storeSelect,
- vbox,
- vboxBuySelected,
- vboxHighlight,
- } = props;
- let text = '';
- let mouseEvent = false;
- const combineLength = stashSelect.length + storeSelect.length;
- if (vboxHighlight && vboxHighlight.length === 0) {
- // The selected items can't be combined with additional items therefore valid combo
- const stashItems = stashSelect.map(j => vbox.bound[j]);
- const shopItems = storeSelect.map(j => vbox.free[j[0]][j[1]]);
- const selectedItems = stashItems.concat(shopItems);
- const combinerCount = countBy(selectedItems, co => co);
+const actions = require('../actions');
- const comboItemObj = itemInfo.combos.find(combo => selectedItems.every(c => {
- if (!combo.components.includes(c)) return false;
- const comboCount = countBy(combo.components, co => co);
- if (combinerCount[c] > comboCount[c]) return false;
- return true;
- }));
- let comboItem = comboItemObj ? comboItemObj.item : 'refine';
- setInfo(comboItem);
- comboItem = comboItem.replace('Plus', '+');
- let bits = 0;
- storeSelect.forEach(item => bits += item[0] + 1);
- text = bits
- ? Buy
{comboItem}
{bits}b
- : Combine
{comboItem}
;
- if (vbox.bits >= bits) mouseEvent = sendVboxCombine;
- } else if (stashSelect.length === 0 && storeSelect.length === 1) {
- const item = storeSelect[0];
- text = Buy
{vbox.free[item[0]][item[1]]}
{item[0] + 1}b
;
- mouseEvent = vboxBuySelected;
- } else {
- for (let i = 0; i < 3; i++) {
- if (combineLength > i) {
- text += '■ ';
- } else {
- text += '▫ ';
- }
+const addState = connect(
+ function receiveState(state) {
+ const {
+ ws,
+ instance,
+ vboxSelected,
+ itemInfo,
+ player,
+ } = state;
+
+ const { vbox } = player;
+ function sendVboxAccept(group, index) {
+ document.activeElement.blur();
+ return ws.sendVboxAccept(instance.id, group, index);
}
+
+ function sendVboxCombine() {
+ return ws.sendVboxCombine(instance.id, vboxSelected.stashSelect, vboxSelected.storeSelect);
+ }
+
+ return {
+ vbox,
+ vboxSelected,
+ itemInfo,
+ sendVboxAccept,
+ sendVboxCombine,
+ };
+ },
+ function receiveDispatch(dispatch) {
+ function setInfo(item) {
+ return dispatch(actions.setInfo(item));
+ }
+
+ return {
+ setInfo,
+ };
+ }
+);
+
+class CombinerBtn extends preact.Component {
+ shouldComponentUpdate(newProps) {
+ // Single variable props
+ if (newProps.vbox !== this.props.vbox) return true;
+ if (newProps.vboxHighlight !== this.props.vboxHighlight) return true;
+ if (newProps.vboxSelected !== this.props.vboxSelected) return true;
+ return false;
+ }
+
+ render(props) {
+ const {
+ vboxHighlight,
+
+ vbox,
+ vboxSelected,
+ itemInfo,
+ sendVboxAccept,
+ sendVboxCombine,
+
+ setInfo,
+ } = props;
+
+ const { stashSelect, storeSelect } = vboxSelected;
+
+ function vboxBuySelected() {
+ if (!(storeSelect.length === 1 && stashSelect.length === 0)) return false;
+ document.activeElement.blur();
+ sendVboxAccept(storeSelect[0][0], storeSelect[0][1]);
+ return true;
+ }
+
+ let text = '';
+ let mouseEvent = false;
+ const combineLength = stashSelect.length + storeSelect.length;
+ if (vboxHighlight && vboxHighlight.length === 0) {
+ // The selected items can't be combined with additional items therefore valid combo
+ const stashItems = stashSelect.map(j => vbox.bound[j]);
+ const shopItems = storeSelect.map(j => vbox.free[j[0]][j[1]]);
+ const selectedItems = stashItems.concat(shopItems);
+ const combinerCount = countBy(selectedItems, co => co);
+
+ const comboItemObj = itemInfo.combos.find(combo => selectedItems.every(c => {
+ if (!combo.components.includes(c)) return false;
+ const comboCount = countBy(combo.components, co => co);
+ if (combinerCount[c] > comboCount[c]) return false;
+ return true;
+ }));
+ let comboItem = comboItemObj ? comboItemObj.item : 'refine';
+ setInfo(comboItem);
+ comboItem = comboItem.replace('Plus', '+');
+ let bits = 0;
+ storeSelect.forEach(item => bits += item[0] + 1);
+ text = bits
+ ? `Buy ${comboItem} ${bits}b`
+ : `Combine${comboItem}`;
+ if (vbox.bits >= bits) mouseEvent = sendVboxCombine;
+ } else if (stashSelect.length === 0 && storeSelect.length === 1) {
+ const item = storeSelect[0];
+ text = `Buy ${vbox.free[item[0]][item[1]]} ${item[0] + 1}b`;
+ mouseEvent = vboxBuySelected;
+ } else {
+ return false;
+ }
+ return (
+
+
+
+ );
}
- return (
-
-
-
- );
}
-module.exports = combinerBtn;
+module.exports = addState(CombinerBtn);
diff --git a/client/src/components/vbox.component.jsx b/client/src/components/vbox.component.jsx
index e51b94be..756f17ee 100644
--- a/client/src/components/vbox.component.jsx
+++ b/client/src/components/vbox.component.jsx
@@ -5,9 +5,9 @@ const forEach = require('lodash/forEach');
const actions = require('../actions');
+const InfoContainer = require('./info.container');
const StashElement = require('./vbox.stash');
const StoreElement = require('./vbox.store');
-const CombinerElement = require('./vbox.combiner');
const addState = connect(
function receiveState(state) {
@@ -16,6 +16,7 @@ const addState = connect(
instance,
player,
vboxSelected,
+ info,
itemInfo,
itemUnequip,
tutorial,
@@ -30,10 +31,6 @@ const addState = connect(
return ws.sendVboxAccept(instance.id, group, index);
}
- function sendVboxCombine() {
- return ws.sendVboxCombine(instance.id, vboxSelected.stashSelect, vboxSelected.storeSelect);
- }
-
function sendVboxReclaim(i) {
return ws.sendVboxReclaim(instance.id, i);
}
@@ -44,9 +41,9 @@ const addState = connect(
return {
instance,
+ info,
player,
sendVboxAccept,
- sendVboxCombine,
sendVboxDiscard,
sendVboxReclaim,
vboxSelected,
@@ -130,7 +127,6 @@ class Vbox extends preact.Component {
// Function Calls
sendItemUnequip,
sendVboxAccept,
- sendVboxCombine,
sendVboxDiscard,
sendVboxReclaim,
setVboxSelected,
@@ -235,6 +231,10 @@ class Vbox extends preact.Component {
{storeHdr()}
{stashHdr()}
+
-
);
}