News | Forum | People | FAQ | Links | Search | Register | Log in
Teaching Old Progs.dat New Tricks.
You know about the info_notnull explosion hack. You know about making monsters drop weapons or alternate ammo using the .weapon and .ammo_whatever hacks. You know about making items float in the air by spawning them on a temporary platform. Let's have a thread where we talk about new ways to use existing behavior and get novel gameplay. If you're a "retired" mapper, this is a great time to do some armchair level design and suggest ideas you'll never have a chance to use yourself.
First | Previous | Next | Last
of using Qmaster's idea would be to put all the enemies in teleport boxes, and kill the teleport destinations of the other paths after the player can't go back to take another route.

Isn't there a problem that in vanilla you don't have multiple targetnames? If you have a single trigger_teleport linked to two info_teleport_destination entities they must have the same targetname. When you killtarget one, the other gets removed as well. I think you need a separate trigger_teleport for each destination, and killtarget that instead (or just only ever trigger one of them).

I mean, there's a way to do it with "use" "SUB_Remove" added to just the first info_teleport_destination on the map, but any hack that is depending on the order of entities in the map is unpleasant to maintain... 
Thanks Guys! 
Why didn't I think of using shared trigger_secrets for each path's secrets; that's genius, Preach! :D Thanks also for telling about the -1 value for the sounds key. I had tried numerous other integer values in vain, from 0 to larger ones, but hadn't thought of negative ones. You're a lifesaver, thank you! :)

Thanks for the monster teleport trick, Qmaster! I had actually read about it somewhere else in this forum, if I recall right. I guess that's really the best one can do in an unmodded game. o:

Actually, I had also read something about updating the secret totals in the mapping thread, in a post written by Preach, actually (post number 4316 from the year 2005)! ;D Something about servers, clients and SVC_UPDATESTAT, which made me think something like "wait, don't servers n' stuff mean multiplayer stuff" but I guess the singleplayer runs on a server/client basis as well, so I guess there really is no easy way to modify the totals.

Anyway, too bad I have some monsters present only in one path. Seems the only thing I can do is add the kill count to the right number after choosing a path or right before ending the map (killtargeting the monsters didn't increase the number of kills in my tests, so I'll have to go with boss_death10). Maybe I'll go with right after choosing a path, so the player can keep looking for enemies in a given path before exiting the map to make sure they've exterminated them all. >:D 
Spare Monsters 
shove a trigger_teleport over the untaken paths (one per). trigger it when you feel evil.
all monsters within the triggered teleporter will be teleported to a single spot, telefragging all of them instantly without needing to do anything per monster.
bonus points if you can come up with some logical reason for the gibs to appear in front of the player. spontaneous fountains of gibs! 
Oooh, I like it! It gave me the idea of adding a Doom 3 like teleport sequence at the end, where the player flies through a hellish shower of red. 
sn't there a problem that in vanilla you don't have multiple targetnames? If you have a single trigger_teleport linked to two info_teleport_destination entities they must have the same targetname. When you killtarget one, the other gets removed as well. I think you need a separate trigger_teleport for each destination, and killtarget that instead (or just only ever trigger one of them).

I forgot that. I have done it with using trigger_once or multiple as intermediates but it was for func_walls and triggers. That way for one route the end entites are killed and for the other routes the intermediates. Teleport destinations can't use intermediates so in this case it cannot be used.

What could work is to put one trigger_teleport for each route on each enemy's box (all of the same route with the same targetname) and the destinations on the desired points and kill the triggers after the route is chosen. The downside is that no enemy can be put before that if only this method to deal with the enemies is used, can contribute to reach the limit for brush entities, and that teleporters have to be activated all of the same route at the same time. The upside is that it is quite fast to do.

killtargeting the monsters didn't increase the number of kills in my tests Interesting, i thought it did. Then try telefragging them like it does at the end of e1m7. 
Other Lethal Weapons 
Although not quite as spectacular as teleport gib fountains, there's a trigger capable of killing all the monsters within a trigger here (the second variety): 
Ambient Sounds From A Point 
Can we do them?

For example, the regular torches and fires in quake create a sound that decreases as you walk away, and originates from a point in the map.
Can we do this with custom sounds? Is it possible in id1 or do we need to code something? 
Need To Modify Progs. 
I'm not entirely certain, but to my knowledge, any sound you intend to use in Quake must be precached, and this is done in your progs file. Thus if you intend to use a custom you must modify the progs.dat and therefore must create a mod in essence.

Arcane Dimensions apparently works some black magic to precache any sound you place in the ad/sounds folder and thus you can use your custom sounds without further altering the AD progs. It also supports attenuation (sound at a distance) with the speed key.

In summary, this has already been done but to my knowledge cannot be done in ID1. 
HexenMapper: something like in #8

