kwin- 插件加载绘制流程

1. 配置文件的作用具体是做什么的?

        相当于用户强制设置了特效的开关,对于没有写在配置文件里的特效,会检测默认加载值,确定是否加载。写在了文件里的会根据返回的值,来加载特效。

2. 为什么配置文件没有写,也可以加载插件?

        之所以配置文件没有写,特效也可以加载,是因为插件加载时,会先检测配置文件的内容,之后才会走默认加载逻辑,具体如下代码

LoadEffectFlags AbstractEffectLoader::readConfig(const QString &effectName, bool defaultValue) const
{Q_ASSERT(m_config);KConfigGroup plugins(m_config, QStringLiteral("Plugins"));const QString key = effectName + QStringLiteral("Enabled");// 如果配置文件内写了该插件if (plugins.hasKey(key)) {// we have a key in the config, so read the enabled state//如果键存在,读取其值。如果键不存在,使用 defaultValue 作为默认值。const bool load = plugins.readEntry(key, defaultValue);// 如果读取到的值(或默认值)为 true,返回 LoadEffectFlags,表示加载效果;否则,返回一个空的 LoadEffectFlags 对象。return load ? LoadEffectFlags(LoadEffectFlag::Load) : LoadEffectFlags();}// we don't have a key, so we just use the enabled by default value/*如果配置中没有找到该键,并且 defaultValue 为 true,返回 LoadEffectFlag::Load | LoadEffectFlag::CheckDefaultFunction,表示需要加载效果并调用默认检查函数;否则,返回一个空的 LoadEffectFlags 对象。*/if (defaultValue) {return LoadEffectFlag::Load | LoadEffectFlag::CheckDefaultFunction;}return LoadEffectFlags();
}

文件说明:

  1. src/effectloader.h
    1. AbstractEffectLoader类

                描述效果加载器如何工作的接口。 AbstractEffectLoader指定了具体加载器必须实现的方法以及这些方法的预期行为。同时,它也为外部世界(即EffectsHandlerImpl)提供了一个接口。

使用这种抽象是因为有多种类型的效果需要加载:

  •  内置效果(Built-In Effects)
  • 脚本效果(Scripted Effects)
  • 二进制插件效果(Binary Plugin Effects)

        由于需要同时查询不同的存储库,因此使用同一个效果加载器来服务所有这些类型相当复杂。因此,想法是为每种类型提供一个实现,并有一个实现利用所有这些并组合加载过程。

