It is currently Sat Dec 16, 2017 11:25 pm

All times are UTC - 7 hours





Post new topic Reply to topic  [ 58 posts ]  Go to page 1, 2, 3, 4  Next
Author Message
 Post subject: Scanline- vs pixelengine
PostPosted: Mon Feb 15, 2016 10:22 am 
Offline
User avatar

Joined: Sun Mar 19, 2006 3:06 am
Posts: 584
Location: Gothenburg/Sweden
I've only done scanline-based graphicsengines for my emulators earlier but I've been thinking of trying to create a pixel-per-pixel engine. Question is if it's worth the effort?
The drawback with (my) scanline-based engines are that they are obviously not as accurate as pixelbased ones (but still works pretty good in most cases).

I'm currently working on a scanline-based engine and discovered a few problems with it that I want to get fixed. Question if I should try to partly rewrite my engine (however, it tends to get a bit "hack-ish" :)) or rewrite it from scratch pixel-per-pixel (which seems pretty complex when I've checked some sources and info on the wiki..).

So, anyone with pixel-per-pixel engine-experience here that'd like to share some wise thoughts/hints if I decide to go that way...?

_________________
http://nes.goondocks.se/


Top
 Profile  
 
PostPosted: Mon Feb 15, 2016 10:50 am 
Offline
User avatar

Joined: Wed Nov 10, 2004 6:47 pm
Posts: 1845
It depends what your goals are, and how much you want to stress accuracy. Obviously a scanline-based emulator is never going to be as accurate as a pixel-based one... but do you really care? If you don't... and if you're happy with getting games to run even if the emu itself isn't completely accurate, then don't bother.


As for difficulty -- it's not as difficult as you think. It's just taking things in smaller steps.


Top
 Profile  
 
PostPosted: Mon Feb 15, 2016 11:10 am 
Offline
User avatar

Joined: Fri Nov 19, 2004 7:35 pm
Posts: 3969
What causes the PPU pixels to change within a scanline?
*Changes in CHR mapping (including automatically triggered stuff from punch out/fire emblem)
*Changes in PPU control $2000 (which banks it uses for Sprites and BG)
*Changes in PPU mask $2001 (enabling/disabling, color emphasis, monochrome, first column hides)
*Changes in fine scroll ($2005 first write)
*Changes in VRAM address

If you properly handle these changes at the correct timings, you've turned a scanline based engine into a pixel based engine.

Note that the process for the PPU pipeline still matters for getting the pixels correct. But if nothing changes in the scanline, you don't worry about anything.

_________________
Here come the fortune cookies! Here come the fortune cookies! They're wearing paper hats!


Top
 Profile  
 
PostPosted: Mon Feb 15, 2016 11:21 am 
Offline
User avatar

Joined: Sat Feb 12, 2005 9:43 pm
Posts: 10169
Location: Rio de Janeiro - Brazil
Disch wrote:
It depends what your goals are

Exactly. A pixel-based emulator is really useful for developers trying to time raster effects and such, but players in general couldn't care less.

Quote:
As for difficulty -- it's not as difficult as you think. It's just taking things in smaller steps.

In fact, breaking it down into smaller steps could actually make things easier!


Top
 Profile  
 
PostPosted: Mon Feb 15, 2016 11:51 am 
Offline
User avatar

Joined: Sun Mar 19, 2006 3:06 am
Posts: 584
Location: Gothenburg/Sweden
It seems a bit frightening to calculate which parts of a tile/Sprite to draw on screen..

Perhaps I don't care about total compability, but something in between perhaps.. Of course, it would also be a nice ego-boost to solve a pixel-based renderer. :)

_________________
http://nes.goondocks.se/


Top
 Profile  
 
PostPosted: Mon Feb 15, 2016 2:15 pm 
Offline
User avatar

Joined: Mon Dec 29, 2014 1:46 pm
Posts: 753
Location: New York, NY
oRBIT2002 wrote:
It seems a bit frightening to calculate which parts of a tile/Sprite to draw on screen..

Perhaps I don't care about total compability, but something in between perhaps.. Of course, it would also be a nice ego-boost to solve a pixel-based renderer.


As mentioned by others above, it's up to you to decide how far down the rabbit hole you wish to travel. When it comes to side projects in general, my advise is to develop them in layers, kind of like an onion. Once a layer of development is completed, you should have something releasable. And, by releasable, I mean, each layer is a give-up point. Time is a limited resource and an NES emulator can contain a surprisingly large set features. Nevertheless, many on this forum have persisted with their efforts on the same side project for many years. And, this is in a world saturated with plenty of accurate emulators out there. The primary audience of your side project is yourself.


Top
 Profile  
 
PostPosted: Tue Feb 16, 2016 12:04 pm 
Offline
User avatar

Joined: Sun Mar 19, 2006 3:06 am
Posts: 584
Location: Gothenburg/Sweden
I'm very tempted to start this project, but we'll see... :)

The basic idea is to draw 3 pixels for each CPU clockcycle right? Currently my CPU emulation calls a clockcycle-countdown function at the end of each opcode to be able to calculate the current scanline etc.
Would it be an idea to implement this "pixel-code" in this clockcycle-counter-function or am I getting it wrong?
I've seen emulators not counting clockcycles at all so perhaps there's a better way..?

_________________
http://nes.goondocks.se/


Top
 Profile  
 
PostPosted: Tue Feb 16, 2016 4:46 pm 
Offline
User avatar

