Unsure how some PVR features behave

If you have any questions on programming, this is the place to ask them, whether you're a newbie or an experienced programmer. Discussion on programming in general is also welcome. We will help you with programming homework, but we will not do your work for you! Any porting requests must be made in Developmental Ideas.
Post Reply
User avatar
Protofall
DCEmu Freak
DCEmu Freak
Posts: 50
Joined: Sun Jan 14, 2018 8:03 pm
Location: Emu land
Has liked: 9 times
Been liked: 5 times
Contact:

Unsure how some PVR features behave

Post by Protofall » Tue Jan 08, 2019 10:31 pm

There's a few small questions I have about the PVR that I can't figure out so I'll clump them into this one post
  • What are the Opaque/Translucent modifier lists used for?
  • How do you use the "oargb" parameter from the pvr_vertex_t struct? No matter what I set it to, no colours seem to change. I'd imagine this parameter (Or maybe the "pvr_poly_ic_hdr_t" struct?) is how you achieve effects like this (With Swampert fading to Blue) https://youtu.be/2oSfhNp-F_Y?t=41
  • When I used OpenGL 3.3, when mapping a texture we had UV coords (Like KOS's) and ST coords which together control texture-space and object-space would allow you to choose a sub texture and the region on the poly to display it, which could give you a cool "Texture repeat" pattern if the ST coords were less than 1.0. It seems by changing the UV-clamping flags I could do this in KOS with a whole texture, but not with a sub-texture (Specific section of a texture). Is there another way to do this in KOS with a sub texture?
  • In KOS, what are the main differences between Sprite mode and Poly mode? Right now the only ones I can list are Sprite mode is faster (1 pvr_prim call instead of 4), sprite mode has no dz and duv params (Instead they are interpolated), poly mode has the colour parameters (o/argb) and the 16/32 bit UV coord difference affecting in Sprite mode with textures larger than 256 by 256. Are there any other major differences I'm forgetting?
Made a recreation of Minesweeper for the Dreamcast <viewtopic.php?f=34&t=104820>
More is yet to come :wink:

Twitter <https://twitter.com/ProfessorToffal>
YouTube (Not much there, but there are a few things) <https://www.youtube.com/user/TrueMenfa>
User avatar
BlueCrab
The Crabby Overlord
The Crabby Overlord
Posts: 5393
Joined: Mon May 27, 2002 11:31 am
Location: Sailing the Skies of Arcadia
Has liked: 1 time
Been liked: 12 times
Contact:

Re: Unsure how some PVR features behave

Post by BlueCrab » Wed Jan 09, 2019 10:45 pm

First off, moved to Programming, since it makes more sense there...

Second, to the questions...
1. The modifier lists are for sending modifier volumes, which change parameters of polygons that are "within" them. They can be used to do things like shadowing (by changing colors), or for changing texturing data, etc. They're pretty powerful, but not exactly easy to use. Unfortunately, there's not all that much in the way of documentation about them, which makes the situation worse.

2. You want to use the argb value to do that fade-to-blue effect. Not oargb. The oargb is used in specular highlights.

3. If I'm understanding what you're asking for, the hardware doesn't really support that, so no you can't do it without breaking the texture up manually (I've never done OpenGL 3.x, but considering the DC's hardware is roughly on-par with OpenGL 1.2ish...).

4. Sprites are handled differently in the hardware. They're not really meant for 3D objects, but if you're doing 2D stuff, then they're quite useful. They do have less data that has to be transferred across to the PVR, which is a bit of a benefit. Yes, the use of 16-bit U/V coordinates can cause some inaccuracy, but generally it shouldn't be a huge problem. I'm not really sure what other differences you'd be looking for, so I don't really know what else to answer this with.
User avatar
Protofall
DCEmu Freak
DCEmu Freak
Posts: 50
Joined: Sun Jan 14, 2018 8:03 pm
Location: Emu land
Has liked: 9 times
Been liked: 5 times
Contact:

Re: Unsure how some PVR features behave

Post by Protofall » Thu Jan 10, 2019 5:12 am

BlueCrab wrote:
Wed Jan 09, 2019 10:45 pm
First off, moved to Programming, since it makes more sense there...

Second, to the questions...
1. The modifier lists are for sending modifier volumes, which change parameters of polygons that are "within" them. They can be used to do things like shadowing (by changing colors), or for changing texturing data, etc. They're pretty powerful, but not exactly easy to use. Unfortunately, there's not all that much in the way of documentation about them, which makes the situation worse.

2. You want to use the argb value to do that fade-to-blue effect. Not oargb. The oargb is used in specular highlights.

3. If I'm understanding what you're asking for, the hardware doesn't really support that, so no you can't do it without breaking the texture up manually (I've never done OpenGL 3.x, but considering the DC's hardware is roughly on-par with OpenGL 1.2ish...).

4. Sprites are handled differently in the hardware. They're not really meant for 3D objects, but if you're doing 2D stuff, then they're quite useful. They do have less data that has to be transferred across to the PVR, which is a bit of a benefit. Yes, the use of 16-bit U/V coordinates can cause some inaccuracy, but generally it shouldn't be a huge problem. I'm not really sure what other differences you'd be looking for, so I don't really know what else to answer this with.
Ah sorry, I forgot there was a programming section.

1. Interesting, I don't think I will touch those lists much since I'm more into 2D stuff, but good to know. If you want to modify an opaque poly do you need to first submit a poly in the "PVR_LIST_OP_POLY" list then submit something else in the opaque modifier list, or just a single submit to the modify list?

2. argb isn't exactly what I want. The way I understand the argb parameter is "This is the colour light hitting the polygon". This means you can't get a fade-to-white effect with argb since white light just shows the texture normally. Also if a texture doesn't have data in one of the channels, say a texture is full of pixels with no blue components, when viewed in blue light the texture will appear entirely black (Except for translucent pixels ofc). Here is a link to a quick cdi (Plus its source) I made showcasing this: http://www.mediafire.com/file/51lvdoveb ... t.zip/file

Also based on your description of the modifier lists, I feel they would be the way of doing the shading effect I want to do. Guess I'll have to look at them sooner rather than later :P

3. Okay, not a big loss. I've only ever used OpenGL version 3.3 hence why I named that version specifically, but yes DC is closer to OpenGL 1.X :goomba:

4. That answers my question, just wasn't sure if there were any other differences. Thanks :)
Made a recreation of Minesweeper for the Dreamcast <viewtopic.php?f=34&t=104820>
More is yet to come :wink:

Twitter <https://twitter.com/ProfessorToffal>
YouTube (Not much there, but there are a few things) <https://www.youtube.com/user/TrueMenfa>
TapamN
DCEmu Junior
DCEmu Junior
Posts: 42
Joined: Sun Oct 04, 2009 11:13 am
Has liked: 0
Been liked: 0

Re: Unsure how some PVR features behave

Post by TapamN » Thu Jan 17, 2019 6:22 am

1: Modifiers are mainly used to preform stencil buffer type effects, like shadow volumes. Pixels outside any modifier volumes use their polygon's default parameters (shading, textures, blend mode, etc) while pixels inside a volume can use a different set of parameters. With normal stencil effects, you have to redraw parts of the screen manually, but with modifiers, the PVR will select the correct parameters while it evaluates the volumes and will draw things once, so it's more efficient, but more limited. The different parameters are stored in the opaque, translucent, and punch-through lists as normal polygons with two sets of lighting and texturing parameters; the modifier lists only store the volume polygons.

2: For the fade to blue effect, modifier volumes are NOT what you need. Your "fade-to-blue" effect is basically alpha blending a solid color on top of the sprite, right? For that, oargb is what you need here.

So the formula of the effect looks like this:

Resulting color = texsample * (1-alpha) + fadecolor * alpha

On the Dreamcast, the argb and oargb values are mixed with the texture color like this:

Resulting color = texsample * argb + oargb;

This is intended to let you preform lighting equations that work like "texsample * diffuse + specular". However, by setting argb to (1-alpha) and oargb to Fadecolor * alpha, you can recreate the formula used for the fade-to-color effect.

To get oargb to work, you need to set a certain bit in the polygon header to enable it. It also only works with regular polygons. It doesn't look like "pvr_poly_compile" has a way to enable specular/offset shading (pvr_poly_compile is kind of poo), so to enable the offset color manually, on the pvr_poly_hdr_t struct, turn on bit 2 of cmd. (So "hdr.cmd |= 0x4;")

I modified your demo to show how to do it.

3: There's actually a trick that kind of lets you use split up textures that are twiddled, have no mipmaps, and are uncompressed, and get correct repeat/clamping for the subtexture, but difficult to explain to how it works and has limitations on where the subtextures are placed. It's probably better to just split up your textures manually.
Attachments
shadeTest mod.zip
(919.32 KiB) Downloaded 54 times
User avatar
Protofall
DCEmu Freak
DCEmu Freak
Posts: 50
Joined: Sun Jan 14, 2018 8:03 pm
Location: Emu land
Has liked: 9 times
Been liked: 5 times
Contact:

Re: Unsure how some PVR features behave

Post by Protofall » Mon Jan 21, 2019 6:23 am

1. Ah yes, I forgot to ask at the beginning how/if stuff like the scissor test could be done with KOS. This answers that question. Are there any publicly available examples using the modifier lists? I'm unsure how it would look/work code wise.

2. Ah, that explains oargb not doing anything. Your modification is exactly what I needed, thanks :grin:

3. Interesting, if the sub-textures need to be in particular positions then it won't be of use to me since my spritesheets are generated automatically. Having individual textures will probably be the way I go instead.
Made a recreation of Minesweeper for the Dreamcast <viewtopic.php?f=34&t=104820>
More is yet to come :wink:

Twitter <https://twitter.com/ProfessorToffal>
YouTube (Not much there, but there are a few things) <https://www.youtube.com/user/TrueMenfa>
TapamN
DCEmu Junior
DCEmu Junior
Posts: 42
Joined: Sun Oct 04, 2009 11:13 am
Has liked: 0
Been liked: 0

Re: Unsure how some PVR features behave

Post by TapamN » Sat Jan 26, 2019 6:10 am

1: How precise does the scissor need to be? The best equivalent to glScissor the hardware supports would be to use the tile accelerator's user clipping command. It's much more efficient than trying to use modifier volumes to clip. You can reverse scissor as well, where only what's outside the scissor area gets draw. The rear view mirror in F355 Challenge was probably done with user clipping. One limitation of user clipping is that it's boundaries have to be aligned to a multiple of 32.

Modifier volumes aren't really intended for clipping. They can be used that way, but it's kind of overkill. Modifier volumes work by modifying the polygon's drawing parameters, like making the shading darker, changing the texture, or changing the blend mode. You can implement clipping by changing the alpha or blend mode of the polygon to make it transparent.

Using modifier volumes to do clipping is more flexible since you can do any shape you want, anywhere you want. But using modifier volumes to clip is less efficient than the TA's user clipping. Since things made to be "clipped" by a modifier volume will still be drawn (they'll just be drawn invisibly), you still have the same fillrate costs for drawing it as if it was visible.