You can, for example, use a 'notouch' trigger (ideally point entity) with a "use" "train_wait" or "use" "plat_hit_bottom" field or the like, and a corresponding "noise" "ambience/fire1.wav" key, provided the sound is precached as Redfield says. If it's a looped sound, it'll play forever from the origin of this entity, although it'll have a different attenuation than regular ambient sounds. As a bonus, it also possible to killtarget it if you want the sound to stop. 
Any Way To Compile The Func_etc? Like The Fields... 
For doors... The "effects" field... I would do this. I don't want a flame war... I have a sever impediment... It is not laziness...
It would be awesome to be incorperated in the Entity def's and qrk. files etc

Ric... Mapper since 99 
New Post: Five Statues Challenge 
Got a challenge from a reader of the old blog and I can't resist a challenge. The basic premise is to have five statues in the map, where the most recently touched one is selected, causing it to be lit up.

It's a real multimedia extravaganza as well today, with a full write-up, an example map and even a video, so come on down! 
Weapon View Angle/Pitch Fix? 
While I know of talisa's/seven's nail-position fix which offsets the NG's & SNG's nails to come out of the barrel instead of your face when aiming upwards, I miss such a fix for every other weapon, especially the GL, which makes shooting upwards a PITA. I'm no coder and wouldn't even try to mess with the source code/progs.dat. So by request, is anyone else up to the task to do it? Thx in advance. 
Nice Preach 
I'm doing exactly the same thing in my current map, except with the AD entity state system, wouldn't have bothered ever trying in vanilla hah. 
Follow Up: The Alternator 
Hot on the heels, the promised hack that lets us ignore the order the entities are placed in the map, but still dictate the order that triggers fire.

The article also includes how to make an "alternator" - a setup where a single input trigger switches between activating two different targets. 
Brain Teaser For Preach 
Imagine you have several shootable triggers or buttons and want to fire an event once a certain total amount of health has been depleted. The damage done to the triggers transfered to an independent source, so to speak. So you can shoot each a random number of trigger a random number of times and once the overall health depletion reaches n, the event fires. Basically like a counter based on "health" instead of "count". > W_FireAxe notnull hack
W_FireAxe hits a func_door. = 1000 or 2000 etc.

And voila, just add func_buttons. 
but, don't you want the player's actual weapon damage to matter? E.g. shooting it with 10 nails should cause less total damage than 10 rockets. 
Make as many "shootable buttons" that you need. Select all of them, turn them all into one func_door with a health value, give it a target, set lip equal to bounding box so it doesn't move. 
The sum of all damage done combined. No idea if it's possible, and the applications would certainly be limited. For the lack of a better example: a machine needs to be damaged by a certain amount in order to be charged or explode and there are several exposed shootable parts. You can focus on a single one, or shoot each of them equally - the event fires once its global health is depleted. 
Exactly was @ metlslime.

But yeah, turning them all into a single door or button should work. Though what happens if they are supposed to be spread all over the map 
yeah, will you exceed max efrags and it disappears? I think in modern engines the efrag issue is solved and it is always drawn maybe... 
Spread All Over 
Nothing as far as I know, so long as the lip is set right for whichever movedir is set. I can't recall if func_button has an option to be silent in vanilla, so a func_door probably would work better. 
One Doesn't Tease Preach's Brain With Trivial Matters! 
And yet, I have another possibly simple or already-answered-but-I'm-too-dumb-to-find question: how to spawn fully functional movers like trains, doors and plats half-way through the map? Basically invisible until triggered and then working like normal entities. Think "use" "func_wall" but without being thwarted by precache functions. 
I'm indeed stupid. It should work just fine that way as long as you override the sounds. Or is there anything more to it? If not, please delete me. 
inline models are implicitly precached, so those are not an issue for doors/plats/trains/etc.
while they'll have a model string set, their starting modelindex will be 0, which means they'll remain invisible until they're properly spawned.

regarding sounds, you can just have a second door/plat anywhere else in the map, its sole purpose being to precache the required sounds.

a bigger issue is that if you're using use+targetname, you'll have no way to clear said targetname before the use is called.
this means that plats will need to be triggered twice (one to spawn, once to activate them so that they can be used).
doors are more problematic - you'll need to manually create a trigger field around the missing door to allow it to open, and you'll need to spawn that trigger field the same way as the door otherwise they'll spawn the door when you walk through them the first time. 
Reaching back to this post from 2009 and trying to understand something.

Would this allow for a silent trigger_push? My set up is:

classname info_notnull
use InitTrigger
touch trigger_push_touch
speed 500
angle 90
spawnflags 2
targetname test

Mark V and Quakespasm are still complaining about not caching the ambience/windfly.wav sound file. I thought this was the whole point of this hack.

