Nighthawk.dk

Templates - Dit første spil

Skrevet d. 28. July 2016 af Claus Nielsen.

Her lærer du at lave et simpelt skydespil uden noget programmering.

Templates

3D Gamestudio har altid haft tradition for, at man skal kunne lave et spil uden noget programmering - og netop hér kommer templates ind i billedet: templates er en samling kode, som du kan bruge i stedet for at programmere dit spil selv. Der er typisk mange parametre at skrue på, når det gælder templates, sådan at du i en vis grad kan tilpasse koden til lige netop dit spil, og i dette afsnit bliver du introduceret templates i A8.

Jeg vil først og fremmest bemærke, at jeg kun selv har brugt de templates der var med i A5 - nu har jeg så kigget lidt på de nyeste (og nu eneste tilgængelige) templates, A8 templates, og jeg er ikke imponeret over dem, idet der både er egentlige fejl og mangler. Nederst i dette afsnit beskriver jeg hvordan man kan rette nogle af de fejl (crashes) som jeg er stødt på. Selve template-systemet i WED (specielt Project Manager), som vi skal bruge omlidt, virker heller ikke ordentligt i skrivende stund, men når først det hele er sat op, ser det ud til at virke fint. Vi vil bruge A8 shooter templates, da de giver et fundament som vi kan bygge videre på, når vi i næste afsnit begynder med lidt programmering.

Opsætning til A8 Shooter Templates

Åben et level i WED (evt. det du arbejdede på i sidste afsnit), eller start på et nyt level (og sørg for at gemme det inden du fortsætter). Åben Map Properties (under File i menuen), og hvis du tidligere har tilføjet et script til dit level (f.eks. Flythrough), så tryk på Remove Script-knappen. Tryk på New Script og vælg Template_project. Gør nu følgende:

  • Åben nu Project Manager (under File) og gå til fanen Add.
  • Sæt Class til SHOOTER.
  • Sæt Script til Player Parameters.
  • Tryk på Add Script.

Gentag nu dette for de andre scripts du kan vælge, når Class er sat til SHOOTER - rækkefølgen bør i princippet være ligegyldig, men jeg har ikke tjekket det.

Startup-template

Du bør også tilføje startup (med CLASS sat til GAME), men selv havde jeg problemer med denne: det viser sig nemlig, at den ikke virker hvis man har gemt sit level som level.wmp.

Hvis man i stedet gemmer sit level under et andet navn, f.eks. bane.wmp, ser der ikke ud til at være noget problem. Bemærk dog at det ikke er navnet på .wmp-filen der er problemet, men i stedet dét, at dit script ikke må hedde level.c (og netop dette navn får dit script hvis dit level hedder level.wmp og du trykker New Script i Map Properties).

Du kan nu lukke Project Manager igen, gå op i menuen under Object -> Add Model, og finde player.mdl eller en anden model, du har lyst til at bruge:

Markér modellen, højre-klik, og vælg Properties. Gå til fanen Behaviour, og klik på Choose Action-knappen. Hvis du fik hentet A8 shooter templates korrekt i Project Manager (og det er ikke en selvfølge at du gjorde, idet Project Manager tilsyneladende er fyldt med fejl), kan du finde t_player (og meget andet) på listen. Vælg t_player og luk Object Properties igen.

Placér modellen inde i et rum i dit level (pas på at f.eks. fødderne ikke sidder fast i gulvet), build, og run. Hvis du fik sat det hele rigtigt op, skulle du nu kunne gå rundt i dit level med W, A, S og D, kigge rundt med musen, og løbe når du holder Shift nede. Tryk Space for at hoppe (se nedenfor hvis du får et crash).

Du kan også bruge F2 for quicksave, F3 quickload, F5 for at skifte opløning, F6 for screenshot (bliver gemt i mappen med dit level), F11 giver en masse information om hvordan spillet kører, og Alt + Enter for at spille med fuld skærm (i stedet for det vindue spillet starter op i). I næste afsnit ser vi på, hvordan man kan sætte opløsning og fuldskærm fra start.

Hvis det ikke virker

