ScratchCSQC?

Discuss CSQC related programming.
Seven
Posts: 301
Joined: Sat Oct 06, 2007 8:49 pm
Location: Germany

Re: ScratchCSQC?

Post by Seven »

Hello toneddu2000,

Thank you for post. I am glad that it works in fte. dp doesnt do me that favour :)
It is not a drama. I know now that csqc is not for me and that is ok.


Hello Spike,

Thank you very much for extending the "types" in your fteqcc. Now it compiles smc just fine.
The progs.dat became even smaller compared to older fteqcc version. :)

Some people tend to forget that it is you who makes Quake modding possible.
Without you Spike, I would not even be able to compile the messy gamecode of smc. frikqcc isnt working.
Others would not be able to use csqc. And the list is even longer...

So, Thank you very much for beeing here for us modders and make Quake modding (with extensions) possible !

Quake wouldnt be what it is without people and devs like you.
toneddu2000
Posts: 1395
Joined: Tue Feb 24, 2009 4:39 pm
Location: Italy

Re: ScratchCSQC?

Post by toneddu2000 »

it works on DP too


added,as said before, a new key in worldspawn entity on NetRadiant with key worldType and value 2

ssdefs

Code: Select all

.float(entity playerent, float changedflags) SendEntity;
.float SendFlags;
float MSG_ENTITY = 5;
.float	worldType;
ssmain

Code: Select all

float SendWorldType(entity playerent, float changedflags)
{
	msg_entity = self;
	WriteByte(MSG_ENTITY, ET_WORLDSPAWN);
	WriteByte(MSG_ENTITY, world.worldType);
	return TRUE;
}

void PutClientInServer()
{
	local entity playerspwn = 		find(world,classname,"info_player_start");
	self.origin = playerspwn.origin;
	self.angles = playerspwn.angles;
	self.health = 100;
	self.movetype = MOVETYPE_WALK;
	self.solid = SOLID_SLIDEBOX;
	self.takedamage = DAMAGE_AIM;
	setsize (self, '-128 -128 -128', '128 128 128');
	self.fixangle = TRUE;
	self.flags = FL_CLIENT;
	self.classname = "player";
	self.SendEntity = SendWorldType;
	self.SendFlags |= 1;//update sent value, maybe put this in a think function if you need a reiteration
}
csdefs

Code: Select all

float wType;
csmain

Code: Select all

void CSQC_Ent_Update (float isnew)
{
	local float i = ReadByte();
	local float wt;
	if (i == ET_WORLDSPAWN){
		wt= ReadByte();
		wType = wt;
	}
}

void CSQC_UpdateView(float w, float h)
{
	centerprint(ftos(wType));
}
it prints 2 on center of the screen, if I change the worldType key in NetRadiant to 3 it prints 3.
If also this is not your goal, maybe I didn't understand what you're trying to achieve
Seven wrote:It is not a drama. I know now that csqc is not for me and that is ok.
No, don't say that. It's just a matter of trying and re-trying!
Seven wrote:Some people tend to forget that it is you who makes Quake modding possible.
Without you Spike, I would not even be able to compile the messy gamecode of smc. frikqcc isnt working.
Others would not be able to use csqc. And the list is even longer...

So, Thank you very much for beeing here for us modders and make Quake modding (with extensions) possible !

Quake wouldnt be what it is without people and devs like you.
Saint words. Spike IS quake. :D
Spike wrote: @toneddu2000:
there is no practical difference between 32bit and 64bit qccs - it refers to the instruction set the compiler executes, not what it generates.
when it comes to windows, I tend not to bother with 64bit on account of both microsoft and third parties not supporting it so well.
ok, thanks. I'll use 32 bit though
Meadow Fun!! - my first commercial game, made with FTEQW game engine
Seven
Posts: 301
Joined: Sat Oct 06, 2007 8:49 pm
Location: Germany

Re: ScratchCSQC?

Post by Seven »

Hi toneddu2000,

Your code works I see the correct value on the centerprint, but the player is spawned in every map at coordinate '0 0 0' and cannot move.
No monsters are spawned as well.

