mirror of
https://github.com/unanmed/HumanBreak.git
synced 2025-11-27 13:42:58 +08:00
fix: 勇士跟随者
This commit is contained in:
parent
4f3154d497
commit
f8c9a2349c
@ -33,6 +33,8 @@ import {
|
||||
import { SetupComponentOptions } from '@motajs/system-ui';
|
||||
import { texture } from '../elements';
|
||||
|
||||
// todo: TextContent 应该改成渲染元素?
|
||||
|
||||
//#region TextContent
|
||||
|
||||
export interface TextContentProps
|
||||
|
||||
@ -283,7 +283,6 @@ export class MapHeroRenderer implements IMapHeroRenderer {
|
||||
this.heroEntity.moving = true;
|
||||
this.heroEntity.animating = true;
|
||||
this.heroEntity.lastAnimateTime = this.ticker.timestamp;
|
||||
this.heroEntity.block.useSpecifiedFrame(1);
|
||||
}
|
||||
|
||||
private endEntityMoving(entity: HeroRenderEntity) {
|
||||
@ -381,6 +380,7 @@ export class MapHeroRenderer implements IMapHeroRenderer {
|
||||
promise: Promise.resolve(),
|
||||
animateDirection: HeroAnimateDirection.Forward
|
||||
};
|
||||
moving.useSpecifiedFrame(0);
|
||||
this.entities.push(entity);
|
||||
}
|
||||
|
||||
|
||||
@ -201,7 +201,7 @@ export class MovingBlock extends DynamicBlockStatus implements IMovingBlock {
|
||||
this.y = this.targetY;
|
||||
this.end = true;
|
||||
this.promiseFunc();
|
||||
return false;
|
||||
return true;
|
||||
} else {
|
||||
const timeProgress = dt / this.time;
|
||||
const progress = this.timing(timeProgress);
|
||||
@ -220,7 +220,7 @@ export class MovingBlock extends DynamicBlockStatus implements IMovingBlock {
|
||||
}
|
||||
this.end = true;
|
||||
this.promiseFunc();
|
||||
return false;
|
||||
return true;
|
||||
} else {
|
||||
const timeProgress = dt / this.time;
|
||||
const progress = this.timing(timeProgress);
|
||||
|
||||
@ -18,6 +18,7 @@ import {
|
||||
IMapBackgroundConfig,
|
||||
IMapRenderConfig,
|
||||
IMapRenderer,
|
||||
IMapRendererPostEffect,
|
||||
IMapRendererTicker,
|
||||
IMapVertexGenerator,
|
||||
IMapViewportController,
|
||||
@ -172,6 +173,11 @@ export class MapRenderer
|
||||
/** 画布上下文数据 */
|
||||
private contextData: IContextData;
|
||||
|
||||
/** 效果对象优先级映射 */
|
||||
private effectPriority: Map<IMapRendererPostEffect, number> = new Map();
|
||||
/** 渲染器效果对象列表,使用数组是因为要有顺序 */
|
||||
private postEffects: IMapRendererPostEffect[] = [];
|
||||
|
||||
/** 地图变换矩阵 */
|
||||
transform: Transform;
|
||||
/** 是否需要更新变换矩阵 */
|
||||
@ -293,6 +299,40 @@ export class MapRenderer
|
||||
gl.bindVertexArray(null);
|
||||
}
|
||||
|
||||
private sortPostEffect() {
|
||||
this.postEffects.sort((a, b) => {
|
||||
const pa = this.effectPriority.get(a) ?? 0;
|
||||
const pb = this.effectPriority.get(b) ?? 0;
|
||||
return pb - pa;
|
||||
});
|
||||
}
|
||||
|
||||
addPostEffect(effect: IMapRendererPostEffect, priority: number): void {
|
||||
this.postEffects.push(effect);
|
||||
this.effectPriority.set(effect, priority);
|
||||
this.sortPostEffect();
|
||||
this.updateRequired = true;
|
||||
}
|
||||
|
||||
removePostEffect(effect: IMapRendererPostEffect): void {
|
||||
const index = this.postEffects.indexOf(effect);
|
||||
if (index === -1) return;
|
||||
this.postEffects.splice(index);
|
||||
this.effectPriority.delete(effect);
|
||||
this.sortPostEffect();
|
||||
this.updateRequired = true;
|
||||
}
|
||||
|
||||
setPostEffectPriority(
|
||||
effect: IMapRendererPostEffect,
|
||||
priority: number
|
||||
): void {
|
||||
if (!this.effectPriority.has(effect)) return;
|
||||
this.effectPriority.set(effect, priority);
|
||||
this.sortPostEffect();
|
||||
this.updateRequired = true;
|
||||
}
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region 状态控制
|
||||
@ -646,7 +686,7 @@ export class MapRenderer
|
||||
gl.disable(gl.CULL_FACE);
|
||||
gl.enable(gl.DEPTH_TEST);
|
||||
gl.enable(gl.BLEND);
|
||||
gl.depthFunc(gl.LEQUAL);
|
||||
gl.depthFunc(gl.LESS);
|
||||
gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA);
|
||||
|
||||
const data: IContextData = {
|
||||
@ -1209,6 +1249,7 @@ export class MapRenderer
|
||||
}
|
||||
|
||||
render(): HTMLCanvasElement {
|
||||
// todo: 改为 FBO,最后把 FBO 画到画布上
|
||||
const gl = this.gl;
|
||||
const data = this.contextData;
|
||||
if (!this.assetData) {
|
||||
|
||||
@ -266,6 +266,29 @@ export interface IMapRendererTicker {
|
||||
remove(): void;
|
||||
}
|
||||
|
||||
export interface IMapRendererPostEffect {
|
||||
/**
|
||||
* 初始化渲染器效果对象,一般是编译着色器、准备数据缓冲区等
|
||||
* @param gl WebGL2 画布上下文
|
||||
* @param data 地图渲染的上下文数据
|
||||
*/
|
||||
init(gl: WebGL2RenderingContext, data: IContextData): void;
|
||||
|
||||
/**
|
||||
* 渲染效果对象,将内容渲染到输出 FBO 上
|
||||
* @param gl WebGL2 画布上下文
|
||||
* @param data 地图渲染的上下文数据
|
||||
* @param input 输入 FBO
|
||||
* @param output 输出 FBO,内容要画到这个 FBO 上
|
||||
*/
|
||||
render(
|
||||
gl: WebGL2RenderingContext,
|
||||
data: IContextData,
|
||||
input: WebGLFramebuffer,
|
||||
output: WebGLFramebuffer
|
||||
): void;
|
||||
}
|
||||
|
||||
export interface IMapRenderer {
|
||||
/** 地图渲染器使用的资源管理器 */
|
||||
readonly manager: IMaterialManager;
|
||||
@ -313,6 +336,29 @@ export interface IMapRenderer {
|
||||
*/
|
||||
destroy(): void;
|
||||
|
||||
/**
|
||||
* 添加一个地图渲染器效果对象,一般是对地图渲染的后处理,可以是一些特效和自定义绘制等
|
||||
* @param effect 地图渲染器效果对象
|
||||
* @param priority 效果对象优先级
|
||||
*/
|
||||
addPostEffect(effect: IMapRendererPostEffect, priority: number): void;
|
||||
|
||||
/**
|
||||
* 移除指定的效果对象
|
||||
* @param effect 地图渲染器效果对象
|
||||
*/
|
||||
removePostEffect(effect: IMapRendererPostEffect): void;
|
||||
|
||||
/**
|
||||
* 设置效果对象的优先级
|
||||
* @param effect 地图渲染器效果对象
|
||||
* @param priority 效果对象优先级
|
||||
*/
|
||||
setPostEffectPriority(
|
||||
effect: IMapRendererPostEffect,
|
||||
priority: number
|
||||
): void;
|
||||
|
||||
/**
|
||||
* 渲染地图
|
||||
*/
|
||||
|
||||
@ -365,7 +365,8 @@ export class MapVertexGenerator
|
||||
assetIndex: number,
|
||||
offsetIndex: number,
|
||||
frames: number,
|
||||
update: VertexUpdate
|
||||
update: VertexUpdate,
|
||||
dynamic: boolean
|
||||
) {
|
||||
const { instancedArray } = vertex;
|
||||
// 顶点数组
|
||||
@ -377,8 +378,9 @@ export class MapVertexGenerator
|
||||
const layerIndex = this.renderer.getLayerIndex(index.layer);
|
||||
// 避免 z 坐标是 1 的时候被裁剪,因此范围选择 [-0.9, 0.9]
|
||||
const layerStart = (layerIndex / layerCount) * 1.8 - 0.9;
|
||||
const zIndex =
|
||||
-layerStart - index.mapY / this.mapHeight / layerCount;
|
||||
const perBlockZ = 1 / this.mapHeight / layerCount;
|
||||
const blockZ = index.mapY * perBlockZ;
|
||||
const zIndex = -layerStart - blockZ - (dynamic ? perBlockZ : 0);
|
||||
const { x, y, w, h } = this.getTilePosition(index, width, height);
|
||||
// 图块位置
|
||||
instancedArray[startIndex] = x;
|
||||
@ -418,7 +420,8 @@ export class MapVertexGenerator
|
||||
vertex: IMapVertexData,
|
||||
index: BlockIndex,
|
||||
tile: IMaterialFramedData,
|
||||
update: VertexUpdate
|
||||
update: VertexUpdate,
|
||||
dynamic: boolean
|
||||
) {
|
||||
const autotile = this.renderer.autotile;
|
||||
const { connection, center } = autotile.connect(
|
||||
@ -442,7 +445,8 @@ export class MapVertexGenerator
|
||||
assetIndex,
|
||||
offsetIndex,
|
||||
tile.frames,
|
||||
update
|
||||
update,
|
||||
dynamic
|
||||
);
|
||||
}
|
||||
|
||||
@ -485,7 +489,8 @@ export class MapVertexGenerator
|
||||
vertex,
|
||||
newIndex,
|
||||
tile,
|
||||
VertexUpdate.Texture
|
||||
VertexUpdate.Texture,
|
||||
false
|
||||
);
|
||||
block.data.markRenderDirty();
|
||||
}
|
||||
@ -501,7 +506,8 @@ export class MapVertexGenerator
|
||||
mapArray: Uint32Array,
|
||||
vertex: IMapVertexData,
|
||||
index: BlockIndex,
|
||||
num: number
|
||||
num: number,
|
||||
dynamic: boolean
|
||||
) {
|
||||
// 此处仅更新当前图块,不更新周围一圈的自动元件
|
||||
// 周围一圈的自动元件需要在更新某个图块或者某个区域时处理,不在这里处理
|
||||
@ -526,7 +532,8 @@ export class MapVertexGenerator
|
||||
vertex,
|
||||
index,
|
||||
tile,
|
||||
VertexUpdate.All
|
||||
VertexUpdate.All,
|
||||
dynamic
|
||||
);
|
||||
} else {
|
||||
// 正常图块
|
||||
@ -553,7 +560,8 @@ export class MapVertexGenerator
|
||||
assetIndex,
|
||||
offsetIndex,
|
||||
tile.frames,
|
||||
VertexUpdate.All
|
||||
VertexUpdate.All,
|
||||
dynamic
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -600,7 +608,7 @@ export class MapVertexGenerator
|
||||
this.checkAutotileConnectionAround(layer, array, index, -1, 1);
|
||||
this.checkAutotileConnectionAround(layer, array, index, -1, 0);
|
||||
// 再更新当前图块
|
||||
this.updateVertexArray(array, vertex, index, num);
|
||||
this.updateVertexArray(array, vertex, index, num, false);
|
||||
block.data.markRenderDirty();
|
||||
}
|
||||
|
||||
@ -795,7 +803,8 @@ export class MapVertexGenerator
|
||||
array,
|
||||
vertex,
|
||||
index,
|
||||
array[mapIndex]
|
||||
array[mapIndex],
|
||||
false
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -840,7 +849,8 @@ export class MapVertexGenerator
|
||||
assetIndex,
|
||||
offset,
|
||||
frames,
|
||||
update
|
||||
update,
|
||||
true
|
||||
);
|
||||
} else {
|
||||
// 正常图块
|
||||
@ -859,7 +869,8 @@ export class MapVertexGenerator
|
||||
assetIndex,
|
||||
offset,
|
||||
frames,
|
||||
update
|
||||
update,
|
||||
true
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
@ -171,7 +171,11 @@ export function initFallback() {
|
||||
|
||||
patch.add(
|
||||
'setHeroLoc',
|
||||
function (name: 'x' | 'y' | 'direction', value: number | Dir) {
|
||||
function (
|
||||
name: 'x' | 'y' | 'direction',
|
||||
value: number | Dir,
|
||||
noGather?: boolean
|
||||
) {
|
||||
if (!core.status.hero) return;
|
||||
// @ts-ignore
|
||||
core.status.hero.loc[name] = value;
|
||||
@ -182,17 +186,21 @@ export function initFallback() {
|
||||
} else if (name === 'x') {
|
||||
// 为了防止逆天样板出问题
|
||||
core.bigmap.posX = value as number;
|
||||
state.hero.setPosition(
|
||||
value as number,
|
||||
core.status.hero.loc.y
|
||||
);
|
||||
if (!noGather) {
|
||||
state.hero.setPosition(
|
||||
value as number,
|
||||
core.status.hero.loc.y
|
||||
);
|
||||
}
|
||||
} else {
|
||||
// 为了防止逆天样板出问题
|
||||
core.bigmap.posY = value as number;
|
||||
state.hero.setPosition(
|
||||
core.status.hero.loc.x,
|
||||
value as number
|
||||
);
|
||||
if (!noGather) {
|
||||
state.hero.setPosition(
|
||||
core.status.hero.loc.x,
|
||||
value as number
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
@ -3489,33 +3489,12 @@ events.prototype.hasAsyncAnimate = function () {
|
||||
|
||||
////// 跟随 //////
|
||||
events.prototype.follow = function (name) {
|
||||
name = core.getMappedName(name);
|
||||
if (core.material.images.images[name]) {
|
||||
core.status.hero.followers.push({ name: name });
|
||||
core.gatherFollowers();
|
||||
core.clearMap('hero');
|
||||
core.drawHero();
|
||||
}
|
||||
core.clearRouteFolding();
|
||||
// Deprecated. Use state.hero.addFollower instead.
|
||||
};
|
||||
|
||||
////// 取消跟随 //////
|
||||
events.prototype.unfollow = function (name) {
|
||||
if (!name) {
|
||||
core.status.hero.followers = [];
|
||||
} else {
|
||||
name = core.getMappedName(name);
|
||||
for (var i = 0; i < core.status.hero.followers.length; i++) {
|
||||
if (core.status.hero.followers[i].name == name) {
|
||||
core.status.hero.followers.splice(i, 1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
core.gatherFollowers();
|
||||
core.clearMap('hero');
|
||||
core.drawHero();
|
||||
core.clearRouteFolding();
|
||||
// Deprecated. Use state.hero.removeFollower instead.
|
||||
};
|
||||
|
||||
events.prototype._updateValueByOperator = function (
|
||||
|
||||
Loading…
Reference in New Issue
Block a user