Start med at trykke Remove Script i Map Properties, og slet dernæst .c-filen med samme navn som dit level: hvis dit level er gemt som mitlevel.wmp, så er det mitlevel.c, som ligger i samme mappe som du har gemt dit level (.wmp-filen) i. Slet evt. også .h-filerne, men det er ikke nødvendigt.

Du kan nu trykke New Script i Map Properties og vælge Template_project igen.

Tilpasning af Templates

Nu hvor du har sat dit spil op til at bruge templates, er det tid til at justere dem. Dette gøres i Project Manager under fanen Customize: vælg f.eks. Player Parameters og tryk på Customize-knappen. Her kan du f.eks. ændre hvor meget liv man skal starte med (Health), hvor hurtigt man skal kunne bevæge sig (Movement speed), samt nogle lidt mere avancerede indstillinger. Da jeg ikke rigtig har brugt disse templates før, vil jeg lade det være op til dig selv at lege med alle disse parametre - de fleste er sikkert indstillet fint nok som standard.

Der er dog én bestemt parameter, som du bør overveje at ændre: hvis du starter spillet op, og ændrer opløsningen så vinduet bliver stærre, kan du se noget der ligner dette:

Der er en stor, halvgennemsigtig og mørk firkant hen over det meste af skærmen (hele skærmen når der anvendes mindre opløsning), og nederst ses toppen af to paneler, der viser hvor meget liv og ammunition man har. Det er endnu et sted hvor template-koden er dårlig; det ser ikke godt ud! Men det er heldigvis nemt at fjerne. Vælg Weapons and Power-ups og tryk på Customize (i Project Manager under Customize-fanen), og sæt Enable HUD til 0.
I et af de næste afsnit laver vi et nyt og bedre panel, som viser liv og ammunition.

Våben og ammo

Der er inkluderet en række våben i template-koden: pistol, maskingevær og sniper. Indsæt en model med Object -> Add Model (f.eks. pistol.mdl, machinegun.mdl eller snipergun.mdl, men du kan i princippet bruge en hvilken som helst model), markér den, højre-klik, og vælg Properties. Gå til Behaviour-fanen og klik på Choose Action. Vælg nu enten t_handgun, t_mgun eller t_sniper.

Placér modellen et sted i dit level, build og run.

Der er to våben mere, t_laser og t_rocket, men begge virker ikke ordentligt - se nedenfor hvordan de kan fikses.

Da du under Behaviour-fanen valgte en action til din våben-model, lad os sige t_sniper, så skiftede SKILL1 på samme fane navn til Sniper_bullets, og det tal, der står her, angiver hvor mange skud man får når man samler våbenet op (der er et tilsvarende skill for de andre våben). Prøv evt. også at lege med de andre skills (det er kun de første skills der bliver brugt, og de får mere beskrivende navne når du vælger en action).

Udover våben kan du også bruge de actions hvis navn starter med t_ammo_, idet de giver mere ammunition til de forskellige våben, når man samler dem op. På samme måde giver modeller med actions t_armor og t_health mere hhv. armor ("rustning"/beskyttelse) og liv, når de bliver samlet op. Læg mærke til at du for alle disse actions kan bruge SKILL1 til at bestemme hvor meget man får.

Du kan sætte alle de våben, ammunitionskasser, osv. ind i dit level som du har lyst til, men hver gang du indsætter eller ændrer en model i WED, skal du bruge build før ændringer kan ses inde i spillet. Hvis du har et stort level, sådan at build tager lang tid, kan du vælge Update Entities i build-vinduet for at spare tid. Husk dog at bruge Build BSP Map igen når du laver andre ændringer i dit level!

Fjender

Nu hvor du har fået nogle våben, mangler du bare nogle fjender at skyde på! Indsæt f.eks. enemy.mdl eller en anden model, og vælg den action der hedder t_enemy. Her er igen nogle skills du kan sætte, f.eks. Health.

Desværre er t_enemy-scriptet ikke specielt godt, som du nok vil opleve på et tidspunkt - måske allerede med det samme - og jeg får endda en fejlmeddelse når de dør (se nedenfor hvordan man fikser det). Til gengæld er der også en anden fjende: t_turret (brug gerne turret.mdl), som er en kanon, der står og skyder efter spilleren. Sæt skill1 (Rockets) til 1 for at lade kanonen skyde med raketter i stedet for maskinkanon.

