Poglavlje 38: Packaging i Platforme

Poglavlje 38: Packaging i Platforme

"Igra koja ne moze da se pokrene na ciljanoj platformi nije igra -- to je samo skup fajlova."

Dosli smo do jednog od najvaznijih, a cesto i najzanemarivanijih koraka u razvoju igre: pakovanje (packaging) projekta za krajnjeg korisnika. Mozete imati najlepsu igru na svetu unutar Unreal editora, ali ako ne mozete da je isporucite igracima na njihovim uredjajima -- sve je uzalud.

U ovom poglavlju cemo detaljno proci kroz ceo proces pretvaranja vaseg UE5 projekta u gotov proizvod koji radi na razlicitim platformama. Razgovracemo o kompilaciji shader-a, PSO kesiranju, procesu kuvanja (cooking), razlikama izmedju platforma, podesavanjima skalabilnosti, i optimizacijama za isporuku. Pripremi se -- ovo je jedno od najguscih poglavlja u knjizi, ali i jedno od najkorisnijih.


38.1 Shader Compilation -- Od Koda do GPU Instrukcija

Shaderi su mali programi koji se izvrsavaju na grafickoj kartici (GPU). Svaki materijal koji napravite u UE5, svaki post-process efekat, svaka cestica -- sve se na kraju svodi na shader kod koji GPU izvrsava. Ali pre nego sto GPU moze da izvrsi taj kod, shader mora biti kompajliran -- preveden iz visokog jezika (HLSL u slucaju Unreal-a) u masinki kod specifican za konkretni GPU i graficki API.

Ako se secate Poglavlja 17 gde smo prvi put pomenuli shader kompilaciju, sada cemo ici mnogo dublje.

38.1.1 Offline vs Runtime Compilation

Postoje dva fundamentalno razlicita pristupa kompilaciji shader-a:

Offline (ahead-of-time) kompilacija znaci da se shaderi kompajliraju unapred, pre nego sto igrac pokrene igru. To je ono sto se desava tokom procesa pakovanja. Prednosti su ogromne:

Runtime kompilacija znaci da se shaderi kompajliraju dok igra radi. Ovo se desava kada igra naidje na kombinaciju materijala i render stanja koju nikada ranije nije videla. U praksi, runtime kompilacija je jedan od najcescih uzroka "stuttering-a" (zastajkivanja) u igrama -- i to je nesto sto apsolutno zelite da minimizujete ili potpuno eliminisete.

// Vizualizacija protoka shader kompilacije

[HLSL Source Code]
        |
        v
[Shader Compiler Frontend]  <-- Platform-nezavisan korak
        |
        v
[Intermediate Representation]
        |
        +---> [DirectX Shader Compiler] ---> DXIL/DXBC bytecode
        |
        +---> [Vulkan SPIR-V Compiler]  ---> SPIR-V bytecode
        |
        +---> [Metal Shader Compiler]   ---> Metal IR
        |
        +---> [Console-specific]        ---> Platform bytecode

UE5 koristi Shader Compiler Worker procese (SCW) za paralelnu kompilaciju. Kada otvorite editor ili pokrenete kuvanje, videcete poruku poput "Compiling Shaders (2847 remaining)" -- to su ti worker procesi na delu.

38.1.2 Shader Compilation Tokom Cooking-a

Kada pokrenete packaging proces (bilo iz editora: File > Package Project, bilo iz komandne linije koristeci RunUAT), jedna od najduzih faza je upravo kompilacija shader-a. Evo sta se desava korak po korak:

  1. Identifikacija potrebnih shader-a: Engine prolazi kroz sve materijale, post-process efekte, i druge shader-zavisne resurse u vasem projektu.

  2. Generisanje shader permutacija: Svaki materijal moze imati desetine ili stotine permutacija -- razlicite kombinacije feature-a (static switches, quality levels, vertex factory types). Na primer, jedan materijal koji podrzava i forward i deferred rendering, sa opcionalnim tessellation-om, i razlicitim quality level-ima moze generisati 50+ permutacija.

  3. Kompilacija u platformski format: Svaka permutacija se kompajlira u bytecode specifican za ciljnu platformu.

  4. Kesiranje rezultata: Kompajlirani shaderi se cuvaju u Derived Data Cache (DDC) da bi se izbegla ponovna kompilacija pri sledecem kuvanju.

Struktura DDC foldera izgleda otprilike ovako:

DerivedDataCache/
    Boot.ddc           -- Kesrani podaci za boot shadere
    ShaderCache/
        PCD3D_SM5/     -- DirectX 11/12 Shader Model 5
        PCD3D_SM6/     -- DirectX 12 Shader Model 6
        SF_VULKAN_SM5/ -- Vulkan shaderi
        SF_METAL_SM5/  -- Metal shaderi (macOS)
        ...

Napomena: DDC je kljucan za efikasan rad. Ako radite u timu, podelite DDC preko mreze (shared DDC) da ne bi svaki clan tima morao ponovo da kompajlira iste shadere. Ovo mozete podesiti u DefaultEngine.ini:

[DerivedDataBackendGraph]
Shared=(Type=FileSystem, ReadOnly=false, Clean=false, Flush=false,
        PurgeTransient=true, DeleteUnused=true, UnusedFileAge=34,
        FoldersToClean=-1, Path="\\SharedServer\DDC",
        EnvPathOverride=UE_SharedDataCachePath)

38.1.3 Platform-Specific Shader Compilation

Svaka platforma ima svoj graficki API i odgovarajuci shader format. Evo pregleda:

DirectX (Windows, Xbox)

DirectX je primarni graficki API za Windows i Xbox platforme.

// Primer HLSL koda koji ce biti kompajliran za DirectX

float4 MainPS(FMaterialPixelParameters Parameters) : SV_Target0
{
    float3 BaseColor = GetMaterialBaseColor(Parameters);
    float Metallic = GetMaterialMetallic(Parameters);
    float Roughness = GetMaterialRoughness(Parameters);
    
    // Ovo se prevodi u platformski bytecode
    return float4(BaseColor, 1.0);
}

Vulkan (Windows, Linux, Android)

Vulkan koristi SPIR-V (Standard Portable Intermediate Representation) kao shader format.

Vulkan shader kompilacija je generalno sporija od DirectX kompilacije, sto je jedna od cescih zalbi developera koji ciljaju Vulkan platforme.

Metal (iOS, macOS)

Apple platforme koriste Metal Shading Language (MSL) i Metal IR.

Konzole (PS5, Xbox Series X|S)

Konzole imaju proprietary (vlasnicke) shader kompajlere:

Vazno: Konzolni SDK-ovi su pod NDA (Non-Disclosure Agreement). Ne mozemo deliti specficne detalje o internim formatima, ali principi su isti -- HLSL se prevodi u platformski bytecode.

38.1.4 Compilation Times i Kako Rastu sa Brojem Materijala

Ovo je tema koja boli svakog UE5 developera. Shader kompilacija moze trajati od nekoliko minuta za mali projekat do nekoliko sati (ili cak dana!) za velike AAA projekte. Evo zasto:

Linearan rast je mit -- rast je superlinearan.

Razmotrimo matematiku:

Broj shader permutacija = Broj materijala
                        x Broj quality level-a
                        x Broj vertex factory tipova
                        x Broj feature permutacija
                        x Broj ciljnih platforma

Primer za srednji projekat:
- 500 materijala
- 5 quality level-a (Low, Medium, High, Epic, Cinematic)
- 4 vertex factory tipa (static mesh, skeletal mesh, landscape, particle)
- Prosecno 8 feature permutacija po materijalu
- 2 platforme (DX12 + Vulkan)

= 500 x 5 x 4 x 8 x 2 = 160,000 shader permutacija!

Za veliki AAA projekat sa 5000+ materijala, taj broj moze lako preci milion permutacija. Svaka permutacija zahteva kompilaciju, validaciju, i cuvanje.

Strategije za smanjenje compilation time-a:

Strategija Uticaj Kompleksnost
Koristite Material Instance-e umesto novih materijala Visok Niska
Minimizirajte Static Switch parametre Visok Srednja
Koristite Shared DDC u timu Visok Srednja
Iskljucite nepotrebne platforme u Target Platforms Srednji Niska
Koristite distributed compilation Veoma visok Visoka
Podesite r.ShaderCompiler.NumThreads Srednji Niska

Material Instance-i vs novi materijali: Ovo ne mozemo dovoljno naglasiti. Ako imate 100 varijacija jednog materijala koje se razlikuju samo po teksturama i skalarnim parametrima, napravite jedan master materijal i 100 Material Instance-a. Instance-i ne generisu nove shader permutacije -- oni reuse-uju kompajlirane shadere svog roditelja.

38.1.5 Distributed Shader Compilation (XGE, IncrediBuild, Horde)

Kada lokalna kompilacija nije dovoljno brza, mozete distribuirati posao na vise masina. UE5 podrzava nekoliko sistema za distribuiranu kompilaciju:

XGE (Xoreax Grid Engine) / IncrediBuild

IncrediBuild (ranije poznat kao Xoreax) je najsire koriscen sistem za distribuiranu kompilaciju u game industriji.

Podesavanje u BuildConfiguration.xml:

<?xml version="1.0" encoding="utf-8" ?>
<Configuration xmlns="https://www.unrealengine.com/BuildConfiguration">
    <BuildConfiguration>
        <bAllowXGE>true</bAllowXGE>
    </BuildConfiguration>
    <ParallelExecutor>
        <MaxLocalActions>4</MaxLocalActions>
    </ParallelExecutor>
</Configuration>

Unreal Horde (Build Farm)

Horde je Epic-ov sopstveni distribuirani build system, koji je sada deo UE5 open-source distribucije.

Horde arhitektura:

[Horde Server]
    |
    +--- [Agent Pool 1: Windows Build Machines]
    |        +--- Agent 1 (16 cores, 64GB RAM)
    |        +--- Agent 2 (16 cores, 64GB RAM)
    |        +--- Agent 3 (32 cores, 128GB RAM)
    |
    +--- [Agent Pool 2: Linux Build Machines]
    |        +--- Agent 4
    |        +--- Agent 5
    |
    +--- [Agent Pool 3: Mac Build Machines]
             +--- Agent 6 (M2 Ultra)

SN-DBS (SN Build System)

