当前位置: 首页 > news >正文

【cocos2dx】记录问题,粒子不会通过setOpacity调整整体透明度

目录

  • 前言
  • 探究问题
    • setOpacity
    • updateColor
  • 解决方案
  • 推送
  • 结语

前言

粒子系统是非常方便使用的一个功能,有时候能节省大量的资源且保有很不错的效果,在使用cocos的粒子系统的时候发现一个问题,粒子只能通过参数内startColor和endColor来控制粒子开始到结束的透明度,通过设置粒子setOpacity或者父节点的透明度,粒子并不会有任何变化,透明没有变化

探究问题

setOpacity


class CC_DLL ParticleSystemQuad : public ParticleSystem

class CC_DLL ParticleSystem : public Node, public TextureProtocol, public PlayableProtocol

我们首先查看了粒子的类CCParticleSystemQuad和其父类CCParticleSystem,我们发现都没有setOpacity,而CCParticleSystem方法是继承Node的,所以直接用的是Node的setOpacity方法

  • CCNode.cpp
void Node::setOpacity(GLubyte opacity)
{
    _displayedOpacity = _realOpacity = opacity;
    
    updateCascadeOpacity();
}

void Node::updateDisplayedOpacity(GLubyte parentOpacity)
{
    _displayedOpacity = _realOpacity * parentOpacity/255.0;
    updateColor();
    
    if (_cascadeOpacityEnabled)
    {
        for(const auto& child : _children)
        {
            child->updateDisplayedOpacity(_displayedOpacity);
        }
    }
}
  • CCNode.h
virtual void updateColor() {}

首先我们找到setOpacity干了什么,通过代码我们发现setOpacity给_displayedOpacity设置了我们传入的值,然后调用了updateCascadeOpacity方法
在在updateCascadeOpacity方法内调用了updateColor方法内调用了updateColor方法,并且遍历执行了子节点的updateCascadeOpacity方法
updateColor方法是一个空的虚函数,用于子类被继承

updateColor

  • CCLayer
void LayerColor::updateColor()
{
    for( unsigned int i=0; i < 4; i++ )
    {
        _squareColors[i].r = _displayedColor.r / 255.0f;
        _squareColors[i].g = _displayedColor.g / 255.0f;
        _squareColors[i].b = _displayedColor.b / 255.0f;
        _squareColors[i].a = _displayedOpacity / 255.0f;
    }
}
  • CCLabel
void Label::updateColor()
{
    if (_batchNodes.empty())
    {
        return;
    }

    Color4B color4( _displayedColor.r, _displayedColor.g, _displayedColor.b, _displayedOpacity );

    // special opacity for premultiplied textures
    if (_isOpacityModifyRGB)
    {
        color4.r *= _displayedOpacity/255.0f;
        color4.g *= _displayedOpacity/255.0f;
        color4.b *= _displayedOpacity/255.0f;
    }

    cocos2d::TextureAtlas* textureAtlas;
    V3F_C4B_T2F_Quad *quads;
    for (auto&& batchNode:_batchNodes)
    {
        textureAtlas = batchNode->getTextureAtlas();
        quads = textureAtlas->getQuads();
        auto count = textureAtlas->getTotalQuads();

        for (int index = 0; index < count; ++index)
        {
            quads[index].bl.colors = color4;
            quads[index].br.colors = color4;
            quads[index].tl.colors = color4;
            quads[index].tr.colors = color4;
            textureAtlas->updateQuad(&quads[index], index);
        }
    }
}

我们在CCParticleSystemQuad和其父类CCParticleSystem内都没有发现对_displayedOpacity的运用或者重写的updateColor,所以我们找一些其他组件来参考一下别的怎么写的
从其他参考后,大致能看出来了,在最终渲染前,_displayedOpacity会乘上四边形(quads)的四个colors(bl、br、tl、tr)

解决方案

在参考其他代码后,可以看出粒子之所以没有跟随自己节点或父节点的透明度变化,主要是因为_displayedOpacity参数没有再设置颜色的时候用上,所以解决方案就很容易了,在设置颜色的时候预乘上_displayedOpacity就好了

  • 旧代码
void ParticleSystemQuad::updateParticleQuads()
{
    ......   
    //set color
    if(_opacityModifyRGB)
    {
        ......
        for (int i = 0; i < _particleCount; ++i,++quad,++r,++g,++b,++a)
        {
            GLubyte colorR = *r * *a * 255;
            GLubyte colorG = *g * *a * 255;
            GLubyte colorB = *b * *a * 255;
            GLubyte colorA = *a * 255;
            quad->bl.colors.set(colorR, colorG, colorB, colorA);
            quad->br.colors.set(colorR, colorG, colorB, colorA);
            quad->tl.colors.set(colorR, colorG, colorB, colorA);
            quad->tr.colors.set(colorR, colorG, colorB, colorA);
        }
    }
    else
    {
       ......
    }
}
  • 新代码