Just put a trigger_push out in the void and it will ensure that sound is precached and avoid the warnings. 
Yep, that's in the map off in a tiny room but the hack'd entity plays the sound in that case. 
Yep, that's in the map off in a tiny room but the hack'd entity plays the sound in that case. 
Different Intent 
The intent is to make a delayed spawn trigger_push. The sound precache is the reason we have to do something a bit different to the standard "classname as use function" hack, it's what we're trying to work around. But the lack of sound is not intended - I would pair this with a regular trigger_push hidden somewhere in the map to perform the precache and remove the warnings.

You'd have to be pretty creative to get rid of the flying sound, only thing I can think might work is finding an entity hack that sets fly_sound on the player to an impossibly high value using ltime shenanigans on a doctored movetype_push entity. Haven't quite cracked that yet.

On a related note, this has reminded me of an undocumented Quoth 2.2 feature: you can specify the sound a trigger_push makes using the "noise" key. You can create a boiing! noise for jumppads, or using "misc/null.wav" will prevent any sound being made. Will write that one up when I get back... 
Alright. I was afraid of that, but luckily it's for academic purposes not a real project. Great news about the noise keys in Quoth 2.2 That does open up some possibilities. Thanks for the response.

I hope you get a chance to play my 100b4 entry. Lot's of sound work went into it. 
Cool Beans 
The pack is next on my list, so I'll watch out for it! 
Func_breakable In Id1 
Hey everyone :) So earlier someone on the TB discord asked if it was possible to make a brush that acts like a HL style func_breakable so I did some fooling around and figured out how to do it! Now this is pretty easy stuff that probably isn't really worthy of going here but I'll post about it anyway lol. So here is how you do it, you make a func_wall as you would normally do, then after you've made it you add a few keyvalues to it. First add a takedamage key and set it to 2, that allows it to take damage, obviously. Then you add a health field and set it to however much health you want the breakable to have. Then when it's health reaches 0 it will try to call the function in the th_die field, if there isn't one the map will crash as I found out :D So add th_die and set it to SUB_Remove or any other function that calls SUB_Remove at some point, depending on what your needs are. Optionally you can add an armortype and armorvalue to give the breakable damage resistance so it can be broken with some weapons but not others. I haven't exactly figured out how to customize the sound it makes when you hit it or break it yet but I will keep trying and see if you can do it without needing a mod 
Previous Post Continued 
So after a little more discussion I've figured out how to add sound playback to the breakable, so the full setup looks like this:

takedamage = 2
health (whatever you want it to be)
armortype/armorvalue (whatever you want it to be
noise (whatever sound you want the brush to make when you hit it but don't break it)
th_pain = train_wait (plays sound in noise field whenever you hit it)
th_die = SUB_UseTargets (targets 2 separate info_notnull's that play the sound you want to play when the object is broken and removes it, respectively)
target = the name of the 2 notnulls

Notnull 1
targetname = whatever you put in the target field of the breakable
noise = the sound you want to play when the breakable breaks
use = train_wait (play the sound when triggered by the breakable dying)

Notnull 2
targetname = same as the first one
killtarget = name of the breakable
use = SUB_UseTargets (remove the breakable when this gets triggered by it dying)

Please feel free to correct me if something I put is incorrect, I'm still pretty new to q1 mapping and map hacks especially. But map hacks are really fun and I've almost become more interested in them than actual mapping at this point (but not completely though) :P I'm also trying to think of how to add rotation to a turret hack I made last week but I haven't really checked any of the quake c sources related to rotating functions to see which ones I might be able to use 
Hi Therektafire 
That's a really well constructed and described hack. Welcome to the thread!

In terms of rotation, a warning and two pointers. First warning is that standard Quake just doesn't do collision on rotation. The amount of highly specialised code that mods apply to get even crude approximation of rotating solids, I wouldn't expect a hack to be able to get anything like collision working.

If you just want visible rotation things are better. There are already suggestions in this thread about how to use avelocity for simple looping animations. If you're looking for something more triggered, you might want to look at SUB_CalcAngleMove. Although any entity which used the function got cut from the final release of Quake, it's still available for hacks to use.

Alternatively, you might want to look into the AI functions if you'd like rotations that follow the player. You need to set quite a few keys on an entity to trick the game into running some of the built-in AI stuff for turning to face an enemy, but it should be possible. More advanced stuff, but something to get your teeth into... 
Having your breakable also create some info_notnulls using external .bsp models for rubble and have a movetype 6 would be cool too. Can't remember a good way to give them starting velocity at the moment though and still be triggered on break. 
Thanks :) I got the idea for the armor from one of your articles I may add it to the turrets too if possible. Speaking of, I will definitely look into the AI turning/rotating functions to see what I can do with them 
How can I make worldspawn shootable and killable?
Perfect accuracy gameplay challenge... 
A Trigger Curiosity 
So, I was idly tugging my way through some of the vanilla QC files, and noticed functionality I was hitherto unaware of!

In the blurb for the trigger_once entity, it says this:

if "angle" is set, the trigger will only fire when someone is facing the direction of the angle. Use "360" for an angle of 0.

The code to do this seems to be in there, but I cannot recall a single time in the id1 levels where I noticed this behaviour.

Is this used anywhere in id1, and if so where?

Yours curiously... 
one place is on start.bsp
those 'this hall selects foo skill' centerprinting triggers only display their messages when you're facing towards the teleports. walk backwards into the teleporters and you won't see the messages at all. 
Two Custom Map Examples 
Rehashing Old Work 
I didn't bother to dig into the whole backlog of messages here, but I made a (fairly simple) hack that allows for killable "static" entities. I've tested this with flames, but not with other things, I suspect that light globes may work.

step one, make a trigger under the player spawn and make it target an info_notnull called "flame". Make sure this info_notnull is some distance from the player, as touching it too early will crash your engine.

Place a "light_flame_large_yellow" somewhere in the map to precache the model.

give the info_notnull the following keys:

targetname flame
model progs/flame2.mdl
frame 1
use func_wall
think PlaceItem
nextthink 2
mdl progs/flame2.mdl

This should now allow you to killtarget the flame entity. Note that static ents don't occupy the edict list, however this hack will. I guess it will also allow for a touch function to be run on it after this point too.

One final thing to consider when using this hack, touching this entity before its had its "nextthink" even by a monster will crash the game. Even shooting the flame will crash it. I suggest spawning them well away from players and monsters.

The nextthink function forces the notnull entity back to a non-solid non-bsp state whilst retaining the flame model. In the example above this happens 2 seconds after it spawns. 
(oh, the trigger should be a trigger once) 
those 'this hall selects foo skill' centerprinting triggers

Blimey, I didn't have to go far then to find one. 
That's a fair amount of work for a killable flame. Rather than messing with thinks and nextthinks and all that, you can just set the modelindex of an info_notnull to that of the spinning flame model (flame2.mdl, check in the console first to see which slot it takes of course) and have a simple displayed model that you can killtarget like normal, no extra futchery with crashing when touched or anything. The flame will automatically do its snazzy little spinning and burning animation, similar to a backpack, and the frame field changes the size with 0 being the smaller flame model (light_flame_small_yellow) and 1 being the larger version. Old example webm here
the flame models are static and don't appear in the edict list though? 
They're still given a modelindex, no different from the player or enemy models or worldspawn/brush models. Not sure how to find which model has what number in Fitzquake-derived engines but Darkplaces (ugh) has a handy modellist command that will print out every model currently loaded by the game in order. Worldspawn comes first, then count the list by one. Worst case scenario, experiment a bit until you find the right modelindex and remember to place things in the right order that enemies/health changing by difficulty won't break the hack. 
Worst Case Scenario 
You might have to make separate entities for different skill levels, with each having the correct model indices for the corresponding skill levels. :/ 
Move On Up 
Moving the static torch you're using to precache the model as near to the top of the entity list as possible will help to stabilise the modelindex across all the skill levels in your map. Also worth remembering that each time you add a brush entity, that adds one to all the precache modelindex values. So you want the map to be basically finished in that respect before you finish off the hack. 
Rotating Turret Hack Finished (mostly)! 
Hey guys, back for another update. My rotating turret hack is almost 100% done :D I just need to take a few minutes tomorrow to iron out some little kinks related to the offsetting of the body model in relation to the shots and it will be good to go and I can make a demo map and full write up on it. In the meantime here is a weirdly rotated screenshot from QuakeDroid showing it in action in a crappy little box room :) 
The Absolute Fucking Madman 
Eagerly looking forward to seeing it in action. 
Nice that a "newer guy" can make cool stuff! 
If what he's posted in #tf and related channels in such short time is any indication, rekta is a new maphax savant. 
I mean it's not that impressive, you can do it easily if you have basic programming knowledge and take the time to read the sources to know what fields and functions you can and cant use where... Or in my case, try and figure out why entire segments of code were replaced and moved elsewhere but still in the original files commented out, then get confused when what you want to do isn't working the way it should :D it's not like I'm making Quake Rally 2 or something like that... Though I do like racing games so maybe I'll give that a shot some day ;) 
Rotating Turret Writeup/demo Map (part 1 
Ok, so, here is the write up on the rotating turret hack. Now my setup probably isn't the best but it works fine, at least in SP, so I'll probably keep using it in maps going forward anyway. It's not too difficult to set up but there are several steps involved. Also apparently this is too long to put in one post since the character limit is 5k and I have more than that :O So i will need to divide it into multiple parts.

So, here is how you do it. First at the map origin you need to set up the model of the turret itself. Of course I suppose you could use a custom mdl but these are vanilla maphax we are talking about here :) Now after you make it you might need to move it up a little depending on the type of projectile you want to use so it doesnt look like complete crap when it shoots, I used hknight_shot so I had to move the model up a few units to get it to look right. After you made the model you need to turn it into a brush entity so it will have a model and modelindex value, I used func_wall. And of course you should encase it in a box to prevent leaks and add appropriate lighting. Then add a info_notnull in the spot where you want the turret to be and give it a target name like "turretmain" or something, it will be the main turret body. Now you will want to copy the main model to the notnull, you do that by setting the modelindex and model fields to the same model and modelindex values of the turret model you want to use, if you want to have multiple different styles in your map you need to create multiple models. You can find these values using the "edicts" command in the console, if you want to be able to find the edict numbers of the turret models easier just cut and paste them to the top of your .map file just under worldspawn, that should make things a little easier since now they should be closer to the top of the edict list. In my case the model was *1 and modelindex was 2.0, so I used those. So so far you should have something that looks like this

.....origin = whatever the position is that you placed the notnull at
.....model = *1 (or whatever the model number of your model is)
.....modelindex = 2.0 (same as above)
targetname = whatever you want the targetname to be i guess.

Now if all things went well when you go into your map you should see your turret in the spot where you placed it. Good. But, it doesn't shoot obviously, or rotate either :( SO we need to fix that. Unfortunately I couldn't figure out a way to get any "smart" player detecting functions working so it can only really reliably track 1 player meaning this hack is technically SP only for now. But that's ok, you can just make multiple copies that track specific players, no big deal. First add an "enemy" field and set it to 1, this will cause it to track the first player since they are always the first entity loaded in a map. Now let's get the rotation part out of the way first. For the rotation to work properly we need two things, we need to add a "yaw_speed" field to the turret that contains the speed that we want it to rotate at, and a function that consistently sets some specifc values, specifically ideal_yaw and angles_y. Luckily there is a function that does just that for us, ai_face. So we need to put that somewhere, but where is a little tricky. We can't put it in think because neither ai_face or ChangeYaw (the helper function that ai_face calls that actually rotates the model) resets nextthink meaning it would only run once which isn't exactly ideal. There are 2 options that we as the mapper can consistently control though, use and th_pain. So we can put our rotation function in one and the shooting function in the other, it doesn't really matter which one since the pain state of the turret will need to be activated by a use'd entity shooting at it anyway. So I put ai_face in use and the shooting function in th_pain, in my case hknight_shot. So now it should look like this: 
Part 2 
.....origin = whatever the position is that you placed the notnull at
.....model = *1 (or whatever the model number of your model is)
.....modelindex = 2.0 (same as above)
targetname = whatever you want the targetname to be I guess
yaw_speed = the speed that you want the turret to rotate at
enemy = 1 (or whatever the player number is that you want it to target)
use = ai_face
th_pain = whatever shoot function you want the turret to have, only *MONSTER* shoot functions can reliably be used as far as I can tell since I haven't been able to find a function that will reliably set the values required for you to be able to use player weapons effectively, you can still technically use them, you just can't constantly re-aim them so they will either always shoot in one direction or shoot wherever the player is pointing at the time, depending on how you have it set up. Who knows, maybe that's what you want and you can find a use for that, but this "tutorial" of sorts is about hostile turrets that attack the player, not shoot in the direction they are facing ;) Oh yeah, and the monster whose shoot function you want to use needs to be precached in the map first.

Now as you can probably imagine, we need to set up some triggers so that the turret will do it's thing. So make 2 identically sized trigger volumes that take up the exact same area that will correspond to the line of sight of the turret, of course they can be multiple brushes if you want a concave shape, it just matters that they are targeting the things they should be. One of the triggers should target the turret itself, which when the player steps on it will cause the turret to rotate since its use function causes it to do that. The other trigger will target a new notnull that we need to add in the exact same position as the turret one which is supposed to trigger the turret's pain state, causing it to shoot. It will do that by being inside the body of the turret and constantly shooting it with it's own projectiles. Of course for the turret to be in pain it needs to have health, so you should add a health field to it and set it to whatever you want. You also need to set "armorvalue" and "armortype" as well, so that the turret won't kill itself by being shot by its pain trigger. If you want it to be destroyable you should set the armortype to soak up exactly as much damage as the triggering projectile will give (a tutorial on how to do that is given by Preach here and make sure that the player will have a weapon at that point that does more damage than that. Finally, you need to add 3 more fields, "solid", "takedamage", and "movetype", and set them to 4, 2, and 7 respectively. The solid and takedamage are set so that it will, you know, be able to be shot and take damage, and movetype 7 (PUSH) is required by solid 4 or else the map will crash.

So now that the turret is all set up to get shot and in doing so shoot at the player, now we need to add the notnull that will be firing those trigger shots. This is suuuuuper easy. just add an info_notnull in the exact same position as the turret and give it a targetname, in my case "turrettrigger", a use of hknight_shot, and an enemy of whatever the edict number of the turret's notnull is, in my case 7. Now when it is triggered, it will shoot at the turret, which will cause it to go into "pain", which will cause it to shoot at the player since that's what it's pain function is set to do! And it will rotate as well assuming you have another trigger covering the same area targeting the main turret itself.

And thats about it! Now you should have a turret that, when triggered, shoots at the player and rotates to track them! The final setup looks something like this:

notnull 1 (turret)
.....origin = whatever the position is that you placed the notnull at
.....modelindex = modelindex of turret model you want to use
.....model = same as above
.....targetname = whatever you want the targetname to be I guess
.....yaw_speed = the speed that you want the turret to rotate at
.....enemy = 1 (or whatever the player number is that you want it to target)
.....use = ai_face
.....th_pain = whatever shoot function you want the turret to have, taking into account the restrictions outlined before = whatever
.....armortype = minimum value required to negate damage from triggering projectile but not from more powerful player weapons
.....armorvalue = a number high enough to where it wont go down when it gets shot, i believe 999999999 is a good amount, Preach has an article on this topic)
.....solid = 4
.....takedamage = 2
.....movetype = 7

notnull 2 (turret shoot trigger)
.....origin = same as the turret itself
.....targetname = whatever
.....use = hknight_shot
.....enemy = entity number of turret 
Demo Map And Map Source 
Here is a link to a zip containing a small crap box demo map showing the turret in action and the map source I would have taken the time to make a somewhat better demo map but this took a little longer than I expected to write since I suck at trying to explain things lol, so I just decided to throw out the map I used for testing instead of making a somewhat more realistic use case environment. As usual if you have corrections or tips for improvements feel free to point them out :) 
Haven't read this yet but GG. Grabbing my reading glasses. 
Well parts of it might be a little overexplained which accounts for some of the length lol. I wanted to be really informative though and make sure people get it so maybe it's ok. 
Holy shit, you got it working and working well to boot. Hell of a write up and a tricksy workaround with the th_pain bit, almost surprised you didn't find some evil way to make it rotate vertically as well as the usual horizontal rotation. 
Cool Turret 
Another impressive hack, well done. It's also inspired me to finish off an article I've been working on for a while. It's an ode to the oft mentioned function while hacking: SUB_CalcMoveDone