Koristi se uglavnom za konzolnu kompilaciju (posebno PlayStation). Sony obezbeduje ovaj sistem kao deo svog SDK-a.

Prakticni saveti za distribuiranu kompilaciju

  1. Mreza je usko grlo: Pobrinite se da imate brzu LAN konekciju izmedju masina (minimum 1Gbps, idealno 10Gbps).
  2. Homogen hardver pomaze: Ako sve masine imaju slicnu konfiguraciju, distribucija je efikasnija.
  3. Ne distribuirajte premale poslove: Overhead mrezne komunikacije moze prevazici korist za male projekte. Distribuirana kompilacija se isplati tek za projekte sa 10,000+ shader permutacija.
  4. Monitoring je kljucan: Koristite IncrediBuild Monitor ili Horde dashboard da pratite iskoriscenost agenta i identifikujete uska grla.
// Tipicna ubrzanja sa distribuiranom kompilacijom:

Lokalna kompilacija (16-core masina):     ~2 sata
IncrediBuild sa 10 agenata (16 cores):    ~15 minuta
IncrediBuild sa 50 agenata:               ~5 minuta
Horde sa 100 agenata:                     ~2 minuta

38.2 PSO Precaching -- Eliminisanje Stuttering-a

Pipeline State Objects (PSO) su jedan od najvaznijih koncepata u modernim grafickim API-jima (DirectX 12, Vulkan, Metal), a istovremeno i jedan od najcesce nerazumevanih. Ako ste ikada iskusili "shader compilation stutter" u igri -- to su PSO-ovi na delu.

Ako se secate Poglavlja 22 gde smo prvi put pomenuli PSO kesiranje u kontekstu materijala, sada cemo ici mnogo dublje u mehaniku i prakticna resenja.

38.2.1 Sta su PSO-ovi?

Pipeline State Object predstavlja kompletno stanje grafickog pipeline-a potrebno za renderovanje jednog draw call-a. To ukljucuje:

// Konceptualni prikaz PSO-a

PSO = {
    VertexShader:     "M_Rock_VS_SM5.dxil",
    PixelShader:      "M_Rock_PS_SM5.dxil",
    RenderTarget:     DXGI_FORMAT_R8G8B8A8_UNORM,
    DepthFormat:      DXGI_FORMAT_D32_FLOAT,
    BlendState: {
        BlendEnable:  false
    },
    RasterizerState: {
        CullMode:     BACK,
        FillMode:     SOLID
    },
    DepthStencilState: {
        DepthEnable:  true,
        DepthFunc:    LESS_EQUAL
    },
    InputLayout: [
        { POSITION, FLOAT3 },
        { NORMAL,   FLOAT3 },
        { TANGENT,  FLOAT4 },
        { TEXCOORD, FLOAT2 }
    ],
    PrimitiveTopology: TRIANGLE_LIST,
    SampleCount:       1
}

U starijim API-jima (DirectX 11, OpenGL), ova stanja su se mogla menjati nezavisno jedno od drugog. GPU driver je interno morao da "sklepi" finalni pipeline state svaki put kada se neko stanje promeni, sto je dovelo do nepredvidivih performance spike-ova.

Moderni API-ji (DX12, Vulkan, Metal) zahtevaju da se sva ova stanja definisu unapred kao jedan monolitni objekat -- PSO. Kreiranje PSO-a je skupa operacija (moze trajati od 1ms do 100ms+), ali jednom kreiran, PSO se moze koristiti za renderovanje bez overhead-a.

38.2.2 Zasto Prvo Renderovanje Novog PSO-a Uzrokuje Hitch

Evo scenarija koji se cesto desava:

  1. Igrac trci kroz level
  2. Ulazi u novu prostoriju sa materijalom koji nikada ranije nije renderovan
  3. Engine treba da renderuje taj materijal
  4. Engine trazi odgovarajuci PSO -- ne postoji!
  5. Engine mora da kreira novi PSO -- sto znaci kompilaciju shader-a i kreiranje pipeline state-a
  6. Dok se PSO kreira, frame se zaustavlja
  7. Igrac vidi stutter (zastajkivanje) od 16-100+ ms

Ovo je posebno problematicno u:

// Vremenski dijagram PSO hitch-a

Frame N:     [Render Scene.......|PSO Miss!|Compile PSO.........|Resume]
             |<-- 8ms ---------->|         |<-- 45ms ---------->|<-- 3ms -->|
             
Ukupno: 56ms umesto ocekivanih 16ms (60 FPS)
= Vidljiv stutter za igraca!

38.2.3 Prikupljanje PSO-ova Tokom Razvoja/Testiranja

UE5 nudi mehanizam za prikupljanje svih PSO-ova koje igra koristi tokom testiranja, i onda njihovo pakovanje sa igrom da bi se izbegli runtime hitch-evi.

Metod 1: Automatsko prikupljanje tokom Play-in-Editor

Kada igrate igru u editoru ili u standalone modu, UE5 moze automatski beleziti svaki PSO koji se kreira. Ovo se aktivira sa:

; DefaultEngine.ini
[ShaderPipelineCacheTools]
bAutoCollectPSOs=true

Ili koristeci konzolnu komandu:

r.ShaderPipelineCache.LogPSO 1
r.ShaderPipelineCache.SaveBoundPSOLog 1

PSO logovi se cuvaju u:

[Project]/Saved/CollectedPSOs/
    PSOCache_DX12_SM6.upipelinecache
    PSOCache_Vulkan_SM5.upipelinecache

Metod 2: Automatski flajteri (Automated Testing / Bots)

Za vece projekte, manualno testiranje nije dovoljno. Koristite Gauntlet (UE5 automation framework) ili sopstvene automation skripte da bots prolaze kroz sve nivoe i interaguju sa svim objektima:

// Primer automatizovanog PSO prikupljanja
void UPSOCollectionTest::RunTest()
{
    // Ucitaj svaki level u projektu
    TArray<FString> AllMaps;
    FPackageName::FindPackagesInDirectory(AllMaps, TEXT("/Game/Maps/"));
    
    for (const FString& MapPath : AllMaps)
    {
        // Ucitaj mapu
        UGameplayStatics::OpenLevel(this, *MapPath);
        
        // Sacekaj da se sve ucita i renderuje
        FPlatformProcess::Sleep(10.0f);
        
        // Rotiraj kameru da pokrije sve pravce
        for (int32 Angle = 0; Angle < 360; Angle += 15)
        {
            RotateCamera(Angle);
            // Renderuj nekoliko frame-ova da se generisu svi PSO-ovi
            RenderFrames(5);
        }
    }
    
    // Sacuvaj prikupljene PSO-ove
    SaveCollectedPSOs();
}

Metod 3: PSO prikupljanje tokom QA testiranja

Najbolji pristup kombinuje automatsko i manualno testiranje:

  1. Automatski botovi prolaze kroz sve nivoe i generisu "baseline" PSO cache
  2. QA testeri igraju igru normalno sa ukljucenim PSO logiranjem
  3. PSO logovi se sakupljaju sa svih testera i spajaju u jedan master cache
  4. Master cache se pakuje sa igrom

38.2.4 Bundled PSO Caches

Bundled PSO cache je fajl koji se isporucuje uz igru i sadrzi pre-kompajlirane PSO-ove. Kada igra startuje, ona ucitava ovaj cache i pre-kreira sve PSO-ove u pozadini (ili tokom loading screen-a).

Kreiranje bundled PSO cache-a:

# Korak 1: Prikupite PSO logove iz testiranja
# (automatski se generisu u Saved/CollectedPSOs/)

# Korak 2: Spojite sve PSO logove u jedan fajl
RunUAT.bat BuildCookRun ^
    -project="MyProject.uproject" ^
    -platform=Win64 ^
    -ShaderPipelineCacheTools ^
    -BuildPSOCache

# Korak 3: Rezultujuci fajl se nalazi u:
# [Project]/Build/[Platform]/PipelineCaches/

U igri, PSO cache se ucitava automatski prilikom startovanja:

// Engine interno radi ovo (ne morate rucno)
void FShaderPipelineCache::Initialize()
{
    // Ucitaj bundled cache
    FString CachePath = FPaths::ProjectContentDir() / TEXT("PipelineCaches");
    LoadPipelineCache(CachePath);
    
    // Pre-kompajliraj PSO-ove u pozadini
    PrecompilePSOs(BackgroundPriority);
}

Konfiguracija ponasanja PSO cache-a:

; DefaultEngine.ini

[ConsoleVariables]
; Koliko PSO-ova da se kompajlira po frame-u tokom ucitavanja
r.ShaderPipelineCache.BatchSize=50

; Da li da se prikaze progress bar tokom PSO kompilacije
r.ShaderPipelineCache.ShowProgressBar=1

; Maksimalno vreme po frame-u posveceno PSO kompilaciji (u ms)
r.ShaderPipelineCache.BatchTime=2.0

; Da li da se koristi background thread za PSO kompilaciju
r.ShaderPipelineCache.BackgroundBatchSize=16

38.2.5 Runtime PSO Precaching

Cak i sa bundled cache-om, postoje situacije gde se pojavi PSO koji nije u cache-u (novi DLC sadrzaj, user-generated content, itd.). UE5 5.4+ ima sistem za runtime PSO precaching koji pokusava da predvidi koji ce PSO-ovi biti potrebni i kreira ih unapred.

Prediktivni precaching radi tako sto:

  1. Kada se objekat ucita u memoriju (ali pre nego sto postane vidljiv), engine analizira njegove materijale
  2. Na osnovu materijala i trenutnog render stanja, engine predvidja koji PSO-ovi ce biti potrebni
  3. Ti PSO-ovi se kreiraju u pozadini, pre nego sto objekat postane vidljiv
; Ukljucite runtime precaching
r.PSOPrecaching=1

; Podesite agresivnost precaching-a
; 0 = samo za vidljive objekte
; 1 = za objekte u streaming distanci
; 2 = za sve ucitane objekte
r.PSOPrecache.Mode=1

; Broj PSO-ova za precache po frame-u
r.PSOPrecache.MaxPerFrame=10

Nivoi PSO precaching strategije:

Nivo 0: Bez precaching-a
         -> Najlosije korisnicko iskustvo, cesti stutter-i

