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

轻量封装WebGPU渲染系统示例<29>- 深度模糊DepthBlur(源码)

实现方式:

step1. 通过mrt机制,输出颜色和深度相关数据的两张rtt纹理。

step2. 基于上述颜色纹理,生成一张模糊之后的新rtt纹理。

setp3. 基于深度(也就是距离摄像机的远近)数据,合成颜色和模糊纹理数据,并最终输出。

当前示例源码github地址:

https://github.com/vilyLei/voxwebgpu/blob/feature/rendering/src/voxgpu/sample/DepthBlur.ts

当前示例运行效果:

微调一点代码,即可获得下述效果:

代码微调方式:

        第一处, 将下述片段着色器中的 f = 1.0 - f * f; 改为 f = f * f;

        第二处, 将

const attachment1 = {texture: vposRTTTex,clearValue: [0.2, 0.25, 0.2, 1.0]};

        改为

const attachment1 = {texture: vposRTTTex,clearValue: [800, 800, 800, 1]};

当然也可以通过第四个分量,来做实际的区分参数,统一处理。

合成模糊效果的WGSL片段着色器代码:

@group(0) @binding(0) var<uniform> param: vec4f;
@group(0) @binding(1) var colorSampler0: sampler;
@group(0) @binding(2) var colorTexture0: texture_2d<f32>;
@group(0) @binding(3) var blurSampler1: sampler;
@group(0) @binding(4) var blurTexture1: texture_2d<f32>;
@group(0) @binding(5) var vposSampler1: sampler;
@group(0) @binding(6) var vposTexture1: texture_2d<f32>;fn calcColor(uv: vec2f) -> vec4f {var color = textureSample(colorTexture0, colorSampler0, uv) * param;var blurColor = textureSample(blurTexture1, blurSampler1, uv);var vpos = textureSample(vposTexture1, vposSampler1, uv);var f = clamp((length(vpos.xyz) - 300.0)/200.0, 0.0, 1.0);f = 1.0 - f * f;var result = vec4f(color.xyz * (1.0 - f) + f * blurColor.xyz, 1.0);return result;
}@fragment
fn main(@location(0) uv: vec2f) -> @location(0) vec4f {var color4 = calcColor( uv );return color4;
}

此示例基于此渲染系统实现,当前示例TypeScript源码如下:

