From ba2092b614e2e38d8e29b1704e2013a15b207f7b Mon Sep 17 00:00:00 2001 From: "Blue (Lukas Rieger)" Date: Wed, 4 Mar 2020 20:31:00 +0100 Subject: [PATCH] Introduce shaders to improve rendering, add night and rework the ui --- .../hires/blockmodel/LiquidModelBuilder.java | 5 + .../src/main/webroot/assets/burger.svg | 12 ++ BlueMapCore/src/main/webroot/assets/night.svg | 13 ++ .../src/main/webroot/assets/skybox/down.png | Bin 4533 -> 0 bytes .../src/main/webroot/assets/skybox/east.png | Bin 4605 -> 0 bytes .../src/main/webroot/assets/skybox/north.png | Bin 4605 -> 0 bytes .../src/main/webroot/assets/skybox/south.png | Bin 4605 -> 0 bytes .../src/main/webroot/assets/skybox/up.png | Bin 4536 -> 0 bytes .../src/main/webroot/assets/skybox/west.png | Bin 4605 -> 0 bytes .../src/main/webroot/js/libs/BlueMap.js | 137 +++++------- .../src/main/webroot/js/libs/TileManager.js | 28 ++- .../main/webroot/js/libs/modules/Compass.js | 20 +- .../modules/{MapMenu.js => MapSeletion.js} | 39 ++-- .../libs/modules/{Info.js => MenuButton.js} | 44 ++-- .../main/webroot/js/libs/modules/Position.js | 55 +++-- .../main/webroot/js/libs/modules/Settings.js | 122 ----------- .../js/libs/shaders/HiresFragmentShader.js | 26 ++- .../js/libs/shaders/HiresVertexShader.js | 7 +- .../js/libs/shaders/SkyFragmentShader.js | 42 ++++ .../js/libs/shaders/SkyVertexShader.js | 39 ++++ .../src/main/webroot/js/libs/ui/Button.js | 63 ++++++ .../src/main/webroot/js/libs/ui/Dropdown.js | 130 +++++++++++ .../libs/{modules/Module.js => ui/Element.js} | 24 +-- .../src/main/webroot/js/libs/ui/Label.js | 42 ++++ .../src/main/webroot/js/libs/ui/Menu.js | 71 ++++++ .../src/main/webroot/js/libs/ui/Separator.js | 58 +++++ .../src/main/webroot/js/libs/ui/Slider.js | 86 ++++++++ .../main/webroot/js/libs/ui/ToggleButton.js | 74 +++++++ .../src/main/webroot/js/libs/ui/Toolbar.js | 55 +++++ BlueMapCore/src/main/webroot/js/libs/ui/UI.js | 115 ++++++++++ .../src/main/webroot/style/constants.scss | 14 ++ .../main/webroot/style/modules/alertbox.scss | 67 ------ .../main/webroot/style/modules/compass.scss | 13 -- .../src/main/webroot/style/modules/info.scss | 10 - .../main/webroot/style/modules/mapmenu.scss | 8 - .../main/webroot/style/modules/position.scss | 61 +++--- .../main/webroot/style/modules/settings.scss | 46 ---- BlueMapCore/src/main/webroot/style/style.scss | 204 +++++++----------- .../src/main/webroot/style/ui/button.scss | 38 ++++ .../src/main/webroot/style/ui/dropdown.scss | 76 +++++++ .../src/main/webroot/style/ui/element.scss | 18 ++ .../src/main/webroot/style/ui/label.scss | 5 + .../src/main/webroot/style/ui/menu.scss | 114 ++++++++++ .../src/main/webroot/style/ui/separator.scss | 10 + .../src/main/webroot/style/ui/slider.scss | 23 ++ .../main/webroot/style/ui/togglebutton.scss | 79 +++++++ .../src/main/webroot/style/ui/toolbar.scss | 93 ++++++++ BlueMapCore/src/main/webroot/style/ui/ui.scss | 95 ++++++++ BlueMapCore/webpack.config.js | 3 +- 49 files changed, 1669 insertions(+), 615 deletions(-) create mode 100644 BlueMapCore/src/main/webroot/assets/burger.svg create mode 100644 BlueMapCore/src/main/webroot/assets/night.svg delete mode 100644 BlueMapCore/src/main/webroot/assets/skybox/down.png delete mode 100644 BlueMapCore/src/main/webroot/assets/skybox/east.png delete mode 100644 BlueMapCore/src/main/webroot/assets/skybox/north.png delete mode 100644 BlueMapCore/src/main/webroot/assets/skybox/south.png delete mode 100644 BlueMapCore/src/main/webroot/assets/skybox/up.png delete mode 100644 BlueMapCore/src/main/webroot/assets/skybox/west.png rename BlueMapCore/src/main/webroot/js/libs/modules/{MapMenu.js => MapSeletion.js} (62%) rename BlueMapCore/src/main/webroot/js/libs/modules/{Info.js => MenuButton.js} (61%) delete mode 100644 BlueMapCore/src/main/webroot/js/libs/modules/Settings.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/shaders/SkyFragmentShader.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/shaders/SkyVertexShader.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/Button.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/Dropdown.js rename BlueMapCore/src/main/webroot/js/libs/{modules/Module.js => ui/Element.js} (73%) create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/Label.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/Menu.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/Separator.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/Slider.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/ToggleButton.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/Toolbar.js create mode 100644 BlueMapCore/src/main/webroot/js/libs/ui/UI.js create mode 100644 BlueMapCore/src/main/webroot/style/constants.scss delete mode 100644 BlueMapCore/src/main/webroot/style/modules/alertbox.scss delete mode 100644 BlueMapCore/src/main/webroot/style/modules/compass.scss delete mode 100644 BlueMapCore/src/main/webroot/style/modules/info.scss delete mode 100644 BlueMapCore/src/main/webroot/style/modules/mapmenu.scss delete mode 100644 BlueMapCore/src/main/webroot/style/modules/settings.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/button.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/dropdown.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/element.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/label.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/menu.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/separator.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/slider.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/togglebutton.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/toolbar.scss create mode 100644 BlueMapCore/src/main/webroot/style/ui/ui.scss diff --git a/BlueMapCore/src/main/java/de/bluecolored/bluemap/core/render/hires/blockmodel/LiquidModelBuilder.java b/BlueMapCore/src/main/java/de/bluecolored/bluemap/core/render/hires/blockmodel/LiquidModelBuilder.java index df075fd2..b76d83f3 100644 --- a/BlueMapCore/src/main/java/de/bluecolored/bluemap/core/render/hires/blockmodel/LiquidModelBuilder.java +++ b/BlueMapCore/src/main/java/de/bluecolored/bluemap/core/render/hires/blockmodel/LiquidModelBuilder.java @@ -216,6 +216,11 @@ private void createElementFace(ExtendedModel model, Direction faceDir, Vector3f float blockLight = bl.getBlockLightLevel(); float sunLight = bl.getSunLightLevel(); + if (faceDir == Direction.UP) { + blockLight = block.getBlockLightLevel(); + sunLight = block.getSunLightLevel(); + } + f1.setC1(color); f1.setC2(color); f1.setC3(color); diff --git a/BlueMapCore/src/main/webroot/assets/burger.svg b/BlueMapCore/src/main/webroot/assets/burger.svg new file mode 100644 index 00000000..751681da --- /dev/null +++ b/BlueMapCore/src/main/webroot/assets/burger.svg @@ -0,0 +1,12 @@ + + + + + + + + diff --git a/BlueMapCore/src/main/webroot/assets/night.svg b/BlueMapCore/src/main/webroot/assets/night.svg new file mode 100644 index 00000000..fbdfd59c --- /dev/null +++ b/BlueMapCore/src/main/webroot/assets/night.svg @@ -0,0 +1,13 @@ + + + + + + + + + + diff --git a/BlueMapCore/src/main/webroot/assets/skybox/down.png b/BlueMapCore/src/main/webroot/assets/skybox/down.png deleted file mode 100644 index 77290fc56ce8cc849d1412ddd56bee9bd6984c0f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4533 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 diff --git a/BlueMapCore/src/main/webroot/assets/skybox/east.png b/BlueMapCore/src/main/webroot/assets/skybox/east.png deleted file mode 100644 index f10f641d8ec163b214c566db7dc5a7a4d87beb45..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4605 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 diff --git a/BlueMapCore/src/main/webroot/assets/skybox/north.png b/BlueMapCore/src/main/webroot/assets/skybox/north.png deleted file mode 100644 index f10f641d8ec163b214c566db7dc5a7a4d87beb45..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4605 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 diff --git a/BlueMapCore/src/main/webroot/assets/skybox/south.png b/BlueMapCore/src/main/webroot/assets/skybox/south.png deleted file mode 100644 index f10f641d8ec163b214c566db7dc5a7a4d87beb45..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4605 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 diff --git a/BlueMapCore/src/main/webroot/assets/skybox/up.png b/BlueMapCore/src/main/webroot/assets/skybox/up.png deleted file mode 100644 index db5cb63178ad193b3f9a7c1bf36c316bde605b64..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4536 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 diff --git a/BlueMapCore/src/main/webroot/js/libs/BlueMap.js b/BlueMapCore/src/main/webroot/js/libs/BlueMap.js index d493da1b..cf5c9947 100644 --- a/BlueMapCore/src/main/webroot/js/libs/BlueMap.js +++ b/BlueMapCore/src/main/webroot/js/libs/BlueMap.js @@ -24,31 +24,24 @@ */ import $ from 'jquery'; import { - AmbientLight, BackSide, BufferGeometryLoader, ClampToEdgeWrapping, - CubeGeometry, - DirectionalLight, + SphereGeometry, FileLoader, FrontSide, Mesh, - MeshBasicMaterial, NearestFilter, - NearestMipmapLinearFilter, + NearestMipMapLinearFilter, PerspectiveCamera, Scene, + ShaderMaterial, Texture, - TextureLoader, VertexColors, - WebGLRenderer, ShaderMaterial, + WebGLRenderer, } from 'three'; -import Compass from './modules/Compass.js'; -import Info from './modules/Info.js'; -import MapMenu from './modules/MapMenu.js'; -import Position from './modules/Position.js'; -import Settings from './modules/Settings.js'; +import UI from './ui/UI.js'; import Controls from './Controls.js'; import TileManager from './TileManager.js'; @@ -57,22 +50,29 @@ import HIRES_VERTEX_SHADER from './shaders/HiresVertexShader.js'; import HIRES_FRAGMENT_SHADER from './shaders/HiresFragmentShader.js'; import LOWRES_VERTEX_SHADER from './shaders/LowresVertexShader.js'; import LOWRES_FRAGMENT_SHADER from './shaders/LowresFragmentShader.js'; +import SKY_VERTEX_SHADER from './shaders/SkyVertexShader.js'; +import SKY_FRAGMENT_SHADER from './shaders/SkyFragmentShader.js'; import { stringToImage, pathFromCoords } from './utils.js'; -import SKYBOX_NORTH from '../../assets/skybox/north.png'; -import SKYBOX_SOUTH from '../../assets/skybox/south.png'; -import SKYBOX_EAST from '../../assets/skybox/east.png'; -import SKYBOX_WEST from '../../assets/skybox/west.png'; -import SKYBOX_UP from '../../assets/skybox/up.png'; -import SKYBOX_DOWN from '../../assets/skybox/down.png'; - export default class BlueMap { constructor(element, dataRoot) { - this.element = element; + this.element = $('
').appendTo(element)[0]; this.dataRoot = dataRoot; - this.loadingNoticeElement = $('
loading...
').appendTo($(this.element)); + this.hiresViewDistance = 160; + this.lowresViewDistance = 3200; + this.targetSunLightStrength = 1; + this.sunLightStrength = { + value: this.targetSunLightStrength + }; + this.mobSpawnOverlay = { + value: false + }; + + this.ui = new UI(this); + + this.loadingNoticeElement = $('
loading...
').appendTo($(this.element)); window.onerror = this.onLoadError; this.fileLoader = new FileLoader(); @@ -88,26 +88,18 @@ export default class BlueMap { await this.loadHiresMaterial(); await this.loadLowresMaterial(); - this.changeMap(this.map); + this.changeMap(this.maps[0]); - this.initModules(); + this.ui.load(); this.start(); }).catch(error => { this.onLoadError(error.toString()); - console.error(error); }); } - initModules() { - this.modules = {}; - this.modules.compass = new Compass(this); - this.modules.position = new Position(this); - this.modules.mapMenu = new MapMenu(this); - this.modules.info = new Info(this); - this.modules.settings = new Settings(this); - } - changeMap(map) { + if (this.map === map) return; + if (this.hiresTileManager !== undefined) this.hiresTileManager.close(); if (this.lowresTileManager !== undefined) this.lowresTileManager.close(); @@ -118,8 +110,6 @@ export default class BlueMap { z: this.settings[this.map]["startPos"]["z"] }; - this.targetSunLightStrength = 1; - this.controls.setTileSize(this.settings[this.map]['hires']['tileSize']); this.controls.resetPosition(); this.controls.targetPosition.set(startPos.x, this.controls.targetPosition.y, startPos.z); @@ -127,7 +117,7 @@ export default class BlueMap { this.lowresTileManager = new TileManager( this, - this.settings[this.map]['lowres']['viewDistance'], + this.lowresViewDistance, this.loadLowresTile, this.lowresScene, this.settings[this.map]['lowres']['tileSize'], @@ -136,7 +126,7 @@ export default class BlueMap { this.hiresTileManager = new TileManager( this, - this.settings[this.map]['hires']['viewDistance'], + this.hiresViewDistance, this.loadHiresTile, this.hiresScene, this.settings[this.map]['hires']['tileSize'], @@ -233,9 +223,9 @@ export default class BlueMap { if (this.controls.update()) this.updateFrame = true; //update lighting - let targetLight = 1; - if (this.camera.position.y < 400){ - targetLight = this.targetSunLightStrength; + let targetLight = this.targetSunLightStrength; + if (this.camera.position.y > 400){ + targetLight = Math.max(targetLight, 0.5); } if (Math.abs(targetLight - this.sunLightStrength.value) > 0.01) { this.sunLightStrength.value += (targetLight - this.sunLightStrength.value) * 0.1; @@ -295,7 +285,6 @@ export default class BlueMap { return sort; }); - this.map = this.maps[0]; resolve(); }); }); @@ -305,11 +294,6 @@ export default class BlueMap { this.updateFrame = true; this.quality = 1; - this.targetSunLightStrength = 1; - this.sunLightStrength = { - value: this.targetSunLightStrength - }; - this.renderer = new WebGLRenderer({ alpha: true, antialias: true, @@ -331,40 +315,22 @@ export default class BlueMap { this.lowresScene = new Scene(); this.hiresScene = new Scene(); - this.element.append(this.renderer.domElement); + $(this.renderer.domElement).addClass("map-canvas").appendTo(this.element); this.handleContainerResize(); $(window).resize(this.handleContainerResize); } createSkybox() { - let geometry = new CubeGeometry(10, 10, 10); - let material = [ - new MeshBasicMaterial({ - map: new TextureLoader().load(SKYBOX_SOUTH), - side: BackSide - }), - new MeshBasicMaterial({ - map: new TextureLoader().load(SKYBOX_NORTH), - side: BackSide - }), - new MeshBasicMaterial({ - map: new TextureLoader().load(SKYBOX_UP), - side: BackSide - }), - new MeshBasicMaterial({ - map: new TextureLoader().load(SKYBOX_DOWN), - side: BackSide - }), - new MeshBasicMaterial({ - map: new TextureLoader().load(SKYBOX_EAST), - side: BackSide - }), - new MeshBasicMaterial({ - map: new TextureLoader().load(SKYBOX_WEST), - side: BackSide - }) - ]; + let geometry = new SphereGeometry(10, 10, 10); + let material = new ShaderMaterial({ + uniforms: { + sunlightStrength: this.sunLightStrength + }, + vertexShader: SKY_VERTEX_SHADER, + fragmentShader: SKY_FRAGMENT_SHADER, + side: BackSide + }); return new Mesh(geometry, material); } @@ -385,7 +351,7 @@ export default class BlueMap { texture.anisotropy = 1; texture.generateMipmaps = opaque || transparent; texture.magFilter = NearestFilter; - texture.minFilter = texture.generateMipmaps ? NearestMipmapLinearFilter : NearestFilter; + texture.minFilter = texture.generateMipmaps ? NearestMipMapLinearFilter : NearestFilter; texture.wrapS = ClampToEdgeWrapping; texture.wrapT = ClampToEdgeWrapping; texture.flipY = false; @@ -397,7 +363,8 @@ export default class BlueMap { type: 't', value: texture }, - sunlightStrength: this.sunLightStrength + sunlightStrength: this.sunLightStrength, + mobSpawnOverlay: this.mobSpawnOverlay }; let material = new ShaderMaterial({ @@ -423,12 +390,10 @@ export default class BlueMap { } async loadLowresMaterial() { - let uniforms = { - sunlightStrength: this.sunLightStrength - }; - this.lowresMaterial = new ShaderMaterial({ - uniforms: uniforms, + uniforms: { + sunlightStrength: this.sunLightStrength + }, vertexShader: LOWRES_VERTEX_SHADER, fragmentShader: LOWRES_FRAGMENT_SHADER, transparent: false, @@ -486,7 +451,7 @@ export default class BlueMap { this.loadingNoticeElement.remove(); this.toggleAlert(undefined, ` -
+

Error

${message}

@@ -496,14 +461,14 @@ export default class BlueMap { // ###### UI ###### toggleAlert(id, content) { - let alertBox = $('#alert-box'); + let alertBox = $(this.element).find('.alert-box'); if (alertBox.length === 0){ - alertBox = $('
').appendTo(this.element); + alertBox = $('
').appendTo(this.ui.hud); } let displayAlert = () => { - let alert = $(``).appendTo(alertBox); - alert.find('.alert-close-button').click(() => { + let alert = $(``).appendTo(alertBox); + alert.find('.close-button').click(() => { alert.stop().fadeOut(200, () => alert.remove()); }); alert.stop().fadeIn(200); diff --git a/BlueMapCore/src/main/webroot/js/libs/TileManager.js b/BlueMapCore/src/main/webroot/js/libs/TileManager.js index 37783879..ac659e9f 100644 --- a/BlueMapCore/src/main/webroot/js/libs/TileManager.js +++ b/BlueMapCore/src/main/webroot/js/libs/TileManager.js @@ -32,10 +32,10 @@ import { hashTile } from './utils.js'; export default class TileManager { constructor(blueMap, viewDistance, tileLoader, scene, tileSize, position) { this.blueMap = blueMap; - this.viewDistance = viewDistance; + this.tileSize = new Vector2(tileSize.x, tileSize.z); + this.setViewDistance(viewDistance); this.tileLoader = tileLoader; this.scene = scene; - this.tileSize = new Vector2(tileSize.x, tileSize.z); this.tile = new Vector2(0, 0); this.tile.set(position.x, position.z).divide(this.tileSize).floor(); @@ -48,6 +48,11 @@ export default class TileManager { this.tiles = {}; } + setViewDistance(viewDistance){ + this.viewDistanceX = viewDistance / this.tileSize.x; + this.viewDistanceZ = viewDistance / this.tileSize.y; + } + setPosition(center) { this.tile.set(center.x, center.z).divide(this.tileSize).floor(); @@ -75,16 +80,19 @@ export default class TileManager { let tile = this.tiles[keys[i]]; - let vd = this.viewDistance; + let vdx = this.viewDistanceX; + let vdz = this.viewDistanceZ; if ( - tile.x + vd < this.tile.x || - tile.x - vd > this.tile.x || - tile.z + vd < this.tile.y || - tile.z - vd > this.tile.y + tile.x + vdx < this.tile.x || + tile.x - vdx > this.tile.x || + tile.z + vdz < this.tile.y || + tile.z - vdz > this.tile.y ) { tile.disposeModel(); delete this.tiles[keys[i]]; + + this.blueMap.updateFrame = true; } } } @@ -98,6 +106,8 @@ export default class TileManager { tile.disposeModel(); delete this.tiles[keys[i]]; } + + this.blueMap.updateFrame = true; } close() { @@ -122,7 +132,7 @@ export default class TileManager { let d = 1; let m = 1; - while (m < this.viewDistance * 2) { + while (m < Math.max(this.viewDistanceX, this.viewDistanceZ) * 2 + 1) { while (2 * x * d < m) { if (this.tryLoadTile(this.tile.x + x, this.tile.y + z)) return true; x = x + d; @@ -140,6 +150,8 @@ export default class TileManager { tryLoadTile(x, z) { if (this.closed) return false; + if (Math.abs(x - this.tile.x) > this.viewDistanceX) return false; + if (Math.abs(z - this.tile.z) > this.viewDistanceZ) return false; let tileHash = hashTile(x, z); diff --git a/BlueMapCore/src/main/webroot/js/libs/modules/Compass.js b/BlueMapCore/src/main/webroot/js/libs/modules/Compass.js index 02b3e099..2d3261fa 100644 --- a/BlueMapCore/src/main/webroot/js/libs/modules/Compass.js +++ b/BlueMapCore/src/main/webroot/js/libs/modules/Compass.js @@ -24,24 +24,28 @@ */ import $ from 'jquery'; -import { getTopLeftElement } from './Module.js'; +import Button from '../ui/Button.js'; import COMPASS from '../../../assets/compass.svg'; -export default class Compass { +export default class Compass extends Button { constructor(blueMap) { + super(undefined, undefined, COMPASS); this.blueMap = blueMap; - $('#bluemap-compass').remove(); - this.element = $(`
`).appendTo(getTopLeftElement(blueMap)); - this.needle = $('#bluemap-compass-needle'); - $(document).on('bluemap-update-frame', this.onBlueMapUpdateFrame); - $(this.element).click(this.onClick); + } + + createElement(){ + let element = super.createElement(); + element.click(this.onClick); + return element; } onBlueMapUpdateFrame = () => { - this.needle.css('transform', `rotate(${this.blueMap.controls.direction}rad)`); + this.elements.forEach(element => { + element.find("img").css('transform', `rotate(${this.blueMap.controls.direction}rad)`); + }); }; onClick = () => { diff --git a/BlueMapCore/src/main/webroot/js/libs/modules/MapMenu.js b/BlueMapCore/src/main/webroot/js/libs/modules/MapSeletion.js similarity index 62% rename from BlueMapCore/src/main/webroot/js/libs/modules/MapMenu.js rename to BlueMapCore/src/main/webroot/js/libs/modules/MapSeletion.js index 9dc2864b..a3c69c7f 100644 --- a/BlueMapCore/src/main/webroot/js/libs/modules/MapMenu.js +++ b/BlueMapCore/src/main/webroot/js/libs/modules/MapSeletion.js @@ -24,40 +24,39 @@ */ import $ from 'jquery'; -import { getTopLeftElement } from './Module.js'; +import Dropdown from "../ui/Dropdown"; -export default class MapMenu { - constructor(blueMap) { - this.bluemap = blueMap; +export default class MapSelection extends Dropdown { + constructor(bluemap) { + super(undefined); + super.onChange = this.onChangeMap; + + this.bluemap = bluemap; + + //add maps const maps = this.bluemap.settings; - - $('#bluemap-mapmenu').remove(); - this.element = $(``).appendTo(getTopLeftElement(blueMap)); - - const dropdown = $('').appendTo(this.element); - this.maplist = $('
    ').appendTo(dropdown); - for (let mapId in maps) { if (!maps.hasOwnProperty(mapId)) continue; const map = maps[mapId]; if (!map.enabled) continue; - $(`
  • ${map.name}
  • `).appendTo(this.maplist); + this.addOption(mapId, map.name); } - this.maplist.find('li[map=' + this.bluemap.map + ']').hide(); - this.maplist.find('li[map]').click(this.onMapClick); $(document).on('bluemap-map-change', this.onBlueMapMapChange); } - onMapClick = event => { - const map = $(event.target).attr('map'); - this.bluemap.changeMap(map); + createElement() { + let element = super.createElement(); + element.addClass("map-selection"); + return element; + } + + onChangeMap = value => { + this.bluemap.changeMap(value); }; onBlueMapMapChange = () => { - this.maplist.find('li').show(); - this.maplist.find('li[map=' + this.bluemap.map + ']').hide(); - this.element.find('.selection').html(this.bluemap.settings[this.bluemap.map].name); + this.select(this.bluemap.map); }; } diff --git a/BlueMapCore/src/main/webroot/js/libs/modules/Info.js b/BlueMapCore/src/main/webroot/js/libs/modules/MenuButton.js similarity index 61% rename from BlueMapCore/src/main/webroot/js/libs/modules/Info.js rename to BlueMapCore/src/main/webroot/js/libs/modules/MenuButton.js index ae3fb6b1..23dbaa8f 100644 --- a/BlueMapCore/src/main/webroot/js/libs/modules/Info.js +++ b/BlueMapCore/src/main/webroot/js/libs/modules/MenuButton.js @@ -24,26 +24,34 @@ */ import $ from 'jquery'; -import { getTopRightElement } from './Module.js'; +import ToggleButton from '../ui/ToggleButton.js'; -export default class Info { - constructor(blueMap) { - this.blueMap = blueMap; - const parent = getTopRightElement(blueMap); - $('#bluemap-info').remove(); - this.elementInfo = $('
    ').appendTo(parent); - this.elementInfo.click(this.onClick); +import BURGER from '../../../assets/burger.svg'; + +export default class MenuButton extends ToggleButton { + constructor(menu) { + super(undefined, false, undefined, BURGER); + this.menu = menu; + + this.menu.element.on('menu-close menu-open', this.updateMenuState); } - onClick = () => { - this.blueMap.toggleAlert('bluemap-info', - '

    Info

    ' + - 'Visit BlueMap on GitHub!
    ' + - 'BlueMap works best with Chrome.
    ' + - '

    Controls

    ' + - 'Leftclick-drag with your mouse or use the arrow-keys to navigate.
    ' + - 'Rightclick-drag with your mouse to rotate your view.
    ' + - 'Scroll to zoom.
    ' - ); + createElement(){ + let element = super.createElement(); + element.click(this.onMenuClick); + return element; + } + + updateMenuState = () => { + this.selected = this.menu.isOpen(); + this.update(); + }; + + onMenuClick = () => { + if (this.selected){ + this.menu.open(); + } else { + this.menu.close(); + } }; } diff --git a/BlueMapCore/src/main/webroot/js/libs/modules/Position.js b/BlueMapCore/src/main/webroot/js/libs/modules/Position.js index 7f279755..232e6c8a 100644 --- a/BlueMapCore/src/main/webroot/js/libs/modules/Position.js +++ b/BlueMapCore/src/main/webroot/js/libs/modules/Position.js @@ -24,38 +24,34 @@ */ import $ from 'jquery'; -import { getTopLeftElement } from './Module.js'; +import Element from "../ui/Element"; -export default class Position { - constructor(blueMap) { +export default class Position extends Element { + constructor(blueMap, axis) { + super(); this.blueMap = blueMap; + this.axis = axis; - $('.bluemap-position').remove(); - this.elements = [ - this.createPositionElement('x'), - null,//this.elementY = this.createPositionElement('y'); - this.createPositionElement('z'), - ]; - - $(document).on('bluemap-update-frame', this.onBlueMapUpdateFrame); + $(document).on('bluemap-update-frame', this.update); } - /** Creates the position display */ - createPositionElement(type) { - const parent = getTopLeftElement(this.blueMap); - const element = $(`
    `) - .appendTo(parent) - .children() - .first(); - element.on('input', this.onInput(type)); - element.on('keydown', this.onKeyDown); + createElement(){ + let element = super.createElement(); + + element.addClass("position"); + element.attr("data-axis", this.axis); + let inputElement = $('').appendTo(element); + inputElement.on('input', this.onInput); + inputElement.on('keydown', this.onKeyDown); + return element; } - onInput = type => event => { + onInput = event => { const value = Number(event.target.value); if (!isNaN(value)) { - this.blueMap.controls.targetPosition[type] = value; + this.blueMap.controls.targetPosition[this.axis] = value; + this.update(); } }; @@ -63,14 +59,11 @@ export default class Position { event.stopPropagation(); }; - onBlueMapUpdateFrame = () => { - const { x, y, z } = this.blueMap.controls.targetPosition; - const values = [ z, y, x ]; - for (let element of this.elements) { - const value = Math.floor(values.pop()); - if (element) { - element.val(value); - } - } + update = () => { + const val = Math.floor(this.blueMap.controls.targetPosition[this.axis]); + + this.elements.forEach(element => { + element.find("input").val(val); + }); }; } diff --git a/BlueMapCore/src/main/webroot/js/libs/modules/Settings.js b/BlueMapCore/src/main/webroot/js/libs/modules/Settings.js deleted file mode 100644 index c2c73c42..00000000 --- a/BlueMapCore/src/main/webroot/js/libs/modules/Settings.js +++ /dev/null @@ -1,122 +0,0 @@ -/* - * This file is part of BlueMap, licensed under the MIT License (MIT). - * - * Copyright (c) Blue (Lukas Rieger) - * Copyright (c) contributors - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - */ -import $ from 'jquery'; -import { Math as Math3 } from 'three'; - -import { getTopRightElement } from './Module.js'; - -import GEAR from '../../../assets/gear.svg'; - -export default class Settings { - constructor(blueMap) { - this.blueMap = blueMap; - const parent = getTopRightElement(blueMap); - - $('#bluemap-settings').remove(); - this.elementMenu = $('').appendTo(parent); - this.elementSettings = $(`
    `).appendTo(parent); - this.elementSettings.click(this.onSettingsClick); - - /* Quality */ - - this.elementQuality = $( - '' - ).prependTo(this.elementMenu); - - this.elementQuality.find('li[data-quality]').click(this.onQualityClick); - this.elementRenderDistance = $('').prependTo(this.elementMenu); - - this.init(); - - $(document).on('bluemap-map-change', this.init); - } - - init = () => { - this.defaultHighRes = this.blueMap.hiresTileManager.viewDistance; - this.defaultLowRes = this.blueMap.lowresTileManager.viewDistance; - - this.elementRenderDistance.html( - 'View Distance: ' + this.blueMap.hiresTileManager.viewDistance + '' + - '' - ); - - this.slider = this.elementRenderDistance.find('input'); - this.slider.on('change input', this.onViewDistanceSlider); - }; - - onViewDistanceSlider = () => { - this.blueMap.hiresTileManager.viewDistance = this.pctToRenderDistance(parseFloat(this.slider.val()), this.defaultHighRes); - this.blueMap.lowresTileManager.viewDistance = this.pctToRenderDistance(parseFloat(this.slider.val()), this.defaultLowRes); - this.elementRenderDistance.find('.selection > span').html(Math.round(this.blueMap.hiresTileManager.viewDistance * 10) / 10); - - this.blueMap.lowresTileManager.update(); - this.blueMap.hiresTileManager.update(); - }; - - onQualityClick = (event) => { - const target = event.target - const desc = $(target).html(); - this.blueMap.quality = parseFloat($(target).attr('data-quality')); - - this.elementQuality.find('li').show(); - this.elementQuality.find(`li[data-quality="${this.blueMap.quality}"]`).hide(); - - this.elementQuality.find('.selection > span').html(desc); - - this.blueMap.handleContainerResize(); - }; - - onSettingsClick = () => { - if (this.elementMenu.css('display') === 'none'){ - this.elementSettings.addClass('active'); - } else { - this.elementSettings.removeClass('active'); - } - - this.elementMenu.animate({ - width: 'toggle' - }, 200); - }; - - pctToRenderDistance(value, defaultValue) { - let max = defaultValue * 5; - if (max > 20) max = 20; - - return Math3.mapLinear(value, 0, 100, 1, max); - } - - renderDistanceToPct(value, defaultValue) { - let max = defaultValue * 5; - if (max > 20) max = 20; - - return Math3.mapLinear(value, 1, max, 0, 100); - } -} diff --git a/BlueMapCore/src/main/webroot/js/libs/shaders/HiresFragmentShader.js b/BlueMapCore/src/main/webroot/js/libs/shaders/HiresFragmentShader.js index 2a6033b0..d4838c40 100644 --- a/BlueMapCore/src/main/webroot/js/libs/shaders/HiresFragmentShader.js +++ b/BlueMapCore/src/main/webroot/js/libs/shaders/HiresFragmentShader.js @@ -26,8 +26,10 @@ const HIRES_FRAGMENT_SHADER = ` uniform sampler2D texture; uniform float sunlightStrength; +uniform bool mobSpawnOverlay; varying vec3 vPosition; +varying vec3 vWorldPosition; varying vec3 vNormal; varying vec2 vUv; varying vec3 vColor; @@ -35,12 +37,34 @@ varying float vAo; varying float vSunlight; varying float vBlocklight; +vec4 lerp(vec4 v1, vec4 v2, float amount){ + return v1 * (1.0 - amount) + v2 * amount; +} +vec3 lerp(vec3 v1, vec3 v2, float amount){ + return v1 * (1.0 - amount) + v2 * amount; +} + +bool mobSpawnColor() { + if (vBlocklight < 7.1){ + float cross1 = vUv.x - vUv.y; + float cross2 = vUv.x - (1.0 - vUv.y); + return cross1 < 0.05 && cross1 > -0.05 || cross2 < 0.05 && cross2 > -0.05; + } + + return false; +} + void main() { vec4 color = texture2D(texture, vUv); if (color.a == 0.0) discard; //apply vertex-color color.rgb *= vColor; + + //mob spawn overlay + if (mobSpawnOverlay && mobSpawnColor()){ + color.rgb = lerp(vec3(1.0, 0.0, 0.0), color.rgb, 0.25); + } //apply ao color.rgb *= vAo; @@ -48,7 +72,7 @@ void main() { //apply light float light = max(vSunlight * sunlightStrength, vBlocklight); color.rgb *= light / 15.0; - + gl_FragColor = color; } `; diff --git a/BlueMapCore/src/main/webroot/js/libs/shaders/HiresVertexShader.js b/BlueMapCore/src/main/webroot/js/libs/shaders/HiresVertexShader.js index 033ede98..b6fd3f41 100644 --- a/BlueMapCore/src/main/webroot/js/libs/shaders/HiresVertexShader.js +++ b/BlueMapCore/src/main/webroot/js/libs/shaders/HiresVertexShader.js @@ -29,6 +29,7 @@ attribute float sunlight; attribute float blocklight; varying vec3 vPosition; +varying vec3 vWorldPosition; varying vec3 vNormal; varying vec2 vUv; varying vec3 vColor; @@ -38,6 +39,7 @@ varying float vBlocklight; void main() { vPosition = position; + vWorldPosition = (vec4(position, 1) * modelMatrix).xyz; vNormal = normal; vUv = uv; vColor = color; @@ -47,8 +49,9 @@ void main() { gl_Position = projectionMatrix * - modelViewMatrix * - vec4(position, 1); + viewMatrix * + modelMatrix * + vec4(position, 1); } `; diff --git a/BlueMapCore/src/main/webroot/js/libs/shaders/SkyFragmentShader.js b/BlueMapCore/src/main/webroot/js/libs/shaders/SkyFragmentShader.js new file mode 100644 index 00000000..ddd41856 --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/shaders/SkyFragmentShader.js @@ -0,0 +1,42 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the 'Software'), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +const SKY_FRAGMENT_SHADER = ` +uniform float sunlightStrength; + +varying vec3 vPosition; + +void main() { + vec4 dayColor = vec4(0.49, 0.67, 1.0, 1.0); + vec4 nightColor = vec4(0.0, 0.02, 0.05, 1.0); + + vec4 color = dayColor * sunlightStrength + nightColor * (1.0 - sunlightStrength); + color.rgb *= (clamp(vPosition.y, -0.02, 0.02) + 0.02) * 25.0; + + gl_FragColor = color; +} +`; + +export default SKY_FRAGMENT_SHADER; \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/shaders/SkyVertexShader.js b/BlueMapCore/src/main/webroot/js/libs/shaders/SkyVertexShader.js new file mode 100644 index 00000000..f6a279ea --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/shaders/SkyVertexShader.js @@ -0,0 +1,39 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the 'Software'), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +const SKY_VERTEX_SHADER = ` +varying vec3 vPosition; + +void main() { + vPosition = position; + + gl_Position = + projectionMatrix * + modelViewMatrix * + vec4(position, 1); +} +`; + +export default SKY_VERTEX_SHADER; \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/Button.js b/BlueMapCore/src/main/webroot/js/libs/ui/Button.js new file mode 100644 index 00000000..4aa51e6a --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Button.js @@ -0,0 +1,63 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import $ from 'jquery'; + +import Element from './Element.js'; + +export default class Button extends Element { + + constructor(label, onClick, icon){ + super(); + + this.label = label; + this.onClickListener = onClick; + this.icon = icon; + } + + createElement() { + let element = super.createElement(); + + element.addClass("button"); + element.click(this.onClickEvent); + + if (this.label !== undefined) { + $(`
    ${this.label}
    `).appendTo(element); + } + + if (this.icon !== undefined){ + element.addClass("icon"); + $(``).appendTo(element); + } + + return element; + } + + onClickEvent = () => { + if (this.onClickListener !== undefined && this.onClickListener !== null) { + this.onClickListener(this); + } + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/Dropdown.js b/BlueMapCore/src/main/webroot/js/libs/ui/Dropdown.js new file mode 100644 index 00000000..af57749b --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Dropdown.js @@ -0,0 +1,130 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import $ from 'jquery'; + +import Element from './Element.js'; + +export default class Dropdown extends Element { + + constructor(onChange, minWidth) { + super(); + this.minWidth = minWidth; + this.value = null; + this.options = []; + this.onChange = onChange; + + $(window).on('click', this.closeAll); + } + + addOption(value, label, select) { + this.options.push({ + value: value, + label: label, + select: select + }); + + if (this.value === null || select){ + this.select(value); + } + } + + createElement(){ + let element = super.createElement(); + + element.addClass("dropdown"); + let headerElement = $('
    ').appendTo(element); + let selectElement = $('').appendTo(element); + + headerElement.click(this.toggleEvent(element)); + + if (this.minWidth !== undefined){ + this.element.addClass("sized"); + this.element.css("min-width", this.minWidth); + } + + this.options.forEach(option => { + let optionElement = $(`
    ${option.label}
    `).appendTo(selectElement); + optionElement.on('click', this.selectButtonEvent(option.value, optionElement)); + + if (this.value === option.value){ + optionElement.addClass('selected'); + headerElement.html(''); + headerElement.append(optionElement.clone().off()); + } + }); + + return element; + } + + toggleEvent = element => event => { + let select = element.find(".select"); + let open = select.css("display") !== "none"; + + this.closeAll(); + + if (!open) { + select.stop(true).slideDown(200); + element.addClass("open"); + event.stopPropagation(); + } + }; + + closeAll = () => { + this.elements.forEach(element => { + element.removeClass("open"); + element.find(".select:not(:hidden)").stop(true).slideUp(200); + }); + }; + + select = value => { + this.value = value; + + this.elements.forEach(element => { + let selectElement = element.find(".select"); + selectElement.find('.selected').removeClass('selected'); + + let option = selectElement.find(`.option[data-value='${value}']`); + option.addClass('selected'); + + let headerElement = element.find(".header"); + headerElement.html(''); + headerElement.append(option.clone().off()); + }); + }; + + selectButtonEvent = (value, option) => event => { + this.select(value); + + //close + option.parents(".select").slideUp(200); + + if (event !== undefined) event.stopPropagation(); + + if (this.onChange !== undefined && this.onChange !== null){ + this.onChange(this.value, this); + } + }; + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/modules/Module.js b/BlueMapCore/src/main/webroot/js/libs/ui/Element.js similarity index 73% rename from BlueMapCore/src/main/webroot/js/libs/modules/Module.js rename to BlueMapCore/src/main/webroot/js/libs/ui/Element.js index 36c0fd0e..3bab6f46 100644 --- a/BlueMapCore/src/main/webroot/js/libs/modules/Module.js +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Element.js @@ -24,24 +24,16 @@ */ import $ from 'jquery'; -// ###### Modules ###### +export default class Element { -export const getTopRightElement = blueMap => { - let element = $('#bluemap-topright'); - - if (element.length === 0){ - element = $('
    ').appendTo(blueMap.element); + constructor() { + this.elements = []; } - return element; -}; - -export const getTopLeftElement = blueMap => { - let element = $('#bluemap-topleft'); - - if (element.length === 0){ - element = $('
    ').appendTo(blueMap.element); + createElement() { + let newElement = $('
    '); + this.elements.push(newElement); + return newElement; } - return element; -}; +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/Label.js b/BlueMapCore/src/main/webroot/js/libs/ui/Label.js new file mode 100644 index 00000000..33dcd9b2 --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Label.js @@ -0,0 +1,42 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +import Element from './Element.js'; + +export default class Label extends Element { + + constructor(label){ + super(); + this.label = label; + } + + createElement() { + let element = super.createElement(); + element.addClass("label"); + element.html(this.label); + return element; + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/Menu.js b/BlueMapCore/src/main/webroot/js/libs/ui/Menu.js new file mode 100644 index 00000000..a1d00f0f --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Menu.js @@ -0,0 +1,71 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import $ from 'jquery'; + +import Element from './Element.js'; + +export default class Menu { + + constructor(){ + this.element = $(''); + this.content = $('
    ').appendTo(this.element); + this.closeButton = $('
    ').appendTo(this.element); + + this.children = []; + + this.closeButton.click(this.close); + } + + addElement(element){ + this.children.push(element); + } + + update() { + this.content.html(""); + this.children.forEach(child => { + this.content.append(child.createElement()); + }); + } + + isOpen = () => { + return !this.element.hasClass('closed'); + }; + + toggleOpen = () => { + this.element.toggleClass('closed'); + }; + + open = () => { + + this.element.removeClass('closed'); + this.element.trigger('menu-open'); + }; + + close = () => { + this.element.addClass('closed'); + this.element.trigger('menu-close'); + }; + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/Separator.js b/BlueMapCore/src/main/webroot/js/libs/ui/Separator.js new file mode 100644 index 00000000..96a4ac76 --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Separator.js @@ -0,0 +1,58 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import Element from './Element.js'; + +export default class Separator extends Element { + + constructor(greedy = false){ + super(); + this.greedy = greedy; + } + + createElement() { + let element = super.createElement(); + + element.addClass("separator"); + if (this.greedy) element.addClass("greedy"); + + return element; + } + + isGreedy(){ + return this.greedy; + } + + setGreedy(greedy){ + this.greedy = greedy; + this.elements.forEach(element => { + if (this.greedy) { + element.addClass("greedy"); + } else { + element.removeClass("greedy"); + } + }); + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/Slider.js b/BlueMapCore/src/main/webroot/js/libs/ui/Slider.js new file mode 100644 index 00000000..cf3b5bf1 --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Slider.js @@ -0,0 +1,86 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import $ from 'jquery'; + +import Element from './Element.js'; + +export default class Slider extends Element { + + constructor(min = 0, max = 1, step = 0.01, value, onChange, minWidth){ + super(); + this.min = min; + this.max = max; + this.step = step; + + if (value === undefined) value = min; + this.value = value; + + this.onChangeListener = onChange; + this.minWidth = minWidth; + } + + createElement() { + let element = super.createElement(); + element.addClass("slider"); + + if (this.minWidth !== undefined){ + element.addClass("sized"); + element.css("min-width", this.minWidth); + } + + let slider = $(``).appendTo(element); + slider.on('input change', this.onChangeEvent(slider)); + $(`
    -
    `).appendTo(element); + + this.update(); + + return element; + } + + getValue() { + return this.value; + } + + update(){ + this.elements.forEach(element => { + let label = element.find(".label"); + let slider = element.find("input"); + + slider.val(this.value); + label.html(Math.round(this.value * 100) / 100); + }); + } + + onChangeEvent = slider => () => { + this.value = slider.val(); + + this.update(); + + if (this.onChangeListener !== undefined && this.onChangeListener !== null) { + this.onChangeListener(this); + } + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/ToggleButton.js b/BlueMapCore/src/main/webroot/js/libs/ui/ToggleButton.js new file mode 100644 index 00000000..dca176ac --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/ToggleButton.js @@ -0,0 +1,74 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import $ from 'jquery'; + +import Button from './Button.js'; + +export default class ToggleButton extends Button { + + constructor(label, selected, onChange, icon){ + super(label, undefined, icon); + this.selected = selected; + this.onChangeListener = onChange; + } + + createElement() { + let element = super.createElement(); + + element.addClass("toggle-button"); + if (this.selected) element.addClass("selected"); + $('
    ').appendTo(element); + element.click(this.onClick); + + return element; + } + + isSelected(){ + return this.selected; + } + + toggle(){ + this.selected = !this.selected; + this.update(); + } + + update(){ + this.elements.forEach(element => { + if (this.selected) + element.addClass("selected"); + else + element.removeClass("selected"); + }); + } + + onClick = () => { + this.toggle(); + + if (this.onChangeListener !== undefined && this.onChangeListener !== null){ + this.onChangeListener(this); + } + }; + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/Toolbar.js b/BlueMapCore/src/main/webroot/js/libs/ui/Toolbar.js new file mode 100644 index 00000000..4ef1b4cb --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/Toolbar.js @@ -0,0 +1,55 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import $ from 'jquery'; + +import Element from './Element.js'; + +export default class Toolbar { + + constructor(){ + this.element = $('
    '); + + this.children = []; + } + + addElement(element, hideOnMobile = false){ + this.children.push({ + element: element, + hideOnMobile: hideOnMobile + }); + } + + update() { + this.element.html(""); + this.children.forEach(child => { + let element = child.element.createElement(); + element.appendTo(this.element); + if (child.hideOnMobile){ + element.addClass("mobile-hide"); + } + }); + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/js/libs/ui/UI.js b/BlueMapCore/src/main/webroot/js/libs/ui/UI.js new file mode 100644 index 00000000..0e5d5528 --- /dev/null +++ b/BlueMapCore/src/main/webroot/js/libs/ui/UI.js @@ -0,0 +1,115 @@ +/* + * This file is part of BlueMap, licensed under the MIT License (MIT). + * + * Copyright (c) Blue (Lukas Rieger) + * Copyright (c) contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ +import $ from 'jquery'; + +import Toolbar from './Toolbar.js'; +import Menu from './Menu.js'; +import Dropdown from "./Dropdown"; +import Separator from "./Separator"; +import Label from "./Label"; +import MenuButton from '../modules/MenuButton.js'; +import Compass from "../modules/Compass"; +import Position from "../modules/Position"; +import Button from "./Button"; +import Slider from "./Slider"; +import ToggleButton from "./ToggleButton"; +import MapSelection from "../modules/MapSeletion"; + +import NIGHT from '../../../assets/night.svg'; + +export default class UI { + + constructor(blueMap) { + this.blueMap = blueMap; + this.element = $('
    ').appendTo(this.blueMap.element); + + this.menu = new Menu(); + this.menu.element.appendTo(this.element); + + this.hud = $('
    ').appendTo(this.element); + + this.toolbar = new Toolbar(); + this.toolbar.element.appendTo(this.hud); + } + + load() { + //elements + let menuButton = new MenuButton(this.menu); + let mapSelect = new MapSelection(this.blueMap); + let nightButton = new ToggleButton("night", blueMap.targetSunLightStrength < 1, button => { + this.blueMap.targetSunLightStrength = button.isSelected() ? 0.1 : 1; + }, NIGHT); + let posX = new Position(this.blueMap, 'x'); + let posZ = new Position(this.blueMap, 'z'); + let compass = new Compass(this.blueMap); + + let mobSpawnOverlay = new ToggleButton("mob-spawnable overlay", blueMap.mobSpawnOverlay.value, button => { + this.blueMap.mobSpawnOverlay.value = button.isSelected(); + this.blueMap.updateFrame = true; + }); + + let quality = new Dropdown(value => { + this.blueMap.quality = parseFloat(value); + this.blueMap.handleContainerResize(); + }); + quality.addOption("2", "high"); + quality.addOption("1", "normal", true); + quality.addOption("0.5", "low"); + let hiresSlider = new Slider(32, 480, 1, this.blueMap.hiresViewDistance, v => { + this.blueMap.hiresViewDistance = v.getValue(); + this.blueMap.hiresTileManager.setViewDistance(this.blueMap.hiresViewDistance); + this.blueMap.hiresTileManager.update(); + }); + let lowresSlider = new Slider(480, 6400, 1, this.blueMap.lowresViewDistance, v => { + this.blueMap.lowresViewDistance = v.getValue(); + this.blueMap.lowresTileManager.setViewDistance(this.blueMap.lowresViewDistance); + this.blueMap.lowresTileManager.update(); + }); + + //toolbar + this.toolbar.addElement(menuButton); + this.toolbar.addElement(mapSelect); + this.toolbar.addElement(new Separator(), true); + this.toolbar.addElement(nightButton, true); + this.toolbar.addElement(new Separator(true)); + this.toolbar.addElement(posX); + this.toolbar.addElement(posZ); + this.toolbar.addElement(compass); + this.toolbar.update(); + + //menu + this.menu.addElement(nightButton); + this.menu.addElement(mobSpawnOverlay); + this.menu.addElement(new Separator()); + this.menu.addElement(new Label('render quality:')); + this.menu.addElement(quality); + this.menu.addElement(new Label('hires render-distance (blocks):')); + this.menu.addElement(hiresSlider); + this.menu.addElement(new Label('lowres render-distance (blocks):')); + this.menu.addElement(lowresSlider); + this.menu.update(); + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/constants.scss b/BlueMapCore/src/main/webroot/style/constants.scss new file mode 100644 index 00000000..d7e3ae11 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/constants.scss @@ -0,0 +1,14 @@ +// colors +$normal_fg: #333; +$normal_bg: #fff; + +$super_light_fg: #484848; +$super_light_bg: #ddd; + +$light_fg: #666; +$light_bg: #aaa; + +// breakpoints +$super-small-max: 500px; +$small-max: 800px; +$middle-max: 1200px; \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/modules/alertbox.scss b/BlueMapCore/src/main/webroot/style/modules/alertbox.scss deleted file mode 100644 index 201566e3..00000000 --- a/BlueMapCore/src/main/webroot/style/modules/alertbox.scss +++ /dev/null @@ -1,67 +0,0 @@ -#alert-box { - position: absolute; - top: 0; - left: 0; - width: 100%; - height: 100%; - display: flex; - align-content: center; - justify-content: center; - flex-wrap: wrap; - flex-direction: column; - pointer-events: none; - - h1 { - font-size: 1.4rem; - font-weight: bold; - - margin: 0; - padding: 15px; - text-align: center; - } - - h2 { - font-size: 1.2rem; - font-weight: bold; - - margin: 0; - padding: 15px 0 5px 0; - text-align: left; - } - - a { - color: #333333; - text-decoration: underline; - - &:hover { - color: #888888; - } - } - - .alert { - position: relative; - pointer-events: all; - margin: 10px; - padding: 10px; - - .alert-close-button { - margin: -10px -10px 0px 0px; - padding: 0 0 5px 5px; - float: right; - width: 15px; - height: 15px; - line-height: 15px; - font-weight: bold; - font-size: 15px; - color: #333333; - - &::after { - content: 'x'; - } - - &:hover { - color: #dd3333; - } - } - } -} diff --git a/BlueMapCore/src/main/webroot/style/modules/compass.scss b/BlueMapCore/src/main/webroot/style/modules/compass.scss deleted file mode 100644 index bfd715d7..00000000 --- a/BlueMapCore/src/main/webroot/style/modules/compass.scss +++ /dev/null @@ -1,13 +0,0 @@ -#bluemap-compass { - width: 2rem; - height: 2rem; - - #bluemap-compass-needle { - width: 100%; - height: 100%; - } - - &:hover #bluemap-compass-needle { - filter: invert(1); - } -} diff --git a/BlueMapCore/src/main/webroot/style/modules/info.scss b/BlueMapCore/src/main/webroot/style/modules/info.scss deleted file mode 100644 index 68b01549..00000000 --- a/BlueMapCore/src/main/webroot/style/modules/info.scss +++ /dev/null @@ -1,10 +0,0 @@ -#bluemap-info { - width: 2rem; - height: 2rem; - text-align: center; - - &::after { - content: 'i'; - font-weight: bold; - } -} diff --git a/BlueMapCore/src/main/webroot/style/modules/mapmenu.scss b/BlueMapCore/src/main/webroot/style/modules/mapmenu.scss deleted file mode 100644 index 5b5d68af..00000000 --- a/BlueMapCore/src/main/webroot/style/modules/mapmenu.scss +++ /dev/null @@ -1,8 +0,0 @@ -#bluemap-mapmenu { - width: 15rem; - cursor: pointer; - - .selection, .dropdown li { - padding-left: 10px; - } -} diff --git a/BlueMapCore/src/main/webroot/style/modules/position.scss b/BlueMapCore/src/main/webroot/style/modules/position.scss index 35acb84d..75dc2dad 100644 --- a/BlueMapCore/src/main/webroot/style/modules/position.scss +++ b/BlueMapCore/src/main/webroot/style/modules/position.scss @@ -1,32 +1,39 @@ -.bluemap-position { - position: relative; +.bluemap-container .ui .ui-element.position { + flex-basis: 6rem; + flex-shrink: 1; + min-width: 4rem; - input { - width: 4rem; - height: 100%; - border: none; - outline: none; - background: transparent; - padding: 0 5px 0 25px; - font: inherit; - color: inherit; + display: flex; - // remove number spinner firefox - -moz-appearance:textfield; + height: 1rem; - // remove number spinner webkit - &::-webkit-inner-spin-button, - &::-webkit-outer-spin-button { - -webkit-appearance: none; - margin: 0; + > input { + width: calc(100% - 2rem); + height: 100%; + padding: 0 0.5rem 0 0; + + font: inherit; + color: inherit; + background: transparent; + + border: none; + outline: none; + + // remove number spinner firefox + -moz-appearance:textfield; + + // remove number spinner webkit + &::-webkit-inner-spin-button, + &::-webkit-outer-spin-button { + -webkit-appearance: none; + margin: 0; + } } - } - - &[data-pos]::before { - position: absolute; - left: 7px; - color: #888888; - content: attr(data-pos)':'; - } -} + &[data-axis]::before { + padding: 0 0.2rem 0 0.5rem; + line-height: 2rem; + color: $light_fg; + content: attr(data-axis)':'; + } +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/modules/settings.scss b/BlueMapCore/src/main/webroot/style/modules/settings.scss deleted file mode 100644 index 8d934126..00000000 --- a/BlueMapCore/src/main/webroot/style/modules/settings.scss +++ /dev/null @@ -1,46 +0,0 @@ -#bluemap-settings { - width: 2rem; - height: 2rem; - - > img { - width: 100%; - height: 100%; - } -} - -#bluemap-settings.active:not(:hover) { - background-color: #dddddd; -} - -#bluemap-settings:hover > img { - filter: invert(1); -} - -#bluemap-settings-container { - display: flex; - white-space: nowrap; -} - -#bluemap-settings-quality { - width: 150px; - height: 2rem; - -} - -#bluemap-settings-quality .selection, #bluemap-settings-quality .dropdown li { - padding-left: 10px; -} - -#bluemap-settings-render-distance { - width: 180px; -} - -#bluemap-settings-render-distance .selection { - padding-left: 10px; -} - -#bluemap-settings-render-distance input { - width: calc(100% - 20px); - margin: 10px; - padding: 0; -} diff --git a/BlueMapCore/src/main/webroot/style/style.scss b/BlueMapCore/src/main/webroot/style/style.scss index d4a723bc..fcbaee59 100644 --- a/BlueMapCore/src/main/webroot/style/style.scss +++ b/BlueMapCore/src/main/webroot/style/style.scss @@ -1,163 +1,105 @@ -@import "./modules/alertbox.scss"; -@import "./modules/compass.scss"; -@import "./modules/info.scss"; -@import "./modules/mapmenu.scss"; -@import "./modules/position.scss"; -@import "./modules/settings.scss"; +@import "constants"; html, body { margin: 0; padding: 0; - font-size: 15px; + font-size: 16px; line-height: 1rem; font-family: Verdana,Helvetica,Arial,sans-serif; - color: #333333; - background-color: #dddddd; + color: $normal_fg; + background-color: $normal_bg; - @media (max-width: 900px) { - font-size: 17px; + @media (max-width: $small-max) { + font-size: 20px; } } -.box { - color: #333333; - background-color: white; - box-shadow: 0 1px 4px 0 rgba(50, 50, 50, 0.8); -} - -.button { - background-color: white; - cursor: pointer; -} - -.button:hover { - background-color: #333333; - color: #dddddd; -} - -.dropdown-container { - background-color: white; - position: relative; - - transition: background-color 0.3s; -} - -.dropdown-container:hover { - background-color: #dddddd; -} - -.dropdown-container > .dropdown { - position: absolute; - background-color: white; - color: #333333; - width: 100%; - - overflow: hidden; - - transition: all 0.3s; - max-height: 0; -} - -.dropdown-container:hover > .dropdown { - max-height: 200px; - border-color: #ddddddFF; -} - -.dropdown-container > .dropdown > ul { - margin: 0; - padding: 0; - list-style: none; -} - -.dropdown-container > .dropdown > ul > li { - cursor: pointer; -} - -.dropdown-container > .dropdown > ul > li:hover { - color: #dddddd; - background-color: #333333; -} - #map-container { position: absolute; + width: 100%; height: 100%; - background-color: black; +} + +.bluemap-container { + position: relative; + + width: 100%; + height: 100%; + overflow: hidden; - } -#map-container canvas { - width: 100%; - height: 100%; -} - -#bluemap-loading { - position: absolute; - width: 200px; - line-height: 20px; - padding: 20px 0; - top: calc(50% - 31px); - left: calc(50% - 101px); - text-align: center; -} - -#bluemap-topright { - position: absolute; - top: 10px; - right: 10px; - - line-height: 2rem; - - display: flex; - - @media (max-width: 900px) { - display: none; - } - - -} - -#bluemap-topright > *:not(:last-child) { - border-right: solid 1px #dddddd; -} - -#bluemap-topleft { - position: absolute; - top: 10px; - left: 10px; - - line-height: 2rem; - - white-space: nowrap; - - display: flex; - - @media (max-width: 900px) { + > .map-canvas { + position: absolute; top: 0; left: 0; + width: 100%; + height: 100%; - >:last-child { - flex-grow: 1; - } + background-color: #000; + + z-index: 0; } - @media (max-width: 500px) { - flex-wrap: wrap; + > .ui { + display: flex; + align-items: stretch; - > :not(:first-child) { - flex-grow: 1; + position: relative; + + width: 100%; + height: 100%; + + color: $normal_fg; + filter: drop-shadow(1px 1px 3px #0008); + + pointer-events: none; + + z-index: 100; + + > * { + pointer-events: auto; } - >:last-child { + > .menu { + position: relative; + + flex-shrink: 0; + + filter: drop-shadow(1px 1px 3px #0008); + + z-index: 200; + + @media (max-width: $middle-max) { + position: absolute; + } + } + + > .hud { + position: relative; + width: 100%; - border-top: solid 1px #dddddd; + + pointer-events: none; + + > * { + pointer-events: auto; + } } } } -#bluemap-topleft > *:not(:last-child) { - border-right: solid 1px #dddddd; -} +@import "ui/ui"; +@import "ui/element"; +@import "ui/toolbar"; +@import "ui/menu"; +@import "ui/button"; +@import "ui/slider"; +@import "ui/togglebutton"; +@import "ui/separator"; +@import "ui/dropdown"; +@import "ui/label"; +@import "modules/position"; diff --git a/BlueMapCore/src/main/webroot/style/ui/button.scss b/BlueMapCore/src/main/webroot/style/ui/button.scss new file mode 100644 index 00000000..0058c539 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/button.scss @@ -0,0 +1,38 @@ +.bluemap-container .ui .ui-element.button { + cursor: pointer; + user-select: none; + + > .label { + margin: 0 0.5rem; + } + + &.icon { + flex-grow: 0; + + > .label { + display: none; + } + } + + &:hover { + background-color: $element_fg; + color: $element_bg; + + > img { + filter: invert(1); + } + } + + &:active { + background-color: $light_fg; + } + + > img { + position: absolute; + top: 0; + left: 0; + + width: 100%; + height: 100%; + } +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/dropdown.scss b/BlueMapCore/src/main/webroot/style/ui/dropdown.scss new file mode 100644 index 00000000..a8ce8a68 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/dropdown.scss @@ -0,0 +1,76 @@ +.bluemap-container .ui .ui-element.dropdown { + padding: 0; + cursor: pointer; + + overflow: visible; + + user-select: none; + + > .header { + height: 100%; + padding-right: 1rem; + + &:hover { + background-color: $light_bg; + } + + > .ui-element { + pointer-events: none; + background-color: transparent; + } + + &::after { + position: absolute; + top: calc(50% - 0.2rem); + right: 0.5rem; + + content: ""; + + width: 0; + height: 0; + + border: solid; + border-width: 0.4rem 0.25rem 0.4rem 0.25rem; + border-color: $normal_fg transparent transparent transparent; + } + } + + &.open > .header::after { + top: calc(50% - 0.6rem); + border-color: transparent transparent $normal_fg transparent; + } + + > .select { + position: absolute; + top: calc(100% - 1px); + left: 0; + + width: calc(100% - 2px); + overflow-x: hidden; + + max-height: 300px; + overflow-y: auto; + + border: solid 1px $light_bg; + + z-index: 110; + + > .option { + background-color: $super-light_bg; + + &.selected { + background-color: $light_bg; + } + + &:hover { + background-color: $normal_fg; + color: $normal_bg; + } + } + } + + .option { + padding: 0 0.5rem; + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/element.scss b/BlueMapCore/src/main/webroot/style/ui/element.scss new file mode 100644 index 00000000..5077effc --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/element.scss @@ -0,0 +1,18 @@ +$element_fg: $normal_fg; +$element_bg: $normal_bg; + +.bluemap-container .ui .ui-element { + position: relative; + + background-color: $element_bg; + color: $element_fg; + + min-width: 2rem; + min-height: 2rem; + line-height: 2rem; + padding: 0; + + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; +} diff --git a/BlueMapCore/src/main/webroot/style/ui/label.scss b/BlueMapCore/src/main/webroot/style/ui/label.scss new file mode 100644 index 00000000..723a90e1 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/label.scss @@ -0,0 +1,5 @@ +.bluemap-container .ui .ui-element.label { + + color: $light_fg; + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/menu.scss b/BlueMapCore/src/main/webroot/style/ui/menu.scss new file mode 100644 index 00000000..7a27d9d4 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/menu.scss @@ -0,0 +1,114 @@ +$menu-width: 375px; + +.bluemap-container .menu { + position: relative; + + height: 100%; + width: $menu-width; + max-width: 100%; + + background-color: $normal_bg; + + overflow: hidden; + + transition: width 0.2s; + + &.closed { + width: 0; + } + + @media (max-width: $menu-width) { + transition: opacity 0.2s; + + &.closed { + opacity: 0; + width: $menu-width; + pointer-events: none; + } + } + + > h1 { + position: absolute; + right: 0; + top: 0; + + width: $menu-width; + height: 1.5rem; + line-height: 1.5rem; + + margin: 0; + padding: 0.25rem; + + text-align: center; + + font-family: inherit; + font-size: 1.2rem; + font-weight: bold; + + box-shadow: 0 0 5px #00000088; + + z-index: 10; + + @media (max-width: $menu-width) { + width: 100%; + } + } + + > .close-button { + z-index: 20; + left: 0; + } + + > .content { + position: absolute; + right: 0; + top: 2rem; + + width: $menu-width; + height: calc(100% - 3rem); + + padding-top: 0.5rem; + + overflow-y: auto; + + @media (max-width: $menu-width) { + width: 100%; + } + + > .separator { + border-top: solid 1px $light_bg; + margin: 0.5rem 0; + } + + > .label { + min-height: 0; + font-size: 0.8rem; + padding: 1rem 0.5rem 0.1rem 1rem; + line-height: 0.8rem; + } + + // a little hacky to force not displaying any icon + > .toggle-button.icon { + > .label { + display: inline !important; + } + + > img { + display: none; + } + + > .switch { + display: block !important; + } + + &.selected:not(:hover) { + background-color: $normal_bg !important; + color: $normal_fg !important; + } + &:hover { + background-color: $light_bg !important; + color: $normal_fg !important; + } + } + } +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/separator.scss b/BlueMapCore/src/main/webroot/style/ui/separator.scss new file mode 100644 index 00000000..dfaf9a5c --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/separator.scss @@ -0,0 +1,10 @@ +.bluemap-container .ui .ui-element.separator { + pointer-events: none; + + min-width: 0; + min-height: 0; + padding: 0; + + background-color: unset; + color: $element_fg; +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/slider.scss b/BlueMapCore/src/main/webroot/style/ui/slider.scss new file mode 100644 index 00000000..d3392a92 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/slider.scss @@ -0,0 +1,23 @@ +.bluemap-container .ui .ui-element.slider { + + display: flex; + align-content: stretch; + + > input { + box-sizing: border-box; + width: 100%; + + padding: 0; + margin: 0 0.5rem; + } + + > .label { + margin: 0 0.5rem; + + min-width: 4rem; + flex-grow: 0; + + text-align: right; + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/togglebutton.scss b/BlueMapCore/src/main/webroot/style/ui/togglebutton.scss new file mode 100644 index 00000000..695e3c8d --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/togglebutton.scss @@ -0,0 +1,79 @@ +.bluemap-container .ui .ui-element.toggle-button { + + &:not(.icon) { + padding-right: 2.75rem; + } + + &:hover, + &:active { + background-color: $light_bg; + color: $normal_fg; + } + + &.icon { + &:hover, + &:active { + background-color: $light_fg; + color: $normal_bg; + } + + &.selected { + background-color: $normal_fg; + color: $normal_bg; + + > img { + filter: invert(1); + } + } + } + + > .switch { + position: absolute; + right: 0.5rem; + top: 50%; + + transform: translate(0, -50%); + + height: 1rem; + width: 1.75rem; + + border-radius: 1rem; + + background-color: $light_fg; + + transition: background-color 0.2s; + + &::after { + position: absolute; + content: ''; + + top: 0; + left: 0; + + height: 0.8rem; + width: 0.8rem; + + margin: 0.1rem; + + border-radius: 100%; + + background-color: $light_bg; + + transition: left 0.2s; + } + + } + + &.selected > .switch { + background-color: #008800; + + &::after { + left: calc(100% - 1rem); + } + } + + &.icon > .switch { + display: none; + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/toolbar.scss b/BlueMapCore/src/main/webroot/style/ui/toolbar.scss new file mode 100644 index 00000000..b558a943 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/toolbar.scss @@ -0,0 +1,93 @@ +.bluemap-container .ui .toolbar { + display: flex; + align-items: stretch; + //justify-content: center; + + width: calc(100% - 20px); + margin: 10px; + + pointer-events: none; + + @media (max-width: $small-max) { + width: 100%; + margin: 0; + + background-color: $super_light_bg; + + > .mobile-hide { + display: none; + } + } + + @media (max-width: $super-small-max) { + flex-wrap: wrap; + } + + > * { + pointer-events: auto; + } + + > .ui-element { + flex-shrink: 0; + + @media (max-width: $small-max) { + border-top: solid 1px $light_bg; + margin-top: -1px; + } + + @media (max-width: $super-small-max) { + flex-grow: 1; + } + } + + > .ui-element:not(.separator) + .ui-element:not(.separator) { + border-left: solid 1px $light_bg; + margin-left: -1px; + } + + > .ui-element.separator { + width: 10px; + flex-shrink: 0; + + @media (max-width: $small-max) { + width: 0; + border-left: solid 1px $light_bg; + margin-left: -1px; + } + + @media (max-width: $super-small-max) { + display: none; + } + } + + > .ui-element.separator.greedy { + flex-grow: 1; + + @media (max-width: $small-max) { + border-right: solid 1px $light_bg; + margin-right: -1px; + + z-index: 101; + } + + @media (max-width: $super-small-max) { + display: unset; + + border-right: none; + margin-right: 0; + + flex-grow: 0; + } + } + + > .ui-element.dropdown { + flex-basis: 15rem; + flex-shrink: 1; + min-width: 10rem; + + @media (max-width: $super-small-max) { + flex-basis: calc(100% - 2rem); //space for dropdown + menu button + } + } + +} \ No newline at end of file diff --git a/BlueMapCore/src/main/webroot/style/ui/ui.scss b/BlueMapCore/src/main/webroot/style/ui/ui.scss new file mode 100644 index 00000000..acefcd68 --- /dev/null +++ b/BlueMapCore/src/main/webroot/style/ui/ui.scss @@ -0,0 +1,95 @@ +.bluemap-container .ui { + position: relative; + + h1, h2, h3, h4, h5, h6 { + font-size: 1rem; + font-weight: bold; + text-decoration: none; + text-align: left; + margin: 0; + padding: 0; + } + + h1 { + font-size: 1.5rem; + } + + h2 { + font-size: 1.3rem; + } + + h3 { + font-size: 1.1rem; + } + + p { + padding: 0; + margin: 0.5rem 0 0 0; + } + + .close-button { + position: absolute; + top: 0; + right: 0; + + width: 1.5rem; + height: 1.5rem; + + margin: 0.25rem; + + font-weight: bold; + + &::after, &::before { + content: ''; + + position: absolute; + top: 50%; + left: 50%; + + width: 0.8rem; + height: 0.2rem; + + background-color: $light_fg; + } + + &::before { + transform: translate(-50%, -50%) rotate(45deg); + } + + &::after { + transform: translate(-50%, -50%) rotate(-45deg); + } + + &:hover::after, &:hover::before { + background-color: darkred; + } + } + + .alert-box { + position: absolute; + top: 0; + left: 0; + + width: 100%; + height: 100%; + + display: flex; + flex-wrap: wrap; + align-items: center; + justify-content: center; + + pointer-events: none; + + .alert { + position: relative; + + pointer-events: all; + + background-color: $normal_bg; + padding: 1rem; + + margin: 1rem; + } + } + +} \ No newline at end of file diff --git a/BlueMapCore/webpack.config.js b/BlueMapCore/webpack.config.js index d62578f6..63497397 100644 --- a/BlueMapCore/webpack.config.js +++ b/BlueMapCore/webpack.config.js @@ -22,7 +22,8 @@ module.exports = { contentBase: WORLD_DATA_PATH, compress: true, port: 8080, - hot: true + hot: true, + host: '0.0.0.0' }, plugins: [ new MiniCssExtractPlugin({