Привет сижу дома, от нефиг делать мучу игрушку.
Ссылка(спрайты весят 15 Mb, нужно подождать пока откроет). Проблема с которой столкнулся- карявое отображение движущихся объектов. На фоне "плиток переднего плана".
Попробую объяснить человеческим языком. Картанка состоит из 3-х канвасов наложенных друг на друга, каждый канвас составлен из "плиток". На заднем плане трава, камни и т.д. На переднем плане - дом и деревья. Между ними- коровы паладины и хз что ещё. Когда корова движется и заходит за дом с верху- она как и задумано теряется из вида, но когда она подходит с низу- то она сцуко залазит под дом.
Редактор состоит из 5 глобалльных объектов
var imgObj = {};//картинки
var canObj = {};//канвасы
var unitObj = {};//движущиеся спрайты отображённые на экране(направление, текуший номер картинки в спрайте, позиция и т.д.)
var spriteObj = {};//инструкция по нарезке unitObj с imgObj (размеры фреймов, исходный img fail и т.д.)
var levelObj = {};//сама карта или левел, состоит из масива отдельных плиток, одно из свойств плитки- z-index канваса на котором она будет печататся. Второй массив- walkareas -collision detection lines.
Все объекты кроме канвасов загружаются с XML файлов
Верхний и нижний канвасы нарезаются при запуске игры и не меняются(если не тыркатся с плитками через редактор). Для загрузки используется функци:
function loadLevel() {
canObj.canvas0.ctx.clearRect(0, 0, canObj.canvas0.canvas.width, canObj.canvas0.canvas.height);
canObj.canvas5.ctx.clearRect(0, 0, canObj.canvas5.canvas.width, canObj.canvas5.canvas.height);
canObj.canvas0.canvas.height = levelObj.level.size.x;
canObj.canvas0.canvas.width = levelObj.level.size.y;
canObj.canvas5.canvas.height = levelObj.level.size.x;
canObj.canvas5.canvas.width = levelObj.level.size.y;
for (var i in levelObj.level.map.tile) {
var zisTile = levelObj.level.map.tile[i];
if (zisTile.z_index === 0) {
var ctx = canObj.canvas0.ctx;
}else if (zisTile.z_index === 5) {
var ctx = canObj.canvas5.ctx;
}
drowTile(zisTile, ctx, levelObj.level.map.tile[i].tilex, levelObj.level.map.tile[i].tiley);
}
}
function drowTile(tile, ctx, ix, iy) {
//console.log(ctx);
ctx.drawImage(imgObj[tile.tileimg.obj],
spriteObj[tile.tileimg.obj][tile.tileimg.sprtype].sx + spriteObj[tile.tileimg.obj].width * tile.tileimg.x,
spriteObj[tile.tileimg.obj][tile.tileimg.sprtype].sy + spriteObj[tile.tileimg.obj].height * tile.tileimg.y,
160,
spriteObj[tile.tileimg.obj][tile.tileimg.sprtype].sheight,
ix,
iy,
160,
spriteObj[tile.tileimg.obj][tile.tileimg.sprtype].sheight);
}
Рендеринг производится с помощью requestAnimationFrame() которая дёргат функцию update() и через неё stopMoving()
function update(dt, now){
canObj.canvas1.ctx.clearRect(0, 0, canObj.canvas1.canvas.width, canObj.canvas1.canvas.height);
for(var i in unitObj){
if (unitObj[i].vy === 0 && unitObj[i].vx === 0) {
unitObj[i].action = "neutral";
}
if ((now - unitObj[i].framestart)>unitObj[i].spr[unitObj[i].action].framerate){
unitObj[i].framestart = now;
if (unitObj[i].framenumber < unitObj[i].spr[unitObj[i].action].numberofframes) {
unitObj[i].framenumber++;
var context = canObj.canvas2.canvas.getContext('2d');
var position = $(canObj.canvas2.canvas).position();
var x = unitObj[i].x + unitObj[i].vx;
var y = unitObj[i].y + unitObj[i].vy;
//проверяем столкновение с colision lines
for (var j in levelObj.level.walkareas) {
levelObj.level.walkareas[j].mouseover = false;
var initx = levelObj.level.walkareas[j].initx;
var inity = levelObj.level.walkareas[j].inity;
var lastx = levelObj.level.walkareas[j].lastx;
var lasty = levelObj.level.walkareas[j].lasty;
var ang = Math.atan2((inity - lasty), (initx - lastx));
context.beginPath();
context.arc(initx, inity, 5, ang - Math.PI/2, ang +Math.PI/2);
context.arc(lastx, lasty, 5, ang + Math.PI/2, ang -Math.PI/2, false);
context.closePath();
if (context.isPointInPath(x, y)) {
unitObj[i].vx = 0;
unitObj[i].vy = 0;
return;
}
}
//////////////////////////
unitObj[i].x+=unitObj[i].vx;
unitObj[i].y+=unitObj[i].vy;
}else {
unitObj[i].framenumber=0;}
}
//console.log(unitObj[i].framenumber);
canObj.canvas1.ctx.drawImage(imgObj[unitObj[i].type],
(unitObj[i].spr[unitObj[i].action][unitObj[i].direction].sx)+unitObj[i].framenumber*(unitObj[i].spr[unitObj[i].action].swidth),
(unitObj[i].spr[unitObj[i].action][unitObj[i].direction].sy),
(unitObj[i].spr[unitObj[i].action].swidth),
(unitObj[i].spr[unitObj[i].action].sheight),
unitObj[i].x - (unitObj[i].spr[unitObj[i].action].width)/2,
unitObj[i].y - (unitObj[i].spr[unitObj[i].action].height)/2,
(unitObj[i].spr[unitObj[i].action].width),
(unitObj[i].spr[unitObj[i].action].height));
stopMoving(i);
}
}
function backgroundRendering(i) {
//code
}
function stopMoving(i){
if (unitObj[i].vx!==0 || unitObj[i].vy!==0) {//if moving
//moving up left
if ((unitObj[i].vx<=0 && unitObj[i].vy<=0) && ((unitObj[i].x <= unitObj[i].destX) || (unitObj[i].y <= unitObj[i].destY))) {
unitObj[i].vx = 0;
unitObj[i].vy = 0;
}
//moving up right
if ((unitObj[i].vx>=0 && unitObj[i].vy<=0) && ((unitObj[i].x >= unitObj[i].destX) || (unitObj[i].y <= unitObj[i].destY))) {
unitObj[i].vx = 0;
unitObj[i].vy = 0;
}
//moving down right
if ((unitObj[i].vx>=0 && unitObj[i].vy>=0) && ((unitObj[i].x >= unitObj[i].destX) || (unitObj[i].y >= unitObj[i].destY))) {
unitObj[i].vx = 0;
unitObj[i].vy = 0;
}
//moving down left
if ((unitObj[i].vx<=0 && unitObj[i].vy>=0) && ((unitObj[i].x <= unitObj[i].destX) || (unitObj[i].y >= unitObj[i].destY))) {
unitObj[i].vx = 0;
unitObj[i].vy = 0;
}
}
}
}
С такой структурой игрушки решить проблему с коровой прячушейся под дом не решить, нужно что-то менять
.
Рассматривал следующие варианты:
перемещять плитки дама на задний план если вектор движения коровы(как звучит ) под определённым углом и её позиция... это бред потому что двигатся должна не только корова, и если несколько коров будут подходить к дому с разных сторон получится месево.
второй вариант(вроде должен работать)- добавить ещё 1-н канвас поверх уже существующих и рендерить коров в зависимости от их положения относительно дома на 2-м или 4-м канвасе
Но вот что до меня не доходит так это к которой точке на спрайте коровы нужно будет привязать Collision detection, либо если эта точка должна меняться- то по какому принципу?