Raycast (UE)

最終更新: 2024年9月5日

此页面包含有关Alpha版的描述。

概述

Raycasting是用于判定用户指定的Cubism网格是否与任意座标相交的功能。
可以获得单击/点击座标、场景中任意物体与指定网格之间的重叠检测。

如何处理组件

通过将CubismRaycastComponent添加到CubismModel Actor的子组件,可以使用Cubism SDK for Unreal Engine中的Raycast。

如果在.model3.json中设置了光线投射对象的图形网格ID,载入时CubismRaycastComponent会自动作为子组件追加到CubismModel Actor,所以用户端无需进行设置。

如何指定对象图形网格

如果在.model3.json中设置了光线投射对象的图形网格ID,载入时CubismRaycastComponent将作为子组件自动追加到CubismModel Actor中,但如果要手动追加Raycast对象参数,请从“详细信息”选项卡中选择CubismRaycast,打开底部显示列表中的“Live2D Cubism”→“Parameters”,在插入新索引时创建的索引列表的“Id”中手动添加参数名称。

参数的应用

CubismRaycastComponent针对Parameters的个元素进行单独的交集判断。 Id中设置的ID对应的图形网格属于交集判断对象。

void UCubismRaycastComponent::Raycast(
	const FVector Origin,
	const FVector Direction,
	TArray<FCubismRaycastHit>& Result,
	const float Length
) const
{
	Result.Empty();

	for (const FCubismRaycastParameter& Parameter : Parameters)
	{
		if (!Parameter.bEnabled)
		{
			continue;
		}

		UCubismDrawableComponent* Drawable = Model->GetDrawable(Parameter.Id);

		if (!Drawable)
		{
			continue;
		}

		const FTransform& Transform = Drawable->GetComponentTransform();
		FVector HitPosition, HitNormal;
		float HitTime;

		const FBox Box = Drawable->CalcBounds(Transform).GetBox();
		const FVector NormDir = Direction.GetSafeNormal();
		const FVector Start = Origin;
		const FVector End = Start + NormDir * Length;

		if (!FMath::LineExtentBoxIntersection(
			Box,
			Start, End, FVector::Zero(),
			HitPosition, HitNormal, HitTime
		))
		{
			continue;
		}

		switch (Parameter.Precision)
		{
			case ECubismRaycastPrecision::BoundingBox:
			{
				// already checked

				break;
			}
			case ECubismRaycastPrecision::Mesh:
			{
				const TArray<int32> Indices = Drawable->GetVertexIndices();

				TArray<FVector> Positions;
				for (const FVector2D& Position : Drawable->GetVertexPositions())
				{
					Positions.Add(Model->GetRelativeTransform().TransformPosition(Drawable->ToGlobalPosition(Position)));
				}

				if (!RayMeshIntersection(
					Start, End,
					Positions, Indices,
					HitPosition, HitTime
				))
				{
					continue;
				}

				break;
			}
		}


		FCubismRaycastHit RaycastHit;

		RaycastHit.Drawable = Drawable;
		RaycastHit.Distance = HitTime * Length;
		RaycastHit.GlobalPosition = HitPosition;
		RaycastHit.LocalPosition = Transform.InverseTransformPosition(HitPosition);

		Result.Add(RaycastHit);
	}
}

如果要追加或删除对象图形网格,请追加或删除组件的Parameters元素。

如果Enabled设置为true,则执行光线的交集判断。
交集判断的行为可以通过CubismRaycastParameter中提供的参数来控制。

  • Precision
    指定判断精度。
    如果选择BoundingBox,则会对图形网格周围的AABB,即沿轴的长方体进行交集判断。这减少了计算负荷,但交集判断精度将会降低。
    如果选择此选项,建议您将模型平面定向为与任一座标轴相同的方向,以优化AABB。
    如果选择Mesh,将在构成图形网格的网格上准确地执行交集判断。这提高了交集判断的精度,但增加了计算负荷。

执行光线投射

通过使用CubismRaycastComponent中提供的函数,可以进行与设置的交集判断物体之间的交集判断。

void Raycast(
	const FVector Origin,
	const FVector Direction,
	TArray<FCubismRaycastHit>& Result,
	const float Length = 10000.f
) const;
  • Origin
    指定代表尝试投射的光线原点的位置向量。
  • Direction
    指定尝试投射的光线的方向向量。
  • Result
    指定用于存储交集判断结果的数组。
  • Length
    指定尝试投射的光线长度。
请问这篇文章对您有帮助吗?
关于本报道,敬请提出您的意见及要求。