/**
* @brief 同步加载给定名称@p name的效果。
*
* 加载效果时,不检查任何配置值或效果提供的任何默认启用函数。
*
* 加载器应执行以下检查:
* 如果效果已经加载,则不应再次加载。因此,加载器应跟踪已加载的效果以及其中哪些已被销毁。
* 加载器应检查效果是否受支持。如果效果表示不受支持,则不应加载。
*
* 如果效果成功加载,则必须发出effectLoaded(KWin::Effect,const QString&)信号。否则,加载器的用户无法获取加载的效果。
* 它不返回效果,因为queryAndLoadAll()是异步工作的,因此加载器的用户应为异步加载做好准备。
* @param name 要加载的效果的内部名称
* @return bool 如果效果可以加载,则返回@c true;如果出错,则返回@c false
* @see queryAndLoadAll()
* @see effectLoaded(KWin::Effect,const QString&)
*/virtual bool loadEffect(const QString &name) = 0;/**
* @brief 效果加载器应查询其存储中的所有可用效果并尝试加载它们。
*
* 效果加载器应以高度异步的方式执行此操作。如果需要进行输入/输出(IO)操作,则应在后台线程中执行,并使用队列来加载效果。
* 加载器应确保在一个事件循环中不加载超过一个效果。
* 加载效果必须在合成器线程中执行,因此会阻塞合成器。因此,在加载一个效果后,应先处理所有事件,以便合成器在需要时可以进行绘制传递。
* 为了简化此操作,可以使用EffectLoadQueue。这需要添加另一个具有自定义加载器特定类型以引用效果和LoadEffectFlags的loadEffect方法。
*
* 必须通过读取配置(readConfig())来确定LoadEffectFlags。如果设置了加载标志,则可以继续加载,并应用来自loadEffect(const QString &)的所有检查。
* 此外,如果设置了CheckDefaultFunction标志,并且效果提供了这样的方法,则应查询该方法以确定效果是否默认启用。
* 如果这样的方法返回@c false,则不应加载效果。如果效果没有提供在运行时查询是否默认启用的方法,则可以忽略该标志。
*
* 如果效果成功加载,则必须发出effectLoaded(KWin::Effect,const QString&)信号。
* @see loadEffect(const QString &)
* @see effectLoaded(KWin::Effect,const QString&)
*/
virtual void queryAndLoadAll() = 0;/**
* @brief 检查由@p effectName标识的效果的配置。
*
* 对于每个效果,可能存在一个名为"<effectName>Enabled"的键。
* 如果存在这样的键,并且其值为@c true,则返回的标志将包含Load。如果键不存在,则@p defaultValue确定是否应加载效果。
* 如果@p defaultValue的值为@c true,则返回Load | CheckDefaultFunction,表示应加载效果并检查其默认启用函数;如果为@c false,则不返回任何加载标志。
*
* @param effectName 在配置中要查找的效果的名称
* @param defaultValue 效果是否默认启用
* @returns 标志,指示是否应加载效果以及如何加载效果
*/LoadEffectFlags readConfig(const QString &effectName, bool defaultValue) const;
  • AbstractEffectLoadQueue类

        这个类用于帮助排队加载特效(Effects)。

        加载一个特效必须在合成线程(compositor thread)中进行,因此在加载特效的过程中,合成器会被阻塞。为了避免合成器在加载所有特效的过程中被阻塞多个帧,我们需要将特效的加载过程排队处理。通过通过一个 QueuedConnection 调用 dequeue() 插槽(slot),队列可以确保在加载两个特效之间处理事件,从而避免合成器被阻塞。

        由于它需要是一个插槽(slot),队列必须继承自 QObject,但同时它也需要是模板类,因为加载特效的信息是特效加载器(Effect Loader)特有的。因此,有一个 AbstractEffectLoadQueue 提供纯虚函数插槽(slots),以及一个继承自 AbstractEffectLoadQueue 的模板类 EffectLoadQueue。

        队列的操作类似于普通队列,提供了 enqueue(入队)和 scheduleDequeue(计划出队)而不是直接的 dequeue(出队)

  • src/libkwineffects/kwineffects.h

        包含所有特效的基类:Effect

        所有KWin效果的基础类, 这是所有效果的基础类。通过重新实现此类的虚拟方法,您可以自定义窗口的绘制方式。这些虚拟方法用于绘制,并需要为实现自定义绘制而实现。为了响应状态变化(例如窗口关闭),效果应该为EffectsHandler发出的信号提供槽函数。

  • 链式调用

        此类的大多数方法都是以链式方式调用的。这意味着当效果A和B都处于活动状态时,首先会调用A::paintWindow(),然后在该方法内部(尽管是间接地)会调用B::paintWindow()。为了实现这一点,您需要从每个这样的方法中确保调用EffectsHandler类的对应方法(使用effects指针):

void MyEffect::postPaintScreen()
{// 在此处执行您自己的处理...// 调用对应的EffectsHandler方法effects->postPaintScreen();// effects指针指向全局的EffectsHandler对象,您可以使用它与窗口进行交互。
}
  • 绘制阶段

        窗口的绘制分为三个阶段:

        首先,是预绘制阶段,在此阶段,您可以指定窗口的绘制方式,例如它们将是半透明的或经过变换的。

        其次,是绘制阶段。在此阶段,实际进行绘制。您可以更改窗口的属性,如透明度,并对它们应用变换。您还可以自己在屏幕上绘制内容。

        最后,是后绘制阶段。在此阶段,您可以标记窗口、窗口的一部分甚至整个屏幕以进行重绘,从而创建动画。

        对于每个阶段,都有Screen()和Window()方法。窗口方法会为每个窗口调用,而屏幕方法通常只调用一次。

