Unity - 搬砖日志 - BRP 管线下的自定义阴影尺寸(脱离ProjectSettings/Quality/ShadowResolution设置)

news2024/11/25 0:58:24

文章目录

  • 环境
  • 原因
  • 解决
    • CSharp 脚本
    • 效果预览 - Light.shadowCustomResolution
    • 效果预览 - Using Quality Settings
  • 应用
    • ControlLightShadowResolution.cs Component
    • Tools Batching add the Component to all Light
  • References


环境

Unity : 2020.3.37f1
Pipeline : BRP


原因

(好久没搬砖了,偶尔健身一下,顺便将这些无技术含量的内容,记到 blog,不要记在脑子)

最近给项目做优化的过程中
发现 BRP 管线下的 Shadow Resolution 只能在 Project Settings/Quality/Shadow Resolution 去设置
而且发现
Shadow Resolution 的一些枚举为:

  • Low Resolution - 1K
  • Medium Resolution - 2K
  • High Resolution - 4K
  • Very High Resolution - 4K (这个可能因硬件不同而不同)

在这里插入图片描述

在这里插入图片描述


解决

但是如果想要设置更小的 shadow resolution 的话,这步就没辙了?
还好我去公司中台请教了 TA 专家,他说 BRP 中一样是可以设置的

在这里插入图片描述


CSharp 脚本

// jave.lin 2023/03/06 custom shadow resolution
// refer to : https://docs.unity3d.com/Manual/shadow-mapping.html

using UnityEngine;

public enum eCustomShadowResolution
{
    UsingQualitySettings = 0,
    Low = 128,
    Medium = 256,
    High = 512,
    VeryHigh = 1024,
}

[ExecuteInEditMode]
public class LightCustomShadowResolution : MonoBehaviour
{
    public bool runInUpdate = true;
    public eCustomShadowResolution shadowSize = eCustomShadowResolution.High;
    private Light lightComp;
    private void Update()
    {
        if (runInUpdate)
        {
            if (lightComp == null)
            {
                lightComp = GetComponent<Light>();
            }
            if (lightComp == null)
            {
                return;
            }
            lightComp.shadowCustomResolution = (int)shadowSize;
        }
    }
}


效果预览 - Light.shadowCustomResolution

Light.shadowCustomResolution = val

  • 这个 val 不等于 0 的话,就是自定义设置,这个 val 会自动 mostest NPOT == Mostest Next Power Of Tow
  • 这个 val 等于 0 的话,就是使用 Quality Settings 的全局配置
    请添加图片描述

效果预览 - Using Quality Settings

请添加图片描述


应用

只需要编写工具,批量对项目中的 Scene、Prefab,遍历其下所有 Light 的 GameObject 添加 改组件即可


ControlLightShadowResolution.cs Component

// jave.lin 2023/03/06 control light shadow resolution, [attach to light]

using UnityEditor.SearchService;
using UnityEngine;
using War.Script;

[ExecuteInEditMode]
public class ControlLightShadowResolution : MonoBehaviour
{
    public eLightShadowResolutionFollowQualitySetting followQualitySetting;
    public int shadowSize;

#if UNITY_EDITOR
    public bool runInUpdate = true;
#endif

    private Light lightComp;

    private void Start()
    {
        int level = UIInterface.GetCsharpEventCenterLevel();
        OnQualityLevelChanged(level);
        // TODO: xxx 修改为对应的时间名
        EventMgr.Instance.RemoveEvent<int>("xxx", OnQualityLevelChanged);
        EventMgr.Instance.AddEvent<int>("xxx", OnQualityLevelChanged);
    }

    private void OnDestroy()
    {
        // TODO: xxx 修改为对应的时间名
        EventMgr.Instance.RemoveEvent<int>("xxx", OnQualityLevelChanged);
    }

#if UNITY_EDITOR
    private void Update()
    {
        if (runInUpdate)
        {
            ApplyChanged();
        }
    }
#endif

    private void OnQualityLevelChanged(int lv)
    {
        if (followQualitySetting == eLightShadowResolutionFollowQualitySetting.On)
        {
            shadowSize = 0;
        }
        else
        {
            eQualityLevel level = (eQualityLevel)lv;
            switch (level)
            {
                case eQualityLevel.VeryLow:
                    shadowSize = (int)eLightCustomShadowResolutionSize.VeryLow;
                    break;
                case eQualityLevel.Low:
                    shadowSize = (int)eLightCustomShadowResolutionSize.Low;
                    break;
                case eQualityLevel.Medium:
                    shadowSize = (int)eLightCustomShadowResolutionSize.Medium;
                    break;
                case eQualityLevel.High:
                    shadowSize = (int)eLightCustomShadowResolutionSize.High;
                    break;
                default:
                    break;
            }
        }
        ApplyChanged();
    }