Nivo 1: Bundled PSO cache
         -> Pokriva 90-95% slucajeva
         -> Preostali PSO-ovi se kompajliraju runtime

Nivo 2: Bundled cache + Runtime precaching
         -> Pokriva 98-99% slucajeva
         -> Retki, kratki stutter-i

Nivo 3: Bundled cache + Runtime precaching + Background compilation
         -> Pokriva 99.9%+ slucajeva
         -> Prakticno nema stuttering-a
         -> Zahteva vise memorije i CPU vremena

38.3 Cook Process -- Pretvaranje Editor Asset-a u Platformski Optimizovane Pakete

Cooking (kuvanje) je proces konvertovanja vasih editor asset-a u format koji je optimizovan za ciljnu platformu. To je srce packaging procesa i jedno od najkompleksnijih sistema u Unreal Engine-u.

38.3.1 Sta je Cooking?

U Unreal editoru, asset-i su sacuvani u generickom formatu (.uasset, .umap) koji sadrzi sve informacije potrebne za editovanje: meta-podatke, editor-only podatke, preview slike, itd. Ovaj format je veliki i spor za runtime ucitavanje.

Cooking transformise ove asset-e u platformski optimizovane pakete:

EDITOR ASSETS                          COOKED ASSETS
+---------------------------+          +---------------------------+
| MyTexture.uasset          |          | MyTexture.uasset          |
| - Source PNG/TGA (32MB)   |   COOK   | - BC7 compressed (4MB)    |
| - Import settings         |  ------> | - Generated mip-maps      |
| - Editor metadata         |          | - Platform-specific header|
| - Thumbnail               |          | (Nema editor metadata)    |
+---------------------------+          +---------------------------+

| MyMesh.uasset             |          | MyMesh.uasset             |
| - Full LOD chain          |   COOK   | - Stripped LODs (mobile)  |
| - Nanite source data      |  ------> | - Optimized vertex buffer |
| - Collision data          |          | - Packed indices          |
| - Editor preview mesh     |          | (Platform-optimized)      |
+---------------------------+          +---------------------------+

| MyBlueprint.uasset        |          | MyBlueprint.uasset        |
| - Blueprint graph nodes   |   COOK   | - Nativized C++ (opciono) |
| - Editor comments         |  ------> | - Bytecode only           |
| - Breakpoint info         |          | (Nema editor podataka)    |
+---------------------------+          +---------------------------+

38.3.2 Content Cooking Pipeline

Cooking pipeline se sastoji od vise faza, svaka sa specificnim zadatkom:

Faza 1: Asset Discovery

Engine skenira projekat i pravi listu svih asset-a koji treba da budu kuvani. Ovo ukljucuje:

; DefaultGame.ini
[/Script/UnrealEd.ProjectPackagingSettings]
; Direktorijumi koji se uvek kuvaju
+DirectoriesToAlwaysCook=(Path="/Game/Core")
+DirectoriesToAlwaysCook=(Path="/Game/UI")

; Mape koje se kuvaju
+MapsToCook=(FilePath="/Game/Maps/MainMenu")
+MapsToCook=(FilePath="/Game/Maps/Level01")

Faza 2: Dependency Resolution

Za svaki asset, engine resolvuje sve zavisnosti. Ako Level01 koristi M_Rock materijal, koji koristi T_Rock_BaseColor teksturu -- sve tri ce biti kuvane.

Ovo je cest izvor problema! Ako imate "sirocice" (orphaned assets) -- asset-e koji su referencovani ali ne postoje, ili cirkularne zavisnosti -- cooking ce prijaviti gresku.

Koristite Reference Viewer u editoru (desni klik na asset > Reference Viewer) da vidite dependency graf.

Faza 3: Platform Conversion

Svaki tip asset-a ima svoj conversion process:

Teksture:

Meshevi:

Animacije:

Audio:

Blueprinti:

Faza 4: Shader Compilation

Svi shaderi se kompajliraju za ciljnu platformu (detaljno opisano u sekciji 38.1).

Faza 5: Packaging

Kuvani asset-i se pakuju u .pak fajlove (videti sekciju 38.7 za detalje o pak fajlovima).

38.3.3 Platform-Specific Data Formats

Svaka platforma ima svoje optimalne formate podataka. Evo pregleda najvaznijih razlika:

+------------------+----------+----------+----------+----------+
| Tip podataka     | PC (DX12)| PS5      | Xbox SX  | Mobile   |
+------------------+----------+----------+----------+----------+
| Teksture         | BC7/BC5  | GNF      | BCn      | ASTC     |
| Shader bytecode  | DXIL     | SB       | DXIL     | SPIR-V   |
| Audio            | OGG/Opus | ATRAC9   | XMA2     | AAC/Opus |
| Video            | VP9/H264 | H265     | H264     | H264     |
| Mesh format      | Nanite   | Nanite   | Nanite   | Trad.LOD |
| Vertex packing   | 32-bit   | 32-bit   | 32-bit   | 16-bit   |
+------------------+----------+----------+----------+----------+

38.3.4 Iterative Cooking vs Full Cook

Full Cook znaci kuvanje svih asset-a od nule. Ovo je neophodno za finalne buildove, ali moze trajati satima za velike projekte.

Iterative Cooking (inkrementalno kuvanje) kuva samo asset-e koji su se promenili od poslednjeg kuvanja. Ovo je mnogo brze za svakodnevni razvoj.

# Full cook (iz komandne linije)
RunUAT.bat BuildCookRun ^
    -project="MyProject.uproject" ^
    -platform=Win64 ^
    -clientconfig=Shipping ^
    -cook ^
    -allmaps ^
    -pak ^
    -stage ^
    -archive

# Iterative cook (dodajte -iterate flag)
RunUAT.bat BuildCookRun ^
    -project="MyProject.uproject" ^
    -platform=Win64 ^
    -clientconfig=Shipping ^
    -cook ^
    -iterate ^
    -allmaps ^
    -pak ^
    -stage ^
    -archive

Poredjenje vremena kuvanja (tipican srednji projekat):

Scenario Full Cook Iterative Cook
Prvo kuvanje 45 min N/A
Promena jedne teksture 45 min 30 sec
Promena jednog materijala 45 min 2 min
Promena jednog Blueprint-a 45 min 1 min
Promena jedne mape 45 min 5 min
Dodavanje novog nivoa 45 min 10 min

Upozorenje: Iterative cooking moze ponekad proizvesti nekonzistentne rezultate ako se zavisnosti ne rezolvuju pravilno. Uvek radite full cook za finalne buildove koji idu igracima!

38.3.5 Cook Times i Optimizacija

Vreme kuvanja moze biti ozbiljan bottleneck u produkciji. Evo strategija za optimizaciju:

1. Koristite SSD/NVMe diskove

Cooking je I/O intenzivan proces. Razlika izmedju HDD i NVMe diska moze biti 3-5x u vremenu kuvanja.

Isti projekat, razliciti diskovi:
HDD (7200 RPM):     90 minuta
SATA SSD:           35 minuta
NVMe SSD:           20 minuta
NVMe Gen4 SSD:      15 minuta

2. Vise RAM-a = manje swapping-a

Cooking moze koristiti ogromne kolicine memorije, pogotovo za velike projekte:

Preporuceni RAM po velicini projekta:
Mali projekat (< 5GB):     16 GB RAM
Srednji projekat (5-20GB): 32 GB RAM
Veliki projekat (20-50GB): 64 GB RAM
AAA projekat (50GB+):      128 GB RAM

3. Iskljucite nepotrebne platforme

Ako kuvate samo za Windows, nema potrebe da kompajlirate shadere za Vulkan, Metal, itd.

; DefaultEngine.ini
[/Script/WindowsTargetPlatform.WindowsTargetSettings]
DefaultGraphicsRHI=DirectX12

; Ili u Project Settings > Platforms > Windows
; Targeted RHIs: DirectX 12
; (Iskljucite DirectX 11 i Vulkan ako ih ne ciljate)

4. DDC warming

Pre kuvanja, "zagrejte" DDC pokretanjem editora sa -run=DerivedDataCache -fill:

UnrealEditor.exe MyProject.uproject -run=DerivedDataCache -fill

5. Paralelno kuvanje

UE5 podrzava paralelno kuvanje asset-a koristeci vise jezgara CPU-a:

; Broj paralelnih cooking procesa
; Podrazumevano je (BrojJezgara - 1)
s.AsyncLoadingThreadCount=8

38.4 Target Platform Differences -- Razliciti Svetovi, Razlicita Pravila

Svaka platforma na kojoj mozete pokrenuti UE5 igru ima svoje specificnosti, ogranicenja, i prednosti. Razumevanje ovih razlika je kljucno za isporuku kvalitetnog proizvoda.

38.4.1 PC: Sirok Raspon Hardvera

PC je najizazovnija platforma jer morate podrzati ogroman raspon hardvera -- od integrisanih Intel/AMD GPU-a do najnovijih NVIDIA RTX 5090 kartica.

Graficki API-ji

Na PC-u imate izbor izmedju vise grafickih API-ja:

API Prednosti Mane
DirectX 11 Siroka kompatibilnost, stabilan Stariji, nema ray tracing
DirectX 12 Visoke performanse, RT podrska Zahteva Windows 10+
Vulkan Cross-platform, Linux podrska Duza shader kompilacija

Preporuka za vecinu projekata: Ciljajte DirectX 12 kao primarni API, sa DirectX 11 kao fallback za stariji hardver. Vulkan koristite samo ako ciljate Linux.

Scalability

PC igre moraju imati sistem za prilagodjavanje kvaliteta grafike razlicitom hardveru. UE5 ima ugrdjeni sistem skalabilnosti koji cemo detaljno objasniti u sekciji 38.5.

Minimum i preporucene specifikacije

Za svaku PC igru morate definisati minimum i preporucene sistemske zahteve:

PRIMER SPECIFIKACIJA:

Minimum:
- OS: Windows 10 64-bit
- CPU: Intel Core i5-8400 / AMD Ryzen 5 2600
- RAM: 8 GB
- GPU: NVIDIA GTX 1060 6GB / AMD RX 580 8GB
- Storage: 50 GB SSD
- DirectX: Version 11

