我的问题是我想创建一个类字段的引用。 (这样我以后可以修改引用并将结果显示在实际的类字段中。)
public static Transform operator +(Transform transform, ManipulationInformation manipulationInformation)
{
// I would like to make this into a reference type.
Vector3 type;
switch (manipulationInformation.ManipulationType)
{
case "Scale":
type = transform.lossyScale;
break;
case "Rotate":
type = transform.rotation.eulerAngles;
break;
case "Move":
type = transform.position;
break;
}
switch (manipulationInformation.Direction)
{
case 'x':
type = new Vector3(
transform.position.x + manipulationInformation.NumericalSign * ModificationIncrement,
transform.position.y,
transform.position.z);
break;
case 'y':
type = new Vector3(
transform.position.x,
transform.position.y + manipulationInformation.NumericalSign * ModificationIncrement,
transform.position.z);
break;
case 'z':
type = new Vector3(
transform.position.x,
transform.position.y,
transform.position.z + manipulationInformation.NumericalSign * ModificationIncrement);
break;
}
return transform;
}
与上面的代码一样,'ManipulationInformation'包含三个与Unity的变换类(比例,位置和旋转)对应的Vector3字段。我希望能够添加和减去这些(因此这里的函数是重载operator +)。我想将'type'变成可以引用transform的Vector3之一的东西,以便我可以简化我的代码。 (一个肯定的但丑陋的选择是在'switch(manipulationInformation.ManipulationType)'语句的每个情况下放置一个'switch(manipulationInformation.Direction)'语句;但是,代码量随着更多case语句呈指数增长而不是很可读的。
我想知道是否有解决这种疯狂的方法。提前全部感谢!
编辑:我的意思是'type'是对transform的scale,rotation和position字段之一的引用。并使其对类型的修改也会修改transform的字段。但是,我现在明白这不是必要的,我的问题是由于其他原因。谢谢Kevin Gosse。
答案 0 :(得分:2)
我认为你过多地超载了+
。如果您不关心这一点,请继续阅读。
你应该做这样的事情:
Action<Transform, Vector3> action;
switch (manipulationInformation.ManipulationType)
{
case "Scale":
action = (t, v) => t.lossyScale = v;
break;
case "Rotate":
action = (t, v) => t.rotation.eulerAngles = v;
break;
case "Move":
action = (t, v) => t.position = v;
break;
}
switch (manipulationInformation.Direction)
{
case 'x':
action(transform, new Vector3(
transform.position.x + manipulationInformation.NumericalSign * ModificationIncrement,
transform.position.y,
transform.position.z));
break;
case 'y':
action(transform, new Vector3(
transform.position.x,
transform.position.y + manipulationInformation.NumericalSign * ModificationIncrement,
transform.position.z));
break;
case 'z':
action(transform, new Vector3(
transform.position.x,
transform.position.y,
transform.position.z + manipulationInformation.NumericalSign * ModificationIncrement));
break;
}
由于transform
不是值类型,因此可以传递它,因此您可以使用一些委托魔法来执行此操作。
答案 1 :(得分:1)
您的方法有两个不同的部分:实际计算和分配。您可以通过提取方法使代码更容易阅读/维护:
public static Transform operator +(Transform transform, ManipulationInformation manipulationInformation)
{
var type = ApplyManipulation(manipulationInformation, transform.position);
switch (manipulationInformation.ManipulationType)
{
case "Scale":
transform.lossyScale = type;
break;
case "Rotate":
transform.eulerAngles = type;
break;
case "Move":
transform.position = type;
break;
}
return transform;
}
private static Vector3 ApplyManipulation(ManipulationInformation manipulationInformation, Vector3 position)
{
var offset = manipulationInformation.NumericalSign * ModificationIncrement;
switch (manipulationInformation.Direction)
{
case 'x':
return new Vector3(
position.x + offset,
position.y,
position.z);
case 'y':
return new Vector3(
position.x,
position.y + offset,
position.z);
case 'z':
return new Vector3(
position.x,
position.y,
position.z + offset);
}
throw new InvalidOperationException("Unknown direction: " + manipulationInformation.Direction);
}
实际上,ApplyManipulation
方法应该直接在ManipulationInformation
类中声明。这是一种称为feature envy的代码气味。从那里,两种类型都可以单独发展,你的代码将成为:
public static Transform operator +(Transform transform, ManipulationInformation manipulationInformation)
{
var type = manipulationInformation.Apply(transform.position, ModificationIncrement);
switch (manipulationInformation.ManipulationType)
{
case "Scale":
transform.lossyScale = type;
break;
case "Rotate":
transform.eulerAngles = type;
break;
case "Move":
transform.position = type;
break;
}
return transform;
}
你可以通过引入知道如何在ManipulationInformation
(整个Transform
代码)上应用switch (manipulationInformation.ManipulationType)
的第三种类型来进一步减少耦合,但那时可能会有点过分