    private void ApplyChanged()
    {
        if (lightComp == null)
        {
            lightComp = GetComponent<Light>();
        }
        if (lightComp == null)
        {
            return;
        }
        lightComp.shadowCustomResolution = shadowSize;
    }
}


Tools Batching add the Component to all Light

// 伪代码
var scene = EditorSceneManager.xxxByPath("xxx");
var roots = scene.GetxxxxRoots();
foreach (var root in roots)
{
	var lights = root.GetComponents<Light>();
	// 剩下的同下代码
}
    public static void AddControlLightShadowResolution()
    {
        var lights = GameObject.FindObjectsOfType<Light>();

        foreach (var light in lights)
        {
            if (light == null)
                continue;

            ControlLightShadowResolution comp = light.transform.GetComponent<ControlLightShadowResolution>();

            if (light.lightmapBakeType == LightmapBakeType.Realtime)
            {
                if (comp == null)
                {
                    light.gameObject.AddComponent<ControlDepthMode>();
                }
            }
            else
            {
                if (comp != null)
                {
                    if (Application.isPlaying)
                        GameObject.Destroy(comp);
                    else
                        GameObject.DestroyImmediate(comp);
                }
            }
        }
    }

References

  • shadow-mapping - unity 官方 shadow map 文档

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

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

相关文章

JVM系统优化实践(8):订单系统的垃圾回收案例

您好&#xff0c;我是湘王&#xff0c;这是我的CSDN博客&#xff0c;欢迎您来&#xff0c;欢迎您再来&#xff5e;上回说到了年轻代和老年代的两个垃圾回收器&#xff1a;ParNew和CMS&#xff0c;并且将CMS的GC过程也一并介绍了&#xff0c;现在来看个订单系统的案例。假设有这…

常见数据结构

一. 数据结构概述、栈、队列 1. 数据结构概述 2. 栈数据结构的执行特点 3. 常见数据结构之队列 二. 常见数据结构之数组 数组它就是内存中的一块儿连续区域。数组变量存的是数组在堆内存当中的起始地址。数组查询任意索引位置的值耗时相同&#xff0c;数组根据索引查询速度快。…

Matlab中旧版modem.qammod与新版不兼容

最近&#xff0c;因为课题需要&#xff0c;在研究通信。在网上下了一个2015年左右的代码&#xff0c;其中用的是matlab旧版中的modem.qammod函数&#xff0c;但是旧版中的函数已经被删除了&#xff0c;&#xff08;这里必须得吐槽一下&#xff0c;直接该函数内部运行机制就行呀…

Lasso回归理论及代码实现

Lasso回归的模型可以写作与一般线性回归相比, Lasso回归加入了回归项系数的一范数, 这样做是为了防止线性回归过程发生的过拟合现象. 直观点看, 其将的分量限制在了一个以圆点为中心以为边的正方形内. 与岭回归相比, 该模型得到的系数矩阵更为稀疏. 由于函数在0点不可导, 因而L…

第二章Linux操作语法1

文章目录vi和vim常用的三种模式vi和vim快捷键Linux开机&#xff0c;重启用户管理用户信息查询管理who和whoami用户组信息查询管理用户和组的相关文件实用指令集合运行级别帮助指令manhelp文件管理类pwd命令ls命令cd命令mkdir命令rmdir命令rm命令touch命令cp指令mv指令文件查看类…

Pytorch学习笔记#2: 搭建神经网络训练MNIST手写数字数据集

学习自https://pytorch.org/tutorials/beginner/basics/quickstart_tutorial.html 导入并预处理数据集 pytorch中数据导入和预处理主要用torch.utils.data.DataLoader 和 torch.utils.data.Dataset Dataset 存储样本及其相应的标签&#xff0c;DataLoader在数据上生成一个可迭…

刷题小抄4-数组

在Python中数组的功能由列表来实现,本文主要介绍一些力扣上关于数组的题目解法 寻找数组中重复的数字 题目链接 题目大意: 给出一个数组,数组长度为n,数组里的数字在[0,n-1]范围以内,数字可以重复,寻找出数组中任意一个重复的数字,返回结果 解法一 该题最基础的思路是使用字…