OpenGL

        如果EffectsHandler::isOpenGLCompositing()返回true,则效果可以使用OpenGL。当执行effect内部的代码时,OpenGL上下文可能并不总是当前的。框架确保在创建、销毁或重新配置效果以及绘制阶段期间,OpenGL上下文是当前的。所有具有当前OpenGL上下文的虚拟方法都有文档说明。如果要在绘制阶段之外执行OpenGL代码,例如响应全局快捷键,那么效果的任务就是使OpenGL上下文成为当前的:

effects->makeOpenGLContextCurrent();

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/55793.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【自用】王道文件管理强化笔记

文章目录 操作系统引导:磁盘初始化文件打开过程角度1文件的打开过程角度2 内存映射的文件访问 操作系统引导: ①CPU从一个特定主存地址开始&#xff0c;取指令&#xff0c;执行ROM中的引导程序(先进行硬件自检&#xff0c;再开机) ②)将磁盘的第一块–主引导记录读入内存&…

【Ubuntu】git

文章目录 1.配置SSH key2. 基础知识操作命令1分支branch 如果对git命令使用不熟悉&#xff0c;推荐一个非常棒的git在线练习工具 Learn Git Branching。 https://m.runoob.com/git/git-basic-operations.html 1.配置SSH key ssh-keygen -t rsa -C "YOUR EMAIL"完成…

markdown 中启用音频支持

markdown 中启用音频支持 markdown 默认不支持音频文件&#xff0c;我们通过 html 标签渲染 flask项目 其中音频文件放在 /static/audios/vad_example.wav markdown 内容如下&#xff1a; ## 音频播放器示例 <audio controls ><source src"vad_example.wav…

Flink源码剖析

写在前面 最近一段时间都没有更新博客了&#xff0c;原因有点离谱&#xff0c;在实现flink的两阶段提交的时候&#xff0c;每次执行自定义的notifyCheckpointComplete时候&#xff0c;好像就会停止消费数据&#xff0c;完成notifyComplete后再消费数据&#xff1b;基于上述原因…

力扣16~20题

题16&#xff08;中等&#xff09;&#xff1a; 思路&#xff1a; 双指针法&#xff0c;和15题差不多&#xff0c;就是要排除了&#xff0c;如果total<target则排除了更小的&#xff08;left右移&#xff09;&#xff0c;如果total>target则排除了更大的&#xff08;rig…

kafka的成神秘籍(java)

kafka的成神秘籍 kafka的简介 ​ Kafka 最初是由Linkedin 即领英公司基于Scala和 Java语言开发的分布式消息发布-订阅系统&#xff0c;现已捐献给Apache软件基金会。Kafka 最被广为人知的是作为一个 消息队列(mq)系统存在&#xff0c;而事实上kafka已然成为一个流行的分布式流…

【mmengine】配置器(config)(进阶)继承与导出,命令行修改配置

