It is currently Sun Oct 22, 2017 6:59 am

All times are UTC - 7 hours





Post new topic Reply to topic  [ 40 posts ]  Go to page 1, 2, 3  Next
Author Message
PostPosted: Sat Sep 23, 2017 3:53 pm 
Offline
User avatar

Joined: Mon Sep 15, 2014 4:35 pm
Posts: 3074
Location: Nacogdoches, Texas
I thought you guys might like this video: https://www.youtube.com/watch?v=784MUbDoLjQ I've seen all of these ports, but this is the first time I have ever heard a technical explanation of any of them. I find it funny how shitty Doom ran on what were supposed to be the "top-of the-line" video game systems of the era, even if it was due to software rendering. I've never quite realized how much more powerful the N64's CPU is over the PS1's and Saturn's if it can software render Doom with seemingly perfect performance at 320x200 (https://www.youtube.com/watch?v=6EPKKaZ3Z0A), although it is made with hardware two years more advanced. Two years seemed to be a lot back then for computer hardware, as I don't think you could even run Doom at full settings and 35fps with a computer from a date earlier than 1991. I wasn't even alive during this time though, so what do I know. :lol:


Top
 Profile  
 
PostPosted: Wed Sep 27, 2017 11:01 pm 
Offline

Joined: Fri Jul 04, 2014 9:31 pm
Posts: 788
Well, I just tried the pixel-doubling mosaic trick I was thinking of back during our discussions about SNES Doom, and it didn't work, at least not on the first couple tries.

The best part is, no two emulators gave me the same result, and the only one that seemed to match the real SNES, maybe (composite FTW), was bsnes/higan compatibility core (not accuracy, which was closer to ZSNES), or in one case Snes9X.

But in no case did the technique actually work. I haven't got time right now to figure out why not, or if it might be possible to force it to, but apparently mosaic is secretly one of the more complicated and unintuitive S-PPU functions, as well as one of the hardest to emulate properly. Not that that excuses the Yoshi's Island bug on the SNES Classic...

EDIT: Had an idea, tried it, got it to work... in Snes9X. For all the good that does. At least the results from higan accuracy and ZSNES are further apart now...


Top
 Profile  
 
PostPosted: Fri Sep 29, 2017 12:42 am 
Offline
User avatar

Joined: Mon Sep 15, 2014 4:35 pm
Posts: 3074
Location: Nacogdoches, Texas
Wait, what was your aim for this? Decreased processing time or VRAM bandwidth requirements? I wrote a much longer comment, but I forgot to copy the text before pressing submit, and the website bugged out and I was unable to retrieve it. :?


Top
 Profile  
 
PostPosted: Fri Sep 29, 2017 4:58 am 
Offline