Preporuceno:
- OS: Windows 11 64-bit
- CPU: Intel Core i7-12700K / AMD Ryzen 7 5800X
- RAM: 16 GB
- GPU: NVIDIA RTX 3070 / AMD RX 6800 XT
- Storage: 50 GB NVMe SSD
- DirectX: Version 12

Posebna razmatranja za PC

38.4.2 Konzole (PS5, Xbox Series X|S): Fiksan Hardver, Garantovane Performanse

Konzole nude luksuz fiksnog hardvera -- znate tacno sta svaki igrac ima, i mozete optimizovati za taj specifican hardver.

PlayStation 5

PS5 specifikacije (relevantne za razvoj):
- CPU: AMD Zen 2, 8 cores @ 3.5GHz (variable)
- GPU: RDNA 2, 10.28 TFLOPS, 36 CUs
- RAM: 16GB GDDR6 (unified)
- Storage: 825GB custom NVMe SSD (5.5GB/s raw, 8-9GB/s compressed)
- Graphics API: AGC (proprietary, baziran na GNM/GNMX)

PS5 ima nekoliko jedinstvenih feature-a:

Xbox Series X|S

Xbox Series X specifikacije:
- CPU: AMD Zen 2, 8 cores @ 3.8GHz (3.6GHz with SMT)
- GPU: RDNA 2, 12 TFLOPS, 52 CUs
- RAM: 16GB GDDR6 (10GB @ 560GB/s + 6GB @ 336GB/s)
- Storage: 1TB custom NVMe SSD (2.4GB/s raw, 4.8GB/s compressed)
- Graphics API: DirectX 12 (GDK varijanta)

Xbox Series S specifikacije:
- GPU: RDNA 2, 4 TFLOPS, 20 CUs
- RAM: 10GB GDDR6
- Target: 1440p

Kljucna razlika: Xbox Series S ima znacajno slabiju grafiku od Series X. Morate odrzavati dva profila performansi: jedan za X (4K, visoki detalji) i jedan za S (1440p ili nize, smanjeni detalji). Ovo se postize kroz Device Profiles (videti sekciju 38.5).

Zajednicke karakteristike konzolnog razvoja

38.4.3 Mobile (iOS, Android): Ogranicenja Na Svakom Koraku

Mobilni razvoj je, iskreno, najizazovniji deo UE5 game dev-a. Radite sa ozbiljnim ogranicenjima na svakom frontu.

GPU ogranicenja

Mobilni GPU-ovi su drasticno slabiji od desktop GPU-a:

Poredjenje GPU snage (approx TFLOPS):

NVIDIA RTX 4090:        82.6 TFLOPS
PS5:                    10.3 TFLOPS
Apple A17 Pro (iPhone): ~2.1 TFLOPS
Qualcomm Adreno 740:    ~1.5 TFLOPS
Mali-G720:              ~1.0 TFLOPS
Stariji mid-range mob:  ~0.3 TFLOPS

Dakle, najjaci mobilni GPU je ~40x slabiji od najjaceg desktop GPU-a!

Posledice za rendering:

Memorijska ogranicenja

Tipicna dostupna memorija za igru:

PC (16GB RAM):          ~12 GB za igru
PS5 (16GB unified):     ~12 GB za igru
iPhone 15 Pro (8GB):    ~4 GB za igru (iOS ubija aplikacije koje koriste vise)
Samsung Galaxy S24 (8GB): ~3-4 GB za igru
Budget Android (4GB):   ~1.5-2 GB za igru

Strategije za upravljanje memorijom na mobilnom:

Thermal Throttling

Ovo je problem unikatan za mobilne uredjaje. Telefoni nemaju aktivno hladjenje (ventilatore), tako da se nakon nekoliko minuta intenzivnog igranja procesor pregreva i smanjuje brzinu da bi se ohladio:

Tipicno ponasanje thermal throttling-a:

Vreme:     0 min    5 min    10 min   15 min   20 min
GPU Clock: 100%     100%     80%      65%      55%
FPS:       60       60       48       39       33

Igrac pocne sa 60 FPS i posle 20 minuta ima 33 FPS!

Strategije za borbu sa thermal throttling-om:

  1. Ne koristite 100% GPU kapaciteta: Ciljajte 70-80% GPU iskoriscenosti
  2. Dynamic resolution: Automatski smanjujte rezoluciju renderovanja kada FPS padne
  3. Adaptive quality: Smanjujte kvalitet efekata kada se detektuje throttling
  4. Frame rate cap: Zakljucajte na 30 FPS umesto 60 FPS da biste smanjili zagrevanje
; Podesavanja za mobile u DefaultDeviceProfiles.ini
[Android DeviceProfile]
+CVars=r.MobileContentScaleFactor=1.5
+CVars=r.Mobile.ForwardShading=1
+CVars=r.Mobile.MaxFrameRate=30
+CVars=r.Mobile.DynamicResolution=1
+CVars=r.Mobile.DynamicResolution.MinScreenPercentage=50

ASTC teksture na mobilnom

ASTC (Adaptive Scalable Texture Compression) je standardni format za kompresiju tekstura na modernim mobilnim uredjajima. Podrzavaju ga svi iOS uredjaji (od iPhone 6) i vecina modernih Android uredjaja.

ASTC blok velicine i kvalitet:

ASTC 4x4:   8 bpp   - Najbolji kvalitet, najveca velicina
ASTC 5x4:   6.4 bpp
ASTC 5x5:   5.12 bpp
ASTC 6x5:   4.27 bpp
ASTC 6x6:   3.56 bpp - Dobar kompromis kvalitet/velicina
ASTC 8x5:   3.2 bpp
ASTC 8x6:   2.67 bpp
ASTC 8x8:   2 bpp    - Nizak kvalitet, mala velicina
ASTC 10x10: 1.28 bpp - Najnizi kvalitet
ASTC 12x12: 0.89 bpp - Za pozadine i manje vazne teksture

38.4.4 Razlike u Sposobnostima Izmedju Platforma

Evo sveobuhvatnog pregleda sta svaka platforma podrzava:

+---------------------------+------+------+------+--------+--------+
| Feature                   | PC   | PS5  | XSX  | iOS    | Android|
|                           | (Hi) |      |      |        |        |
+---------------------------+------+------+------+--------+--------+
| Ray Tracing (HW)         | DA   | DA   | DA   | DA*    | NE     |
| Nanite                    | DA   | DA   | DA   | NE     | NE     |
| Lumen (HW RT)            | DA   | DA   | DA   | NE     | NE     |
| Lumen (SW)               | DA   | DA   | DA   | NE     | NE     |
| Virtual Shadow Maps       | DA   | DA   | DA   | NE     | NE     |
| Mesh Shaders              | DA*  | DA   | DA   | NE     | NE     |
| Compute Shaders           | DA   | DA   | DA   | DA     | DA*    |
| MSAA                      | DA   | DA   | DA   | DA     | DA     |
| TSR (Temporal SR)         | DA   | DA   | DA   | Ogrn.  | Ogrn.  |
| Forward Rendering         | DA   | DA   | DA   | DA     | DA     |
| Deferred Rendering        | DA   | DA   | DA   | NE     | NE     |
| World Partition            | DA   | DA   | DA   | DA     | DA     |
| Max Texture Size          | 16K  | 16K  | 16K  | 8K     | 4K-8K  |
| HDR Output                | DA   | DA   | DA   | DA*    | DA*    |
+---------------------------+------+------+------+--------+--------+

* = Zavisi od konkretnog hardvera/modela

38.5 Scalability Settings -- Prilagodjavanje Svakom Hardveru

UE5 ima sofisticiran sistem skalabilnosti koji omogucava da se kvalitet renderovanja automatski prilagodi mogucnostima hardvera. Ovo je kriticno za PC platformu gde je raspon hardvera ogroman, ali koristan je i za razlikovanje izmedju Xbox Series X i S, ili izmedju razlicitih generacija mobilnih uredjaja.

38.5.1 Kako UE5 Upravlja Quality Level-ima

UE5 definise pet standardnih quality level-a:

Level Indeks Opis
Low 0 Za najslabiji hardver. Minimum vizuelnog kvaliteta, maksimalne performanse.
Medium 1 Za stariji ili budget hardver. Pristojne vizuelije sa dobrim performansama.
High 2 Za srednji hardver. Dobar balans kvaliteta i performansi.
Epic 3 Za jaci hardver. Blizu maksimalnog kvaliteta. Podrazumevano podesavanje.
Cinematic 4 Za najjaci hardver. Maksimalan kvalitet, koristi se i za offline renderovanje.

Svaki quality level kontrolise grupu podesavanja koja se primenjuju zajedno. Igraci mogu birati izmedju ovih level-a u meniju podesavanja, ili engine moze automatski detektovati optimalan level na osnovu hardvera.

38.5.2 sg.* Console Variables

Skalabilnost se kontrolise preko sg.* (scalability group) konzolnih promenljivih. Svaka grupa kontrolise set povezanih podesavanja:

; Scalability Groups i njihov uticaj

sg.ViewDistanceQuality=3      ; Udaljenost na kojoj se objekti renderuju
sg.AntiAliasingQuality=3      ; Kvalitet anti-aliasing-a
sg.ShadowQuality=3            ; Kvalitet senki (rezolucija shadow mape, kaskade)
sg.GlobalIlluminationQuality=3; Kvalitet globalnog osvetljenja (Lumen)
sg.ReflectionQuality=3        ; Kvalitet refleksija (SSR, Lumen reflections)
sg.PostProcessQuality=3       ; Kvalitet post-process efekata
sg.TextureQuality=3           ; Kvalitet tekstura (mip level bias)
sg.EffectsQuality=3           ; Kvalitet efekata (cestica, itd.)
sg.FoliageQuality=3           ; Kvalitet i gustina vegetacije
sg.ShadingQuality=3           ; Kvalitet shading-a (shader kompleksnost)
sg.LandscapeQuality=3         ; Kvalitet terena (LOD, tessellation)

Vrednosti idu od 0 (Low) do 4 (Cinematic). Mozete ih postaviti koristeci konzolu (tipka ~), iz Blueprint-a, ili programski:

// Iz C++ koda
#include "Scalability.h"

// Postavi sve na High
Scalability::FQualityLevels QualityLevels;
QualityLevels.SetFromSingleQualityLevel(2); // 2 = High
Scalability::SetQualityLevels(QualityLevels);

