diff --git a/Assets/Preset.meta b/Assets/Preset.meta new file mode 100644 index 00000000..5686247b --- /dev/null +++ b/Assets/Preset.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: ecda75af11211dd4ead9d2948b3d3b7e +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Preset/후원.meta b/Assets/Preset/후원.meta new file mode 100644 index 00000000..b4f29315 --- /dev/null +++ b/Assets/Preset/후원.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 6d80c97dc0290914c9ccf17efc450e2f +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Preset/후원/WefLab.prefab b/Assets/Preset/후원/WefLab.prefab new file mode 100644 index 00000000..7f1efe81 --- /dev/null +++ b/Assets/Preset/후원/WefLab.prefab @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:b0ee97ead98f0e435692aa7b7c2e1233f7dfc4d8042f2722aa26448ccaa1635a +size 4294 diff --git a/Assets/Preset/후원/WefLab.prefab.meta b/Assets/Preset/후원/WefLab.prefab.meta new file mode 100644 index 00000000..fce9d4f9 --- /dev/null +++ b/Assets/Preset/후원/WefLab.prefab.meta @@ -0,0 +1,7 @@ +fileFormatVersion: 2 +guid: 9470035ddd1c1aa4bb67805985097d7d +PrefabImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Preset/후원/던질 프랍.meta b/Assets/Preset/후원/던질 프랍.meta new file mode 100644 index 00000000..fc16f9e2 --- /dev/null +++ b/Assets/Preset/후원/던질 프랍.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 7066e932cb18c694594dc51b487741c2 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Preset/후원/던질 프랍/돈주머니.prefab b/Assets/Preset/후원/던질 프랍/돈주머니.prefab new file mode 100644 index 00000000..9c7e9a21 --- /dev/null +++ b/Assets/Preset/후원/던질 프랍/돈주머니.prefab @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:f441163a128e2a89a8028c12b951d3b0f260e74879d801b19cc5d2518e81a9c5 +size 5239 diff --git a/Assets/Preset/후원/던질 프랍/돈주머니.prefab.meta b/Assets/Preset/후원/던질 프랍/돈주머니.prefab.meta new file mode 100644 index 00000000..e6a2062a --- /dev/null +++ b/Assets/Preset/후원/던질 프랍/돈주머니.prefab.meta @@ -0,0 +1,7 @@ +fileFormatVersion: 2 +guid: 6b5a0e552e06dfd4a82dfbaa0d8fdac3 +PrefabImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Resources/Settings/BackgroundSceneDatabase.asset b/Assets/Resources/Settings/BackgroundSceneDatabase.asset index 6fcb2c56..af5dbd4c 100644 --- a/Assets/Resources/Settings/BackgroundSceneDatabase.asset +++ b/Assets/Resources/Settings/BackgroundSceneDatabase.asset @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:bd05369600d7fbe597a7594d232ad20b5204b6e91932c5aa44d5e7a5dd496ef3 -size 16760 +oid sha256:c1105a6411bafc16123c0dd1b9fe21da6652a32a69ba94c5a83e6e953b25a229 +size 16817 diff --git a/Assets/Resources/Settings/PropDatabase.asset b/Assets/Resources/Settings/PropDatabase.asset index 2d604778..45660590 100644 --- a/Assets/Resources/Settings/PropDatabase.asset +++ b/Assets/Resources/Settings/PropDatabase.asset @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:24f5dc70556d857d6e1ddfe9bb98b55766d1c54cfc3c1caabc709ddbcc7b0a26 -size 14756 +oid sha256:d11275bdfb6985c9782fcef88d9b97d91a66ca8b8b1d2ff4d5d6d76272ecd621 +size 15280 diff --git a/Assets/Resources/Settings/Streamingle Render Pipeline Asset_Renderer.asset b/Assets/Resources/Settings/Streamingle Render Pipeline Asset_Renderer.asset index 8f27120e..dfe49140 100644 --- a/Assets/Resources/Settings/Streamingle Render Pipeline Asset_Renderer.asset +++ b/Assets/Resources/Settings/Streamingle Render Pipeline Asset_Renderer.asset @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:8f7cef64b1251ba5c14b794828bd3d2a93853036c00ad15d5dc460b199104f5b +oid sha256:7b7c172f8b3382a5a1bcd3ea423c0ecf91ea069e90841388d85f56bf4789bca3 size 18958 diff --git a/Assets/ResourcesData/Prop/돈주머니.meta b/Assets/ResourcesData/Prop/돈주머니.meta new file mode 100644 index 00000000..40d10ea7 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 4b7d1ad4cc4839d408d3d6e39ec6047f +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Model.meta b/Assets/ResourcesData/Prop/돈주머니/Model.meta new file mode 100644 index 00000000..b857043f --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 06d22216356ccad42b5434d79bc5ac8c +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials.meta b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials.meta new file mode 100644 index 00000000..b1105236 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 2195070c29d0ed04ab72ed53f6780ce0 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials/material_0.mat b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials/material_0.mat new file mode 100644 index 00000000..a1728c4c --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials/material_0.mat @@ -0,0 +1,1191 @@ +%YAML 1.1 +%TAG !u! tag:unity3d.com,2011: +--- !u!114 &-155935107956252699 +MonoBehaviour: + m_ObjectHideFlags: 11 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 0} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: d0353a89b1f911e48b9e16bdc9f2e058, type: 3} + m_Name: + m_EditorClassIdentifier: Unity.RenderPipelines.Universal.Editor::UnityEditor.Rendering.Universal.AssetVersion + version: 10 +--- !u!21 &2100000 +Material: + serializedVersion: 8 + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_Name: material_0 + m_Shader: {fileID: 4800000, guid: b4f674f383806e5419ee221e39445de0, type: 3} + m_Parent: {fileID: 0} + m_ModifiedSerializedProperties: 0 + m_ValidKeywords: + - _DEPTHTEX_RIMLIGHT_FIX_DOTTED_LINE_ARTIFACTS + - _RECEIVE_URP_SHADOW + m_InvalidKeywords: [] + m_LightmapFlags: 4 + m_EnableInstancingVariants: 0 + m_DoubleSidedGI: 0 + m_CustomRenderQueue: -1 + stringTagMap: {} + disabledShaderPasses: + - MOTIONVECTORS + m_LockedProperties: + m_SavedProperties: + serializedVersion: 3 + m_TexEnvs: + - _AlphaOverrideTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMap: + m_Texture: {fileID: 2800000, guid: 3ded3cb3c3ae6f243b3a449aef14524f, type: 3} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer10MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer10Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer1MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer1Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer2MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer2Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer3MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer3Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer4MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer4Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer5MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer5Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer6MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer6Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer7MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer7Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer8MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer8Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer9MaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BaseMapStackingLayer9Tex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BumpMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _CharacterAreaColorFillTexture: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DepthTexRimLightAndShadowWidthTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DepthTexRimLightMaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DetailAlbedoMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DetailMask: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DetailNormalMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DissolveThresholdMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DynamicEyePupilMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DynamicEyePupilMaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DynamicEyeWhiteMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DynamicRampLightingTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _EmissionAnimTintRampMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _EmissionMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _EmissionMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _EnvironmentReflectionMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _Face3DRimLightAndShadow_CheekRimLightMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _Face3DRimLightAndShadow_CheekShadowMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _Face3DRimLightAndShadow_NoseRimLightMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _Face3DRimLightAndShadow_NoseShadowMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _FaceMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _FaceShadowGradientMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _FaceShadowGradientMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _HairStrandSpecularTintMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MainTex: + m_Texture: {fileID: 2800000, guid: 3ded3cb3c3ae6f243b3a449aef14524f, type: 3} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MatCapAdditiveMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MatCapAdditiveMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MatCapAlphaBlendMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MatCapAlphaBlendMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MatCapOcclusionMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MatCapOcclusionMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MetallicGlossMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _NiloGlitterTintColorTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _NiloToonSelfShadowIntensityMultiplierTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OcclusionMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OutlineTintColorMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OutlineWidthTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OutlineZOffsetMaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OverrideOutlineColorTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OverrideShadowColorMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OverrideShadowColorTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _ParallaxMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _PerCharacterBaseMapOverrideMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _PerMaterialDissolvePatternMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _PerMaterialDissolveThresholdMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _RampLightingSampleUvYTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _RampLightingTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _RampSpecularSampleUvYTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _RampSpecularTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _ScreenSpaceOutlineDepthSensitivityTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _ScreenSpaceOutlineNormalsSensitivityTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _ShadingGradeMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _SkinMaskMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _SmoothnessMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _SpecGlossMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _SpecularColorTintMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _SpecularMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _ZOffsetMaskTex: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - unity_Lightmaps: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - unity_LightmapsInd: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - unity_ShadowMasks: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + m_Ints: + - _CharacterID: 0 + - _DissolveMode: 0 + m_Floats: + - _AddPrecomputedVelocity: 0 + - _AdditionalLightCelShadeMidPoint: 0 + - _AdditionalLightCelShadeMidPointForFaceArea: 0 + - _AdditionalLightCelShadeSoftness: 0.05 + - _AdditionalLightCelShadeSoftnessForFaceArea: 0.15 + - _AdditionalLightDistanceAttenuationClamp: 2 + - _AdditionalLightIgnoreCelShade: 0.2 + - _AdditionalLightIgnoreCelShadeForFaceArea: 0.2 + - _AdditionalLightIgnoreOcclusion: 0.2 + - _AllowNiloToonBloomCharacterAreaOverride: 1 + - _AllowPerCharacterDissolve: 1 + - _AllowPerCharacterDitherFadeout: 1 + - _AllowRenderDepthOnlyOrDepthNormalsPass: 1 + - _AllowRenderExtraThickOutlinePass: 1 + - _AllowRenderMotionVectorsPass: 1 + - _AllowRenderNiloToonCharacterAreaColorFillPass: 1 + - _AllowRenderNiloToonCharacterAreaStencilBufferFillPass: 1 + - _AllowRenderNiloToonPrepassBufferPass: 1 + - _AllowRenderNiloToonSelfShadowPass: 1 + - _AllowRenderURPShadowCasterPass: 1 + - _AllowRenderURPUniversalForwardOnlyPass: 1 + - _AllowedNiloToonBloomOverrideStrength: 1 + - _AlphaClip: 0 + - _AlphaOverrideMode: 0 + - _AlphaOverrideStrength: 1 + - _AlphaOverrideTexInvertColor: 0 + - _AlphaOverrideTexUVIndex: 0 + - _AlphaOverrideTexValueOffset: 0 + - _AlphaOverrideTexValueScale: 1 + - _AlphaToMask: 0 + - _ApplyAlphaOverrideOnlyWhenFaceForwardIsPointingToCamera: 0 + - _ApplyAlphaOverrideOnlyWhenFaceForwardIsPointingToCameraRemapEnd: 1 + - _ApplyAlphaOverrideOnlyWhenFaceForwardIsPointingToCameraRemapMinMaxSlider: 1 + - _ApplyAlphaOverrideOnlyWhenFaceForwardIsPointingToCameraRemapStart: 0 + - _ApplyDepthTexRimLightFixDottedLineArtifacts: 1 + - _AsUnlit: 0 + - _BackFaceForceShadow: 0 + - _BaseMapBrightness: 1 + - _BaseMapStackingLayer10ApplytoFaces: 0 + - _BaseMapStackingLayer10ColorBlendMode: 0 + - _BaseMapStackingLayer10Enable: 0 + - _BaseMapStackingLayer10MaskInvertColor: 0 + - _BaseMapStackingLayer10MaskRemapEnd: 1 + - _BaseMapStackingLayer10MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer10MaskRemapStart: 0 + - _BaseMapStackingLayer10MaskTexAsIDMap: 0 + - _BaseMapStackingLayer10MaskTexExtractFromID: 255 + - _BaseMapStackingLayer10MaskUVIndex: 0 + - _BaseMapStackingLayer10MasterStrength: 1 + - _BaseMapStackingLayer10TexIgnoreAlpha: 0 + - _BaseMapStackingLayer10TexUVIndex: 0 + - _BaseMapStackingLayer10TexUVRotateSpeed: 0 + - _BaseMapStackingLayer10TexUVRotatedAngle: 0 + - _BaseMapStackingLayer1ApplytoFaces: 0 + - _BaseMapStackingLayer1ColorBlendMode: 0 + - _BaseMapStackingLayer1Enable: 0 + - _BaseMapStackingLayer1MaskInvertColor: 0 + - _BaseMapStackingLayer1MaskRemapEnd: 1 + - _BaseMapStackingLayer1MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer1MaskRemapStart: 0 + - _BaseMapStackingLayer1MaskTexAsIDMap: 0 + - _BaseMapStackingLayer1MaskTexExtractFromID: 255 + - _BaseMapStackingLayer1MaskUVIndex: 0 + - _BaseMapStackingLayer1MasterStrength: 1 + - _BaseMapStackingLayer1TexIgnoreAlpha: 0 + - _BaseMapStackingLayer1TexUVIndex: 0 + - _BaseMapStackingLayer1TexUVRotateSpeed: 0 + - _BaseMapStackingLayer1TexUVRotatedAngle: 0 + - _BaseMapStackingLayer2ApplytoFaces: 0 + - _BaseMapStackingLayer2ColorBlendMode: 0 + - _BaseMapStackingLayer2Enable: 0 + - _BaseMapStackingLayer2MaskInvertColor: 0 + - _BaseMapStackingLayer2MaskRemapEnd: 1 + - _BaseMapStackingLayer2MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer2MaskRemapStart: 0 + - _BaseMapStackingLayer2MaskTexAsIDMap: 0 + - _BaseMapStackingLayer2MaskTexExtractFromID: 255 + - _BaseMapStackingLayer2MaskUVIndex: 0 + - _BaseMapStackingLayer2MasterStrength: 1 + - _BaseMapStackingLayer2TexIgnoreAlpha: 0 + - _BaseMapStackingLayer2TexUVIndex: 0 + - _BaseMapStackingLayer2TexUVRotateSpeed: 0 + - _BaseMapStackingLayer2TexUVRotatedAngle: 0 + - _BaseMapStackingLayer3ApplytoFaces: 0 + - _BaseMapStackingLayer3ColorBlendMode: 0 + - _BaseMapStackingLayer3Enable: 0 + - _BaseMapStackingLayer3MaskInvertColor: 0 + - _BaseMapStackingLayer3MaskRemapEnd: 1 + - _BaseMapStackingLayer3MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer3MaskRemapStart: 0 + - _BaseMapStackingLayer3MaskTexAsIDMap: 0 + - _BaseMapStackingLayer3MaskTexExtractFromID: 255 + - _BaseMapStackingLayer3MaskUVIndex: 0 + - _BaseMapStackingLayer3MasterStrength: 1 + - _BaseMapStackingLayer3TexIgnoreAlpha: 0 + - _BaseMapStackingLayer3TexUVIndex: 0 + - _BaseMapStackingLayer3TexUVRotateSpeed: 0 + - _BaseMapStackingLayer3TexUVRotatedAngle: 0 + - _BaseMapStackingLayer4ApplytoFaces: 0 + - _BaseMapStackingLayer4ColorBlendMode: 0 + - _BaseMapStackingLayer4Enable: 0 + - _BaseMapStackingLayer4MaskInvertColor: 0 + - _BaseMapStackingLayer4MaskRemapEnd: 1 + - _BaseMapStackingLayer4MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer4MaskRemapStart: 0 + - _BaseMapStackingLayer4MaskTexAsIDMap: 0 + - _BaseMapStackingLayer4MaskTexExtractFromID: 255 + - _BaseMapStackingLayer4MaskUVIndex: 0 + - _BaseMapStackingLayer4MasterStrength: 1 + - _BaseMapStackingLayer4TexIgnoreAlpha: 0 + - _BaseMapStackingLayer4TexUVIndex: 0 + - _BaseMapStackingLayer4TexUVRotateSpeed: 0 + - _BaseMapStackingLayer4TexUVRotatedAngle: 0 + - _BaseMapStackingLayer5ApplytoFaces: 0 + - _BaseMapStackingLayer5ColorBlendMode: 0 + - _BaseMapStackingLayer5Enable: 0 + - _BaseMapStackingLayer5MaskInvertColor: 0 + - _BaseMapStackingLayer5MaskRemapEnd: 1 + - _BaseMapStackingLayer5MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer5MaskRemapStart: 0 + - _BaseMapStackingLayer5MaskTexAsIDMap: 0 + - _BaseMapStackingLayer5MaskTexExtractFromID: 255 + - _BaseMapStackingLayer5MaskUVIndex: 0 + - _BaseMapStackingLayer5MasterStrength: 1 + - _BaseMapStackingLayer5TexIgnoreAlpha: 0 + - _BaseMapStackingLayer5TexUVIndex: 0 + - _BaseMapStackingLayer5TexUVRotateSpeed: 0 + - _BaseMapStackingLayer5TexUVRotatedAngle: 0 + - _BaseMapStackingLayer6ApplytoFaces: 0 + - _BaseMapStackingLayer6ColorBlendMode: 0 + - _BaseMapStackingLayer6Enable: 0 + - _BaseMapStackingLayer6MaskInvertColor: 0 + - _BaseMapStackingLayer6MaskRemapEnd: 1 + - _BaseMapStackingLayer6MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer6MaskRemapStart: 0 + - _BaseMapStackingLayer6MaskTexAsIDMap: 0 + - _BaseMapStackingLayer6MaskTexExtractFromID: 255 + - _BaseMapStackingLayer6MaskUVIndex: 0 + - _BaseMapStackingLayer6MasterStrength: 1 + - _BaseMapStackingLayer6TexIgnoreAlpha: 0 + - _BaseMapStackingLayer6TexUVIndex: 0 + - _BaseMapStackingLayer6TexUVRotateSpeed: 0 + - _BaseMapStackingLayer6TexUVRotatedAngle: 0 + - _BaseMapStackingLayer7ApplytoFaces: 0 + - _BaseMapStackingLayer7ColorBlendMode: 0 + - _BaseMapStackingLayer7Enable: 0 + - _BaseMapStackingLayer7MaskInvertColor: 0 + - _BaseMapStackingLayer7MaskRemapEnd: 1 + - _BaseMapStackingLayer7MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer7MaskRemapStart: 0 + - _BaseMapStackingLayer7MaskTexAsIDMap: 0 + - _BaseMapStackingLayer7MaskTexExtractFromID: 255 + - _BaseMapStackingLayer7MaskUVIndex: 0 + - _BaseMapStackingLayer7MasterStrength: 1 + - _BaseMapStackingLayer7TexIgnoreAlpha: 0 + - _BaseMapStackingLayer7TexUVIndex: 0 + - _BaseMapStackingLayer7TexUVRotateSpeed: 0 + - _BaseMapStackingLayer7TexUVRotatedAngle: 0 + - _BaseMapStackingLayer8ApplytoFaces: 0 + - _BaseMapStackingLayer8ColorBlendMode: 0 + - _BaseMapStackingLayer8Enable: 0 + - _BaseMapStackingLayer8MaskInvertColor: 0 + - _BaseMapStackingLayer8MaskRemapEnd: 1 + - _BaseMapStackingLayer8MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer8MaskRemapStart: 0 + - _BaseMapStackingLayer8MaskTexAsIDMap: 0 + - _BaseMapStackingLayer8MaskTexExtractFromID: 255 + - _BaseMapStackingLayer8MaskUVIndex: 0 + - _BaseMapStackingLayer8MasterStrength: 1 + - _BaseMapStackingLayer8TexIgnoreAlpha: 0 + - _BaseMapStackingLayer8TexUVIndex: 0 + - _BaseMapStackingLayer8TexUVRotateSpeed: 0 + - _BaseMapStackingLayer8TexUVRotatedAngle: 0 + - _BaseMapStackingLayer9ApplytoFaces: 0 + - _BaseMapStackingLayer9ColorBlendMode: 0 + - _BaseMapStackingLayer9Enable: 0 + - _BaseMapStackingLayer9MaskInvertColor: 0 + - _BaseMapStackingLayer9MaskRemapEnd: 1 + - _BaseMapStackingLayer9MaskRemapMinMaxSlider: 1 + - _BaseMapStackingLayer9MaskRemapStart: 0 + - _BaseMapStackingLayer9MaskTexAsIDMap: 0 + - _BaseMapStackingLayer9MaskTexExtractFromID: 255 + - _BaseMapStackingLayer9MaskUVIndex: 0 + - _BaseMapStackingLayer9MasterStrength: 1 + - _BaseMapStackingLayer9TexIgnoreAlpha: 0 + - _BaseMapStackingLayer9TexUVIndex: 0 + - _BaseMapStackingLayer9TexUVRotateSpeed: 0 + - _BaseMapStackingLayer9TexUVRotatedAngle: 0 + - _BaseMapUVIndex: 0 + - _Blend: 0 + - _BlendModePreserveSpecular: 1 + - _BlendOp: 0 + - _BumpMapApplytoFaces: 0 + - _BumpMapUVIndex: 0 + - _BumpScale: 1 + - _CelShadeMidPoint: 0 + - _CelShadeMidPointForFaceArea: -0.3 + - _CelShadeSoftness: 0.05 + - _CelShadeSoftnessForFaceArea: 0.15 + - _CharacterAreaColorFillEnabled: 0 + - _CharacterAreaColorFillRendersBlockedArea: 0 + - _CharacterAreaColorFillRendersVisibleArea: 0 + - _CharacterAreaColorFillTextureUVIndex: 5 + - _CharacterBoundRadius: 1.25 + - _ClearCoatMask: 0 + - _ClearCoatSmoothness: 0 + - _ColorMask: 15 + - _ColorRenderStatesGroup: 0 + - _ColorRenderStatesGroupPreset: 0 + - _ControlledByNiloToonPerCharacterRenderController: 0 + - _Cull: 2 + - _CullNiloToonSelfShadowCaster: 1 + - _CullOutline: 1 + - _Cutoff: 0.5 + - _DebugFaceShadowGradientMap: 0 + - _DecalAlbedoApplyStrength: 1 + - _DecalGroup: 0 + - _DecalNormalApplyStrength: 1 + - _DecalOcclusionApplyStrength: 1 + - _DecalSmoothnessApplyStrength: 1 + - _DecalSpecularApplyStrength: 1 + - _DepthRenderStatesGroup: 0 + - _DepthTexRimLight3DFallbackMidPoint: 0.7 + - _DepthTexRimLight3DFallbackRemoveFlatPolygonRimLight: 1 + - _DepthTexRimLight3DFallbackSoftness: 0.02 + - _DepthTexRimLight3DRimMaskEnable: 0 + - _DepthTexRimLight3DRimMaskThreshold: 0.5 + - _DepthTexRimLightAndShadowReduceWidthWhenCameraIsClose: 1 + - _DepthTexRimLightAndShadowSafeViewDistance: 1 + - _DepthTexRimLightAndShadowWidthExtraMultiplier: 1 + - _DepthTexRimLightAndShadowWidthMultiplier: 0.5 + - _DepthTexRimLightBlockByShadow: 0 + - _DepthTexRimLightFadeoutRange: 1 + - _DepthTexRimLightFixDottedLineArtifactsExtendMultiplier: 0.1 + - _DepthTexRimLightIgnoreLightDir: 0 + - _DepthTexRimLightIntensity: 1.5 + - _DepthTexRimLightMaskTexInvertColor: 0 + - _DepthTexRimLightMinimumThresholdOffsetForFace: 0.5 + - _DepthTexRimLightMixWithBaseMapColor: 0.5 + - _DepthTexRimLightThresholdOffset: 0 + - _DepthTexRimLightUsage: 1 + - _DepthTexRimLightWidthClampForFace: 0.5 + - _DepthTexRimLightWidthMultiplier: 1 + - _DepthTexShadowBrightness: 0.85 + - _DepthTexShadowBrightnessForFace: 1 + - _DepthTexShadowColorStyleForFacePreset: 0 + - _DepthTexShadowColorStyleForNonFacePreset: 0 + - _DepthTexShadowFadeoutRange: 1 + - _DepthTexShadowFixedDirectionForFace: 0 + - _DepthTexShadowThresholdOffset: 0 + - _DepthTexShadowUsage: 1 + - _DepthTexShadowWidthMultiplier: 1 + - _DetailAlbedoMapScale: 1 + - _DetailAlbedoWhitePoint: 0.5 + - _DetailMaskInvertColor: 0 + - _DetailNormalMapScale: 1 + - _DetailUseSecondUv: 0 + - _DissolveAmount: 0 + - _DissolveBorderRange: 0.02 + - _DissolveNoiseStrength: 1 + - _DissolvePatternMapPreset: 0 + - _DissolveThresholdMapPreset: 0 + - _DissolveThresholdMapTilingX: 1 + - _DissolveThresholdMapTilingY: 1 + - _DitherFadeoutAmount: 0 + - _DitherFadeoutNormalScaleFix: 1 + - _DstBlend: 0 + - _DstBlendAlpha: 0 + - _DynamicEyeFinalBrightness: 2 + - _DynamicEyePupilDepthScale: 0.4 + - _DynamicEyePupilMaskSoftness: 0.216 + - _DynamicEyePupilSize: -0.384 + - _DynamicEyeSize: 2.2 + - _EditFinalOutputAlphaEnable: 0 + - _EmissionAnimTintRampMapSpeed: 1 + - _EmissionIntensity: 1 + - _EmissionMapUseSingleChannelOnly: 0 + - _EmissionMaskMapInvertColor: 0 + - _EmissionMaskMapRemapEnd: 1 + - _EmissionMaskMapRemapMinMaxSlider: 1 + - _EmissionMaskMapRemapStart: 0 + - _EnableDynamicEyeFeature: 0 + - _EnableEmissionAnimTintRampMap: 0 + - _EnableFace3DRimLightAndShadow: 0 + - _EnableNiloToonSelfShadowMapping: 1 + - _EnableNiloToonSelfShadowMappingDepthBias: 0 + - _EnableNiloToonSelfShadowMappingNormalBias: 0 + - _EnablePerMaterialDissolve: 0 + - _EnableRendering: 1 + - _EnableShadowColor: 1 + - _EnableUVEditGroup: 0 + - _EnvironmentReflectionApplyAddBlending: 0 + - _EnvironmentReflectionApplyReplaceBlending: 1 + - _EnvironmentReflectionApplytoFaces: 0 + - _EnvironmentReflectionBrightness: 1 + - _EnvironmentReflectionFresnelEffect: 0 + - _EnvironmentReflectionFresnelPower: 1 + - _EnvironmentReflectionFresnelRemapEnd: 1 + - _EnvironmentReflectionFresnelRemapMinMaxSlider: 1 + - _EnvironmentReflectionFresnelRemapStart: 0 + - _EnvironmentReflectionMaskMapInvertColor: 0 + - _EnvironmentReflectionMaskMapRemapEnd: 1 + - _EnvironmentReflectionMaskMapRemapMinMaxSlider: 1 + - _EnvironmentReflectionMaskMapRemapStart: 0 + - _EnvironmentReflectionShouldApplyToFaceArea: 0 + - _EnvironmentReflectionSmoothnessMultiplier: 1 + - _EnvironmentReflectionTintAlbedo: 1 + - _EnvironmentReflectionUsage: 1 + - _EnvironmentReflections: 1 + - _ExtraThickOutlineEnabled: 0 + - _ExtraThickOutlineMaxFinalWidth: 100 + - _ExtraThickOutlineWidth: 4 + - _ExtraThickOutlineWriteIntoDepthTexture: 0 + - _ExtraThickOutlineZOffset: -0.1 + - _ExtraThickOutlineZWrite: 0 + - _Face3DRimLightAndShadow_CheekRimLightIntensity: 1 + - _Face3DRimLightAndShadow_CheekRimLightSoftness: 0.1 + - _Face3DRimLightAndShadow_CheekRimLightThreshold: 0.7 + - _Face3DRimLightAndShadow_CheekShadowIntensity: 1 + - _Face3DRimLightAndShadow_CheekShadowSoftness: 0.1 + - _Face3DRimLightAndShadow_CheekShadowThreshold: 0.7 + - _Face3DRimLightAndShadow_NoseRimLightIntensity: 1 + - _Face3DRimLightAndShadow_NoseShadowIntensity: 1 + - _FaceAreaCameraDepthTextureZWriteOffset: 0.04 + - _FaceMaskMapInvertColor: 0 + - _FaceMaskMapRemapEnd: 1 + - _FaceMaskMapRemapMinMaxSlider: 1 + - _FaceMaskMapRemapStart: 0 + - _FaceShadowBrightness: 1 + - _FaceShadowGradientIntensity: 1 + - _FaceShadowGradientMapFaceMidPoint: 0.5 + - _FaceShadowGradientMapInvertColor: 0 + - _FaceShadowGradientMapPreset: 0 + - _FaceShadowGradientMapUVIndex: 0 + - _FaceShadowGradientMapUVxInvert: 1 + - _FaceShadowGradientMaskMapInvertColor: 0 + - _FaceShadowGradientMaskMapUVIndex: 0 + - _FaceShadowGradientOffset: 0.1 + - _FaceShadowGradientResultSoftness: 0.005 + - _FaceShadowGradientThresholdMax: 1 + - _FaceShadowGradientThresholdMin: 0 + - _FaceShadowGradientThresholdMinMax: 1 + - _FixFaceNormalAmount: 1 + - _FixFaceNormalAmountPerMaterial: 1 + - _FixFaceNormalUseFlattenOrProxySphereMethod: 0 + - _ForceFinalOutputAlphaEqualsOne: 0 + - _GGXDirectSpecularSmoothnessMultiplier: 1 + - _GlossMapScale: 0 + - _Glossiness: 0 + - _GlossyReflections: 0 + - _HairStrandSpecularMainExponent: 256 + - _HairStrandSpecularMainIntensity: 1 + - _HairStrandSpecularMixWithBaseMapColor: 0.5 + - _HairStrandSpecularOverallIntensity: 1 + - _HairStrandSpecularSecondExponent: 128 + - _HairStrandSpecularSecondIntensity: 1 + - _HairStrandSpecularShapeFrequency: 750 + - _HairStrandSpecularShapePositionOffset: 0 + - _HairStrandSpecularShapeShift: 0.015 + - _HairStrandSpecularTintMapUsage: 1 + - _HairStrandSpecularUVDirection: 0 + - _HairStrandSpecularUVIndex: 0 + - _IgnoreDefaultMainLightFaceShadow: 1 + - _IndirectLightFlatten: 1 + - _IsFace: 0 + - _IsSkin: 0 + - _LightingStyleDirectionalLightRenderFacePreset: 0 + - _LightingStyleFaceOverrideGroup: 0 + - _LightingStyleGroup: 0 + - _LitToShadowTransitionAreaHueOffset: 0.01 + - _LitToShadowTransitionAreaIntensity: 1 + - _LitToShadowTransitionAreaSaturationBoost: 0.5 + - _LitToShadowTransitionAreaValueMul: 1 + - _MainLightIgnoreCelShade: 0 + - _MainLightIgnoreCelShadeForFaceArea: 0 + - _MainLightNonSkinDiffuseNormalMapStrength: 1 + - _MainLightSkinDiffuseNormalMapStrength: 1 + - _MatCapAdditiveApplytoFaces: 0 + - _MatCapAdditiveExtractBrightArea: 0 + - _MatCapAdditiveIntensity: 1 + - _MatCapAdditiveMapAlphaAsMask: 0 + - _MatCapAdditiveMaskMapInvertColor: 0 + - _MatCapAdditiveMaskMapRemapEnd: 1 + - _MatCapAdditiveMaskMapRemapMinMaxSlider: 1 + - _MatCapAdditiveMaskMapRemapStart: 0 + - _MatCapAdditiveMixWithBaseMapColor: 0.5 + - _MatCapAdditivePreset: 0 + - _MatCapAdditiveUvScale: 1 + - _MatCapAlphaBlendMapAlphaAsMask: 0 + - _MatCapAlphaBlendMaskMapInvertColor: 0 + - _MatCapAlphaBlendMaskMapRemapEnd: 1 + - _MatCapAlphaBlendMaskMapRemapMinMaxSlider: 1 + - _MatCapAlphaBlendMaskMapRemapStart: 0 + - _MatCapAlphaBlendPreset: 0 + - _MatCapAlphaBlendUsage: 1 + - _MatCapAlphaBlendUvScale: 1 + - _MatCapOcclusionIntensity: 1 + - _MatCapOcclusionMapAlphaAsMask: 0 + - _MatCapOcclusionMapRemapEnd: 1 + - _MatCapOcclusionMapRemapMinMaxSlider: 1 + - _MatCapOcclusionMapRemapStart: 0 + - _MatCapOcclusionMaskMapInvert: 0 + - _MatCapOcclusionMaskMapRemapEnd: 1 + - _MatCapOcclusionMaskMapRemapMinMaxSlider: 1 + - _MatCapOcclusionMaskMapRemapStart: 0 + - _MatCapOcclusionPreset: 0 + - _MatCapOcclusionUvScale: 1 + - _Metallic: 0 + - _MultiplyBRPColor: 0 + - _MultiplyBaseColorToEmissionColor: 0 + - _MultiplyBaseColorToSpecularColor: 0.5 + - _MultiplyLightColorToEmissionColor: 0 + - _NiloGlitterDensity: 1 + - _NiloGlitterIntensity: 1 + - _NiloGlitterRndomNormalStrength: 0.5 + - _NiloGlitterSize: 1 + - _NiloGlitterTintColorTexUVIndex: 0 + - _NiloGlitterUVIndex: 0 + - _NiloToonSelfShadowIntensity: 1 + - _NiloToonSelfShadowIntensityForFace: 0 + - _NiloToonSelfShadowIntensityForNonFace: 1 + - _NiloToonSelfShadowMappingDepthBias: 0 + - _NiloToonSelfShadowMappingNormalBias: 0 + - _OcclusionMapApplytoFaces: 0 + - _OcclusionMapInvertColor: 0 + - _OcclusionMapStylePreset: 0 + - _OcclusionMapUVIndex: 0 + - _OcclusionRemapEnd: 1 + - _OcclusionRemapMinMaxSlider: 1 + - _OcclusionRemapStart: 0 + - _OcclusionStrength: 1 + - _OutlineApplyAutoWidthAdjustment: 1 + - _OutlineBaseZOffset: 0 + - _OutlineUniformLengthInViewSpace: 0 + - _OutlineUseBakedSmoothNormal: 1 + - _OutlineUsePreLightingReplaceColor: 0 + - _OutlineUseReplaceColor: 0 + - _OutlineWidth: 0.5 + - _OutlineWidthExtraMultiplier: 1 + - _OutlineZOffset: 0.0001 + - _OutlineZOffsetForFaceArea: 0.02 + - _OutlineZOffsetMaskRemapEnd: 1 + - _OutlineZOffsetMaskRemapMinMaxSlider: 1 + - _OutlineZOffsetMaskRemapStart: 0 + - _OutlineZOffsetMaskTexFromVertexColorInvertColor: 0 + - _OutlineZOffsetMaskTexInvertColor: 0 + - _OverrideAdditionalLightCelShadeParamForFaceArea: 1 + - _OverrideByFaceShadowTintColor: 1 + - _OverrideBySkinShadowTintColor: 1 + - _OverrideCelShadeParamForFaceArea: 1 + - _OverrideOutlineColorByTexIntensity: 1 + - _OverrideOutlineColorTexIgnoreAlphaChannel: 0 + - _OverrideShadowColorByTexIntensity: 1 + - _OverrideShadowColorByTexMode: 0 + - _OverrideShadowColorMaskMapInvertColor: 0 + - _OverrideShadowColorTexIgnoreAlphaChannel: 0 + - _Parallax: 0.005 + - _ParallaxApplyToUVIndex: 0 + - _ParallaxMapEnable: 0 + - _ParallaxSampleUVIndex: 0 + - _PassOnOffGroup: 0 + - _PerCharEffectDesaturatePercentage: 0 + - _PerCharEffectRimSharpnessPower: 4 + - _PerCharReceiveAverageURPShadowMap: 1 + - _PerCharReceiveNiloToonSelfShadowMap: 1 + - _PerCharReceiveStandardURPShadowMap: 1 + - _PerCharZOffset: 0 + - _PerCharacterBaseMapOverrideAmount: 0 + - _PerCharacterBaseMapOverrideBlendMode: 0 + - _PerCharacterBaseMapOverrideUVIndex: 0 + - _PerCharacterEffectGroup: 0 + - _PerCharacterOutlineWidthMultiply: 1 + - _PerCharacterRenderOutline: 1 + - _PerMaterialDissolveCutoff: -1 + - _PerMaterialDissolveEdgeWidth: 0.05 + - _PerMaterialDissolvePatternMapInvertColor: 0 + - _PerMaterialDissolvePatternMapStrength: 0.1 + - _PerMaterialDissolvePatternMapUVIndex: 0 + - _PerMaterialDissolvePatternMapUVTiling: 1 + - _PerMaterialDissolveThresholdMapInvertColor: 0 + - _PerMaterialDissolveThresholdMapUVIndex: 0 + - _PerMaterialDissolveThresholdMapUVTiling: 1 + - _PerMaterialEnableDepthTextureRimLightAndShadow: 1 + - _PerspectiveRemovalAmount: 0 + - _PerspectiveRemovalEndHeight: 1 + - _PerspectiveRemovalRadius: 1 + - _PerspectiveRemovalStartHeight: 0 + - _PreMultiplyAlphaIntoRGBOutput: 0 + - _QueueOffset: 0 + - _RampLightTexMode: 1 + - _RampLightingFaceAreaRemoveEffect: 1 + - _RampLightingNdotLRemapEnd: 1 + - _RampLightingNdotLRemapMinMaxSlider: 1 + - _RampLightingNdotLRemapStart: 0 + - _RampLightingSampleUvYTexInvertColor: 0 + - _RampLightingTexSampleUvY: 0.5 + - _RampLightingUvYRemapEnd: 1 + - _RampLightingUvYRemapMinMaxSlider: 1 + - _RampLightingUvYRemapStart: 0 + - _RampSpecularTexSampleUvY: 0.5 + - _RampSpecularWhitePoint: 0.5 + - _ReceiveEnvironmentReflection: 0 + - _ReceiveSelfShadowMappingPosOffset: 0 + - _ReceiveSelfShadowMappingPosOffsetForFaceArea: 1 + - _ReceiveShadows: 1 + - _ReceiveURPAdditionalLightShadowMapping: 1 + - _ReceiveURPAdditionalLightShadowMappingAmount: 1 + - _ReceiveURPAdditionalLightShadowMappingAmountForFace: 1 + - _ReceiveURPAdditionalLightShadowMappingAmountForNonFace: 1 + - _ReceiveURPShadowMapping: 1 + - _ReceiveURPShadowMappingAmount: 1 + - _ReceiveURPShadowMappingAmountForFace: 1 + - _ReceiveURPShadowMappingAmountForNonFace: 1 + - _RenderCharacter: 1 + - _RenderFaceGroup: 0 + - _RenderFacePreset: 0 + - _RenderOutline: 1 + - _RenderScreenSpaceOutline: 0 + - _RenderScreenSpaceOutlineV2: 0 + - _ScreenSpaceOutlineDepthSensitivity: 1 + - _ScreenSpaceOutlineDepthSensitivityIfFace: 1 + - _ScreenSpaceOutlineDepthSensitivityTexRemapEnd: 1 + - _ScreenSpaceOutlineDepthSensitivityTexRemapMinMaxSlider: 1 + - _ScreenSpaceOutlineDepthSensitivityTexRemapStart: 0 + - _ScreenSpaceOutlineNormalsSensitivity: 1 + - _ScreenSpaceOutlineNormalsSensitivityIfFace: 1 + - _ScreenSpaceOutlineNormalsSensitivityTexRemapEnd: 1 + - _ScreenSpaceOutlineNormalsSensitivityTexRemapMinMaxSlider: 1 + - _ScreenSpaceOutlineNormalsSensitivityTexRemapStart: 0 + - _ScreenSpaceOutlineUseReplaceColor: 0 + - _ScreenSpaceOutlineWidth: 1 + - _ScreenSpaceOutlineWidthIfFace: 0 + - _SelfShadowAreaHSVStrength: 1 + - _SelfShadowAreaHueOffset: 0 + - _SelfShadowAreaSaturationBoost: 0.2 + - _SelfShadowAreaValueMul: 0.7 + - _ShadingGradeMapApplyRange: 1 + - _ShadingGradeMapInvertColor: 0 + - _ShadingGradeMapMidPointOffset: 0 + - _ShadingGradeMapRemapEnd: 1 + - _ShadingGradeMapRemapMinMaxSlider: 1 + - _ShadingGradeMapRemapStart: 0 + - _ShadingGradeMapStrength: 1 + - _SkinFaceShadowColorPreset: 0 + - _SkinMaskMapAsIDMap: 0 + - _SkinMaskMapExtractFromID: 255 + - _SkinMaskMapInvertColor: 0 + - _SkinMaskMapRemapEnd: 1 + - _SkinMaskMapRemapMinMaxSlider: 1 + - _SkinMaskMapRemapStart: 0 + - _SkinShadowBrightness: 1 + - _Smoothness: 0.39999998 + - _SmoothnessGroup: 0 + - _SmoothnessMapInputIsRoughnessMap: 0 + - _SmoothnessMapRemapEnd: 1 + - _SmoothnessMapRemapMinMaxSlider: 1 + - _SmoothnessMapRemapStart: 0 + - _SmoothnessTextureChannel: 0 + - _SpecularApplytoFaces: 0 + - _SpecularAreaRemapMidPoint: 0.1 + - _SpecularAreaRemapRange: 0.05 + - _SpecularAreaRemapUsage: 0 + - _SpecularColorTintMapUsage: 1 + - _SpecularColorTintMapUseSecondUv: 0 + - _SpecularHighlights: 1 + - _SpecularIntensity: 1 + - _SpecularMapAsIDMap: 0 + - _SpecularMapExtractFromID: 255 + - _SpecularMapInvertColor: 0 + - _SpecularMapRemapEnd: 1 + - _SpecularMapRemapMinMaxSlider: 1 + - _SpecularMapRemapStart: 0 + - _SpecularMapUVIndex: 0 + - _SpecularReactToLightDirMode: 0 + - _SpecularShowInShadowArea: 0 + - _SpecularUseReplaceBlending: 0 + - _SrcBlend: 1 + - _SrcBlendAlpha: 1 + - _StencilComp: 0 + - _StencilGroup: 0 + - _StencilPass: 0 + - _StencilPreset: 0 + - _StencilRef: 0 + - _SupportClothDynamics: 0 + - _Surface: 0 + - _SurfaceTypePreset: 0 + - _UIDisplayMode: 100 + - _UV0RotateSpeed: 0 + - _UV0RotatedAngle: 0 + - _UV1RotateSpeed: 0 + - _UV1RotatedAngle: 0 + - _UV2RotateSpeed: 0 + - _UV2RotatedAngle: 0 + - _UV3RotateSpeed: 0 + - _UV3RotatedAngle: 0 + - _UnityCameraDepthTextureWriteOutlineExtrudedPosition: 0 + - _UseAlphaOverrideTex: 0 + - _UseDepthTexRimLightAndShadowWidthMultiplierFromVertexColor: 0 + - _UseDepthTexRimLightAndShadowWidthTex: 0 + - _UseDepthTexRimLightMaskTex: 0 + - _UseDetailMap: 0 + - _UseEmission: 0 + - _UseFaceMaskMap: 0 + - _UseFaceShadowGradientMap: 0 + - _UseGGXDirectSpecular: 1 + - _UseHairStrandSpecularTintMap: 0 + - _UseKajiyaKaySpecular: 0 + - _UseMatCapAdditive: 0 + - _UseMatCapAlphaBlend: 0 + - _UseMatCapOcclusion: 0 + - _UseNiloGlitter: 0 + - _UseNiloToonSelfShadowIntensityMultiplierTex: 0 + - _UseNormalMap: 0 + - _UseOcclusion: 0 + - _UseOutlineTintColorMap: 0 + - _UseOutlineWidthMaskFromVertexColor: 0 + - _UseOutlineWidthTex: 0 + - _UseOutlineZOffsetMaskFromVertexColor: 0 + - _UseOutlineZOffsetTex: 0 + - _UseOverrideOutlineColorByTexture: 0 + - _UseOverrideShadowColorByTexture: 0 + - _UseRampLightingSampleUvYTex: 0 + - _UseRampLightingTex: 0 + - _UseRampSpecularSampleUvYTex: 0 + - _UseRampSpecularTex: 0 + - _UseShadingGradeMap: 0 + - _UseSkinMaskMap: 0 + - _UseSmoothnessMap: 0 + - _UseSpecular: 0 + - _UseSpecularColorTintMap: 0 + - _UseZOffsetMaskTex: 0 + - _WorkflowMode: 1 + - _XRMotionVectorsPass: 1 + - _ZOffset: 0 + - _ZOffsetEnable: 0 + - _ZOffsetMaskMapInvertColor: 0 + - _ZOffsetMultiplierForTraditionalOutlinePass: 1 + - _ZOffsetPreset: 0 + - _ZTest: 4 + - _ZWrite: 1 + m_Colors: + - _AlphaOverrideTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _BackFaceBaseMapReplaceColor: {r: 0, g: 0, b: 0, a: 0} + - _BackFaceTintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseColor2: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer10MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer10TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer10TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer10TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer10TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer1MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer1TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer1TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer1TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer1TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer2MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer2TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer2TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer2TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer2TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer3MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer3TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer3TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer3TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer3TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer4MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer4TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer4TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer4TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer4TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer5MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer5TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer5TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer5TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer5TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer6MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer6TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer6TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer6TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer6TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer7MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer7TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer7TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer7TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer7TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer8MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer8TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer8TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer8TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer8TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BaseMapStackingLayer9MaskTexChannel: {r: 0, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer9TexUVAnimSpeed: {r: 0, g: 0, b: 0, a: 0} + - _BaseMapStackingLayer9TexUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer9TexUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BaseMapStackingLayer9TintColor: {r: 1, g: 1, b: 1, a: 1} + - _BumpMapUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _BumpMapUVScrollSpeed: {r: 0, g: 0, b: 0, a: 0} + - _CharacterAreaColorFillColor: {r: 1, g: 1, b: 1, a: 0.5} + - _CharacterAreaColorFillTextureUVScrollSpeed: {r: 0, g: 0, b: 0, a: 1} + - _CharacterAreaColorFillTextureUVTilingOffset: {r: 1, g: 1, b: 0, a: 0} + - _CharacterBoundCenterPosWS: {r: 0, g: 0, b: 0, a: 1} + - _Color: {r: 1, g: 1, b: 1, a: 1} + - _DepthTexRimLightAndShadowWidthMultiplierFromVertexColorChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _DepthTexRimLightAndShadowWidthTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _DepthTexRimLightMaskTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _DepthTexRimLightTintColor: {r: 1, g: 1, b: 1, a: 1} + - _DepthTexShadowTintColor: {r: 1, g: 1, b: 1, a: 1} + - _DepthTexShadowTintColorForFace: {r: 1, g: 0.85, b: 0.85, a: 1} + - _DetailMapsScaleTiling: {r: 1, g: 1, b: 0, a: 0} + - _DetailMaskChannelMask: {r: 1, g: 0, b: 0, a: 0} + - _DissolveBorderTintColor: {r: 0, g: 4, b: 4, a: 1} + - _DynamicEyeFinalTintColor: {r: 1, g: 1, b: 1, a: 1} + - _DynamicEyePupilColor: {r: 1, g: 1, b: 1, a: 1} + - _DynamicEyePupilMaskTexChannelMask: {r: 0, g: 0, b: 0, a: 1} + - _EmissionColor: {r: 0, g: 0, b: 0, a: 1} + - _EmissionMapSingleChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _EmissionMapTilingXyOffsetZw: {r: 1, g: 1, b: 0, a: 0} + - _EmissionMapUVScrollSpeed: {r: 0, g: 0, b: 0, a: 0} + - _EmissionMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _EnvironmentReflectionColor: {r: 1, g: 1, b: 1, a: 1} + - _EnvironmentReflectionMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _ExtraThickOutlineColor: {r: 1, g: 1, b: 1, a: 1} + - _ExtraThickOutlineViewSpacePosOffset: {r: 0, g: 0, b: 0, a: 1} + - _Face3DRimLightAndShadow_CheekRimLightMaskMapChannel: {r: 1, g: 0, b: 0, a: 0} + - _Face3DRimLightAndShadow_CheekRimLightTintColor: {r: 1, g: 1, b: 1, a: 1} + - _Face3DRimLightAndShadow_CheekShadowMaskMapChannel: {r: 1, g: 0, b: 0, a: 0} + - _Face3DRimLightAndShadow_CheekShadowTintColor: {r: 1, g: 1, b: 1, a: 1} + - _Face3DRimLightAndShadow_NoseRimLightMaskMapChannel: {r: 1, g: 0, b: 0, a: 0} + - _Face3DRimLightAndShadow_NoseRimLightTintColor: {r: 1, g: 1, b: 1, a: 1} + - _Face3DRimLightAndShadow_NoseShadowMaskMapChannel: {r: 1, g: 0, b: 0, a: 0} + - _Face3DRimLightAndShadow_NoseShadowTintColor: {r: 1, g: 1, b: 1, a: 1} + - _FaceForwardDirection: {r: 0, g: 0, b: 1, a: 1} + - _FaceMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _FaceShadowGradientMapChannel: {r: 1, g: 0, b: 0, a: 0} + - _FaceShadowGradientMapUVCenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _FaceShadowGradientMapUVScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _FaceShadowGradientMaskMapChannel: {r: 0, g: 1, b: 0, a: 0} + - _FaceShadowTintColor: {r: 1, g: 0.9, b: 0.9, a: 1} + - _FaceShadowTintColor2: {r: 1, g: 1, b: 1, a: 1} + - _FaceUpDirection: {r: 0, g: 1, b: 0, a: 1} + - _HairStrandSpecularMainColor: {r: 1, g: 1, b: 1, a: 1} + - _HairStrandSpecularSecondColor: {r: 1, g: 1, b: 1, a: 1} + - _HairStrandSpecularTintMapTilingXyOffsetZw: {r: 1, g: 1, b: 0, a: 0} + - _HeadBonePositionWS: {r: 0, g: 0, b: 0, a: 1} + - _LitToShadowTransitionAreaTintColor: {r: 1, g: 1, b: 1, a: 1} + - _LowSaturationFallbackColor: {r: 0.3764706, g: 0.4141177, b: 0.5019608, a: 0} + - _MatCapAdditiveColor: {r: 1, g: 1, b: 1, a: 1} + - _MatCapAdditiveMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _MatCapAlphaBlendMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _MatCapAlphaBlendTintColor: {r: 1, g: 1, b: 1, a: 1} + - _MatCapOcclusionMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _MatCapOcclusionMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _MatCapUVTiling: {r: 1, g: 1, b: 0, a: 0} + - _NiloGlitterTintColor: {r: 1, g: 1, b: 1, a: 1} + - _NiloToonSelfShadowMappingTintColor: {r: 1, g: 1, b: 1, a: 1} + - _OcclusionMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _OutlineOcclusionAreaTintColor: {r: 1, g: 1, b: 1, a: 1} + - _OutlinePreLightingReplaceColor: {r: 1, g: 1, b: 1, a: 1} + - _OutlineReplaceColor: {r: 1, g: 1, b: 1, a: 1} + - _OutlineTintColor: {r: 0.25, g: 0.25, b: 0.25, a: 1} + - _OutlineTintColorSkinAreaOverride: {r: 0.4, g: 0.2, b: 0.2, a: 1} + - _OutlineWidthMaskFromVertexColor: {r: 0, g: 1, b: 0, a: 0} + - _OutlineWidthTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _OutlineZOffsetMaskFromVertexColor: {r: 0, g: 1, b: 0, a: 0} + - _OutlineZOffsetMaskTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _OverrideOutlineColorTexTintColor: {r: 1, g: 1, b: 1, a: 1} + - _OverrideShadowColorMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _OverrideShadowColorTexTintColor: {r: 1, g: 1, b: 1, a: 1} + - _PerCharEffectAddColor: {r: 0, g: 0, b: 0, a: 1} + - _PerCharEffectLerpColor: {r: 1, g: 1, b: 0, a: 0} + - _PerCharEffectRimColor: {r: 0, g: 0, b: 0, a: 1} + - _PerCharEffectTintColor: {r: 1, g: 1, b: 1, a: 1} + - _PerCharacterBaseColorTint: {r: 1, g: 1, b: 1, a: 1} + - _PerCharacterBaseMapOverrideTilingOffset: {r: 1, g: 1, b: 0, a: 0} + - _PerCharacterBaseMapOverrideTintColor: {r: 1, g: 1, b: 1, a: 1} + - _PerCharacterBaseMapOverrideUVScrollSpeed: {r: 0, g: 0, b: 0, a: 0} + - _PerCharacterOutlineColorLerp: {r: 1, g: 1, b: 1, a: 0} + - _PerCharacterOutlineColorTint: {r: 1, g: 1, b: 1, a: 1} + - _PerMaterialDissolveEdgeColor: {r: 16, g: 8, b: 0, a: 1} + - _PerMaterialDissolvePatternMapChannelMask: {r: 1, g: 0, b: 0, a: 0} + - _PerMaterialDissolveThresholdMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _RampLightingSampleUvYTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _ScreenSpaceOutlineDepthSensitivityTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _ScreenSpaceOutlineNormalsSensitivityTexChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _ScreenSpaceOutlineOcclusionAreaTintColor: {r: 1, g: 1, b: 1, a: 1} + - _ScreenSpaceOutlineReplaceColor: {r: 1, g: 1, b: 1, a: 1} + - _ScreenSpaceOutlineTintColor: {r: 0.1, g: 0.1, b: 0.1, a: 1} + - _SelfShadowTintColor: {r: 1, g: 1, b: 1, a: 1} + - _ShadingGradeMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _SkinMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + - _SkinShadowTintColor: {r: 1, g: 0.8, b: 0.8, a: 1} + - _SkinShadowTintColor2: {r: 1, g: 1, b: 1, a: 1} + - _SmoothnessMapChannelMask: {r: 0, g: 0, b: 0, a: 1} + - _SpecColor: {r: 0.19999996, g: 0.19999996, b: 0.19999996, a: 1} + - _SpecularColor: {r: 1, g: 1, b: 1, a: 1} + - _SpecularColorTintMapTilingXyOffsetZw: {r: 1, g: 1, b: 0, a: 0} + - _SpecularMapChannelMask: {r: 0, g: 0, b: 1, a: 0} + - _URPShadowMappingTintColor: {r: 1, g: 1, b: 1, a: 1} + - _UV0CenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _UV0ScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _UV0ScrollSpeed: {r: 0, g: 0, b: 0, a: 0} + - _UV1CenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _UV1ScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _UV1ScrollSpeed: {r: 0, g: 0, b: 0, a: 0} + - _UV2CenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _UV2ScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _UV2ScrollSpeed: {r: 0, g: 0, b: 0, a: 0} + - _UV3CenterPivotScalePos: {r: 1, g: 1, b: 0, a: 0} + - _UV3ScaleOffset: {r: 1, g: 1, b: 0, a: 0} + - _UV3ScrollSpeed: {r: 0, g: 0, b: 0, a: 0} + - _ZOffsetMaskMapChannelMask: {r: 0, g: 1, b: 0, a: 0} + m_BuildTextureStacks: [] + m_AllowLocking: 1 diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials/material_0.mat.meta b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials/material_0.mat.meta new file mode 100644 index 00000000..53908c25 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Materials/material_0.mat.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 83c9cb0f42010264f86ac30b1da1432d +NativeFormatImporter: + externalObjects: {} + mainObjectFileID: 2100000 + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures.meta b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures.meta new file mode 100644 index 00000000..39b23341 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 60e1891c4dc0c374da17786077d08f80 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures/Image_0.png b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures/Image_0.png new file mode 100644 index 00000000..62835c2a --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures/Image_0.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:69e487b728dff510d28dce366f6540a914aee8bed75cc354f140d18a609df2f3 +size 173098 diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures/Image_0.png.meta b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures/Image_0.png.meta new file mode 100644 index 00000000..7990f751 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.Textures/Image_0.png.meta @@ -0,0 +1,117 @@ +fileFormatVersion: 2 +guid: 3ded3cb3c3ae6f243b3a449aef14524f +TextureImporter: + internalIDToNameTable: [] + externalObjects: {} + serializedVersion: 13 + mipmaps: + mipMapMode: 0 + enableMipMap: 1 + sRGBTexture: 1 + linearTexture: 0 + fadeOut: 0 + borderMipMap: 0 + mipMapsPreserveCoverage: 0 + alphaTestReferenceValue: 0.5 + mipMapFadeDistanceStart: 1 + mipMapFadeDistanceEnd: 3 + bumpmap: + convertToNormalMap: 0 + externalNormalMap: 0 + heightScale: 0.25 + normalMapFilter: 0 + flipGreenChannel: 0 + isReadable: 0 + streamingMipmaps: 0 + streamingMipmapsPriority: 0 + vTOnly: 0 + ignoreMipmapLimit: 0 + grayScaleToAlpha: 0 + generateCubemap: 6 + cubemapConvolution: 0 + seamlessCubemap: 0 + textureFormat: 1 + maxTextureSize: 2048 + textureSettings: + serializedVersion: 2 + filterMode: 2 + aniso: 1 + mipBias: 0 + wrapU: 0 + wrapV: 0 + wrapW: 0 + nPOTScale: 1 + lightmap: 0 + compressionQuality: 50 + spriteMode: 0 + spriteExtrude: 1 + spriteMeshType: 1 + alignment: 0 + spritePivot: {x: 0.5, y: 0.5} + spritePixelsToUnits: 100 + spriteBorder: {x: 0, y: 0, z: 0, w: 0} + spriteGenerateFallbackPhysicsShape: 1 + alphaUsage: 1 + alphaIsTransparency: 0 + spriteTessellationDetail: -1 + textureType: 0 + textureShape: 1 + singleChannelComponent: 0 + flipbookRows: 1 + flipbookColumns: 1 + maxTextureSizeSet: 0 + compressionQualitySet: 0 + textureFormatSet: 0 + ignorePngGamma: 0 + applyGammaDecoding: 0 + swizzle: 50462976 + cookieLightType: 0 + platformSettings: + - serializedVersion: 4 + buildTarget: DefaultTexturePlatform + maxTextureSize: 512 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + ignorePlatformSupport: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + - serializedVersion: 4 + buildTarget: Standalone + maxTextureSize: 2048 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + ignorePlatformSupport: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + spriteSheet: + serializedVersion: 2 + sprites: [] + outline: [] + customData: + physicsShape: [] + bones: [] + spriteID: + internalID: 0 + vertices: [] + indices: + edges: [] + weights: [] + secondaryTextures: [] + spriteCustomMetadata: + entries: [] + nameFileIdTable: {} + mipmapLimitGroupName: + pSDRemoveMatte: 0 + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.glb b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.glb new file mode 100644 index 00000000..2448732a --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.glb @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:2a80912dfc77b55770f6ea22ebee47196a8d372359613527b1c998963842553a +size 124600 diff --git a/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.glb.meta b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.glb.meta new file mode 100644 index 00000000..62102b91 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Model/돈주머니.glb.meta @@ -0,0 +1,22 @@ +fileFormatVersion: 2 +guid: 61efca492f301314c9b7189c17f6e417 +ScriptedImporter: + internalIDToNameTable: [] + externalObjects: + - first: + type: UnityEngine:Material + assembly: UnityEngine.CoreModule + name: material_0 + second: {fileID: 2100000, guid: 83c9cb0f42010264f86ac30b1da1432d, type: 2} + - first: + type: UnityEngine:Texture + assembly: UnityEngine.CoreModule + name: Image_0 + second: {fileID: 2800000, guid: 3ded3cb3c3ae6f243b3a449aef14524f, type: 3} + serializedVersion: 2 + userData: + assetBundleName: + assetBundleVariant: + script: {fileID: 11500000, guid: cc45016b844e7624dae3aec10fb443ea, type: 3} + reverseAxis: 2 + renderPipeline: 1 diff --git a/Assets/ResourcesData/Prop/돈주머니/Particle.meta b/Assets/ResourcesData/Prop/돈주머니/Particle.meta new file mode 100644 index 00000000..b0a81c64 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Particle.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 259f604cdbf223b4c85a423dd5d3d63c +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Particle/Coin Particle System.prefab b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin Particle System.prefab new file mode 100644 index 00000000..5ff1a3b4 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin Particle System.prefab @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:471a82dd50603a32d37b35628b93ab2785ed94bd86a368a025597026bddc502d +size 119031 diff --git a/Assets/ResourcesData/Prop/돈주머니/Particle/Coin Particle System.prefab.meta b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin Particle System.prefab.meta new file mode 100644 index 00000000..3e16b175 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin Particle System.prefab.meta @@ -0,0 +1,7 @@ +fileFormatVersion: 2 +guid: 80d0fe3b10048864f93050efd36883e9 +PrefabImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.mat b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.mat new file mode 100644 index 00000000..631886cb --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.mat @@ -0,0 +1,158 @@ +%YAML 1.1 +%TAG !u! tag:unity3d.com,2011: +--- !u!21 &2100000 +Material: + serializedVersion: 8 + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_Name: Coin + m_Shader: {fileID: 211, guid: 0000000000000000f000000000000000, type: 0} + m_Parent: {fileID: 0} + m_ModifiedSerializedProperties: 0 + m_ValidKeywords: + - _ALPHATEST_ON + m_InvalidKeywords: [] + m_LightmapFlags: 0 + m_EnableInstancingVariants: 0 + m_DoubleSidedGI: 0 + m_CustomRenderQueue: 2450 + stringTagMap: + RenderType: TransparentCutout + disabledShaderPasses: + - MOTIONVECTORS + - GRABPASS + m_LockedProperties: + m_SavedProperties: + serializedVersion: 3 + m_TexEnvs: + - _BaseMap: + m_Texture: {fileID: 2800000, guid: 08c6cf6250054064fb85c4f953406a6f, type: 3} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _BumpMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DetailAlbedoMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DetailMask: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _DetailNormalMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _EmissionMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MainTex: + m_Texture: {fileID: 2800000, guid: 08c6cf6250054064fb85c4f953406a6f, type: 3} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _MetallicGlossMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _OcclusionMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _ParallaxMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - _SpecGlossMap: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - unity_Lightmaps: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - unity_LightmapsInd: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + - unity_ShadowMasks: + m_Texture: {fileID: 0} + m_Scale: {x: 1, y: 1} + m_Offset: {x: 0, y: 0} + m_Ints: [] + m_Floats: + - _AddPrecomputedVelocity: 0 + - _AlphaClip: 0 + - _AlphaToMask: 0 + - _Blend: 0 + - _BlendModePreserveSpecular: 1 + - _BlendOp: 0 + - _BumpScale: 1 + - _CameraFadingEnabled: 0 + - _CameraFarFadeDistance: 2 + - _CameraNearFadeDistance: 1 + - _ClearCoatMask: 0 + - _ClearCoatSmoothness: 0 + - _ColorMode: 0 + - _Cull: 0 + - _Cutoff: 0.5 + - _DetailAlbedoMapScale: 1 + - _DetailNormalMapScale: 1 + - _DistortionBlend: 0.5 + - _DistortionEnabled: 0 + - _DistortionStrength: 1 + - _DistortionStrengthScaled: 0 + - _DstBlend: 0 + - _DstBlendAlpha: 0 + - _EmissionEnabled: 0 + - _EnvironmentReflections: 1 + - _FlipbookMode: 0 + - _GlossMapScale: 0 + - _Glossiness: 0 + - _GlossyReflections: 0 + - _LightingEnabled: 0 + - _Metallic: 0 + - _Mode: 1 + - _OcclusionStrength: 1 + - _Parallax: 0.005 + - _QueueOffset: 0 + - _ReceiveShadows: 1 + - _Smoothness: 0.5 + - _SmoothnessTextureChannel: 0 + - _SoftParticlesEnabled: 0 + - _SoftParticlesFarFadeDistance: 1 + - _SoftParticlesNearFadeDistance: 0 + - _SpecularHighlights: 1 + - _SrcBlend: 1 + - _SrcBlendAlpha: 1 + - _Surface: 0 + - _WorkflowMode: 1 + - _XRMotionVectorsPass: 1 + - _ZWrite: 1 + m_Colors: + - _BaseColor: {r: 1, g: 1, b: 1, a: 1} + - _CameraFadeParams: {r: 0, g: Infinity, b: 0, a: 0} + - _Color: {r: 1, g: 1, b: 1, a: 1} + - _ColorAddSubDiff: {r: 0, g: 0, b: 0, a: 0} + - _EmissionColor: {r: 0, g: 0, b: 0, a: 1} + - _SoftParticleFadeParams: {r: 0, g: 0, b: 0, a: 0} + - _SpecColor: {r: 0.19999996, g: 0.19999996, b: 0.19999996, a: 1} + m_BuildTextureStacks: [] + m_AllowLocking: 1 +--- !u!114 &6738923856525603992 +MonoBehaviour: + m_ObjectHideFlags: 11 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 0} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: d0353a89b1f911e48b9e16bdc9f2e058, type: 3} + m_Name: + m_EditorClassIdentifier: Unity.RenderPipelines.Universal.Editor::UnityEditor.Rendering.Universal.AssetVersion + version: 10 diff --git a/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.mat.meta b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.mat.meta new file mode 100644 index 00000000..3b6b77ca --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.mat.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 77bcf914247406744892f91d7497c54e +NativeFormatImporter: + externalObjects: {} + mainObjectFileID: 2100000 + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.png b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.png new file mode 100644 index 00000000..e72863da --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:fde5f90f7a879842fd9cd851dd103ff0b4f44a032d99e13236503f638633f1b1 +size 659850 diff --git a/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.png.meta b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.png.meta new file mode 100644 index 00000000..934ab257 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Particle/Coin.png.meta @@ -0,0 +1,117 @@ +fileFormatVersion: 2 +guid: 08c6cf6250054064fb85c4f953406a6f +TextureImporter: + internalIDToNameTable: [] + externalObjects: {} + serializedVersion: 13 + mipmaps: + mipMapMode: 0 + enableMipMap: 1 + sRGBTexture: 1 + linearTexture: 0 + fadeOut: 0 + borderMipMap: 0 + mipMapsPreserveCoverage: 0 + alphaTestReferenceValue: 0.5 + mipMapFadeDistanceStart: 1 + mipMapFadeDistanceEnd: 3 + bumpmap: + convertToNormalMap: 0 + externalNormalMap: 0 + heightScale: 0.25 + normalMapFilter: 0 + flipGreenChannel: 0 + isReadable: 0 + streamingMipmaps: 0 + streamingMipmapsPriority: 0 + vTOnly: 0 + ignoreMipmapLimit: 0 + grayScaleToAlpha: 0 + generateCubemap: 6 + cubemapConvolution: 0 + seamlessCubemap: 0 + textureFormat: 1 + maxTextureSize: 2048 + textureSettings: + serializedVersion: 2 + filterMode: 1 + aniso: 1 + mipBias: 0 + wrapU: 0 + wrapV: 0 + wrapW: 0 + nPOTScale: 1 + lightmap: 0 + compressionQuality: 50 + spriteMode: 0 + spriteExtrude: 1 + spriteMeshType: 1 + alignment: 0 + spritePivot: {x: 0.5, y: 0.5} + spritePixelsToUnits: 100 + spriteBorder: {x: 0, y: 0, z: 0, w: 0} + spriteGenerateFallbackPhysicsShape: 1 + alphaUsage: 1 + alphaIsTransparency: 0 + spriteTessellationDetail: -1 + textureType: 0 + textureShape: 1 + singleChannelComponent: 0 + flipbookRows: 1 + flipbookColumns: 1 + maxTextureSizeSet: 0 + compressionQualitySet: 0 + textureFormatSet: 0 + ignorePngGamma: 0 + applyGammaDecoding: 0 + swizzle: 50462976 + cookieLightType: 0 + platformSettings: + - serializedVersion: 4 + buildTarget: DefaultTexturePlatform + maxTextureSize: 2048 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + ignorePlatformSupport: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + - serializedVersion: 4 + buildTarget: Standalone + maxTextureSize: 2048 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + ignorePlatformSupport: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + spriteSheet: + serializedVersion: 2 + sprites: [] + outline: [] + customData: + physicsShape: [] + bones: [] + spriteID: + internalID: 0 + vertices: [] + indices: + edges: [] + weights: [] + secondaryTextures: [] + spriteCustomMetadata: + entries: [] + nameFileIdTable: {} + mipmapLimitGroupName: + pSDRemoveMatte: 0 + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Prefab.meta b/Assets/ResourcesData/Prop/돈주머니/Prefab.meta new file mode 100644 index 00000000..49382aed --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Prefab.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: ac3169f25f136984e9eda821c9b67868 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Prefab/돈주머니.prefab b/Assets/ResourcesData/Prop/돈주머니/Prefab/돈주머니.prefab new file mode 100644 index 00000000..1d1c6b16 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Prefab/돈주머니.prefab @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:67b485f9031ad05e028f4a64a0263382e3d6991969349c8a7cf63c4bf43ae1db +size 2473 diff --git a/Assets/ResourcesData/Prop/돈주머니/Prefab/돈주머니.prefab.meta b/Assets/ResourcesData/Prop/돈주머니/Prefab/돈주머니.prefab.meta new file mode 100644 index 00000000..f2da8015 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Prefab/돈주머니.prefab.meta @@ -0,0 +1,7 @@ +fileFormatVersion: 2 +guid: 4a438ec402234494db1c4597ce20dc41 +PrefabImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Sound.meta b/Assets/ResourcesData/Prop/돈주머니/Sound.meta new file mode 100644 index 00000000..b78cd737 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Sound.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: ec9ad2e9fbffb604184a0ee84836d48b +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Sound/돈주머니 효과음.mp3 b/Assets/ResourcesData/Prop/돈주머니/Sound/돈주머니 효과음.mp3 new file mode 100644 index 00000000..9d7be189 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Sound/돈주머니 효과음.mp3 @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:ab021d388a4847c9c326909737f13740e171ac41937a61afdacbc1eb893fe1de +size 24000 diff --git a/Assets/ResourcesData/Prop/돈주머니/Sound/돈주머니 효과음.mp3.meta b/Assets/ResourcesData/Prop/돈주머니/Sound/돈주머니 효과음.mp3.meta new file mode 100644 index 00000000..eb69c1c9 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Sound/돈주머니 효과음.mp3.meta @@ -0,0 +1,23 @@ +fileFormatVersion: 2 +guid: 483113300e6fec0488ef74bbb771c3da +AudioImporter: + externalObjects: {} + serializedVersion: 8 + defaultSettings: + serializedVersion: 2 + loadType: 0 + sampleRateSetting: 0 + sampleRateOverride: 44100 + compressionFormat: 1 + quality: 1 + conversionMode: 0 + preloadAudioData: 0 + platformSettingOverrides: {} + forceToMono: 0 + normalize: 1 + loadInBackground: 0 + ambisonic: 0 + 3D: 1 + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Thumbnail.meta b/Assets/ResourcesData/Prop/돈주머니/Thumbnail.meta new file mode 100644 index 00000000..ce582e24 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Thumbnail.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 0597c595d70f57242b02e1f8ecd7f88e +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/ResourcesData/Prop/돈주머니/Thumbnail/돈주머니_thumbnail.png b/Assets/ResourcesData/Prop/돈주머니/Thumbnail/돈주머니_thumbnail.png new file mode 100644 index 00000000..a7c32e44 --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Thumbnail/돈주머니_thumbnail.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:0585af71802a2d9f9a22596bc428a51bb3f6e0c4dd536120402901843261d3d2 +size 58572 diff --git a/Assets/ResourcesData/Prop/돈주머니/Thumbnail/돈주머니_thumbnail.png.meta b/Assets/ResourcesData/Prop/돈주머니/Thumbnail/돈주머니_thumbnail.png.meta new file mode 100644 index 00000000..8241628d --- /dev/null +++ b/Assets/ResourcesData/Prop/돈주머니/Thumbnail/돈주머니_thumbnail.png.meta @@ -0,0 +1,117 @@ +fileFormatVersion: 2 +guid: 52eff15a79fe4224993692534a200c90 +TextureImporter: + internalIDToNameTable: [] + externalObjects: {} + serializedVersion: 13 + mipmaps: + mipMapMode: 0 + enableMipMap: 1 + sRGBTexture: 1 + linearTexture: 0 + fadeOut: 0 + borderMipMap: 0 + mipMapsPreserveCoverage: 0 + alphaTestReferenceValue: 0.5 + mipMapFadeDistanceStart: 1 + mipMapFadeDistanceEnd: 3 + bumpmap: + convertToNormalMap: 0 + externalNormalMap: 0 + heightScale: 0.25 + normalMapFilter: 0 + flipGreenChannel: 0 + isReadable: 0 + streamingMipmaps: 0 + streamingMipmapsPriority: 0 + vTOnly: 0 + ignoreMipmapLimit: 0 + grayScaleToAlpha: 0 + generateCubemap: 6 + cubemapConvolution: 0 + seamlessCubemap: 0 + textureFormat: 1 + maxTextureSize: 2048 + textureSettings: + serializedVersion: 2 + filterMode: 1 + aniso: 1 + mipBias: 0 + wrapU: 0 + wrapV: 0 + wrapW: 0 + nPOTScale: 1 + lightmap: 0 + compressionQuality: 50 + spriteMode: 0 + spriteExtrude: 1 + spriteMeshType: 1 + alignment: 0 + spritePivot: {x: 0.5, y: 0.5} + spritePixelsToUnits: 100 + spriteBorder: {x: 0, y: 0, z: 0, w: 0} + spriteGenerateFallbackPhysicsShape: 1 + alphaUsage: 1 + alphaIsTransparency: 0 + spriteTessellationDetail: -1 + textureType: 0 + textureShape: 1 + singleChannelComponent: 0 + flipbookRows: 1 + flipbookColumns: 1 + maxTextureSizeSet: 0 + compressionQualitySet: 0 + textureFormatSet: 0 + ignorePngGamma: 0 + applyGammaDecoding: 0 + swizzle: 50462976 + cookieLightType: 0 + platformSettings: + - serializedVersion: 4 + buildTarget: DefaultTexturePlatform + maxTextureSize: 2048 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + ignorePlatformSupport: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + - serializedVersion: 4 + buildTarget: Standalone + maxTextureSize: 2048 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + ignorePlatformSupport: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + spriteSheet: + serializedVersion: 2 + sprites: [] + outline: [] + customData: + physicsShape: [] + bones: [] + spriteID: + internalID: 0 + vertices: [] + indices: + edges: [] + weights: [] + secondaryTextures: [] + spriteCustomMetadata: + entries: [] + nameFileIdTable: {} + mipmapLimitGroupName: + pSDRemoveMatte: 0 + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Scripts/Streamingle/DonationThrowable.meta b/Assets/Scripts/Streamingle/DonationThrowable.meta new file mode 100644 index 00000000..c801194d --- /dev/null +++ b/Assets/Scripts/Streamingle/DonationThrowable.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: fd54180499ff72f4bbcb70fe47ba5f8a +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObject.cs b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObject.cs new file mode 100644 index 00000000..ae3fb793 --- /dev/null +++ b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObject.cs @@ -0,0 +1,315 @@ +using UnityEngine; + +namespace Streamingle +{ + /// + /// Component attached to throwable objects. + /// Uses parabolic interpolation for smooth arc trajectory. + /// On reaching target, enables collision detection - bounces off colliders or falls. + /// + public class ThrowableObject : MonoBehaviour + { + [HideInInspector] + public ThrowableObjectLauncher launcher; + + [Header("Settings")] + [Tooltip("Play sound on hit")] + public AudioClip[] hitSounds; + + [Tooltip("Spawn particle effect on hit")] + public GameObject hitEffectPrefab; + + [Tooltip("Destroy hit effect after this time")] + public float hitEffectLifetime = 2f; + + [Header("Trajectory Settings")] + [Tooltip("Time to reach target in seconds")] + public float flightDuration = 1.5f; + + [Tooltip("Arc height (higher = more curved trajectory)")] + public float arcHeight = 2f; + + [Tooltip("Rotation speed while flying")] + public float rotationSpeed = 180f; + + [Header("Collision Settings")] + [Tooltip("Bounce force multiplier when hitting collider")] + public float bounceForce = 5f; + + [Tooltip("Additional upward force on bounce")] + public float bounceUpForce = 2f; + + [Tooltip("Time to stay after reaching target before deactivating")] + public float postArrivalLifetime = 3f; + + // Trajectory state + private Vector3 startPosition; + private Vector3 targetPosition; + private Transform targetTransform; + private float flightTime; + private float currentTime; + private bool isFlying = false; + private bool hasArrived = false; + private bool hasCollided = false; + private Vector3 rotationAxis; + private Vector3 arrivalVelocity; + + // Components + private Rigidbody rb; + private AudioSource audioSource; + private Collider[] colliders; + + // Lifetime + private float lifetime; + private float spawnTime; + + void Awake() + { + rb = GetComponent(); + audioSource = GetComponent(); + colliders = GetComponents(); + } + + /// + /// Initialize the throwable object with target position + /// + public void Initialize(Transform target, float lifetime) + { + Initialize(target, lifetime, Vector3.zero); + } + + /// + /// Initialize with offset for target position + /// + public void Initialize(Transform target, float lifetime, Vector3 targetOffset) + { + this.lifetime = lifetime; + this.spawnTime = Time.time; + this.hasArrived = false; + this.hasCollided = false; + this.isFlying = true; + this.currentTime = 0f; + this.flightTime = flightDuration; + this.startPosition = transform.position; + this.targetTransform = target; + + // Calculate target position with offset + if (target != null) + { + this.targetPosition = target.position + targetOffset; + } + else + { + this.targetPosition = transform.position + Vector3.forward * 5f; + } + + // Random rotation axis for spinning effect + rotationAxis = Random.insideUnitSphere.normalized; + + // Disable physics during flight + if (rb != null) + { + rb.isKinematic = true; + rb.useGravity = false; + } + + // Disable colliders during flight + SetCollidersEnabled(false); + } + + void Update() + { + // Check lifetime + if (lifetime > 0 && Time.time - spawnTime > lifetime) + { + Deactivate(); + return; + } + + if (!isFlying) return; + + // Store previous position for velocity calculation + Vector3 prevPos = transform.position; + + currentTime += Time.deltaTime; + float t = Mathf.Clamp01(currentTime / flightTime); + + // Calculate parabolic position + Vector3 currentPos = CalculateParabolicPosition(t); + transform.position = currentPos; + + // Calculate velocity for when we switch to physics + if (Time.deltaTime > 0) + { + arrivalVelocity = (currentPos - prevPos) / Time.deltaTime; + } + + // Rotate while flying + transform.Rotate(rotationAxis, rotationSpeed * Time.deltaTime, Space.World); + + // Check if reached target + if (t >= 1f) + { + OnReachedTarget(); + } + } + + /// + /// Calculate position along parabolic arc + /// + private Vector3 CalculateParabolicPosition(float t) + { + // Linear interpolation for base position + Vector3 linearPos = Vector3.Lerp(startPosition, targetPosition, t); + + // Parabolic arc (peaks at t=0.5) + float parabola = 4f * arcHeight * t * (1f - t); + + // Add arc height to Y position + linearPos.y += parabola; + + return linearPos; + } + + /// + /// Called when object reaches the target position + /// + private void OnReachedTarget() + { + isFlying = false; + hasArrived = true; + + // Re-enable colliders for collision detection + SetCollidersEnabled(true); + + // Enable physics - object will either hit a collider and bounce or fall + if (rb != null) + { + rb.isKinematic = false; + rb.useGravity = true; + + // Continue with the arrival velocity (maintains momentum) + rb.linearVelocity = arrivalVelocity; + rb.angularVelocity = rotationAxis * rotationSpeed * Mathf.Deg2Rad; + } + + // Schedule deactivation (object falls if no collision) + Invoke(nameof(Deactivate), postArrivalLifetime); + } + + void OnCollisionEnter(Collision collision) + { + if (!hasArrived || hasCollided) return; + + // Check if collision is with the target + bool isTargetHit = false; + if (targetTransform != null) + { + // Check if collided object is the target or a child of target + Transform hitTransform = collision.collider.transform; + isTargetHit = hitTransform == targetTransform || hitTransform.IsChildOf(targetTransform); + } + + hasCollided = true; + + // Only notify launcher and play effects if hit the target + if (isTargetHit) + { + if (launcher != null) + { + launcher.OnObjectHitTarget(gameObject, collision.collider, collision); + } + + // Play hit sound + PlayHitSound(); + + // Spawn hit effect + SpawnHitEffect(collision); + } + + // Apply bounce force regardless of what was hit + if (rb != null && collision.contacts.Length > 0) + { + Vector3 normal = collision.contacts[0].normal; + Vector3 reflectedVel = Vector3.Reflect(rb.linearVelocity, normal); + + // Apply bounce with some force + rb.linearVelocity = reflectedVel.normalized * bounceForce + Vector3.up * bounceUpForce; + rb.angularVelocity = Random.insideUnitSphere * 10f; + } + } + + private void SetCollidersEnabled(bool enabled) + { + if (colliders == null) return; + foreach (var col in colliders) + { + if (col != null) col.enabled = enabled; + } + } + + private void PlayHitSound() + { + if (hitSounds == null || hitSounds.Length == 0) return; + + AudioClip clip = hitSounds[Random.Range(0, hitSounds.Length)]; + if (clip == null) return; + + if (audioSource != null) + { + audioSource.PlayOneShot(clip); + } + else + { + AudioSource.PlayClipAtPoint(clip, transform.position); + } + } + + private void SpawnHitEffect(Collision collision = null) + { + if (hitEffectPrefab == null) return; + + Vector3 pos = transform.position; + Quaternion rot = Quaternion.identity; + + if (collision != null && collision.contacts.Length > 0) + { + pos = collision.contacts[0].point; + rot = Quaternion.LookRotation(collision.contacts[0].normal); + } + + GameObject effect = Instantiate(hitEffectPrefab, pos, rot); + if (hitEffectLifetime > 0) + { + Destroy(effect, hitEffectLifetime); + } + } + + private void Deactivate() + { + CancelInvoke(); + isFlying = false; + hasArrived = false; + hasCollided = false; + + if (launcher != null && launcher.usePooling) + { + // Return to pool + gameObject.SetActive(false); + } + else + { + // Destroy + Destroy(gameObject); + } + } + + void OnDisable() + { + CancelInvoke(); + isFlying = false; + hasArrived = false; + hasCollided = false; + } + } +} diff --git a/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObject.cs.meta b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObject.cs.meta new file mode 100644 index 00000000..d4332251 --- /dev/null +++ b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObject.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: 53f705dd7db28b4489129cbca2dfe7b7 \ No newline at end of file diff --git a/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObjectLauncher.cs b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObjectLauncher.cs new file mode 100644 index 00000000..aca87622 --- /dev/null +++ b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObjectLauncher.cs @@ -0,0 +1,340 @@ +using UnityEngine; +using UnityEngine.Events; + +namespace Streamingle +{ + /// + /// Launches throwable objects at a target (avatar's head). + /// Connect to WefLab donation events to throw objects on donations. + /// Uses parabolic interpolation for smooth arc trajectories. + /// + public class ThrowableObjectLauncher : MonoBehaviour + { + [Header("Target")] + [Tooltip("The target transform to throw objects at (usually avatar's head)")] + public Transform target; + + [Tooltip("Fixed offset from target position")] + public Vector3 targetOffset = Vector3.zero; + + [Tooltip("Random offset range for hit position")] + public Vector3 targetRandomOffset = new Vector3(0.1f, 0.1f, 0.1f); + + [Header("Target Collider")] + [Tooltip("Automatically create a collider on target for bounce detection")] + public bool autoCreateTargetCollider = true; + + [Tooltip("Radius of the auto-created sphere collider")] + public float targetColliderRadius = 0.15f; + + [Header("Spawn Settings")] + [Tooltip("Prefabs to throw (randomly selected)")] + public GameObject[] throwablePrefabs; + + [Tooltip("Spawn position offset from this transform")] + public Vector3 spawnOffset = new Vector3(0, 1f, 0); + + [Tooltip("Randomize spawn position within this range")] + public Vector3 spawnRandomRange = new Vector3(5f, 1f, 5f); + + [Header("Throw Settings")] + [Tooltip("Delay between throws when throwing multiple")] + public float throwInterval = 0.15f; + + [Header("Object Lifetime")] + [Tooltip("Destroy thrown objects after this time (0 = never)")] + public float objectLifetime = 5f; + + [Tooltip("Use object pooling instead of instantiate/destroy")] + public bool usePooling = true; + + [Tooltip("Pool size per prefab")] + public int poolSizePerPrefab = 10; + + [Header("Events")] + public UnityEvent onObjectThrown; + public UnityEvent onObjectHit; + + // Object pool + private GameObject[][] objectPool; + private int[] poolIndices; + + // Auto-created collider + private SphereCollider createdTargetCollider; + + void Start() + { + if (usePooling) + { + InitializePool(); + } + + if (autoCreateTargetCollider && target != null) + { + SetupTargetCollider(); + } + } + + private void SetupTargetCollider() + { + // Check if target already has a collider + var existingCollider = target.GetComponent(); + if (existingCollider != null) + { + UnityEngine.Debug.Log($"[ThrowableObjectLauncher] Target already has collider: {existingCollider.GetType().Name}"); + return; + } + + // Create sphere collider on target with offset applied + createdTargetCollider = target.gameObject.AddComponent(); + createdTargetCollider.radius = targetColliderRadius; + // Apply targetOffset to collider center (convert world offset to local space) + createdTargetCollider.center = target.InverseTransformDirection(targetOffset); + + // Ensure target has rigidbody (kinematic) for collision detection + var rb = target.GetComponent(); + if (rb == null) + { + rb = target.gameObject.AddComponent(); + rb.isKinematic = true; + rb.useGravity = false; + } + + UnityEngine.Debug.Log($"[ThrowableObjectLauncher] Created SphereCollider on target: {target.name}, radius: {targetColliderRadius}, center: {createdTargetCollider.center}"); + } + + void OnDestroy() + { + // Clean up created collider + if (createdTargetCollider != null) + { + Destroy(createdTargetCollider); + } + } + + private void InitializePool() + { + if (throwablePrefabs == null || throwablePrefabs.Length == 0) return; + + objectPool = new GameObject[throwablePrefabs.Length][]; + poolIndices = new int[throwablePrefabs.Length]; + + for (int i = 0; i < throwablePrefabs.Length; i++) + { + if (throwablePrefabs[i] == null) continue; + + objectPool[i] = new GameObject[poolSizePerPrefab]; + for (int j = 0; j < poolSizePerPrefab; j++) + { + var obj = Instantiate(throwablePrefabs[i], transform); + obj.SetActive(false); + + // Add throwable component if not present + var throwable = obj.GetComponent(); + if (throwable == null) + { + throwable = obj.AddComponent(); + } + throwable.launcher = this; + + objectPool[i][j] = obj; + } + } + } + + /// + /// Throw a random object at the target + /// + public void ThrowObject() + { + ThrowObject(Random.Range(0, throwablePrefabs.Length)); + } + + /// + /// Throw a specific object at the target + /// + public void ThrowObject(int prefabIndex) + { + if (throwablePrefabs == null || throwablePrefabs.Length == 0) + { + UnityEngine.Debug.LogWarning("[ThrowableObjectLauncher] No throwable prefabs assigned"); + return; + } + + if (target == null) + { + UnityEngine.Debug.LogWarning("[ThrowableObjectLauncher] No target assigned"); + return; + } + + prefabIndex = Mathf.Clamp(prefabIndex, 0, throwablePrefabs.Length - 1); + if (throwablePrefabs[prefabIndex] == null) return; + + // Get or create object + GameObject obj = GetObject(prefabIndex); + if (obj == null) return; + + // Calculate spawn position + Vector3 spawnPos = transform.position + transform.TransformDirection(spawnOffset); + spawnPos += new Vector3( + Random.Range(-spawnRandomRange.x, spawnRandomRange.x), + Random.Range(-spawnRandomRange.y, spawnRandomRange.y), + Random.Range(-spawnRandomRange.z, spawnRandomRange.z) + ); + + // Calculate random offset for target position + Vector3 randomOffset = new Vector3( + Random.Range(-targetRandomOffset.x, targetRandomOffset.x), + Random.Range(-targetRandomOffset.y, targetRandomOffset.y), + Random.Range(-targetRandomOffset.z, targetRandomOffset.z) + ); + + // Combine fixed offset + random offset + Vector3 combinedOffset = targetOffset + randomOffset; + + // Setup object position + obj.transform.position = spawnPos; + obj.transform.rotation = Random.rotation; + obj.SetActive(true); + + // Setup throwable component with combined offset + var throwable = obj.GetComponent(); + if (throwable != null) + { + throwable.Initialize(target, objectLifetime, combinedOffset); + } + + onObjectThrown?.Invoke(obj); + } + + /// + /// Throw multiple objects + /// + public void ThrowMultiple(int count) + { + for (int i = 0; i < count; i++) + { + // Delay each throw slightly + float delay = i * throwInterval; + StartCoroutine(ThrowDelayed(delay)); + } + } + + private System.Collections.IEnumerator ThrowDelayed(float delay) + { + yield return new WaitForSeconds(delay); + ThrowObject(); + } + + private GameObject GetObject(int prefabIndex) + { + GameObject obj; + + if (usePooling && objectPool != null && objectPool[prefabIndex] != null) + { + // Find inactive object in pool + for (int i = 0; i < poolSizePerPrefab; i++) + { + int idx = (poolIndices[prefabIndex] + i) % poolSizePerPrefab; + if (!objectPool[prefabIndex][idx].activeInHierarchy) + { + poolIndices[prefabIndex] = (idx + 1) % poolSizePerPrefab; + obj = objectPool[prefabIndex][idx]; + // Ensure launcher reference is set + var throwable = obj.GetComponent(); + if (throwable != null) throwable.launcher = this; + return obj; + } + } + + // All in use, reuse oldest + poolIndices[prefabIndex] = (poolIndices[prefabIndex] + 1) % poolSizePerPrefab; + obj = objectPool[prefabIndex][poolIndices[prefabIndex]]; + obj.SetActive(false); + // Ensure launcher reference is set + var throwableOldest = obj.GetComponent(); + if (throwableOldest != null) throwableOldest.launcher = this; + return obj; + } + else + { + // Instantiate new + obj = Instantiate(throwablePrefabs[prefabIndex]); + var throwable = obj.GetComponent(); + if (throwable == null) + { + throwable = obj.AddComponent(); + } + throwable.launcher = this; + return obj; + } + } + + /// + /// Called by ThrowableObject when it reaches the target + /// + public void OnObjectHitTarget(GameObject obj, Collider hitCollider, Collision collision) + { + onObjectHit?.Invoke(obj, collision); + } + + #region Context Menu Test Methods + + [ContextMenu("Test: Throw 1")] + private void TestThrowOne() + { + ThrowObject(); + } + + [ContextMenu("Test: Throw 5")] + private void TestThrowFive() + { + ThrowMultiple(5); + } + + #endregion + + void OnDrawGizmosSelected() + { + // Draw spawn area + Gizmos.color = Color.green; + Vector3 spawnPos = transform.position + transform.TransformDirection(spawnOffset); + Gizmos.DrawWireCube(spawnPos, spawnRandomRange * 2); + + // Draw target + if (target != null) + { + Gizmos.color = Color.red; + Vector3 targetPos = target.position + targetOffset; + Gizmos.DrawWireSphere(targetPos, 0.2f); + Gizmos.DrawWireCube(targetPos, targetRandomOffset * 2); + + // Draw target collider radius (at offset position) + if (autoCreateTargetCollider) + { + Gizmos.color = Color.cyan; + Gizmos.DrawWireSphere(target.position + targetOffset, targetColliderRadius); + } + + // Draw trajectory preview (parabolic arc) + Gizmos.color = Color.yellow; + DrawParabolicArc(spawnPos, targetPos, 2f, 20); + } + } + + private void DrawParabolicArc(Vector3 start, Vector3 end, float arcHeight, int segments) + { + Vector3 prevPos = start; + for (int i = 1; i <= segments; i++) + { + float t = i / (float)segments; + Vector3 linearPos = Vector3.Lerp(start, end, t); + float parabola = 4f * arcHeight * t * (1f - t); + linearPos.y += parabola; + + Gizmos.DrawLine(prevPos, linearPos); + prevPos = linearPos; + } + } + } +} diff --git a/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObjectLauncher.cs.meta b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObjectLauncher.cs.meta new file mode 100644 index 00000000..60bd421f --- /dev/null +++ b/Assets/Scripts/Streamingle/DonationThrowable/ThrowableObjectLauncher.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: 85064059a4495fd48824a7a421bee446 \ No newline at end of file diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneData.cs b/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneData.cs index ce474b44..7a65b120 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneData.cs +++ b/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneData.cs @@ -1,5 +1,4 @@ using System; -using System.Collections.Generic; using UnityEngine; namespace Streamingle.Background @@ -37,48 +36,4 @@ namespace Streamingle.Background } } - /// - /// 배경 씬 데이터를 저장하는 ScriptableObject - /// - [CreateAssetMenu(fileName = "BackgroundSceneDatabase", menuName = "Streamingle/Background Scene Database")] - public class BackgroundSceneDatabase : ScriptableObject - { - public List scenes = new List(); - - /// - /// 카테고리별로 씬 목록 반환 - /// - public Dictionary> GetScenesByCategory() - { - var result = new Dictionary>(); - - foreach (var scene in scenes) - { - string category = scene.Category; - if (!result.ContainsKey(category)) - { - result[category] = new List(); - } - result[category].Add(scene); - } - - return result; - } - - /// - /// 씬 이름으로 검색 - /// - public BackgroundSceneInfo FindByName(string sceneName) - { - return scenes.Find(s => s.sceneName == sceneName); - } - - /// - /// 씬 경로로 검색 - /// - public BackgroundSceneInfo FindByPath(string scenePath) - { - return scenes.Find(s => s.scenePath == scenePath); - } - } } diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneDatabase.cs b/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneDatabase.cs new file mode 100644 index 00000000..52800bc9 --- /dev/null +++ b/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneDatabase.cs @@ -0,0 +1,50 @@ +using System.Collections.Generic; +using UnityEngine; + +namespace Streamingle.Background +{ + /// + /// 배경 씬 데이터를 저장하는 ScriptableObject + /// + [CreateAssetMenu(fileName = "BackgroundSceneDatabase", menuName = "Streamingle/Background Scene Database")] + public class BackgroundSceneDatabase : ScriptableObject + { + public List scenes = new List(); + + /// + /// 카테고리별로 씬 목록 반환 + /// + public Dictionary> GetScenesByCategory() + { + var result = new Dictionary>(); + + foreach (var scene in scenes) + { + string category = scene.Category; + if (!result.ContainsKey(category)) + { + result[category] = new List(); + } + result[category].Add(scene); + } + + return result; + } + + /// + /// 씬 이름으로 검색 + /// + public BackgroundSceneInfo FindByName(string sceneName) + { + return scenes.Find(s => s.sceneName == sceneName); + } + + /// + /// 씬 경로로 검색 + /// + public BackgroundSceneInfo FindByPath(string scenePath) + { + return scenes.Find(s => s.scenePath == scenePath); + } + } +} diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneDatabase.cs.meta b/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneDatabase.cs.meta new file mode 100644 index 00000000..73cf15a0 --- /dev/null +++ b/Assets/Scripts/Streamingle/StreamingleControl/Background/BackgroundSceneDatabase.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: ee084dfc7f17cb7498423a57ca4bd971 \ No newline at end of file diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Controllers/CameraController.cs b/Assets/Scripts/Streamingle/StreamingleControl/Controllers/CameraController.cs index d1e9bf3a..63935b1d 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Controllers/CameraController.cs +++ b/Assets/Scripts/Streamingle/StreamingleControl/Controllers/CameraController.cs @@ -1,4 +1,5 @@ using UnityEngine; +using UnityEngine.Rendering; using UnityEngine.Rendering.Universal; using System.Collections; using System.Collections.Generic; @@ -164,6 +165,11 @@ public class CameraManager : MonoBehaviour, IController [System.NonSerialized] public Vector3 savedFocusPoint; [System.NonSerialized] public bool hasOrbitState = false; + // 프리셋별 FOV 저장 (Alt+Q 복원용) + [System.NonSerialized] public float initialFOV; + [System.NonSerialized] public float savedFOV; + [System.NonSerialized] public bool hasInitialFOV = false; + public CameraPreset(CinemachineCamera camera) { virtualCamera = camera; @@ -181,6 +187,14 @@ public class CameraManager : MonoBehaviour, IController initialPosition = virtualCamera.transform.position; initialRotation = virtualCamera.transform.rotation; hasInitialState = true; + + // FOV 초기값 저장 + if (virtualCamera.Lens.FieldOfView > 0) + { + initialFOV = virtualCamera.Lens.FieldOfView; + savedFOV = initialFOV; + hasInitialFOV = true; + } } // 초기 상태 복원 (Alt+Q) @@ -189,25 +203,36 @@ public class CameraManager : MonoBehaviour, IController if (!hasInitialState || virtualCamera == null) return; virtualCamera.transform.position = initialPosition; virtualCamera.transform.rotation = initialRotation; + + // FOV 초기값 복원 + if (hasInitialFOV) + { + var lens = virtualCamera.Lens; + lens.FieldOfView = initialFOV; + virtualCamera.Lens = lens; + savedFOV = initialFOV; + } } // orbit 상태 저장 (카메라 전환 시) - public void SaveOrbitState(float hAngle, float vAngle, float dist, Vector3 focus) + public void SaveOrbitState(float hAngle, float vAngle, float dist, Vector3 focus, float fov) { savedHorizontalAngle = hAngle; savedVerticalAngle = vAngle; savedDistance = dist; savedFocusPoint = focus; + savedFOV = fov; hasOrbitState = true; } // orbit 상태 복원 (카메라 전환 시) - public bool TryRestoreOrbitState(out float hAngle, out float vAngle, out float dist, out Vector3 focus) + public bool TryRestoreOrbitState(out float hAngle, out float vAngle, out float dist, out Vector3 focus, out float fov) { hAngle = savedHorizontalAngle; vAngle = savedVerticalAngle; dist = savedDistance; focus = savedFocusPoint; + fov = savedFOV; return hasOrbitState; } } @@ -235,6 +260,11 @@ public class CameraManager : MonoBehaviour, IController [SerializeField] private float minZoomDistance = 0.5f; [SerializeField] private float maxZoomDistance = 50f; + [Header("FOV Settings")] + [SerializeField, Range(0.1f, 5f)] private float fovSensitivity = 1f; + [SerializeField] private float minFOV = 1f; + [SerializeField] private float maxFOV = 90f; + [Header("Rotation Target")] [Tooltip("체크하면 아바타 머리를 자동으로 찾아 회전 중심점으로 사용합니다.")] [SerializeField] private bool useAvatarHeadAsTarget = true; @@ -246,9 +276,12 @@ public class CameraManager : MonoBehaviour, IController [SerializeField] private bool useBlendTransition = false; [Tooltip("블렌드 전환 시간 (초)")] [SerializeField, Range(0.1f, 2f)] private float blendTime = 0.5f; + [Tooltip("실시간 블렌딩 (두 카메라 동시 렌더링). 비활성화 시 스냅샷 블렌딩 사용")] + [SerializeField] private bool useRealtimeBlend = true; // 블렌드용 렌더 텍스처와 카메라 private RenderTexture blendRenderTexture; + private RenderTexture prevCameraRenderTexture; // 실시간 블렌딩용 이전 카메라 렌더 텍스처 private Camera blendCamera; private CinemachineCamera currentCamera; @@ -433,7 +466,6 @@ public class CameraManager : MonoBehaviour, IController avatarHeadTransform = animator.GetBoneTransform(HumanBodyBones.Head); if (avatarHeadTransform != null) { - Debug.Log($"[CameraManager] 아바타 머리를 회전 중심점으로 설정: {avatarHeadTransform.name}"); return; } } @@ -543,7 +575,7 @@ public class CameraManager : MonoBehaviour, IController private void HandleInput() { - // 입력 우선순위 처리: Orbit > AltRightZoom > Zoom > Rotation > Panning + // 입력 우선순위 처리: Orbit > CtrlRightZoom > Zoom > FOV > Rotation > Panning if (inputHandler.IsOrbitActive()) { HandleOrbiting(); @@ -556,6 +588,10 @@ public class CameraManager : MonoBehaviour, IController { HandleDragZoom(); } + else if (inputHandler.IsFOVActive()) + { + HandleFOV(); + } else if (inputHandler.IsRightMouseHeld()) { HandleRotation(); @@ -651,6 +687,24 @@ public class CameraManager : MonoBehaviour, IController targetDistance = Mathf.Clamp(targetDistance, minZoomDistance, maxZoomDistance); } + /// + /// Shift + 좌클릭/우클릭 드래그: FOV 조절 (위로 밀면 FOV 감소=줌인, 아래로 밀면 FOV 증가=줌아웃) + /// + private void HandleFOV() + { + if (currentCamera == null) return; + + Vector2 delta = inputHandler.GetLookDelta(); + if (delta.sqrMagnitude < float.Epsilon) return; + + // 위로 밀면 FOV 감소 (줌인 효과), 아래로 밀면 FOV 증가 (줌아웃 효과) + float fovDelta = -delta.y * fovSensitivity; + + var lens = currentCamera.Lens; + lens.FieldOfView = Mathf.Clamp(lens.FieldOfView + fovDelta, minFOV, maxFOV); + currentCamera.Lens = lens; + } + /// /// 스무딩을 적용하여 카메라 위치 업데이트 /// @@ -742,8 +796,6 @@ public class CameraManager : MonoBehaviour, IController /// public void SetImmediate(int index) { - Debug.Log($"[CameraManager] 카메라 {index}번으로 전환 시작 (총 {cameraPresets?.Count ?? 0}개)"); - if (!ValidateCameraIndex(index)) return; var newPreset = cameraPresets[index]; @@ -760,7 +812,8 @@ public class CameraManager : MonoBehaviour, IController // 이전 프리셋의 orbit 상태 저장 if (oldPreset != null && oldPreset.allowMouseControl) { - oldPreset.SaveOrbitState(targetHorizontalAngle, targetVerticalAngle, targetDistance, targetFocusPoint); + float currentFOV = oldPreset.virtualCamera != null ? oldPreset.virtualCamera.Lens.FieldOfView : 60f; + oldPreset.SaveOrbitState(targetHorizontalAngle, targetVerticalAngle, targetDistance, targetFocusPoint, currentFOV); } currentPreset = newPreset; @@ -770,7 +823,7 @@ public class CameraManager : MonoBehaviour, IController if (newPreset.hasOrbitState && newPreset.allowMouseControl) { // 저장된 orbit 상태 복원 - if (newPreset.TryRestoreOrbitState(out float hAngle, out float vAngle, out float dist, out Vector3 focus)) + if (newPreset.TryRestoreOrbitState(out float hAngle, out float vAngle, out float dist, out Vector3 focus, out float fov)) { targetHorizontalAngle = hAngle; targetVerticalAngle = vAngle; @@ -781,6 +834,14 @@ public class CameraManager : MonoBehaviour, IController verticalAngle = vAngle; currentDistance = dist; focusPoint = focus; + + // FOV 복원 + if (newPreset.virtualCamera != null && fov > 0) + { + var lens = newPreset.virtualCamera.Lens; + lens.FieldOfView = fov; + newPreset.virtualCamera.Lens = lens; + } } } else @@ -797,7 +858,6 @@ public class CameraManager : MonoBehaviour, IController streamDeckManager.NotifyCameraChanged(); } - Debug.Log($"[CameraManager] 카메라 전환 완료: {newCameraName}"); } private bool ValidateCameraIndex(int index) @@ -832,9 +892,10 @@ public class CameraManager : MonoBehaviour, IController return; } - // 블렌드용 카메라 생성 - GameObject blendCamObj = new GameObject("BlendCamera"); - blendCamObj.transform.SetParent(mainCamera.transform.parent); + // 블렌드용 카메라 생성 - 독립적인 오브젝트로 (부모 없음) + // Cinemachine Brain의 영향을 피하기 위해 부모를 설정하지 않음 + GameObject blendCamObj = new GameObject("BlendCamera_Independent"); + blendCamObj.transform.SetParent(null); // 부모 없이 루트에 배치 blendCamera = blendCamObj.AddComponent(); // 메인 카메라 설정 복사 @@ -860,7 +921,6 @@ public class CameraManager : MonoBehaviour, IController blendCameraData.volumeTrigger = mainCameraData.volumeTrigger; } - Debug.Log("[CameraManager] 블렌드 카메라 생성 완료 (URP 설정 포함)"); } /// @@ -886,61 +946,73 @@ public class CameraManager : MonoBehaviour, IController Destroy(blendRenderTexture); } - // 새 렌더 텍스처 생성 - blendRenderTexture = new RenderTexture(width, height, 24, RenderTextureFormat.ARGB32); + // 새 렌더 텍스처 생성 - 색상 전용 (depth 없음), 리니어 색공간에서 올바른 블렌딩 + var descriptor = new RenderTextureDescriptor(width, height, RenderTextureFormat.ARGB32, 0); // depth = 0 + descriptor.sRGB = true; // sRGB 텍스처로 설정하여 리니어 파이프라인과 일치 + blendRenderTexture = new RenderTexture(descriptor); blendRenderTexture.name = "CameraBlendRT"; blendRenderTexture.Create(); - Debug.Log($"[CameraManager] 블렌드 렌더 텍스처 생성: {width}x{height}"); } /// /// 크로스 디졸브 블렌드 전환 코루틴 /// private IEnumerator BlendTransitionCoroutine(int targetIndex, float duration) + { + if (useRealtimeBlend) + { + yield return RealtimeBlendTransitionCoroutine(targetIndex, duration); + } + else + { + yield return SnapshotBlendTransitionCoroutine(targetIndex, duration); + } + } + + /// + /// 스냅샷 블렌딩 (이전 화면 정지) + /// + private IEnumerator SnapshotBlendTransitionCoroutine(int targetIndex, float duration) { isBlending = true; - // 블렌드 카메라/텍스처 준비 - EnsureBlendCamera(); + // 블렌드 텍스처 준비 EnsureBlendRenderTexture(); - if (blendCamera == null || blendRenderTexture == null) + if (blendRenderTexture == null) { - Debug.LogError("[CameraManager] 블렌드 카메라 또는 텍스처 생성 실패"); SetImmediate(targetIndex); isBlending = false; blendCoroutine = null; yield break; } - // 메인 카메라의 현재 위치/회전 복사 (Cinemachine이 제어하는 실제 카메라) - Camera mainCamera = Camera.main; - if (mainCamera != null) + // 렌더 패스에서 현재 프레임(포스트 프로세싱 적용 후)을 캡처하도록 요청 + CameraBlendController.RequestCapture(blendRenderTexture); + + // 캡처가 완료될 때까지 대기 (다음 프레임 렌더링 후) + yield return new WaitForEndOfFrame(); + yield return null; // 렌더 패스가 실행될 때까지 한 프레임 더 대기 + + // 캡처 완료 확인 + if (!CameraBlendController.CaptureReady) { - blendCamera.transform.position = mainCamera.transform.position; - blendCamera.transform.rotation = mainCamera.transform.rotation; - blendCamera.fieldOfView = mainCamera.fieldOfView; + CameraBlendController.EndBlend(); + SetImmediate(targetIndex); + isBlending = false; + blendCoroutine = null; + yield break; } - // 블렌드 카메라로 현재 화면을 렌더 텍스처에 렌더링 - blendCamera.targetTexture = blendRenderTexture; - blendCamera.enabled = true; - blendCamera.Render(); - blendCamera.enabled = false; + // 블렌딩 시작 - BlendAmount = 1 (이전 카메라만 보임) + CameraBlendController.StartBlendAfterCapture(); + CameraBlendController.BlendAmount = 1f; - Debug.Log($"[CameraManager] 블렌드 시작 - Duration: {duration}s"); - - // 블렌딩 시작 - BlendAmount = 0 (이전 카메라 A만 보임) - CameraBlendController.StartBlend(blendRenderTexture); - - // 한 프레임 대기 - 블렌딩이 적용된 상태로 렌더링되도록 - yield return null; - - // 카메라 전환 (이제 BlendAmount=0이므로 A만 보임) + // 카메라 전환 (이제 BlendAmount=1이므로 캡처된 이전 화면만 보임) SetImmediate(targetIndex); - // 블렌드 진행: 0 → 1 (A에서 B로) + // 블렌드 진행: 1 → 0 (이전 카메라가 서서히 사라지고 새 카메라가 드러남) float elapsed = 0f; while (elapsed < duration) { @@ -948,21 +1020,145 @@ public class CameraManager : MonoBehaviour, IController float t = Mathf.Clamp01(elapsed / duration); // 부드러운 이징 적용 (SmoothStep) t = t * t * (3f - 2f * t); - CameraBlendController.BlendAmount = t; + // 1에서 0으로: 이전 카메라가 서서히 사라짐 + CameraBlendController.BlendAmount = 1f - t; yield return null; } - CameraBlendController.BlendAmount = 1f; + CameraBlendController.BlendAmount = 0f; // 블렌딩 종료 CameraBlendController.EndBlend(); - Debug.Log("[CameraManager] 블렌드 완료"); + isBlending = false; + blendCoroutine = null; + } + + /// + /// 실시간 블렌딩 (두 카메라 동시 렌더링) + /// 이전 카메라 위치를 저장해두고 그 위치에서 렌더링, 서서히 사라지면서 새 카메라가 드러남 + /// + private IEnumerator RealtimeBlendTransitionCoroutine(int targetIndex, float duration) + { + isBlending = true; + + // 이전 카메라 프리셋 저장 + var prevPreset = currentPreset; + if (prevPreset == null || prevPreset.virtualCamera == null) + { + SetImmediate(targetIndex); + isBlending = false; + blendCoroutine = null; + yield break; + } + + // SetImmediate 호출 전에 이전 카메라의 위치/회전/FOV를 저장 + Vector3 prevCameraPosition = prevPreset.virtualCamera.transform.position; + Quaternion prevCameraRotation = prevPreset.virtualCamera.transform.rotation; + float prevCameraFOV = prevPreset.virtualCamera.Lens.FieldOfView; + + // 블렌드 텍스처 준비 + EnsureBlendRenderTexture(); + EnsurePrevCameraRenderTexture(); + + if (blendRenderTexture == null || prevCameraRenderTexture == null) + { + SetImmediate(targetIndex); + isBlending = false; + blendCoroutine = null; + yield break; + } + + // 블렌드 카메라 준비 + EnsureBlendCamera(); + if (blendCamera == null) + { + SetImmediate(targetIndex); + isBlending = false; + blendCoroutine = null; + yield break; + } + + // 블렌드 카메라를 이전 카메라 위치로 설정하고 첫 프레임 렌더링 + blendCamera.transform.SetPositionAndRotation(prevCameraPosition, prevCameraRotation); + blendCamera.fieldOfView = prevCameraFOV; + blendCamera.targetTexture = prevCameraRenderTexture; + + // Camera.Render()로 렌더링 (URP에서도 포스트 프로세싱 적용됨) + blendCamera.Render(); + Graphics.Blit(prevCameraRenderTexture, blendRenderTexture); + + // 실시간 블렌딩 시작 (BlendAmount = 1에서 시작, 이전 카메라가 100% 보임) + CameraBlendController.StartRealtimeBlend(blendRenderTexture); + CameraBlendController.BlendAmount = 1f; + + // 새 카메라로 전환 (메인 카메라는 이제 새 위치에서 렌더링됨) + SetImmediate(targetIndex); + + // 블렌드 진행: 1 → 0 (이전 카메라 화면이 서서히 사라지고 새 카메라가 드러남) + float elapsed = 0f; + while (elapsed < duration) + { + // 이전 카메라 시점에서 먼저 렌더링 (메인 카메라 렌더링 전에) + blendCamera.transform.SetPositionAndRotation(prevCameraPosition, prevCameraRotation); + blendCamera.fieldOfView = prevCameraFOV; + blendCamera.targetTexture = prevCameraRenderTexture; + + // Camera.Render()로 렌더링 (URP에서도 포스트 프로세싱 적용됨) + blendCamera.Render(); + Graphics.Blit(prevCameraRenderTexture, blendRenderTexture); + + // 다음 프레임까지 대기 + yield return null; + + elapsed += Time.deltaTime; + float t = Mathf.Clamp01(elapsed / duration); + // 부드러운 이징 적용 (SmoothStep) + t = t * t * (3f - 2f * t); + // 1에서 0으로: 이전 카메라가 서서히 사라짐 + CameraBlendController.BlendAmount = 1f - t; + } + + CameraBlendController.BlendAmount = 0f; + + // 블렌딩 종료 + CameraBlendController.EndBlend(); isBlending = false; blendCoroutine = null; } + /// + /// 실시간 블렌딩용 이전 카메라 렌더 텍스처 생성/갱신 + /// + private void EnsurePrevCameraRenderTexture() + { + int width = Screen.width; + int height = Screen.height; + + // 이미 적절한 크기의 텍스처가 있으면 재사용 + if (prevCameraRenderTexture != null && + prevCameraRenderTexture.width == width && + prevCameraRenderTexture.height == height) + { + return; + } + + // 기존 텍스처 해제 + if (prevCameraRenderTexture != null) + { + prevCameraRenderTexture.Release(); + Destroy(prevCameraRenderTexture); + } + + // 새 렌더 텍스처 생성 - HDR 포맷 + depth 포함 (포스트 프로세싱 지원) + var descriptor = new RenderTextureDescriptor(width, height, RenderTextureFormat.DefaultHDR, 24); + descriptor.sRGB = false; // HDR은 리니어 포맷 + prevCameraRenderTexture = new RenderTexture(descriptor); + prevCameraRenderTexture.name = "PrevCameraRT"; + prevCameraRenderTexture.Create(); + } + private void UpdateCameraPriorities(CinemachineCamera newCamera) { if (newCamera == null) diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Editor/CameraManagerEditor.cs b/Assets/Scripts/Streamingle/StreamingleControl/Editor/CameraManagerEditor.cs index dc32a65a..1730a09f 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Editor/CameraManagerEditor.cs +++ b/Assets/Scripts/Streamingle/StreamingleControl/Editor/CameraManagerEditor.cs @@ -17,6 +17,7 @@ public class CameraManagerEditor : Editor private bool showControlSettings = true; private bool showSmoothingSettings = true; private bool showZoomSettings = true; + private bool showFOVSettings = true; private bool showRotationTarget = true; private bool showBlendSettings = true; @@ -29,10 +30,14 @@ public class CameraManagerEditor : Editor private SerializedProperty rotationSmoothingProp; private SerializedProperty minZoomDistanceProp; private SerializedProperty maxZoomDistanceProp; + private SerializedProperty fovSensitivityProp; + private SerializedProperty minFOVProp; + private SerializedProperty maxFOVProp; private SerializedProperty useAvatarHeadAsTargetProp; private SerializedProperty manualRotationTargetProp; private SerializedProperty useBlendTransitionProp; private SerializedProperty blendTimeProp; + private SerializedProperty useRealtimeBlendProp; // 스타일 private GUIStyle headerStyle; @@ -52,10 +57,14 @@ public class CameraManagerEditor : Editor rotationSmoothingProp = serializedObject.FindProperty("rotationSmoothing"); minZoomDistanceProp = serializedObject.FindProperty("minZoomDistance"); maxZoomDistanceProp = serializedObject.FindProperty("maxZoomDistance"); + fovSensitivityProp = serializedObject.FindProperty("fovSensitivity"); + minFOVProp = serializedObject.FindProperty("minFOV"); + maxFOVProp = serializedObject.FindProperty("maxFOV"); useAvatarHeadAsTargetProp = serializedObject.FindProperty("useAvatarHeadAsTarget"); manualRotationTargetProp = serializedObject.FindProperty("manualRotationTarget"); useBlendTransitionProp = serializedObject.FindProperty("useBlendTransition"); blendTimeProp = serializedObject.FindProperty("blendTime"); + useRealtimeBlendProp = serializedObject.FindProperty("useRealtimeBlend"); } private void OnDisable() @@ -126,6 +135,9 @@ public class CameraManagerEditor : Editor // 줌 제한 섹션 DrawZoomLimitsSection(); + // FOV 설정 섹션 + DrawFOVSettingsSection(); + // 회전 타겟 섹션 DrawRotationTargetSection(); @@ -211,6 +223,35 @@ public class CameraManagerEditor : Editor EditorGUILayout.EndVertical(); } + private void DrawFOVSettingsSection() + { + EditorGUILayout.BeginVertical(sectionBoxStyle); + + showFOVSettings = EditorGUILayout.Foldout(showFOVSettings, "FOV Settings", true, EditorStyles.foldoutHeader); + + if (showFOVSettings) + { + EditorGUILayout.Space(5); + EditorGUI.indentLevel++; + + EditorGUILayout.PropertyField(fovSensitivityProp, new GUIContent("FOV 감도", "Shift + 드래그 시 FOV 변화 감도 (0.01 ~ 5)")); + EditorGUILayout.PropertyField(minFOVProp, new GUIContent("최소 FOV", "카메라 최소 FOV (줌인 한계)")); + EditorGUILayout.PropertyField(maxFOVProp, new GUIContent("최대 FOV", "카메라 최대 FOV (줌아웃 한계)")); + + // 경고 표시 + if (minFOVProp.floatValue >= maxFOVProp.floatValue) + { + EditorGUILayout.HelpBox("최소 FOV는 최대 FOV보다 작아야 합니다.", MessageType.Warning); + } + + EditorGUILayout.HelpBox("Shift + 좌클릭/우클릭 드래그로 FOV를 조절합니다.\n위로 밀면 줌인(FOV 감소), 아래로 밀면 줌아웃(FOV 증가)", MessageType.Info); + + EditorGUI.indentLevel--; + } + + EditorGUILayout.EndVertical(); + } + private void DrawRotationTargetSection() { EditorGUILayout.BeginVertical(sectionBoxStyle); @@ -254,11 +295,20 @@ public class CameraManagerEditor : Editor EditorGUI.BeginDisabledGroup(!useBlendTransitionProp.boolValue); EditorGUILayout.PropertyField(blendTimeProp, new GUIContent("블렌드 시간", "크로스 디졸브 소요 시간 (초)")); + EditorGUILayout.PropertyField(useRealtimeBlendProp, new GUIContent("실시간 블렌딩", "두 카메라를 동시에 렌더링하며 블렌딩 (성능 비용 증가)")); EditorGUI.EndDisabledGroup(); if (useBlendTransitionProp.boolValue) { - EditorGUILayout.HelpBox("URP Renderer에 CameraBlendRendererFeature가 추가되어 있어야 합니다.", MessageType.Info); + if (useRealtimeBlendProp.boolValue) + { + EditorGUILayout.HelpBox("실시간 모드: 블렌딩 중 두 카메라 모두 실시간으로 렌더링됩니다.\n성능 비용이 증가하지만 이전 카메라도 움직입니다.", MessageType.Info); + } + else + { + EditorGUILayout.HelpBox("스냅샷 모드: 이전 화면을 캡처한 후 블렌딩합니다.\n성능 효율적이지만 이전 화면이 정지합니다.", MessageType.Info); + } + EditorGUILayout.HelpBox("URP Renderer에 CameraBlendRendererFeature가 추가되어 있어야 합니다.", MessageType.Warning); } EditorGUI.indentLevel--; diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Input/InputHandler.cs b/Assets/Scripts/Streamingle/StreamingleControl/Input/InputHandler.cs index 6c9cedb3..0a87f120 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Input/InputHandler.cs +++ b/Assets/Scripts/Streamingle/StreamingleControl/Input/InputHandler.cs @@ -9,6 +9,7 @@ public class InputHandler : MonoBehaviour private bool isOrbitActive; private bool isZoomActive; private bool isCtrlRightZoomActive; + private bool isFOVActive; // 현재 활성화된 입력 모드 (충돌 방지) private InputMode currentMode = InputMode.None; @@ -23,6 +24,7 @@ public class InputHandler : MonoBehaviour Orbit, // Alt + 우클릭 또는 Alt + 좌클릭 Zoom, // Ctrl + 좌클릭 CtrlRightZoom, // Ctrl + 우클릭 + FOV, // Shift + 좌클릭 또는 Shift + 우클릭 Rotation, // 우클릭 Pan // 휠클릭 } @@ -57,6 +59,7 @@ public class InputHandler : MonoBehaviour isOrbitActive = false; isZoomActive = false; isCtrlRightZoomActive = false; + isFOVActive = false; isRightMouseHeld = false; isMiddleMouseHeld = false; lastScrollValue = 0f; @@ -85,6 +88,7 @@ public class InputHandler : MonoBehaviour bool middleMouse = Input.GetMouseButton(2); bool altKey = Input.GetKey(KeyCode.LeftAlt) || Input.GetKey(KeyCode.RightAlt); bool ctrlKey = Input.GetKey(KeyCode.LeftControl) || Input.GetKey(KeyCode.RightControl); + bool shiftKey = Input.GetKey(KeyCode.LeftShift) || Input.GetKey(KeyCode.RightShift); // 모든 마우스 버튼이 해제되면 모드 리셋 if (!leftMouse && !rightMouse && !middleMouse) @@ -107,6 +111,10 @@ public class InputHandler : MonoBehaviour { currentMode = InputMode.Zoom; } + else if (shiftKey && (leftMouse || rightMouse)) + { + currentMode = InputMode.FOV; + } else if (rightMouse) { currentMode = InputMode.Rotation; @@ -121,6 +129,7 @@ public class InputHandler : MonoBehaviour isOrbitActive = (currentMode == InputMode.Orbit) && (rightMouse || leftMouse) && altKey; isZoomActive = (currentMode == InputMode.Zoom) && leftMouse && ctrlKey; isCtrlRightZoomActive = (currentMode == InputMode.CtrlRightZoom) && rightMouse && ctrlKey; + isFOVActive = (currentMode == InputMode.FOV) && (leftMouse || rightMouse) && shiftKey; isRightMouseHeld = (currentMode == InputMode.Rotation) && rightMouse; isMiddleMouseHeld = (currentMode == InputMode.Pan) && middleMouse; @@ -137,6 +146,10 @@ public class InputHandler : MonoBehaviour { currentMode = InputMode.None; } + else if (currentMode == InputMode.FOV && ((!leftMouse && !rightMouse) || !shiftKey)) + { + currentMode = InputMode.None; + } else if (currentMode == InputMode.Rotation && !rightMouse) { currentMode = InputMode.None; @@ -156,6 +169,7 @@ public class InputHandler : MonoBehaviour public bool IsOrbitActive() => isOrbitActive; public bool IsZoomActive() => isZoomActive; public bool IsCtrlRightZoomActive() => isCtrlRightZoomActive; + public bool IsFOVActive() => isFOVActive; /// /// 현재 어떤 입력 모드도 활성화되지 않았는지 확인합니다. diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Prop/Editor/PropBrowserWindow.cs b/Assets/Scripts/Streamingle/StreamingleControl/Prop/Editor/PropBrowserWindow.cs index 5c7d15da..f9d4dd62 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Prop/Editor/PropBrowserWindow.cs +++ b/Assets/Scripts/Streamingle/StreamingleControl/Prop/Editor/PropBrowserWindow.cs @@ -727,7 +727,12 @@ namespace Streamingle.Prop.Editor if (ext == ".prefab") { - propInfo.prefabPaths.Add(assetPath); + // Prefab 폴더 안에 있는 프리팹만 수집 (Particle 등 다른 폴더 제외) + string parentFolder = Path.GetFileName(Path.GetDirectoryName(file)); + if (parentFolder.Equals("Prefab", StringComparison.OrdinalIgnoreCase)) + { + propInfo.prefabPaths.Add(assetPath); + } } else if (ext == ".glb" || ext == ".fbx" || ext == ".obj") { diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.mat b/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.mat index 95cbb56f..fbcb8667 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.mat +++ b/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.mat @@ -33,7 +33,7 @@ Material: m_Offset: {x: 0, y: 0} m_Ints: [] m_Floats: - - _BlendAmount: 1 + - _BlendAmount: 0.000075280666 m_Colors: [] m_BuildTextureStacks: [] m_AllowLocking: 1 diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.shader b/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.shader index 21b573cb..5585439e 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.shader +++ b/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlend.shader @@ -37,14 +37,15 @@ Shader "Streamingle/CameraBlend" { float2 uv = input.texcoord; - // 현재 카메라 (Blitter에서 전달됨) + // 현재 카메라 (Blitter에서 전달됨) - 동일한 샘플러 사용 float4 currentColor = SAMPLE_TEXTURE2D(_BlitTexture, sampler_LinearClamp, uv); - // 이전 카메라 (캡처된 텍스처) - float4 prevColor = SAMPLE_TEXTURE2D(_PrevTex, sampler_PrevTex, uv); + // 이전 카메라 (캡처된 텍스처) - 동일한 Linear 샘플러 사용 + float4 prevColor = SAMPLE_TEXTURE2D(_PrevTex, sampler_LinearClamp, uv); - // 두 카메라를 블렌딩 (BlendAmount: 0 = 이전, 1 = 현재) - float4 finalColor = lerp(prevColor, currentColor, _BlendAmount); + // 리니어 공간에서 블렌딩 (BlendAmount: 1 = 이전, 0 = 현재) + // 이전 카메라(B)가 위에 덮이고 서서히 사라짐 + float4 finalColor = lerp(currentColor, prevColor, _BlendAmount); return finalColor; } diff --git a/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlendRendererFeature.cs b/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlendRendererFeature.cs index fef6c8b8..1a5a7da4 100644 --- a/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlendRendererFeature.cs +++ b/Assets/Scripts/Streamingle/StreamingleControl/Rendering/CameraBlendRendererFeature.cs @@ -12,8 +12,8 @@ public class CameraBlendRendererFeature : ScriptableRendererFeature [System.Serializable] public class Settings { - // BeforeRenderingPostProcessing으로 변경 - 포스트 프로세싱 전에 블렌딩 - public RenderPassEvent renderPassEvent = RenderPassEvent.BeforeRenderingPostProcessing; + // AfterRenderingPostProcessing - 모든 포스트 프로세싱 적용 후 블렌딩 + public RenderPassEvent renderPassEvent = RenderPassEvent.AfterRenderingPostProcessing; public Material blendMaterial; } @@ -35,8 +35,9 @@ public class CameraBlendRendererFeature : ScriptableRendererFeature if (renderingData.cameraData.cameraType != CameraType.Game) return; - // 블렌딩이 활성화된 경우에만 패스 추가 - if (CameraBlendController.IsBlending && CameraBlendController.BlendTexture != null) + // 캡처 요청이 있거나 블렌딩 중일 때 패스 추가 + if (CameraBlendController.CaptureRequested || + (CameraBlendController.IsBlending && CameraBlendController.BlendTexture != null)) { renderer.EnqueuePass(blendPass); } @@ -63,6 +64,12 @@ public class CameraBlendRenderPass : ScriptableRenderPass public TextureHandle destinationTexture; } + private class CapturePassData + { + public TextureHandle sourceTexture; + public RenderTexture targetTexture; + } + public CameraBlendRenderPass(CameraBlendRendererFeature.Settings settings) { this.settings = settings; @@ -75,16 +82,12 @@ public class CameraBlendRenderPass : ScriptableRenderPass if (settings.blendMaterial == null) return; - if (!CameraBlendController.IsBlending || CameraBlendController.BlendTexture == null) - return; - var resourceData = frameData.Get(); var cameraData = frameData.Get(); - // 백버퍼인 경우 스킵 (BeforeRenderingPostProcessing에서는 일반적으로 false) + // 백버퍼인 경우 스킵 if (resourceData.isActiveTargetBackBuffer) { - Debug.LogWarning("[CameraBlend] isActiveTargetBackBuffer - skipping"); return; } @@ -93,10 +96,36 @@ public class CameraBlendRenderPass : ScriptableRenderPass // source가 유효한지 확인 if (!source.IsValid()) { - Debug.LogWarning("[CameraBlend] source texture is not valid"); return; } + // 캡처 요청 처리 - 현재 프레임(포스트 프로세싱 적용 후)을 캡처 + if (CameraBlendController.CaptureRequested && CameraBlendController.BlendTexture != null) + { + // UnsafePass를 사용하여 RenderTexture에 직접 복사 + using (var builder = renderGraph.AddUnsafePass("Camera Blend Capture", out var captureData, profilingSampler)) + { + captureData.sourceTexture = source; + captureData.targetTexture = CameraBlendController.BlendTexture; + + builder.UseTexture(source, AccessFlags.Read); + builder.AllowPassCulling(false); + + builder.SetRenderFunc((CapturePassData data, UnsafeGraphContext context) => + { + // NativeCommandBuffer를 통해 Blit 수행 + var nativeCmd = CommandBufferHelpers.GetNativeCommandBuffer(context.cmd); + nativeCmd.Blit(data.sourceTexture, data.targetTexture); + CameraBlendController.CaptureReady = true; + }); + } + return; // 캡처만 하고 블렌딩은 다음 프레임부터 + } + + // 블렌딩이 활성화되지 않았으면 스킵 + if (!CameraBlendController.IsBlending || CameraBlendController.BlendTexture == null) + return; + // cameraColorDesc 사용 - 카메라 색상 텍스처 설명자 var cameraTargetDesc = renderGraph.GetTextureDesc(resourceData.cameraColor); cameraTargetDesc.name = "_CameraBlendDestination"; @@ -158,6 +187,9 @@ public static class CameraBlendController private static bool isBlending = false; private static float blendAmount = 1f; private static RenderTexture blendTexture; + private static bool captureRequested = false; + private static bool captureReady = false; + private static bool isRealtimeMode = false; public static bool IsBlending { @@ -177,6 +209,63 @@ public static class CameraBlendController set => blendTexture = value; } + public static bool CaptureRequested + { + get => captureRequested; + set => captureRequested = value; + } + + public static bool CaptureReady + { + get => captureReady; + set => captureReady = value; + } + + public static bool IsRealtimeMode + { + get => isRealtimeMode; + set => isRealtimeMode = value; + } + + /// + /// 다음 프레임에서 현재 화면을 캡처하도록 요청합니다. (스냅샷 모드) + /// + public static void RequestCapture(RenderTexture targetTexture) + { + blendTexture = targetTexture; + captureRequested = true; + captureReady = false; + isRealtimeMode = false; + } + + /// + /// 캡처가 완료된 후 블렌딩을 시작합니다. (스냅샷 모드) + /// BlendAmount = 1에서 시작 (이전 카메라 100% 보임) + /// + public static void StartBlendAfterCapture() + { + if (captureReady && blendTexture != null) + { + blendAmount = 1f; + isBlending = true; + captureRequested = false; + } + } + + /// + /// 실시간 블렌딩을 시작합니다. (매 프레임 이전 카메라 렌더링) + /// BlendAmount = 1에서 시작 (이전 카메라 100% 보임) + /// + public static void StartRealtimeBlend(RenderTexture texture) + { + blendTexture = texture; + blendAmount = 1f; + isBlending = true; + isRealtimeMode = true; + captureRequested = false; + captureReady = false; + } + public static void StartBlend(RenderTexture texture) { blendTexture = texture; @@ -189,6 +278,9 @@ public static class CameraBlendController isBlending = false; blendAmount = 1f; blendTexture = null; + captureRequested = false; + captureReady = false; + isRealtimeMode = false; } public static void Reset() diff --git a/Assets/Scripts/WefLab/WefLabWebSocketClient.cs b/Assets/Scripts/WefLab/WefLabWebSocketClient.cs index 9f1a30c0..545c0bb1 100644 --- a/Assets/Scripts/WefLab/WefLabWebSocketClient.cs +++ b/Assets/Scripts/WefLab/WefLabWebSocketClient.cs @@ -47,14 +47,29 @@ namespace WefLab [Tooltip("Maximum donation amount (inclusive, -1 for unlimited)")] public int maxAmount = -1; - [Header("Event Settings")] - [Tooltip("Number of times to repeat the event (minimum 1)")] + [Header("Repeat Settings")] + [Tooltip("Use amount-based repeat count (divide amount by amountPerRepeat)")] + public bool useAmountBasedRepeat = false; + + [Tooltip("Amount of KRW per repeat (e.g., 1000 = 1 repeat per 1000 KRW)")] [Min(1)] - public int repeatCount = 1; + public int amountPerRepeat = 1000; + + [Tooltip("Minimum repeat count")] + [Min(1)] + public int minRepeatCount = 1; + + [Tooltip("Maximum repeat count (0 = unlimited)")] + [Min(0)] + public int maxRepeatCount = 20; + + [Tooltip("Fixed repeat count (used when useAmountBasedRepeat is false)")] + [Min(1)] + public int fixedRepeatCount = 1; [Tooltip("Delay between each repeat in seconds (0 for immediate)")] [Min(0)] - public float repeatDelay = 0f; + public float repeatDelay = 0.15f; [Header("Event")] [Tooltip("Unity event to trigger when donation amount is in range")] @@ -73,6 +88,29 @@ namespace WefLab return true; } + + /// + /// Calculate repeat count based on donation amount + /// + public int GetRepeatCount(int amount) + { + if (!useAmountBasedRepeat) + { + return fixedRepeatCount; + } + + // Calculate repeat count based on amount + int count = amount / amountPerRepeat; + + // Apply min/max limits + count = Mathf.Max(count, minRepeatCount); + if (maxRepeatCount > 0) + { + count = Mathf.Min(count, maxRepeatCount); + } + + return count; + } } /// @@ -89,6 +127,27 @@ namespace WefLab [Tooltip("Donation event triggers based on amount ranges")] public DonationEventTrigger[] donationTriggers = Array.Empty(); + [Header("Queue Settings")] + [Tooltip("Enable sequential processing of donations")] + public bool enableQueue = true; + + [Tooltip("Delay between each donation alert (seconds)")] + [Min(0.1f)] + public float alertDelay = 3f; + + [Tooltip("Maximum queue size (0 = unlimited)")] + [Min(0)] + public int maxQueueSize = 50; + + // Queue state (visible in Inspector for debugging) + [Header("Queue Status (Read Only)")] + [SerializeField] private int queueCount = 0; + [SerializeField] private bool isProcessingQueue = false; + + // Donation queue + private Queue donationQueue = new Queue(); + private Coroutine queueProcessorCoroutine = null; + // Hidden connection info [HideInInspector] public bool isConnected = false; [HideInInspector] public string currentSid = ""; @@ -532,7 +591,7 @@ namespace WefLab timestamp = timestamp }; - TriggerDonationEvents(donation); + EnqueueDonation(donation); } /// @@ -580,8 +639,64 @@ namespace WefLab Debug.Log($"[WefLab] Donation: {donorName} - {rawAmount} → {amount} KRW ({platform})"); - // Trigger events - TriggerDonationEvents(donation); + // Enqueue donation for sequential processing + EnqueueDonation(donation); + } + + /// + /// Enqueue donation for sequential processing + /// + private void EnqueueDonation(DonationData donation) + { + if (enableQueue) + { + // Check queue size limit + if (maxQueueSize > 0 && donationQueue.Count >= maxQueueSize) + { + Debug.LogWarning($"[WefLab] Queue full ({maxQueueSize}), dropping oldest donation"); + donationQueue.Dequeue(); + } + + donationQueue.Enqueue(donation); + queueCount = donationQueue.Count; + Debug.Log($"[WefLab] Donation queued. Queue size: {queueCount}"); + + // Start queue processor if not running + if (!isProcessingQueue) + { + queueProcessorCoroutine = StartCoroutine(ProcessDonationQueue()); + } + } + else + { + // Direct trigger without queue (original behavior) + TriggerDonationEvents(donation); + } + } + + /// + /// Process donation queue sequentially with fixed delay + /// + private IEnumerator ProcessDonationQueue() + { + isProcessingQueue = true; + + while (donationQueue.Count > 0) + { + var donation = donationQueue.Dequeue(); + queueCount = donationQueue.Count; + + // Trigger events + TriggerDonationEvents(donation); + + Debug.Log($"[WefLab] Alert triggered. Waiting {alertDelay:F1}s. Remaining in queue: {donationQueue.Count}"); + + // Wait for fixed delay + yield return new WaitForSeconds(alertDelay); + } + + isProcessingQueue = false; + queueProcessorCoroutine = null; } /// @@ -606,10 +721,11 @@ namespace WefLab // Check if donation amount is in range if (trigger.IsInRange(donation.amount)) { - Debug.Log($"[WefLab] Triggering: {trigger.triggerName} (Amount: {donation.amount}, Range: {trigger.minAmount}-{(trigger.maxAmount >= 0 ? trigger.maxAmount.ToString() : "unlimited")}, Repeat: {trigger.repeatCount}x)"); + int repeatCount = trigger.GetRepeatCount(donation.amount); + Debug.Log($"[WefLab] Triggering: {trigger.triggerName} (Amount: {donation.amount}, Range: {trigger.minAmount}-{(trigger.maxAmount >= 0 ? trigger.maxAmount.ToString() : "unlimited")}, Repeat: {repeatCount}x)"); // Start coroutine to handle repeated invocation - StartCoroutine(InvokeRepeatedEvent(trigger, donation)); + StartCoroutine(InvokeRepeatedEvent(trigger, donation, repeatCount)); triggeredAny = true; } } @@ -623,15 +739,15 @@ namespace WefLab /// /// Coroutine to invoke event multiple times with delay /// - private IEnumerator InvokeRepeatedEvent(DonationEventTrigger trigger, DonationData donation) + private IEnumerator InvokeRepeatedEvent(DonationEventTrigger trigger, DonationData donation, int repeatCount) { - for (int i = 0; i < trigger.repeatCount; i++) + for (int i = 0; i < repeatCount; i++) { // Invoke the event trigger.onDonation?.Invoke(donation); // Wait for delay before next repetition (skip on last iteration) - if (i < trigger.repeatCount - 1 && trigger.repeatDelay > 0) + if (i < repeatCount - 1 && trigger.repeatDelay > 0) { yield return new WaitForSeconds(trigger.repeatDelay); } @@ -724,6 +840,81 @@ namespace WefLab return isConnected && ws != null && ws.IsAlive; } + /// + /// Get current queue count + /// + public int GetQueueCount() + { + return donationQueue.Count; + } + + /// + /// Check if queue is being processed + /// + public bool IsQueueProcessing() + { + return isProcessingQueue; + } + + /// + /// Clear all pending donations in queue + /// + public void ClearQueue() + { + donationQueue.Clear(); + queueCount = 0; + Debug.Log("[WefLab] Queue cleared"); + } + + /// + /// Skip current alert and move to next in queue + /// + public void SkipCurrentAlert() + { + if (queueProcessorCoroutine != null) + { + StopCoroutine(queueProcessorCoroutine); + queueProcessorCoroutine = null; + } + + if (donationQueue.Count > 0) + { + Debug.Log("[WefLab] Skipping to next alert"); + queueProcessorCoroutine = StartCoroutine(ProcessDonationQueue()); + } + else + { + isProcessingQueue = false; + Debug.Log("[WefLab] No more alerts in queue"); + } + } + + /// + /// Pause queue processing + /// + public void PauseQueue() + { + if (queueProcessorCoroutine != null) + { + StopCoroutine(queueProcessorCoroutine); + queueProcessorCoroutine = null; + isProcessingQueue = false; + Debug.Log("[WefLab] Queue paused"); + } + } + + /// + /// Resume queue processing + /// + public void ResumeQueue() + { + if (!isProcessingQueue && donationQueue.Count > 0) + { + queueProcessorCoroutine = StartCoroutine(ProcessDonationQueue()); + Debug.Log("[WefLab] Queue resumed"); + } + } + #endregion } }