const blurRTTTex0 = { diffuse: { uuid: "rtt0", rttTexture: {} } };
const blurRTTTex1 = { diffuse: { uuid: "rtt1", rttTexture: {} } };
const rtts = [blurRTTTex0, blurRTTTex1];
const attachment = {texture: blurRTTTex0,clearValue: [] as ColorDataType,loadOp: "clear",storeOp: "store"
} as WGRPassColorAttachment;
const colorAttachments = [attachment];const colorRTTTex = { diffuse: { uuid: "colorRTT", rttTexture: {} } };
const vposRTTTex = { diffuse: { uuid: "floatRTT", rttTexture: {}, format: 'rgba16float' } };class PassGraph extends WGRPassNodeGraph {blurEntity: FixScreenPlaneEntity;srcEntity: FixScreenPlaneEntity;constructor() {super();}run(): void {let pass = this.passes[0];const entity = this.blurEntity;let ms = entity.materials;for (let i = 0; i < 11; ++i) {const ia = i % 2;const ib = (i + 1) % 2;pass.colorAttachments[0].clearEnabled = i < 1;this.srcEntity.visible = i < 1;this.blurEntity.visible = i > 0;attachment.texture = rtts[ia];ms[ia].visible = false;ms[ib].visible = true;pass.render();}}
}export class DepthBlur {private mRscene = new RendererScene();private mGraph = new PassGraph();private uniformValues = [{ data: new Float32Array([512, 512, 3.0, 0]) }];initialize(): void {let multisampleEnabled = true;let depthTestEnabled = false;let rpassparam = { multisampleEnabled, depthTestEnabled };this.mRscene.initialize({ rpassparam });this.initEvent();this.initScene();}private initEvent(): void {const rc = this.mRscene;rc.addEventListener(MouseEvent.MOUSE_DOWN, this.mouseDown);new MouseInteraction().initialize(rc, 0, false).setAutoRunning(true);}private mouseDown = (evt: MouseEvent): void => {}private createMaterial(shadinguuid: string, textures: WGTextureDataDescriptor[], type: number): WGMaterial {let shaderCodeSrc = {vert: { code: vertWGSL, uuid: "vert" },frag: { code: type > 0 ? blurVWGSL : blurHWGSL, uuid: "frag" }};shadinguuid += "-" + type;let pipelineDefParam = {depthWriteEnabled: false};const material = new WGMaterial({shadinguuid,shaderCodeSrc,pipelineDefParam});material.uniformValues = this.uniformValues;material.addTextures(textures);return material;}private applyBlurPass(clearColor: ColorDataType, extent: number[]): void {let rs = this.mRscene;const graph = this.mGraph;attachment.clearValue = clearColor;let rPass = rs.createRenderPass({ separate: true, colorAttachments });graph.passes = [rPass];let materials = [this.createMaterial("shd-00", [blurRTTTex0], 0), this.createMaterial("shd-01", [blurRTTTex1], 1)];let rttEntity = new FixScreenPlaneEntity({ extent: [-1, -1, 2, 2], flipY: true, textures: [colorRTTTex] });rttEntity.uuid = "src-entity";rPass.addEntity(rttEntity);graph.srcEntity = rttEntity;rs.setPassNodeGraph(graph);let entity = new FixScreenPlaneEntity({ extent, flipY: true, materials });entity.materials[0].visible = false;entity.uuid = "blur-entity";rPass.addEntity(entity);graph.blurEntity = entity;let shaderSrc = {vert: { code: vertWGSL, uuid: "vert" },frag: { code: depthBlurFragWGSL, uuid: "depthBlur" }};// display blur rendering resultlet textures = [colorRTTTex, blurRTTTex0, vposRTTTex];extent = [-0.8, -0.8, 1.6, 1.6];entity = new FixScreenPlaneEntity({ extent, flipY: false, shaderSrc, textures, shadinguuid: "smallImgMaterial" });rs.addEntity(entity);}private applyMRTPass(extent: number[]): void {let rs = this.mRscene;const attachment0 = {texture: colorRTTTex,clearValue: [0.15, 0.15, 0.15, 1.0]};const attachment1 = {texture: vposRTTTex,clearValue: [0.2, 0.25, 0.2, 1.0]};const colorAttachments = [attachment0, attachment1];let rPass = rs.createRenderPass({ separate: true, colorAttachments });let shaderSrc = {vert: { code: entityVertWGSL, uuid: "vertMRT" },frag: { code: entityFragWGSL, uuid: "fragMRT" }};let torus = new TorusEntity({shaderSrc, radius: 150});torus.setAlbedo([0.7,0.02,0.1]);rPass.addEntity(torus);shaderSrc = {vert: { code: vertWGSL, uuid: "vert" },frag: { code: vposReadFragWGSL, uuid: "readNromal" }};// display depth value drawing resultextent = [-0.95, -0.95, 0.6, 0.6];let entity = new FixScreenPlaneEntity({ extent, shaderSrc, textures: [vposRTTTex], shadinguuid: "readDepth" });rs.addEntity(entity);// display albedo drawing resultextent = [-0.33, -0.95, 0.6, 0.6];entity = new FixScreenPlaneEntity({ extent, textures: [colorRTTTex] });rs.addEntity(entity);// display blur drawing resultextent = [0.3, -0.95, 0.6, 0.6];entity = new FixScreenPlaneEntity({ extent, textures: [blurRTTTex0] });rs.addEntity(entity);}private initScene(): void {this.applyBlurPass([0.0, 0.0, 0.03, 1.0], [-1, -1, 2, 2]);this.applyMRTPass( [-1, -1, 2, 2] );}run(): void {this.mRscene.run();}
}

相关文章:

轻量封装WebGPU渲染系统示例<29>- 深度模糊DepthBlur(源码)

实现方式: step1. 通过mrt机制&#xff0c;输出颜色和深度相关数据的两张rtt纹理。 step2. 基于上述颜色纹理&#xff0c;生成一张模糊之后的新rtt纹理。 setp3. 基于深度(也就是距离摄像机的远近)数据&#xff0c;合成颜色和模糊纹理数据&#xff0c;并最终输出。 当前示例…...

LeetCode226. Invert Binary Tree

文章目录 一、题目二、题解2.1 前序遍历版本2.2 中序遍历版本2.3 后序遍历版本 一、题目 Given the root of a binary tree, invert the tree, and return its root. Example 1: Input: root [4,2,7,1,3,6,9] Output: [4,7,2,9,6,3,1] Example 2: Input: root [2,1,3] Ou…...

Java设计模式-创建型模式-建造者模式

建造者模式 建造者模式案例与工厂模式的区别&#xff1a;Builder 注解 建造者模式 建造者模式是将一个复杂对象的构件与表示分离&#xff0c;使得同样的构件过程可以创建不同的表示。 建造者模式将内部构件的创建和组装分割开&#xff0c;一般使用链式编程&#xff0c;代码整洁…...

PyQt中QFrame窗口中的组件不显示的原因

文章目录 问题代码&#xff08;例&#xff09;原因和解决方法 问题代码&#xff08;例&#xff09; from PyQt5.QtWidgets import * from PyQt5.QtGui import QFont, QIcon, QCursor, QPixmap import sysclass FrameToplevel(QFrame):def __init__(self, parentNone):super().…...

git 命令行回退版本

git 命令行回退版本 git 命令行回退版本命令: 1.切换到需要回退的分支 git checkout branch-v2.0.02.更新远程分支 git fetch3.找到需要回退版本的版本号git revert a6914da55ff40a09e67ac2426b86f1212e6580eb4.清除工作区缓存git clean -df5.强制提交git push -f...

IntelliJ IDEA 安装 GitHub Copilot插件 (最新)

注意&#xff1a; GitHub Copilot 插件对IDEA最低版本要求是2021.2&#xff0c;建议直接用2023.3&#xff0c;一次到位反正后续要升级的。 各个版本的依赖关系&#xff0c;请参照&#xff1a; ##在线安装&#xff1a; 打开 IntelliJ IDEA扩展商店&#xff0c;输入 "Git…...

viewpage选择器

GitHub - hackware1993/MagicIndicator: A powerful, customizable and extensible ViewPager indicator framework. As the best alternative of ViewPagerIndicator, TabLayout and PagerSlidingTabStrip —— 强大、可定制、易扩展的 ViewPager 指示器框架。是ViewPagerIndi…...

vue中如何将json数组指定的key赋值给el-form-item并均匀的分成2列

在Vue中&#xff0c;你可以使用v-for指令来遍历JSON数组&#xff0c;并将指定的key赋值给el-form-item。下面是一个示例&#xff1a; <template><el-form><el-row><el-col :span"6" v-for"item in jsonArray" :key"item.key&qu…...

笔记本分屏怎么操作?3个方法提高工作效率!

“有朋友知道笔记本怎么才能实现分屏吗&#xff1f;我在工作时&#xff0c;经常需要来回切换屏幕&#xff0c;效率真的太低了&#xff0c;有什么方法可以实现两个屏幕同时使用吗&#xff1f;” 在现代生活中&#xff0c;多任务处理已成为常态&#xff0c;而笔记本分屏技术为用户…...

Android 使用poi生成Excel ,word并保存在指定路径内

一添加依赖&#xff08;一定要用新版依赖防止一些bug&#xff09; minSdk 26 //注意最小支持SDK26 dependencies {implementation org.apache.poi:poi:5.2.4implementation org.apache.poi:poi-ooxml:5.2.4implementation javax.xml.stream:stax-api:1.0-2 }二&#xff0c;创…...

嵌入式杂记 -- MCU的大小端模式

MCU的大小端模式 大端模式小端模式大小端模式测试联合体概念MCU大小端模式测试大端模式测试小端模式测试 大小端模式转换 在进行MCU开发的时候&#xff0c;我们需要注意MCU的数据存储模式&#xff0c;在嵌入式中有两种不同的存储模式&#xff0c;分别是 大端模式和小端模式。 …...

对这套BI零售数据分析方案心动,是零售人天性

零售数据分析做了这么多年&#xff0c;难道真的没累积点经验&#xff0c;摸索出一条又快又能满足绝大多数需求的数据分析捷径&#xff1f;别人不知道&#xff0c;奥威BI还真就有这么一套标准化的BI零售数据分析方案&#xff0c;不管是服装零售、医药连锁、商超都能利用这套方案…...

vuekeyclock 集成

前端集成keycloak鉴权的主要写法&#xff0c; 在main.js里面写 import VueKeycloakJs from dsb-norge/vue-keycloak-js import { KeycloakInstance } from "keycloak-js";// 回调地址 const pageIndex process.env.NODE_ENV production ? http://xxxx/#/ : http:…...

ARM Linux 基础学习 / 配置交叉编译工具链 / 编译 Linux 应用和驱动 / 编译内核

编辑整理 by Staok。 本文部分内容摘自 “100ask imx6ull” 开发板的配套资料&#xff08;如 百问网的《嵌入式Linux应用开发完全手册》&#xff0c;在 百问网 imx6ull pro 开发板 页面 中的《2.1 100ASK_IMX6ULL_PRO&#xff1a;开发板资料》或《2.2 全系列Linux教程&#xf…...

通讯协议学习之路(实践部分):SPI开发实践

通讯协议之路主要分为两部分&#xff0c;第一部分从理论上面讲解各类协议的通讯原理以及通讯格式&#xff0c;第二部分从具体运用上讲解各类通讯协议的具体应用方法。 后续文章会同时发表在个人博客(jason1016.club)、CSDN&#xff1b;视频会发布在bilibili(UID:399951374) 本文…...

【系统安装】ubuntu20.04启动盘制作,正经教程,小白安装教程,百分百成功安装

1.所需材料&#xff1a; 64GBU盘&#xff08;其实8g和16g也可以&#xff09; 2.制作U盘启动盘 使用windows制作ubuntu 20.04启动盘 1&#xff09;下载制作工具&#xff1a;Rufus&#xff1a;Rufus - 轻松创建 USB 启动盘 2&#xff09;插入用来做启动盘的U盘 3&#xff0…...

2023云计算发展趋势

目录 一、云计算是什么&#xff1f; 二、云计算发展趋势 三、总结 一、云计算是什么&#xff1f; 云计算是一种基于互联网的计算方式&#xff0c;通过网络连接的方式提供计算能力、存储服务、应用程序和数据资源。它通常通过虚拟化技术实现多个计算机资源的池化&#xff0c;…...

C# .NET Core API Controller以及辅助专案

准备工作 Windows 10Visual Studio 2019(2017就有可以集中发布到publish目录的功能了吧)C#将方法封装(据说可以提高效率,就像是我们用的dll那种感觉新增专案作为我们API的辅助专案(作用类似dll&#xff0c;此处&#xff0c;你也可以在你自己的API专案里建文件夹&#xff0c;但…...

asp.net图书管理系统

asp.net图书管理系统 基本操作图书管理 读者管理 借书 修改资料 修改密码 说明文档 运行前附加数据库.mdf&#xff08;或sql生成数据库&#xff09; 主要技术&#xff1a; 基于C#winform架构和sql server数据库 功能模块&#xff1a; 图书管理 读者管理 借书 修改资料 修改…...

概念解析 | LoRA:低秩矩阵分解在神经网络微调中的作用

注1:本文系“概念解析”系列之一,致力于简洁清晰地解释、辨析复杂而专业的概念。本次辨析的概念是:基于低秩矩阵分解的神经网络微调方法LoRA LoRA: Low-Rank Adaptation of Large Language Models LoRA由如下论文提出,详细信息请参见论文原文 https://arxiv.org/abs/2106.0968…...

Python|GIF 解析与构建(5):手搓截屏和帧率控制

目录 Python&#xff5c;GIF 解析与构建&#xff08;5&#xff09;&#xff1a;手搓截屏和帧率控制 一、引言 二、技术实现&#xff1a;手搓截屏模块 2.1 核心原理 2.2 代码解析&#xff1a;ScreenshotData类 2.2.1 截图函数&#xff1a;capture_screen 三、技术实现&…...

中南大学无人机智能体的全面评估!BEDI:用于评估无人机上具身智能体的综合性基准测试

作者&#xff1a;Mingning Guo, Mengwei Wu, Jiarun He, Shaoxian Li, Haifeng Li, Chao Tao单位&#xff1a;中南大学地球科学与信息物理学院论文标题&#xff1a;BEDI: A Comprehensive Benchmark for Evaluating Embodied Agents on UAVs论文链接&#xff1a;https://arxiv.…...

376. Wiggle Subsequence

376. Wiggle Subsequence 代码 class Solution { public:int wiggleMaxLength(vector<int>& nums) {int n nums.size();int res 1;int prediff 0;int curdiff 0;for(int i 0;i < n-1;i){curdiff nums[i1] - nums[i];if( (prediff > 0 && curdif…...

CocosCreator 之 JavaScript/TypeScript和Java的相互交互

引擎版本&#xff1a; 3.8.1 语言&#xff1a; JavaScript/TypeScript、C、Java 环境&#xff1a;Window 参考&#xff1a;Java原生反射机制 您好&#xff0c;我是鹤九日&#xff01; 回顾 在上篇文章中&#xff1a;CocosCreator Android项目接入UnityAds 广告SDK。 我们简单讲…...

Mac下Android Studio扫描根目录卡死问题记录

环境信息 操作系统: macOS 15.5 (Apple M2芯片)Android Studio版本: Meerkat Feature Drop | 2024.3.2 Patch 1 (Build #AI-243.26053.27.2432.13536105, 2025年5月22日构建) 问题现象 在项目开发过程中&#xff0c;提示一个依赖外部头文件的cpp源文件需要同步&#xff0c;点…...

JVM虚拟机:内存结构、垃圾回收、性能优化

1、JVM虚拟机的简介 Java 虚拟机(Java Virtual Machine 简称:JVM)是运行所有 Java 程序的抽象计算机,是 Java 语言的运行环境,实现了 Java 程序的跨平台特性。JVM 屏蔽了与具体操作系统平台相关的信息,使得 Java 程序只需生成在 JVM 上运行的目标代码(字节码),就可以…...

AGain DB和倍数增益的关系

我在设置一款索尼CMOS芯片时&#xff0c;Again增益0db变化为6DB&#xff0c;画面的变化只有2倍DN的增益&#xff0c;比如10变为20。 这与dB和线性增益的关系以及传感器处理流程有关。以下是具体原因分析&#xff1a; 1. dB与线性增益的换算关系 6dB对应的理论线性增益应为&…...

20个超级好用的 CSS 动画库

分享 20 个最佳 CSS 动画库。 它们中的大多数将生成纯 CSS 代码&#xff0c;而不需要任何外部库。 1.Animate.css 一个开箱即用型的跨浏览器动画库&#xff0c;可供你在项目中使用。 2.Magic Animations CSS3 一组简单的动画&#xff0c;可以包含在你的网页或应用项目中。 3.An…...

tauri项目,如何在rust端读取电脑环境变量

如果想在前端通过调用来获取环境变量的值&#xff0c;可以通过标准的依赖&#xff1a; std::env::var(name).ok() 想在前端通过调用来获取&#xff0c;可以写一个command函数&#xff1a; #[tauri::command] pub fn get_env_var(name: String) -> Result<String, Stri…...

redis和redission的区别

Redis 和 Redisson 是两个密切相关但又本质不同的技术&#xff0c;它们扮演着完全不同的角色&#xff1a; Redis: 内存数据库/数据结构存储 本质&#xff1a; 它是一个开源的、高性能的、基于内存的 键值存储数据库。它也可以将数据持久化到磁盘。 核心功能&#xff1a; 提供丰…...