I think we must not put the player into/through csqc, because there is no code to update him.
There must be a way to only give the world.worldtype value to csqc without manipulating the player (self).

Maybe Spike can help here ?

I am already happy that I see the correct world.worldtype value on the screen now. :)
Maybe it is now only a small edit to leave the player entity as it is, so that he starts at map spawnpoint and not at '0 0 0' ?

I already tried to use this inside ssqc´s PutClientInServer:
world.SendEntity = SendWorldType;
instead of this:
self.SendEntity = SendWorldType;

That fixes the player spawn position and all monsters are there as well, but the .worldtype value is again always '0' :?

Such a small value and such a big effort to bring it over... :)


EDITED:
Your code makes the function: CSQC_Ent_Update() mandatory.
I didnt have it in the csqc code until then, I fear that this the culprit for the player cannot move and is spawned at maps origin ?
Spike
Posts: 2914
Joined: Fri Nov 05, 2004 3:12 am
Location: UK
Contact:

Re: ScratchCSQC?

Post by Spike »

.SendEntity in ssqc causes the entity to be sent via the 'csqc shared entity' protocol _INSTEAD_ of the engine's normal protocol.
The client forwards the actual entity data to the csqc for the csqc to parse. The data itself is in a format that is completely unknowable to the client - the only thing the client knows is the entity number (and with that, it maintains context so that it can retain the same 'self' value for each call to CSQC_Ent_Update).
So yeah, the csqc is required to call readcoord etc and store that into the ent's .origin etc.
If the csqc wants the entity to be visible, the csqc can either explicitly call addentity on the entity, or set .drawmask to something so that the addentities builtin can add the entity (yay for bulk processing, this also provides the predraw notification just before the implicit addentity call, and is the normal way to interpolate or animate entities or other things that must be done per-frame).

seven, in your case, you might want to spawn some entity in worldspawn (not world itself as world is not normally networked). with that entity, you can then use customizeentityforclient and setorigin the entity to match the client's origin, thus ensuring that it does not leave the player's pvs. you will need to set a model in order to make dp happy (fte does not require this step).
so yeah, just use this single other entity instead of the player/world. job done.

using a 'shared' player is possible, but its really really messy, primarily because it requires quite a lot of hoops for you to jump through, and then it presents you with a lot of expectations that you must match existing features (read: prediction). These are not easy.
You can still query the player's position via getentity, of course, just make sure that you don't set SendEntity on ssqc's player entities until you're ready.

but yeah, the easiest way *should* be stats.
you could also parse periodic stuffcmds or something, maybe with a clientcommand sent from CSQC_Init so the ssqc knows to resend stuff after a loaded saved game.
Seven
Posts: 301
Joined: Sat Oct 06, 2007 8:49 pm
Location: Germany

Re: ScratchCSQC?

Post by Seven »

Spike wrote:seven, in your case, you might want to spawn some entity in worldspawn (not world itself as world is not normally networked). with that entity, you can then use customizeentityforclient and setorigin the entity to match the client's origin, thus ensuring that it does not leave the player's pvs. you will need to set a model in order to make dp happy (fte does not require this step).
so yeah, just use this single other entity instead of the player/world. job done.
Hello Spike,

That was the last puzzle piece. :)
Using the player did not work, but using a dummy entity and connect it via customizeentityforclient with the player works.
That was a really difficult birth, as a supposedly "easy" value translation could become a real struggle. Especially with DP´s restrictions in this area.
But now at least I learned something new.

Thank you Spike and toneddu2000


Just in case someone else will ever need a non-player-value in csqc again (based on original id1 gamecode):

add into ssqc defs.qc:

Code: Select all

.float (entity playerent, float changedflags) SendEntity;
.float SendFlags;
float MSG_ENTITY = 5;
float ET_WORLDSPAWN;
add into ssqc world.qc at the end of worldspawn():

Code: Select all

	local entity foo;
	foo = spawn();
	setmodel(foo, "progs/player.mdl");
	foo.customizeentityforclient = connect_me_with_client;
	foo.worldtype = world.worldtype;  // maybe not needed
	foo.SendEntity = SendWorldType;
	foo.SendFlags |= 1;
and just above worldspawn() add:

Code: Select all