Also, you can only clip into two spaces for the entire screen if you use modifier volumes. If you use user clipping, you can move the clip area around multiple times to do 3 or 4 player split screen.

One issue with user clipping, is that you can't get a horizontal split screen to split perfectly in the middle of the screen, since 480 doesn't divide evenly by 32. It will have to be rounded up or down by 16 pixels to the nearest 32 pixel boundary.

I think KOS comes with a modifier volume example, but it uses the simple shadow mode of the PVR, which just darkens what's being modified. It will show you how to send the actual volumes, but not how to set up the polygons to not draw outside the volume and not how to enable the true two-mode polygons required for clipping.

I could make a clipping demo of either method, if you want one. I would go with user clipping, since it's a closer match to glScissor, faster, and simpler, but I don't know what you need exactly.

3: Why does it cause problems if the sprites share a texture?
User avatar
Protofall
DCEmu Freak
DCEmu Freak
Posts: 50
Joined: Sun Jan 14, 2018 8:03 pm
Location: Emu land
Has liked: 9 times
Been liked: 5 times
Contact:

Re: Unsure how some PVR features behave

Post by Protofall » Tue Jan 29, 2019 5:28 am

1. Here's my context: I'm making a library called "Crayon" that depends on KOS (For the Dreamcast) and it will make it easier to create 2D projects for the Dreamcast (No 3D support). Later on I plan to make a PC port that depends on OpenGL and for PC I'll use the scissor test for this kind of scenario. For all versions I want to use the same code structure and when drawing a sprite I want to pass the following struct into my draw functions to draw onto a specific region of the screen