[java Spring JdbcTemplate配合mysql实现数据批量删除

之前的文章 java Spring JdbcTemplate配合mysql实现数据批量添加和文章java Spring JdbcTemplate配合mysql实现数据批量修改 先后讲解了 mysql数据库的批量添加和批量删除操作 会了这两个操作之后 批量删除就不要太简单 我们看到数据库 这里 我们用的是mysql工具 这里 我们有…

Java——单词接龙

题目链接 leetcode在线oj题——单词接龙 题目描述 字典 wordList 中从单词 beginWord 和 endWord 的 转换序列 是一个按下述规格形成的序列 beginWord -> s1 -> s2 -> … -> sk&#xff1a; 每一对相邻的单词只差一个字母。 对于 1 < i < k 时&#xff…

QML Text详解

1.简介 文本项可以显示普通文本和富文本。 2.示例 示例1&#xff1a;一个简单的text&#xff0c;可以设置字体颜色、大小等。 Window {visible: truewidth: 400height: 400title: qsTr("Hello World")Rectangle{width: 200height: 200border.width: 2Text {text: …

(flutter)黑苹果系统 Xcode iOS flutter 跑通真机模拟器 此oc clover 彼oc swift

前段时间写了关于flutter的一系列基础知识和入门的一些坑&#xff0c;中间把ios端的项目编译部署等工作一带而过&#xff0c;这里我觉得还是有必要专门写一篇文章来讲讲这个&#xff0c;顺便把环境问题也一起说了。 我们都知道开发ios应用需要用到苹果电脑&#xff0c;即使flu…

【NLP】Word2Vec 介绍

Word2Vec 是一种非常流行的自然语言处理技术&#xff0c;它将每个单词表示为高维向量&#xff0c;并且通过向量之间的相似度来表示单词之间的语义关系。 1 One-Hot 编码&#x1f342; 在自然语言处理任务中&#xff0c;我们需要将文本转换为计算机可以理解的形式&#xff0c;即…

ChatGPT后劲很大,问题也是

ChatGPT亮相即封神&#xff0c;最初的访客是程序员、工程师、AI从业者、投资人&#xff0c;最后是无数懵懂又好奇的普通人&#xff1a;ChatGPT是什么&#xff1f;自己会被ChatGPT取代吗&#xff1f;看待ChatGPT的立场也是两个极端&#xff1a; 快乐&#xff0c;是因为ChatGPT太…

科普| 什么是云原生?

“新冠疫情从根本上改变了商业模式&#xff0c;工作流向在线迁移的速度比以往任何时候都要快。越来越多的公司和消费者依靠电子商务“ B2B”和B2C”&#xff0c;以及网上银行促进创新以满足日益增长的客户需求&#xff0c;云原生技术在其中发挥重要作用&#xff0c;同时也加速了…

vm centos7搭建k8s集群

关闭防火墙&#xff0c;三台systemctl stop firewalld关闭selinux&#xff0c;三台sed -i s/enforcing/disabled/ /etc/selinux/config关闭swap&#xff0c;三台swapoff -a设置主机名&#xff0c;三台hostnamectl set-hostname 主机名&#xff0c;三个主机名分别设置成k8s-mast…

JavaScript新手学习手册-基础代码(一)

什么是JavaScript&#xff1f; 百度百科 什么是控制台&#xff1f; 网页➡快捷键F12 进入Console就是控制台&#xff0c;它的作用与开发软件相同&#xff0c;可以进行代码的编写在紫色位置进行编写&#xff0c;另外console.log()方法所打印的内容都是在此进行输出。 一&#…

Spark Join

Spark Join关联形式内关联外关联左外关联右外关联全外关联左半/逆关联关联机制NLJSMJHJ分发模式Join 选择等值 Join不等值 JoinJoin 按照关联形式&#xff08;Join Types&#xff09;划分 : 内关联、外关联、左关联、右关联 Join 按实现机制划分 : NLJ (Nested Loop Join) 、S…

【操作系统原理实验】页面替换策略模拟实现

选择一种高级语言如C/C等&#xff0c;编写一个页面替换算法的模拟实现程序。1) 设计内存管理相关数据结构&#xff1b;2) 随机生成一个页面请求序列&#xff1b;3) 设置内存管理模拟的关键参数&#xff1b;4) 实现该页面置换算法&#xff1b;5) 模拟实现给定配置请求序列的换页…

【python socket】实现websocket服务端

一、获取握手信息首先通过如下代码&#xff0c;我们使用socket来获取客户端的握手信息import socketsock socket.socket(socket.AF_INET, socket.SOCK_STREAM) sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) sock.bind(("127.0.0.1", 8002)) sock.li…

启动项管理工具Autoruns使用实验(20)

实验目的 &#xff08;1&#xff09;了解注册表的相关知识&#xff1b; &#xff08;2&#xff09;了解程序在开机过程中的自启动&#xff1b; &#xff08;3&#xff09;掌握Autoruns在注册表和启动项方面的功能&#xff1b;预备知识 注册表是windows操作系统中的一个核心数据…