게임에서 스마트 스크립팅을 어떻게 구현할 수 있습니까?


18

게임 엔진을 개발 중입니다. 엔티티 / 컴포넌트 기반의 것으로 가정합니다. 게임 자체를 개발하기 위해 실제로 엔터티를 만드는 데 스크립팅 언어를 사용하려고 생각했습니다.

예를 들어, 플레이어에게 공격적인 몬스터를 추가하려면 여러 구성 요소가있는 엔티티가됩니다. 이러한 구성 요소는 몬스터 유형에 따라 변경되므로 게임에 100 가지 유형의 몬스터가있는 경우 내 게임 코드에서 직접 각기 다른 방법을 만들 필요가 없습니다.

구성 요소 측면에서이 엔티티를 설명하기 위해 스크립팅 언어를 사용해야합니까, 아니면 더 잘 작동하는 다른 것이 있습니까? 보다 일반적으로 게임에서 스크립팅을 어떻게 사용해야합니까?


엔터티 설명의 경우 스크립팅없이 xml 또는 이와 유사한 것을 사용할 수 있습니다. 스크립팅에는 C #을 사용하지만 엔진이 .NET에있는 경우에만 사용할 수 있습니다.
— Kikaimaru

@Kikaimaru C #은 스크립팅 언어가 아닙니다. 루아를 사용하는 것이 더 좋은 아이디어이거나 엔진에 내장 될 수있는 다른 언어 일 것입니다.
— JDSweetBeat

@DJMethaneMan "C #은 스크립팅 언어가 아닙니다"는 아무 의미가 없습니다. C #으로 작성된 게임에서 C #으로 스크립트를 작성하고 컴파일을 위해 Roselyn과 같은 것을 사용하는 데 전혀 문제가 없습니다 ... 그러나 4 년 후에는 json a를 사용합니다. xml 및 C # 대신 javascript :)
— Kikaimaru

답변:


17

내 게임은 엔터티 구성 요소 프레임 워크를 사용하고 스크립트를 사용하여 엔터티를 정의합니다 (이것은 동작을 직접 정의하지는 않지만 마지막에 자세히 설명하겠습니다). 스크립트는 각 엔티티를 작성하는 데 사용할 실제 구성 요소를 정의합니다. 내가 만든 간단한 스크립팅 언어를 사용합니다. 다음은 내 스크립트 중 하나의 단순화 된 버전입니다.

ENTITY:"Goblin"
{
    description="It's currently their age."
    commonname="goblin"
    pluralCommonName="goblins"
    childname="gob'in"
    pluralChildName="gob'ins"
    active=Nocturnal
    tags=Mobile
    baseAttributes="OrganicMobileCreature"

    [Model]{
            meshname="Goblin"
            texturename="GoblinTexture"
    }

    [Motion]{
            maxvelocity=0.01:0.015
            locomotion=Walk,Swim
    }

    [Skills]{
            ALL=0.01:0.05,Mine=8.3:8.8,PlaceCube=8.3:8.8
    }

    [Inventory]{
            maxItems=2
            Allow=ALL
            Disallow=NONE
    }
}

그 중 많은 부분이 자체 설명이지만 다음과 같은 주요 내용이 있습니다.

  • 첫 번째 섹션은 엔티티에 대한 공통 정보를 설명합니다. 여기에는 엔터티의 다양한 측면에 대한 설명 및 표시 이름이 포함됩니다.
  • 이 baseAttributes태그는 여러 번 재정의 할 필요가없는 공통 구성 요소를 정의하는 다른 스크립트 파일을 참조합니다. 이 같은 구성 요소를 포함 position, liferequirements등등을. 여기에 컴포넌트가 다시 정의되면이 컴포넌트는 공통 컴포넌트를 겹쳐 씁니다.
  • 각 [NAME] { }세트는 이러한 엔티티에 추가 될 새 컴포넌트를 정의합니다.
  • 이 설명은 단지 하나의 엔티티를위한 것이 아니라 생성 된 모든 고블린을위한 것입니다. 당신은 값의 일부가 범위 (즉, 0.01:0.015)를 가짐을 볼 것입니다 . 새로운 고블린이 생성 될 때 그 값은 그 범위에서 임의의 값을 가진 컴포넌트로 생성됩니다. 따라서 각 고블린은 기술과 속도가 약간 다릅니다. 이 설정은 모든 고블린이 큐브와 마이닝을 배치하는 데 실제로 훌륭한 기술로 시작한다는 것을 정의합니다. 이는 실제로 테스트 목적입니다. 그러나 내가 짐작할 수 있듯이 값을 원하는대로 변경하는 것은 매우 쉽습니다.

