2017-11-17 4 views
1

어젯밤에 나는 GameObjects가 서로 충돌하는 것을 코딩하려고하는 C-Sharp 프로젝트를 진행하고있었습니다. 서로 다른 무기 (예 : 클럽, 검, 도끼)로 분류 할 수있는 다양한 게이트 유형 (예 : 목재, 돌, 금속)을 원했습니다.Unity - enum 속성을 사용하여 충돌하는 객체를 감지합니다.

GateManager에서 충돌을 감지하기 위해 각 게이트에 태그를 사용하고있었습니다. 따라서 예 :

void OnTriggerEnter(Collider collider) { 
     switch (gameObject.tag) { 
     case "WoodenGate": 
      ... 
     case "StoneGate": 
      ... 

위의 코드는 정확하지 않지만 아이디어를 제공해야합니다. 각 게이트 유형을 다른 태그로 설정하는 것은 잘못되었습니다 (모든 게이트 유형마다 다른 태그가 있고 모든 재료 유형에 다른 태그가있는 경우 수백 개의 태그로 끝납니다).

그래서 나는 대안을 생각해 냈습니다. GateType 열거 형을 설정하고 3 개의 값 (WoodenGate, StoneGate, MetalGate)을 생성했습니다. 그런 다음 공용 GateType 속성을 GateManager 클래스에 연결했습니다. 이 덕분에 'Inspector'창안의 각 조립식과 관련있는 열거 형을 선택할 수있었습니다. 그것은 매우 산뜻했고 나는 정말로 행복했습니다.

다음 문제가 발생했습니다. 네 번째 열거 형을 목록의 중간에 추가했습니다 (예 : GlassGate). 열거 형은 단순히 int 값이므로 세 번째 항목은 더 이상 MetalGate가 아니지만 지금은 StoneGate입니다. 이것은 금속 게이트 프리 패브가 갑자기 GateType이 스톤 게이트를 가짐을 의미했습니다. 내 게임을 어 겼어.

사소한 질문에 대해서는 사과하겠습니다. 그러나 제 질문은 어떻게하면 다른 종류의 많은 상품에 라벨을 붙이고 식별해야합니까? 태그를 사용하고 싶지 않기 때문에 (너무 많이 필요하기 때문에) 화일을 사용하고 싶지 않습니다 (단결 속성 관리자와 결합하여 사용할 때 취성 문제가 발생하기 때문에).

많은 게임에 대한 공통 요구 사항 (예 : 게임에서 서로 다른 게임 개체를 많이 사용하여 서로 다른 리소스를 수집 할 수 있음) 그냥 모범 사례가 궁금합니다.

+0

각 게이트 유형과 관련하여 어떤 종류의 상호 작용을하려고합니까? ? GateManager 스크립트에 모든 로직을 사용하는 대신 반응을 지시하는 MonoBehaviour 클래스 세트를 작성하여 각 게이트에 필요에 따라 첨부하고 게이트와의 충돌시 맹목적으로 호출 할 수 있습니까? (그냥 똑같은 클래스에서 상속 받거나 쉽게 같은 인터페이스를 구현하여 호출하고 불러올 수 있습니다.) – Serlite

+0

논리는 단순히 게이트와 충돌하는 무기가 충분히 높은 레벨 인 경우 로직을 적용한 다음 게이트를 비활성으로 설정합니다 그것을 파괴하십시오). 그래서 예. 칼은 나무 문을 파괴 할 수는 있지만 금속 문은 파괴 할 수 없습니다. 그래서 매우 간단한 논리가 실제로 여러 클래스를 갖는 것은 아마도 과잉 일 것입니다. –

+2

그럴 경우 왜 각 물체 (또는 물체가 구성되는 물체)에 강도 값을 할당하고 각 무기에 해당하는 강도를 지정하는 것이 좋을까요? 그런 다음 충돌시 두 값을 비교합니다. 모든 종류의 게이트에 대한 열거 형을 작성해야한다면 모든 종류의 바리케이드/가구 항목/블록/etc ...이 프로젝트의 성장에 따라 점점 더 많은 가치를 잃을 것입니다. – Serlite

답변

1

숫자를 사용하는 것이 가장 편리한 방법입니다. enum 값을 수동으로 증가 시키십시오.

public GateType gateType; 

public enum GateType 
{ 
    Wood = 0, 
    Stone = 1, 
    Brick = 2 
} 

이제 '목록'중간에 다른 것을 추가하고 싶습니다. 이 :

public GateType gateType; 

public enum GateType 
{ 
    Wood = 0, 
    Metall = 3, 
    Stone = 1, 
    Brick = 2 
} 

색인을 추가했기 때문에 Unity는 개체에 올바른 값을 유지해야합니다.

3

우선은 선언하고이를 위해 많은 인터페이스를 사용하지만, 단점은 당신이 그들 중 많은 선언하고 각 개체에 연결된 스크립트의 많은 그들을 구현해야한다는 것입니다 수 1:

public interface IDestroyable { } 

public interface IOpenable { } 

는 당신은 당신의 스크립트를 ITIN에서 상속 :

: 그것은 충돌시 하나

public class MyScript : MonoBehaviour, IDestroyable{} 

public class MyOtherScript : MonoBehaviour, IOpenable{} 

확인


2 우선은 또한 당신이 언급 열거를 사용할 수 있습니다.

public enum GateType 
{ 
    WoodenGate, 
    StoneGate, 
    MetalGate 
} 

는 그것이 하나 편집기 나 스크립트

public class GateDescription : MonoBehaviour 
{ 
    public GateType gateType; 
} 

확인 각 하나에 대한 열거 선택이 개체는 모든 게이트 객체 조립식이다 게이트의 유형을 설명하는 하나의 스크립트를 첨부 충돌시 :

void OnTriggerEnter(Collider collider) 
{ 
    GateDescription gateType = collider.GetComponent<GateDescription>(); 

    if (gateType != null) 
    { 
     switch (gateType.gateType) 
     { 
      case GateType.StoneGate: 
       break; 

      case GateType.WoodenGate: 
       break; 

      case GateType.MetalGate: 
       break; 
     } 
    } 
} 
+1

나는 인터페이스가 갈 길이라고 생각한다. –

+0

@AdamB 인터페이스 사용의 단점은 다른 인터페이스를 상속받은 각 게이트에 대해 많은 스크립트를 만들어야한다는 것입니다. 그 외에는 괜찮을거야. – Programmer

+0

네,하지만 장기적으로 볼 때 코드가 훨씬 더 읽기 쉽다고 생각합니다. 설정에 더 많은 시간이 걸리지 만 결국에는 무한히 이해할 수 있고 사용할 수 있습니다. –

0

spawn/init 이벤트에 따라 설정할 수 있습니다. enum 메서드를 사용하려는 경우에는 개체가 생성 될 때 정의 할 수 있습니다. 이것은 분명히 게임 메카닉에 달려 있습니다. 그러나 나는 아마 당신이 원하는 물질적 인 행동을 위해 특별히 monobehaviour에 이것을 아웃소싱 할 것입니다. 그런 식으로 나무 아치가 어떻게 행동 하는지를 바꾸고 싶다면 단지 하나의 스크립트 만 업데이트하면됩니다. 이 코드베이스가 커짐에 따라 도움이 될 것이며 2017.3의 기능을 사용하여 어떤 파일을 어떤 어셈블리에 넣을 지 정의 할 수 있다면 컴파일과로드 시간이 향상됩니다

관련 문제