mirror of
https://github.com/EDCD/coriolis.git
synced 2025-12-10 15:15:34 +00:00
Restyle modifications menu
This commit is contained in:
@@ -15,6 +15,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
static propTypes = {
|
||||
ship: React.PropTypes.object.isRequired,
|
||||
m: React.PropTypes.object.isRequired,
|
||||
marker: React.PropTypes.string.isRequired,
|
||||
onChange: React.PropTypes.func.isRequired
|
||||
};
|
||||
|
||||
@@ -25,7 +26,6 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
*/
|
||||
constructor(props, context) {
|
||||
super(props);
|
||||
this.state = this._initState(props, context);
|
||||
|
||||
this._toggleBlueprintsMenu = this._toggleBlueprintsMenu.bind(this);
|
||||
this._toggleSpecialsMenu = this._toggleSpecialsMenu.bind(this);
|
||||
@@ -34,33 +34,59 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
this._rollBest = this._rollBest.bind(this);
|
||||
this._rollExtreme = this._rollExtreme.bind(this);
|
||||
this._reset = this._reset.bind(this);
|
||||
|
||||
this.state = {
|
||||
blueprintMenuOpened: false,
|
||||
specialMenuOpened: false
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialise state
|
||||
* @param {Object} props React Component properties
|
||||
* @param {Object} context React Component context
|
||||
* Render the blueprints
|
||||
* @param {Object} props React component properties
|
||||
* @param {Object} context React component context
|
||||
* @return {Object} list: Array of React Components
|
||||
*/
|
||||
_initState(props, context) {
|
||||
let { m } = props;
|
||||
_renderBlueprints(props, context) {
|
||||
const { m } = props;
|
||||
const { language, tooltip, termtip } = context;
|
||||
const translate = language.translate;
|
||||
|
||||
// Set up the blueprints
|
||||
let blueprints = [];
|
||||
const blueprints = [];
|
||||
for (const blueprintName in Modifications.modules[m.grp].blueprints) {
|
||||
for (const grade in Modifications.modules[m.grp].blueprints[blueprintName].grades) {
|
||||
const blueprint = getBlueprint(blueprintName, m);
|
||||
let blueprintGrades = [];
|
||||
for (let grade in Modifications.modules[m.grp].blueprints[blueprintName].grades) {
|
||||
// Grade is a string in the JSON so make it a number
|
||||
grade = Number(grade);
|
||||
const classes = cn('c', {
|
||||
active: m.blueprint && blueprint.id === m.blueprint.id && grade === m.blueprint.grade
|
||||
});
|
||||
const close = this._blueprintSelected.bind(this, blueprintName, grade);
|
||||
const key = blueprintName + ':' + grade;
|
||||
const blueprint = getBlueprint(blueprintName, m);
|
||||
const tooltipContent = blueprintTooltip(translate, blueprint.grades[grade], Modifications.modules[m.grp].blueprints[blueprintName].grades[grade].engineers);
|
||||
blueprints.push(<div style={{ cursor: 'pointer' }} key={ key } onMouseOver={termtip.bind(null, tooltipContent)} onMouseOut={tooltip.bind(null, null)} onClick={ close }>{translate(blueprint.name + ' grade ' + grade)}</div>);
|
||||
blueprintGrades.unshift(<li key={key} className={classes} style={{ width: '2em' }} onMouseOver={termtip.bind(null, tooltipContent)} onMouseOut={tooltip.bind(null, null)} onClick={close}>{grade}</li>);
|
||||
}
|
||||
if (blueprintGrades) {
|
||||
blueprints.push(<div key={blueprint.name} className={'select-group cap'}>{translate(blueprint.name)}</div>);
|
||||
blueprints.push(<ul key={blueprintName}>{blueprintGrades}</ul>);
|
||||
}
|
||||
}
|
||||
return blueprints;
|
||||
}
|
||||
|
||||
// Set up the special effects
|
||||
let specials = [];
|
||||
/**
|
||||
* Render the specials
|
||||
* @param {Object} props React component properties
|
||||
* @param {Object} context React component context
|
||||
* @return {Object} list: Array of React Components
|
||||
*/
|
||||
_renderSpecials(props, context) {
|
||||
const { m } = props;
|
||||
const { language, tooltip, termtip } = context;
|
||||
const translate = language.translate;
|
||||
|
||||
const specials = [];
|
||||
if (Modifications.modules[m.grp].specials && Modifications.modules[m.grp].specials.length > 0) {
|
||||
const close = this._specialSelected.bind(this, null);
|
||||
specials.push(<div style={{ cursor: 'pointer' }} key={ 'none' } onClick={ close }>{translate('PHRASE_NO_SPECIAL')}</div>);
|
||||
@@ -69,24 +95,17 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
specials.push(<div style={{ cursor: 'pointer' }} key={ specialName } onClick={ close }>{translate(Modifications.specials[specialName].name)}</div>);
|
||||
}
|
||||
}
|
||||
|
||||
// Set up the modifications
|
||||
const modifications = this._setModifications(props);
|
||||
|
||||
const blueprintMenuOpened = false;
|
||||
const specialMenuOpened = false;
|
||||
|
||||
return { blueprintMenuOpened, blueprints, modifications, specialMenuOpened, specials };
|
||||
return specials;
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialise the modifications
|
||||
* Render the modifications
|
||||
* @param {Object} props React Component properties
|
||||
* @return {Object} list: Array of React Components
|
||||
*/
|
||||
_setModifications(props) {
|
||||
_renderModifications(props) {
|
||||
const { m, onChange, ship } = props;
|
||||
let modifications = [];
|
||||
const modifications = [];
|
||||
for (const modName of Modifications.modules[m.grp].modifications) {
|
||||
if (!Modifications.modifications[modName].hidden) {
|
||||
const key = modName + (m.getModValue(modName) / 100 || 0);
|
||||
@@ -116,8 +135,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
blueprint.grade = grade;
|
||||
m.blueprint = blueprint;
|
||||
|
||||
const blueprintMenuOpened = false;
|
||||
this.setState({ blueprintMenuOpened });
|
||||
this.setState({ blueprintMenuOpened: false });
|
||||
this.props.onChange();
|
||||
}
|
||||
|
||||
@@ -148,8 +166,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
ship.recalculateEps();
|
||||
}
|
||||
|
||||
const specialMenuOpened = false;
|
||||
this.setState({ specialMenuOpened, modifications: this._setModifications(this.props) });
|
||||
this.setState({ specialMenuOpened: false });
|
||||
this.props.onChange();
|
||||
}
|
||||
|
||||
@@ -181,7 +198,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
let value = features[featureName][0];
|
||||
this._setRollResult(ship, m, featureName, value);
|
||||
}
|
||||
this.setState({ modifications: this._setModifications(this.props) });
|
||||
|
||||
this.props.onChange();
|
||||
}
|
||||
|
||||
@@ -196,7 +213,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
let value = features[featureName][0] + (Math.random() * (features[featureName][1] - features[featureName][0]));
|
||||
this._setRollResult(ship, m, featureName, value);
|
||||
}
|
||||
this.setState({ modifications: this._setModifications(this.props) });
|
||||
|
||||
this.props.onChange();
|
||||
}
|
||||
|
||||
@@ -210,7 +227,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
let value = features[featureName][1];
|
||||
this._setRollResult(ship, m, featureName, value);
|
||||
}
|
||||
this.setState({ modifications: this._setModifications(this.props) });
|
||||
|
||||
this.props.onChange();
|
||||
}
|
||||
|
||||
@@ -241,7 +258,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
|
||||
this._setRollResult(ship, m, featureName, value);
|
||||
}
|
||||
this.setState({ modifications: this._setModifications(this.props) });
|
||||
|
||||
this.props.onChange();
|
||||
}
|
||||
|
||||
@@ -253,7 +270,6 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
ship.clearModifications(m);
|
||||
ship.clearBlueprint(m);
|
||||
|
||||
this.setState({ modifications: this._setModifications(this.props) });
|
||||
this.props.onChange();
|
||||
}
|
||||
|
||||
@@ -291,8 +307,10 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
specialLabel = translate('PHRASE_SELECT_SPECIAL');
|
||||
}
|
||||
|
||||
const specials = this._renderSpecials(this.props, this.context);
|
||||
|
||||
const showBlueprintsMenu = blueprintMenuOpened;
|
||||
const showSpecial = haveBlueprint && this.state.specials.length > 0 && !blueprintMenuOpened;
|
||||
const showSpecial = haveBlueprint && specials.length && !blueprintMenuOpened;
|
||||
const showSpecialsMenu = specialMenuOpened;
|
||||
const showRolls = haveBlueprint && !blueprintMenuOpened && !specialMenuOpened;
|
||||
const showReset = !blueprintMenuOpened && !specialMenuOpened;
|
||||
@@ -304,12 +322,12 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
onClick={(e) => e.stopPropagation() }
|
||||
onContextMenu={stopCtxPropagation}
|
||||
>
|
||||
{ haveBlueprint ?
|
||||
{ showBlueprintsMenu ? '' : haveBlueprint ?
|
||||
<div className={ cn('section-menu', { selected: blueprintMenuOpened })} style={{ cursor: 'pointer' }} onMouseOver={termtip.bind(null, blueprintTt)} onMouseOut={tooltip.bind(null, null)} onClick={_toggleBlueprintsMenu}>{blueprintLabel}</div> :
|
||||
<div className={ cn('section-menu', { selected: blueprintMenuOpened })} style={{ cursor: 'pointer' }} onClick={_toggleBlueprintsMenu}>{translate('PHRASE_SELECT_BLUEPRINT')}</div> }
|
||||
{ showBlueprintsMenu ? this.state.blueprints : null }
|
||||
{ showBlueprintsMenu ? this._renderBlueprints(this.props, this.context) : null }
|
||||
{ showSpecial ? <div className={ cn('section-menu', { selected: specialMenuOpened })} style={{ cursor: 'pointer' }} onClick={_toggleSpecialsMenu}>{specialLabel}</div> : null }
|
||||
{ showSpecialsMenu ? this.state.specials : null }
|
||||
{ showSpecialsMenu ? specials : null }
|
||||
{ showRolls || showReset ?
|
||||
<table style={{ width: '100%', backgroundColor: 'transparent' }}>
|
||||
<tbody>
|
||||
@@ -329,7 +347,7 @@ export default class ModificationsMenu extends TranslatedComponent {
|
||||
</table> : null }
|
||||
{ showMods ?
|
||||
<span onMouseOver={termtip.bind(null, 'HELP_MODIFICATIONS_MENU')} onMouseOut={tooltip.bind(null, null)} >
|
||||
{ this.state.modifications }
|
||||
{ this._renderModifications(this.props) }
|
||||
</span> : null }
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -79,7 +79,7 @@ export default class Slot extends TranslatedComponent {
|
||||
let language = this.context.language;
|
||||
let translate = language.translate;
|
||||
let { ship, m, dropClass, dragOver, onOpen, onChange, selected, eligible, onSelect, warning, availableModules } = this.props;
|
||||
let slotDetails, menu;
|
||||
let slotDetails, modificationsMarker, menu;
|
||||
|
||||
if (!selected) {
|
||||
// If not selected then sure that modifications flag is unset
|
||||
@@ -88,8 +88,10 @@ export default class Slot extends TranslatedComponent {
|
||||
|
||||
if (m) {
|
||||
slotDetails = this._getSlotDetails(m, translate, language.formats, language.units); // Must be implemented by sub classes
|
||||
modificationsMarker = JSON.stringify(m);
|
||||
} else {
|
||||
slotDetails = <div className={'empty'}>{translate(eligible ? 'emptyrestricted' : 'empty')}</div>;
|
||||
modificationsMarker = '';
|
||||
}
|
||||
|
||||
if (selected) {
|
||||
@@ -99,6 +101,7 @@ export default class Slot extends TranslatedComponent {
|
||||
onChange={onChange}
|
||||
ship={ship}
|
||||
m={m}
|
||||
marker={modificationsMarker}
|
||||
/>;
|
||||
} else {
|
||||
menu = <AvailableModulesMenu
|
||||
|
||||
@@ -16,7 +16,6 @@
|
||||
@import 'tooltip';
|
||||
@import 'buttons';
|
||||
@import 'error';
|
||||
@import 'shipselector';
|
||||
@import 'sortable';
|
||||
@import 'loader';
|
||||
@import 'pips';
|
||||
|
||||
@@ -29,7 +29,7 @@ select {
|
||||
padding: 0.5em 0;
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
max-height: 400px;
|
||||
max-height: 500px;
|
||||
overflow-y: auto;
|
||||
overflow-x: hidden;
|
||||
z-index: 0;
|
||||
|
||||
@@ -1,199 +0,0 @@
|
||||
.shipselector {
|
||||
background-color: @bgBlack;
|
||||
margin: 0;
|
||||
padding: 0 0 0 1em;
|
||||
height: 3em;
|
||||
line-height: 3em;
|
||||
font-family: @fTitle;
|
||||
vertical-align: middle;
|
||||
position: relative;
|
||||
|
||||
.user-select-none();
|
||||
|
||||
.menu {
|
||||
position: relative;
|
||||
z-index: 1;
|
||||
cursor: default;
|
||||
|
||||
&.r {
|
||||
.menu-list {
|
||||
right: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.smallTablet({
|
||||
position: static;
|
||||
position: initial;
|
||||
});
|
||||
}
|
||||
|
||||
.menu-header {
|
||||
padding : 0 1em;
|
||||
cursor: pointer;
|
||||
color: @warning;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
|
||||
.menu-list {
|
||||
font-family: @fStandard;
|
||||
position: absolute;
|
||||
padding: 0.5em 1em;
|
||||
box-sizing: border-box;
|
||||
min-width: 100%;
|
||||
overflow-x: hidden;
|
||||
background-color: @bgBlack;
|
||||
font-size: 0.9em;
|
||||
overflow-y: auto;
|
||||
z-index: 0;
|
||||
-webkit-overflow-scrolling: touch;
|
||||
max-height: 500px;
|
||||
|
||||
&::-webkit-scrollbar {
|
||||
width: 0.5em;
|
||||
}
|
||||
|
||||
&::-webkit-scrollbar-track {
|
||||
background-color: transparent;
|
||||
}
|
||||
|
||||
&::-webkit-scrollbar-thumb {
|
||||
background-color: @warning-disabled;
|
||||
}
|
||||
|
||||
input {
|
||||
border: none;
|
||||
background-color: transparent;
|
||||
text-align: right;
|
||||
font-size: 1em;
|
||||
font-family: @fStandard;
|
||||
}
|
||||
|
||||
.smallTablet({
|
||||
max-height: 400px;
|
||||
left: 0;
|
||||
right: 0;
|
||||
border-bottom: 1px solid @bg;
|
||||
});
|
||||
|
||||
|
||||
.tablet({
|
||||
li, a {
|
||||
padding: 0.3em 0;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
.dbl {
|
||||
-webkit-column-count: 2; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 2; /* Firefox */
|
||||
column-count: 2;
|
||||
ul {
|
||||
min-width: 10em;
|
||||
}
|
||||
|
||||
.smallTablet({
|
||||
-webkit-column-count: 3; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 3; /* Firefox */
|
||||
column-count: 3;
|
||||
|
||||
ul {
|
||||
min-width: 20em;
|
||||
}
|
||||
});
|
||||
|
||||
.largePhone({
|
||||
-webkit-column-count: 2; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 2; /* Firefox */
|
||||
column-count: 2;
|
||||
});
|
||||
|
||||
.smallPhone({
|
||||
-webkit-column-count: 1; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 1; /* Firefox */
|
||||
column-count: 1;
|
||||
});
|
||||
}
|
||||
|
||||
.quad {
|
||||
-webkit-column-count: 4; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 4; /* Firefox */
|
||||
column-count: 4;
|
||||
ul {
|
||||
min-width: 10em;
|
||||
}
|
||||
|
||||
.smallTablet({
|
||||
-webkit-column-count: 3; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 3; /* Firefox */
|
||||
column-count: 3;
|
||||
|
||||
ul {
|
||||
min-width: 20em;
|
||||
}
|
||||
});
|
||||
|
||||
.largePhone({
|
||||
-webkit-column-count: 2; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 2; /* Firefox */
|
||||
column-count: 2;
|
||||
});
|
||||
|
||||
.smallPhone({
|
||||
-webkit-column-count: 1; /* Chrome, Safari, Opera */
|
||||
-moz-column-count: 1; /* Firefox */
|
||||
column-count: 1;
|
||||
});
|
||||
}
|
||||
|
||||
ul {
|
||||
display: inline-block;
|
||||
white-space: nowrap;
|
||||
margin: 0 0 0.5em;
|
||||
padding: 0;
|
||||
line-height: 1.3em;
|
||||
}
|
||||
|
||||
li {
|
||||
white-space: normal;
|
||||
list-style: none;
|
||||
margin-left: 1em;
|
||||
line-height: 1.1em;
|
||||
}
|
||||
|
||||
a {
|
||||
vertical-align: middle;
|
||||
color: @warning;
|
||||
text-decoration: none;
|
||||
|
||||
&:visited {
|
||||
color: @warning;
|
||||
}
|
||||
.no-touch &:hover {
|
||||
color: teal;
|
||||
}
|
||||
&.active {
|
||||
color: @primary;
|
||||
}
|
||||
}
|
||||
|
||||
hr {
|
||||
border: none;
|
||||
border-top: 1px solid @disabled;
|
||||
}
|
||||
|
||||
.no-wrap {
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.block {
|
||||
display: block;
|
||||
line-height: 1.5em;
|
||||
}
|
||||
|
||||
.title {
|
||||
font-size: 1.3em;
|
||||
display: inline-block;
|
||||
margin:0px;
|
||||
text-transform: uppercase;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user