void ParticleSystemQuad::updateParticleQuads()
{
    ......   
    //set color
    if(_opacityModifyRGB)
    {
        ......
        for (int i = 0; i < _particleCount; ++i,++quad,++r,++g,++b,++a)
        {
            GLubyte colorR = *r * *a * _displayedOpacity;
            GLubyte colorG = *g * *a * _displayedOpacity;
            GLubyte colorB = *b * *a * _displayedOpacity;
            GLubyte colorA = *a * _displayedOpacity;
            quad->bl.colors.set(colorR, colorG, colorB, colorA);
            quad->br.colors.set(colorR, colorG, colorB, colorA);
            quad->tl.colors.set(colorR, colorG, colorB, colorA);
            quad->tr.colors.set(colorR, colorG, colorB, colorA);
        }
    }
    else
    {
       ......
    }
}

如此修改,在opacityModifyRGB被设置为true的情况下,整体粒子透明度就会随当前节点或父节点的透明度变化而变化

推送

  • Github
https://github.com/KingSun5

结语

若是觉得博主的文章写的不错,不妨关注一下博主,点赞一下博文,另博主能力有限,若文中有出现什么错误的地方,欢迎各位评论指摘。
QQ交流群:806091680(Chinar)
该群为CSDN博主Chinar所创,推荐一下!我也在群里!
本文属于原创文章,转载请著名作者出处并置顶!!

相关文章:

  • Docker部署可能遇到的问题
  • Java配置41-搭建Kafka服务器
  • VSCode中ESLint插件修复+配置教程
  • 来!PyFlink 作业的多种部署模式
  • 电脑重装系统后Win11安全中心无法打开如何解决
  • ue4打包出现问题解决[Callstack] 0x00007ffa47e6474c KERNELBASE.dll!UnknownFunction []
  • 【Matlab】状态空间模型的极点配置法 place() 函数
  • Chrome常用插件收集整理
  • [车联网安全自学篇] Android安全之APK内存敏感信息泄露挖掘【静态分析】
  • cpacr_el1等特殊寄存器
  • 代码层走进“百万级”分布式ID设计
  • 开源众包-项目大厅数据爬取
  • 数仓工具—Hive源码之SQL解析Antlr进阶(8)
  • 家用烘干机家电出口欧盟CE认证资料您是否准备好了
  • Ant Design Pro of Vue 构建打包后使用 Nginx 发布,API 请求报 404 错
  • 分享一款快速APP功能测试工具
  • 【MySQL经典案例分析】 Waiting for table metadata lock
  • 【Under-the-hood-ReactJS-Part0】React源码解读
  • go append函数以及写入
  • MySQL QA
  • open-falcon 开发笔记(一):从零开始搭建虚拟服务器和监测环境
  • PHP 程序员也能做的 Java 开发 30分钟使用 netty 轻松打造一个高性能 websocket 服务...
  • Python学习之路16-使用API
  • Spring Boot MyBatis配置多种数据库
  • tab.js分享及浏览器兼容性问题汇总
  • thinkphp5.1 easywechat4 微信第三方开放平台
  • 等保2.0 | 几维安全发布等保检测、等保加固专版 加速企业等保合规
  • 试着探索高并发下的系统架构面貌
  • - 转 Ext2.0 form使用实例
  • 哈罗单车融资几十亿元,蚂蚁金服与春华资本加持 ...
  • ​低代码平台的核心价值与优势
  • #{}和${}的区别?
  • #我与Java虚拟机的故事#连载07:我放弃了对JVM的进一步学习
  • (arch)linux 转换文件编码格式
  • (八)Spring源码解析:Spring MVC
  • (过滤器)Filter和(监听器)listener
  • (算法)Travel Information Center
  • (一)C语言之入门:使用Visual Studio Community 2022运行hello world
  • (转)详解PHP处理密码的几种方式
  • .NET CF命令行调试器MDbg入门(二) 设备模拟器
  • .Net Web项目创建比较不错的参考文章
  • .net 中viewstate的原理和使用
  • /ThinkPHP/Library/Think/Storage/Driver/File.class.php  LINE: 48
  • /usr/local/nginx/logs/nginx.pid failed (2: No such file or directory)
  • ??eclipse的安装配置问题!??
  • @ModelAttribute使用详解
  • [14]内置对象
  • [Android]创建TabBar
  • [Android]使用Git将项目提交到GitHub
  • [AutoSAR 存储] 汽车智能座舱的存储需求
  • [CF543A]/[CF544C]Writing Code
  • [CodeForces-759D]Bacterial Melee
  • [CSS]中子元素在父元素中居中
  • [DNS网络] 网页无法打开、显示不全、加载卡顿缓慢 | 解决方案
  • [linux] GFLOPS和TFLOPS的换算