안동민 개발노트 아이콘

안동민 개발노트

9장 : 성능 최적화

에셋과 레벨 최적화 기법

병목을 찾는 도구를 익혔다면, 이제는 실제로 비용이 큰 자산을 줄여야 성능이 올라갑니다.

같은 장면이라도 메시 밀도, 텍스처 크기, 머티리얼 복잡도, 레벨 구성 방식에 따라 프레임 차이가 크게 벌어집니다.

이번 절에서는 에셋(Asset)레벨(Level)을 대상으로 즉시 적용 가능한 최적화 기법을 정리합니다. 핵심은 무작정 화질을 낮추는 것이 아니라, 플레이어가 체감하기 어려운 영역부터 비용을 줄이는 순서를 잡는 것입니다.

이 절을 마치면 어떤 항목을 얼마나 줄일지 근거를 가지고 결정할 수 있습니다.


에셋 및 레벨 최적화의 목표

에셋 및 레벨 최적화는 게임의 성능을 좌우하는 핵심 요소입니다.

  • 렌더 제출 비용 감소: 드로우콜, 머티리얼 섹션 수, 렌더 상태 변경, RHI 제출 비용을 함께 줄입니다.
  • 기하 비용 조정: 모바일, 비 Nanite, 스켈레탈 메시, 폴리지처럼 폴리곤 수가 직접 부담이 되는 대상을 먼저 줄입니다.
  • 텍스처 메모리 사용량 조정: 텍스처가 차지하는 VRAM, 스트리밍 풀, 디스크 크기, 압축 품질을 함께 봅니다.
  • 오버드로우 감소: 투명하거나 반투명한 부분이 겹쳐 그려지는 횟수와 픽셀 셰이더 비용을 줄입니다.
  • 그림자와 조명 비용 조정: 그림자 맵, 동적 광원, Lumen/라이트맵 선택이 만드는 런타임 비용과 메모리를 나눕니다.
  • 데이터 크기 감소: 게임의 빌드(Binary) 크기와 런타임 메모리 사용량을 줄입니다.

메시 (Mesh) 최적화

가장 기본적이면서도 중요한 최적화 대상은 3D 모델, 즉 메시입니다.

폴리곤 수 감소 (Poly Count Reduction, 모바일 우선)

  • 필요성: 모바일, 비 Nanite 메시, 스켈레탈 메시, 폴리지에서는 화면에 보이는 폴리곤 수가 렌더링 부담으로 이어질 수 있습니다. UE5/Nanite 환경에서는 폴리곤 수만 보지 말고 화면 픽셀 비용, 머티리얼, 오버드로우, 그림자 비용을 같이 봅니다.
  • 방법
    • 리토폴로지 (Retopology): 외부 3D 모델링 툴(Blender, Maya, ZBrush 등)에서 모델의 폴리곤 밀도를 최적화합니다.
    • 디시메이션 (Decimation): 언리얼 엔진 내에서 Static Mesh Editor메시 Simplification (Mesh Simplification) 도구를 사용하여 폴리곤 수를 줄일 수 있습니다. (프로세스 탭)
      • 주의: 너무 줄이면 디테일 손실이 크거나 외형이 깨질 수 있으므로, 육안으로 확인하며 적절한 수준을 찾아야 합니다.
    • 불필요한 디테일 제거: 플레이어에게 보이지 않는 면(벽 뒤, 땅 속)의 폴리곤은 과감히 제거합니다.

LOD (Level of Detail)

  • 필요성: 멀리 있는 오브젝트는 가까이 있는 오브젝트만큼 디테일할 필요가 없습니다. LOD는 거리나 화면 크기에 따라 메시, 애니메이션, 머티리얼 비용을 낮추는 장치입니다. Nanite 사용 여부와 플랫폼 제약에 따라 효과와 설정 방식이 달라집니다.
  • 설정

    Static Mesh Editor를 엽니다.

    Details 패널의 LOD Settings 섹션에서 Num LODs를 설정합니다. (기본적으로 1)

    LOD Import 섹션에서 외부에서 가져온 LOD 메시를 할당하거나, Generate LODs를 클릭하여 엔진이 자동으로 LOD를 생성하도록 합니다.

    각 LOD의 Screen Size를 조절하여 어떤 거리에서 해당 LOD가 활성화될지 정의합니다.

    LOD Coloration 뷰 모드 (뷰 모드 > LOD 색상)를 사용하여 각 LOD가 언제 활성화되는지 시각적으로 확인합니다.

  • : 수동으로 만든 LOD가 자동 생성된 LOD보다 품질이 좋고 효율적일 수 있습니다.