// Ili individualno
QualityLevels.ShadowQuality = 3;    // Epic shadows
QualityLevels.TextureQuality = 1;   // Medium textures
Scalability::SetQualityLevels(QualityLevels);

38.5.3 Sta Svaki Quality Level Konkretno Menja

Pogledajmo sta se desava kada menjate neke od najvaznijih scalability grupa:

Shadow Quality

; [Low] sg.ShadowQuality=0
r.Shadow.MaxResolution=512
r.Shadow.MaxCSMResolution=512
r.Shadow.CSM.MaxCascades=1
r.Shadow.RadiusThreshold=0.06
r.Shadow.DistanceScale=0.6
r.Shadow.CSM.TransitionScale=0
r.Shadow.VirtualShadowMaps=0

; [Epic] sg.ShadowQuality=3
r.Shadow.MaxResolution=2048
r.Shadow.MaxCSMResolution=2048
r.Shadow.CSM.MaxCascades=10
r.Shadow.RadiusThreshold=0.01
r.Shadow.DistanceScale=1.0
r.Shadow.CSM.TransitionScale=1.0
r.Shadow.VirtualShadowMaps=1

Razlika: Na Low, imate jednu shadow cascade sa 512px rezolucijom i bez Virtual Shadow Maps. Na Epic, imate 10 kaskada sa 2048px rezolucijom i VSM ukljucen. Vizuelna razlika je dramticna.

Texture Quality

; [Low] sg.TextureQuality=0
r.Streaming.MipBias=2.5        ; Koristi mip-mape 2.5 nivoa nize
r.MaxAnisotropy=0              ; Bez anizotropnog filtriranja
r.Streaming.PoolSize=200       ; 200MB texture streaming pool

; [Epic] sg.TextureQuality=3
r.Streaming.MipBias=0          ; Koristi pune teksture
r.MaxAnisotropy=8              ; 8x anizotropno filtriranje
r.Streaming.PoolSize=1000      ; 1000MB texture streaming pool

View Distance

; [Low] sg.ViewDistanceQuality=0
r.SkeletalMeshLODBias=2        ; Forsira nizi LOD za skeletal mesheve
r.ViewDistanceScale=0.4        ; 40% od podrazumevane view distance

; [Epic] sg.ViewDistanceQuality=3
r.SkeletalMeshLODBias=0        ; Koristi najvisi LOD
r.ViewDistanceScale=1.0        ; 100% view distance

38.5.4 Konfiguracija Scalability-ja

Scalability podesavanja se definisu u BaseScalability.ini (engine default) i mogu se pregaziti u vasem projektu u DefaultScalability.ini:

; DefaultScalability.ini - Primer custom podesavanja

[ShadowQuality@0]
; Low shadow settings
r.Shadow.MaxResolution=256
r.Shadow.VirtualShadowMaps=0
r.ContactShadows=0

[ShadowQuality@1]
; Medium shadow settings
r.Shadow.MaxResolution=512
r.Shadow.VirtualShadowMaps=0
r.ContactShadows=1

[ShadowQuality@2]
; High shadow settings
r.Shadow.MaxResolution=1024
r.Shadow.VirtualShadowMaps=1
r.ContactShadows=1

[ShadowQuality@3]
; Epic shadow settings
r.Shadow.MaxResolution=2048
r.Shadow.VirtualShadowMaps=1
r.ContactShadows=1

[ShadowQuality@4]
; Cinematic shadow settings
r.Shadow.MaxResolution=4096
r.Shadow.VirtualShadowMaps=1
r.ContactShadows=1
r.Shadow.CSM.MaxCascades=14

38.5.5 Device Profiles

Device Profiles su mehanizam za automatsko prilagodjavanje podesavanja specificnom hardveru. Umesto da igrac sam bira quality level, igra moze automatski detektovati hardver i primeniti optimalna podesavanja.

Device profili se definisu u DefaultDeviceProfiles.ini:

; DefaultDeviceProfiles.ini

; --- PC Profili ---

[Windows DeviceProfile]
DeviceType=Desktop
BaseProfileName=

[WindowsLow DeviceProfile]
DeviceType=Desktop
BaseProfileName=Windows
+CVars=sg.ShadowQuality=0
+CVars=sg.TextureQuality=0
+CVars=sg.ViewDistanceQuality=0

[WindowsHigh DeviceProfile]
DeviceType=Desktop
BaseProfileName=Windows
+CVars=sg.ShadowQuality=3
+CVars=sg.TextureQuality=3
+CVars=sg.ViewDistanceQuality=3

; --- Konzolni Profili ---

[PS5 DeviceProfile]
DeviceType=Console
+CVars=r.Shadow.VirtualShadowMaps=1
+CVars=r.RayTracing=1
+CVars=r.Nanite=1
+CVars=r.Lumen.Enabled=1
+CVars=r.ScreenPercentage=100

[XboxSeriesX DeviceProfile]
DeviceType=Console
+CVars=r.Shadow.VirtualShadowMaps=1
+CVars=r.RayTracing=1
+CVars=r.Nanite=1
+CVars=r.Lumen.Enabled=1

[XboxSeriesS DeviceProfile]
DeviceType=Console
+CVars=r.Shadow.VirtualShadowMaps=0
+CVars=r.RayTracing=0
+CVars=r.Nanite=1
+CVars=r.Lumen.Enabled=0
+CVars=r.Lumen.Software=1
+CVars=r.ScreenPercentage=66

; --- Mobilni Profili ---

[IOS DeviceProfile]
DeviceType=Mobile
+CVars=r.Mobile.ForwardShading=1
+CVars=sg.ShadowQuality=1
+CVars=sg.TextureQuality=1

[Android_Adreno7xx DeviceProfile]
DeviceType=Mobile
BaseProfileName=Android
+CVars=r.Mobile.ForwardShading=1
+CVars=sg.ShadowQuality=2
+CVars=sg.TextureQuality=2
+CVars=r.MobileContentScaleFactor=2.0

[Android_Mali_G7xx DeviceProfile]
DeviceType=Mobile
BaseProfileName=Android
+CVars=r.Mobile.ForwardShading=1
+CVars=sg.ShadowQuality=1
+CVars=sg.TextureQuality=1
+CVars=r.MobileContentScaleFactor=1.5

[Android_Low DeviceProfile]
DeviceType=Mobile
BaseProfileName=Android
+CVars=r.Mobile.ForwardShading=1
+CVars=sg.ShadowQuality=0
+CVars=sg.TextureQuality=0
+CVars=r.MobileContentScaleFactor=1.0

Engine automatski bira profil na osnovu detektovanog hardvera. Za Android, ovo se bazira na GPU model-u (Adreno, Mali, PowerVR), a za iOS na modelu uredjaja (iPhone 12, iPad Pro, itd.).

Mozete i programski birati profil:

// Provera trenutnog device profila
FString CurrentProfile = UDeviceProfileManager::Get()
    .GetActiveProfile()->GetName();

// Aktivacija specificnog profila
UDeviceProfileManager::Get()
    .SetActiveDeviceProfile(TEXT("WindowsHigh"));

38.6 Platform-Specific Considerations -- Detalji Koji Cine Razliku

38.6.1 Memory Budgets Per Platform

Jedna od najkritcnijih razlika izmedju platforma je koliko memorije imate na raspolaganju. Evo realisticnih budzeta:

MEMORY BUDGETS (approx, za igru u toku rada):

+----------------------+--------+--------+--------+--------+--------+
| Kategorija           | PC     | PS5    | XSX    | XSS    | Mobile |
|                      | (16GB) |        |        |        | (6GB)  |
+----------------------+--------+--------+--------+--------+--------+
| OS / System          | 3-4 GB | 3 GB   | 2.5 GB | 2.5 GB | 2-3 GB |
| Engine Core          | 1 GB   | 1 GB   | 1 GB   | 0.7 GB | 0.5 GB |
| Texture Streaming    | 4 GB   | 4 GB   | 4 GB   | 2 GB   | 0.5 GB |
| Mesh Data (Nanite)   | 2 GB   | 2 GB   | 2 GB   | 1 GB   | N/A    |
| Audio                | 0.5 GB | 0.5 GB | 0.5 GB | 0.3 GB | 0.1 GB |
| Animation            | 0.5 GB | 0.5 GB | 0.5 GB | 0.3 GB | 0.2 GB |
| Physics              | 0.3 GB | 0.3 GB | 0.3 GB | 0.2 GB | 0.1 GB |
| Gameplay/Blueprints  | 0.5 GB | 0.5 GB | 0.5 GB | 0.3 GB | 0.2 GB |
| GPU Buffers          | 2 GB   | 2 GB   | 2 GB   | 1 GB   | 0.3 GB |
| Slobodno / Buffer    | 1.7 GB | 2.2 GB | 2.7 GB | 1.7 GB | 0.1 GB |
+----------------------+--------+--------+--------+--------+--------+
| UKUPNO               | ~16 GB | ~16 GB | ~16 GB | ~10 GB | ~4 GB  |
+----------------------+--------+--------+--------+--------+--------+

NAPOMENA: Ovo su okvirne vrednosti. Vaš projekat ce imati drugacije raspodele.

Kljucne lekcije:

  1. Na mobilnom nemate mesta za greske. Sa samo 0.1 GB slobodnog prostora, svako curenje memorije (memory leak) ce brzo dovesti do pada aplikacije.

  2. Konzole su predvidljive -- uvek imate tacno poznatu kolicinu memorije. Koristite to kao prednost za optimizaciju.

  3. PC je nepredvidljiv -- igrac sa 8GB RAM-a ce imati drasticno drugacije iskustvo od igraca sa 32GB. Koristite texture streaming agresivno.

Alati za pracenje memorije

// Konzolna komanda za pregled memorije
// U editoru: ~ pa kucajte:
memreport -full

// Dobijate detaljno razlaganje:
// - Ukupna fizicka memorija
// - Memorija po kategoriji (textures, meshes, audio, etc.)
// - Top 20 najvecih alokacija
// - Memory pool statistike

Takodje, koristite stat memory za real-time prikaz memorije ili Unreal Insights za detaljnu analizu.

38.6.2 GPU Capabilities

Razliciti GPU-ovi podrzavaju razlicite feature-e. Evo kako da proverite i prilagodite se:

// Provera GPU mogucnosti u runtime-u

