Skip to content

Commit

Permalink
GH-28 Getting raycasts of viable locations
Browse files Browse the repository at this point in the history
- Calculating viable locations for movement based on original positions.
  • Loading branch information
amaccann committed Apr 15, 2020
1 parent cda740e commit 249c4d0
Show file tree
Hide file tree
Showing 10 changed files with 431 additions and 62 deletions.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
9 changes: 7 additions & 2 deletions packages/phaser3-formation-generator/src/demo/index.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import Phaser from 'phaser';
import { DragSelectPlugin } from '@pixelburp/phaser3-drag-select';
import { GameObjectEnginePlugin } from '@pixelburp/phaser3-game-object-engine';

import DemoScene from './scene/demo-scene';
import FormationGeneratorPlugin from '../js/formation-generator-plugin';
Expand All @@ -9,7 +11,11 @@ const config = {
height: 1000,
parent: 'mycanvas',
plugins: {
global: [{ key: 'FormationGeneratorPlugin', plugin: FormationGeneratorPlugin }],
global: [
{ key: 'DragSelectPlugin', plugin: DragSelectPlugin },
{ key: 'GameObjectEnginePlugin', plugin: GameObjectEnginePlugin },
{ key: 'FormationGeneratorPlugin', plugin: FormationGeneratorPlugin },
],
},
physics: {
default: 'arcade',
Expand All @@ -22,4 +28,3 @@ const config = {
};

const game = new Phaser.Game(config);

129 changes: 94 additions & 35 deletions packages/phaser3-formation-generator/src/demo/scene/demo-scene.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,69 @@ import Phaser, { Scene } from 'phaser';
import { forEach, MOUSE_BUTTONS } from '@pixelburp/phaser3-utils';

import FormationGeneratorPlugin from 'src/js/formation-generator-plugin';
import DemoTileMap from './tile-map.js';
import DemoSprite from './demo-sprite';

const { KeyCodes } = Phaser.Input.Keyboard;
const DEBUG_PREVIEW_COLOR = 0x00ff00;
const DEBUG_SELECTION_COLOR = 0xff00ff;

export default class DemoScene extends Scene {
fpsText;
mySprites;
mySprites = [];
selectedSprites = [];

constructor() {
super({ key: 'DemoScene', active: true });
}

onPreview = ({ items }) => {
forEach(this.children.getChildren(), sprite => {
// Ignore if already selected...
if (sprite.tintTopLeft === DEBUG_SELECTION_COLOR) {
return;
}

// If one of the sprites under the selection, set tint
if (items.includes(sprite)) {
return sprite.setTint(DEBUG_PREVIEW_COLOR);
}

// Otherwise, clear it.
if (!!sprite.input) {
sprite.setTint(0xffffff);
}
});
};

onSelect = ({ items }) => {
console.warn('items', items);
this.children.getChildren().forEach(s => s.input && s.setTint(0xffffff));

items.forEach(sprite => sprite.setTint(DEBUG_SELECTION_COLOR));
this.selectedSprites = items;
};

onPointerUp = pointer => {
const { cameras, dummySprite } = this;
const { shiftKey } = pointer.event;

if (!this.selectedSprites.length || pointer.button !== 2) {
return;
}

const result = this.formationMovement.calculate(this.selectedSprites, {
maxCols: 15,
minCols: 3,
});

result.forEach(item => {
const x = item.tile.getCenterX(cameras.main);
const y = item.tile.getCenterY(cameras.main);
item.gameObject.pxlEngine.addWayPoint(new Phaser.Geom.Point(x, y));
});
};

createCamera() {
const { keyboard } = this.input;

Expand All @@ -32,20 +84,43 @@ export default class DemoScene extends Scene {
this.myControls = new Phaser.Cameras.Controls.SmoothedKeyControl(controlConfig);
}

createInputEvents() {
const { formationMovement, mySprites } = this;

this.input.on('pointerdown', () => {
console.log('mySprites', mySprites);
formationMovement.calculate(mySprites, {
maxCols: 15,
minCols: 3
});
createAllPlugins() {
const { cameras } = this;
const mainCamera = cameras.main;

this.dragSelect = this.plugins.start('DragSelectPlugin', 'dragSelect');
this.dragSelect.setup(this, {
camera: mainCamera,
dragCameraBy: false,
onPreview: this.onPreview,
onSelect: this.onSelect,
outlineColor: 0x00ff00,
outlineWidth: 2,
rectBgColor: 0x33ff00,
rectAlpha: 0.2,
});

this.formationMovement = this.plugins.start('FormationGeneratorPlugin', 'formationMovement');
this.formationMovement.setup({
camera: mainCamera,
collisionIndices: this.tileMap.collisionIndices,
gridSize: 64,
scene: this,
mouseClickToTrack: MOUSE_BUTTONS.RIGHT,
onComplete: this.onPointerUp,
tileLayer: this.tileMap.bgLayer,
});

this.gameObjectEnginePlugin = this.plugins.start('GameObjectEnginePlugin', 'gameObjectEnginePlugin');
this.gameObjectEnginePlugin.setup(this, mainCamera);
}

createInputEvents() {
this.input.on('pointerup', this.onPointerUp);
}

createSprites() {
let sprite, setAsInteractive, y, spriteKey, worldX, worldY;
let sprite, y, worldX, worldY;
this.mySprites = [];
let x = 1;
const length = 5;
Expand All @@ -54,53 +129,37 @@ export default class DemoScene extends Scene {
for (x; x <= length; x += 1) {
y = 1;
for (y; y <= length; y += 1) {
// Every even numbered item will be set as "interactive"
setAsInteractive = x % 2 === 0;
spriteKey = setAsInteractive ? 'enabled-sprite' : 'disabled-sprite';
worldX = x * 100 + OFFSET;
worldY = y * 100 + OFFSET;
sprite = new Phaser.GameObjects.Sprite(this, worldX, worldY, spriteKey);
sprite.isSelected = setAsInteractive; // @TODO temp setting as "selected"

if (setAsInteractive) {
sprite.setInteractive();
}
sprite = new DemoSprite(this, worldX, worldY);

this.add.existing(sprite);
this.mySprites.push(sprite);
}
}
}

preload() {
this.load.image('ground_1x1', 'src/assets/ground_1x1.png');
this.load.image('disabled-sprite', 'src/assets/disabled-sprite-50x50.png');
this.load.image('enabled-sprite', 'src/assets/enabled-sprite-50x50.png');
}

create() {
const { cameras } = this;
const mainCamera = cameras.main;

console.log('DemoScene scene', this);
this.formationMovement = this.plugins.start('FormationGeneratorPlugin', 'formationMovement');
this.formationMovement.setup({
camera: mainCamera,
gridSize: 64,
scene: this,
mouseClickToTrack: MOUSE_BUTTONS.RIGHT,
});

this.fpsText = this.add.text(10, 10, '');
this.fpsText.setScrollFactor(0);
this.tileMap = new DemoTileMap(this);

this.createAllPlugins();

this.createCamera();
this.createSprites();
this.createInputEvents();

this.fpsText = this.add.text(10, 10, '');
this.fpsText.setScrollFactor(0);
}

update(time, delta) {
this.myControls.update(time, delta);
this.gameObjectEnginePlugin.update(time, delta);
this.fpsText.setText(`FPS: ${this.game.loop.actualFps.toFixed(3)}`);
}
}
21 changes: 21 additions & 0 deletions packages/phaser3-formation-generator/src/demo/scene/demo-sprite.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import Phaser from 'phaser';
import { v4 } from 'uuid';

const TEMP_SPEED = 250;

export default class DemoSprite extends Phaser.GameObjects.Sprite {
constructor(scene, x, y) {
super(scene, x, y, 'enabled-sprite');
this.id = v4();

scene.gameObjectEnginePlugin.addEngineToGameObject(this, {
rotateOnMove: false,
rotateSpeed: 10,
speed: TEMP_SPEED,
gameObjectStoppingDistance: 128,
});
scene.add.existing(this);
scene.physics.world.enable(this);
this.setInteractive();
}
}
113 changes: 113 additions & 0 deletions packages/phaser3-formation-generator/src/demo/scene/tile-map.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
import Phaser from 'phaser';

const WIDTH_TILES = 40;
const HEIGHT_TILES = 30;
const TILE_SIZE = 32;
const MAP_CONFIG = {
tileWidth: TILE_SIZE,
tileHeight: TILE_SIZE,
width: WIDTH_TILES,
height: HEIGHT_TILES,
};
const COLLISION_INDICES = new Array(24).fill('').map((d, i) => i); // Ignore the last item in ground_1x1 (grass)

const STAGGERED_TILES = [
[20, 20],
[21, 20],
[21, 21],
[22, 21],
[22, 22],
[23, 22],

[25, 20],
[26, 20],
[26, 21],
[27, 21],
[27, 22],
[28, 22],
];

export default class DemoTileMap {
bgLayer;
collisionLayer;
map;
scene;
tileSet;

constructor(scene) {
this.scene = scene;
this.map = scene.make.tilemap(MAP_CONFIG);

this.tileSet = this.map.addTilesetImage('demo-ground-tile-set', 'ground_1x1', TILE_SIZE, TILE_SIZE);

this.initLayers();
this.drawBackgroundLayer();
this.drawGrid();

// Must be after we add the layer / tileSet
this.map.setCollision(COLLISION_INDICES);
}

get collisionIndices() {
return COLLISION_INDICES;
}

initLayers() {
this.bgLayer = this.map.createBlankDynamicLayer('demo-bg-layer-id', this.tileSet);
this.collisionLayer = this.map.createBlankDynamicLayer('demo-layer-id', this.tileSet);
}

drawBackgroundLayer() {
const { width, height } = this.map;
let y = 0;
let x;

for (y; y < height; y++) {
x = 0;
for (x; x < width; x++) {
this.map.putTileAt(24, x, y, true, this.bgLayer);
}
}
}

/**
* @description Draws a random shape on the map for testing
*/
drawGrid() {
const { map } = this;
const startAtX = 5;
const startAtY = 5;
const yLength = startAtY + 10;
let y = startAtY;
let xLength;
let x;
let tileIndex;

for (y; y < yLength; y++) {
x = startAtX;
xLength = startAtX + 20;
for (x; x < xLength; x++) {
if (x !== startAtX && y !== startAtY && x !== xLength - 4 && y !== yLength - 1) {
continue;
}

tileIndex = Math.floor(Phaser.Math.Between(0, COLLISION_INDICES.length - 1));
map.putTileAt(tileIndex, x, y, true, this.collisionLayer);
}
}

STAGGERED_TILES.forEach(([tileX, tileY]) => {
tileIndex = Math.floor(Phaser.Math.Between(0, COLLISION_INDICES.length - 1));
map.putTileAt(tileIndex, tileX, tileY, true, this.collisionLayer);
});
}

placeTileAtWorldPoint(worldPoint) {
// Rounds down to nearest tile
const pointerTileX = this.map.worldToTileX(worldPoint.x);
const pointerTileY = this.map.worldToTileY(worldPoint.y);

const tileIndex = Phaser.Math.Between(0, 23);
this.map.putTileAt(tileIndex, pointerTileX, pointerTileY, true, this.collisionLayer);
}
}
Loading

0 comments on commit 249c4d0

Please sign in to comment.