[task] | code [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | SideviewbodyComponent의 IsOnGround 결과와 InputDirection, IsCrouchKeyPressed 값을 조합하여 StateComponent의 ChangeState로 IDLE, MOVE, CROUCH, FALL 상태를 정확히 전환하는 UpdateAnimationState 메서드를 작성하는 스크립트를 작성해줘 [answer] | ```lua Property: [None] Vector2 InputDirection = Vector2(0, 0) [None] boolean IsCrouchKeyPressed = false Method: [client only] void UpdateAnimationState() { local body = self.Entity.SideviewbodyComponent local state = self.Entity.StateComponent if body:IsOnGround() then if [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 11. 캐릭터의 애니메이션을 제어하는 `UpdateAnimationState` 함수도 추가합니다. ```lua void UpdateAnimationState() { local body = self.Entity.SideviewbodyComponent local state = self.Entity.StateComponent if body:IsOnGround() then if self.InputDirection.x ~= 0 then
[task] | single_turn [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | PlayerControllerComponent를 비활성화하고 직접 이동 속도를 제어할 때, 왜 점프와 이동 애니메이션이 자동으로 작동하지 않는 건가요? [answer] | `PlayerControllerComponent`는 캐릭터의 물리 이동뿐만 아니라 점프 동작(`ActionJump`, `ActionDownJump`)과 이동 애니메이션을 자동으로 처리하는 핵심 컴포넌트입니다. SideViewRectTileMap에서 직접 이동 속도를 제어하기 위해 `PlayerControllerComponent`를 비활성화하면, 이 컴포넌트가 담당하던 자동 동작 및 애니메이션 트리거 로직이 함께 꺼지게 됩니다. 따라서 코드에서 `SideviewbodyComponent`의 `MoveVelocity`만 수정하여 좌우 [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 7. 유저의 키 입력이 없을 때는 감속하고 키 입력이 있을 때는 가속하도록 설정해봅시다. 아래와 같이 `UpdateVelocity` 함수와 `SignOf` 함수를 추가합니다. ```lua number SignOf(number value) { if value >= 0 then return 1 else return -1 end } void UpdateVelocity(number delta)
[task] | code [pass] | ⏳ 미판정 [title] | 충돌 그룹 만들기 [question] | 충돌 그룹 Player, Monster, Item 이 모두 생성된 상태에서, PlayerComponent 와 MonsterComponent 가 각각 HandleTriggerEnterEvent 를 구현하여 event.TriggerBodyEntity 의 CollisionGroup 을 비교해 자신이 속한 그룹과 충돌 허용 관계에 있는지 판별한 후 적격인 경우에만 ItemComponent 를 self.Entity:Destroy() 로 삭제하는 스크립트를 작성해줘 [answer] | 충돌 그룹(Player, Monster, Item)이 모두 생성되어 있고, 각 엔티티의 `TriggerComponent`에 해당 `CollisionGroup`이 이미 지정되어 있다고 가정합니다. `HandleTriggerEnterEvent`가 발생한 엔티티(`self.Entity`)의 `CollisionGroup`과, 들어온 대상(`event.TriggerBodyEntity`)의 `CollisionGroup`을 비교하여, **충돌 허용 관계가 성립할 때만** 코인(`Item` 그룹)을 삭제하는 로직을 구현해야 합니다. 참고 문서 [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 충돌 그룹 매트릭스(Matrix)는 충돌 그룹끼리의 충돌을 허용할지 말지를 결정할 때 사용합니다. 충돌 그룹을 생성하면 매트릭스에 자동으로 새로운 충돌 그룹이 생성됩니다. 충돌 그룹끼리의 충돌 허용 여부는 체크 박스를 선택해서 간단하게 설정할 수 있습니다. 매트릭스에 적힌 충돌 그룹끼리의 관계를 확인하고 충돌을 허용하고 싶다면 체크 박스를 활성화합니다. 1. **Panels - Collision Groups - Matrix**를 선택합니다. 2. 가로 세로의 그룹명을 확인한 뒤 충돌을 허용하면 체크 박스를 활성화합니다.
[task] | instruction_following [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | RevoluteJointComponent 설정 시 TargetEntityRef와 LocalAnchorB 값을 지정하는 과정을 단계별 번호 목록으로 작성하세요. [answer] | RevoluteJointComponent의 `TargetEntityRef`와 `LocalAnchorB` 값을 지정하는 과정은 다음과 같습니다. 1. 원형 모양 엔티티에 `RevoluteJointComponent`를 추가합니다. 2. 추가된 `RevoluteJointComponent`의 `TargetEntityRef` 프로퍼티에 연결할 대상 엔티티(예: LeftBar)를 지정합니다. 3. `RevoluteJointComponent`의 `LocalAnchorB` 프로퍼티 값을 설정합니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 1. 새로운 **LeftEntity, LeftBar** 오브젝트 엔티티를 만들고, **PhysicsRigidbodyComponent, PhysicsColliderComponent**를 추가합니다. * LeftEntity SpriteRUID: **e75cac80f719471fa482195531ed57cc** * LeftBar SpriteRUID: **0308ac89b10843fcab6384aa43f6ae22** 2. 원형 모양 엔티티에 **RevoluteJointComponent**를 추가하고, **Joint**에 **
[task] | two_turn [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | `UpdateAction` 함수를 통해 캐릭터의 점프와 엎드리기 동작을 제어할 때, `IsOnGround` 상태와 키 입력 조합에 따른 분기 로직은 어떻게 구성되나요? [answer] | `UpdateAction` 함수에서는 `PlayerControllerComponent`와 `SideviewbodyComponent`를 활용하여 캐릭터의 상태와 입력을 확인합니다. 이 함수는 `OnUpdate` 루프 내에서 호출되며, 아래 두 가지 동작을 제어합니다. 1. **엎드리기 (Crouch)** * **조건**: `IsCrouchKeyPressed`가 `true`이고, `body:IsOnGround()`가 `true`일 때. * **동작**: `controller:ActionCrouch()`를 호출하 [followup] | `IsJumpKeyPressed`와 `IsCrouchKeyPressed`가 동시에 눌렸을 때 `ActionDownJump`가 실행되는 조건을 확인하고, `SideviewbodyComponent`의 `MoveVelocity`를 직접 조작하는 방식과 `PlayerControllerComponent`의 액션 메서드를 함께 사용할 때 발생할 수 있는 충돌이나 주의사항은 무엇인가요? [followup_answer] | `IsJumpKeyPressed`와 `IsCrouchKeyPressed`가 동시에 눌렸을 때 `ActionDownJump`가 실행되는 조건은 다음과 같습니다. 1. `self.IsJumpKeyPressed`가 `true`이고 2. `self.Entity.SideviewbodyComponent:IsOnGround()`가 `true`인 상태여야 하며 3. 위 두 조건이 만족된 후, 내부 분기에서 `self.IsCrouchKeyPressed`가 `true`인 경우에만 `controller:ActionDownJump()`가 호출됩니 [scores] | [judge_reason] | [source_doc] | 7. 유저의 키 입력이 없을 때는 감속하고 키 입력이 있을 때는 가속하도록 설정해봅시다. 아래와 같이 `UpdateVelocity` 함수와 `SignOf` 함수를 추가합니다. ```lua number SignOf(number value) { if value >= 0 then return 1 else return -1 end } void UpdateVelocity(number delta)
[task] | instruction_following [pass] | ⏳ 미판정 [title] | 엔티티에 물리 적용하기 [question] | ApplyForce 계열과 SetVelocity 계열 함수의 질량 영향 관계에 대한 정보를 단계별 번호 목록으로 작성해줘. [answer] | ApplyForce 계열 함수와 SetVelocity 계열 함수의 질량 영향 관계는 다음과 같습니다. 1. **ApplyForce 계열 함수**: 해당 Entity에 대응하는 물리 강체의 질량 값에 영향을 받습니다. 2. **SetVelocity 계열 함수**: 질량 값과 관계없이 속도를 지정할 수 있습니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | # 학습 과정 소개 물리 법칙을 엔티티에 적용하고 물리 엔티티끼리 충돌할 수 있게 만들어 봅시다. 월드에 물리를 만드는 방법은 [물리 사용하기](/docs?postId=757%7B%22target%22:%22_self%22%7D)를 참고하세요. # PhysicsRigidbodyComponent Entity에 PhysicsRigidbodyComponent를 추가하면 Entity가 물리 엔진에 의해 제어됩니다. 또한 엔티티의 저항 계수, 마찰 계수, 질량 등 물리 연산에 영향을 주는 값을 설정할 수 있습니다. Entity가 Phy
[task] | instruction_following [pass] | ⏳ 미판정 [title] | 엔티티에 물리 적용하기 [question] | CollisionDetectionMode의 Discrete와 Continuous 차이점을 3문장 이내로 설명해줘. [answer] | Discrete는 충돌을 비연속적으로 확인하여 속도가 빠르거나 크기가 작은 물체가 충돌을 감지하지 못하고 통과할 수 있습니다. Continuous는 충돌을 연속적으로 확인하여 물체가 충돌하지 못하고 통과하는 상황을 방지합니다. Continuous 방식은 충돌을 막아주지만, 연산에 더 많은 자원이 필요합니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | # 학습 과정 소개 물리 법칙을 엔티티에 적용하고 물리 엔티티끼리 충돌할 수 있게 만들어 봅시다. 월드에 물리를 만드는 방법은 [물리 사용하기](/docs?postId=757%7B%22target%22:%22_self%22%7D)를 참고하세요. # PhysicsRigidbodyComponent Entity에 PhysicsRigidbodyComponent를 추가하면 Entity가 물리 엔진에 의해 제어됩니다. 또한 엔티티의 저항 계수, 마찰 계수, 질량 등 물리 연산에 영향을 주는 값을 설정할 수 있습니다. Entity가 Phy
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | TargetEntityRef와 LocalAnchor A, B의 위치 설정이 잘못된 경우 발생할 수 있는 일반적인 오류 현상은 무엇인가요? [answer] | 제공된 참고 문서에는 `TargetEntityRef`와 `LocalAnchor A, B`의 위치 설정이 잘못된 경우 구체적으로 발생할 수 있는 오류 현상(예: 물리 충돌 오류, 위치 이탈, 회전 이상 등)에 대한 설명이 포함되어 있지 않습니다. 문서에는 JointComponent를 추가할 때 **Size**에 생성할 Joint 개수를 입력하고, **TargetEntityRef**로 엔티티를 선택한 후 **LocalAnchor A, B**의 위치를 설정해야 한다는 절차만 안내하고 있을 뿐, 설정 오류에 따른 결과나 오류 메시지에 대 [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | WheelJoint는 연결된 엔티티가 바퀴처럼 동작하도록 제한을 설정합니다. Motor를 사용한 TargetEntityRef는 MotorSpeed 값을 목표 속도로 사용합니다. | 주요 프로퍼티 | 설명 | | --- | --- | | **MaxMotorTorque** | 목표 모터 속도에 도달하기 위한 Joint의 모터에 적용할 수 있는 최대 힘을 설정합니다. | | **MotorEnable** | Motor를 사용할지 여부를 설정합니다. True일 경우 연결된 Entity가 LocalAxis 방향의 힘을 받습니다. | | *
[task] | code [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | SignOf 함수를 구현하여 전달된 숫자 값이 0 이상일 경우 1, 그 외에는 -1 을 반환하도록 하는 유틸리티 메서드를 포함하는 스크립트를 작성해줘. [answer] | ```lua Method: number SignOf(number value) { if value >= 0 then return 1 else return -1 end } ``` [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 7. 유저의 키 입력이 없을 때는 감속하고 키 입력이 있을 때는 가속하도록 설정해봅시다. 아래와 같이 `UpdateVelocity` 함수와 `SignOf` 함수를 추가합니다. ```lua number SignOf(number value) { if value >= 0 then return 1 else return -1 end } void UpdateVelocity(number delta)
[task] | two_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | Joint의 LocalAnchor 위치가 ColliderOffset을 기준으로 설정된다는 설명이 이해가 안 됩니다. [answer] | Joint의 `LocalAnchor` 위치는 해당 엔티티의 `PhysicsColliderComponent`에 설정된 `ColliderOffset` 값을 원점(0,0)으로 삼아 상대적으로 정의됩니다. 즉, 실제 월드 좌표계에서의 Anchor 위치는 단순히 `LocalAnchor` 값 자체가 아니라, **엔티티의 현재 위치 + ColliderOffset + LocalAnchor**의 합으로 계산됩니다. 이를 통해 이해할 수 있는 핵심 포인트는 다음과 같습니다. 1. **기준점의 차이**: 두 엔티티(A, B)가 동일한 `Loca [followup] | Entity A와 Entity B의 ColliderOffset이 서로 다른 경우, 동일한 LocalAnchor 값(예: (3,0))을 설정해도 실제 연결 위치가 어떻게 달라지는지 예외 상황을 들어 설명해 주세요. [followup_answer] | Entity A와 Entity B의 `ColliderOffset`이 서로 다른 경우, 동일한 `LocalAnchor` 값을 설정하더라도 두 Anchor가 실제 월드 좌표계에서 차지하는 위치(즉, Joint가 물리적으로 연결하는 지점)는 `ColliderOffset`의 차이에 따라 달라집니다. `LocalAnchor`는 해당 엔티티의 `ColliderOffset`을 원점(0,0)으로 한 상대 좌표이므로, 실제 월드 좌표계에서의 Anchor 위치는 다음과 같이 계산됩니다. * **실제 Anchor 위치** = 엔티티의 현재 Tr [scores] | [judge_reason] | [source_doc] | # 학습 과정 소개 물리를 사용하는 맵에서 특정 엔티티끼리의 운동 방식을 설정하는 방법을 알아봅시다. 다양한 JointComponent를 활용해 다양한 운동을 하는 엔티티를 만들어 월드 제작에 활용할 수 있습니다. # Joint Joint란 물리 법칙을 적용한 맵에서 특정 엔티티끼리만 연결해 서로 영향을 주고받을 수 있게 만드는 특정 연결부를 의미합니다. 아래의 그림과 같이 Entity A와 Entity B가 서로 영향을 주고받을 수 있도록 하는 연결부가 바로 Joint입니다. 기준 엔티티인 Entity A에 Joint 연결
[task] | instruction_following [pass] | ⏳ 미판정 [title] | 엔티티에 물리 적용하기 [question] | PhysicsRigidbodyComponent의 BodyType 종류와 각 특징을 표로 정리해서 알려줘. [answer] | `PhysicsRigidbodyComponent`의 `BodyType` 프로퍼티는 엔티티가 물리 엔진에서 어떻게 동작하는지를 결정하며, 총 3가지 종류가 있습니다. 각 타입의 특징은 다음과 같습니다. | BodyType | 특징 | | :--- | :--- | | **Static** | 질량이 무한히 큰 엔티티로 취급됩니다. `Dynamic` 타입의 엔티티와 충돌할 수 있습니다. | | **Dynamic** | 엔티티가 물리 법칙에 따라 동작합니다. 물리 충돌이 가능한 다른 `Entity`와 충돌할 수 있습니다. | | **Kin [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | # 학습 과정 소개 물리 법칙을 엔티티에 적용하고 물리 엔티티끼리 충돌할 수 있게 만들어 봅시다. 월드에 물리를 만드는 방법은 [물리 사용하기](/docs?postId=757%7B%22target%22:%22_self%22%7D)를 참고하세요. # PhysicsRigidbodyComponent Entity에 PhysicsRigidbodyComponent를 추가하면 Entity가 물리 엔진에 의해 제어됩니다. 또한 엔티티의 저항 계수, 마찰 계수, 질량 등 물리 연산에 영향을 주는 값을 설정할 수 있습니다. Entity가 Phy
[task] | code [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | SideviewbodyComponent의 IsOnGround와 PlayerControllerComponent의 LookDirectionX를 이용해 이동 상태에 따라 StateComponent의 애니메이션을 변경하고 시선을 좌우로 전환하는 스크립트를 작성해줘 [answer] | SideviewbodyComponent의 `IsOnGround()`와 `PlayerControllerComponent`의 `LookDirectionX`를 활용하여 이동 상태에 따른 애니메이션 변경과 시선 제어를 수행하는 스크립트입니다. ```lua Property: [None] number InputDirection = 0 [None] boolean IsCrouchKeyPressed = false Method: [client only] void UpdateAnimationState() { local body = self. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 11. 캐릭터의 애니메이션을 제어하는 `UpdateAnimationState` 함수도 추가합니다. ```lua void UpdateAnimationState() { local body = self.Entity.SideviewbodyComponent local state = self.Entity.StateComponent if body:IsOnGround() then if self.InputDirection.x ~= 0 then
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | RevoluteJoint에서 LowerAngle과 UpperAngle은 엔티티의 Local Vector2(1, 0)를 기준으로 상대 각도가 측정되는 것인가요? [answer] | 네, 맞습니다. RevoluteJoint의 `LowerAngle`과 `UpperAngle`은 엔티티의 Local Vector2(1, 0)을 기준으로 상대 각도가 측정됩니다. 이 각도 제한을 적용하려면 `UseLimits` 프로퍼티를 활성화해야 합니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | RevoluteJoint는 엔티티의 회전과 관련된 제한을 설정합니다. UseLimits를 활성화한 후, LowerAngle, UpperAngle를 활용해 회전 각도를 제한할 수 있습니다. 엔티티가 회전할 때는 LocalAnchorA와 B가 만나는 지점을 공통의 Anchor로 사용합니다. 또한 Motor를 사용하면 Anchor를 기준으로 회전하는 힘을 받을 수 있습니다. | 주요 프로퍼티 | 설명 | | --- | --- | |**UseLimits** | 상대적 각도에 제한을 설정할지 여부를 결정합니다. | |**LowerAn
[task] | code [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | WeldJointComponent를 적용하여 엔티티 A와 엔티티 B가 완전히 고정되어 함께 움직이도록 연결하는 스크립트를 작성해줘 [answer] | WeldJointComponent는 두 엔티티를 완전히 고정하여 함께 움직이게 하는 Joint입니다. 제공된 문서의 예제 코드를 참고하여 엔티티 A와 엔티티 B를 연결하는 스크립트는 다음과 같이 작성할 수 있습니다. `AddJoint` 메서드를 사용하여 대상 엔티티(TargetEntityRef)와 각 Anchor 위치(LocalAnchor A, B)를 지정해야 합니다. ```lua Method: [server] void ConnectEntity(Entity targetEntity) { -- self.Entity: JointCo [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | # 학습 과정 소개 물리를 사용하는 맵에서 특정 엔티티끼리의 운동 방식을 설정하는 방법을 알아봅시다. 다양한 JointComponent를 활용해 다양한 운동을 하는 엔티티를 만들어 월드 제작에 활용할 수 있습니다. # Joint Joint란 물리 법칙을 적용한 맵에서 특정 엔티티끼리만 연결해 서로 영향을 주고받을 수 있게 만드는 특정 연결부를 의미합니다. 아래의 그림과 같이 Entity A와 Entity B가 서로 영향을 주고받을 수 있도록 하는 연결부가 바로 Joint입니다. 기준 엔티티인 Entity A에 Joint 연결
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | PulleyJoint에서 Ratio 값이 3일 때 한쪽 엔티티의 선 길이가 줄어드는 양과 다른 쪽 엔티티의 구속력 관계가 어떻게 되나요? [answer] | Ratio 값이 3일 때, 한쪽 엔티티(Entity A)의 선 길이가 3만큼 줄어든다면 다른 쪽 엔티티(Entity B)의 선 길이는 1만큼 늘어나게 됩니다. 이때 Entity A의 선은 Entity B의 선에 비해 구속력(constraint force)이 1/3이 됩니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | RevoluteJoint는 엔티티의 회전과 관련된 제한을 설정합니다. UseLimits를 활성화한 후, LowerAngle, UpperAngle를 활용해 회전 각도를 제한할 수 있습니다. 엔티티가 회전할 때는 LocalAnchorA와 B가 만나는 지점을 공통의 Anchor로 사용합니다. 또한 Motor를 사용하면 Anchor를 기준으로 회전하는 힘을 받을 수 있습니다. | 주요 프로퍼티 | 설명 | | --- | --- | |**UseLimits** | 상대적 각도에 제한을 설정할지 여부를 결정합니다. | |**LowerAn
[task] | two_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | WheelJoint의 MotorSpeed와 MaxMotorTorque가 어떻게 상호작용하며 바퀴의 구동 속도를 제어하는지 설명해 주세요 [answer] | WheelJoint는 연결된 엔티티가 바퀴처럼 회전하도록 동작을 제한하며, `Motor` 기능을 통해 목표 속도에 도달하도록 힘을 가합니다. `MotorSpeed`와 `MaxMotorTorque`는 다음과 같이 상호작용하여 바퀴의 구동 속도를 제어합니다. 1. **MotorSpeed (목표 속도)** * Joint가 도달해야 할 목표 모터 속도(각속도)를 정의합니다. * 이 값은 `MotorEnable`이 `True`일 때만 유효합니다. * 바퀴가 이 속도로 회전하도록 시스템이 힘을 가하는 기준점 [followup] | MotorEnable이 True인데도 바퀴가 돌지 않을 때, TargetEntityRef의 LocalAxis 방향 설정이나 물리 엔티티의 BodyType 상태 중 어떤 부분을 먼저 확인해야 하는지 알려주세요. [followup_answer] | `MotorEnable`이 `True`로 설정되어 있음에도 바퀴가 회전하지 않는다면, 다음 두 가지 사항을 우선적으로 확인해야 합니다. **1. 물리 엔티티의 `BodyType` 상태 확인 (우선순위 1)** Joint가 물리적으로 동작하려면 연결된 엔티티 중 적어도 하나 이상이 물리 시뮬레이션에 영향을 받도록 설정되어 있어야 합니다. * **확인 포인트:** `TargetEntityRef`로 연결된 바퀴 엔티티와 차체(또는 고정된 엔티티)의 `PhysicsRigidbodyComponent`에서 **`BodyType`** 설정 [scores] | [judge_reason] | [source_doc] | WheelJoint는 연결된 엔티티가 바퀴처럼 동작하도록 제한을 설정합니다. Motor를 사용한 TargetEntityRef는 MotorSpeed 값을 목표 속도로 사용합니다. | 주요 프로퍼티 | 설명 | | --- | --- | | **MaxMotorTorque** | 목표 모터 속도에 도달하기 위한 Joint의 모터에 적용할 수 있는 최대 힘을 설정합니다. | | **MotorEnable** | Motor를 사용할지 여부를 설정합니다. True일 경우 연결된 Entity가 LocalAxis 방향의 힘을 받습니다. | | *
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | WeldJointComponent와 DistanceJointComponent 중 고정된 연결과 거리 유지 중 어떤 상황에서 각각을 사용해야 하는지 차이점을 알려주세요. [answer] | WeldJointComponent와 DistanceJointComponent는 두 엔티티 간의 연결 방식에서 명확한 차이가 있으며, 제작 의도에 따라 다음과 같이 구분하여 사용해야 합니다. **1. WeldJointComponent (용접 연결)** * **특징**: 두 엔티티를 **고정된 상태**로 연결합니다. * **사용 상황**: * 엔티티끼리 떨어지지 않고 하나의 단단한 구조처럼 붙어 있어야 할 때. * 예시: 특정 물체가 다른 물체에 달라붙거나, 고정된 지점에 물체를 매달아 두는 경우. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | # 학습 과정 소개 물리를 사용하는 맵에서 특정 엔티티끼리의 운동 방식을 설정하는 방법을 알아봅시다. 다양한 JointComponent를 활용해 다양한 운동을 하는 엔티티를 만들어 월드 제작에 활용할 수 있습니다. # Joint Joint란 물리 법칙을 적용한 맵에서 특정 엔티티끼리만 연결해 서로 영향을 주고받을 수 있게 만드는 특정 연결부를 의미합니다. 아래의 그림과 같이 Entity A와 Entity B가 서로 영향을 주고받을 수 있도록 하는 연결부가 바로 Joint입니다. 기준 엔티티인 Entity A에 Joint 연결
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | RevoluteJoint의 UseLimits를 활성화하지 않으면 LowerAngle과 UpperAngle 값이 어떻게 적용되나요? [answer] | 참고 문서에 따르면, `UseLimits`는 상대적 각도에 제한을 설정할지 여부를 결정하는 프로퍼티입니다. 따라서 `UseLimits`를 활성화하지 않으면(거짓값인 경우), `LowerAngle`과 `UpperAngle` 값은 적용되지 않으며 회전 각도 제한이 설정되지 않습니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | RevoluteJoint는 엔티티의 회전과 관련된 제한을 설정합니다. UseLimits를 활성화한 후, LowerAngle, UpperAngle를 활용해 회전 각도를 제한할 수 있습니다. 엔티티가 회전할 때는 LocalAnchorA와 B가 만나는 지점을 공통의 Anchor로 사용합니다. 또한 Motor를 사용하면 Anchor를 기준으로 회전하는 힘을 받을 수 있습니다. | 주요 프로퍼티 | 설명 | | --- | --- | |**UseLimits** | 상대적 각도에 제한을 설정할지 여부를 결정합니다. | |**LowerAn
[task] | instruction_following [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | Swing 스크립트 컴포넌트의 HandleKeyDownEvent와 HandleKeyReleaseEvent 구현 로직만 출력하고 설명은 주석으로 작성하세요. [answer] | ```lua Event Handler: [service: InputService] HandleKeyDownEvent(KeyDownEvent event) { -- Parameters local key = event.key -------------------------------------------------------- -- N 키가 눌리면 왼쪽 막대(Left)의 RevoluteJoint 모터를 활성화합니다. if key == KeyboardKey.N then self:MoveLeft(true) -- M 키가 눌리면 [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 1. 새로운 **LeftEntity, LeftBar** 오브젝트 엔티티를 만들고, **PhysicsRigidbodyComponent, PhysicsColliderComponent**를 추가합니다. * LeftEntity SpriteRUID: **e75cac80f719471fa482195531ed57cc** * LeftBar SpriteRUID: **0308ac89b10843fcab6384aa43f6ae22** 2. 원형 모양 엔티티에 **RevoluteJointComponent**를 추가하고, **Joint**에 **
[task] | code [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | PlayerControllerComponent 와 SideviewbodyComponent 를 활용하여 IsCrouchKeyPressed 와 IsJumpKeyPressed 상태를 확인하고, 지면에 있을 때 ActionCrouch, ActionDownJump, ActionJump 메서드를 호출하여 캐릭터의 엎드리기 및 점프 동작을 제어하는 UpdateAction 함수를 구현하는 스크립트를 작성해줘. [answer] | 참고 문서에 제시된 내용을 기반으로, 지면에 있을 때 엎드리기 및 점프 동작을 제어하는 `UpdateAction` 함수를 포함한 스크립트를 작성합니다. ```lua Method: void UpdateAction() { local controller = self.Entity.PlayerControllerComponent local body = self.Entity.SideviewbodyComponent -- 엎드리기 if self.IsCrouchKeyPressed and body:IsOnGround() [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 7. 유저의 키 입력이 없을 때는 감속하고 키 입력이 있을 때는 가속하도록 설정해봅시다. 아래와 같이 `UpdateVelocity` 함수와 `SignOf` 함수를 추가합니다. ```lua number SignOf(number value) { if value >= 0 then return 1 else return -1 end } void UpdateVelocity(number delta)
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | PrismaticJoint의 MotorSpeed가 설정되어도 엔티티가 움직이지 않는다면 어떤 설정을 먼저 확인해야 하나요? [answer] | PrismaticJoint의 `MotorSpeed`가 설정되어 있더라도 엔티티가 움직이지 않는다면, 가장 먼저 **`MotorEnable`** 프로퍼티가 `True`로 설정되어 있는지 확인해야 합니다. 문서에 따르면 `MotorSpeed`는 **`MotorEnable`이 `True`여야만 동작**합니다. `MotorEnable`이 `False` 상태라면 `MotorSpeed` 값이 얼마로 설정되어 있든 Motor 기능은 비활성화되어 엔티티에 힘이 가해지지 않습니다. 따라서 확인 순서는 다음과 같습니다: 1. `MotorEnab [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | RevoluteJoint는 엔티티의 회전과 관련된 제한을 설정합니다. UseLimits를 활성화한 후, LowerAngle, UpperAngle를 활용해 회전 각도를 제한할 수 있습니다. 엔티티가 회전할 때는 LocalAnchorA와 B가 만나는 지점을 공통의 Anchor로 사용합니다. 또한 Motor를 사용하면 Anchor를 기준으로 회전하는 힘을 받을 수 있습니다. | 주요 프로퍼티 | 설명 | | --- | --- | |**UseLimits** | 상대적 각도에 제한을 설정할지 여부를 결정합니다. | |**LowerAn
[task] | two_turn [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | SideViewRectTileMap에서 캐릭터의 가속과 감속 로직을 구현하기 위해 `UpdateVelocity` 함수를 추가할 때, `SignOf` 함수의 역할은 무엇이며 `OnUpdate`에서 어떻게 호출해야 하나요? [answer] | SideViewRectTileMap에서 캐릭터의 가속과 감속 로직을 구현할 때 `SignOf` 함수와 `OnUpdate` 호출 방식은 다음과 같습니다. **1. `SignOf` 함수의 역할** `SignOf` 함수는 전달된 수치의 부호를 판단하여 방향성(1 또는 -1)을 반환하는 역할을 합니다. * 전달된 값이 0 이상이면 `1`을 반환합니다. * 전달된 값이 0 미만이면 `-1`을 반환합니다. 이 함수는 `UpdateVelocity` 내에서 현재 속도의 방향(`vel.x`)을 파악하여, 감속할 때 속도가 0을 지나 반대 [followup] | `UpdateVelocity` 코드에서 `math.min(vel.x * sign, self.MaxSpeed) * sign` 문장의 정확한 의미와, `PlayerControllerComponent`가 비활성화된 상태에서 이 로직만 적용했을 때 발생하는 점프·애니메이션 관련 문제는 무엇인가요? [followup_answer] | `UpdateVelocity` 코드에서 해당 문장의 의미와 `PlayerControllerComponent` 비활성화 시 발생하는 문제는 다음과 같습니다. **1. `math.min(vel.x * sign, self.MaxSpeed) * sign` 문장의 의미** 이 문장은 캐릭터의 속도가 최대 속도(`self.MaxSpeed`)를 넘지 않도록 제한하고, 원래의 방향(부호)을 유지하는 역할을 합니다. * `vel.x * sign`: 현재 속도(`vel.x`)와 방향(`sign`)을 곱하여 방향을 제거한 상태의 절대값(크기)을 [scores] | [judge_reason] | [source_doc] | 7. 유저의 키 입력이 없을 때는 감속하고 키 입력이 있을 때는 가속하도록 설정해봅시다. 아래와 같이 `UpdateVelocity` 함수와 `SignOf` 함수를 추가합니다. ```lua number SignOf(number value) { if value >= 0 then return 1 else return -1 end } void UpdateVelocity(number delta)
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | WheelJoint의 MotorSpeed와 MaxMotorTorque가 각각 어떤 역할을 하는지 차이가 궁금합니다. [answer] | WheelJoint에서 `MotorSpeed`와 `MaxMotorTorque`는 바퀴의 회전 동작을 제어하는 서로 다른 역할을 수행합니다. **MotorSpeed (목표 모터 속도)** * **역할:** Joint가 도달해야 할 **목표 회전 속도**를 정의합니다. * **동작 방식:** `MotorEnable`이 `True`로 설정되어 있을 때만 동작하며, 연결된 엔티티가 이 속도에 도달하도록 힘을 가합니다. 단순히 속도를 지정하는 것일 뿐, 도달하기 위해 얼마나 큰 힘을 쓸지는 이 값만으로는 결정되지 않습니다. **M [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | WheelJoint는 연결된 엔티티가 바퀴처럼 동작하도록 제한을 설정합니다. Motor를 사용한 TargetEntityRef는 MotorSpeed 값을 목표 속도로 사용합니다. | 주요 프로퍼티 | 설명 | | --- | --- | | **MaxMotorTorque** | 목표 모터 속도에 도달하기 위한 Joint의 모터에 적용할 수 있는 최대 힘을 설정합니다. | | **MotorEnable** | Motor를 사용할지 여부를 설정합니다. True일 경우 연결된 Entity가 LocalAxis 방향의 힘을 받습니다. | | *
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | RevoluteJoint 예제에서 PhysicsRigidbodyComponent의 BodyType을 Dynamic으로 설정해야 하는 이유와 Static과의 차이는 무엇인가요? [answer] | RevoluteJoint 예제에서 `PhysicsRigidbodyComponent`의 `BodyType`을 `Dynamic`으로 설정해야 하는 이유는, 이 물리 엔티티가 외부 힘(예: 중력, 충돌, 모터 힘 등)의 영향을 받아 실제 물리 시뮬레이션에 따라 이동하고 회전할 수 있어야 하기 때문입니다. `Dynamic`과 `Static`의 주요 차이는 다음과 같습니다: 1. **Dynamic (동적)**: * 중력, 충돌, 임펄스(`ApplyLinearImpulse`) 등 물리 엔진의 계산에 의해 위치와 속도가 변경됩니 [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | WheelJoint는 연결된 엔티티가 바퀴처럼 동작하도록 제한을 설정합니다. Motor를 사용한 TargetEntityRef는 MotorSpeed 값을 목표 속도로 사용합니다. | 주요 프로퍼티 | 설명 | | --- | --- | | **MaxMotorTorque** | 목표 모터 속도에 도달하기 위한 Joint의 모터에 적용할 수 있는 최대 힘을 설정합니다. | | **MotorEnable** | Motor를 사용할지 여부를 설정합니다. True일 경우 연결된 Entity가 LocalAxis 방향의 힘을 받습니다. | | *
[task] | two_turn [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | 얼음 타일에서 마찰력을 줄여 미끄러움을 구현할 때, `IceTileChecker` 컴포넌트에서 `DefaultDrag`와 `IceDrag` 프로퍼티를 어떻게 설정하고 초기화해야 하는지 알려주세요. [answer] | `IceTileChecker` 컴포넌트에서 `DefaultDrag`와 `IceDrag` 프로퍼티는 아래 방법으로 설정하고 초기화합니다. 1. **프로퍼티 선언**: * `IceDrag`: 얼음 타일에서 적용할 마찰력(드래그) 값으로, 기본값은 `2`로 설정합니다. * `DefaultDrag`: 일반 타일에서 적용할 마찰력(드래그) 값을 저장할 변수로, 초기값은 `0`으로 설정합니다. ```lua Property: [None] number IceDrag = 2 [None] [followup] | 만약 얼음 타일 외에 다른 특수 타일(예: 점프 패드)도 처리하려면 `OnUpdate` 함수의 if-else 구조를 어떻게 확장하는지 코드 예시를 보여주세요. [followup_answer] | 참고 문서에는 얼음 타일(`Name == "Ice"`) 처리에 대한 내용만 포함되어 있으며, 점프 패드와 같은 다른 특수 타일의 이름이나 처리 로직에 대한 정보는 없습니다. 따라서 문서에 근거하여 점프 패드 처리를 위한 구체적인 코드나 API를 제시할 수 없습니다. 다만, 문서에 나와 있는 얼음 타일 처리 구조를 기반으로 `if` 조건을 추가하는 일반적인 Lua 문법적 확장 방식만 보여드릴 수 있습니다. (점프 패드 타일 이름과 동작은 문서에 없으므로 실제 프로젝트에서 정의한 값으로 대체해야 합니다) ```lua Method: [scores] | [judge_reason] | [source_doc] | ## 더 미끄러운 타일 만들기 `GetUnderfootTile` 함수를 사용하면 캐릭터가 현재 밟고 있는 타일이 무엇인지 알 수 있습니다. 이를 이용해서 얼음 타일을 밟으면 마찰력이 감소해 더 많이 미끄러지는 기능을 만들어 보겠습니다. 1. MyDesk 아래에 새 스크립트 컴포넌트 IceTileChecker를 만든 뒤, DefaultPlayer에 추가합니다. 2. IceTileChecker를 연 뒤, 아래와 같이 프로퍼티를 추가합니다. ```lua Property : [None] numbe
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | SetMotorEnable 메서드의 첫 번째 인자 1은 무엇을 나타내며, 다른 값으로 설정하면 어떻게 되나요? [answer] | 제시된 참고 문서에는 `SetMotorEnable` 메서드 호출 시 첫 번째 인자로 `1`이 사용된 예시는 있으나, 이 인자의 구체적인 의미(예: 모터 인덱스 등)나 다른 값으로 설정했을 때의 동작에 대한 설명은 포함되어 있지 않습니다. 따라서 해당 인자의 정확한 의미와 다른 값에 따른 동작은 제공된 문서만으로 알 수 없습니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 1. 새로운 **LeftEntity, LeftBar** 오브젝트 엔티티를 만들고, **PhysicsRigidbodyComponent, PhysicsColliderComponent**를 추가합니다. * LeftEntity SpriteRUID: **e75cac80f719471fa482195531ed57cc** * LeftBar SpriteRUID: **0308ac89b10843fcab6384aa43f6ae22** 2. 원형 모양 엔티티에 **RevoluteJointComponent**를 추가하고, **Joint**에 **
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | 스크립트에서 Left와 Right 엔티티 경로를 하드코딩으로 지정했는데, 엔티티 이름이 바뀌면 에러가 나는 것을 방지하는 더 나은 접근 방식이 있나요? [answer] | 제공된 참고 문서에는 엔티티 경로를 하드코딩(`/maps/map01/LeftEntity`)하는 방법 외에 다른 접근 방식(예: 경로 변경 시 자동 업데이트, 동적 경로 조회, 또는 다른 레퍼런싱 기법)에 대한 설명이 포함되어 있지 않습니다. 따라서 주어진 문서의 범위 내에서 엔티티 이름 변경 시 에러를 방지하는 "더 나은 접근 방식"에 대해 답변할 수 있는 정보가 없습니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 1. 새로운 **LeftEntity, LeftBar** 오브젝트 엔티티를 만들고, **PhysicsRigidbodyComponent, PhysicsColliderComponent**를 추가합니다. * LeftEntity SpriteRUID: **e75cac80f719471fa482195531ed57cc** * LeftBar SpriteRUID: **0308ac89b10843fcab6384aa43f6ae22** 2. 원형 모양 엔티티에 **RevoluteJointComponent**를 추가하고, **Joint**에 **
[task] | instruction_following [pass] | ⏳ 미판정 [title] | 엔티티에 물리 적용하기 [question] | `ApplyForce()`와 `ApplyLinearImpulse()` 함수의 차이점을 질량 값 영향 여부 기준으로 3문장 이내로 설명하세요. [answer] | `ApplyForce()`와 `ApplyLinearImpulse()`는 모두 해당 Entity의 물리 강체 질량 값에 영향을 받습니다. `ApplyForce()`는 특정 방향에 지속적으로 힘을 가하는 데 사용되며, `ApplyLinearImpulse()`는 대포 발사나 방망이 휘두르기처럼 일시적인 짧은 충격을 가할 때 사용합니다. [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | #### 힘을 가하는 함수 `ApplyForce()`, `ApplyTorque()` 함수는 지속적인 힘을 가할 수 있습니다. 특정 Key를 눌러 지속적으로 특정 방향으로 힘 가하고 싶을 때가 해당됩니다. 매개 변수 force는 힘을 의미합니다. 해당 Entity에 대응하는 물리 강체의 질량 값에 영향을 받습니다. #### 충격량을 적용하는 함수 `ApplyAngularImpulse()`, `ApplyLinearImpulse()` 함수는 일시적으로 짧은 충격을 가할 수 있습니다. 대포 발파, 방망이 휘두르기 같은 짧은 충격을 주
[task] | single_turn [pass] | ⏳ 미판정 [title] | 다양한 물리 joint 활용하기 [question] | UseLimits와 LowerAngle, UpperAngle 값을 설정할 때 각도 범위를 잘못 지정하면 막대가 어떻게 움직이게 되나요? [answer] | 제공된 문서에는 `UseLimits`, `LowerAngle`, `UpperAngle` 값을 설정할 때 각도 범위를 잘못 지정했을 때 막대가 어떻게 움직이는지에 대한 설명이 포함되어 있지 않습니다. 문서에는 `RevoluteJointComponent`에 `Joint` 값 1을 입력하고 `TargetEntityRef`에 LeftBar를 지정하며, `LocalAnchorB`, `LowerAngle`, `UpperAngle`, `MotorSpeed`, `UseLimits` 값을 지정하라고 안내만 하고 있을 뿐, 잘못된 각도 범위로 인한 [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 1. 새로운 **LeftEntity, LeftBar** 오브젝트 엔티티를 만들고, **PhysicsRigidbodyComponent, PhysicsColliderComponent**를 추가합니다. * LeftEntity SpriteRUID: **e75cac80f719471fa482195531ed57cc** * LeftBar SpriteRUID: **0308ac89b10843fcab6384aa43f6ae22** 2. 원형 모양 엔티티에 **RevoluteJointComponent**를 추가하고, **Joint**에 **
[task] | code [pass] | ⏳ 미판정 [title] | SideViewRectTileMap에서 캐릭터 이동 제어 [question] | SideviewbodyComponent의 EnableDownJump를 활성화하고 DownJumpSpeed를 3.3으로 설정하며, 입력 방향에 따라 StateComponent의 상태와 PlayerControllerComponent의 LookDirectionX를 갱신하는 OnUpdate 로직을 구현하는 스크립트를 작성해줘 [answer] | SideviewbodyComponent의 `EnableDownJump`와 `DownJumpSpeed`는 스크립트 코드로 설정하는 것이 아니라, 에디터의 **Workspace - DefaultPlayer - Property - SideviewbodyComponent** 창에서 직접 체크하고 값을 입력해야 합니다. 스크립트는 입력 방향에 따라 StateComponent의 상태와 PlayerControllerComponent의 LookDirectionX를 갱신하는 로직만 담당합니다. 요청하신 OnUpdate 로직을 포함하는 스크립트는 [followup] | [followup_answer] | [scores] | [judge_reason] | [source_doc] | 11. 캐릭터의 애니메이션을 제어하는 `UpdateAnimationState` 함수도 추가합니다. ```lua void UpdateAnimationState() { local body = self.Entity.SideviewbodyComponent local state = self.Entity.StateComponent if body:IsOnGround() then if self.InputDirection.x ~= 0 then