Døre og nøgler

Template-koden indeholder også scripts til døre og nøgler, t_door og t_key, men i stedet for at indsætte en model som dør (selvom du sagtens kan bruge en model), vil vi lave en Map Entity. Lav en kasse i WED, som passer ind i en af dine døråbninger, og vælg en texture. Kopier kassen, gem dit level, og gå op i menuen under File -> New. Indsæt nu din kasse igen med Edit -> Paste, og indlæs standard.wad så kassen får sine textures på. Gem og build - og du er nu færdig her.

Åben igen dit level i WED, slet den kasse du kopierede før, og gå op i menuen under Object -> Add Map Entity og vælg den fil som du lige har lavet med build af din dør. Din dør er nu blevet en entity (modeller er også en slags entity) i stedet for en almindelig kasse i WED, og du kan derfor vælge en action til den: vælg t_door.

Der er en række egenskaber (skills) som kan indstilles for din dør, først og fremmest hvordan den skal åbne: hvis den skal "køre" sidelæns eller op/ned (de tre Offset skills styrer hvor langt den bevæger sig), så sæt Swing til 0, og hvis den i stedet skal dreje/svinge op (Angle angiver hvor mange grader døren skal dreje), så sæt Swing til 1. Sæt Open Manually til 1 hvis man skal trykke E for at åbne døren, og 0 hvis den skal åbne automatisk, når man kommer tæt nok på. Key angiver hvilken nøgle der skal bruges for at åbne døren - sættes key til 0 behøver man ingen nøgle.

Du kan indsætte en model og vælge den action, der hedder t_key for at lave en nøgle. Her angiver det færste skill, Key, hvilken nøgle det er: hvis du sætter Key til 1, kan den åbne alle døre hvor Key er sat til 1, sættes Keyt_key til 5 kan den åbne alle t_door med Key 5, osv.

Bemærk: Når du laver en map entity til en dør, som skal svinge op, så kan du vælge den akse, som døren skal dreje omkring, i WED. Den vil nemlig dreje omkring origo (nulpunktet), der i WED er det punkt hvor de grønne linier skærer hinanden, som vist herunder:

Elevatorer m.m.

Template-koden indeholder også scripts til elevatorere (entities der bevæger sig op og ned) og platforme (der bevæger sig i x- eller y-retningen, i stedet for op og ned). Det er de to actions t_elevator og t_platform, og jeg vil lade det være op til dig at afprøve dem.

Ændring af template-filer

Template-koden bruger af række filer, f.eks. lyde fra 3DGS/templates/sounds/-mappen eller selve kodefilerne i 3DGS/include/, hvor 3DGS er mappen hvor du har installeret 3DGS (den hedder sandsynligvis noget andet på din computer). Hvis du vil ændre i nogle af disse filer, så kopier dem først over i den mappe, som du har gemt dit level i: dit spil bruger først og fremmest de filer, der ligger i denne mappe, og bliver de ikke fundet dér, bliver der kigget i 3DGS/include og undermapper til 3DGS/templates.

Til gengæld vil ændringer du laver direkte i 3DGS/templates-mapperne gælde for alle dine spil, der bruger templates (både tidligere og fremtidige projekter), så derfor vil jeg som udgangspunkt anbefale ikke at ændre disse filer - i hvert fald ikke med mindre du har lavet en backup!

Publish - Det færdige spil

Når du har lavet et spil, og gerne vil lade andre prøve det, kan du kompilere det, så du får et egentligt program, du kan køre. Hvis du åbner dit level i WED, og går op i menuen under File -> Publish, så bliver der lavet en mappe til det færdige spil (med samme navn som dit level, og endelsen .cd - og den vil være en undermappe til mappen, som dit level ligger i).