Joined: Wed Nov 10, 2004 6:47 pm
Posts: 1845
Not necessarily 3 pixels per CPU cycle... but 3 PPU cycles per CPU cycle. Only some PPU cycles actually render pixels.

As far as cycle tallying, I typically do a catchup approach with timestamps to keep track of where each subsystem is... with the timestamp scaled up to some "master clock" setting.

Typically I do:
1 PPU cycle = 5 master clocks
1 NTSC CPU cycle = 15 master cycles
1 PAL CPU cycle = 16 master cycles

So every time the CPU does 1 cycle, you would add 15 to its timestamp (or 16, if PAL)


On the CPU side, 1 cycle always corresponds to either a read or a write. So if you emulate all the dummy reads for all instructions, you don't have to tally cycles. You just increment the timestamp on every read/write.

When the CPU does something that affects the PPU (like reading/writing to a PPU reg), "catch up" the PPU by emulating it until its timestamp reaches the CPU's current timestamp (so the CPU runs ahead of everything, and then other system catch up to it when they need to sync for something).



Of course there are countless ways to do this. This is just the way I found that works for me.


Top
 Profile  
 
PostPosted: Tue Feb 16, 2016 4:59 pm 
Offline
Formerly Fx3
User avatar

Joined: Fri Nov 12, 2004 4:59 pm
Posts: 3076
Location: Brazil
oRBIT2002 wrote:
The basic idea is to draw 3 pixels for each CPU clockcycle right?

Right. Remeber that 3 pixels = 3 PPU cycles. You know, it's not only a matter of drawing pixels. You must write your PPU timing loop - VBlank, NMI, scanline/cycle switch case, DMC cycles...
Quote:
Currently my CPU emulation calls a clockcycle-countdown function at the end of each opcode to be able to calculate the current scanline etc.
Would it be an idea to implement this "pixel-code" in this clockcycle-counter-function or am I getting it wrong?

Well, my emulator uses the "microcode level" - runs the PPU at every CPU memory access. Running the PPU at the end of instruction..!? No clue - PPU timing is very sensitive, and even me is having problems with timing (Battletoads, The Simpsons, Mega Man V). So, try yourself and get ready for long sessions of timing debugging... until it's finally fine-tunned.
Quote:
I've seen emulators not counting clockcycles at all so perhaps there's a better way..?

Good. I don't need any CPU cycle counters. All the timing is driven by the PPU.


Top
 Profile  
 
PostPosted: Wed Feb 17, 2016 12:02 am 
Offline
User avatar

Joined: Sun Mar 19, 2006 3:06 am
Posts: 584
Location: Gothenburg/Sweden
One question (among many others) are how you pixelrendering guys keep track of sprites and drawing them with this approach?
Assuming, for example, you're gonna draw a backgroundpixel at position 100,100.. And you have to know if there's a sprite there and draw the correct pixel from it. It has to be shortcut I doesn't know about? :)

_________________
http://nes.goondocks.se/


Top
 Profile  
 
PostPosted: Wed Feb 17, 2016 8:05 am 
Offline
User avatar

Joined: Fri Nov 19, 2004 7:35 pm
Posts: 3969
The answer to sprites is how the NES itself does it.
During each scanline, it looks for the first 8 sprites that are in Y range. Then during Hblank time, it fetches the 16 graphics bytes for the 1px tall sliver those sprites. So if you have the X coordinate of 8 sprite slivers, and the graphics for those sprites, they are easy enough to draw.

_________________
Here come the fortune cookies! Here come the fortune cookies! They're wearing paper hats!


Top
 Profile  
 
PostPosted: Wed Feb 17, 2016 8:56 am 
Offline
User avatar

Joined: Sat Feb 12, 2005 9:43 pm
Posts: 10169
Location: Rio de Janeiro - Brazil
Isn't it a bad idea to lock the PPU:CPU ratio to 3:1 if you plan to support PAL as well?


Top
 Profile  
 
PostPosted: Wed Feb 17, 2016 12:16 pm 
Offline
User avatar

Joined: Sun Mar 19, 2006 3:06 am
Posts: 584
Location: Gothenburg/Sweden
I've been checking this on the wiki:
Image
Larger one here:
http://wiki.nesdev.com/w/images/d/d1/Ntsc_timing.png

Just to clarify things, here's an example:
Assume we start on scanline 0. First CPU instruction is a NOP. A NOP is 2 CPU clockcycles. Assuming screen is turned on etc.. during this time 6 pixels will be drawn (2*3 "PPU Cycles"). Am I right so far?

_________________
http://nes.goondocks.se/


Top
 Profile  
 
PostPosted: Wed Feb 17, 2016 1:30 pm 
Offline
Formerly Fx3
User avatar

Joined: Fri Nov 12, 2004 4:59 pm
Posts: 3076
Location: Brazil
Actually, the PPU is always running. For each CPU cycle, the PPU runs for 3 cycles. Pixels are rendered only if background or sprites are enabled. Keep track of the PPU cycle and scanline - you need it for VBlank, NMI... as I already mentioned here.


Last edited by Zepper on Wed Feb 17, 2016 5:31 pm, edited 1 time in total.

Top
 Profile  
 
PostPosted: Wed Feb 17, 2016 1:34 pm 
Offline
User avatar

Joined: Sun Mar 19, 2006 3:06 am
Posts: 584
Location: Gothenburg/Sweden
Ok, except for the part about "screen turned on" etc, I was right then..

_________________
http://nes.goondocks.se/


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

All times are UTC - 7 hours


Who is online

Users browsing this forum: No registered users and 5 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