If you want to know the best way to make a gib fountain, or what the "Duke of York" hack is all about, come have a read... 
I am just getting started "cutting and pasting" QuakeC. I followed your recently revised tutorial on monster spawning here:

I'd like to add a small random delay automatically to each teleporting monster as you can do in Quoth. Reason is I am using custents multiple triggers to trigger these delays spawns. As in Quoth it would be nice to have a little variation on the timing if the monsters all share a targetname.

Would this be as simple as modifying this:

//override the random delay some go functions apply
self.nextthink = time + 0.1;
spawn_tfog (self.origin);
spawn_tdeath(self.origin, self);

to this:

//override the random delay some go functions apply
self.nextthink = self.nextthink + random()*0.5;
spawn_tfog (self.origin);
spawn_tdeath(self.origin, self);
I was finally able to try this last night. Does do it. Any hints would be appreciated. 
Typo Above 
Doesn't do it. 
No Expert Here But... 
Should it be

self.nextthink = time + random()*0.5 
I tried that as well. It's going to be a bit more complex I think. 
Don't Have The Source Files On This Computer 
What values does the random function give? Anything between 0 and 1? Does the function require parameters? Like random(5) giving values between and 0 and 5? 
Just googled the answer myself. 
QuakeC Questions 
would be better discussed in the Coding Help thread. 
Apologies. I associate this thread with Preach and forgot it was more of a hacks thread. 
See my suggestion in Coding Help 
Very Interesting Stuff All This Is, But I Have A Question. 
First off I mostly play a form of teamfortress, regtf, custom, and megatf. I've noticed a lot of maps use trigger_hurts to simulate mine fields and things of similar sort. I wanted real exploasion, real particles, and I used the infomation here in this to do just that. It's targetable or touchable however you need it, but it only fires once. Nothing I have done will make it work again. Is there a way to reset an info_notnull? 
You probably tried the barrel_explode hack which indeed only works once. The only way I could imagine for this to work without custom code is using a W_FireRocket hack that shoots a rocket right into the ground. It can the used multiple times because you can set its ammo count to a very high value. Of course there'll be the rocket launch sound, but that's probably acceptable. Read above to see how it's done. 
I See, So It's Relying On The Ammo In Needs. 
"classname" "info_notnull"
"use" "GrenadeExplode"
"enemy" "1"
"group_no" "1001"
"health" "1"
"targetname" "proxi1"
"nextthink" "0"
"origin" "-264 -90 -352"