.cd-mappen indeholder en programfil (.exe), som du kan køre for at spille dit spil. Derudover indeholder mappen alle de filer, som dit spil bruger - dvs. alle template-filer er kopieret over i denne mappe. Bemærk at alle disse filer skal være der, for at dit spil virker, og nogle gange kan Publish-funktionen "overse" nogle filer, som så manuelt skal kopieres over i denne mappe. Derfor er det vigtigt at du tester det færdige spil, inden du sender det til nogen - for at være på den sikre side!

Fejl i template-koden

Jeg har fundet nogle fejl i template-koden, og herunder kan du finde hjælp til at fikse det. Når jeg nedenfor referer til filer, så er mappen 3DGS den mappe, som du har installeret 3D Gamestudio i - den hedder højst sandsynligt noget andet på din computer (det er den mappe hvor f.eks. WED.exe og SED.exe ligger).

Bemærk: Lav altid en backup inden du ændrer i template-filer (filerne i 3DGS/include eller 3DGS/templates).

"Script crash in t_player" når du trykker space/hopper

Kopiér filen 3DGS/include/t_player.c over i den mappe, hvor dit level ligger, og åben den i SED. Find dette sted i koden:

action t_player()
{
	player = my;
	set (my, INVISIBLE); // using a 1st person player
	set (my, FLAG2); // will be used by enemies' c_scan instructions to detect the player
	var forward_on, backward_on, right_on, left_on, jump_on, run_on;
	var current_height = 0, jump_handle;
	VECTOR horizontal_speed, vertical_speed, temp;
	vec_set(horizontal_speed.x, nullvector); // initialize this vector
	vec_set(vertical_speed.x, nullvector); // initialize this vector
	while(t_players_health > 0)
	{

Den markerede tekst er på linie 54 i min version af t_player.c, og den skal ændres til:

var current_height = 0, jump_handle = 0;

ændringen er markeret. Gem ændringen i t_player.c og start dit spil igen for at se om fejlen er fikset, og om alt andet stadig virker: hvis det hele virker, kan du kopiere den ændrede t_player.c tilbage i 3DGS/include/.

"Invalid function arguments in t_enemy_dead" når en t_enemy dør

Denne fejl opstår fordi der ikke blev fundet nogen fil kaldet dead.wav. Lydfilerne ligger i mappen 3DGS/templates/sounds/ og har endelsen .wav, og hvis du ikke har dead.wav kan du kopiere en af de andre lydfiler og give den navnet dead.wav (jeg brugte tshooter_jump.wav, men du kan bruge en hvilken som helst Waveform-lydfilm). Dermed burde problemet være løst.

"Invalid function arguments in t_player_laser" når man skyder med sin lasergun

Dette er samme problem som med t_enemy_dead ovenfor: du mangler en lydfil, denne gang kaldet lasersound.wav. Jeg brugte en kopi af hit.wav.

"Invalid call in event rocket_event" når man bruger sin rocket launcher

Kopiér filen 3DGS/include/t_weapons.c over i den mappe, hvor dit level ligger, og åben den i SED. Find dette sted i koden (fra linie 977 i min udgave af t_weapons.c):

function rocket_event()
{
	if (you) // hit an entity? (maybe one of the enemies)
		you.skill99 -= my.skill88; // damage the entity (hopefully, an enemy)
	ent_create (explo13_tga, my.x, destroy_rocket); // and create an explosion sprite at impact
	wait (1);
	ent_remove(my);	
}

Der skal indsættes wait(1); inden linien med ent_create:

function rocket_event()
{
	if (you) // hit an entity? (maybe one of the enemies)
		you.skill99 -= my.skill88; // damage the entity (hopefully, an enemy)
	wait(1);
	ent_create (explo13_tga, my.x, destroy_rocket); // and create an explosion sprite at impact
	wait (1);
	ent_remove(my);	
}

Ændringen er markeret. Gem ændringen i t_weapons.c og start dit spil igen for at se om fejlen er fikset, og om alt andet stadig virker: hvis det hele virker, kan du kopiere den ændrede t_weapons.c tilbage i 3DGS/include/.

Relaterede ressourcer
Acknex Unlimited

Mange ressourcer til 3D Gamestudio.

Se mere her

3D Gamestudio

Game-engine til udvikling af 3D-spil.

Se mere her

×