특정 지역의 건물을 절차 적으로 생성


15

나와 팀은 게임을 시작할 때 플레이어에게 무작위 공장을 제공하는 팩토리 빌더 게임을 진행하고 있습니다. "공정성"에 대한 감각을 확보하기 위해, 임의로 생성 된 공장은 (자리 표시 자 값) 30의 몇 단위 내에 영역을 갖는 것이 이상적입니다.

이러한 사양을 충족하기 위해 기본 임의 직사각형 생성기를 작성하는 것은 비교적 간단하지만 우리의 목표는 공장이 더 복잡하고, 아마도 2, 3 또는 4 개의 교차 사각형으로 구성되어 더 복잡한 모양을 생성하는 것입니다 (L, U 및 O 모양의 건물).

임의의 사각형을 생성 한 다음 기본 대수를 사용하여 두 번째 사각형을 채우려 고했지만 지금까지 두 개 이상의 사각형을 구현하는 것은 운이 없었으며 심지어 2 사각형 디자인의 결과에 만족하지 못했습니다. .

더 관련성 높은 정보 : 2D 하향식 일부 역학은 팩토리 오 스타일이므로 기계의 공간을 확보 할 수 있도록 적절한 길이와 너비를 가져야합니다. 현재 Java 및 Lua (필요한 경우 내장 라이브러리를 사용할 수 있음)

미리 감사드립니다!

편집 : 내가 "좋은"또는 "나쁜"출력을 말할 때, 나쁜 출력은 플레이어가 사용할 수없는 공간이있는 출력입니다. 공장 형태는 플레이어가 컨베이어 벨트와 같은 공장 기계를 배치 할 수있는 위치를 제한합니다. 이상적으로, 공장은 1-2 블록 너비의 영역을 가져서는 안되며 모양은 1-2 블록의 선이 한쪽으로 "걸려"있는 하나 또는 두 개의 큰 직사각형이 아니어야합니다. 모든 바닥 공간이 "작업 가능"할 수있는 좋은 결과물이 될 수 있으므로 모든 영역의 너비는 3-4 블록 이상입니다. 좋은 출력이 항상 복잡 할 필요는 없지만 (1 개 또는 2 개의 사각형은 괜찮음) 1-2 개 이상의 사각형으로 구성된 경우 공정한 기회가 있어야합니다.

답변:


7

사전 생성 된 폴리 노 미노 를 메타 모양으로 사용하여 다양한 건물을 만들 수 있습니다.

허용 가능한 최소 거리가 3 블록이라고 가정 해 봅시다. 우리가 고려해야 할 가장 작은 수용 단위는 3x3입니다. 편의상 셀이라고 부르고 9 블록의 영역을 제공합니다. 그런 다음 대상 시작 영역을 가져 와서 셀 영역으로 나눕니다. 제공 한 시작 값을 사용하여 3.333을 얻습니다. 그래서 3 개의 세포는 당신이 원하는 것보다 조금 적게 줄 것이고 4 개의 세포는 당신에게 더 많은 것을 줄 것입니다.

여기에는 몇 가지 옵션이 있습니다. 시작 영역에서 융통성이 있다면 허용 가능한 양을 제공하는 셀 수를 선택하는 데 가장 적합한 방법을 사용하십시오 (예 : 가장 가까운 값으로 반올림, 반올림 등). 이것을 셀 수라고합니다.

다음으로 원하는 세포 수를 가진 polyomino를 무작위로 선택하십시오. polyomino의 각 사각형을 빌딩 셀로 교체하면 최종 모양이됩니다.

예를 들어, 반올림하기로 선택했다고 가정하십시오. 다음은 모든 크기 3 폴리 노 미노입니다 (회전 / 뒤집기를 포함하지 않음).

여기에 이미지 설명을 입력하십시오

L 모양을 임의로 선택하고 임의의 회전을 적용한다고 가정 해 봅시다. 건물의 레이아웃은 다음과 같습니다.

여기에 이미지 설명을 입력하십시오