이 모든 것은 커스텀 파서, 엔티티 정의를 보유하는 일종의 구조 (Lexicon이라고 부릅니다) 및 엔티티 정의를 가져 와서 새로운 엔티티를 생성하는 팩토리를 포함합니다. 나 에게이 시스템은 아직 초기 단계이지만 실제로는 실제로 잘 진행되고 있습니다. 엔터티를 빠르게 정의 할 수있는 매우 강력한 시스템이며 생성 한 구성 요소를 사용하여 원하는 엔터티를 만들 수 있습니다. 독자적인 파서를 작성하는 것이 편하지 않다면 XML이 잘 작동한다고 생각합니다. 나는 약간의 프로그래밍 언어를 위해 작성한 푸시 백 재귀 파서에서 내 것을 변환했다.

보시다시피 이것은 엔티티를 정의합니다. 나는 그것이 행동을 직접적으로 정의하지 않는다고 언급했다. 그러나 미워하는 적과 같은 적에 대한 공격적인 반응을 쉽게 정의 할 수 있습니다. 이러한 동작을 제어하는 ​​데 사용하는 구성 요소를 정의하는 것만 큼 간단합니다. 내 엔터티에는 다음과 같은 것을 정의하는 지능 구성 요소 (표시되지 않음)가 있습니다.

  • 경로를 찾는 방법 (간단한 시선 이동, 간단한 A *, 예측 A * 등)
  • 그들이 얼마나 공격적이고 방어 적인가. 엔터티에는 방어 할 홈 영역이있을 수 있지만 해당 영역 외부에서는 공격적이지 않을 수 있습니다.
  • 기술 인식 (문호 개방, 가제트 사용, 트랩 방지 등)
  • 그리고 더...

그러나 귀하가 정의한 것은 해당 구성 요소의 데이터를 구동하는 시스템이며, 이는 귀하의 응모 행위에 영향을 미칩니다.


공유해 주셔서 감사합니다. 실제로 XML 형식을 사용하여 시도 할 것이라고 생각합니다. 나는 그것에 대해 많이 생각하고 (AbstractChaos btw 덕분에) (필자는 엔티티 설명을 위해) 내 요구를 충족시켜야합니다.
— nathan

1
@nathan XML을 사용해야한다는 데 동의합니다. 내 게시물의 이유는 XML에 포함 할 데이터와 사용 방법이 더 많기 때문입니다. 데이터 형식은 원하는대로 지정할 수 있습니다. 포함하기로 선택한 데이터와 사용 방법이 훨씬 중요합니다.
— MichaelHouse

@ Byte56이 게시물이 오래되었다는 것을 알고 있지만 부모 자식 관계를 어떻게 처리 할 수 ​​있습니까? 스킬 트리가 있고 A [1]을 사용하려면 기술 A [0]에 10 점, A [2]를 사용하려면 10 점이 필요하다고 가정 해 봅시다. ParentId? 분명히 그것들은 논리적으로 동일하지만 실제 통찰력을 가지기를 바랍니다.
— Superstringcheese

@Superstringcheese if player.hasPoints(10) then i++ end skillTree[i]는 일부 의사 코드입니다. 그러나 그 질문이 게시물과 어떤 관련이 있는지 전혀 모르겠습니다.
— JDSweetBeat

4

실제로 필요한 것이 Monster의 구성 요소를 정의하는 방법이라면 XML은 C #과 java 모두 잘 작동합니다.

당신의 XML은

<?xml version="1.0" encoding="UTF-8"?>
<mobs>
  <mob>
    <personality>Aggressive</personality>
    <intelligence>20</intelligence>
  </mob>
</mobs>

그러면 당신의 폭도 클래스는 다음과 같습니다. (자바)