// Da li je ray tracing podrzan?
bool bRayTracingSupported = GRHISupportsRayTracing;

// Shader Model nivo
ERHIFeatureLevel::Type FeatureLevel = GMaxRHIFeatureLevel;
// SM5 = DirectX 11 nivo
// SM6 = DirectX 12 sa novim feature-ima

// Da li je compute shader podrzan?
bool bComputeSupported = RHISupportsComputeShaders(GMaxRHIShaderPlatform);

// Koliko VRAM-a ima GPU?
int64 TotalVRAM = GRHIAdapterInternalDriverVersion;
FTextureMemoryStats TexMemStats;
RHIGetTextureMemoryStats(TexMemStats);
int64 DedicatedVRAM = TexMemStats.DedicatedVideoMemory;

Adaptivni kvalitet na osnovu GPU-a:

void AMyGameMode::AdjustQualityForGPU()
{
    FTextureMemoryStats TexMemStats;
    RHIGetTextureMemoryStats(TexMemStats);
    int64 VRAM_MB = TexMemStats.DedicatedVideoMemory / (1024 * 1024);
    
    Scalability::FQualityLevels Quality;
    
    if (VRAM_MB >= 8192)        // 8GB+ VRAM
    {
        Quality.SetFromSingleQualityLevel(3); // Epic
    }
    else if (VRAM_MB >= 4096)   // 4-8GB VRAM
    {
        Quality.SetFromSingleQualityLevel(2); // High
    }
    else if (VRAM_MB >= 2048)   // 2-4GB VRAM
    {
        Quality.SetFromSingleQualityLevel(1); // Medium
    }
    else                        // < 2GB VRAM
    {
        Quality.SetFromSingleQualityLevel(0); // Low
    }
    
    Scalability::SetQualityLevels(Quality);
}

38.6.3 Texture Format Support

Razlicite platforme podrzavaju razlicite formate kompresije tekstura:

+------------------+------+------+------+------+---------+
| Format           | PC   | PS5  | XSX  | iOS  | Android |
+------------------+------+------+------+------+---------+
| BC1 (DXT1)       | DA   | DA   | DA   | NE   | NE*     |
| BC3 (DXT5)       | DA   | DA   | DA   | NE   | NE*     |
| BC4              | DA   | DA   | DA   | NE   | NE*     |
| BC5              | DA   | DA   | DA   | NE   | NE*     |
| BC6H (HDR)       | DA   | DA   | DA   | NE   | NE*     |
| BC7              | DA   | DA   | DA   | NE   | NE*     |
| ASTC             | NE   | DA   | NE   | DA   | DA      |
| ETC2             | NE   | NE   | NE   | DA   | DA      |
| PVRTC             | NE   | NE   | NE   | DA** | NE      |
+------------------+------+------+------+------+---------+

*  Android sa Vulkan moze emulirati BCn kompresiju, ali nije nativno
** PVRTC je zastareo od iOS 17; koristi se ASTC umesto njega

UE5 automatski bira pravi format tokom cooking-a na osnovu ciljne platforme. Vi samo treba da se pobrinete da vase source teksture budu u visokom kvalitetu (nekompresovane ili sa minimalnom kompresijom), a engine ce se pobrinuti za ostalo.

38.6.4 Shader Model Support

+------------------+------+------+------+--------+---------+
| Shader Model     | PC   | PS5  | XSX  | iOS    | Android |
+------------------+------+------+------+--------+---------+
| SM 5.0           | DA   | DA   | DA   | DA     | DA*     |
| SM 5.1           | DA   | DA   | DA   | DA     | NE      |
| SM 6.0           | DA   | DA   | DA   | NE     | NE      |
| SM 6.3 (RT)      | DA*  | DA   | DA   | DA*    | NE      |
| SM 6.5 (Mesh)    | DA*  | DA   | DA   | NE     | NE      |
| SM 6.6           | DA*  | DA   | DA   | NE     | NE      |
+------------------+------+------+------+--------+---------+

* = Zavisi od GPU modela

38.6.5 Input Differences

Nemojte zaboraviti da razlicite platforme imaju razlicite ulazne uredjaje:

+------------------+----------+----------+----------+----------+
| Ulaz             | PC       | Konzola  | Mobile   | VR       |
+------------------+----------+----------+----------+----------+
| Tastatura/Mis    | Primarno | Opciono  | NE       | NE       |
| Gamepad          | Opciono  | Primarno | Opciono* | NE       |
| Touch screen     | NE       | NE       | Primarno | NE       |
| Motion controls  | NE       | DA (PS5) | DA       | DA       |
| VR kontrolleri   | NE       | NE       | NE       | Primarno |
+------------------+----------+----------+----------+----------+

* Bluetooth gamepad konekcija

Prakticni saveti za input:

  1. Koristite Enhanced Input System (EIS) umesto starog input sistema. EIS je dizajniran za multi-platform podrsku.

  2. Input Actions treba da budu apstraktne: Umesto "Keyboard_W", definisajte "MoveForward" akciju i mapirajte je na razlicite uredjaje.

  3. UI mora da se prilagodi: Ako igrac koristi gamepad, prikazujte gamepad ikone. Ako koristi mis i tastaturu, prikazujte tastaturne precice. Na mobilnom, prikazujte touch kontrole.

// Provera tipa ulaznog uredjaja
void AMyPlayerController::UpdateInputIcons()
{
    // Da li je poslednji input bio sa gamepada?
    if (IsGamepadConnected())
    {
        // Prikazi gamepad ikone u UI
        HUD->ShowGamepadPrompts();
    }
    else
    {
        // Prikazi tastaturne/mis ikone
        HUD->ShowKeyboardMousePrompts();
    }
}
  1. Haptic feedback: PS5 DualSense i mobilni uredjaji podrzavaju hapticki feedback. Koristite ga za imerziju, ali omogucite igracima da ga iskljuce.

38.7 Shipping Optimization -- Smanjenje Velicine i Poboljsanje Performansi

Kada je igra kuvana i testirana, poslednji korak je optimizacija za distribuciju. Velicina instalacije, vreme ucitavanja, i efikasno koriscenje memorije su kriticni za zadovoljstvo igraca.

38.7.1 Pak Files i Kompresija

UE5 pakuje sve kuvane asset-e u .pak fajlove. Pak fajl je u sustini arhiva (slicna ZIP-u) koja sadrzi sve asset-e u optimizovanom formatu za brzo ucitavanje.

Struktura tipicnog pakovanog projekta:

MyGame/
    MyGame.exe                    ; Izvrsni fajl
    MyGame-Win64-Shipping.exe     ; Alternativno ime
    Engine/
        Binaries/                 ; Engine DLL-ovi
        Content/
            Paks/
                Engine.pak        ; Engine content
    MyGame/
        Binaries/
            Win64/
                MyGame.exe
        Content/
            Paks/
                MyGame-Windows.pak    ; Glavni content pak
                MyGame-Windows_0_P.pak ; Patch pak (ako postoji)

Kompresija Pak Fajlova

UE5 podrzava nekoliko algoritama za kompresiju pak fajlova:

; DefaultGame.ini
[/Script/UnrealEd.ProjectPackagingSettings]
; Opcije kompresije:
; None       - Bez kompresije (najbrze ucitavanje, najveci fajl)
; Zlib       - Standard kompresija (dobar balans)
; Gzip       - Slicno Zlib-u
; Oodle      - Epical proprietary, najbolji kompresioni odnos i brzina
;              (preporuceno za shipping)
; LZ4        - Veoma brza dekompresija, manji kompresioni odnos

bCompressed=true
CompressionMethod=Oodle

Poredjenje kompresionih algoritama:

Testni projekat: 15 GB nekompresovan

+-----------+----------+-----------+---------------+
| Algoritam | Velicina | Odnos     | Dekompresija  |
+-----------+----------+-----------+---------------+
| None      | 15.0 GB  | 1.00x     | N/A           |
| Zlib      | 10.2 GB  | 1.47x     | 350 MB/s      |
| LZ4       | 11.5 GB  | 1.30x     | 1800 MB/s     |
| Oodle Kraken | 8.8 GB | 1.70x    | 1400 MB/s     |
| Oodle Leviathan | 8.3 GB | 1.81x | 1100 MB/s     |
+-----------+----------+-----------+---------------+

Oodle Kraken je preporucen: odlican kompresioni odnos SA brzom dekompresijom.

Napomena: Oodle kompresija je besplatna za koristcenje u UE5 projektima. Epic je licencirao Oodle od RAD Game Tools-a (koje je i kupio) za sve UE korisnike.

Enkripcija Pak Fajlova

Mozete enkriptovati pak fajlove da bi sprecili neovlascen pristup vasim asset-ima:

; DefaultCrypto.ini
[Core.Encryption]
SignPak=true
EncryptPakIndex=true
EncryptPakIniFiles=true
EncryptAssets=false  ; true za punu enkripciju (sporije ucitavanje!)

; Kljuc za enkripciju (AES-256)
; NIKADA ne hardkodujte kljuc u repo! Koristite build sistem za injectovanje.
[/Script/CryptoKeys.CryptoKeysSettings]
EncryptionKey=<vas_AES_256_kljuc_ovde>

Upozorenje: Enkripcija ne pruza apsolutnu zastitu -- odlucan haker ce uvek naci nacin da pristupi asset-ima (jer se moraju dekriptovati za renderovanje). Ali pruza razuman nivo zastite za vecinu projekata.

38.7.2 Asset Chunking za Streaming

Za velike igre, posebno open-world igre, neophodno je podeliti content u chunk-ove (delove) koji se mogu ucitavati i izbacivati iz memorije po potrebi.

Primary Asset Labels

UE5 koristi Primary Asset Labels za definisanje chunk-ova:

// Definisanje chunk-ova u Asset Manager podesavanjima
// Project Settings > Game > Asset Manager

// Ili programski:
UCLASS()
class UMyChunkLabel : public UPrimaryAssetLabel
{
    GENERATED_BODY()
    
public:
    // Chunk ID - asset-i sa istim chunk ID-jem se pakuju zajedno
    UPROPERTY(EditAnywhere, Category="Chunks")
    int32 ChunkID = 0;
    
    // Prioritet ucitavanja
    UPROPERTY(EditAnywhere, Category="Chunks")
    EPrimaryAssetCookRule CookRule = EPrimaryAssetCookRule::AlwaysCook;
};