몇 가지 문제. 첫째, 사용할 수있는 셀 수에 제한이 있습니다. Wikipedia는 최대 8 크기의 ocomino를 제공 합니다. 그것은 크기 12까지의 요약 데이터를 포함하지만 모든 온라인 목록이 있는지 모르겠습니다. 둘째, 위의 솔루션은 9의 배수 인 건물 크기에만 정확하게 작동합니다. 이러한 문제 중 일부를 해결하는 방법에는 두 가지가 있습니다.

1) 다른 셀 크기를 사용하십시오. 예를 들어 3x4, 4x4 등

2) 출발 폴리오 미노에 추가 세포를 첨가한다. 모든 모양을 동일하게 보장해야하는 경우 까다로울 수 있지만 대부분의 게임 개발 목적에서는 건물 모양의 균일 한 분포가 필요하지 않습니다.

3) 건물을 더 크게 만들기 위해 밖으로 나갑니다. 예제로 돌아가서 3 개의 셀을 사용한 경우 건물의 면적은 27 제곱으로 짧아지고 3은 줄어 듭니다. 그런 다음 둘레를 스캔하여 1x3 크기의 사각형 그룹을 붙일 위치를 찾을 수 있습니다. 메이크업 그룹이 AxB 이상이고 A가 최소 허용 거리 이상인 경우 결과는 최소 허용 거리 제한을 위반하지 않습니다. 위의 예를 작성하면 가능한 결과를 보여줍니다.

여기에 이미지 설명을 입력하십시오

4) 너무 작은 건물을 채우는 대신 너무 큰 건물을 잘라낼 수 있습니다. 허용 가능한 최소 거리 제한을 따르는 것이 패딩 옵션보다 더 복잡하지만 고려해야 할 대안이 더 많습니다.

다른 의견들 :

주어진 크기의 가능한 모든 폴리 노 미노를 사용할 수 있다고해서 꼭 그렇게해야하는 것은 아닙니다. 그들 중 일부가 재미 있지 않거나, 주제를 깨뜨 리거나, 청중에게 불쾌감을 주거나 (swastika 패턴), 다른 문제를 일으키는 경우, 꺼내십시오. 또한 일부 패턴이 흥미롭지 만 일상적으로 팝업하기에는 너무 이상하다면 선택 루틴에 가중치를 부여 할 수 있습니다. 마지막으로이 솔루션을 현재 전략과 함께 사용할 수 있습니다. 직사각형 건물을 생성하는 시간의 70 %와 polyomino 접근법을 사용하는 시간의 30 % 일 수 있습니다. 또는 직사각형 건물로 시작하여 작은 폴리 아미노를 외부에 붙이십시오.


16

절차 생성기를 작성하는 간단한 방법은 다음과 같습니다.

  1. 임의로 구축
  2. 출력이 양호한 지 확인하는 기능을 실행하십시오.
  3. 출력이 좋지 않으면 1 단계로 이동하십시오.

완료하는 데 수천 번의 실행이 필요하더라도 대부분의 간단한 발전기는이 접근 방식만으로도 충분합니다. 장점은 발전기에 필요한 스마트가 많지 않다는 점이며, 100 % 좋은 무언가를 만드는 것보다 좋은 것이 있는지 확인하기 때문에이 방법은 매우 쉽습니다.

출력이 좋은지에 대한 객관적인 조치를 나열했습니다. 빠르고 더러운 생성기를 만들기에 충분해야합니다. 예를 들어 폭이 1-2 블록에 불과한 영역이있는 경우 영역 내부에 사각형을 임의로 배치하고 출력을 거부하십시오.

그로 시작하여 나중에 개선하고 최적화하십시오.


감사합니다! 나는 이것을 고려한 것을 기억하지만 몇 초 +로드 시간이있을 가능성이 있다는 생각이 나를 막았다. 나는 이제 그 기회가 얼마나 작은 지 알고 있습니다. 나는 그것을 시도해야 할 것이지만, 누군가가 더 직접적인 해결책을 먼저 가지고 있는지 기다릴 수 있습니다.
user2129189

@ user2129189 생성기를 실행 한 후에도 테스트를 통과 할 수없는 레이아웃 생성을 피하기 위해 난수 범위를 조정할 수 있습니다. 각 코어가 한 번에 하나의 레이아웃을 생성하도록하여 여러 코어에서이 시행 착오 생성 알고리즘을 병렬화 할 수도 있습니다.
Philipp