public class Mob {
  private IPersonality personality;
  private Integer intelligence

  //**  Getters & Setters **//
}

IPersonality는 인터페이스입니다.

그런 다음 XML을로드하고 팩토리를 통해 각 값을 구문 분석 할 수 있습니다.

예를 들어, Personality Factory로 Personality Value를 구문 분석하십시오.

public IPersonality getPersonality(String personalityName) {
  if(personalityName.equals("Aggressive")) {
    return new AggressivePersonality();
  }
  else if(personalityName.equals("Passive")) {
    return new PassivePersonality();
  }
  else {
     //Maybe allow for no personality (We all know monster like that ;) )
     return null; 
  }
}

그럼 당신은 이렇게 폭도를 설정할 수 있습니다

Mob mob = new Mob();
mob.setPersonality(getPersonality(xmlValue));
mobList.add(mob);

핵심은 엔진이 XML의 형식을 알고 있으며 필요한 모든 팩토리를 가지고 있다는 것입니다.

xml의 ​​한 가지 장점은 형식이 항상 올바른지 확인하기 위해 고유 한 스키마를 정의 할 수 있다는 것 입니다. 여기를 참조 하십시오 .

도움이 되었기를 바랍니다


실제로 게임 개발 과정에서 새로운 엔티티를 쉽게 만들 수있는 방법을 찾아야합니다. XML이 충분히 유연할까요? 내부 게임 로직을 위해 스크립팅을 추가해야합니다.
— nathan

Mob 클래스를 엔터티로 읽는 경우 다른 구성 요소 (IPersonality, Intelligence [해당 mob의 데이터 예])를 사용하여 XML을 사용하여 새 Enitity (Mob)를 만듭니다. 그리고 불행히도 내가 지정한 것 이외의 것을 더 많이 알지 못하기에 충분히 유연하다면 대답 할 수는 없지만 XML은 각 섹션을 해석하는 방식이 유일한 경계입니다. 자세한 예를 들어 질문을 업데이트하면 처리 할 수있는 XML을 보여 드리겠습니다. 내부 게임 로직은 내부 용이어야합니까?
— AbstractChaos

0

파이썬은 괜찮습니다. 프로그램에 스크립팅 기능을 추가하려는 경우 종종 LUA가 좋은 대안입니다.

XML을 사용하여 몬스터의 행동을 설명 할 수 있습니다. 실제 게임 코드에는 코딩이 필요합니다. "이름"만 저장하거나 행동 (속도, 몬스터가 사용하는 무기 유형, 게임 코드에서 사용할 행동 등)

스크립트 엔진 (예 : LUA)을 사용하는 경우이 코드를 사전 컴파일 된 프로그램에서 런타임 중에로드 된 스크립트 파일로 전송할 수 있습니다. 이를 위해서는 "몬스터"의 API를 scriptengine에 노출시켜야합니다. 이를 통해 외부에서 몬스터 게임 코드의 메소드를 호출 할 수 있습니다.


내 괴물의 API? 즉, 스크립트에서 새 구성 요소를 만들 수 있어야합니다 (인스턴스화). 가능합니까?
— nathan

Afaik 이것이 가능해야합니다. 또한 외부 저장소 (abstractchaos 또는 byte56에서 언급 한 것처럼)와 스크립팅 언어 (LUA, Python ...)를 혼합하여 사용할 수도 있습니다. 예를 들어 LUA의 주요 장점은 런타임에 코드를 변경할 수 있으며 실행중인 게임 / 엔진에서 즉시 사용할 수 있다는 것입니다.
— Aron_dc

호 진심이야? 실제로 큰 장점입니다. 또한 "게임 타임 라인"에 대한 LUA (또는 다른 스크립팅 언어)가 있습니다. 플레이어가 막혀 있어야하는 장면을 만들려면이 스프라이트를 여기 저기 움직여야합니다. 그러면 엔터티로드에 스크립트 언어를 사용할 수도 있습니까? 또한 내가 "관리자"라고 부르는 것보다 엔티티 / 구성 요소를 관리하는 현재 방법을 노출시키는 또 다른 질문을 게시하려고합니다.
— nathan
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.