I'll try adding this to it and see if that helps.
"no_grenades_1" "200"

thanks btw. 
Well My Way Doesn't Quite Work. 
I could perhaps use the rocket like you said, however, I was hoping more to use effects from something not a trap already. Like triggering detpacks, or airstrikes. So far the only thing that keeps firing are monster attacks. Now consider these mods are stripped down, there are no monsters so none of their effects can be used. I'm starting to think I've gone about this wrong, and theres a better hack, but I only noticed this a week ago. I am at a huge loss right now, I'm quite ignorant. 
You should take a look at MechTech's progref.

There are several examples of what can be done within the commen progs.dat.
It's just a way of placing map entities with the right statements.
The first example is a trigger_multiple for lavaballs. I think it is easy to change it to GrenadeExplosion. 
Thanks Madfox 
I will surely look right now. 
Reading, Reading And More Reading, But 
The more I try things the better it gets, so far I have managed to find a repeating explosion. However, it always targets 0 0 0. Is there anyway I can simulate a players perspective to get a fixed point other than 0 0 0. That's what the code is calling for, someone to paint a target. 
Which funtion name are you using? W_FireGrenade? 
Not Quite 
I know you all recommend using standard quake progs, I am using the tf mod. It's not going to be updated. I used airstrike_target. I cannot use monster skills, well there are some but limited to zombie, grunt, dog, and fish. The rest of the code was stripped down to make room for the tf classes and abilities. I'm having to go through the qc and find function names. Trial and error for me at this point. 
Multiple Explosions 
The difficulty with a hack that lets an entity repeatedly explode is the explosion sprite. Typically the entity that explodes gets turned into the sprite, and the last command in the sprite animation sequence is deleting yourself.

