mirror of
https://gitee.com/dgflash/oops-framework.git
synced 2026-06-06 19:19:33 +08:00
UI框架添加自动释放窗口内存功能
显示对象GameComponent添加自动释放的资源API
This commit is contained in:
12
assets/res/common/texture/role.meta
Normal file
12
assets/res/common/texture/role.meta
Normal file
@@ -0,0 +1,12 @@
|
||||
{
|
||||
"ver": "1.1.0",
|
||||
"importer": "directory",
|
||||
"imported": true,
|
||||
"uuid": "d7a109d3-8659-4487-a915-2c38b3d88f58",
|
||||
"files": [],
|
||||
"subMetas": {},
|
||||
"userData": {
|
||||
"compressionType": {},
|
||||
"isRemoteBundle": {}
|
||||
}
|
||||
}
|
||||
@@ -2,12 +2,11 @@
|
||||
* @Author: dgflash
|
||||
* @Date: 2021-11-11 19:05:32
|
||||
* @LastEditors: dgflash
|
||||
* @LastEditTime: 2022-06-14 19:53:02
|
||||
* @LastEditTime: 2022-06-21 12:17:24
|
||||
*/
|
||||
|
||||
import { Component, Node, _decorator } from 'cc';
|
||||
import { EventDispatcher } from '../../../../../extensions/oops-framework/assets/core/common/event/EventDispatcher';
|
||||
import { ViewUtil } from '../../../../../extensions/oops-framework/assets/core/utils/ViewUtil';
|
||||
import { _decorator } from 'cc';
|
||||
import { GameComponent } from '../../../../../extensions/oops-framework/assets/core/game/GameComponent';
|
||||
import { ecs } from '../../../../../extensions/oops-framework/assets/libs/ecs/ECS';
|
||||
|
||||
const { ccclass, property } = _decorator;
|
||||
@@ -21,7 +20,7 @@ const { ccclass, property } = _decorator;
|
||||
* 4、对象管理的所有节点摊平,直接通过节点名获取cc.Node对象(节点名不能有重名)
|
||||
*/
|
||||
@ccclass('CCComp')
|
||||
export abstract class CCComp extends Component implements ecs.IComp {
|
||||
export abstract class CCComp extends GameComponent implements ecs.IComp {
|
||||
static tid: number = -1;
|
||||
static compName: string;
|
||||
|
||||
@@ -29,94 +28,4 @@ export abstract class CCComp extends Component implements ecs.IComp {
|
||||
ent!: ecs.Entity;
|
||||
|
||||
abstract reset(): void;
|
||||
|
||||
private nodes: Map<string, Node> = new Map();
|
||||
|
||||
/** 通过节点名获取预制上的节点,整个预制不能有重名节点 */
|
||||
get(name: string): Node | undefined {
|
||||
return this.nodes.get(name);
|
||||
}
|
||||
|
||||
onLoad() {
|
||||
ViewUtil.nodeTreeInfoLite(this.node, this.nodes);
|
||||
}
|
||||
|
||||
//#region 全局事件管理
|
||||
private _eventDispatcher: EventDispatcher | null = null;
|
||||
|
||||
public get eventDispatcher(): EventDispatcher {
|
||||
if (!this._eventDispatcher) {
|
||||
this._eventDispatcher = new EventDispatcher();
|
||||
}
|
||||
return this._eventDispatcher;
|
||||
}
|
||||
|
||||
// 事件是否绑定node的active
|
||||
private _isBindMessageActive: boolean = false;
|
||||
|
||||
/** 绑定node active属性,即只有active为true才会响应事件 */
|
||||
public bindMessageActive() {
|
||||
this._isBindMessageActive = true;
|
||||
}
|
||||
|
||||
/** 解绑node active属性,无论node是否可见都会响应事件 */
|
||||
public unbindMessageActive() {
|
||||
this._isBindMessageActive = false;
|
||||
}
|
||||
|
||||
/**
|
||||
* 注册全局事件
|
||||
* @param event(string) 事件名
|
||||
* @param listener(function) 处理事件的侦听器函数
|
||||
* @param thisObj(object) 侦听函数绑定的this对象
|
||||
*/
|
||||
public on(event: string, listener: Function, thisObj: any) {
|
||||
this.eventDispatcher.on(event, (event, args) => {
|
||||
if (!this.isValid) {
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.destroy();
|
||||
this._eventDispatcher = null;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (this._isBindMessageActive) {
|
||||
if (this.node.active) {
|
||||
listener.call(thisObj, event, args);
|
||||
}
|
||||
}
|
||||
else {
|
||||
listener.call(thisObj, event, args);
|
||||
}
|
||||
}, thisObj);
|
||||
}
|
||||
|
||||
/**
|
||||
* 移除全局事件
|
||||
* @param event(string) 事件名
|
||||
*/
|
||||
public off(event: string) {
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.off(event);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 触发全局事件
|
||||
* @param event(string) 事件名
|
||||
* @param arg(Array) 事件参数
|
||||
*/
|
||||
public dispatchEvent(event: string, arg: any = null) {
|
||||
this.eventDispatcher.dispatchEvent(event, arg);
|
||||
}
|
||||
|
||||
onDestroy() {
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.destroy();
|
||||
this._eventDispatcher = null;
|
||||
}
|
||||
|
||||
this.nodes.clear();
|
||||
}
|
||||
//#endregion
|
||||
}
|
||||
@@ -2,12 +2,10 @@
|
||||
* @Author: dgflash
|
||||
* @Date: 2021-11-11 19:05:32
|
||||
* @LastEditors: dgflash
|
||||
* @LastEditTime: 2022-06-14 19:53:11
|
||||
* @LastEditTime: 2022-06-21 12:17:51
|
||||
*/
|
||||
|
||||
import { Node, _decorator } from 'cc';
|
||||
import { EventDispatcher } from '../../../../../extensions/oops-framework/assets/core/common/event/EventDispatcher';
|
||||
import { ViewUtil } from '../../../../../extensions/oops-framework/assets/core/utils/ViewUtil';
|
||||
import { _decorator } from 'cc';
|
||||
import { ecs } from '../../../../../extensions/oops-framework/assets/libs/ecs/ECS';
|
||||
import VMParent from '../../../../../extensions/oops-framework/assets/libs/model-view/VMParent';
|
||||
|
||||
@@ -30,95 +28,4 @@ export abstract class CCVMParentComp extends VMParent implements ecs.IComp {
|
||||
ent!: ecs.Entity;
|
||||
|
||||
abstract reset(): void;
|
||||
|
||||
private nodes: Map<string, Node> = new Map();
|
||||
|
||||
/** 通过节点名获取预制上的节点,整个预制不能有重名节点 */
|
||||
get(name: string): Node | undefined {
|
||||
return this.nodes.get(name);
|
||||
}
|
||||
|
||||
onLoad() {
|
||||
ViewUtil.nodeTreeInfoLite(this.node, this.nodes);
|
||||
super.onLoad();
|
||||
}
|
||||
|
||||
//#region 全局事件管理
|
||||
private _eventDispatcher: EventDispatcher | null = null;
|
||||
|
||||
public get eventDispatcher(): EventDispatcher {
|
||||
if (!this._eventDispatcher) {
|
||||
this._eventDispatcher = new EventDispatcher();
|
||||
}
|
||||
return this._eventDispatcher;
|
||||
}
|
||||
|
||||
// 事件是否绑定node的active
|
||||
private _isBindMessageActive: boolean = false;
|
||||
|
||||
/** 绑定node active属性,即只有active为true才会响应事件 */
|
||||
public bindMessageActive() {
|
||||
this._isBindMessageActive = true;
|
||||
}
|
||||
|
||||
/** 解绑node active属性,无论node是否可见都会响应事件 */
|
||||
public unbindMessageActive() {
|
||||
this._isBindMessageActive = false;
|
||||
}
|
||||
|
||||
/**
|
||||
* 注册全局事件
|
||||
* @param event(string) 事件名
|
||||
* @param listener(function) 处理事件的侦听器函数
|
||||
* @param thisObj(object) 侦听函数绑定的this对象
|
||||
*/
|
||||
public on(event: string, listener: Function, thisObj: any) {
|
||||
this.eventDispatcher.on(event, (event, args) => {
|
||||
if (!this.isValid) {
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.destroy();
|
||||
this._eventDispatcher = null;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (this._isBindMessageActive) {
|
||||
if (this.node.active) {
|
||||
listener.call(thisObj, event, args);
|
||||
}
|
||||
}
|
||||
else {
|
||||
listener.call(thisObj, event, args);
|
||||
}
|
||||
}, thisObj);
|
||||
}
|
||||
|
||||
/**
|
||||
* 移除全局事件
|
||||
* @param event(string) 事件名
|
||||
*/
|
||||
public off(event: string) {
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.off(event);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 触发全局事件
|
||||
* @param event(string) 事件名
|
||||
* @param arg(Array) 事件参数
|
||||
*/
|
||||
public dispatchEvent(event: string, arg: any = null) {
|
||||
this.eventDispatcher.dispatchEvent(event, arg);
|
||||
}
|
||||
|
||||
onDestroy() {
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.destroy();
|
||||
this._eventDispatcher = null;
|
||||
}
|
||||
|
||||
this.nodes.clear();
|
||||
}
|
||||
//#endregion
|
||||
}
|
||||
@@ -2,7 +2,7 @@
|
||||
* @Author: dgflash
|
||||
* @Date: 2021-07-03 16:13:17
|
||||
* @LastEditors: dgflash
|
||||
* @LastEditTime: 2022-06-17 16:32:26
|
||||
* @LastEditTime: 2022-06-21 15:31:05
|
||||
*/
|
||||
import { Component, dynamicAtlasManager, EventTouch, _decorator } from "cc";
|
||||
import { tips } from "../common/prompt/TipsManager";
|
||||
@@ -10,6 +10,7 @@ import { oops } from "../../../../extensions/oops-framework/assets/core/Oops";
|
||||
import { UIID } from "../common/config/GameUIConfig";
|
||||
import { SingletonModuleComp } from "../common/ecs/SingletonModuleComp";
|
||||
import { ecs } from "../../../../extensions/oops-framework/assets/libs/ecs/ECS";
|
||||
import { resLoader } from "../../../../extensions/oops-framework/assets/core/common/loader/ResLoader";
|
||||
|
||||
const { ccclass, property } = _decorator;
|
||||
// 视图层实体是空的
|
||||
@@ -26,6 +27,10 @@ export class Demo extends Component {
|
||||
}
|
||||
|
||||
start() {
|
||||
// 释放加载界面资源
|
||||
console.log("内存中现有资源");
|
||||
resLoader.dump();
|
||||
|
||||
console.log("当前图集数量", dynamicAtlasManager.atlasCount);
|
||||
console.log("可以创建的最大图集数量", dynamicAtlasManager.maxAtlasCount);
|
||||
console.log("创建的图集的宽高", dynamicAtlasManager.textureSize);
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* @Author: dgflash
|
||||
* @Date: 2021-07-03 16:13:17
|
||||
* @LastEditors: dgflash
|
||||
* @LastEditTime: 2022-06-14 19:55:31
|
||||
* @LastEditTime: 2022-06-21 15:30:55
|
||||
*/
|
||||
import { _decorator } from "cc";
|
||||
import { resLoader } from "../../../../../extensions/oops-framework/assets/core/common/loader/ResLoader";
|
||||
@@ -44,16 +44,13 @@ export class LoadingViewComp extends CCVMParentComp {
|
||||
// 关闭加载界面
|
||||
oops.gui.remove(UIID.Loading);
|
||||
|
||||
// 释放加载界面资源
|
||||
resLoader.releaseDir("loading");
|
||||
|
||||
// 打开游戏主界面(自定义逻辑)
|
||||
oops.gui.open(UIID.Demo);
|
||||
}
|
||||
|
||||
start() {
|
||||
// if (!sys.isNative) {
|
||||
this.enter();
|
||||
this.enter();
|
||||
// }
|
||||
}
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { Asset, AssetManager, assetManager, Constructor, error, js, resources, __private } from "cc";
|
||||
import { Asset, AssetManager, assetManager, Constructor, error, js, Prefab, resources, __private } from "cc";
|
||||
|
||||
export type ProgressCallback = __private._cocos_core_asset_manager_shared__ProgressCallback;
|
||||
export type CompleteCallback<T = any> = __private._cocos_core_asset_manager_shared__CompleteCallbackWithData;
|
||||
@@ -165,17 +165,23 @@ export default class ResLoader {
|
||||
assetManager.loadRemote<T>(url, options, onComplete);
|
||||
}
|
||||
|
||||
/** 通过资源相对路径释放资源 */
|
||||
public release(path: string, bundleName: string = "resources") {
|
||||
var bundle = assetManager.getBundle(bundleName);
|
||||
bundle?.release(path);
|
||||
if (bundle) {
|
||||
var asset = bundle.get(path);
|
||||
if (asset) {
|
||||
this.releasePrefabtDepsRecursively(asset._uuid);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** 通过相对文件夹路径删除所有文件夹中资源 */
|
||||
public releaseDir(path: string, bundleName: string = "resources") {
|
||||
var bundle: AssetManager.Bundle | null = assetManager.getBundle(bundleName);
|
||||
var infos = bundle?.getDirWithPath(path);
|
||||
infos?.map(function (info) {
|
||||
var asset = assetManager.assets.get(info.uuid)!;
|
||||
assetManager.releaseAsset(asset);
|
||||
infos?.map((info) => {
|
||||
this.releasePrefabtDepsRecursively(info.uuid);
|
||||
});
|
||||
|
||||
if (path == "" && bundleName != "resources" && bundle) {
|
||||
@@ -183,6 +189,19 @@ export default class ResLoader {
|
||||
}
|
||||
}
|
||||
|
||||
/** 释放预制依赖资源 */
|
||||
private releasePrefabtDepsRecursively(uuid: string) {
|
||||
var asset = assetManager.assets.get(uuid)!;
|
||||
if (asset instanceof Prefab) {
|
||||
var uuids: string[] = assetManager.dependUtil.getDepsRecursively(uuid)!;
|
||||
uuids.forEach(uuid => {
|
||||
assetManager.assets.get(uuid)!.decRef();
|
||||
});
|
||||
}
|
||||
assetManager.releaseAsset(asset);
|
||||
}
|
||||
|
||||
/** 获取资源 */
|
||||
public get<T extends Asset>(path: string, type?: __private._cocos_core_asset_manager_shared__AssetType<T> | null, bundleName: string = "resources"): T | null {
|
||||
var bundle: AssetManager.Bundle | null = assetManager.getBundle(bundleName);
|
||||
return bundle!.get(path, type);
|
||||
@@ -190,7 +209,7 @@ export default class ResLoader {
|
||||
|
||||
public dump() {
|
||||
assetManager.assets.forEach((value: Asset, key: string) => {
|
||||
console.log(key);
|
||||
console.log(assetManager.assets.get(key));
|
||||
})
|
||||
console.log(`当前资源总数:${assetManager.assets.count}`);
|
||||
}
|
||||
|
||||
@@ -2,13 +2,15 @@
|
||||
* @Author: dgflash
|
||||
* @Date: 2022-04-14 17:08:01
|
||||
* @LastEditors: dgflash
|
||||
* @LastEditTime: 2022-04-14 19:07:39
|
||||
* @LastEditTime: 2022-06-21 15:30:04
|
||||
*/
|
||||
import { Component, _decorator } from "cc";
|
||||
import { Asset, Component, isValid, Node, _decorator } from "cc";
|
||||
import { EventDispatcher } from "../common/event/EventDispatcher";
|
||||
import { ViewUtil } from "../utils/ViewUtil";
|
||||
|
||||
const { ccclass } = _decorator;
|
||||
|
||||
/** 游戏显示对象组件模板 */
|
||||
@ccclass("GameComponent")
|
||||
export class GameComponent extends Component {
|
||||
private _eventDispatcher: EventDispatcher | null = null;
|
||||
@@ -33,13 +35,42 @@ export class GameComponent extends Component {
|
||||
this._isBindMessageActive = false;
|
||||
}
|
||||
|
||||
/** 自动释放资源 */
|
||||
private dynamicsAssets: Asset[] = [];
|
||||
/** 摊平的节点集合(不能重名) */
|
||||
private nodes: Map<string, Node> = new Map();
|
||||
|
||||
/** 通过节点名获取预制上的节点,整个预制不能有重名节点 */
|
||||
get(name: string): Node | undefined {
|
||||
return this.nodes.get(name);
|
||||
}
|
||||
|
||||
onLoad() {
|
||||
ViewUtil.nodeTreeInfoLite(this.node, this.nodes);
|
||||
}
|
||||
|
||||
/** 添加自动释放的资源 */
|
||||
addAutoReleaseAsset(asset: Asset) {
|
||||
if (isValid(asset)) {
|
||||
asset.addRef();
|
||||
this.dynamicsAssets.push(asset);
|
||||
}
|
||||
}
|
||||
|
||||
/** 添加自动释放的资源数组 */
|
||||
addAutoReleaseAssets(assets: Asset[]) {
|
||||
assets.forEach(asset => {
|
||||
this.addAutoReleaseAsset(asset);
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 注册全局事件
|
||||
* @param event(string) 事件名
|
||||
* @param listener(function) 处理事件的侦听器函数
|
||||
* @param thisObj(object) 侦听函数绑定的this对象
|
||||
*/
|
||||
public on(event: string, listener: Function, thisObj: any) {
|
||||
on(event: string, listener: Function, thisObj: any) {
|
||||
this.eventDispatcher.on(event, (event, args) => {
|
||||
if (!this.isValid) {
|
||||
if (this._eventDispatcher) {
|
||||
@@ -64,7 +95,7 @@ export class GameComponent extends Component {
|
||||
* 移除全局事件
|
||||
* @param event(string) 事件名
|
||||
*/
|
||||
public off(event: string) {
|
||||
off(event: string) {
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.off(event);
|
||||
}
|
||||
@@ -75,14 +106,24 @@ export class GameComponent extends Component {
|
||||
* @param event(string) 事件名
|
||||
* @param arg(Array) 事件参数
|
||||
*/
|
||||
public dispatchEvent(event: string, arg = null) {
|
||||
dispatchEvent(event: string, arg = null) {
|
||||
this.eventDispatcher.dispatchEvent(event, arg);
|
||||
}
|
||||
|
||||
onDestroy() {
|
||||
protected onDestroy() {
|
||||
// 释放消息对象
|
||||
if (this._eventDispatcher) {
|
||||
this._eventDispatcher.destroy();
|
||||
this._eventDispatcher = null;
|
||||
}
|
||||
|
||||
// 节点引用数据清除
|
||||
this.nodes.clear();
|
||||
|
||||
// 自动释放资源
|
||||
this.dynamicsAssets.forEach(asset => {
|
||||
asset.decRef();
|
||||
});
|
||||
this.dynamicsAssets.splice(0, this.dynamicsAssets.length);
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
import { Component, Node, _decorator } from "cc";
|
||||
import { resLoader } from "../../common/loader/ResLoader";
|
||||
import { ViewParams } from "./Defines";
|
||||
|
||||
const { ccclass } = _decorator;
|
||||
@@ -48,10 +49,15 @@ export class DelegateComponent extends Component {
|
||||
viewParams.callbacks!.onRemoved(this.node, viewParams.params);
|
||||
}
|
||||
|
||||
if (isDestroy)
|
||||
if (isDestroy) {
|
||||
this.node.destroy();
|
||||
else
|
||||
|
||||
// 释放界面相关资源
|
||||
resLoader.release(viewParams.prefabPath);
|
||||
}
|
||||
else {
|
||||
this.node.removeFromParent();
|
||||
}
|
||||
}
|
||||
|
||||
onDestroy() {
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import { Component, _decorator } from 'cc';
|
||||
import { GameComponent } from '../../core/game/GameComponent';
|
||||
import { VM } from './ViewModel';
|
||||
|
||||
const { ccclass, help, executionOrder } = _decorator;
|
||||
@@ -13,7 +14,7 @@ const { ccclass, help, executionOrder } = _decorator;
|
||||
@ccclass
|
||||
@executionOrder(-1)
|
||||
@help('https://github.com/wsssheep/cocos_creator_mvvm_tools/blob/master/docs/VMParent.md')
|
||||
export default class VMParent extends Component {
|
||||
export default class VMParent extends GameComponent {
|
||||
/** 绑定的标签,可以通过这个tag 获取 当前的 vm 实例 */
|
||||
protected tag: string = '_temp';
|
||||
|
||||
@@ -33,7 +34,7 @@ export default class VMParent extends Component {
|
||||
* ```
|
||||
*
|
||||
*/
|
||||
protected onLoad() {
|
||||
onLoad() {
|
||||
if (this.data == null) return;
|
||||
this.tag = '_temp' + '<' + this.node.uuid.replace('.', '') + '>';
|
||||
VM.add(this.data, this.tag);
|
||||
@@ -48,6 +49,8 @@ export default class VMParent extends Component {
|
||||
// console.groupEnd()
|
||||
|
||||
this.onBind();
|
||||
|
||||
super.onLoad();
|
||||
}
|
||||
|
||||
/**在 onLoad 完成 和 start() 之前调用,你可以在这里进行初始化数据等操作 */
|
||||
@@ -111,8 +114,11 @@ export default class VMParent extends Component {
|
||||
*/
|
||||
protected onDestroy() {
|
||||
this.onUnBind();
|
||||
//解除全部引用
|
||||
|
||||
// 解除全部引用
|
||||
VM.remove(this.tag);
|
||||
this.data = null;
|
||||
|
||||
super.onDestroy();
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user