3
나 자신은 거부 및 재시도 생성 방법의 팬이 아닙니다. 제너레이터가 한 가지 간단한 작업을 수행하면 속도가 빠르지 만 게임 레벨에서는 일반적으로 더 많은 기능과 생성 단계를 계층화하여 더 풍부한 맵을 만듭니다. 이 시점에서 실행 가능한 맵을 칠 확률은 각 단계가 성공할 확률의 곱이며 빠르게 줄어들 수 있습니다. 이것은 학문적 인 문제가 아닙니다. 저는 건설 별 단일 패스 생성기가 더 쉬웠을 때 과도한 생성 시간을 피하기 위해 좋은 / 나쁜 시드 캐싱 시스템을 구현해야하는 개발자들과 이야기를 나 ve습니다.
DMGregory

@DMGregory 네, 확실히 알 수 있습니다. 기본 무작위 생성기는 내 경우에 몇 번의 통과로 99 %의 시간과 같이 작동하지만 나중에 더 많은 복잡성을 추가하려면 크게 느려질 수 있습니다. 누구나 추측 및 체크와 같은 모델의 실제 프로그래밍 / 게임 응용 프로그램을 알고 있습니까?
user2129189

조건의 표현을 현재 세대 수준에 맞추기 위해주의를 기울여 세대 기능과 검사의 계층이있을 수 있습니다. 이렇게하면 항목을 약간 잘못 배치 한 오류로 인해 전체 레벨을 전체적으로 다시 생성 할 필요가 없습니다.
Pysis

7

"모든 영역이 최소 3-4 블록 너비"에 대한 제한을 감안할 때, 내 마음에 도약하는 첫 번째 아이디어는 다음과 같습니다.

  1. 3x3, 3x4, 4x3 또는 4x4 중 하나를 선택하십시오
  2. 그리드 중앙에 해당 크기의 블록을 배치
  3. 방향을 정하십시오 (위, 왼쪽, 오른쪽, 아래)
  4. 이전에 배치 된 블록과 함께 3x3 블록을 그 방향으로 배치하십시오.
  5. 성공할 경우 확률이 높지만 선택한 방향 중 하나에서 블록을 4x3 블록으로 확장하십시오.
  6. 약간의 확률로, 채워진 블록의 임의의 가장자리로
  7. 면적이 충분히 커질 때까지 3-6 단계를 반복하십시오.

기본 아이디어는 모든 영역이 최소한 주어진 크기를 갖기를 원한다면 해당 크기의 영역에서만 작동한다는 것입니다. 보다 일반적으로, 생성 된 모든 출력에 대해 무언가를 적용하려는 경우, 부분적으로 생성 된 모든 출력에 해당되는 것이 있는지 확인하십시오.


4
항상 3x3 블록에서 시작한 다음 각 사각형이 기존 사각형에 인접한 임의의 위치에 3x1 블록을 추가하여 작업을 단순화합니다. 3x3 블록에 추가 할 수있는 위치는 네 가지입니다. 모두 3x4 블록을 제공하며 다음 블록에는 6 개의 가능한 위치가 있습니다. 거기에서 그것은 더 복잡해 지지만 그렇게 나쁘지는 않습니다.
JollyJoker

0

부울 NOT과 UNION을 사용하고 무작위로 선택하는 것을 고려하십시오.

  1. 임의의 사각형을 배치하십시오.
  2. 두 번째 임의의 사각형을 배치하십시오.
  3. 처음부터 두 번째를 UNION 또는 SUBTRACT 중에서 임의로 선택할 수 있습니다.
  4. 여러 사각형에 대해 반복하십시오. 그러나 2 ~ 3 개만으로도 충분한 결과를 얻을 수 있습니다.

그런 다음 면적을 계산하고 원하는 대략적인 크기에 더 가깝게 확대 또는 축소 한 다음 필요한 최소량보다 작은 치수가 없는지 테스트합니다.


원하는 영역을 얻는 스케일링 아이디어는 실제로는 영리합니다. 나는 이런 식으로 조용한 것을 구현할 수 있습니다.
user2129189
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.