diff options
Diffstat (limited to 'src/components/map')
| -rw-r--r-- | src/components/map/MapConstants.js | 3 | ||||
| -rw-r--r-- | src/components/map/MapStage.js | 48 | ||||
| -rw-r--r-- | src/components/map/elements/HoverTile.js | 4 | ||||
| -rw-r--r-- | src/components/map/elements/TilePlusIcon.js | 20 | ||||
| -rw-r--r-- | src/components/map/layers/HoverLayerComponent.js | 23 | ||||
| -rw-r--r-- | src/components/map/layers/ObjectHoverLayerComponent.js | 2 |
6 files changed, 69 insertions, 31 deletions
diff --git a/src/components/map/MapConstants.js b/src/components/map/MapConstants.js index d776901e..f24e450f 100644 --- a/src/components/map/MapConstants.js +++ b/src/components/map/MapConstants.js @@ -15,6 +15,9 @@ export const RACK_FILL_ICON_WIDTH = OBJECT_SIZE_IN_PIXELS / 3; export const RACK_FILL_ICON_OPACITY = 0.8; export const MAP_MOVE_PIXELS_PER_EVENT = 20; +export const MAP_SCALE_PER_EVENT = 1.1; +export const MAP_MIN_SCALE = 0.5; +export const MAP_MAX_SCALE = 1.5; export const MAX_NUM_UNITS_PER_MACHINE = 4; export const DEFAULT_RACK_SLOT_CAPACITY = 42; diff --git a/src/components/map/MapStage.js b/src/components/map/MapStage.js index c4579965..ab2f0839 100644 --- a/src/components/map/MapStage.js +++ b/src/components/map/MapStage.js @@ -8,7 +8,13 @@ import jQuery from "../../util/jquery"; import {NAVBAR_HEIGHT} from "../navigation/Navbar"; import Backdrop from "./elements/Backdrop"; import GridGroup from "./groups/GridGroup"; -import {MAP_MOVE_PIXELS_PER_EVENT, MAP_SIZE_IN_PIXELS} from "./MapConstants"; +import { + MAP_MAX_SCALE, + MAP_MIN_SCALE, + MAP_MOVE_PIXELS_PER_EVENT, + MAP_SCALE_PER_EVENT, + MAP_SIZE_IN_PIXELS +} from "./MapConstants"; class MapStage extends React.Component { state = { @@ -16,6 +22,7 @@ class MapStage extends React.Component { height: 400, x: 0, y: 0, + scale: 1, mouseX: 0, mouseY: 0 }; @@ -26,16 +33,34 @@ class MapStage extends React.Component { componentDidMount() { window.addEventListener("resize", this.updateDimensions.bind(this)); + window.addEventListener("wheel", this.updateScale.bind(this)); } componentWillUnmount() { window.removeEventListener("resize", this.updateDimensions.bind(this)); + window.removeEventListener("wheel", this.updateScale.bind(this)); } updateDimensions() { this.setState({width: jQuery(window).width(), height: jQuery(window).height() - NAVBAR_HEIGHT}); } + updateScale(e) { + e.preventDefault(); + const mousePointsTo = { + x: this.state.mouseX / this.state.scale - this.state.x / this.state.scale, + y: this.state.mouseY / this.state.scale - this.state.y / this.state.scale, + }; + const newScale = e.deltaY < 0 ? this.state.scale * MAP_SCALE_PER_EVENT : this.state.scale / MAP_SCALE_PER_EVENT; + const boundedScale = Math.min(Math.max(MAP_MIN_SCALE, newScale), MAP_MAX_SCALE); + + const newX = -(mousePointsTo.x - this.state.mouseX / boundedScale) * boundedScale; + const newY = -(mousePointsTo.y - this.state.mouseY / boundedScale) * boundedScale; + + this.setPositionWithBoundsCheck(newX, newY); + this.setState({scale: boundedScale}); + } + updateMousePosition() { const mousePos = this.stage.getStage().getPointerPosition(); this.setState({mouseX: mousePos.x, mouseY: mousePos.y}); @@ -61,18 +86,19 @@ class MapStage extends React.Component { } moveWithDelta(deltaX, deltaY) { + this.setPositionWithBoundsCheck(this.state.x + deltaX, this.state.y + deltaY); + } + + setPositionWithBoundsCheck(newX, newY) { + const scaledMapSize = MAP_SIZE_IN_PIXELS * this.state.scale; const updatedPosition = { - x: this.state.x + deltaX > 0 ? 0 : - (this.state.x + deltaX < -MAP_SIZE_IN_PIXELS + this.state.width - ? -MAP_SIZE_IN_PIXELS + this.state.width : this.state.x + deltaX), - y: this.state.y + deltaY > 0 ? 0 : - (this.state.y + deltaY < -MAP_SIZE_IN_PIXELS + this.state.height - ? -MAP_SIZE_IN_PIXELS + this.state.height : this.state.y + deltaY) + x: newX > 0 ? 0 : + (newX < -scaledMapSize + this.state.width ? -scaledMapSize + this.state.width : newX), + y: newY > 0 ? 0 : + (newY < -scaledMapSize + this.state.height ? -scaledMapSize + this.state.height : newY) }; this.setState(updatedPosition); - - return updatedPosition; } render() { @@ -85,7 +111,7 @@ class MapStage extends React.Component { onMouseMove={this.updateMousePosition.bind(this)} > <Layer> - <Group x={this.state.x} y={this.state.y}> + <Group x={this.state.x} y={this.state.y} scaleX={this.state.scale} scaleY={this.state.scale}> <Backdrop/> <DatacenterContainer/> <GridGroup/> @@ -96,12 +122,14 @@ class MapStage extends React.Component { mainGroupY={this.state.y} mouseX={this.state.mouseX} mouseY={this.state.mouseY} + scale={this.state.scale} /> <ObjectHoverLayer mainGroupX={this.state.x} mainGroupY={this.state.y} mouseX={this.state.mouseX} mouseY={this.state.mouseY} + scale={this.state.scale} /> </Stage> </Shortcuts> diff --git a/src/components/map/elements/HoverTile.js b/src/components/map/elements/HoverTile.js index a8bb2085..02d31714 100644 --- a/src/components/map/elements/HoverTile.js +++ b/src/components/map/elements/HoverTile.js @@ -4,10 +4,12 @@ import {Rect} from "react-konva"; import {ROOM_HOVER_INVALID_COLOR, ROOM_HOVER_VALID_COLOR} from "../../../colors/index"; import {TILE_SIZE_IN_PIXELS} from "../MapConstants"; -const HoverTile = ({pixelX, pixelY, isValid, onClick}) => ( +const HoverTile = ({pixelX, pixelY, isValid, scale, onClick}) => ( <Rect x={pixelX} y={pixelY} + scaleX={scale} + scaleY={scale} width={TILE_SIZE_IN_PIXELS} height={TILE_SIZE_IN_PIXELS} fill={isValid ? ROOM_HOVER_VALID_COLOR : ROOM_HOVER_INVALID_COLOR} diff --git a/src/components/map/elements/TilePlusIcon.js b/src/components/map/elements/TilePlusIcon.js index 4c22c23c..3327525c 100644 --- a/src/components/map/elements/TilePlusIcon.js +++ b/src/components/map/elements/TilePlusIcon.js @@ -4,19 +4,19 @@ import {Group, Line} from "react-konva"; import {TILE_PLUS_COLOR} from "../../../colors/index"; import {TILE_PLUS_MARGIN_IN_PIXELS, TILE_PLUS_WIDTH_IN_PIXELS, TILE_SIZE_IN_PIXELS} from "../MapConstants"; -const TilePlusIcon = ({pixelX, pixelY}) => { +const TilePlusIcon = ({pixelX, pixelY, scale}) => { const linePoints = [ [ - pixelX + 0.5 * TILE_SIZE_IN_PIXELS, - pixelY + TILE_PLUS_MARGIN_IN_PIXELS, - pixelX + 0.5 * TILE_SIZE_IN_PIXELS, - pixelY + TILE_SIZE_IN_PIXELS - TILE_PLUS_MARGIN_IN_PIXELS, + pixelX + 0.5 * TILE_SIZE_IN_PIXELS * scale, + pixelY + TILE_PLUS_MARGIN_IN_PIXELS * scale, + pixelX + 0.5 * TILE_SIZE_IN_PIXELS * scale, + pixelY + TILE_SIZE_IN_PIXELS * scale - TILE_PLUS_MARGIN_IN_PIXELS * scale, ], [ - pixelX + TILE_PLUS_MARGIN_IN_PIXELS, - pixelY + 0.5 * TILE_SIZE_IN_PIXELS, - pixelX + TILE_SIZE_IN_PIXELS - TILE_PLUS_MARGIN_IN_PIXELS, - pixelY + 0.5 * TILE_SIZE_IN_PIXELS, + pixelX + TILE_PLUS_MARGIN_IN_PIXELS * scale, + pixelY + 0.5 * TILE_SIZE_IN_PIXELS * scale, + pixelX + TILE_SIZE_IN_PIXELS * scale - TILE_PLUS_MARGIN_IN_PIXELS * scale, + pixelY + 0.5 * TILE_SIZE_IN_PIXELS * scale, ], ]; return ( @@ -27,7 +27,7 @@ const TilePlusIcon = ({pixelX, pixelY}) => { points={points} lineCap="round" stroke={TILE_PLUS_COLOR} - strokeWidth={TILE_PLUS_WIDTH_IN_PIXELS} + strokeWidth={TILE_PLUS_WIDTH_IN_PIXELS * scale} listening={false} /> ))} diff --git a/src/components/map/layers/HoverLayerComponent.js b/src/components/map/layers/HoverLayerComponent.js index 861d2b9a..54a63383 100644 --- a/src/components/map/layers/HoverLayerComponent.js +++ b/src/components/map/layers/HoverLayerComponent.js @@ -10,6 +10,7 @@ class HoverLayerComponent extends React.Component { mouseY: PropTypes.number.isRequired, mainGroupX: PropTypes.number.isRequired, mainGroupY: PropTypes.number.isRequired, + scale: PropTypes.number.isRequired, isEnabled: PropTypes.func.isRequired, onClick: PropTypes.func.isRequired, }; @@ -25,8 +26,8 @@ class HoverLayerComponent extends React.Component { return; } - const positionX = Math.floor((this.props.mouseX - this.props.mainGroupX) / TILE_SIZE_IN_PIXELS); - const positionY = Math.floor((this.props.mouseY - this.props.mainGroupY) / TILE_SIZE_IN_PIXELS); + const positionX = Math.floor((this.props.mouseX - this.props.mainGroupX) / (this.props.scale * TILE_SIZE_IN_PIXELS)); + const positionY = Math.floor((this.props.mouseY - this.props.mainGroupY) / (this.props.scale * TILE_SIZE_IN_PIXELS)); if (positionX !== this.state.positionX || positionY !== this.state.positionY) { this.setState({positionX, positionY, validity: this.props.isValid(positionX, positionY)}); @@ -38,19 +39,23 @@ class HoverLayerComponent extends React.Component { return <Layer/>; } - const positionX = Math.floor((this.props.mouseX - this.props.mainGroupX) / TILE_SIZE_IN_PIXELS); - const positionY = Math.floor((this.props.mouseY - this.props.mainGroupY) / TILE_SIZE_IN_PIXELS); - const pixelX = positionX * TILE_SIZE_IN_PIXELS + this.props.mainGroupX; - const pixelY = positionY * TILE_SIZE_IN_PIXELS + this.props.mainGroupY; + const pixelX = this.props.scale * this.state.positionX * TILE_SIZE_IN_PIXELS + this.props.mainGroupX; + const pixelY = this.props.scale * this.state.positionY * TILE_SIZE_IN_PIXELS + this.props.mainGroupY; return ( <Layer opacity={0.6}> <HoverTile - pixelX={pixelX} pixelY={pixelY} + pixelX={pixelX} + pixelY={pixelY} + scale={this.props.scale} isValid={this.state.validity} - onClick={() => this.state.validity ? this.props.onClick(positionX, positionY) : undefined} + onClick={() => this.state.validity ? + this.props.onClick(this.state.positionX, this.state.positionY) : undefined} /> - {this.props.children ? React.cloneElement(this.props.children, {pixelX, pixelY}) : undefined} + {this.props.children ? + React.cloneElement(this.props.children, {pixelX, pixelY, scale: this.props.scale}) : + undefined + } </Layer> ); } diff --git a/src/components/map/layers/ObjectHoverLayerComponent.js b/src/components/map/layers/ObjectHoverLayerComponent.js index 91757cb3..aa79f8c3 100644 --- a/src/components/map/layers/ObjectHoverLayerComponent.js +++ b/src/components/map/layers/ObjectHoverLayerComponent.js @@ -4,7 +4,7 @@ import HoverLayerComponent from "./HoverLayerComponent"; const ObjectHoverLayerComponent = (props) => ( <HoverLayerComponent {...props}> - <TilePlusIcon/> + <TilePlusIcon {...props}/> </HoverLayerComponent> ); |