충돌 메시 최적화

  • 필요성: 물리 시뮬레이션의 성능에 가장 직접적인 영향을 미칩니다.
  • 방법: 7장 5절 물리 시뮬레이션 성능 조정에서 다룬 것처럼, Simple Collision (단순 충돌)을 적극적으로 사용합니다.
    • Static Mesh Editor에서 Collision 메뉴를 통해 Add Box/Sphere/Capsule Simplified Collision 또는 Auto Convex Collision을 사용하여 단순 충돌을 생성합니다.
  • Complex Collision (복잡 충돌)은 극도로 제한적으로 사용합니다. (예: Collision ComplexityUse Complex as Simple로 설정하는 것)

텍스처 (Texture) 최적화

텍스처는 VRAM 사용량에 큰 영향을 미칩니다.

해상도 조정 (Resolution Adjustment)

  • 필요성: 텍스처 해상도가 높을수록 더 많은 VRAM을 소모합니다.
  • 방법
    • 텍스처 에셋 더블클릭: Details 패널의 Compression SettingsMax Texture Size를 조정합니다.
    • Max Texture Size: 텍스처의 최대 해상도를 제한합니다. (예: 2048x2048 대신 1024x1024)
    • Power of 2 (2의 거듭제곱): 텍스처 해상도는 2의 거듭제곱(예: 256, 512, 1024, 2048)으로 설정하는 것이 GPU 효율에 좋습니다.
  • 활용: 멀리 있거나 중요하지 않은 오브젝트의 텍스처는 낮은 해상도를 사용합니다.

압축 설정 (Compression Settings, 플랫폼별)

  • 필요성: 플랫폼별 GPU 압축 포맷과 알파 채널 유무에 따라 VRAM, 디스크 크기, 품질이 달라집니다.
  • 방법: 텍스처 에셋의 Details 패널에서 Compression Settings를 선택합니다.
    • 플랫폼별 포맷: 데스크톱은 BCn 계열, 모바일은 ASTC/ETC 계열처럼 대상 플랫폼에 맞는 압축 포맷이 사용됩니다.
    • Normalmap: 노멀 맵에 사용됩니다.
    • VectorDisplacementmap: 변위 맵에 사용됩니다.
    • UserInterface2D (RGBA): UI 텍스처 등 알파 채널이 중요한 경우.
    • Masks (R, G, B, A): 채널별로 독립적인 데이터를 담는 마스크 텍스처에 사용됩니다. (예: AO, Roughness, Metallic을 하나의 텍스처에 묶을 때)
  • : 불필요한 알파 채널을 제거하거나, 여러 흑백 맵(AO, Roughness, Metallic)을 하나의 텍스처의 각 채널에 넣어 VRAM 사용량을 절약하는 것이 좋습니다.

밉맵 (Mipmap)

  • 필요성: 밉맵은 텍스처의 여러 해상도 버전을 추가로 만들기 때문에 원본 대비 데이터가 늘어납니다. 대신 거리별로 낮은 mip을 사용해 샘플링 품질, 텍스처 캐시 효율, 스트리밍 안정성을 높입니다.
  • 설정: 대부분의 텍스처는 기본적으로 밉맵이 활성화되어 있습니다. 텍스처 에셋의 Details 패널에서 Mip Gen Settings를 확인합니다. (UI 텍스처처럼 밉맵이 불필요한 경우 NoMipmaps로 설정)

머티리얼 (Material) 최적화

복잡한 머티리얼은 셰이더 연산 부하를 증가시킵니다.

셰이더 복잡도 감소

  • 필요성: 머티리얼 비용은 단순한 노드 수보다 shader instruction, texture fetch, 분기, permutation, 오버드로우에 더 크게 좌우됩니다.
  • 방법
    • Shader Complexity 뷰 모드: 가장 비싼 머티리얼을 식별합니다.
    • 최적화
      • 불필요한 노드 제거.
      • 연산량이 많은 노드 대신 간단한 수학 연산 사용.
      • Static Switch Parameter를 사용하여 사용하지 않는 브랜치를 컴파일 시 제거.
      • 여러 머티리얼에 걸쳐 중복되는 로직은 머티리얼 함수 (Material Function)로 만들어 재사용.
      • 마스터 머티리얼 - 인스턴스 (Master Material - Instance) 패턴을 사용하여 머티리얼 인스턴스에서 파라미터만 변경하여 재컴파일 시간을 줄입니다.
  • : 조명 반응이 필요 없는 배경, UI, 특수 효과는 Unlit을 검토할 수 있습니다. 조명 정보가 필요한 표면까지 무리하게 바꾸면 품질 기준이 흔들립니다.

