egret-core
egret-core copied to clipboard
Egret Engine2D 5.3.5以后换肤,Canvas下无法渲染Dragonbons中使用网格的图片
问题描述
我换肤方案是使用的官方提供的替换slot图片的方案,发现在Canvas下无法渲染Dragonbons中使用网格的图片;
//封装简单的换肤函数
/**
* 替换插槽
* @param slotName 插槽名称 原材料
* @param textureName 图片名 xxx_png
* @param 偏移量
*/
public setNewSlot( slotName:string, textureName:string ,offsetX:number=0, offsetY:number=0){
var slot:dragonBones.Slot = this.armatureDisplay.armature.getSlot(slotName);
var b:egret.Bitmap = new egret.Bitmap();
b.texture = RES.getRes(textureName);
b.x = slot.display.x;
b.y = slot.display.y;
b.anchorOffsetX = b.width/2 + offsetX;
b.anchorOffsetY = b.height/2 + offsetY;
slot.setDisplay( b );
}
问题追踪
通过追溯源码发现,换肤后会打断龙骨本身的批处理,会执行disableBatch()函数,之后Dragonbons的渲染流程会发生变化,
上面是批处理和非批处理的渲染流程,只是针对与网格Mesh图片,追溯源码后发现,打断批处理后之所以渲染不出来是因为图片的matrix属性丢失;
matrix属性丢失原因
原因是getRenderNode()的时候调用了cleanBeforeRender(),此处matrix被置为空;
/**
* 在显示对象的$updateRenderNode()方法被调用前,自动清空自身的drawData数据。
*/
MeshNode.prototype.cleanBeforeRender = function () {
_super.prototype.cleanBeforeRender.call(this);
this.image = null;
this.matrix = null;
};
而在renderMesh()中有这样一段代码,如果m为空,则无法调用context.translate,移动canvas画笔,因此绘制不出来;
if (m) {
context.save();
saved = true;
if (context.$offsetX != 0 || context.$offsetY != 0) {
context.translate(context.$offsetX, context.$offsetY);
offsetX = context.$offsetX;
offsetY = context.$offsetY;
context.$offsetX = context.$offsetY = 0;
}
context.transform(m.a, m.b, m.c, m.d, m.tx, m.ty);
}
我的解决方案
修改renderMesh()
context.save();
saved = true;
if (context.$offsetX != 0 || context.$offsetY != 0) {
context.translate(context.$offsetX, context.$offsetY);
offsetX = context.$offsetX;
offsetY = context.$offsetY;
context.$offsetX = context.$offsetY = 0;
}
m && context.transform(m.a, m.b, m.c, m.d, m.tx, m.ty);
麻烦看看这样解决是否正确,盼复。
我在webgl下也遇到这个问题,新版的龙骨更改了渲染流程,新增了frameData这个数据,导致空的slot设置display的时候,根本不起效,因为没有对应的frameData,暂时没有解决方法,只能用旧版的龙骨