Author
|
Topic: 16x16 2bpp vwf (Read 2 times)
|
Gideon Zhi
Guest
|
|
« on: January 24, 2007, 01:35:40 am » |
|
Alright, I'm having trouble getting this to work. It's the binary logic that's making my head spin, mostly; the code is generally functional, as it's a mashup of my Rudra no Hihou 1bpp vwf code (which does work.) Here are some snaps of the tile layout. The first is the font in ROM; the second is the rendered font bitmap in RAM. The idea behind the code is to load the tile into a scratchpad, rotate it to the right an equivalent number of shifts as the previous character required, then OR it with the font bitmap at $B080. Exceptions for not having to shift at all (a shift value of 0 or $10) have been accounted for and tested; they work fine. I've looked at the VWF examples in the database, but they're constructed differently... I apologize if my code's messy, I don't do VWFs very often. $20 - Font address (ROM) $0B - Bitmap write position (RAM) FF00-FF7F - 2bpp Scratchpad $FFE0 - Shift value
VWF: LDY #$0000 SEP #$20
FontScratchpadCopyLoop1: LDA [$20],Y STA $FF00,Y INY CPY #$0010 BNE FontScratchpadCopyLoop1 REP #$20 LDA $20 CLC ADC #$0100 STA $20 SEP #$20 LDY #$0000
FontScratchpadCopyLoop2: LDA [$20],Y STA $FF40,Y INY CPY #$0020 BNE FontScratchpadCopyLoop2
;At this point, I've got my character into the scratchpad.... ;Next is the shift loop. REP #$20 LDA $FFE0 AND #$00FF TAY SEP #$20 LDX #$0000
;Y is now number of shifts ;X is offset to shift ;A is 16 bits wide ShiftLoop0: PHY SEP #$20 ShiftLoop1: CLC ROR $FF00,X ROR $FF02,X ROR $FF04,X ROR $FF06,X CLC ROR $FF01,X ROR $FF03,X ROR $FF05,X ROR $FF07,X CLC DEY BNE ShiftLoop1 INX INX INX INX INX INX INX INX PLY CPX #$0080 BNE ShiftLoop0
;Merge scratchpad with buffer LDX #$0000 LDY $0B REP #$20
BufferMerge: LDA $FF00,X ORA $0000,Y STA $0000,Y
LDA $FF40,X ORA $0100,Y STA $0100,Y
INX INX INY INY CPX #$0040 BNE BufferMerge
The rest of it after this is cleanup and tilemap stuff, which does work. It's the meat that's broken; I get my addresses mixed up and confused :/ Figured I'd post this before going to bed with the hope that someone will come in the night and offer some help, hahah. Edit: Updated the code with the bottom-half or/copy in the merge loop.
|
|
« Last Edit: January 24, 2007, 01:58:45 am by Gideon Zhi »
|
|
|
|
RedComet
Guest
|
|
« Reply #1 on: January 24, 2007, 01:52:55 am » |
|
The only thing that stands out at me is ShiftLoop1. That looks like you're rotating too much data per iteration. Do you have a ram snap shot of the tile in the scratchpad before and after the shifts?
|
|
|
|
|
RedComet
Guest
|
|
« Reply #3 on: January 24, 2007, 02:33:50 am » |
|
I'm assuming your buffer is laid out like this in ram ($10 bytes for each 8x8 tile): TopLeft : TopRight : TempTopLeft : TempTopRight: BottomLeft : BottomRight : TempBottomLeft : TempBottomRight ;I'm assuming X = 0
ROR $FF00,X ;TopLeft Row 0 ROR $FF02,X ;TopLeft Row 1 ROR $FF04,X ;TopLeft Row 2 ROR $FF06,X ;TopLeft Row 3
You're could here goes like this: Shift TopLeft pixel row N Catch Overflow and place on TopLeft pixel row N+1 When you should be: Shift TopLeft pixel row N Catch overflow and place on TopRight pixel row N, which would be $10 bytes away. ;I'll assume X = 0
ROR $FF00,X ;TopLeft Row 0 ROR $FF10,X ;TopRight Row 0
My brain's not up for calculating the position of the next tile, so that $10 bytes (whatever size the 8x8 tile is) may be different. But you're shifting one row of pixels and instead of catching the overflow on the neighboring tile, you're catching it on the row below the row being shifted. Hope that makes sense.
|
|
|
|
Nightcrawler
Guest
|
|
« Reply #4 on: January 24, 2007, 10:20:54 am » |
|
I'm not sure what you're trying to do with your shift loop, but you're not even using the 'number of shifts value' stored in y...
Here's an idea. How about you tell us what you INTENDED for the shift loop to do. Because I doubt it's doing it. I don't know how you could have possibly tested shift value cases like you said. Unless I have a case of the Mondays on Wednesday, you're not using the shift value in Y at all.
|
|
|
|
Gideon Zhi
Guest
|
|
« Reply #5 on: January 24, 2007, 11:26:03 am » |
|
It's definitely using the value in Y: DEY BNE ShiftLoop1 I push the value in Y, run through the shift loop a number of times equivalent to the value in Y for a single line, then increase X and move on to the next line. In 1BPP at least, it looks like this: ShiftLoop0: PHY SEP #$20 ShiftLoop1: CLC ROR $FF80,X ROR $FF81,X ROR $FF82,X ROR $FF83,X DEY BNE ShiftLoop1 INX INX INX INX PLY CPX #$0040 BNE ShiftLoop0
Basically what the shift loop's supposed to be doing is going through the tile in the scratchpad line by line, rotating the character over to the right an appropriate number of times (i.e. if the previous character ended on a 16x16 pixel position 6, the rotate loop rotates the new character over 6 + a pixel of padding, all stored in Y before the shift loop calls.) Then it's supposed to be merging it with the main buffer, line by line.
|
|
|
|
Gideon Zhi
Guest
|
|
« Reply #6 on: January 24, 2007, 01:47:36 pm » |
|
Edit: Got it even cleaner! Alright, I took KingMike's suggestion. Here's the new routine, and the new output. It almost works.... (original, for easy reference) VWF: LDY #$0000 SEP #$20
FontScratchpadCopyLoop1: LDA [$20],Y STA $FF00,Y INY CPY #$0020 BNE FontScratchpadCopyLoop1 REP #$20 LDA $20 CLC ADC #$0100 STA $20 SEP #$20 LDY #$0000
FontScratchpadCopyLoop2: LDA [$20],Y STA $FF40,Y INY CPY #$0020 BNE FontScratchpadCopyLoop2
;At this point, I've got my character into the scratchpad.... ;Next is the shift loop. REP #$20 LDA $FFE0 AND #$00FF TAY SEP #$20 LDX #$0000
;Y is now number of shifts ;X is offset to shift ;A is 16 bits wide ShiftLoop0: PHY SEP #$20 ShiftLoop1: CLC ROR $FF00,X ROR $FF10,X ROR $FF20,X ROR $FF30,X ROR $FF40,X ROR $FF50,X ROR $FF60,X ROR $FF70,X CLC ROR $FF01,X ROR $FF11,X ROR $FF21,X ROR $FF31,X ROR $FF41,X ROR $FF51,X ROR $FF61,X ROR $FF71,X CLC DEY BNE ShiftLoop1 INX INX PLY CPX #$0010 BNE ShiftLoop0
;Merge scratchpad with buffer LDX #$0000 LDY $0B REP #$20
BufferMerge: LDA $FF00,X ORA $0000,Y STA $0000,Y
LDA $FF40,X ORA $0100,Y STA $0100,Y INX INX INY INY CPX #$0040 BNE BufferMerge
|
|
« Last Edit: January 24, 2007, 01:55:43 pm by Gideon Zhi »
|
|
|
|
Gideon Zhi
Guest
|
|
« Reply #7 on: January 24, 2007, 02:18:32 pm » |
|
Alright, fixed it. Had to trap for the drop-down at the end of the top row. All that's left is to fix some tilemapping issues
|
|
|
|
Cyberman
Guest
|
|
« Reply #8 on: January 24, 2007, 02:25:08 pm » |
|
Ack... well I was going to say the problem was your 'symbol wrap' algorythm. LOL. Oh well glad it works for your sanitys sake.
Cyb
|
|
|
|
RedComet
Guest
|
|
« Reply #9 on: January 24, 2007, 05:31:42 pm » |
|
Good job, Gid.
|
|
|
|
Nightcrawler
Guest
|
|
« Reply #10 on: January 24, 2007, 05:45:15 pm » |
|
Oops Sorry Gid. I indeed did have case of the Mondays on Wednesday. Higher level intelligence was not functioning today. I don't know how I missed that. Maybe it was the eight INX statements.
|
|
|
|
KingMike
Guest
|
|
« Reply #11 on: January 24, 2007, 08:24:35 pm » |
|
Alright, I took KingMike's suggestion. Here's the new routine, and the new output. It almost works....
I can't remember what my suggestion was, but it looks good just the same.
|
|
|
|
Gideon Zhi
Guest
|
|
« Reply #12 on: January 24, 2007, 08:32:56 pm » |
|
It was redcomet's suggestion My brain wasn't working at the time, I swear! ...seems like this is pretty common around here today, hah.
|
|
|
|
Neil
Guest
|
|
« Reply #13 on: January 01, 2009, 09:08:43 pm » |
|
-necrobump to save a thread from the great board prune of 2009- some arguably useful teaching type stuff in here.
|
|
|
|
|