You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
86 lines
3.0 KiB
C#
86 lines
3.0 KiB
C#
using System;
|
|
using System.Linq;
|
|
using System.Threading;
|
|
using UnityEngine;
|
|
using UnityEngine.Rendering;
|
|
|
|
namespace FluffyGroomingTool {
|
|
[Serializable]
|
|
public class ClumpGroomModifier : ICloneable {
|
|
[SerializeField] [Range(0f, 0.5f)] public float clumpsSpacing = 0.05f;
|
|
|
|
[SerializeField] public AnimationCurve attractionCurve = new AnimationCurve(
|
|
new Keyframe(0, 1f, 0.00592891034f, 0.00592891034f, 0, 0.397826046f),
|
|
new Keyframe(1f, 0f, -0.0187702253f, -0.0187702253f, 0.628260851f, 0)
|
|
);
|
|
|
|
[SerializeField] public StrandGroom[] strandsGroom;
|
|
public ComputeBuffer clumpGroomBuffer;
|
|
public bool needsUpdate;
|
|
private float curveSum = -1;
|
|
public string id = Guid.NewGuid().ToString();
|
|
|
|
public bool isSameCurve(float sum) {
|
|
// ReSharper disable CompareOfFloatsByEqualityOperator
|
|
if (curveSum == -1f) curveSum = sum;
|
|
|
|
if (sum != curveSum) {
|
|
curveSum = sum;
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
public void update() {
|
|
if (needsUpdate && strandsGroom != null) {
|
|
needsUpdate = false;
|
|
clumpGroomBuffer?.Dispose();
|
|
clumpGroomBuffer = new ComputeBuffer(strandsGroom.Length, StrandGroomStruct.size());
|
|
clumpGroomBuffer.SetData(strandsGroom.ToList().Select(StrandGroomStruct.convertToStruct).ToArray());
|
|
}
|
|
}
|
|
|
|
public void copyValuesFromComputeBufferToNativeObject() {
|
|
if (clumpGroomBuffer != null) AsyncGPUReadback.Request(clumpGroomBuffer, OnCompleteReadback);
|
|
}
|
|
|
|
void OnCompleteReadback(AsyncGPUReadbackRequest request) {
|
|
if (request.hasError) {
|
|
Debug.Log("GPU readback error detected for clumps.");
|
|
return;
|
|
}
|
|
|
|
var groomStructs = request.ToPersistentArray<StrandGroomStruct>();
|
|
new Thread(() => {
|
|
strandsGroom = groomStructs.Select(StrandGroom.convertFromStruct).ToArray();
|
|
groomStructs.Dispose();
|
|
}).Start();
|
|
}
|
|
|
|
public object Clone() {
|
|
return new ClumpGroomModifier {
|
|
clumpsSpacing = clumpsSpacing,
|
|
attractionCurve = new AnimationCurve(attractionCurve.keys),
|
|
strandsGroom = strandsGroom,
|
|
needsUpdate = true,
|
|
curveSum = curveSum,
|
|
id = id = Guid.NewGuid().ToString()
|
|
};
|
|
}
|
|
|
|
private float _tempClumpsSpacing = -1;
|
|
|
|
public float TempClumpSpacing {
|
|
get {
|
|
if (_tempClumpsSpacing == -1f) _tempClumpsSpacing = clumpsSpacing;
|
|
return _tempClumpsSpacing;
|
|
}
|
|
set => _tempClumpsSpacing = value;
|
|
}
|
|
|
|
public bool isDistanceBetweenClumpsUndoPerformed() {
|
|
return Math.Abs(TempClumpSpacing - clumpsSpacing) > GroomLayer.FLOAT_COMPARISON_TOLERANCE;
|
|
}
|
|
}
|
|
} |