You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

SolidWorks API使用Transform2移动组件时多列表组件联动移动问题求助

SolidWorks API使用Transform2移动组件时多列表组件联动移动问题求助

各位SolidWorks API的大佬们好,我现在遇到一个头疼的问题:我尝试对一个Component2列表使用Transform2做爆炸位移,但当我操作其中一个列表里的组件时,另一个列表的组件居然也跟着一起动了!以下是我的代码片段,麻烦帮忙看看哪里出问题了?

private double[][] transform2ProssedPartAndGetCache(List<Component2> processedPart, double[] explosionDirection, IMathUtility mathUtility)
{
    int counter = 0;
    double[][] cacheTransform = new double[processedPart.Count][];

    foreach (Component2 component in processedPart)
    {
        cacheTransform[counter] = component.Transform2.ArrayData;
        double[] transformArray = component.Transform2.ArrayData;
        double explosionMagnitude = 0.085;
        transformArray[9] += explosionDirection[0] * explosionMagnitude;
        transformArray[10] += explosionDirection[1] * explosionMagnitude;
        transformArray[11] += explosionDirection[2] * explosionMagnitude;
        MathTransform newTransform = mathUtility.CreateTransform(transformArray);
        component.Transform2 = newTransform;
        counter++;
    }

    return cacheTransform;
}

问题根源分析

我之前也踩过类似的坑,核心原因其实是**Component2是引用类型**:如果你的两个列表指向的是同一个Component2实例集合,那你修改其中一个列表里组件的属性时,本质上是在修改这个实例本身的属性,另一个列表里的对应组件自然会跟着变——它们本来就是同一个对象啊!

另外你的代码还有个小隐患:cacheTransform[counter] = component.Transform2.ArrayData;这里直接存的是数组的引用,不是副本。后面你修改transformArray的时候,缓存里的数组也会被同步改掉,这肯定不是你想缓存原始变换数据的初衷对吧?

解决方案

  1. 如果需要组件独立操作:先复制组件实例
    要是你本来就想让两个列表的组件各自动各自的,那得先给每个组件创建副本,比如用Component2.Copy()方法,把副本放进另一个列表里。这样两个列表的组件就是完全独立的实例,改一个不会影响另一个。

  2. 缓存数组时一定要存副本
    要是只是想缓存原始的Transform数据,避免后续修改影响缓存,那得用Clone()创建数组副本:

    cacheTransform[counter] = (double[])component.Transform2.ArrayData.Clone();
    
  3. 修改Transform的稳妥姿势
    你代码里直接改了ArrayData返回的数组,虽然最后重新赋值了Transform2,但更稳妥的是先拿数组副本修改,再生成新的Transform:

    foreach (Component2 component in processedPart)
    {
        // 缓存原始数组副本
        cacheTransform[counter] = (double[])component.Transform2.ArrayData.Clone();
        // 拿副本出来修改,不碰原始数组
        double[] transformArray = (double[])component.Transform2.ArrayData.Clone();
        double explosionMagnitude = 0.085;
        transformArray[9] += explosionDirection[0] * explosionMagnitude;
        transformArray[10] += explosionDirection[1] * explosionMagnitude;
        transformArray[11] += explosionDirection[2] * explosionMagnitude;
        MathTransform newTransform = mathUtility.CreateTransform(transformArray);
        component.Transform2 = newTransform;
        counter++;
    }
    

这样改完之后,既能正确缓存原始数据,也能解决组件联动的问题啦!如果是因为两个列表共享实例导致的,记得还要处理组件的复制哦~

备注:内容来源于stack exchange,提问作者itay bielski

火山引擎 最新活动