一、配置文件的继承 1.1 继承机制概述 新建optimizer_cfg.py: optimizer dict(typeSGD, lr0.02, momentum0.9, weight_decay0.0001)新建runtime_cfg.py: device "cuda" gpu_ids [0, 1] batch_size 64 epochs 100 num_workers 8新建resnet50.py: _base_ […

Vue 路由设置

为了防止遗忘&#xff0c;记录一下用Vue写前端配置路由时的过程&#xff0c;方便后续再需要用到时回忆。 一、举个例子 假如需要实现这样的界面逻辑&#xff1a; 在HomePage中有一组选项卡按钮用于导航到子页面&#xff0c;而子页面Page1中有一个按钮&#xff0c;其响应事件是…

笔记-stm32移植ucos

文章目录 一、UCOS的基础知识1.1 前后台系统:1.2 RTOS系统可剥夺型内核:前后台系统和RTOS系统 1.3 UCOS系统简介学习方法 二、ucossii移植Step1&#xff1a;在工程中建立存放UCOSS代码的文件夹UCOSIIStep2:向CORE文件夹添加文件Step3:向Config文件夹添加文件Step4:向port文件夹…

LLM4Rec最新工作: 字节发布用于序列推荐的分层大模型HLLM

前几个月 Meta HSTU 点燃各大厂商对 LLM4Rec 的热情&#xff0c;一时间&#xff0c;探索推荐领域的 Scaling Law、实现推荐的 ChatGPT 时刻、取代传统推荐模型等一系列话题让人兴奋&#xff0c;然而理想有多丰满&#xff0c;现实就有多骨感&#xff0c;尚未有业界公开真正复刻 …

vscode中配置python虚拟环境

python虚拟环境作用 Python虚拟环境允许你为每个独立的项目创建一个隔离的环境&#xff0c;这样每个项目都可以拥有自己的一套Python安装包和依赖&#xff0c;不会互相影响。实际使用中&#xff0c;可以在vscode或pycharm中使用虚拟环境。 1.创建虚拟环境的方法&#xff1a; …

【NLP自然语言处理】01-基础学习路径简介

目的&#xff1a;让大家能够在 AI-NLP 领域由基础到入门具体安排&#xff1a; NLP介绍 文本预处理RNN 及其变体&#xff08;涉及案例&#xff09;Transformer 原理详解迁移学习 和 Bert 模型详解 &#xff08;涉及案例&#xff09;特点&#xff1a; 原理 实践每个文章会有练习…

04-SpringBootWeb案例(中)

3. 员工管理 完成了部门管理的功能开发之后&#xff0c;我们进入到下一环节员工管理功能的开发。 基于以上原型&#xff0c;我们可以把员工管理功能分为&#xff1a; 分页查询&#xff08;今天完成&#xff09;带条件的分页查询&#xff08;今天完成&#xff09;删除员工&am…

算法题总结(十)——二叉树上

#二叉树的递归遍历 // 前序遍历递归LC144_二叉树的前序遍历 class Solution {public List<Integer> preorderTraversal(TreeNode root) {List<Integer> result new ArrayList<Integer>(); //也可以把result 作为全局变量&#xff0c;只需要一个函数即可。…

Linus Torvalds 要求内核开发人员编写更好的 Git 合并提交信息

昨天在宣布 Linux 6.12-rc2 内核时&#xff0c;Linus Torvalds 要求内核维护者在提交信息方面做得更好。Torvalds 尤其希望内核维护者在描述拉取请求中的变更时&#xff0c;能更好地使用积极、命令式的语气。 Linux创建者在6.12-rc2 公告中解释道&#xff1a; 总之&#xff0c…

论文阅读笔记-XLNet: Generalized Autoregressive Pretraining for Language Understanding

前言 Google发布的XLNet在问答、文本分类、自然语言理解等任务上都大幅超越BERT,XLNet提出一个框架来连接语言建模方法和预训练方法。我们所熟悉的BERT是denoising autoencoding模型,最大的亮点就是能够获取上下文相关的双向特征表示,所以相对于标准语言模型(自回归)的预…

【AIGC】ChatGPT提示词Prompt高效编写模式:结构化Prompt、提示词生成器与单样本/少样本提示

博客主页&#xff1a; [小ᶻZ࿆] 本文专栏: AIGC | ChatGPT 文章目录 &#x1f4af;前言&#x1f4af;结构化Prompt (Structured Prompt)组成元素应用实例优势结论 &#x1f4af;提示词生成器 (Prompt Creator)如何工作应用实例优势结论 &#x1f4af;单样本/少样本提示 (O…

什么是安全运营中心 SOC?

SOC 代表安全运营中心&#xff0c;它是任何企业中负责组织安全、保护企业免受网络风险的单一、集中的团队或职能。 安全运营中心将管理和控制业务运营的所有安全要素&#xff0c;从监控资产到雇用合适的人员和流程&#xff0c;再到检测和应对威胁。 在本文中&#xff0c;我们…

PHP变量(第④篇)

本栏目教学是php零基础到精通&#xff0c;如果你还没有安装php开发工具请查看下方链接&#xff1a; Vscode、小皮面板安装-CSDN博客 今天来讲一讲php中的变量&#xff0c;变量是用于存储信息的"容器"&#xff0c;这些数据可以在程序执行期间被修改&#xff08;即其…

ThinkBook 16+ 锐龙6800h 安装ubuntu键盘失灵

问题&#xff1a;在ThinkBook 16 锐龙6800h 安装ubuntu18.04 出现笔记本键盘按下延迟非常高&#xff0c;输出卡死的情况&#xff0c;但是外接键盘可以正常使用 解决&#xff1a;更新内核 1、进入 https://kernel.ubuntu.com/~kernel-ppa/mainline/ 下载所需内核版本&#x…