Code: Select all

typedef struct crayon_viewport_t{
	//Top left of the world region and dimensions.
	float world_x;
	float world_y;
	uint16_t world_width;
	uint16_t world_height;

	//The scrolling modifier for stuff like parallax
	float world_movement_factor;

	//Top left of where to render to on screen and dimensions
	uint32_t window_x;
	uint32_t window_y;
	uint16_t window_width;
	uint16_t window_height;
} crayon_viewport_t;
The PC/OpenGL port would simply read the window variables and use them to set and enable a scissor test for wherever you want to draw. For the Dreamcast options, TA wouldn't be that useful unless the window coordinate/lengths happened to line up with the 32 by 32 grid, so I could have a simple check and use TA for quicker renders in that case. Modifier values could be used for TA-incompatible cases, the idea I was planning before I asked about this was to adjust the positions/UVs of sprites/polygons so all vertices are within the boundaries and the adjusted UV coordinates make them appear as normal.

For example if my window values are is 30, 30, 100, 100 and I have a sprite with "vertices" at (40,100), (60, 100), (60, 140), (40, 140). Since 30 + 100 = 130 and the last two vertices are outside of my drawing area I can change the y values of those last two vertices to 130 and reduce v1 so (v1 - v0) is 75% what it used to be. I don't know if thats more or less efficient than the modifier values approach, but it would be rendering less and would allow for more than 2 clipping spaces.

