如何根据顶点颜色丢弃像素并在 MonoBehaviour 中打开或关闭它?
How do I discard pixels based on vertex color and turn that on or off in a MonoBehaviour?
我已经编写了一个使用网格顶点颜色的着色器,并且还有一个函数可以裁剪蓝色通道中插值顶点颜色大于 0.5 的所有顶点(丢弃所有蓝色顶点)。
我正在尝试创建一个语音命令,允许用户在他们准备好时调用该功能。然而,在微软的混合现实工具包语音输入处理程序中,它只允许我从我引用的游戏对象的组件(网格渲染器、网格过滤器、网格碰撞器等)调用函数,而不是着色器或 material的对象。
我怎样才能让语音命令可以调用我在下面分享的 'hide' 功能?
我尝试在着色器之外编写 'hide' 功能,但似乎没有用。
Shader "Custom/VertexColor" { // Where it will appear inside of the Shader Dropdown Menu of the Material / Name of the shader
Properties{
_Toggle ("Toggle context", int) = 0
}
SubShader{
Tags { "RenderType" = "Opaque" }
LOD 200
CGPROGRAM
#pragma surface surf Lambert vertex:vert
#pragma target 3.0
#include "UnityCG.cginc"
struct Input {
float4 vertColor;
};
void vert(inout appdata_full v, out Input o) {
UNITY_INITIALIZE_OUTPUT(Input, o);
o.vertColor = v.color;
}
void surf(Input IN, inout SurfaceOutput o) {
#include "UnityCG.cginc"
int _Toggle = 0;
o.Albedo = IN.vertColor.rgb;
clip(_Toggle * (0.5f - IN.vertColor.b));
}
ENDCG
}
FallBack "Diffuse"
}
我希望语音输入处理程序允许我从着色器调用函数,但它没有。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using HoloToolkit.Unity;
public class AnchorScript : MonoBehaviour
{
public Renderer rend;
Vector3 scale;
public WorldAnchorManager worldAnchorManager;
// Start is called before the first frame update
void Start()
{
transform.localScale = scale;
TurnOffContext();
}
private void Update()
{
SaveScale();
}
public void AnchorIt()
{
worldAnchorManager.AttachAnchor(this.gameObject);
this.gameObject.GetComponent<Renderer>().material.color = Color.red;
}
public void ReleaseAnchor()
{
worldAnchorManager.RemoveAnchor(this.gameObject);
this.gameObject.GetComponent<Renderer>().material.color = Color.green;
}
public void ShowDifferences()
{
gameObject.GetComponent<Renderer>().enabled = true;
}
public void HideAugmentations()
{
gameObject.GetComponent<Renderer>().enabled = false;
}
public void TurnOffContext()
{
rend.material.SetFloat("_Toggle", 1);
}
public void SaveScale()
{
scale = gameObject.GetComponent<Transform>().localScale;
}
}
我将 TurnOffContext() 函数放在 Start() 函数中只是为了测试它是否有效。理论上它应该立即将 _Toggle 属性 设置为 1,这会丢弃所有蓝色像素,但在启动我的应用程序时我仍然看到完整的原始网格。我也试过不把它放在 Start() 函数中,而只是使用运行函数 TurnOffContext() 的语音命令,但这也没有用。
这是我的 GameObject material 的检查面板的屏幕截图。
https://imgur.com/a/wkVh5Tj
您的着色器代码中有多余的 #include
,并且您在错误的位置声明了 _Toggle
变量。另外,你不应该初始化int _Toggle
,你只想声明它以便unity可以设置它的值。
去掉第二个#include "UnityCG.cginc"
,去掉int _Toggle = 0;
,把int _Toggle;
(注意:没有初始化)放在CGPROGRAM
.[=26=下面的某个地方]
此外,将 Properties
块更改为使用大写字母 I Int
:
Shader "Custom/VertexColor" { // Where it will appear inside of the Shader Dropdown Menu of the Material / Name of the shader
Properties{
_Toggle ("Toggle context", Int) = 0
}
SubShader{
Tags { "RenderType" = "Opaque" }
LOD 200
CGPROGRAM
#pragma surface surf Lambert vertex:vert
#pragma target 3.0
#include "UnityCG.cginc"
int _Toggle;
struct Input {
float4 vertColor;
};
void vert(inout appdata_full v, out Input o) {
UNITY_INITIALIZE_OUTPUT(Input, o);
o.vertColor = v.color;
}
void surf(Input IN, inout SurfaceOutput o) {
o.Albedo = IN.vertColor.rgb;
clip(_Toggle * (0.5f - IN.vertColor.b));
}
ENDCG
}
FallBack "Diffuse"
}
然后,在你的 C# 代码中,你需要使用 SetInt
而不是 SetFloat
因为 _Toggle
是一个 int
.
此外,使用 renderer.sharedMaterial
而不是 renderer.material
!
我已经编写了一个使用网格顶点颜色的着色器,并且还有一个函数可以裁剪蓝色通道中插值顶点颜色大于 0.5 的所有顶点(丢弃所有蓝色顶点)。
我正在尝试创建一个语音命令,允许用户在他们准备好时调用该功能。然而,在微软的混合现实工具包语音输入处理程序中,它只允许我从我引用的游戏对象的组件(网格渲染器、网格过滤器、网格碰撞器等)调用函数,而不是着色器或 material的对象。
我怎样才能让语音命令可以调用我在下面分享的 'hide' 功能?
我尝试在着色器之外编写 'hide' 功能,但似乎没有用。
Shader "Custom/VertexColor" { // Where it will appear inside of the Shader Dropdown Menu of the Material / Name of the shader
Properties{
_Toggle ("Toggle context", int) = 0
}
SubShader{
Tags { "RenderType" = "Opaque" }
LOD 200
CGPROGRAM
#pragma surface surf Lambert vertex:vert
#pragma target 3.0
#include "UnityCG.cginc"
struct Input {
float4 vertColor;
};
void vert(inout appdata_full v, out Input o) {
UNITY_INITIALIZE_OUTPUT(Input, o);
o.vertColor = v.color;
}
void surf(Input IN, inout SurfaceOutput o) {
#include "UnityCG.cginc"
int _Toggle = 0;
o.Albedo = IN.vertColor.rgb;
clip(_Toggle * (0.5f - IN.vertColor.b));
}
ENDCG
}
FallBack "Diffuse"
}
我希望语音输入处理程序允许我从着色器调用函数,但它没有。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using HoloToolkit.Unity;
public class AnchorScript : MonoBehaviour
{
public Renderer rend;
Vector3 scale;
public WorldAnchorManager worldAnchorManager;
// Start is called before the first frame update
void Start()
{
transform.localScale = scale;
TurnOffContext();
}
private void Update()
{
SaveScale();
}
public void AnchorIt()
{
worldAnchorManager.AttachAnchor(this.gameObject);
this.gameObject.GetComponent<Renderer>().material.color = Color.red;
}
public void ReleaseAnchor()
{
worldAnchorManager.RemoveAnchor(this.gameObject);
this.gameObject.GetComponent<Renderer>().material.color = Color.green;
}
public void ShowDifferences()
{
gameObject.GetComponent<Renderer>().enabled = true;
}
public void HideAugmentations()
{
gameObject.GetComponent<Renderer>().enabled = false;
}
public void TurnOffContext()
{
rend.material.SetFloat("_Toggle", 1);
}
public void SaveScale()
{
scale = gameObject.GetComponent<Transform>().localScale;
}
}
我将 TurnOffContext() 函数放在 Start() 函数中只是为了测试它是否有效。理论上它应该立即将 _Toggle 属性 设置为 1,这会丢弃所有蓝色像素,但在启动我的应用程序时我仍然看到完整的原始网格。我也试过不把它放在 Start() 函数中,而只是使用运行函数 TurnOffContext() 的语音命令,但这也没有用。
这是我的 GameObject material 的检查面板的屏幕截图。 https://imgur.com/a/wkVh5Tj
您的着色器代码中有多余的 #include
,并且您在错误的位置声明了 _Toggle
变量。另外,你不应该初始化int _Toggle
,你只想声明它以便unity可以设置它的值。
去掉第二个#include "UnityCG.cginc"
,去掉int _Toggle = 0;
,把int _Toggle;
(注意:没有初始化)放在CGPROGRAM
.[=26=下面的某个地方]
此外,将 Properties
块更改为使用大写字母 I Int
:
Shader "Custom/VertexColor" { // Where it will appear inside of the Shader Dropdown Menu of the Material / Name of the shader
Properties{
_Toggle ("Toggle context", Int) = 0
}
SubShader{
Tags { "RenderType" = "Opaque" }
LOD 200
CGPROGRAM
#pragma surface surf Lambert vertex:vert
#pragma target 3.0
#include "UnityCG.cginc"
int _Toggle;
struct Input {
float4 vertColor;
};
void vert(inout appdata_full v, out Input o) {
UNITY_INITIALIZE_OUTPUT(Input, o);
o.vertColor = v.color;
}
void surf(Input IN, inout SurfaceOutput o) {
o.Albedo = IN.vertColor.rgb;
clip(_Toggle * (0.5f - IN.vertColor.b));
}
ENDCG
}
FallBack "Diffuse"
}
然后,在你的 C# 代码中,你需要使用 SetInt
而不是 SetFloat
因为 _Toggle
是一个 int
.
此外,使用 renderer.sharedMaterial
而不是 renderer.material
!