오버드로우 감소 (Overdraw Reduction)

  • 필요성: 투명/반투명 머티리얼(유리, 물, 파티클, 식물 잎)은 겹쳐질수록 여러 번 렌더링되어 GPU 부하를 크게 증가시킵니다.
  • 방법
    • Overdraw 뷰 모드: 오버드로우가 심한 부분을 식별합니다.
    • 블렌드 모드 선택: 가능하면 Opaque를 우선하고, Translucent가 필요한 경우 면적과 겹침을 줄입니다. Masked는 정렬/블렌딩 부담을 낮출 수 있지만 알파 테스트와 픽셀 비용이 남으므로 Shader Complexity와 Quad Overdraw로 확인합니다.
    • 투명 오브젝트 수 제한: 한 화면에 보이는 투명 오브젝트의 수를 줄입니다.
    • 파티클 최적화: 파티클 시스템에서 파티클의 수, 크기, 수명, 텍스처 오버드로우를 최소화합니다.

레벨 (Level) 최적화

레벨 구성 방식도 성능에 큰 영향을 미칩니다.

액터 병합 (Merge Actors)

  • 필요성: 여러 작은 스태틱 메시 액터를 병합하면 렌더 제출 비용을 줄일 수 있습니다. 다만 머티리얼 섹션 수가 남아 있거나 오클루전/LOD 단위가 커지면 이득이 줄어들 수 있으므로 병합 전후를 비교해야 합니다.
  • 사용법: 레벨 에디터에서 병합할 액터들을 모두 선택한 후, 창(Window) > 개발자 도구(Developer Tools) > 액터 병합(Merge Actors)를 클릭합니다.
  • 활용: 건축물 구성 요소(벽, 창문, 기둥)나 작은 오브젝트 그룹(돌 무더기, 나뭇가지 묶음)에 효과적입니다.
  • 주의: 병합된 액터는 더 이상 개별적으로 움직이거나 LOD를 가질 수 없게 됩니다. 동적인 오브젝트에는 적합하지 않습니다.

컬링 (Culling)

  • 필요성: 화면에 보이지 않는 오브젝트는 렌더링되지 않도록 하여 성능을 절약합니다.
  • 종류
    • 프러스텀 컬링 (Frustum Culling): 카메라 시야(Frustum) 밖에 있는 오브젝트는 렌더링되지 않습니다. (엔진이 자동으로 수행)
    • 오클루전 컬링 (Occlusion Culling): 다른 오브젝트에 완전히 가려져 보이지 않는 오브젝트는 렌더링되지 않습니다. (엔진이 자동으로 수행)
    • 거리 컬링 (Distance Culling): 특정 거리 밖에 있는 오브젝트는 아예 렌더링되지 않도록 설정합니다.
      • 설정: Static Mesh ComponentRendering 섹션에서 Min Draw Distance, Desired Max Draw Distance, Current Max Draw Distance를 확인하거나, 여러 액터에는 Cull Distance Volume을 사용합니다.
    • LOD와 컬링 분리: LOD는 표시 품질을 단계적으로 낮추는 장치이고, 완전 제거는 거리 컬링 또는 Cull Distance Volume 기준으로 관리합니다.

조명 방식 선택

  • Static Lighting: 빌드 후 런타임 조명 비용은 낮지만 라이트맵 메모리, 빌드 시간, 동적 변화 제약이 생깁니다.
  • Stationary Lighting: 정적/동적 요소를 섞을 수 있지만 overlap 제한과 동적 그림자 비용을 함께 관리해야 합니다.
  • Movable/Lumen: 실시간 변화와 동적 GI가 필요한 경우에 적합하지만, 그림자와 반사 비용을 ProfileGPU에서 확인해야 합니다. Lumen 중심 프로젝트에서는 precomputed static lighting 사용 여부도 프로젝트 설정과 함께 봅니다.

프로파일링 및 반복

  • 측정 루프: 최적화는 분석 -> 적용 -> 재측정 -> 재분석의 반복 과정입니다.
  • 단계적 접근: 한 번에 너무 많은 것을 바꾸지 말고, Stat Unit, ProfileGPU, Shader Complexity, Quad Overdraw, texture streaming 통계를 통해 움직인 지표를 기록합니다.

메시, 텍스처, 머티리얼, 레벨 최적화는 각각 다른 지표를 움직이므로 변경 전후 기록도 항목별로 나누어야 합니다.


최적화 적용 후에는 품질 손상, 성능 개선, 되돌릴 기준을 함께 확인해야 무리한 감량을 피할 수 있습니다.


에셋과 레벨 최적화는 메시, 텍스처, 머티리얼, 스트리밍, 컬링 설정을 목표 성능에 맞추는 과정입니다. 분석 결과를 기준으로 비용이 큰 항목부터 조정해야 합니다.

에셋과 레벨 최적화는 로딩 비용, 메모리, LOD, 스트리밍 기준으로 점검합니다.