I must have missed that KOS modifier example last time I checked. If you want to make demos for the TA and Modifier methods, that would be amazing, I know I won't be the last person who will want to know about these things. If they can be added to the KOS examples that would really benefit people who are new and don't know where to start.

3. Oh no, I was referring to a particular case where I wanted to display a single sprite (16 by 16) across the whole screen like that so I can have just that sprite as its own texture and manipulate the UV to draw it all across the screen in one `pvr_prim()` meanwhile the rest of my textures are in spritesheets.
Made a recreation of Minesweeper for the Dreamcast <viewtopic.php?f=34&t=104820>
More is yet to come :wink:

Twitter <https://twitter.com/ProfessorToffal>
YouTube (Not much there, but there are a few things) <https://www.youtube.com/user/TrueMenfa>
TapamN
DCEmu Junior
DCEmu Junior
Posts: 42
Joined: Sun Oct 04, 2009 11:13 am
Has liked: 0
Been liked: 0

Re: Unsure how some PVR features behave

Post by TapamN » Tue Feb 12, 2019 11:27 pm

Your idea to do the clipping in software when the TA's user clipping won't do is probably the best. Doing clipping with modifier volumes complicates basically all rendering code. Doing clipping manually only has extra complexity when clipping needs to occur. It would also be the more efficient method in terms of fillrate, since you save the PVR from having to draw invisible pixels.

Most 3D hardware during the Dreamcast's time frame either did clipping in software inside the driver, or required the programmer to do it manually, depending on the graphics library (A MiniGL would do clipping in the driver, something like Glide would require manual clipping). The PVR was unusual for the time for being able to do XY clipping completely in hardware (with the 32-pixel limitation). You still have to do near-Z clipping in software, though.

When I was working on a Dreamcast/PC 2D engine a long time ago, I was just going to make camera boundary's having a multiple-of-32 requirement be part of the spec. Too lazy to work around it. :P

I've included two demos of how to use the user clipping feature and how to use modifier volumes to clip.

The controls for both demos are the same:
Pressing A prints the PVR render time to the console (I was curious what kind of speed differences there would be for different clipping methods)
Holding B disables clipping
Holding X does a more complex clipping example (for user clipping, it does 4 way split screen, for modifier clipping it does a wavy split)
Holding Y changes the demo from displaying rotating sprites to randomly placed sprites

The code is designed to be pretty simple, but I feel like the modifier clipping example really doesn't explain how everything works if you don't already understand how modifier volumes work; the comments explain what is happening, but not why, but I don't really feel like writing a theory of operation for it...

Since the examples are meant to be simple, not everything is done the most efficient way (e.g. it uses pvr_prim to draw instead of directly using the store queues).
Attachments
clipping examples.zip
(506.88 KiB) Downloaded 41 times
User avatar
Protofall
DCEmu Freak
DCEmu Freak
Posts: 50
Joined: Sun Jan 14, 2018 8:03 pm
Location: Emu land
Has liked: 9 times
Been liked: 5 times
Contact:

