mirror of
https://github.com/unanmed/HumanBreak.git
synced 2026-11-03 10:14:34 +08:00
feat: 宝石血瓶显伤
This commit is contained in:
1 parent
57760d501e
commit
1c369251b1
11 files changed
+218
-144
No files matched your search
@@ -0,0 +1,42 @@
|
||||
import { FloorItemDetail } from '@/plugin/fx/itemDetail';
|
||||
import { FloorDamageExtends } from './preset/damage';
|
||||
import { LayerGroupFloorBinder } from './preset/floor';
|
||||
import { HeroRenderer } from './preset/hero';
|
||||
import { LayerGroup, FloorLayer } from './preset/layer';
|
||||
import { MotaRenderer } from './render';
|
||||
|
||||
let main: MotaRenderer;
|
||||
|
||||
export function getMainRenderer() {
|
||||
return main;
|
||||
}
|
||||
|
||||
Mota.require('var', 'loading').once('loaded', () => {
|
||||
const render = new MotaRenderer();
|
||||
main = render;
|
||||
render.mount();
|
||||
render.hide();
|
||||
|
||||
const layer = new LayerGroup();
|
||||
|
||||
['bg', 'bg2', 'event', 'fg', 'fg2'].forEach(v => {
|
||||
layer.addLayer(v as FloorLayer);
|
||||
});
|
||||
|
||||
const damage = new FloorDamageExtends();
|
||||
const hero = new HeroRenderer();
|
||||
const detail = new FloorItemDetail();
|
||||
layer.extends(damage);
|
||||
layer.extends(detail);
|
||||
layer.getLayer('event')?.extends(hero);
|
||||
|
||||
render.appendChild(layer);
|
||||
});
|
||||
|
||||
Mota.require('var', 'hook').on('reset', () => {
|
||||
main.show();
|
||||
});
|
||||
|
||||
Mota.require('var', 'hook').on('restart', () => {
|
||||
main.hide();
|
||||
});
|
||||
@@ -40,7 +40,7 @@ export class FloorDamageExtends
|
||||
* 立刻刷新伤害渲染
|
||||
*/
|
||||
update(floor: FloorIds) {
|
||||
if (!this.sprite) return;
|
||||
if (!this.sprite || !floor) return;
|
||||
const map = core.status.maps[floor];
|
||||
this.sprite.setMapSize(map.width, map.height);
|
||||
ensureFloorDamage(floor);
|
||||
@@ -89,21 +89,19 @@ export class FloorDamageExtends
|
||||
}
|
||||
|
||||
awake(group: LayerGroup): void {
|
||||
group.requestBeforeFrame(() => {
|
||||
const ex = group.getExtends('floor-binder');
|
||||
if (ex instanceof LayerGroupFloorBinder) {
|
||||
this.floorBinder = ex;
|
||||
this.group = group;
|
||||
this.create();
|
||||
this.listen();
|
||||
} else {
|
||||
logger.warn(
|
||||
17,
|
||||
`Floor-damage extends needs 'floor-binder' extends as dependency.`
|
||||
);
|
||||
group.removeExtends('floor-damage');
|
||||
}
|
||||
});
|
||||
const ex = group.getExtends('floor-binder');
|
||||
if (ex instanceof LayerGroupFloorBinder) {
|
||||
this.floorBinder = ex;
|
||||
this.group = group;
|
||||
this.create();
|
||||
this.listen();
|
||||
} else {
|
||||
logger.warn(
|
||||
17,
|
||||
`Floor-damage extends needs 'floor-binder' extends as dependency.`
|
||||
);
|
||||
group.removeExtends('floor-damage');
|
||||
}
|
||||
}
|
||||
|
||||
onDestroy(group: LayerGroup): void {
|
||||
@@ -132,6 +130,7 @@ interface DamageCache {
|
||||
interface EDamageEvent extends ESpriteEvent {
|
||||
setMapSize: [width: number, height: number];
|
||||
beforeDamageRender: [need: Set<number>, transform: Transform];
|
||||
updateBlocks: [blocks: Set<number>];
|
||||
}
|
||||
|
||||
export class Damage extends Sprite<EDamageEvent> {
|
||||
@@ -241,13 +240,16 @@ export class Damage extends Sprite<EDamageEvent> {
|
||||
/**
|
||||
* 更新指定分块
|
||||
* @param blocks 要更新的分块集合
|
||||
* @param map 是否更新地图伤害
|
||||
*/
|
||||
updateBlocks(blocks?: Set<number>) {
|
||||
updateBlocks(blocks?: Set<number>, map: boolean = true) {
|
||||
if (blocks) {
|
||||
blocks.forEach(v => this.updateBlock(v));
|
||||
blocks.forEach(v => this.updateBlock(v, map));
|
||||
this.emit('updateBlocks', blocks);
|
||||
} else {
|
||||
this.blockData.forEach((_, k) => this.updateBlock(k, false));
|
||||
this.extractAllMapDamage();
|
||||
if (map) this.extractAllMapDamage();
|
||||
this.emit('updateBlocks', new Set(this.blockData.keys()));
|
||||
}
|
||||
this.update(this);
|
||||
}
|
||||
@@ -274,7 +276,9 @@ export class Damage extends Sprite<EDamageEvent> {
|
||||
this.needUpdateBlocks.add(block);
|
||||
this.requestBeforeFrame(() => {
|
||||
this.needUpdateBlock = false;
|
||||
this.needUpdateBlocks.forEach(v => this.updateBlock(v, false));
|
||||
this.updateBlocks(this.needUpdateBlocks, false);
|
||||
this.needUpdateBlocks.clear();
|
||||
// this.needUpdateBlocks.forEach(v => this.updateBlock(v, false));
|
||||
// todo: 阻击夹域等地图伤害检测是否必要更新,例如不包含阻击夹域的怪就不必要更新这个怪物信息
|
||||
// this.extractAllMapDamage();
|
||||
});
|
||||
@@ -423,6 +427,7 @@ export class Damage extends Sprite<EDamageEvent> {
|
||||
ctx.save();
|
||||
this.damageMap.clear();
|
||||
transformCanvas(this.damageMap, transform);
|
||||
// console.trace();
|
||||
|
||||
const { res: render } = this.calNeedRender(transform);
|
||||
const block = this.block;
|
||||
|
||||
@@ -149,9 +149,9 @@ export class LayerGroupFloorBinder
|
||||
LayerGroupFloorBinder.activedBinder.add(this);
|
||||
}
|
||||
|
||||
onLayerAdd(group: LayerGroup, layer: Layer): void {
|
||||
this.checkLayerExtends(layer);
|
||||
}
|
||||
// onLayerAdd(group: LayerGroup, layer: Layer): void {
|
||||
// this.checkLayerExtends(layer);
|
||||
// }
|
||||
|
||||
onDestroy(group: LayerGroup) {
|
||||
LayerGroupFloorBinder.activedBinder.delete(this);
|
||||
|
||||
@@ -145,7 +145,10 @@ export class HeroRenderer
|
||||
*/
|
||||
private moveTick(time: number) {
|
||||
if (this.status !== 'moving') return;
|
||||
if (!this.renderable) return;
|
||||
if (!this.renderable) {
|
||||
this.emit('stepEnd');
|
||||
return;
|
||||
}
|
||||
|
||||
if (time - this.lastFrameTime > this.speed) {
|
||||
this.lastFrameTime = time;
|
||||
@@ -379,6 +382,10 @@ adapter.recieve('turn', (item, dir: Dir2) => {
|
||||
item.turn(dir);
|
||||
return Promise.resolve();
|
||||
});
|
||||
adapter.recieve('setImage', (item, image: SizedCanvasImageSource) => {
|
||||
item.setImage(image);
|
||||
return Promise.resolve();
|
||||
});
|
||||
// 同步fallback,用于适配现在的样板,之后会删除
|
||||
adapter.recieveSync('setHeroLoc', (item, x?: number, y?: number) => {
|
||||
item.setHeroLoc(x, y);
|
||||
|
||||
@@ -8,6 +8,7 @@ import { RenderableData, texture } from '../cache';
|
||||
import { glMatrix } from 'gl-matrix';
|
||||
import { BlockCacher } from './block';
|
||||
import { Transform } from '../transform';
|
||||
import { LayerFloorBinder, LayerGroupFloorBinder } from './floor';
|
||||
|
||||
export interface ILayerGroupRenderExtends {
|
||||
/** 拓展的唯一标识符 */
|
||||
@@ -60,6 +61,18 @@ export interface ILayerGroupRenderExtends {
|
||||
*/
|
||||
onFrameUpdate?(group: LayerGroup, frame: number): void;
|
||||
|
||||
/**
|
||||
* 在渲染之前执行的函数
|
||||
* @param group 目标LayerGroup实例
|
||||
*/
|
||||
onBeforeRender?(group: LayerGroup): void;
|
||||
|
||||
/**
|
||||
* 在渲染之后执行的函数
|
||||
* @param group 目标LayerGroup实例
|
||||
*/
|
||||
onAfterRender?(group: LayerGroup): void;
|
||||
|
||||
/**
|
||||
* 当拓展被取消挂载时执行的函数(LayerGroup被销毁,拓展被移除等)
|
||||
* @param group 目标LayerGroup实例
|
||||
@@ -100,6 +113,10 @@ export class LayerGroup extends Container implements IAnimateFrame {
|
||||
});
|
||||
|
||||
renderEmits.addFramer(this);
|
||||
|
||||
const binder = new LayerGroupFloorBinder();
|
||||
this.extends(binder);
|
||||
binder.bindThis();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -675,6 +692,8 @@ export class Layer extends Container {
|
||||
ctx.drawImage(this.staticMap.canvas, 0, 0, width, height);
|
||||
ctx.drawImage(this.movingMap.canvas, 0, 0, width, height);
|
||||
});
|
||||
|
||||
this.extends(new LayerFloorBinder());
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -1,14 +1,7 @@
|
||||
import { Animation, hyper, linear, sleep } from 'mutate-animate';
|
||||
import { MotaCanvas2D, MotaOffscreenCanvas2D } from '../fx/canvas2d';
|
||||
import { MotaCanvas2D } from '../fx/canvas2d';
|
||||
import { Container } from './container';
|
||||
import { RenderItem, transformCanvas } from './item';
|
||||
import { FloorLayer, Layer, LayerGroup } from './preset/layer';
|
||||
import { LayerGroupFloorBinder } from './preset/floor';
|
||||
import { FloorDamageExtends } from './preset/damage';
|
||||
import { HeroRenderer } from './preset/hero';
|
||||
import { RenderItem } from './item';
|
||||
import { Transform } from './transform';
|
||||
import { Text } from './preset/misc';
|
||||
import { Shader } from './shader';
|
||||
|
||||
export class MotaRenderer extends Container {
|
||||
static list: Set<MotaRenderer> = new Set();
|
||||
@@ -69,65 +62,3 @@ export class MotaRenderer extends Container {
|
||||
window.addEventListener('resize', () => {
|
||||
MotaRenderer.list.forEach(v => v.update(v));
|
||||
});
|
||||
|
||||
Mota.require('var', 'hook').once('reset', () => {
|
||||
const render = new MotaRenderer();
|
||||
const transform = render.transform;
|
||||
render.mount();
|
||||
|
||||
const ani = new Animation();
|
||||
|
||||
const shader = new Shader();
|
||||
const layer = new LayerGroup();
|
||||
|
||||
['bg', 'bg2', 'event', 'fg', 'fg2'].forEach(v => {
|
||||
layer.addLayer(v as FloorLayer);
|
||||
});
|
||||
|
||||
const binder = new LayerGroupFloorBinder();
|
||||
const damage = new FloorDamageExtends();
|
||||
const hero = new HeroRenderer();
|
||||
layer.extends(binder);
|
||||
layer.extends(damage);
|
||||
layer.getLayer('event')?.extends(hero);
|
||||
binder.bindThis();
|
||||
render.appendChild(shader);
|
||||
shader.appendChild(layer);
|
||||
shader.size(480, 480);
|
||||
shader.fs(`
|
||||
uniform float u_offset;
|
||||
|
||||
void main() {
|
||||
// 计算当前像素到爆炸中心的距离
|
||||
vec2 coordToCenter = v_texCoord - vec2(0.5, 0.5);
|
||||
float distance = length(coordToCenter);
|
||||
|
||||
// 根据时间计算当前距离上的波动相位
|
||||
float wavePhase = 100.0 * (distance - u_offset);
|
||||
|
||||
// 计算波动的强度(正弦波)并结合衰减
|
||||
float wave = sin(wavePhase) * 0.02 / (1.0 + 10.0 * distance);
|
||||
|
||||
// 将波动效果应用到纹理坐标上,造成扭曲
|
||||
vec2 warpedCoords = v_texCoord + normalize(coordToCenter) * wave;
|
||||
|
||||
// 采样纹理并输出颜色
|
||||
gl_FragColor = texture2D(u_sampler, warpedCoords);
|
||||
}
|
||||
`);
|
||||
shader.compileShader();
|
||||
|
||||
const offset = shader.getUniform('u_offset');
|
||||
shader.delegateTicker(() => {
|
||||
shader.gl.uniform1f(offset, ani.value.offset);
|
||||
shader.update();
|
||||
}, 20000);
|
||||
ani.value.offset = 0;
|
||||
ani.mode(linear()).time(10000).absolute().apply('offset', 1);
|
||||
|
||||
layer.requestAfterFrame(() => {
|
||||
hero.setImage(core.material.images.images['hero2.png']);
|
||||
});
|
||||
|
||||
console.log(render);
|
||||
});
|
||||
Reference in new issue
Block a user