Chunk organizacija za open-world igru

Chunk 0: Core                 (uvek ucitan)
    - Engine content
    - Main menu
    - Player character
    - Core gameplay systems
    - UI assets

Chunk 1: Area_Forest          (ucitava se po potrebi)
    - Forest environment meshevi
    - Forest materijali
    - Forest zvukovi
    - Forest NPC-jevi

Chunk 2: Area_Desert           
    - Desert environment meshevi
    - Desert materijali
    - Desert zvukovi
    
Chunk 3: Area_Snow             
    - Snow environment meshevi
    ...

Chunk 10: Cinematics_Act1     
    - Cinematicki asseti za prvi cin
    
Chunk 20: Audio_Music          
    - Muzicke numere
    
Chunk 30: Localization_SR      
    - Srpska lokalizacija
; DefaultGame.ini - Chunk podesavanje
[/Script/UnrealEd.ProjectPackagingSettings]
bGenerateChunks=true

; Chunk za svaku mapu
+ChunkAssignments=(PackageName="/Game/Maps/Forest/*", ChunkId=1)
+ChunkAssignments=(PackageName="/Game/Maps/Desert/*", ChunkId=2)
+ChunkAssignments=(PackageName="/Game/Maps/Snow/*", ChunkId=3)

Rezultat pakovanja sa chunk-ovima:

MyGame/Content/Paks/
    pakchunk0-Windows.pak         ; Core (1.5 GB)
    pakchunk1-Windows.pak         ; Forest area (2.1 GB)
    pakchunk2-Windows.pak         ; Desert area (1.8 GB)
    pakchunk3-Windows.pak         ; Snow area (2.3 GB)
    pakchunk10-Windows.pak        ; Cinematics Act 1 (3.2 GB)
    pakchunk20-Windows.pak        ; Music (0.8 GB)
    pakchunk30-Windows.pak        ; Serbian localization (0.1 GB)

38.7.3 Download Size Optimization

U eri digitalnih prodavnica, velicina download-a je kriticna. Igraci nece cekati da skinu 200GB igru (bar ne rado). Evo strategija za smanjenje velicine:

1. Audit vasih asset-a

Koristite Size Map alat u editoru (Window > Developer Tools > Size Map) da vidite sta zauzima najvise prostora:

Tipicna raspodela velicine u UE5 projektu:

Teksture:           40-60% ukupne velicine
Mesh/Nanite podaci: 15-25%
Audio:              10-20%
Animacije:          5-10%
Shaderi:            3-8%
Blueprinti/Code:    1-3%
Ostalo:             1-5%

Teksture su uvek najveci deo! Fokusirajte se na optimizaciju tekstura pre svega.

2. Optimizacija tekstura za velicinu

; Smanjite maksimalnu rezoluciju tekstura za shipping
; Project Settings > Engine > Rendering > Textures
MaxTextureSize=4096  ; Umesto 8192

; Koristite agresivniju kompresiju za manje vazne teksture
; U Material editoru za svaku teksturu:
; - Detail teksture: BC1 (najjaca kompresija)
; - Normal mape: BC5 (specijalizovano za 2-kanalne podatke)
; - Base color: BC7 (dobar kvalitet sa razumnom kompresijom)

3. Eliminisanje nekoristenih asset-a

# RunUAT komanda za analizu referencovanih asset-a
RunUAT.bat AnalyzeReferences ^
    -project="MyProject.uproject" ^
    -platform=Win64

# Ili koristite editor: Window > Developer Tools > Asset Audit
# Ovo prikazuje sve asset-e koji NISU referencovani

Cest problem: Developeri zaborave da uklone test asset-e, placeholder teksture, ili stare verzije mesheva. Projekat od 30GB cesto moze da se smanji na 20GB samo uklanjanjem nekoristenih asset-a!

4. Audio optimizacija

; Smanjite kvalitet audio-a za manje kriticne zvukove
; Za ambijentalne zvukove: 22050 Hz, mono
; Za voice over: 22050 Hz, mono
; Za muziku: 44100 Hz, stereo
; Za SFX: 44100 Hz, mono

; DefaultEngine.ini
[Audio]
OggQuality=60          ; 0-100, nizi = manji fajl
OpusQuality=6          ; 1-10
MaxChannels=32         ; Ogranicite za mobile

5. On-demand download (DLC/Patches)

Za igre koje su prevelike za jednokratan download, razmislite o on-demand content sistemu:

38.7.4 Install Size vs Runtime Memory

Vazno je razumeti razliku izmedju velicine na disku i koriscenja memorije u toku rada:

VELICINA NA DISKU vs RUNTIME MEMORY

+------------------+------------+---------------+
| Asset            | Na disku   | U memoriji    |
+------------------+------------+---------------+
| Tekstura 4K BC7  | 22 MB      | 22 MB (GPU)   |
| Tekstura 4K RGBA | 64 MB      | 64 MB (GPU)   |
| Nanite mesh 10M  | 45 MB      | 45 MB (GPU)   |
| Trad. mesh 100K  | 8 MB       | 8 MB (GPU+CPU)|
| Audio 5 min OGG  | 5 MB       | 0.5 MB (stream)|
| Audio 5 min WAV  | 50 MB      | 50 MB (RAM)   |
| Blueprint BP     | 0.1 MB     | 0.3 MB (RAM)  |
| Level (streamed) | 200 MB     | 50 MB (subset)|
+------------------+------------+---------------+

Kljucne opservacije:
1. Kompresovane teksture zauzimaju ISTO u memoriji kao na disku
   (jer se dekompresuju na GPU, a GPU cita kompresovane podatke)
   
2. Audio streaming drasticno smanjuje memory footprint
   (samo mali buffer se drzi u memoriji)
   
3. Level streaming znaci da samo deo nivoa je u memoriji

Best practices za balansiranje disk/memory:

  1. Koristite texture streaming: Ne ucitavajte sve mip-mape svih tekstura. UE5 automatski ucitava samo potrebne mip nivoe.

  2. Koristite audio streaming: Za duge audio fajlove (muzika, ambient, naracija), koristite streaming umesto ucitavanja celog fajla u memoriju.

  3. Level streaming: Podelite velike nivoe na sub-nivoe koji se ucitavaju i izbacuju po potrebi.

  4. Object pooling: Umesto kreiranja i unistavanje objekata, koristite pool. Smanjuje i fragmentaciju memorije.


38.8 Prakticni Vodic: Packaging Korak po Korak

Da bismo sve ovo spojili u koherentnu celinu, evo kompletnog vodicca za pakovanje UE5 projekta:

Korak 1: Priprema projekta

Checklist pre pakovanja:
[ ] Svi asset-i su finalni (nema placeholder-a)
[ ] Nema broken referenci (proverite sa Asset Audit)
[ ] Build configuration je "Shipping" (ne Development)
[ ] Svi test/debug Blueprint-i su uklonjeni ili isljuceni
[ ] Console komande su onemogucene u Shipping build-u
[ ] Error handling je implementiran (nema neuhvacenih izuzetaka)
[ ] Svi nivoi su testirani u Standalone modu

Korak 2: Project Settings za packaging

; DefaultGame.ini

[/Script/UnrealEd.ProjectPackagingSettings]
; Build konfiguracija
BuildConfiguration=PPBC_Shipping

; Blueprint nativizacija (opciono, za performanse)
bNativizeBlueprintAssets=false

; Kompresija
bCompressed=true
CompressionMethod=Oodle

; Sta da se pakuje
bCookAll=false          ; Ne kuvaj sve, samo referencovane asset-e
bCookMapsOnly=false     ; Kuvaj i asset-e van mapa

; Mape za kuvanje
+MapsToCook=(FilePath="/Game/Maps/MainMenu")
+MapsToCook=(FilePath="/Game/Maps/Level_01")
+MapsToCook=(FilePath="/Game/Maps/Level_02")

; Direktorijumi koji se uvek kuvaju
+DirectoriesToAlwaysCook=(Path="/Game/Core")
+DirectoriesToAlwaysCook=(Path="/Game/UI")

; Direktorijumi koji se NIKADA ne kuvaju
+DirectoriesToNeverCook=(Path="/Game/Test")
+DirectoriesToNeverCook=(Path="/Game/Debug")
+DirectoriesToNeverCook=(Path="/Game/Prototypes")

Korak 3: Pakovanje iz komandne linije

# Windows Shipping build
RunUAT.bat BuildCookRun ^
    -project="C:/Projects/MyGame/MyGame.uproject" ^
    -noP4 ^
    -platform=Win64 ^
    -clientconfig=Shipping ^
    -serverconfig=Shipping ^
    -cook ^
    -allmaps ^
    -build ^
    -stage ^
    -pak ^
    -archive ^
    -archivedirectory="C:/Builds/MyGame" ^
    -compressed ^
    -prereqs ^
    -distribution ^
    -nodebuginfo

# PS5 build (zahteva PS5 SDK)
RunUAT.bat BuildCookRun ^
    -project="C:/Projects/MyGame/MyGame.uproject" ^
    -platform=PS5 ^
    -clientconfig=Shipping ^
    -cook ^
    -allmaps ^
    -build ^
    -stage ^
    -pak ^
    -archive ^
    -archivedirectory="C:/Builds/MyGame_PS5"

# Android build
RunUAT.bat BuildCookRun ^
    -project="C:/Projects/MyGame/MyGame.uproject" ^
    -platform=Android ^
    -clientconfig=Shipping ^
    -cookflavor=ASTC ^
    -cook ^
    -allmaps ^
    -build ^
    -stage ^
    -pak ^
    -archive ^
    -archivedirectory="C:/Builds/MyGame_Android"

Korak 4: Verifikacija build-a

Post-build checklist:
[ ] Pokrenite build na svim ciljnim platformama
[ ] Proverite loading vremena
[ ] Proverite memory usage (nema leak-ova)
[ ] Proverite da nema shader compilation stutter-a
[ ] Testirajte na minimum spec hardveru
[ ] Proverite pak file integritet
[ ] Proverite da debug/test sadrzaj nije ukljucen
[ ] Proverite certificate/signing (za konzole i mobile)

Korak 5: Profajliranje finalnog build-a

// Koristite ove komande u Development build-u za profajliranje
// (pre nego sto napravite finalni Shipping build)