I think you could pull something off though, using SUB_CalcMoveDone as a use function to cancel the removal on the sprite just before it happens. You'd need a second field like th_pain to be setting off the explosion I guess, not tried to build all this but it sound feasible... 
place a spawn and a scrag in the map

place the spawn somewhere else because we only want him for the precaches

give the scrag a touch key, set the value to tbaby_jump1

run up and bump into the scrag
there will be error messages, but shit is hilarious. 
Works Spookily Well 
Dang if only I werent at work 
Lightning Without Event_lightning 
I'm working on a gate where flashes should light to a central point. I've tried event_lightning with gate_logic and read everything about it. This does not seam to work because it's not continouse and also not continouse triggable.
I thought about using a lightgun to direct it to an info_null.
Has someone an idea or solution to this? 
See post number 11 on this page. Click the thread name to load all posts. Not sure how to bookmark a post 
Extra Trick 
Thanks. Will check it out. 
Metal Gear Solid Map (question For The "progs Whisperer Preach) 
Hey Preach, I'm a really good friend of Shamblernaut and a lot of the guys at the Quake speedrunning scene/Discord. I've been making Kaizo (insanely hard and novel) maps for an episode. I'm starting the 6th map and wanted it's theme to be, stealth. Now sure invis rings are great for this, but I want parts of the map to require you to dodge pathcorner monsters without invisibility using swift movement and other tricks. However, I want it so that if 1 monster is aggro'd (by seeing you, you shooting them, etc.) that ALL specified monsters in a group/unit are aggro'd as well immediately. Not just upon said monster's death. I've tried all manner of map hacks and the closest I got was using the touch function in conjunction with SUB_UseTargets. But obviously that won't suffice. I want a group of monsters to aggro as one unit, REGARDLESS Of line of sight if any of them are aggro'd. Is this at all possible? Thank you so much in advance. <3 
Hm well it could be doable but you might need to design your map in a specific way. My first instinct would be to have the monster set up to where its path comes near several triggers or maybe is even completely bordered by triggers, said triggers would be what aggros the other monsters if one spots you and deviates from its path, now the obvious problem with that is that the player could trigger it too, im not sure if setting the owner to 1 (the entity number of the player in SP games) would help prevent the player from triggering it or not since I haven't tried that before but I guess its worth a try? 
Not A New Trick... 
Just noticed in the id QC, if you "use" a func_wall it toggles its animated texture sequence.

I can't recall ever seeing this in action in the original maps - was it ever used? 
I don't think so, but it's relatively well-known and is listed in most documentation you can find online. Sort of the opposite scenario of something like directional trigger volumes, which are used in the start map but rarely mentioned anywhere when looking for information. 
directional trigger volumes

Holy shit i'd forgotten about those.

Seems we need some kind of resource of "things quake is designed to do but no-one knows about". Sort of the slightly more straight-edge, but still cool, cousin of this thread. 
Kinn said:
Just noticed in the id QC, if you "use" a func_wall it toggles its animated texture sequence.

This is actually surprisingly annoying from the point of view of hacks, because it means you can't set the use function on a func_wall in a hack - in fact it's nearly impossible to set a custom use function on any solid brush entity. It is used in the high framerate animation hack though, so not a complete loss.

FODDER said:
...However, I want it so that if 1 monster is aggro'd (by seeing you, you shooting them, etc.) that ALL specified monsters in a group/unit are aggro'd as well immediately...

I've come up with a new hack, that's pretty interesting, but doesn't quite do what you want yet. I think it would suffice for static monsters, but would be nearly impossible to use for patrolling monsters without some false positives (which is of course the worst possible thing imaginable for stealth gameplay).

I'll keep playing with it a while to see if I can work around that somehow. If not, I'll write up what I found and share it anyway. I think the functions which the hack uses are the ones you'd need to modify the QC to get the desired effect - so it might prove useful in a roundabout manner anyway. 
New Year, New Hack 
Here's the idea I came up with over the weekend - Security Cameras!

You can train a security camera on a static monster and it'll always notice if that monster has been alerted (with a bit of fiddling you can also ensure that it never sets off by itself, even if the monster is killed under its nose). The problem is that this doesn't generalise to a moving monster, so it doesn't quite do what FODDER was after. Still, I think it's a pretty cool idea in its own right. 
Progdefs.h Is Out Of Date 
I'm trying to change some things about a the swinging hook mod that require it to be recompiled. I can get the code to compile and have no problems when changing the game over to the mod. When I try to load a map or start a new game VkQuake gives the error:

Host_Error: progs.dat system vars have been modified, progdefs.h is out of date

I'm new to Quake C so any help would be nice.
If its helpful this is the progs.src


I am pretty new to this myself but it's very important to not change certain things in defs.qc.

If you change anything above line 220 (give or take) you are asking for trouble. The rule of thumb is don't change anything above

void end_sys_fields; // flag for structure dumping

Not sure if this is your issue but good info nevertheless. 
new to QuakeC, and yet your progs.src is lacking monsters?
Sounds like you're trying to compile a QuakeWorld mod instead of a (Net)Quake one.
The two are similar but mutually incompatible (primarily but not exclusively due to changes above end_sys_fields).

If you truely want to run a QuakeWorld mod then use a QuakeWorld engine (eg: FTE, ezQuake, or MVDSV). (Net)Quake engines like VkQuake, QuakeSpasm, or even DarkPlaces cannot run QuakeWorld gamecode. 
Its probably the quakeworld thing since I have not touched defs.qc. I'll try that, thanks. 
That Was The Problem 
Thanks for the help. It works now. 
TY Preach 
I appreciate that new map hack idea a lot Preach <3 even if it isn't exactly/fully what I needed (since I had ideas for patrolling monsters) I still will definitely look into it. I'm putting off my Metal Gear Solid map for now until my 2nd Kaizo Quake episode now since, as you can imagine after making this hack, getting what I want is virtually impossible in vanilla Quake sadly. :[ 
Controllable Models 
I'm needing a way to control a mdl with an entity. So when I target it it will start frame group 2 and it's series of animation. I tried using an info_notnull, and I must have gotten close but the server shutdown with non bsp model error. 
Custom Model 
Hi Aberrant. I think there's little chance of that being possible with a map hack. I'm unaware of any hack in vanilla quake that allows inclusion of a custom model the way that misc_model entities allow in some mods.

Quoth's equivalent does come with the ability to toggle between two framegroups, but you need to set the model up so that those two framegroups are frame 0 and frame 1. See full details at 
If my guess is correct, Aberrant isn't looking to load totally custom models, but to use existing ingame models and animate them when activated; e.g. using an info_notnull to display a monster's model, and then make the 'fake monster' display one of its animations (run, shoot, die, etc) when the notnull is triggered by something else. 
Does QuakeSpasm, QSS, FTEQW or Darkplaces support custom (QC-defined) interpolation timing for MDL frame animations?

Makaqu supports this through self.frame_interval, but I'm not aware of any hardware-accelerated engine that does. 
Fitzquake variants have it in the protocol but it’s not directly controllable from qc — it uses the nextthink field to decide how to set it and caps it at 1 second 
Ok, thanks.

By the way, what are the known engine-independent methods for fixing the problem of the player sliding over the heads of the monsters when he jumps on them?

I've tried setting a .touch function on the player, to detect when the player touches a monster, but it's not working. 
Good question ... I fixed it in-engine in early builds of fitzquake but then removed the fix later once i realized it's a bad idea to make bug fixes that change gameplay. In my readme I said "this bug can be fixed in quakec also" but I have no memory of how. Maybe setting the .solid of monsters to a different value? SOLID_BSP? 
Needs to be a monster touch function
Also works if you set it on exploboxes

void() monster_touch =
if (other.classname != "player")
if ( <= 0)

if ((!other.flags & FL_ONGROUND) && (other.absmin_z >= self.absmax_z - 2))
other.flags = other.flags + FL_ONGROUND;
That worked, thanks c0burn. 
also this stuff should be in Coding Help thread. 
I had forgotten about Coding Help; can that thread go to the Permanent Threads section? 
First | Previous | Next | Last
Post A Reply:
Website copyright © 2002-2019 John Fitzgibbons. All posts are copyright their respective authors.