float SendWorldType(entity dummyent, float changedflags)
{
	msg_entity = self;
	WriteByte(MSG_ENTITY, ET_WORLDSPAWN);
	WriteByte(MSG_ENTITY, world.worldtype);
	return TRUE;
};


float() connect_me_with_client =
{
	setorigin (self, other.origin);
	return TRUE; 
};

add into csqc defs.qc:

Code: Select all

float wType;
float ET_WORLDSPAWN;
add into csqc main.qc:

Code: Select all

void(float isnew) CSQC_Ent_Update =
{
   local float i;
   i = ReadByte();
   local float wt;
   if (i == ET_WORLDSPAWN)
   {
      wt= ReadByte();
      wType = wt;
   }
};

void()CSQC_Ent_Remove =	// or DP will drop when dummy ent gets out of players pvs
{
   remove(self);
}; 
Then you can use the float wType (for example in CSQC_UpdateView() ):

Code: Select all

cprint(ftos(wType));

or 

if (wType == 2)
... do something


Also savegames seem to work. As worldspawn() is always called when loading.

Best wishes,
Seven
toneddu2000
Posts: 1395
Joined: Tue Feb 24, 2009 4:39 pm
Location: Italy

Re: ScratchCSQC?

Post by toneddu2000 »

Glad you made it working, Seven. The example I post you it wasn't meant to be complete, it was just an explanation about how SendEntity works. The player didn't move because the placeholder position was at '0 0 0', instead of self.position.
Usually you set this kind of position for things that don't move (like a message to be sent or a variable like score or so).
Usually, you update SendFlags in PlayerPostThink, otherwise player remains still at middle air.
If you want to make a fully CSQC client-server relationship, you can write, in your send function, all the values that need to be shared with CSQC (origin,angles,velocity,v_angle,health,weapon,etc.) and read the same values in CSQC by CSQC_EntUpdate (premitting the ENT_ constant in a switch or if/else cycle to distinguish every entity reading). Remember that vectors need to be split in self.origin_x = WriteCoord();self.origin_x = readcoord(); and so on. Don't use WriteShort / readshort or your movements will result laggy (I tried first! :lol: ).

Cheers
Meadow Fun!! - my first commercial game, made with FTEQW game engine
drm_wayne
Posts: 232
Joined: Sat Feb 11, 2012 5:47 pm

Re: ScratchCSQC?

Post by drm_wayne »

Has anybody made something out of shpulds baseqc?
For some reason i cant get viewmodels get to work... i replaced the pistol.iqm with my own md3,
but it doesnt show up ingame :/
toneddu2000
Posts: 1395
Joined: Tue Feb 24, 2009 4:39 pm
Location: Italy

Re: ScratchCSQC?

Post by toneddu2000 »

No, I don't use Shpuld's code but mine, and I can say that the only method I could use, to display a viewmodel is to use the renderflag RF_VIEWMODEL in csqc. Hope it helps.
Meadow Fun!! - my first commercial game, made with FTEQW game engine
toneddu2000
Posts: 1395
Joined: Tue Feb 24, 2009 4:39 pm
Location: Italy

Re: ScratchCSQC?

Post by toneddu2000 »

last week I made a very imprecise answer, I'd like to make it more detailed.

To make a weapon visible in First Person View in CSQC

in your defs

Code: Select all

entity myweapon;
vector myweaponoffset = [0,0,-20]//tweak this to center/decenter weapon on view;
in CSQC_Init

Code: Select all

myweapon= spawn();
setmodel(myweapon,"models/myweapon.iqm");
setsize(myweapon,[-2,-6,-8],[20,6,8]);
myweapon.drawmask = MASK_VIEWMODEL;
myweapon.renderflags = RF_VIEWMODEL;
myweapon.predraw = MyWeaponPredraw;
weapon predraw function

Code: Select all

float MyWeaponPredraw()
{
	self.origin = myweaponoffset;
	
	return PREDRAW_AUTOADD;
}
Then just tweak myweaponoffset to make appear weapon where you desire

drawmask and renderflags are vital to make it become a viewmodel
Meadow Fun!! - my first commercial game, made with FTEQW game engine
Post Reply