2: A brief overview of the basic sample
So you've seen the basic sample, a static coloured triangle in the middle of the screen.  To do anything with it, we have to understand how.  The process is very, very simple.

Using a C program, we generate a data file containing a single GIFpacket.  This GIFpacket contains instructions on how to draw a triangle.

Then we generate a code file which says nothing more than "Send the GIFpacket that's in memory over to the GS and get it to draw it"  Then it loops back to the start to draw it again.

If you're happy with GIFtags and what they do, you can skip the rest of this lesson.  Move on to 3: Making your data file.  If not, grab hold of your GS User's Manual and your EE User's Manual, (Not any of the EE Core books) and read on.  I have version 5.0 of each of these manuals, they came with my Linux kit.  Thus, if you have a version other than 5.0, ignore my page references :)

Firstly, consider what a triangle is.  Amongst other things, it is a shape defined by 3 points (vertices), each joined to the other two, with the area between these three lines filled in.  The GS (Graphics Synthesiser) is perfectly happy drawing a triangle if you give it the position and colour of each of the 3 vertices.  You can think of the GS as a graphics card if you like, although the terminology doesn't sit well in the console world, as it implies the GS is an add-on part which could be changed.

To tell the GS to draw our triangle, we need to send a few bytes of data, preceded by a GIFtag, which acts as a kind of header, telling the GS what data follows.

Section 3.2 (Page 38) of the GS User's Manual tell us about GS Primitives, including the triangle amongst others.  It then goes on to describe an outline of a drawing procedure, and some examples of the drawing procedure for each primitive.  If you haven't read Section 3.2 yet, read it now.

In particular, the top of P42 shows an example of drawing a triangle.  First we set the PRIM register, then we loop through the RGBAQ and XYZ2 registers for each vertex.  After the third vertex, a drawing kick is performed for us, which renders the triangle.  Page 116 has details of the PRIM register, and similarly RGBAQ is on P119, with XYZ2 on P137.  Those pages tell you what format the data in those register is expected to be.

What about the GIFtag itself?  They're explained on P151 of the EE User's Manual.  As it says there, it has a 128-bit fixed length.  The interesting thing to note is the PRIM field from bits 57:47, which allows us to set the PRIM register right in the GIFtag.

Now we know what we need to accomplish.  Send a GIFtag setting the PRIM register to draw a triangle, then send 3 vertices worth of co-ordinates and colour info.


Filling in the GIFtag
NLOOP and NREG - This is where we tell the GS how much data to expect.  NREG is the number of registers we are setting.  We are going to set the RGBAQ and XYZ2 registers, so that's 2.  NLOOP is the number of times we loop through those register.  We are going to be sending 3 vertices, so we set that to 3.  That means the GS will expect 3x2 QWords of data to follow (A QWord is a measure of data length = 16 bytes or 128 bits.)

EOP - The explanation of this field is a little cryptic in the manual!  I think it should stand for "End of packet".  If it were set to 0, the GS would expect a second GIFsegment to immediately follow the first.  Set it to 1 and the GS knows that this is the last GIFsegment of the GIFpacket.

PRE - Are we going to send PRIM information within the GIFtag itself?  Yes we are, so set it to 1.

