我正在尝试使用滑块动态调整粒子大小,以及更改其颜色。
粒子用于在3D散点图中显示数据点。我正在使用以下代码:https://github.com/PrinzEugn/Scatterplot_Standalone
private ParticleSystem.Particle[] particlePoints;
void Update () {
pointScale = sizeSlider.value;
for (int i = 0; i < pointList.Count; i++) {
Quaternion quaternion = Camera.current.transform.rotation;
Vector3 angles = quaternion.eulerAngles;
// Set point color
particlePoints[i].startColor = new Color(angles.x, angles.y, angles.z, 1.0f);
particlePoints[i].transform.localScale = new Vector3(pointScale, pointScale, pointScale);
}
}
问题是粒子没有转换方法,并且更改“ startColour”不会更改任何内容。
API指出“粒子的当前大小是根据此值和活动大小模块按程序计算的。”
这是什么意思,我该如何更改粒子的大小?
答案 0 :(得分:0)
我刚刚看过PointRenderer.cs-> CreateParticles
和PlacePrefabPoints
很好地提示了必须更改的地方。
所以我想您只需更改比例值
foreach (var point in particlePoints)
{
Quaternion quaternion = Camera.current.transform.rotation;
Vector3 angles = quaternion.eulerAngles;
// Set point color
point.startColor = new Color(angles.x, angles.y, angles.z, 1.0f);
point.startSize = sizeSlider.value;
}
然后调用
GetComponent<ParticleSystem>().SetParticles(particlePoints, particlePoints.Length);
尽管您是否真的会在Update
中进行此操作,这还是个问题。我宁愿在sizeSlider.onValueChanged
中执行此操作,仅在必要时进行此操作(您甚至可以在更新视图之前设置一定的阈值,但必须对其进行更改),但是对于颜色来说,除了在其中进行操作外,别无选择Update
,但至少要在此使用阈值:
privtae ParticleSystem ps;
// I assume you have that referenced in the inspector
public Slider sizeSlider;
// flag to control whether system should be updated
private bool updateSystem;
privtae void Awake()
{
ps = GetComponent<ParticleSystem>();
}
private void OnEnable()
{
// add a listener to onValueChanged
// it is secure to remove it first (even if not there yet)
// this makes sure it is not added twice
sizeSlider.onValueChanged.RemoveListener(OnsliderChanged());
sizeSlider.onValueChanged.AddListener(OnsliderChanged());
}
private void OnDisable()
{
// cleanup listener
sizeSlider.onValueChanged.RemoveListener(OnsliderChanged());
}
private void OnSliderChanged()
{
foreach (var point in particlePoints)
{
point.startSize = sizeSlider.value;
}
// do the same also for the instantiated prefabs
foreach(Transform child in PointHolder.transform)
{
child.localScale = Vecto3.one * sizeSlider.value;
}
updateSystem = true;
}
private Quaternion lastCameraRot;
public float CameraUpdateThreshold;
private void Update()
{
if(Quaternion.Angle(Camera.current.transform.rotation, lastCameraRot) > CameraUpdateThreshold)
{
foreach (var point in particlePoints)
{
Quaternion quaternion = Camera.current.transform.rotation;
Vector3 angles = quaternion.eulerAngles;
// Set point color
point.startColor = new Color(angles.x, angles.y, angles.z, 1.0f);
}
lastCameraRot = Camera.current.transform.rotation;
updateSystem = true;
}
if(!updateSystem) return;
updateSystem = false;
ps.SetParticles(particlePoints, particlePoints.Length);
}
答案 1 :(得分:0)
由于以前的回答,我设法使它起作用:
在PlacePrefabPoints方法中,我将每个实例化的预制件添加到列表中,并向滑块添加一个侦听器,如下所示:
void changedPointSize(){
pointScale = sizeSlider.value;
for (int i = 0; i < objects.Count; i++) {
objects[i].transform.localScale = new Vector3(pointScale, pointScale, pointScale);
}
}
谢谢!