Joined: Fri Jul 04, 2014 9:31 pm
Posts: 788
If it could be got working, it would cut DMA requirements in half, yes. This saves some GSU idle time and might leave more headroom for weapon graphics or something. It might also allow the engine to render two scanlines at once rather than just drawing every pixel twice, saving half the PLOT bandwidth (at least in cases where both lines are solid - I don't know how the engine works), though I'm not sure how much that helps because the RAM buffer is probably not the bottleneck. I'm assuming the Doom engine doesn't need a framebuffer clear, but if it did that would be halved too.

Combine this with a bit of CPU ROM, so that stuff like music, sound effects, auxiliary graphics and S-CPU code could be handled with more freedom independent of the Super FX, and it's conceivable the port could be significantly improved. I'm not proposing to do it necessarily, but it would be interesting to know if it's possible.

The CPU ROM thing is possible; we know this. I don't know how much extra space that frees up in the 2 MB the GSU2 can address - it might even be possible to add back some of the cut features. But so far it's not clear that the mosaic trick is possible. I don't think I'm done trying, but I gotta say, the behaviour is weird...


Top
 Profile  
 
PostPosted: Fri Sep 29, 2017 9:23 pm 
Offline
User avatar

Joined: Mon Sep 15, 2014 4:35 pm
Posts: 3074
Location: Nacogdoches, Texas
Thinking about how games like this rendered the walls, yeah, the SNES graphics format really is a bitch. If you wanted to make something simple that could reasonably run on the SNES by itself (Wolfenstein 3D, although the existing port blows), I would just have different code for every height a sliver of wall could be. This would be a huge chunk of memory, but for a standard packed pixel 8bit pixel, the code would look something like this:

Code:
lda TextureBank,x
sta Framebuffer,y
lda TextureBank+1,x
sta Framebuffer+8,y
etc...

However, for the SNES graphics format, you would have to load the first byte, "and" it, do 0-4 bitshifts (and check how many you need to do, which takes more CPU time), "ora" with the framebuffer, and then finally store the result there. But then, you've only done a fourth of a pixel... You could burn through even more memory and have 4 copies of textures for different positions, but you're getting, at best, a fourth the performance of the previous example.


Top
 Profile  
 
PostPosted: Fri Sep 29, 2017 11:01 pm 
Offline

Joined: Fri Jul 04, 2014 9:31 pm
Posts: 788
That's why Wolfenstein 3D uses Mode 7, and Doom uses the Super FX chip with its PLOT circuitry. I don't know if anyone has ever tried to do a raycaster on the 5A22 in any of the bitplane modes.

Espozo wrote:
I would just have different code for every height a sliver of wall could be.

That's how Toy Story on the Mega Drive did it. Over 50 KB of unrolled loops.

They also mirrored the walls vertically, and took advantage of the graphics format by making every wall sliver two pixels wide.


Top
 Profile  
 
PostPosted: Sat Sep 30, 2017 5:21 pm 
Offline

Joined: Wed May 19, 2010 6:12 pm
Posts: 2295
Espozo wrote:
Thinking about how games like this rendered the walls, yeah, the SNES graphics format really is a bitch. If you wanted to make something simple that could reasonably run on the SNES by itself (Wolfenstein 3D, although the existing port blows), I would just have different code for every height a sliver of wall could be. This would be a huge chunk of memory, but for a standard packed pixel 8bit pixel, the code would look something like this:

Code:
lda TextureBank,x
sta Framebuffer,y
lda TextureBank+1,x
sta Framebuffer+8,y
etc...

However, for the SNES graphics format, you would have to load the first byte, "and" it, do 0-4 bitshifts (and check how many you need to do, which takes more CPU time), "ora" with the framebuffer, and then finally store the result there. But then, you've only done a fourth of a pixel... You could burn through even more memory and have 4 copies of textures for different positions, but you're getting, at best, a fourth the performance of the previous example.


If you're doing every pixel only once, going left to right, you can get by just by doing lsr and ror abs,x 4 times per pixel. However it still takes about 30 cycles per pixel.

I've been experimenting with LUT-based conversions, and the fastest method I got so far was dividing 8 pixels into 3 parts, each 2 or 3 pixels, and each group of 2 or 3 pixels is used as an index into 2 LUT tables for each pair of bit planes. I've been also thinking of using 2 groups of 4 pixels, but that would take 256kB of LUTs.


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 10:01 am 
Offline
User avatar

Joined: Mon Sep 15, 2014 4:35 pm
Posts: 3074
Location: Nacogdoches, Texas
I thought of a silly idea; what if the top and bottom of the Mode 7 framebuffer were Mode 3 for more space (probably like 32 rows), while still better performance than all Mode 3? It would be easiest to implement having the code for drawing the walls would work the same way from top to bottom, and converting the graphics later. Originally, I thought of an idea to make this even greater by implementing a system where only tiles with non-solid color graphics would be converted, as this would be trivial to implement (for walls anyway), but then I thought about how a wall will take up your entire view if you just approach it head on. :? Is performance in raycasters generally better if you just look straight at a wall rather than across a reasonably complex room? If so, this might still be worth implementing.


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 11:22 am 
Offline

Joined: Tue Oct 06, 2015 10:16 am
Posts: 558
There is less work if the ray hits a wall immediately vs 100m away, but how much depends on the game.


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 11:28 am 
Offline

Joined: Sun Sep 19, 2004 11:12 pm
Posts: 19115
Location: NE Indiana, USA (NTSC)
And I think that's part of why Faceball 2000 has fog about 3 cells away from the camera.


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 12:17 pm 
Offline
User avatar

Joined: Sat Feb 12, 2005 9:43 pm
Posts: 10066
Location: Rio de Janeiro - Brazil
Espozo wrote:
Is performance in raycasters generally better if you just look straight at a wall rather than across a reasonably complex room?

calima wrote:
There is less work if the ray hits a wall immediately vs 100m away, but how much depends on the game.

Based on my own experience making raycasters on the NES, things almost balance out in the end: Casting a long ray and drawing a small wall is not so different from casting a short ray and drawing a large wall. With my own code, rendering walls appears to be slightly slower than casting rays though, so you get slightly better performance from looking at a reasonably-sized open space than from putting your nose against the wall. This would probably change if complex floors and ceilings were added into the mix.

I'm not sure this is pertinent to Doom though, because AFAIK, it doesn't use raycasting.


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 12:21 pm 
Offline

Joined: Wed May 19, 2010 6:12 pm
Posts: 2295
I always thought games like doom found where the edges of walls are first, and then calculated the zoom factor mathematically. I don't know why any game would need to count steps before hitting a wall.


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 12:47 pm 
Offline
User avatar

Joined: Sat Feb 12, 2005 9:43 pm
Posts: 10066
Location: Rio de Janeiro - Brazil
psycopathicteen wrote:
I always thought games like doom found where the edges of walls are first, and then calculated the zoom factor mathematically.

Yeah, I don't know the specifics of Doom, but I think it does indeed calculate the distances between wall edges and the viewport, and then uses interpolation of heights and textures to complete the image.

Quote:
I don't know why any game would need to count steps before hitting a wall.

Firing rays is conceptually simpler than doing real 3D to 2D transformations, and once a ray hits a wall you can quickly calculate everything you need to render a column to the screen: the height, the texture slice, and so on.


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 1:43 pm 
Offline

Joined: Sat Apr 25, 2015 1:47 pm
Posts: 329
Location: FL
The "Walls" section of Fabian Sanglard's Doom renderer overview describes pretty much what you're talking about.

It's perhaps worth mentioning that the "walls" in this context are actually the "segs" structures which are generated at build time when splitting arbitrarily-shaped sectors into convex polygons, so a single visible "wall" (i.e. a linedef/sidedef) might actually comprise multiple segs and so you're not always guaranteed to be interpolating over the entire visible surface in one pass.

(Also, tokumaru was correct - Doom doesn't use a raycasting engine.)


Top
 Profile  
 
PostPosted: Sun Oct 01, 2017 2:45 pm 
Offline
User avatar

Joined: Mon Sep 15, 2014 4:35 pm
Posts: 3074
Location: Nacogdoches, Texas
What exactly does "raycaster" even mean? I know it's not how the walls are actually rendered, as Doom renders walls the same way as Wolfenstein 3D, (in one pixel wide, vertical slivers) but how the engine figures out where the walls are and their distance from the camera? I have no idea how Wolfenstein 3D does it, but Doom (if I'm not mistaken) has multiple shapes on the floor with sides that are either connected to other shapes or have walls (or both if there is a difference in elevation). The level has a list of what shapes are visible from others, and during runtime, the game finds what walls are facing the player. Finally, it renders the walls (determining their position from the player by the position of the edges relative to the player) from front to back to avoid overdraw. How does Wolfenstein 3D accomplish this?


Top
 Profile  
 
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 40 posts ]  Go to page 1, 2, 3  Next

All times are UTC - 7 hours


Who is online

Users browsing this forum: Google [Bot] and 4 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
Powered by phpBB® Forum Software © phpBB Group