Heaven/TQA Posted May 6, 2005 Share Posted May 6, 2005 hi, sorry to post this here but you might popped by this: http://www.atariage.com/forums/index.php?s...pic=68025&st=25 we are discussion several methods in enhancing atari's sprite capabilities... actually i am dealing with sprite multiplexing via raster interrupts and i was wondering how you 2600 guys handle the mutliplexing & kernel? f.e. joust, asteroids or pac man are using kind of flickering when more than 2 hardwaresprites are on one scanline... how are you dealing with it? maybe there is a kind of effective approach which i could adapt... Quote Link to comment Share on other sites More sharing options...
Thomas Jentzsch Posted May 6, 2005 Share Posted May 6, 2005 i was wondering how you 2600 guys handle the mutliplexing & kernel? a. repositioning inside the kernel, which allows displaying the same sprite more than once at different positions and with different graphics (vertical separation) b. intelligent flicker (there has been a quite extensive discussion about this at [stella] around March 2002.) Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 7, 2005 Author Share Posted May 7, 2005 danke, thomas. but i haven't found any logical description or even source code? i went through several pages...maybe you can point me to post directly??? i would need information how the actual flickering is done, f.e. flicker through the virtual sprites which share the same scanline... Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 7, 2005 Author Share Posted May 7, 2005 ah...sorry... i should not start from beginning but instead from your mentioned march 2002... aha...sorting is discussed as well... good that i have a sorter implemented as well...could be not wrong... Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 7, 2005 Author Share Posted May 7, 2005 uj...you are using bubble sort??? strange... i am using a derivate of radix sorting: http://www.student.oulu.fi/~loorni/covert/rants/sprite.htm how does the sheduler or "mapper" work? oops. sorry should now be moved into programming forum... Quote Link to comment Share on other sites More sharing options...
Thomas Jentzsch Posted May 7, 2005 Share Posted May 7, 2005 uj...you are using bubble sort??? strange Since the array should be almost sorted from the previous frame, bubble sort is pretty good. Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 7, 2005 Author Share Posted May 7, 2005 but how do you "inteligent flicker"??? Quote Link to comment Share on other sites More sharing options...
Thomas Jentzsch Posted May 7, 2005 Share Posted May 7, 2005 but how do you "inteligent flicker"??? I don't have any code, but generally you sort the Y positions and when two or more objects overlap in that sorted list, you display them alternating. Manuel has written some special code for Star Fire and explained how it works quite detailed at [stella]. Another idea is, to give every object a priority variable, which is decreased when it is drawn and increased when not. When objects overlap, the one with highest priority is drawn. There are a few problems to solve and decissions to make (e.g. to you want to draw partial objects?). And the final solutions more or less depends on the game you are writing. Quote Link to comment Share on other sites More sharing options...
Cybergoth Posted May 7, 2005 Share Posted May 7, 2005 Hi there! Manuel has written some special code for Star Fire and explained how it works quite detailed at [stella]. In short: The sorting in Star Fire does just one iteration of a bubble sort per frame and no complete sort. The sorting is also tweaked in a way that overlapping sprites (doesn't matter how many!) will constantly(!) swap positions, so each sprite of the "conflicting" group will get equal display time. There is never a "final" sorting result (especially when all things are moving), but the sorting of objects is "constanly improving". If you have 7 objects entering the screen at once, then after 6 frames you have them "almost" sorted, with only the conflicting sprites continuing at swapping their positions. During display, I just move through my sorted list and display as many sprites as possible, skipping those where I already "missed" the starting point. Don't know if parts or any of this will help in a system with 4 hardware sprites though, as in Star Fire I have only one object per scannline, as I combined both sprites to 16 pixel wide objects. Greetings, Manuel Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 7, 2005 Author Share Posted May 7, 2005 thanks manuel... question: when you are refering to "just move through my sorted list and display..." what exactly are you meaning? i mean... f.e. if your sorted list is: 1,2,3,4,[5] ; assuming 4 hardwaresprites 5th sprite is marked as "rejected" how would you walk through this list? in my test i am sorting every frame 16 randomly moving sprites and map them to 4 hardware sprites... rejecting overlapping ones which could not fit on the scanline... and now i am searching for a method (f.e. MSX ringbuffer method...) to display the rest... examples on atari8bit are ms pacman & joust as most knewn commercial games doing this kind of "intelligent flickering". Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 7, 2005 Author Share Posted May 7, 2005 here are more theory: http://www.atariage.com/forums/index.php?s...pic=66811&st=25 Quote Link to comment Share on other sites More sharing options...
Thomas Jentzsch Posted May 7, 2005 Share Posted May 7, 2005 thanks manuel... question: when you are refering to "just move through my sorted list and display..." what exactly are you meaning? Since RAM is extremly precious on the 2600, the same list is used for the display kernel too. 1,2,3,4,[5] ; assuming 4 hardwaresprites 5th sprite is marked as "rejected" There are no "rejected" sprites, just sprites that overlap. Only the first of those sprites is drawn then, the other ones are "automatically" skipped, because the display kernel "misses" their starting position and continues with the next sprite, which didn't overlap the previous one. Before the next frame, the list is resorted and overlapping sprites are swapped. So in the next round, the display kernel "choses" a different sprite to draw. Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 12, 2005 Author Share Posted May 12, 2005 what do you think of this? ;XASM 6502 source code format ;you have to know about the atari800 hardware (4 player (8x256), 4 missles (2x256). ;DLI zone 1 mva sortsprx stack mva sortsprx+1 stack+1 mva sortsprx+2 stack+2 mva sortsprx+3 stack+3 sta ll+1 ldx #4 loop lda sortspry,x sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue ;saves for the VBL how many sprites are per zone ;DLI zone 2 mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ sta ll+1 loop lda sortspry,x sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue+1 ;saves for the VBL how many sprites are per zone ;DLI zone 3 mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ sta ll+1 loop lda sortspry,x sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue+2 ;saves for the VBL how many sprites are per zone ;DLI zone 4 mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ sta ll+1 loop lda sortspry,x sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue+3 ;saves for the VBL how many sprites are per zone ... the VBL can now flicker through the display stack and prepare the DLI flags to handle the display properly. Of course it must copy the sprite data in the correct player/missle area but this should be no problem at all as we move data in to the players in the order 4,3,2,1,4,3,2,1 etc... --> MS Pac Man Atari 800. the DLIs can reposition the sprites each VBL... the DLI (Rasterinterrupts) will be set to each zone where the next free sprite can be displayed without any overlapping... sortsprx,y contain the virtual sprite positions after they have been sorted by y-pos. what do you think? now it should be easy to flicker through the display stack for each zone as the CUE table contains the virtual sprites per zone... Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 12, 2005 Author Share Posted May 12, 2005 i think this works better: ;DLI zone 1 mva sortsprx stack mva sortsprx+1 stack+1 mva sortsprx+2 stack+2 mva sortsprx+3 stack+3 sta ll+1 ldy #4 loop lda sortspry,y sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue ;saves for the VBL how many sprites are per zone txa tay ;DLI zone 2 mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ sta ll+1 loop lda sortspry,y sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue+1 ;saves for the VBL how many sprites are per zone txa tay ;DLI zone 3 mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ sta ll+1 loop lda sortspry,y sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue+2 ;saves for the VBL how many sprites are per zone txa tay ;DLI zone 4 mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ mva sortsprx,x stack,x+ sta ll+1 loop lda sortspry,y sec ll sbc #[next spr] cmp #8 ;vertical size of sprite bcs no_overlap ;if y2-y1<8 then they do overlap lda sortsprx,x sta stack,x inx cpx #max_sprites bcc loop no_overlap stx cue+3 ;saves for the VBL how many sprites are per zone ... the VBL can now flicker through the display stack and prepare the DLI flags to handle the display properly. Of course it must copy the sprite data in the correct player/missle area but this should be no problem at all as we move data in to the players in the order 4,3,2,1,4,3,2,1 etc... --> MS Pac Man Atari 800. Quote Link to comment Share on other sites More sharing options...
Thomas Jentzsch Posted May 12, 2005 Share Posted May 12, 2005 Sorry, I don't understand very much from this. What does 'mva' do? Maybe some pseudo-code would be better. Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 12, 2005 Author Share Posted May 12, 2005 mva is XASM specific and will be assembled to LDA, STA ("Move Value with Accu") and ",x+" is a post increment and will be assembled to "command, INX" f.e. sta adres, x+ STA adress INX sorry.... i thought this is clear. Quote Link to comment Share on other sites More sharing options...
Heaven/TQA Posted May 12, 2005 Author Share Posted May 12, 2005 it makes the code more compact so your mentioned "pseudo code" mva sortsprx,x stack,x+ should be assembled to lda sortsprx,x sta stack,x inx btw. the code was written in notepad and wasn't tested or assembled. it grew just in my head this morning... Quote Link to comment Share on other sites More sharing options...
Sheddy Posted May 12, 2005 Share Posted May 12, 2005 (edited) Here's the full list of XASM assembler non-standard 6502 syntax "pseudo-commands" and the real 6502 code they generate. Maybe it should be called a compiler rather than an assembler!: PSEUDO-COMMANDS Pseudo-commands are built-in macros. ADD - addition without carry If you have ever programmed a 6502, you must have noticed that you had to use a CLC before ADC for every simple addition. xasm can do it for you. ADD replaces two instructions: CLC and ADC. SUB - subtraction It is SEC and SBC. RCC, RCS, REQ, RMI, RNE, RPL, RVC, RVS - conditional repeat These are branches to the previous instruction. They take no operand, because the branch target is the address of previously assembled instruction. Example: ldx #0 mva:rne $500,x $600,x+ The example code copies memory $500-$5ff to $600-$6ff. Here is the same written with standard 6502 commands only: ldx #0 loop lda $500,x sta $600,x inx bne loop SCC, SCS, SEQ, SMI, SNE, SPL, SVC, SVS - conditional skip These are branches over the next instructions. No operand is required, because the target is the address of the instruction following the next instruction. Example: lda #40 add:sta $80 scc:inc $81 In the above example the word-sized variable $80 is incremented by 40. JCC, JCS, JEQ, JMI, JNE, JPL, JVC, JVS - conditional jumps These are a kind of 'long' branches. While standard branches (such as BNE) have range of -128..+127, these jumps have range of all 64 kB. Example: jne dest is equivalent to: seq:jmp dest INW - increment word Increments a 16-bit word in the memory. Example: inw dest is equivalent to: inc dest sne:inc dest+1 MVA, MVX, MVY - move byte using accumulator, X or Y Each of these pseudo-commands requires two operands and substitutes two commands: mva source dest = lda source : sta dest mvx source dest = ldx source : stx dest mvy source dest = ldy source : sty dest MWA, MWX, MWY - move word using accumulator, X or Y These pseudo-commands require two operands and are combinations of two MV*'s: one to move the low byte, and the other to move the high byte. You can't use indirect nor pseudo addressing mode with MW*. Destination must be an absolute address (optionally indexed). When source is also absolute, an mw* source dest will be: mv* source dest mv* source+1 dest+1 When source is an immediate, an mw* #immed dest will be: mv* <immed dest mv* >immed dest+1 When <immed equals >immed and immed is not forward-referenced, xasm uses an optimization: mv* <immed dest st* dest+1 If possible, MWX and MWY use increment/decrement commands. E.g. mwx #1 dest is assembled as: ldx #1 stx dest dex stx dest+1 Edited May 12, 2005 by Sheddy Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.