stat unit          // FPS, Game thread, Render thread, GPU vreme
stat gpu           // Detaljne GPU statistike
stat memory        // Memorija po kategoriji
stat streaming     // Texture streaming statistike
stat scenerendering // Rendering pipeline statistike
profilegpu         // GPU profiler snapshot
memreport -full    // Detaljan memory report

38.9 Troubleshooting -- Cesti Problemi pri Pakovanju

Problem 1: "Failed to cook package"

LogCook: Error: Failed to cook /Game/Assets/MyBrokenAsset

Mogući uzroci:
1. Asset je korumpiran -> Otvorite u editoru, ako se ne otvara, obrisite i ponovo napravite
2. Broken reference -> Proverite Reference Viewer
3. Cirkularna zavisnost -> Reorganizujte asset-e
4. Out of memory -> Povecajte RAM ili kuvajte manje asset-a odjednom

Problem 2: "Shader compilation failed"

LogShaderCompilers: Error: Failed to compile shader for material M_Complex

Mogući uzroci:
1. Material koristi feature koji nije podrzan na ciljnoj platformi
   -> Proverite platform kompatibilnost svake node-e
2. Previse instrukcija u shader-u
   -> Pojednostavite materijal, koristite LOD za materijale
3. Shader compiler bug
   -> Azurirajte engine na najnoviju verziju

Problem 3: "Package is too large"

Mogući uzroci i resenja:
1. Nekoristeni asset-i -> Asset Audit + Remove Unused
2. Prevelike teksture -> Smanjite max rezoluciju
3. Nekompresovani audio -> Prebacite na streaming
4. Debug content -> Dodajte u DirectoriesToNeverCook
5. Duplirani asset-i -> Koristite redirectors i consolidate

Problem 4: "Stuttering during gameplay"

Mogući uzroci:
1. Runtime shader compilation -> Implementirajte PSO precaching
2. Texture streaming -> Povecajte streaming pool
3. Level streaming -> Optimizujte streaming distances
4. Garbage collection -> Smanjite broj kratkozivih objekata
5. Hitches od asset ucitavanja -> Koristite async loading

Problem 5: "Out of memory" na konzoli/mobilnom

Resenja:
1. Smanjite texture streaming pool za tu platformu
2. Koristite agresivnije LOD-ove
3. Smanjite broj istovremeno ucitanih nivoa
4. Koristite memory budget profiling alate
5. Implementirajte memory warning callback:
// Reagovanje na low memory warning (iOS/Android)
FCoreDelegates::GetMemoryTrimDelegate().AddLambda([]()
{
    // Pokusaj da oslobodis memoriju
    GEngine->ForceGarbageCollection(true);
    
    // Smanji texture streaming pool
    IConsoleVariable* PoolSize = IConsoleManager::Get()
        .FindConsoleVariable(TEXT("r.Streaming.PoolSize"));
    if (PoolSize)
    {
        float CurrentSize = PoolSize->GetFloat();
        PoolSize->Set(CurrentSize * 0.75f); // Smanji za 25%
    }
});

38.10 Automatizacija Build Procesa (CI/CD)

Za profesionalne timove, rucno pokretanje build-ova nije odrzivo. Postavite Continuous Integration / Continuous Delivery (CI/CD) pipeline koji automatski gradi, testira, i distribuira vase buildove.

Jenkins Pipeline primer

// Jenkinsfile za UE5 CI/CD

pipeline {
    agent { label 'ue5-build-machine' }
    
    parameters {
        choice(name: 'PLATFORM', choices: ['Win64', 'PS5', 'XSX', 'Android', 'IOS'])
        choice(name: 'CONFIG', choices: ['Development', 'Shipping'])
        booleanParam(name: 'FULL_COOK', defaultValue: false)
    }
    
    stages {
        stage('Compile') {
            steps {
                bat '''
                    RunUAT.bat BuildCookRun ^
                        -project="%PROJECT_PATH%" ^
                        -platform=%PLATFORM% ^
                        -clientconfig=%CONFIG% ^
                        -build ^
                        -cook ^
                        %FULL_COOK_FLAG% ^
                        -pak ^
                        -stage ^
                        -archive ^
                        -archivedirectory="%BUILD_OUTPUT%"
                '''
            }
        }
        
        stage('Automated Tests') {
            steps {
                bat '''
                    RunUAT.bat RunTests ^
                        -project="%PROJECT_PATH%" ^
                        -platform=%PLATFORM% ^
                        -testFilter="Project+Functional"
                '''
            }
        }
        
        stage('PSO Collection') {
            when { params.CONFIG == 'Shipping' }
            steps {
                bat '''
                    RunUAT.bat BuildPSOCache ^
                        -project="%PROJECT_PATH%" ^
                        -platform=%PLATFORM%
                '''
            }
        }
        
        stage('Deploy') {
            when { params.CONFIG == 'Shipping' }
            steps {
                // Upload na Steam, PlayStation Store, Xbox Store, itd.
                echo "Deploying to distribution platform..."
            }
        }
    }
    
    post {
        success { 
            slackSend(color: 'good', 
                      message: "Build ${PLATFORM} ${CONFIG} uspesno zavrsen!")
        }
        failure { 
            slackSend(color: 'danger', 
                      message: "Build ${PLATFORM} ${CONFIG} NEUSPESAN!")
        }
    }
}

Horde kao alternativa

Ako koristite Epic-ov Horde build sistem, konfiguracija je drugacija ali principi su isti:

// horde.json primer
{
    "streams": [{
        "id": "my-game-main",
        "name": "MyGame Main",
        "tabs": [{
            "title": "Build",
            "columns": [{
                "category": "Cook",
                "groups": [{
                    "type": "job",
                    "name": "Cook Win64",
                    "template": "cook-windows"
                }, {
                    "type": "job", 
                    "name": "Cook PS5",
                    "template": "cook-ps5"
                }]
            }]
        }]
    }]
}

38.11 Distribucija na Razlicite Prodavnice

Steam (PC)

Steam distribucija zahteva:
1. Steamworks SDK integraciju
2. Steam app ID
3. Depot konfiguraciju (definise koji fajlovi idu gde)
4. Steam build upload putem SteamCMD

// steamcmd upload primer:
steamcmd +login "username" "password" ^
         +run_app_build "app_build.vdf" ^
         +quit

Epic Games Store (PC)

EGS distribucija:
1. Epic Online Services (EOS) integracija
2. BuildPatchTool za upload
3. Binary chunking za efikasan patching

// BuildPatchTool upload:
BuildPatchTool.exe ^
    -mode=UploadBinary ^
    -OrganizationId="..." ^
    -ProductId="..." ^
    -ArtifactId="..." ^
    -BuildRoot="C:/Builds/MyGame" ^
    -CloudDir="..." ^
    -BuildVersion="1.0.0"

PlayStation Store / Xbox Store

Konzolna distribucija zahteva:

Google Play / Apple App Store

Mobilna distribucija:

; Za Android AAB format:
[/Script/AndroidRuntimeSettings.AndroidRuntimeSettings]
bBuildForES31=true
bSupportsVulkan=true
bPackageForGooglePlayStore=true
bUseAABFormat=true

38.12 Kljucni Pojmovi

Termin Objasnjenje
Cooking Proces konvertovanja editor asset-a u platformski optimizovane pakete za runtime
Pak File Arhiva koja sadrzi kuvane asset-e, optimizovana za brzo ucitavanje
PSO (Pipeline State Object) Monolitni objekat koji definise kompletno stanje grafickog pipeline-a za jedan draw call
PSO Precaching Tehnika pre-kreiranja PSO-ova pre nego sto budu potrebni, da bi se izbegao stuttering
DDC (Derived Data Cache) Kes kompajliranih podataka (shaderi, teksture, itd.) koji ubrzava ponovna kuvanja
Shader Permutation Jedna varijacija shader-a nastala kombinacijom razlicitih feature-a i podesavanja
Scalability Group (sg.*) Grupa podesavanja koja kontrolise vizuelni kvalitet na razlicitim nivoima
Device Profile Skup podesavanja specificnih za konkretan hardver ili platformu
Chunking Podela content-a u logicke grupe (chunk-ove) za efikasno streaming ucitavanje
Oodle RAD Game Tools kompresioni algoritam integrisan u UE5, optimalan za game data
DXIL DirectX Intermediate Language -- shader bytecode format za DirectX 12
SPIR-V Standard Portable Intermediate Representation -- shader bytecode format za Vulkan
ASTC Adaptive Scalable Texture Compression -- standardni format za mobilne teksture
Iterative Cook Inkrementalno kuvanje koje procesira samo promenjene asset-e
Full Cook Kompletno kuvanje svih asset-a od nule
Thermal Throttling Smanjenje brzine procesora zbog pregrevanja, posebno na mobilnim uredjajima
Forward Rendering Rendering tehnika gde se osvetljenje racuna direktno tokom renderovanja geometrije
Deferred Rendering Rendering tehnika gde se geometrija prvo renderuje u G-buffer, pa se osvetljenje racuna naknadno
XGE / IncrediBuild Sistem za distribuiranu kompilaciju shader-a i koda preko mreze
Horde Epic-ov distribuirani build sistem dizajniran za Unreal projekte
TRC / XR Technical Requirements Checklist -- sertifikacioni zahtevi za Sony (TRC) i Microsoft (XR) konzole
Dynamic Resolution Tehnika automatskog prilagodjavanja rezolucije renderovanja za odrzavanje ciljanog frame rate-a
Texture Streaming Sistem za dinamicko ucitavanje i izbacivanje mip-mapa tekstura na osnovu vidljivosti
Level Streaming Sistem za dinamicko ucitavanje i izbacivanje delova nivoa na osnovu pozicije igraca
Nativization Konverzija Blueprint koda u C++ za bolje runtime performanse

38.13 Unakrsne Reference na Druga Poglavlja


38.14 Korisni Linkovi i Resursi

Zvanicna Epic dokumentacija

Epic Learning Resources

Community Resources


U sledecem poglavlju cemo se pozabaviti distribucijom igre i post-launch podrskom -- patchevima, hotfixevima, i DLC sadrzajem. Ali pre toga, pobrinite se da imate stabilan packaging pipeline -- jer bez njega, nema ni distribucije!