Greetings. First post.
I'm experimenting with generating map files from custom software. I was working on it with Q3A and finally sussed the old block format which was something like this:
Quote:
{
( 112 128 128 ) ( 112 128 1152 ) ( 128 128 1152 ) common/caulk 0 0 0.000000 0.062500 0.062500
( 128 1152 128 ) ( 128 1152 1152 ) ( 112 1152 1152 ) common/caulk 0 0 0.000000 -0.062500 0.062500
( 112 1152 128 ) ( 112 1152 1152 ) ( 112 128 1152 ) common/caulk 0 0 0.000000 -0.062500 0.062500
( 128 128 128 ) ( 128 128 1152 ) ( 128 1152 1152 ) metal_512x512 0 0 0.000000 0.062500 0.062500
( 112 1152 128 ) ( 112 128 128 ) ( 128 128 128 ) common/caulk 0 0 0.000000 -0.062500 0.062500
( 112 128 1152 ) ( 112 1152 1152 ) ( 128 1152 1152 ) common/caulk 0 0 0.000000 0.062500 0.062500
}
The new Doom3 Brush Primitives format is something like this:
Quote:
// primitive 5
{
brushDef3
{
( 0 -1 0 384 ) ( ( 0.0625 0 0 ) ( 0 0.0625 0 ) ) "textures/common/caulk" 0 0 0
( 0 1 0 -896 ) ( ( -0.0625 0 0 ) ( 0 0.0625 0 ) ) "textures/common/caulk" 0 0 0
( -1 0 0 384 ) ( ( -0.0625 0 0 ) ( 0 0.0625 0 ) ) "textures/common/caulk" 0 0 0
( 1 0 0 -896 ) ( ( 0.0625 0 0 ) ( 0 0.0625 0 ) ) "textures/common/caulk" 0 0 0
( 0 0 -1 896 ) ( ( -0.0625 0 0 ) ( 0 0.0625 0 ) ) "textures/archatron/arch_down_512x512" 0 0 0
( 0 0 1 -912 ) ( ( 0.0625 0 0 ) ( 0 0.0625 0 ) ) "textures/common/caulk" 0 0 0
}
}
The above two are not for the same block, BTW, just examples.
I understand the way the three sets of { 3 points } defining a plane of the Q3A map format have been change to a normal and a distance in the Doom3 brush primitives map format, and can output that geometry fine.
However texture mapping is another story. It took me ages to get the offsetX, offsetY, rotation, scaleX, scaleY system of Q3A sorted. Now it has been changed to some nighmarish system where the two sets of three numbers represent the first two rows of a matrix that operates on the plane to translate into texture coordinates... or something. Arrr!

I've looked at some of the old Radiant code regarding brush primitives but don't really understand it much. I pulled out this snippet:
Quote:
// compute back the texture matrix from fake shift scale rot
// the matrix returned must be understood as a qtexture_t with width=2 height=2 ( the default one )
void FakeTexCoordsToTexMat( float shift[2], float rot, float scale[2], vec_t texMat[2][3] )
{
texMat[0][0] = scale[0] * cos( DEG2RAD( rot ) );
texMat[1][0] = scale[0] * sin( DEG2RAD( rot ) );
texMat[0][1] = -1.0f * scale[1] * sin( DEG2RAD( rot ) );
texMat[1][1] = scale[1] * cos( DEG2RAD( rot ) );
texMat[0][2] = -shift[0];
texMat[1][2] = shift[1];
}
And found it converted some of the simpler texture mapping fine, but got other bits back to front, and made a total mess of anything involving rotations or anything complex.
The only hard info I've found is from
https://adidas.servegame.org/projects/buildutils/wiki/BrushPrimitiveswhere it says, amongst other things:
Quote:
After the three points that define the face follow the first two rows of a homogeneous 3x3 matrix A_ij, in the format:
( ( a11 a12 a13 ) ( a21 a22 a23 ) )
Where the a_ij are decimal values. (Homogeneous matrices have the bottom row as [0 0 1]).
Let n = (nx, ny, nz) be a unit vector normal to the face.
theta_y = arctan(nz / sqrt(ny^2 + nx^2))
theta_z = arctan(ny / nx)
theta_y is the angle between n and the XY plane. theta_z is the angle between n and the XZ plane. N.b. these results depend on division by zero returning Inf (IEEE floating point).
Let Bij be the matrix such that:
b11 = -sin(theta_z) b21 = sin(theta_y) * cos(theta_z) b31 = 0
b12 = cos(theta_z) b22 = sin(theta_y) * sin(theta_z) b32 = 0
b13 = 0 b23 = -cos(theta_y) b33 = 0
Note that there are many ways of finding a suitable matrix for transforming from world coordinates to face coordinates, but this is the particular one used by the Brush Primitives file format.
Let A be the homogeneous matrix from the texture definition.
Let r = (x, y, z) be a point in 3D space. Let t be the texture coordinates corresponding to r. Clearly, t = A * B * r
The BSP file requires two vectors u and v, and offsets in the u and v directions (k1 and k2), so that t1 = u . r + k1 and t2 = v . r + k2 -- in vector notation, this could be written as t = Mr where Mij is a 3x3 matrix such that M = AB.
I can barely make heads or tails of that, plus there's some code that seems irrelevant. I may have to get my hands dirty with that stuff, but first I thought I'd check if anyone already knew if this problem had been worked out for Doom3 Brush Primitives map format, and could point me to some handy information about how to create those 6 magic texture mapping numbers.