fix move
This commit is contained in:
parent
b4ddfaa6be
commit
f0a7f3357b
197
src/cat.js
197
src/cat.js
|
@ -1,5 +1,5 @@
|
||||||
export class Cat {
|
export class Cat {
|
||||||
constructor(x, y, targetSize) {
|
constructor(x, y, targetSize, groundRef, obstacleRefs) {
|
||||||
this.x = x;
|
this.x = x;
|
||||||
this.y = y;
|
this.y = y;
|
||||||
this.size = 171;
|
this.size = 171;
|
||||||
|
@ -7,6 +7,8 @@ export class Cat {
|
||||||
this.sprite = null;
|
this.sprite = null;
|
||||||
this.loaded = false;
|
this.loaded = false;
|
||||||
this.velocity = 24;
|
this.velocity = 24;
|
||||||
|
this.ground = groundRef;
|
||||||
|
this.obstacles = obstacleRefs;
|
||||||
|
|
||||||
this.steps = [];
|
this.steps = [];
|
||||||
|
|
||||||
|
@ -15,10 +17,14 @@ export class Cat {
|
||||||
this.stepTimer = 0;
|
this.stepTimer = 0;
|
||||||
this.stepDuration = 40; // frames to complete one movement
|
this.stepDuration = 40; // frames to complete one movement
|
||||||
this.moveDirection = null;
|
this.moveDirection = null;
|
||||||
|
this.lastDirection = null;
|
||||||
|
|
||||||
|
this.hasJumped = false;
|
||||||
|
|
||||||
loadImage('assets/cat.webp', (img) => {
|
loadImage('assets/cat.webp', (img) => {
|
||||||
this.sprite = new Sprite(this.x, this.y, this.size, this.size);
|
this.sprite = new Sprite(this.x, this.y, this.size, this.size, 'dynamic');
|
||||||
|
this.sprite.rotationLock = true;
|
||||||
|
this.sprite.bounciness = 0.1;
|
||||||
this.sprite.spriteSheet = img;
|
this.sprite.spriteSheet = img;
|
||||||
this.sprite.anis.offset.y = 3;
|
this.sprite.anis.offset.y = 3;
|
||||||
this.sprite.anis.frameDelay = 8;
|
this.sprite.anis.frameDelay = 8;
|
||||||
|
@ -39,7 +45,6 @@ export class Cat {
|
||||||
}
|
}
|
||||||
|
|
||||||
update() {
|
update() {
|
||||||
// if (!this.sprite) return;
|
|
||||||
if (!this.sprite || this.steps.length === 0) return;
|
if (!this.sprite || this.steps.length === 0) return;
|
||||||
console.log(`updating sprite...`);
|
console.log(`updating sprite...`);
|
||||||
|
|
||||||
|
@ -49,27 +54,18 @@ export class Cat {
|
||||||
this._startMovement(this.steps[this.currentStepIndex]);
|
this._startMovement(this.steps[this.currentStepIndex]);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.sprite.position.x = this.x;
|
|
||||||
this.sprite.position.y = this.y;
|
|
||||||
|
|
||||||
// console.log(`steps to run: ${this.steps}`);
|
|
||||||
|
|
||||||
this._handleInput();
|
this._handleInput();
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
update() {
|
// update() {
|
||||||
if (!this.sprite || this.steps.length === 0) return;
|
// if (!this.sprite || this.steps.length === 0) return;
|
||||||
|
|
||||||
if (this.isMoving) {
|
// if (this.isMoving) {
|
||||||
this._continueMovement();
|
// this._continueMovement();
|
||||||
} else if (this.currentStepIndex < this.steps.length) {
|
// } else if (this.currentStepIndex < this.steps.length) {
|
||||||
this._startMovement(this.steps[this.currentStepIndex]);
|
// this._startMovement(this.steps[this.currentStepIndex]);
|
||||||
}
|
// }
|
||||||
|
// }
|
||||||
this.sprite.position.x = this.x;
|
|
||||||
this.sprite.position.y = this.y;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
run(steps) {
|
run(steps) {
|
||||||
|
@ -79,34 +75,178 @@ export class Cat {
|
||||||
}
|
}
|
||||||
|
|
||||||
_startMovement(direction) {
|
_startMovement(direction) {
|
||||||
|
const blockSize = 100;
|
||||||
this.moveDirection = direction;
|
this.moveDirection = direction;
|
||||||
this.stepTimer = 0;
|
this.stepTimer = 0;
|
||||||
this.isMoving = true;
|
this.isMoving = true;
|
||||||
|
|
||||||
if (direction === 'right') {
|
if (direction === 'right') {
|
||||||
|
this.targetX = this.sprite.x + blockSize;
|
||||||
|
this.sprite.vel.x = this.velocity;
|
||||||
|
this.lastDirection = 'right';
|
||||||
this.changeAni('w');
|
this.changeAni('w');
|
||||||
} else if (direction === 'up' || direction === 'down') {
|
} else if (direction === 'left') {
|
||||||
|
this.targetX = this.sprite.x - blockSize;
|
||||||
|
this.sprite.vel.x = -this.velocity;
|
||||||
|
this.lastDirection = 'left';
|
||||||
|
this.changeAni('w');
|
||||||
|
} else if (direction === 'up') {
|
||||||
|
this.targetY = this.sprite.y - blockSize;
|
||||||
|
this.hasJumped = false;
|
||||||
|
|
||||||
|
// Check platform
|
||||||
|
let isOnPlatform = this._checkPlatform();
|
||||||
|
if (isOnPlatform) {
|
||||||
|
this.sprite.vel.y = -10;
|
||||||
|
if (this.lastDirection === 'right') this.sprite.vel.x = this.velocity;
|
||||||
|
else if (this.lastDirection === 'left') this.sprite.vel.x = -this.velocity;
|
||||||
|
else this.sprite.vel.x = 0;
|
||||||
this.changeAni('j');
|
this.changeAni('j');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
_checkPlatform() {
|
||||||
|
if (!this.sprite) return false;
|
||||||
|
// if (this.ground && this.sprite.colliding(this.ground)) return true;
|
||||||
|
|
||||||
|
if (this.ground && Array.isArray(this.ground)) {
|
||||||
|
for (let block of this.ground) {
|
||||||
|
if (this.sprite.colliding(block)) return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.obstacles && Array.isArray(this.obstacles)) {
|
||||||
|
for (let block of this.obstacles) {
|
||||||
|
if (this.sprite.colliding(block)) return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// _continueMovement() {
|
||||||
|
// this.stepTimer++;
|
||||||
|
|
||||||
|
// // let isOnPlatform = false;
|
||||||
|
// let isOnPlatform = this._checkPlatform(); // Use existing _checkPlatform method instead
|
||||||
|
|
||||||
|
|
||||||
|
// if (this.ground && this.sprite.colliding(this.ground)) {
|
||||||
|
// isOnPlatform = true;
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if (this.obstacles && Array.isArray(this.obstacles)) {
|
||||||
|
// for (let block of this.obstacles) {
|
||||||
|
// if (this.sprite.colliding(block)) {
|
||||||
|
// isOnPlatform = true;
|
||||||
|
// break;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if (this.moveDirection === 'right') {
|
||||||
|
// this.sprite.vel.x = 3;
|
||||||
|
// this.lastDirection = 'right';
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if (this.moveDirection === 'left') {
|
||||||
|
// this.sprite.vel.x = -3;
|
||||||
|
// this.lastDirection = 'left';
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if (this.moveDirection === 'up' && isOnPlatform && !this.hasJumped) {
|
||||||
|
// this.sprite.vel.y = -20;
|
||||||
|
|
||||||
|
// // use lastDirection to add horizontal push
|
||||||
|
// if (this.lastDirection === 'right') {
|
||||||
|
// this.sprite.vel.x = 3;
|
||||||
|
// } else if (this.lastDirection === 'left') {
|
||||||
|
// this.sprite.vel.x = -3;
|
||||||
|
// } else {
|
||||||
|
// this.sprite.vel.x = 0; // jump straight up
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// this.hasJumped = true;
|
||||||
|
|
||||||
|
// if (this.stepTimer >= this.stepDuration) {
|
||||||
|
// this.isMoving = false;
|
||||||
|
// this.currentStepIndex++;
|
||||||
|
// this.sprite.vel.x = 0;
|
||||||
|
// this.changeAni('i');
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
_continueMovement() {
|
_continueMovement() {
|
||||||
this.stepTimer++;
|
this.stepTimer++;
|
||||||
|
|
||||||
const delta = this.velocity / this.stepDuration;
|
let isOnPlatform = this._checkPlatform(); // ✅ use this only
|
||||||
|
|
||||||
if (this.moveDirection === 'right') this.x += delta;
|
if (this.moveDirection === 'right') {
|
||||||
if (this.moveDirection === 'up') this.y -= delta;
|
this.sprite.vel.x = 3;
|
||||||
if (this.moveDirection === 'down') this.y += delta;
|
this.lastDirection = 'right';
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.moveDirection === 'left') {
|
||||||
|
this.sprite.vel.x = -3;
|
||||||
|
this.lastDirection = 'left';
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.moveDirection === 'up' && isOnPlatform && !this.hasJumped) {
|
||||||
|
this.sprite.vel.y = -20;
|
||||||
|
|
||||||
|
if (this.lastDirection === 'right') {
|
||||||
|
this.sprite.vel.x = 3;
|
||||||
|
} else if (this.lastDirection === 'left') {
|
||||||
|
this.sprite.vel.x = -3;
|
||||||
|
} else {
|
||||||
|
this.sprite.vel.x = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
this.hasJumped = true;
|
||||||
|
|
||||||
if (this.stepTimer >= this.stepDuration) {
|
if (this.stepTimer >= this.stepDuration) {
|
||||||
this.isMoving = false;
|
this.isMoving = false;
|
||||||
this.currentStepIndex++;
|
this.currentStepIndex++;
|
||||||
this.changeAni('i'); // back to idle after each move
|
this.sprite.vel.x = 0;
|
||||||
|
this.changeAni('i');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
restart() {
|
||||||
|
console.log('resetting initial position.....');
|
||||||
|
|
||||||
|
if (!this.sprite) return null;
|
||||||
|
|
||||||
|
// Reset position to initial coordinates (from constructor)
|
||||||
|
this.sprite.x = this.x;
|
||||||
|
this.sprite.y = this.y;
|
||||||
|
|
||||||
|
// Reset velocities
|
||||||
|
this.sprite.vel.x = 0;
|
||||||
|
this.sprite.vel.y = 0;
|
||||||
|
|
||||||
|
// Reset movement states
|
||||||
|
this.steps = [];
|
||||||
|
this.currentStepIndex = 0;
|
||||||
|
this.isMoving = false;
|
||||||
|
this.stepTimer = 0;
|
||||||
|
this.moveDirection = null;
|
||||||
|
this.targetX = null;
|
||||||
|
this.targetY = null;
|
||||||
|
|
||||||
|
// Reset animation
|
||||||
|
this.changeAni('i');
|
||||||
|
|
||||||
|
setTimeout(() => {
|
||||||
|
console.log('finish resetting...')
|
||||||
|
}, 1000);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
keyPressed(key) {
|
keyPressed(key) {
|
||||||
console.log(`receiving keyboard input: ${key}`);
|
console.log(`receiving keyboard input: ${key}`);
|
||||||
}
|
}
|
||||||
|
@ -154,11 +294,6 @@ export class Cat {
|
||||||
this.sprite = null;
|
this.sprite = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
moveUp(){
|
|
||||||
console.log(`sprite should move up...`);
|
|
||||||
this.changeAni('j')
|
|
||||||
}
|
|
||||||
|
|
||||||
// helper
|
// helper
|
||||||
_getSpritePosition(){
|
_getSpritePosition(){
|
||||||
console.log(`sprite's actual position: ${this.sprite.x}, ${this.sprite.y}`);
|
console.log(`sprite's actual position: ${this.sprite.x}, ${this.sprite.y}`);
|
||||||
|
|
|
@ -12,7 +12,6 @@ export class ClickableArrow {
|
||||||
}
|
}
|
||||||
|
|
||||||
constructor(direction, clickable = false) {
|
constructor(direction, clickable = false) {
|
||||||
console.log(`constructing a new clickable arrow....`);
|
|
||||||
this.direction = direction;
|
this.direction = direction;
|
||||||
this.image = ClickableArrow.images[direction];
|
this.image = ClickableArrow.images[direction];
|
||||||
this.clickable = clickable;
|
this.clickable = clickable;
|
||||||
|
|
|
@ -8,7 +8,7 @@ let mgr;
|
||||||
|
|
||||||
function setup(){
|
function setup(){
|
||||||
createCanvas(windowWidth, windowHeight);
|
createCanvas(windowWidth, windowHeight);
|
||||||
console.log(`window size: ${windowWidth}x${windowHeight}`);
|
world.gravity.y = 50;
|
||||||
textFont('Pixelify Sans', 'sans-serif');
|
textFont('Pixelify Sans', 'sans-serif');
|
||||||
textAlign(CENTER);
|
textAlign(CENTER);
|
||||||
textSize(128);
|
textSize(128);
|
||||||
|
|
|
@ -2,16 +2,33 @@ import { colors } from '../utils/theme.js';
|
||||||
import { Cat } from '../cat.js';
|
import { Cat } from '../cat.js';
|
||||||
import { buttonS } from '../utils/theme.js';
|
import { buttonS } from '../utils/theme.js';
|
||||||
import { MyButton } from '../utils/components.js';
|
import { MyButton } from '../utils/components.js';
|
||||||
import { Arrow } from '../components/Arrow.js';
|
|
||||||
import { ClickableArrow } from '../components/ClickableArrow.js';
|
import { ClickableArrow } from '../components/ClickableArrow.js';
|
||||||
import { ControlPanel } from '../components/controlPanel.js';
|
import { ControlPanel } from '../components/controlPanel.js';
|
||||||
|
|
||||||
|
|
||||||
export default function GameScene() {
|
export default function GameScene() {
|
||||||
const groundHeight = 100;
|
// for ground
|
||||||
const worldHeight = windowHeight - groundHeight;
|
let ground;
|
||||||
|
let blocksGround = [];
|
||||||
|
let blockSprites = [];
|
||||||
|
|
||||||
|
let restart = false;
|
||||||
|
|
||||||
const catSize = 150;
|
const catSize = 150;
|
||||||
const worldBlockSize = 100;
|
const worldBlockSize = 100;
|
||||||
|
const groundHeight = worldBlockSize;
|
||||||
|
// const worldHeight = windowHeight - groundHeight;
|
||||||
|
const maxIdx = {
|
||||||
|
x: Math.ceil(windowWidth / worldBlockSize),
|
||||||
|
y: Math.floor(windowHeight / worldBlockSize)
|
||||||
|
}
|
||||||
|
|
||||||
|
const obstacle = [
|
||||||
|
...Array(maxIdx.y - 3 - 1).fill(...Array(maxIdx.x).fill(0)),
|
||||||
|
[...Array(9).fill(0), ...Array(maxIdx.x - 9).fill(1)],
|
||||||
|
[...Array(8).fill(0), ...Array(maxIdx.x - 8).fill(1)],
|
||||||
|
[...Array(7).fill(0), ...Array(maxIdx.x - 7).fill(1)],
|
||||||
|
];
|
||||||
|
|
||||||
let cat;
|
let cat;
|
||||||
let runButton;
|
let runButton;
|
||||||
|
@ -45,15 +62,13 @@ export default function GameScene() {
|
||||||
this.name = "GameScene";
|
this.name = "GameScene";
|
||||||
|
|
||||||
this.setup = () => {
|
this.setup = () => {
|
||||||
cat = new Cat(width / 4, height - 175 - 2, catSize);
|
|
||||||
|
|
||||||
runButton = new MyButton({
|
runButton = new MyButton({
|
||||||
x: width / 32 * 28.5,
|
x: (width / 32) * 28.5,
|
||||||
y: height / 32,
|
y: height / 32,
|
||||||
text: "run >>",
|
text: "run >>",
|
||||||
mode: "CORNER",
|
mode: "CORNER",
|
||||||
style: buttonS,
|
style: buttonS,
|
||||||
onPress: () => cat.run(steps.contents),
|
onPress: () => this.startGame(),
|
||||||
});
|
});
|
||||||
|
|
||||||
blocks = new ControlPanel({
|
blocks = new ControlPanel({
|
||||||
|
@ -78,6 +93,42 @@ export default function GameScene() {
|
||||||
// y: height / 32,
|
// y: height / 32,
|
||||||
// numBoxes: 4
|
// numBoxes: 4
|
||||||
// });
|
// });
|
||||||
|
|
||||||
|
for (let i = 0; i < width; i += worldBlockSize) {
|
||||||
|
let b = new Sprite(
|
||||||
|
i + worldBlockSize / 2, // x position for each block
|
||||||
|
height - groundHeight / 2, // y position
|
||||||
|
worldBlockSize, // width of each block
|
||||||
|
worldBlockSize, // height of each block
|
||||||
|
'static'
|
||||||
|
);
|
||||||
|
const i_cnt = Math.floor(i / worldBlockSize);
|
||||||
|
|
||||||
|
b.color = (i_cnt % 2) === 0 ? color(colors.secondary) : color(colors.darkRed);
|
||||||
|
b.strokeWeight = 5;
|
||||||
|
b.stroke = (i_cnt % 2) === 0 ? color(colors.darkRed) : color(colors.darkRed);
|
||||||
|
blocksGround.push(b);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obstacles (physical)
|
||||||
|
for (let y = windowHeight - groundHeight - 2; y > 0; y -= worldBlockSize) {
|
||||||
|
for (let x = 0; x < width; x += worldBlockSize) {
|
||||||
|
const x_cnt = Math.floor(x / worldBlockSize);
|
||||||
|
const y_cnt = Math.floor(y / worldBlockSize);
|
||||||
|
const isObs = obstacle[y_cnt] && obstacle[y_cnt][x_cnt];
|
||||||
|
|
||||||
|
if (isObs) {
|
||||||
|
let b = new Sprite(x + worldBlockSize / 2, y + worldBlockSize / 2, worldBlockSize, worldBlockSize, 'static');
|
||||||
|
b.color = (x_cnt + y_cnt) % 2 === 0 ? color(colors.tertiary) : color(colors.accent);
|
||||||
|
b.strokeWeight = 0;
|
||||||
|
blockSprites.push(b);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Cat sprite
|
||||||
|
// cat = new Cat(width / 4, height - catSize * 13/12, catSize, blocksGround, blockSprites);
|
||||||
|
cat = new Cat(3.5 * worldBlockSize, height - catSize * 13/12, catSize, blocksGround, blockSprites);
|
||||||
};
|
};
|
||||||
|
|
||||||
this.draw = () => {
|
this.draw = () => {
|
||||||
|
@ -90,35 +141,10 @@ export default function GameScene() {
|
||||||
textAlign(LEFT, TOP);
|
textAlign(LEFT, TOP);
|
||||||
text('lvl.1', width / 32, height /32 - 4);
|
text('lvl.1', width / 32, height /32 - 4);
|
||||||
|
|
||||||
// Ground
|
|
||||||
rectMode(CORNER);
|
|
||||||
fill(colors.secondary);
|
|
||||||
rect(0, height - groundHeight, width, groundHeight);
|
|
||||||
|
|
||||||
console.log(`ground is drawn at (0, ${height - groundHeight}) with size of ${width}x${groundHeight}`)
|
|
||||||
|
|
||||||
// Obstacle
|
|
||||||
console.log(`world size: ${windowWidth}, ${windowHeight}`);
|
|
||||||
for (let y = windowHeight - groundHeight - 2; y > 0; y -= worldBlockSize) {
|
|
||||||
for (let x = 0; x < width ; x += worldBlockSize) {
|
|
||||||
stroke(0)
|
|
||||||
strokeWeight(1)
|
|
||||||
noFill()
|
|
||||||
rect(x, y, worldBlockSize, worldBlockSize);
|
|
||||||
textSize(24);
|
|
||||||
const x_cnt = Math.floor(x / worldBlockSize);
|
|
||||||
const y_cnt = Math.floor(y / worldBlockSize);
|
|
||||||
const txt = `${x_cnt}, ${y_cnt}`;
|
|
||||||
text(txt, x + 8, y + 8);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
runButton.draw();
|
runButton.draw();
|
||||||
blocks.draw();
|
blocks.draw();
|
||||||
steps.draw();
|
steps.draw();
|
||||||
// loops.draw();
|
// loops.draw();
|
||||||
|
|
||||||
// Sprite
|
|
||||||
cat.draw();
|
cat.draw();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -171,4 +197,10 @@ export default function GameScene() {
|
||||||
});
|
});
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
this.startGame = () => {
|
||||||
|
if (restart) cat.restart();
|
||||||
|
cat.run(steps.contents);
|
||||||
|
this.restart = true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@ const colors = {
|
||||||
secondary: "#ff4f64",
|
secondary: "#ff4f64",
|
||||||
tertiary: "#fff29d",
|
tertiary: "#fff29d",
|
||||||
accent: "#a4e4b6",
|
accent: "#a4e4b6",
|
||||||
|
darkRed: "#C0404F"
|
||||||
};
|
};
|
||||||
|
|
||||||
const button = {
|
const button = {
|
||||||
|
|
Loading…
Reference in New Issue
Block a user