PRIM - The PRIM field itself is split up into a number of sub-fields corresponding to the fields of the PRIM register (P116 of the GS User's Manual)
PRIM - Type of drawing primitive.  We're drawing a triangle, so that's 011 (binary) = 3 (decimal)
IIP - Shading method.  The triangle is displayed with a mix of colours, so that's Gouraud Shading = 1
TME - Texture Mapping?  No thanks = 0
FGE - Fogging?  No thanks = 0
ABE - Alpha Blending?  No thanks = 0
AA1 - Antialiasing?  No thanks = 0
FST - Method of specifying texture co-ordinates.  We aren't using texture mapping, so it doesn't matter what we put in here
CTXT - Which context shall we use?  Let's use the 1st context = 0.  Contexts are generally used to allow the VU and CPU to operate on different parts of a scene at the same time without having to switch back and forth between different settings.  You may find an imaginative way to use them in your VU demo.
FIX - Fragment value Control.  Set that to 0 as well (Todo: I don't actually know what this field does!)

A word of warning: I recently answered a question on the forums relating to using REGLIST mode instead of PACKED mode.  In REGLIST mode, the PRE and PRIM fields of the GIFtag are completely ignored!  That means that, to use REGLIST mode, you must explicitly set up the PRIM register yourself.  Just something to bear in mind.

FLG - What mode are we going to send data in?  Let's use packed mode (See P153 of the EE User's Manual).  Packed mode = 0.

REGS - Which registers are we writing to?  RGBAQ and XYZ2.  Look on pages 119 and 137 of the GS Manual, on the right hand side it tells us the addresses of these registers - 0x01 and 0x05 respectively.  However, the field, like all other, is read right-to-left, so we need 0x51 in here.  Alternatively a list of all GS register addresses is on P158 of the GS Manual

Phew, all that to set up 1 triangle?  Yes, I'm afraid so.  Now though, we only have to put the data we promised, i.e. 3 loops through of the RGBAQ and XYZ2 registers.  Those of you who well versed in HTML will probably have done colours in RGB hex notation before, if not, just see the first two (hex) digits as the red component, the second two as the green component, the third two as the blue component, and the final 2 as the alpha component (which we aren't using yet, so we'll keep it as zero) To edit a colour to make it a little more blue, increment the 6th digit.  To make it a lot more blue, increment the 5th digit.

So, the data we send goes something like this:

GIFtag (described above)
RGBAQ: 0xFF000000 (A nice red)
XYZ2: (2048 - 100, 2048 - 50, 1)
RGBAQ: 0x00FF0000 (A nice green)
XYZ2: (2048 + 100, 2048 - 50, 1)
RGBAQ: 0x0000FF00 (A nice blue)
XYZ2: (2048 + 100, 2048 + 50, 1)

What are all those 2048's doing in the X and Y co-ordinates?  The GS treats the centre of the screen as co-ordinates (20248, 2048), so the co-ordinates (2048 - 100, 2048 - 50) really means (-100, -50) relative to the centre of the screen.

Homework
Before we see how the data file is actually generated, let's have a few little homework questions:

1) What (hex) digit should I increment to make a colour a little more red?
2) Change the above XYZ2 values to make the triangle fill the top-right half of the screen, assuming the screen is 640x224 pixels large (Positive X is to the right, positive Y is *down*).
3) Change the NLOOP field of the GIFtag to allow for a second triangle, draw this somewhere in the bottom-left half of the screen.
4) Create a second GIFsegment that allows for the drawing of a single blue point at (-50, 50) relative to the centre of the screen.
5) Modify Q4 to draw 5 green points in a horizontal line, starting at (-50, 50), spaced 10 pixels apart.

If you can answer these questions, then you can say you understand basic GIFtags.  Don't worry if you don't get it yet, some people work better with the theory up front, but some have to fiddle with a practical to get the answers... if you're on the practical side then lesson 3 will be right up your street.

Prev - 1: How does the harness work? Next - 3: Making your data file

Aside: GIFtags? GIFpackets? GIFsegments?
I'm probably guilty of abusing the terminology used in the manual somewhere along the line, so I'll try to clarify the terms I'm using here.  A GIFtag is the 128-bit long header that tells the GS what data to expect next.  It is followed by a data segment that has to be exactly the size and shape specified by the GIFtag.  If the EOP field of the GIFtag is 0, then this data segment is immediately followed by another GIFtag, and another data segment, and so on until a GIFtag with the EOP field set to 1 is encountered.  This collection of GIFtags and data segments is known as a GIFpacket.  As far as I'm aware, there's no word for the part of a GIFpacket comprising a single GIFtag and the associated data segment.  I'm going to call them GIFsegments.  This is not an official term, so don't expect to see it anywhere else :)