mirror of
https://github.com/unanmed/HumanBreak.git
synced 2025-01-31 23:29:27 +08:00
feat: 录像播放工具栏
This commit is contained in:
parent
cbc09e6b86
commit
7ed74c8004
@ -1325,6 +1325,8 @@ control.prototype.startReplay = function (list) {
|
|||||||
this._replay_drawProgress();
|
this._replay_drawProgress();
|
||||||
core.updateStatusBar(false, true);
|
core.updateStatusBar(false, true);
|
||||||
core.drawTip('开始播放');
|
core.drawTip('开始播放');
|
||||||
|
Mota.require('var', 'hook').emit('replayStatus', false);
|
||||||
|
Mota.require('class', 'CustomToolbar').setDefaultTool(true);
|
||||||
this.replay();
|
this.replay();
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1340,6 +1342,7 @@ control.prototype.pauseReplay = function () {
|
|||||||
core.status.replay.pausing = true;
|
core.status.replay.pausing = true;
|
||||||
core.updateStatusBar(false, true);
|
core.updateStatusBar(false, true);
|
||||||
core.drawTip('暂停播放');
|
core.drawTip('暂停播放');
|
||||||
|
Mota.require('var', 'hook').emit('replayStatus', false);
|
||||||
};
|
};
|
||||||
|
|
||||||
////// 恢复播放 //////
|
////// 恢复播放 //////
|
||||||
@ -1353,6 +1356,7 @@ control.prototype.resumeReplay = function () {
|
|||||||
core.updateStatusBar(false, true);
|
core.updateStatusBar(false, true);
|
||||||
core.drawTip('恢复播放');
|
core.drawTip('恢复播放');
|
||||||
core.replay();
|
core.replay();
|
||||||
|
Mota.require('var', 'hook').emit('replayStatus', true);
|
||||||
};
|
};
|
||||||
|
|
||||||
////// 单步播放 //////
|
////// 单步播放 //////
|
||||||
@ -1417,6 +1421,8 @@ control.prototype.stopReplay = function (force) {
|
|||||||
core.deleteCanvas('replay');
|
core.deleteCanvas('replay');
|
||||||
core.updateStatusBar(false, true);
|
core.updateStatusBar(false, true);
|
||||||
core.drawTip('停止播放并恢复游戏');
|
core.drawTip('停止播放并恢复游戏');
|
||||||
|
Mota.require('var', 'hook').emit('replayStatus', true);
|
||||||
|
Mota.require('class', 'CustomToolbar').setDefaultTool(false);
|
||||||
};
|
};
|
||||||
|
|
||||||
////// 回退 //////
|
////// 回退 //////
|
||||||
@ -1453,6 +1459,7 @@ control.prototype.rewindReplay = function () {
|
|||||||
core.control._replay_drawProgress();
|
core.control._replay_drawProgress();
|
||||||
core.updateStatusBar(false, true);
|
core.updateStatusBar(false, true);
|
||||||
core.drawTip('成功回退到上一个节点');
|
core.drawTip('成功回退到上一个节点');
|
||||||
|
Mota.require('class', 'CustomToolbar').setDefaultTool(true);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1686,6 +1693,7 @@ control.prototype._replay_error = function (action, callback) {
|
|||||||
if (core.status.replay.save.length > 0) {
|
if (core.status.replay.save.length > 0) {
|
||||||
core.status.replay.replaying = true;
|
core.status.replay.replaying = true;
|
||||||
core.status.replay.pausing = true;
|
core.status.replay.pausing = true;
|
||||||
|
Mota.require('var', 'hook').emit('replayStatus', false);
|
||||||
core.rewindReplay();
|
core.rewindReplay();
|
||||||
} else {
|
} else {
|
||||||
core.playSound('操作失败');
|
core.playSound('操作失败');
|
||||||
|
@ -4492,19 +4492,27 @@ events.prototype._checkLvUp_check = function () {
|
|||||||
|
|
||||||
////// 尝试使用道具 //////
|
////// 尝试使用道具 //////
|
||||||
events.prototype.tryUseItem = function (itemId, noRoute, callback) {
|
events.prototype.tryUseItem = function (itemId, noRoute, callback) {
|
||||||
if (itemId == 'book') {
|
if (itemId === 'book') {
|
||||||
|
if (core.isReplaying()) {
|
||||||
|
core.control._replay_book();
|
||||||
|
} else {
|
||||||
core.ui.closePanel();
|
core.ui.closePanel();
|
||||||
core.openBook(false);
|
core.openBook(false);
|
||||||
callback?.();
|
callback?.();
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (itemId == 'fly') {
|
if (core.isReplaying()) {
|
||||||
|
callback?.();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (itemId === 'fly') {
|
||||||
core.ui.closePanel();
|
core.ui.closePanel();
|
||||||
core.useFly(false);
|
core.useFly(false);
|
||||||
callback?.();
|
callback?.();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (itemId == 'centerFly') {
|
if (itemId === 'centerFly') {
|
||||||
core.ui.closePanel();
|
core.ui.closePanel();
|
||||||
core.ui._drawCenterFly();
|
core.ui._drawCenterFly();
|
||||||
callback?.();
|
callback?.();
|
||||||
|
@ -77,6 +77,8 @@ var functions_d6ad677b_427a_4623_b50f_a445a3b0ef8a = {
|
|||||||
delete flags[v];
|
delete flags[v];
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Mota.require('class', 'CustomToolbar').setDefaultTool(false);
|
||||||
},
|
},
|
||||||
win: function (reason, norank, noexit) {
|
win: function (reason, norank, noexit) {
|
||||||
// 游戏获胜事件
|
// 游戏获胜事件
|
||||||
|
@ -127,6 +127,48 @@ const misc: Misc = {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const playingDefaultTool: MiscToolbar = {
|
||||||
|
id: '@defaults_misc',
|
||||||
|
type: 'misc',
|
||||||
|
folded: false,
|
||||||
|
noDefaultAction: true,
|
||||||
|
items: [
|
||||||
|
'book',
|
||||||
|
'fly',
|
||||||
|
'save',
|
||||||
|
'load',
|
||||||
|
'toolbox',
|
||||||
|
'equipbox',
|
||||||
|
'shop',
|
||||||
|
'virtualKey',
|
||||||
|
'setting',
|
||||||
|
'undo',
|
||||||
|
'redo',
|
||||||
|
'viewMap',
|
||||||
|
'danmaku',
|
||||||
|
'minimap'
|
||||||
|
]
|
||||||
|
};
|
||||||
|
const replayingDefaultTool: MiscToolbar = {
|
||||||
|
id: '@defaults_misc',
|
||||||
|
type: 'misc',
|
||||||
|
folded: false,
|
||||||
|
noDefaultAction: true,
|
||||||
|
items: [
|
||||||
|
'startReplay',
|
||||||
|
'stopReplay',
|
||||||
|
'rewindReplay',
|
||||||
|
'stepReplay',
|
||||||
|
'book',
|
||||||
|
'speedDownReplay',
|
||||||
|
'speedUpReplay',
|
||||||
|
'save',
|
||||||
|
'viewMap',
|
||||||
|
'danmaku',
|
||||||
|
'minimap'
|
||||||
|
]
|
||||||
|
};
|
||||||
|
|
||||||
export class CustomToolbar extends EventEmitter<CustomToolbarEvent> {
|
export class CustomToolbar extends EventEmitter<CustomToolbarEvent> {
|
||||||
static num: number = 0;
|
static num: number = 0;
|
||||||
static list: CustomToolbar[] = shallowReactive([]);
|
static list: CustomToolbar[] = shallowReactive([]);
|
||||||
@ -369,6 +411,44 @@ export class CustomToolbar extends EventEmitter<CustomToolbarEvent> {
|
|||||||
static closeAll() {
|
static closeAll() {
|
||||||
this.list.forEach(v => v.closeAll());
|
this.list.forEach(v => v.closeAll());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 设置默认工具栏的内容
|
||||||
|
*/
|
||||||
|
static setDefaultTool(replaying: boolean) {
|
||||||
|
const mainStorage = GameStorage.for(GameStorage.fromGame('main'));
|
||||||
|
mainStorage.read();
|
||||||
|
let defaultsTool = CustomToolbar.list.find(v => v.id === '@defaults');
|
||||||
|
const hasDefaults = !!defaultsTool;
|
||||||
|
if (!defaultsTool) {
|
||||||
|
defaultsTool = new CustomToolbar('@defaults', true);
|
||||||
|
}
|
||||||
|
defaultsTool.closeAll();
|
||||||
|
defaultsTool.items.splice(0);
|
||||||
|
defaultsTool.add(replaying ? replayingDefaultTool : playingDefaultTool);
|
||||||
|
if (!mainStorage.getValue('played', false)) {
|
||||||
|
mainStorage.setValue('played', true);
|
||||||
|
|
||||||
|
// 计算位置,显示在游戏画面下方
|
||||||
|
if (!hasDefaults) {
|
||||||
|
const game = core.dom.gameDraw;
|
||||||
|
const bottom = game.offsetTop + game.offsetHeight;
|
||||||
|
const left = game.offsetLeft;
|
||||||
|
const width = game.offsetWidth;
|
||||||
|
|
||||||
|
if (isMobile) {
|
||||||
|
// 手机端显示在最下方
|
||||||
|
defaultsTool.setPos(16, bottom);
|
||||||
|
defaultsTool.setSize(window.innerWidth - 32, 85);
|
||||||
|
} else {
|
||||||
|
// 电脑显示在屏幕右方
|
||||||
|
defaultsTool.setPos(left, bottom);
|
||||||
|
defaultsTool.setSize(width, 70);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
defaultsTool.show();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Mota.require('var', 'loading').once('coreInit', () => {
|
Mota.require('var', 'loading').once('coreInit', () => {
|
||||||
@ -387,57 +467,6 @@ Mota.require('var', 'hook').on('reset', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
Mota.require('var', 'hook').once('reset', () => {
|
Mota.require('var', 'hook').once('reset', () => {
|
||||||
const mainStorage = GameStorage.for(GameStorage.fromGame('main'));
|
CustomToolbar.setDefaultTool(false);
|
||||||
mainStorage.read();
|
|
||||||
if (!mainStorage.getValue('played', false)) {
|
|
||||||
mainStorage.setValue('played', true);
|
|
||||||
let defaultsTool = CustomToolbar.list.find(v => v.id === '@defaults');
|
|
||||||
const hasDefaults = !!defaultsTool;
|
|
||||||
if (!defaultsTool) {
|
|
||||||
defaultsTool = new CustomToolbar('@defaults', true);
|
|
||||||
}
|
|
||||||
defaultsTool.closeAll();
|
|
||||||
defaultsTool.items = reactive([]);
|
|
||||||
defaultsTool.add({
|
|
||||||
id: '@defaults_misc',
|
|
||||||
type: 'misc',
|
|
||||||
folded: false,
|
|
||||||
noDefaultAction: true,
|
|
||||||
items: [
|
|
||||||
'book',
|
|
||||||
'fly',
|
|
||||||
'save',
|
|
||||||
'load',
|
|
||||||
'toolbox',
|
|
||||||
'equipbox',
|
|
||||||
'shop',
|
|
||||||
'virtualKey',
|
|
||||||
'setting',
|
|
||||||
'undo',
|
|
||||||
'redo',
|
|
||||||
'danmaku',
|
|
||||||
'minimap'
|
|
||||||
]
|
|
||||||
});
|
|
||||||
// 计算位置,显示在游戏画面下方
|
|
||||||
if (!hasDefaults) {
|
|
||||||
const game = core.dom.gameDraw;
|
|
||||||
const bottom = game.offsetTop + game.offsetHeight;
|
|
||||||
const left = game.offsetLeft;
|
|
||||||
const width = game.offsetWidth;
|
|
||||||
|
|
||||||
if (isMobile) {
|
|
||||||
// 手机端显示在最下方
|
|
||||||
defaultsTool.setPos(16, bottom);
|
|
||||||
defaultsTool.setSize(window.innerWidth - 32, 85);
|
|
||||||
} else {
|
|
||||||
// 电脑显示在屏幕右方
|
|
||||||
defaultsTool.setPos(left, bottom);
|
|
||||||
defaultsTool.setSize(width, 70);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
defaultsTool.show();
|
|
||||||
CustomToolbar.save();
|
CustomToolbar.save();
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
@ -18,18 +18,24 @@ import {
|
|||||||
import { MotaSettingItem, mainSetting } from '../setting';
|
import { MotaSettingItem, mainSetting } from '../setting';
|
||||||
import Minimap from '@/components/minimap.vue';
|
import Minimap from '@/components/minimap.vue';
|
||||||
import { gameKey } from '../custom/hotkey';
|
import { gameKey } from '../custom/hotkey';
|
||||||
import { FunctionalComponent, StyleValue, h } from 'vue';
|
import { FunctionalComponent, StyleValue, h, ref } from 'vue';
|
||||||
import { mainUi } from './ui';
|
import { mainUi } from './ui';
|
||||||
import { isMobile } from '@/plugin/use';
|
import { isMobile } from '@/plugin/use';
|
||||||
import {
|
import {
|
||||||
|
BackwardFilled,
|
||||||
BackwardOutlined,
|
BackwardOutlined,
|
||||||
|
BorderOuterOutlined,
|
||||||
|
CaretRightOutlined,
|
||||||
EllipsisOutlined,
|
EllipsisOutlined,
|
||||||
FolderOpenOutlined,
|
FolderOpenOutlined,
|
||||||
|
ForwardOutlined,
|
||||||
LayoutOutlined,
|
LayoutOutlined,
|
||||||
MessageOutlined,
|
MessageOutlined,
|
||||||
|
PauseOutlined,
|
||||||
RetweetOutlined,
|
RetweetOutlined,
|
||||||
RollbackOutlined,
|
RollbackOutlined,
|
||||||
SwapOutlined
|
StepBackwardOutlined,
|
||||||
|
StepForwardOutlined
|
||||||
} from '@ant-design/icons-vue';
|
} from '@ant-design/icons-vue';
|
||||||
import { generateKeyboardEvent } from '../custom/keyboard';
|
import { generateKeyboardEvent } from '../custom/keyboard';
|
||||||
|
|
||||||
@ -758,6 +764,10 @@ Mota.require('var', 'hook').once('reset', () => {
|
|||||||
const scale = mainSetting.getSetting('ui.toolbarScale') as Readonly<
|
const scale = mainSetting.getSetting('ui.toolbarScale') as Readonly<
|
||||||
MotaSettingItem<number>
|
MotaSettingItem<number>
|
||||||
>;
|
>;
|
||||||
|
const replaying = ref(false);
|
||||||
|
Mota.require('var', 'hook').on('replayStatus', re => {
|
||||||
|
replaying.value = re;
|
||||||
|
});
|
||||||
|
|
||||||
CustomToolbar.misc.register('danmaku', '发弹幕', openDanmakuPoster, () =>
|
CustomToolbar.misc.register('danmaku', '发弹幕', openDanmakuPoster, () =>
|
||||||
h(MessageOutlined)
|
h(MessageOutlined)
|
||||||
@ -869,7 +879,11 @@ Mota.require('var', 'hook').once('reset', () => {
|
|||||||
'save',
|
'save',
|
||||||
'存档',
|
'存档',
|
||||||
() => {
|
() => {
|
||||||
|
if (core.isReplaying()) {
|
||||||
|
core.control._replay_SL();
|
||||||
|
} else {
|
||||||
core.save(true);
|
core.save(true);
|
||||||
|
}
|
||||||
},
|
},
|
||||||
() => (
|
() => (
|
||||||
<img
|
<img
|
||||||
@ -973,6 +987,86 @@ Mota.require('var', 'hook').once('reset', () => {
|
|||||||
},
|
},
|
||||||
() => h(LayoutOutlined)
|
() => h(LayoutOutlined)
|
||||||
);
|
);
|
||||||
|
CustomToolbar.misc.register(
|
||||||
|
'startReplay',
|
||||||
|
'播放录像',
|
||||||
|
() => {
|
||||||
|
core.triggerReplay();
|
||||||
|
},
|
||||||
|
() => (
|
||||||
|
<span>
|
||||||
|
{replaying.value ? <PauseOutlined /> : <CaretRightOutlined />}
|
||||||
|
</span>
|
||||||
|
)
|
||||||
|
);
|
||||||
|
CustomToolbar.misc.register(
|
||||||
|
'stopReplay',
|
||||||
|
'停止录像',
|
||||||
|
() => {
|
||||||
|
core.stopReplay();
|
||||||
|
},
|
||||||
|
() => (
|
||||||
|
<svg
|
||||||
|
width="1em"
|
||||||
|
height="1em"
|
||||||
|
fill="currentColor"
|
||||||
|
viewBox="0 0 512 512"
|
||||||
|
focusable="false"
|
||||||
|
>
|
||||||
|
<rect x="128" y="128" width="256" height="256"></rect>
|
||||||
|
</svg>
|
||||||
|
)
|
||||||
|
);
|
||||||
|
CustomToolbar.misc.register(
|
||||||
|
'rewindReplay',
|
||||||
|
'回退录像',
|
||||||
|
() => {
|
||||||
|
core.rewindReplay();
|
||||||
|
},
|
||||||
|
() => <StepBackwardOutlined />
|
||||||
|
);
|
||||||
|
CustomToolbar.misc.register(
|
||||||
|
'stepReplay',
|
||||||
|
'单步前进录像',
|
||||||
|
() => {
|
||||||
|
core.stepReplay();
|
||||||
|
},
|
||||||
|
() => <StepForwardOutlined />
|
||||||
|
);
|
||||||
|
CustomToolbar.misc.register(
|
||||||
|
'speedDownReplay',
|
||||||
|
'录像减速',
|
||||||
|
() => {
|
||||||
|
core.speedDownReplay();
|
||||||
|
},
|
||||||
|
() => <BackwardOutlined />
|
||||||
|
);
|
||||||
|
CustomToolbar.misc.register(
|
||||||
|
'speedUpReplay',
|
||||||
|
'录像加速',
|
||||||
|
() => {
|
||||||
|
core.speedUpReplay();
|
||||||
|
},
|
||||||
|
() => <ForwardOutlined />
|
||||||
|
);
|
||||||
|
CustomToolbar.misc.register(
|
||||||
|
'viewMap',
|
||||||
|
'浏览地图',
|
||||||
|
() => {
|
||||||
|
if (core.isReplaying()) {
|
||||||
|
core.control._replay_viewMap();
|
||||||
|
} else {
|
||||||
|
if (
|
||||||
|
core.isPlaying() &&
|
||||||
|
!core.isMoving() &&
|
||||||
|
!core.status.lockControl
|
||||||
|
) {
|
||||||
|
core.ui._drawViewMaps();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
() => <BorderOuterOutlined />
|
||||||
|
);
|
||||||
|
|
||||||
CustomToolbar.misc.bindActivable('minimap', true, () => minimapTool);
|
CustomToolbar.misc.bindActivable('minimap', true, () => minimapTool);
|
||||||
});
|
});
|
||||||
|
@ -77,393 +77,6 @@ export class Shader extends GL2 {
|
|||||||
): void {}
|
): void {}
|
||||||
}
|
}
|
||||||
|
|
||||||
// export class Shader extends Container<EShaderEvent> {
|
|
||||||
// /** 是否支持此组件 */
|
|
||||||
// static readonly support: boolean = isWebGL2Supported();
|
|
||||||
|
|
||||||
// // 会用到的一些常量
|
|
||||||
// // 着色器版本
|
|
||||||
// readonly VERSION_ES_100: ShaderVersion.ES_100 = 0;
|
|
||||||
// readonly VERSION_ES_300: ShaderVersion.ES_300 = 1;
|
|
||||||
// // uniform 类型
|
|
||||||
// readonly UNIFORM_1f: UniformType.Uniform1f = UniformType.Uniform1f;
|
|
||||||
// readonly UNIFORM_1fv: UniformType.Uniform1fv = UniformType.Uniform1fv;
|
|
||||||
// readonly UNIFORM_1i: UniformType.Uniform1i = UniformType.Uniform1i;
|
|
||||||
// readonly UNIFORM_1iv: UniformType.Uniform1iv = UniformType.Uniform1iv;
|
|
||||||
// readonly UNIFORM_1ui: UniformType.Uniform1ui = UniformType.Uniform1ui;
|
|
||||||
// readonly UNIFORM_1uiv: UniformType.Uniform1uiv = UniformType.Uniform1uiv;
|
|
||||||
// readonly UNIFORM_2f: UniformType.Uniform2f = UniformType.Uniform2f;
|
|
||||||
// readonly UNIFORM_2fv: UniformType.Uniform2fv = UniformType.Uniform2fv;
|
|
||||||
// readonly UNIFORM_2i: UniformType.Uniform2i = UniformType.Uniform2i;
|
|
||||||
// readonly UNIFORM_2iv: UniformType.Uniform2iv = UniformType.Uniform2iv;
|
|
||||||
// readonly UNIFORM_2ui: UniformType.Uniform2ui = UniformType.Uniform2ui;
|
|
||||||
// readonly UNIFORM_2uiv: UniformType.Uniform2uiv = UniformType.Uniform2uiv;
|
|
||||||
// readonly UNIFORM_3f: UniformType.Uniform3f = UniformType.Uniform3f;
|
|
||||||
// readonly UNIFORM_3fv: UniformType.Uniform3fv = UniformType.Uniform3fv;
|
|
||||||
// readonly UNIFORM_3i: UniformType.Uniform3i = UniformType.Uniform3i;
|
|
||||||
// readonly UNIFORM_3iv: UniformType.Uniform3iv = UniformType.Uniform3iv;
|
|
||||||
// readonly UNIFORM_3ui: UniformType.Uniform3ui = UniformType.Uniform3ui;
|
|
||||||
// readonly UNIFORM_3uiv: UniformType.Uniform3uiv = UniformType.Uniform3uiv;
|
|
||||||
// readonly UNIFORM_4f: UniformType.Uniform4f = UniformType.Uniform4f;
|
|
||||||
// readonly UNIFORM_4fv: UniformType.Uniform4fv = UniformType.Uniform4fv;
|
|
||||||
// readonly UNIFORM_4i: UniformType.Uniform4i = UniformType.Uniform4i;
|
|
||||||
// readonly UNIFORM_4iv: UniformType.Uniform4iv = UniformType.Uniform4iv;
|
|
||||||
// readonly UNIFORM_4ui: UniformType.Uniform4ui = UniformType.Uniform4ui;
|
|
||||||
// readonly UNIFORM_4uiv: UniformType.Uniform4uiv = UniformType.Uniform4uiv;
|
|
||||||
// // uniform matrix 类型
|
|
||||||
// readonly U_MATRIX_2x2: UniformMatrix.UMatrix2x2 = UniformMatrix.UMatrix2x2;
|
|
||||||
// readonly U_MATRIX_2x3: UniformMatrix.UMatrix2x3 = UniformMatrix.UMatrix2x3;
|
|
||||||
// readonly U_MATRIX_2x4: UniformMatrix.UMatrix2x4 = UniformMatrix.UMatrix2x4;
|
|
||||||
// readonly U_MATRIX_3x2: UniformMatrix.UMatrix3x2 = UniformMatrix.UMatrix3x2;
|
|
||||||
// readonly U_MATRIX_3x3: UniformMatrix.UMatrix3x3 = UniformMatrix.UMatrix3x3;
|
|
||||||
// readonly U_MATRIX_3x4: UniformMatrix.UMatrix3x4 = UniformMatrix.UMatrix3x4;
|
|
||||||
// readonly U_MATRIX_4x2: UniformMatrix.UMatrix4x2 = UniformMatrix.UMatrix4x2;
|
|
||||||
// readonly U_MATRIX_4x3: UniformMatrix.UMatrix4x3 = UniformMatrix.UMatrix4x3;
|
|
||||||
// readonly U_MATRIX_4x4: UniformMatrix.UMatrix4x4 = UniformMatrix.UMatrix4x4;
|
|
||||||
// // attribute 类型
|
|
||||||
// readonly ATTRIB_1f: AttribType.Attrib1f = AttribType.Attrib1f;
|
|
||||||
// readonly ATTRIB_1fv: AttribType.Attrib1fv = AttribType.Attrib1fv;
|
|
||||||
// readonly ATTRIB_2f: AttribType.Attrib2f = AttribType.Attrib2f;
|
|
||||||
// readonly ATTRIB_2fv: AttribType.Attrib2fv = AttribType.Attrib2fv;
|
|
||||||
// readonly ATTRIB_3f: AttribType.Attrib3f = AttribType.Attrib3f;
|
|
||||||
// readonly ATTRIB_3fv: AttribType.Attrib3fv = AttribType.Attrib3fv;
|
|
||||||
// readonly ATTRIB_4f: AttribType.Attrib4f = AttribType.Attrib4f;
|
|
||||||
// readonly ATTRIB_4fv: AttribType.Attrib4fv = AttribType.Attrib4fv;
|
|
||||||
// readonly ATTRIB_I4i: AttribType.AttribI4i = AttribType.AttribI4i;
|
|
||||||
// readonly ATTRIB_I4iv: AttribType.AttribI4iv = AttribType.AttribI4iv;
|
|
||||||
// readonly ATTRIB_I4ui: AttribType.AttribI4ui = AttribType.AttribI4ui;
|
|
||||||
// readonly ATTRIB_I4uiv: AttribType.AttribI4uiv = AttribType.AttribI4uiv;
|
|
||||||
// // 渲染模式
|
|
||||||
// readonly DRAW_ARRAYS = RenderMode.Arrays;
|
|
||||||
// readonly DRAW_ELEMENTS = RenderMode.Elements;
|
|
||||||
// readonly DRAW_ARRAYS_INSTANCED = RenderMode.ArraysInstanced;
|
|
||||||
// readonly DRAW_ELEMENTS_INSTANCED = RenderMode.ElementsInstanced;
|
|
||||||
// // 其他常量
|
|
||||||
// readonly MAX_TEXTURE_COUNT: number = 0;
|
|
||||||
|
|
||||||
// canvas: HTMLCanvasElement;
|
|
||||||
// gl: WebGL2RenderingContext;
|
|
||||||
|
|
||||||
// /** 是否需要重新渲染着色器 */
|
|
||||||
// private shaderRenderDirty: boolean = true;
|
|
||||||
|
|
||||||
// /** webgl使用的程序 */
|
|
||||||
// private program: ShaderProgram | null = null;
|
|
||||||
|
|
||||||
// /** 当前渲染实例的所有着色器程序 */
|
|
||||||
// private programs: Set<ShaderProgram> = new Set();
|
|
||||||
// /** framebuffer 映射 */
|
|
||||||
// private framebufferMap: Map<string, WebGLFramebuffer> = new Map();
|
|
||||||
|
|
||||||
// constructor(type: RenderItemPosition = 'static') {
|
|
||||||
// super(type, !Shader.support);
|
|
||||||
|
|
||||||
// this.canvas = document.createElement('canvas');
|
|
||||||
// this.gl = this.canvas.getContext('webgl2')!;
|
|
||||||
// if (!Shader.support) {
|
|
||||||
// this.canvas.width = 0;
|
|
||||||
// this.canvas.height = 0;
|
|
||||||
// } else {
|
|
||||||
// const num = this.gl.getParameter(this.gl.MAX_TEXTURE_IMAGE_UNITS);
|
|
||||||
// if (typeof num === 'number') {
|
|
||||||
// this.MAX_TEXTURE_COUNT = num;
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
// this.init();
|
|
||||||
// }
|
|
||||||
|
|
||||||
// protected render(
|
|
||||||
// canvas: MotaOffscreenCanvas2D,
|
|
||||||
// transform: Transform
|
|
||||||
// ): void {
|
|
||||||
// if (!Shader.support || !this.program || !this.program.modified) {
|
|
||||||
// super.render(canvas, transform);
|
|
||||||
// } else {
|
|
||||||
// const compile = this.program.requestCompile();
|
|
||||||
// if (compile) {
|
|
||||||
// this.gl.useProgram(this.program.program);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// if (this.cacheDirty) {
|
|
||||||
// const { ctx } = this.cache;
|
|
||||||
// ctx.clearRect(0, 0, canvas.width, canvas.height);
|
|
||||||
// ctx.save();
|
|
||||||
// super.render(this.cache, transform);
|
|
||||||
// ctx.restore();
|
|
||||||
// this.cacheDirty = false;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// if (this.shaderRenderDirty) {
|
|
||||||
// this.drawScene();
|
|
||||||
// this.shaderRenderDirty = false;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// canvas.ctx.drawImage(this.canvas, 0, 0, this.width, this.height);
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
// setHD(hd: boolean): void {
|
|
||||||
// super.setHD(hd);
|
|
||||||
// this.sizeGL(this.width, this.height);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// size(width: number, height: number): void {
|
|
||||||
// super.size(width, height);
|
|
||||||
// this.sizeGL(width, height);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// private sizeGL(width: number, height: number) {
|
|
||||||
// const ratio = this.highResolution ? devicePixelRatio : 1;
|
|
||||||
// const scale = ratio * core.domStyle.scale;
|
|
||||||
// this.canvas.width = width * scale;
|
|
||||||
// this.canvas.height = height * scale;
|
|
||||||
// this.shaderRenderDirty = true;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// update(item?: RenderItem<any>): void {
|
|
||||||
// super.update(item);
|
|
||||||
// this.shaderRenderDirty = true;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// drawScene() {
|
|
||||||
// const gl = this.gl;
|
|
||||||
// const program = this.program;
|
|
||||||
// if (!gl || !program) return;
|
|
||||||
// const useDefault = program.defaultReady;
|
|
||||||
// const dr = useDefault ? this.defaultReady() : true;
|
|
||||||
// const ready = dr && program.ready();
|
|
||||||
// if (!ready) return;
|
|
||||||
// const indices = program.usingIndices;
|
|
||||||
// const param = program.getDrawParams(program.renderMode);
|
|
||||||
// if (!param) return;
|
|
||||||
|
|
||||||
// // 清空画布
|
|
||||||
// gl.viewport(0, 0, this.canvas.width, this.canvas.height);
|
|
||||||
// gl.clearColor(0, 0, 0, 0);
|
|
||||||
// gl.clearDepth(1);
|
|
||||||
// gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
|
|
||||||
|
|
||||||
// const pre = this.preDraw(gl, program, param, indices);
|
|
||||||
// if (!pre) {
|
|
||||||
// this.postDraw(gl, program, param, indices);
|
|
||||||
// return;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// this.draw(gl, program, param, indices);
|
|
||||||
|
|
||||||
// this.postDraw(gl, program, param, indices);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// draw(
|
|
||||||
// gl: WebGL2RenderingContext,
|
|
||||||
// program: ShaderProgram,
|
|
||||||
// param: DrawParamsMap[keyof DrawParamsMap],
|
|
||||||
// indices: IShaderIndices | null
|
|
||||||
// ) {
|
|
||||||
// switch (program.renderMode) {
|
|
||||||
// case RenderMode.Arrays: {
|
|
||||||
// const { mode, first, count } = param as DrawArraysParam;
|
|
||||||
// gl.drawArrays(mode, first, count);
|
|
||||||
// }
|
|
||||||
// case RenderMode.Elements: {
|
|
||||||
// if (!indices) return;
|
|
||||||
// const { mode, count, type, offset } =
|
|
||||||
// param as DrawElementsParam;
|
|
||||||
// gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, indices.data);
|
|
||||||
// gl.drawElements(mode, count, type, offset);
|
|
||||||
// }
|
|
||||||
// case RenderMode.ArraysInstanced: {
|
|
||||||
// const { mode, first, count, instanceCount } =
|
|
||||||
// param as DrawArraysInstancedParam;
|
|
||||||
// gl.drawArraysInstanced(mode, first, count, instanceCount);
|
|
||||||
// }
|
|
||||||
// case RenderMode.ElementsInstanced: {
|
|
||||||
// if (!indices) return;
|
|
||||||
// const {
|
|
||||||
// mode,
|
|
||||||
// count,
|
|
||||||
// type,
|
|
||||||
// offset,
|
|
||||||
// instanceCount: ins
|
|
||||||
// } = param as DrawElementsInstancedParam;
|
|
||||||
// gl.bindBuffer(gl.ELEMENT_ARRAY_BUFFER, indices.data);
|
|
||||||
// gl.drawElementsInstanced(mode, count, type, offset, ins);
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 在本着色器内部渲染之前执行的渲染,如果返回false,则表示不进行内部渲染,但依然会执行 {@link postDraw}。
|
|
||||||
// * 继承本类,并复写此方法即可实现前置渲染功能
|
|
||||||
// */
|
|
||||||
// protected preDraw(
|
|
||||||
// gl: WebGL2RenderingContext,
|
|
||||||
// program: ShaderProgram,
|
|
||||||
// param: DrawParamsMap[keyof DrawParamsMap],
|
|
||||||
// indices: IShaderIndices | null
|
|
||||||
// ): boolean {
|
|
||||||
// return true;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 在本着色器内部渲染之后执行的渲染,即使preDraw返回false,本函数也会执行
|
|
||||||
// * 继承本类,并复写此方法即可实现后置渲染功能
|
|
||||||
// */
|
|
||||||
// protected postDraw(
|
|
||||||
// gl: WebGL2RenderingContext,
|
|
||||||
// program: ShaderProgram,
|
|
||||||
// param: DrawParamsMap[keyof DrawParamsMap],
|
|
||||||
// indices: IShaderIndices | null
|
|
||||||
// ) {}
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 默认的准备函数
|
|
||||||
// * @returns 是否准备成功
|
|
||||||
// */
|
|
||||||
// protected defaultReady(): boolean {
|
|
||||||
// const program = this.program;
|
|
||||||
// if (!program) return false;
|
|
||||||
// const tex = program.getTexture('u_sampler');
|
|
||||||
// if (!tex) return false;
|
|
||||||
// const canvas = this.cache.canvas;
|
|
||||||
// if (tex.width === canvas.width && tex.height === canvas.height) {
|
|
||||||
// tex.sub(canvas, 0, 0, canvas.width, canvas.height);
|
|
||||||
// } else {
|
|
||||||
// tex.set(canvas);
|
|
||||||
// }
|
|
||||||
// return true;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 将画面渲染至帧缓冲
|
|
||||||
// * @param name 帧缓冲名称
|
|
||||||
// * @param texture 渲染至的纹理
|
|
||||||
// * @param clear 是否先清空画布再渲染
|
|
||||||
// */
|
|
||||||
// framebuffer(
|
|
||||||
// name: string,
|
|
||||||
// texture: IShaderTexture2D,
|
|
||||||
// clear: boolean = true
|
|
||||||
// ) {
|
|
||||||
// const gl = this.gl;
|
|
||||||
// const buffer = this.framebufferMap.get(name);
|
|
||||||
// const program = this.program;
|
|
||||||
// if (!gl || !buffer || !program) return;
|
|
||||||
// const indices = program.usingIndices;
|
|
||||||
// if (!indices) return;
|
|
||||||
// const param = program.getDrawParams(program.renderMode);
|
|
||||||
// if (!param) return;
|
|
||||||
|
|
||||||
// const tex = texture.texture;
|
|
||||||
// gl.bindTexture(gl.TEXTURE_2D, tex);
|
|
||||||
// gl.bindFramebuffer(gl.FRAMEBUFFER, buffer);
|
|
||||||
// if (clear) {
|
|
||||||
// gl.viewport(0, 0, this.canvas.width, this.canvas.height);
|
|
||||||
// gl.clearColor(0, 0, 0, 0);
|
|
||||||
// gl.clearDepth(1);
|
|
||||||
// gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
|
|
||||||
// }
|
|
||||||
// gl.framebufferTexture2D(
|
|
||||||
// gl.FRAMEBUFFER,
|
|
||||||
// gl.COLOR_ATTACHMENT0,
|
|
||||||
// gl.TEXTURE_2D,
|
|
||||||
// tex,
|
|
||||||
// 0
|
|
||||||
// );
|
|
||||||
// this.draw(gl, program, param, indices);
|
|
||||||
// gl.bindFramebuffer(gl.FRAMEBUFFER, null);
|
|
||||||
// gl.bindTexture(gl.TEXTURE_2D, null);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 创建一个帧缓冲对象
|
|
||||||
// * @param name 帧缓冲名称
|
|
||||||
// * @returns 是否创建成功
|
|
||||||
// */
|
|
||||||
// createFramebuffer(name: string): boolean {
|
|
||||||
// const gl = this.gl;
|
|
||||||
// if (!gl) return false;
|
|
||||||
// const buffer = gl.createFramebuffer();
|
|
||||||
// if (!buffer) return false;
|
|
||||||
// this.framebufferMap.set(name, buffer);
|
|
||||||
// return true;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 删除一个帧缓冲对象
|
|
||||||
// * @param name 帧缓冲名称
|
|
||||||
// * @returns 是否删除成功
|
|
||||||
// */
|
|
||||||
// deleteFramebuffer(name: string): boolean {
|
|
||||||
// const gl = this.gl;
|
|
||||||
// if (!gl) return false;
|
|
||||||
// const buffer = this.framebufferMap.get(name);
|
|
||||||
// if (!buffer) return false;
|
|
||||||
// gl.deleteFramebuffer(buffer);
|
|
||||||
// return this.framebufferMap.delete(name);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 切换着色器程序
|
|
||||||
// * @param program 着色器程序
|
|
||||||
// */
|
|
||||||
// useProgram(program: ShaderProgram) {
|
|
||||||
// if (!this.gl) return;
|
|
||||||
// if (program.element !== this) {
|
|
||||||
// logger.error(17);
|
|
||||||
// return;
|
|
||||||
// }
|
|
||||||
// if (this.program !== program) {
|
|
||||||
// this.program?.unload();
|
|
||||||
// this.program = program;
|
|
||||||
// this.gl.useProgram(program.program);
|
|
||||||
// program.load();
|
|
||||||
// }
|
|
||||||
// this.shaderRenderDirty = true;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 创建一个着色器程序
|
|
||||||
// * @param vs 顶点着色器,可选
|
|
||||||
// * @param fs 片元着色器,可选
|
|
||||||
// */
|
|
||||||
// createProgram(vs?: string, fs?: string) {
|
|
||||||
// const program = new ShaderProgram(this, vs, fs);
|
|
||||||
// this.programs.add(program);
|
|
||||||
// return program;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// /**
|
|
||||||
// * 删除一个着色器程序
|
|
||||||
// * @param program 要删除的着色器程序
|
|
||||||
// */
|
|
||||||
// deleteProgram(program: ShaderProgram) {
|
|
||||||
// if (program.element !== this) {
|
|
||||||
// logger.error(18);
|
|
||||||
// return;
|
|
||||||
// }
|
|
||||||
// program.destroy();
|
|
||||||
// this.programs.delete(program);
|
|
||||||
// }
|
|
||||||
|
|
||||||
// destroy(): void {
|
|
||||||
// this.programs.forEach(v => v.destroy());
|
|
||||||
// super.destroy();
|
|
||||||
// }
|
|
||||||
|
|
||||||
// // ----- 初始化部分
|
|
||||||
|
|
||||||
// private init() {
|
|
||||||
// const gl = this.gl;
|
|
||||||
// if (!gl) return;
|
|
||||||
// gl.enable(gl.DEPTH_TEST);
|
|
||||||
// gl.enable(gl.BLEND);
|
|
||||||
// gl.blendFunc(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA);
|
|
||||||
// gl.depthFunc(gl.LEQUAL);
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
|
||||||
export class ShaderProgram extends GL2Program {
|
export class ShaderProgram extends GL2Program {
|
||||||
protected readonly prefix: IGL2ProgramPrefix = SHADER_PREFIX;
|
protected readonly prefix: IGL2ProgramPrefix = SHADER_PREFIX;
|
||||||
|
|
||||||
@ -474,17 +87,6 @@ export class ShaderProgram extends GL2Program {
|
|||||||
if (!vs && !fs) {
|
if (!vs && !fs) {
|
||||||
this.modified = false;
|
this.modified = false;
|
||||||
}
|
}
|
||||||
this.setReady(() => {
|
|
||||||
const tex = this.getTexture('u_sampler');
|
|
||||||
if (!tex) return false;
|
|
||||||
const c = this.element.canvas;
|
|
||||||
if (tex.width === c.width && tex.height === c.height) {
|
|
||||||
tex.sub(c, 0, 0, c.width, c.height);
|
|
||||||
} else {
|
|
||||||
tex.set(c);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override compile() {
|
protected override compile() {
|
||||||
|
@ -101,6 +101,8 @@ export interface GameEvent {
|
|||||||
y: number,
|
y: number,
|
||||||
floorId: FloorIds
|
floorId: FloorIds
|
||||||
];
|
];
|
||||||
|
/** Emitted in lib/control.js */
|
||||||
|
replayStatus: [replaying: boolean];
|
||||||
}
|
}
|
||||||
|
|
||||||
export const hook = new EventEmitter<GameEvent>();
|
export const hook = new EventEmitter<GameEvent>();
|
||||||
|
2
src/types/control.d.ts
vendored
2
src/types/control.d.ts
vendored
@ -1163,6 +1163,8 @@ interface Control {
|
|||||||
frame?: number
|
frame?: number
|
||||||
): void;
|
): void;
|
||||||
_moveAction_popAutomaticRoute(): void;
|
_moveAction_popAutomaticRoute(): void;
|
||||||
|
_replay_SL(): void;
|
||||||
|
_replay_viewMap(): void;
|
||||||
}
|
}
|
||||||
|
|
||||||
declare const control: new () => Control;
|
declare const control: new () => Control;
|
||||||
|
Loading…
Reference in New Issue
Block a user