Re: Unsure how some PVR features behave

Post by Protofall » Wed Feb 13, 2019 9:37 pm

Yeah, that makes sense. Vertex/UV modification would be a bit more efficient than modifier volumes in most cases. Since my last post I realise my software-clipping approach is only good for "sprite" mode and x/y axis aligned polygons. Depending on how a rotated poly is cropped, its not really possible to crop it by modifying existing verts and UVs. However for my purposes I think I'll be fine with this limitation/flaw.

The demos are great :red) :biggrin: I've looked through the source code for both, the TA example is really simple and works perfectly. The modifier example is a lot more complex like you said, I get the general gist of whats happening and the comments provided do help a bit, but I think I need to dig up and read some official Sega docs on modifiers to truly comprehend it, still really cool and its much appreciated. However I think the modifier example is broken, pressing "X" appears to do nothing. The red/yellow circles and random red dots are always the same/uncropped and the green/white circles and random green dots only appear at all when clipping is disabled ("B" press). I tried running your pre-compiled executable in lxdream and Redream emulators as well as compiling my own with modern KOS, but I only got the same result. I think something might be wrong in the setup code and the modifier volume is just removing everything or nothing.
Made a recreation of Minesweeper for the Dreamcast <viewtopic.php?f=34&t=104820>
More is yet to come :wink:

Twitter <https://twitter.com/ProfessorToffal>
YouTube (Not much there, but there are a few things) <https://www.youtube.com/user/TrueMenfa>
TapamN
DCEmu Junior
DCEmu Junior
Posts: 42
Joined: Sun Oct 04, 2009 11:13 am
Has liked: 0
Been liked: 0

Re: Unsure how some PVR features behave

Post by TapamN » Thu Feb 14, 2019 5:51 am

The clipping will be more complicated with rotated sprites, but it's still possible. You can do clipping of an arbitrary polygon to a convex shape with something like Sutherland-Hodgman. Google, "polygon clipping" or "Sutherland-Hodgman", and you'll find explanations on how to do it.

The modifier demo works fine on real hardware, the problem is with the emulators. Few/no games used modifier volumes this way so the emulator writers probably never bothered to support it or never had a way to test it. It sounds like it's drawing everything as though it's outside the modifier volume. Fully emulating the PVR's ability to do 3D modifier volumes on transparent polygons is really difficult to implement on conventional GPUs. I've included a screenshot of what it looks like with X+Y held, taken from real HW. The wave pattern is animated.
Attachments
00000094.jpg
User avatar
Protofall
DCEmu Freak
DCEmu Freak
Posts: 50
Joined: Sun Jan 14, 2018 8:03 pm
Location: Emu land
Has liked: 9 times
Been liked: 5 times
Contact:

Re: Unsure how some PVR features behave

Post by Protofall » Thu Feb 14, 2019 6:26 am

TapamN wrote:
Thu Feb 14, 2019 5:51 am
The clipping will be more complicated with rotated sprites, but it's still possible. You can do clipping of an arbitrary polygon to a convex shape with something like Sutherland-Hodgman. Google, "polygon clipping" or "Sutherland-Hodgman", and you'll find explanations on how to do it.

The modifier demo works fine on real hardware, the problem is with the emulators. Few/no games used modifier volumes this way so the emulator writers probably never bothered to support it or never had a way to test it. It sounds like it's drawing everything as though it's outside the modifier volume. Fully emulating the PVR's ability to do 3D modifier volumes on transparent polygons is really difficult to implement on conventional GPUs. I've included a screenshot of what it looks like with X+Y held, taken from real HW. The wave pattern is animated.
Really? Nice! I'll read up on "Sutherland-Hodgman"

Ah yes, I should have expected it wasn't used enough for emulators to support it. Thats good to know, thanks again :grin:
Made a recreation of Minesweeper for the Dreamcast <viewtopic.php?f=34&t=104820>
More is yet to come :wink:

Twitter <https://twitter.com/ProfessorToffal>
YouTube (Not much there, but there are a few things) <https://www.youtube.com/user/TrueMenfa>
Post Reply