![]() |
Routines |
| Prev: C352 | Up: Map | Next: C463 |
|
Used by the routine at DrawPicture.
Continues from DrawPicture.
|
||||
|
Find out where this code is in memory. The call leaves its return address (DrawPicture_ReturnAddress) just below the stack pointer. An interrupt at this point would overwrite it, so BASIC calls Disable Interrupts first and Enable Interrupts afterwards.
|
||||
| DrawPicture_Unpack | C356 | CALL $007C | Call the RET instruction at 007C, at the end of CH_ADD+1, which returns straight away. | |
| DrawPicture_ReturnAddress | C359 | DEC SP | Move the stack pointer back down to the return address. | |
| C35A | DEC SP | |||
| C35B | EX (SP),HL | Swap it into HL, so HL=DrawPicture_ReturnAddress. | ||
| C35C | INC SP | Move the stack pointer back up again. | ||
| C35D | INC SP | |||
| C35E | AND A | Clear the carry flag ready for the subtraction. | ||
| C35F | LD DE,$0007 | HL=DrawPicture_Number (DrawPicture_ReturnAddress less 0007). | ||
| C362 | SBC HL,DE | |||
| C364 | PUSH HL | Stash the address of the parameters on the stack. | ||
| C365 | POP IY | Restore the address of the parameters from the stack into IY. | ||
| C367 | LD DE,$012A | HL=Graphics_Desk (DrawPicture_Number plus 012A), the first picture record. | ||
| C36A | ADD HL,DE | |||
| C36B | LD A,(IY+$00) | A=the picture number from *DrawPicture_Number. | ||
|
Skip over the records before the requested picture.
|
||||
| DrawPicture_FindPicture | C36E | DEC A | Decrease the picture number by one. | |
| C36F | JR Z,DrawPicture_Found | Jump to DrawPicture_Found if HL points to the requested picture. | ||
| C371 | LD E,(HL) | DE=the length of this record, less one. | ||
| C372 | INC HL | |||
| C373 | LD D,(HL) | |||
| C374 | ADD HL,DE | Add it to HL, so HL points to the next record. | ||
| C375 | JR DrawPicture_FindPicture | Jump to DrawPicture_FindPicture. | ||
| DrawPicture_Found | C377 | LD DE,$4000 | DE=4000. This value is never used, as D and E are both set again before they are needed. | |
| C37A | INC HL | Move HL past the length, to the record's screen third. | ||
| C37B | INC HL | |||
| C37C | LD A,(IY+$01) | A=*DrawPicture_Third. | ||
| C37F | INC A | Increment A by one, so that FF becomes zero. | ||
| C380 | JR NZ,DrawPicture_Unpack_0 | Jump to DrawPicture_Unpack_0 if *DrawPicture_Third is not FF. | ||
| C382 | LD A,(HL) | Else write the record's screen third to *DrawPicture_Third. | ||
| C383 | LD (IY+$01),A | |||
| DrawPicture_Unpack_0 | C386 | INC HL | Move on to the record's number of thirds. | |
| C387 | LD A,(IY+$02) | A=*DrawPicture_Thirds. | ||
| C38A | INC A | Increment A by one, so that FF becomes zero. | ||
| C38B | JR NZ,DrawPicture_Unpack_1 | Jump to DrawPicture_Unpack_1 if *DrawPicture_Thirds is not FF. | ||
| C38D | LD A,(HL) | Else write the record's number of thirds to *DrawPicture_Thirds. | ||
| C38E | LD (IY+$02),A | |||
| DrawPicture_Unpack_1 | C391 | INC HL | Move on to the record's flags. | |
| C392 | LD A,(HL) | Copy the record's flags to *DrawPicture_Flags. | ||
| C393 | LD (IY+$03),A | |||
|
Make sure the picture fits on the screen.
|
||||
| C396 | LD A,(IY+$01) | A=*DrawPicture_Third. | ||
| C399 | CP $03 | Jump to DrawPicture_Unpack_2 if the screen third is less than 03. | ||
| C39B | JR C,DrawPicture_Unpack_2 | |||
| C39D | LD (IY+$01),$00 | Else start at the top third (write 00 to *DrawPicture_Third). | ||
| DrawPicture_Unpack_2 | C3A1 | LD A,(IY+$02) | A=*DrawPicture_Thirds. | |
| C3A4 | CP $04 | Jump to DrawPicture_Unpack_3 if the number of thirds is less than 04. | ||
| C3A6 | JR C,DrawPicture_Unpack_3 | |||
| C3A8 | LD (IY+$02),$01 | Else draw one third (write 01 to *DrawPicture_Thirds). | ||
| DrawPicture_Unpack_3 | C3AC | ADD A,(IY+$01) | Add the screen third to A. A still holds the number of thirds read at DrawPicture_Unpack_2, even when it has just been changed. | |
| C3AF | CP $04 | Jump to DrawPicture_Unpack_4 if the picture ends on the screen (the total is less than 04). | ||
| C3B1 | JR C,DrawPicture_Unpack_4 | |||
| C3B3 | LD (IY+$02),$01 | Else draw one third (write 01 to *DrawPicture_Thirds). | ||
| DrawPicture_Unpack_4 | C3B7 | LD A,(IY+$02) | A=*DrawPicture_Thirds. | |
| C3BA | AND A | Jump to DrawPicture_Pixels if the number of thirds is not zero. | ||
| C3BB | JR NZ,DrawPicture_Pixels | |||
| C3BD | LD (IY+$02),$01 | Else draw one third (write 01 to *DrawPicture_Thirds). | ||
|
Draw the pixels.
|
||||
| DrawPicture_Pixels | C3C1 | INC HL | Move HL on to the start of the picture data. | |
| C3C2 | LD E,$00 | E=00 (the left-hand column). | ||
| C3C4 | LD A,(IY+$01) | A=*DrawPicture_Third. | ||
| C3C7 | ADD A,A | Multiply it by 08 as each third of the screen is 08 pages long. | ||
| C3C8 | ADD A,A | |||
| C3C9 | ADD A,A | |||
| DrawPicture_PixelsHighByte | C3CA | ADD A,$40 | Add the high byte of the start of the screen (40). BASIC POKEs this byte to draw into a buffer instead. | |
| C3CC | LD D,A | Set D and C to the high byte of the top pixel line of the picture, so DE holds its screen address. | ||
| C3CD | LD C,A | |||
| C3CE | LD B,$01 | B=01 (one pass, for row order). | ||
| C3D0 | BIT 0,(IY+$03) | Jump to DrawPicture_PassLoop if bit 0 of *DrawPicture_Flags is set (row order). | ||
| C3D4 | JR NZ,DrawPicture_PassLoop | |||
| C3D6 | LD B,$20 | Else B=20 (one pass for each column). | ||
| DrawPicture_PassLoop | C3D8 | PUSH BC | Stash the pass counter on the stack. | |
| C3D9 | LD B,(IY+$02) | B=the number of thirds from *DrawPicture_Thirds. | ||
| DrawPicture_ThirdLoop | C3DC | PUSH BC | Stash the thirds counter on the stack. | |
| C3DD | LD B,$08 | B=08 (character rows in a third). | ||
| DrawPicture_RowLoop | C3DF | PUSH BC | Stash the character row counter on the stack. | |
| C3E0 | LD B,$08 | B=08 (pixel lines in a character row). | ||
| DrawPicture_LineLoop | C3E2 | PUSH BC | Stash the pixel line counter on the stack. | |
| C3E3 | LD B,$01 | B=01 (one byte, for column order). | ||
| C3E5 | BIT 0,(IY+$03) | Jump to DrawPicture_Unpack_5 if bit 0 of *DrawPicture_Flags is clear (column order). | ||
| C3E9 | JR Z,DrawPicture_Unpack_5 | |||
| C3EB | LD B,$20 | Else B=20 (a whole pixel line, for row order). | ||
| DrawPicture_Unpack_5 | C3ED | PUSH DE | Stash the screen address of this pixel line on the stack. | |
| DrawPicture_ByteLoop | C3EE | PUSH BC | Stash the byte counter on the stack. | |
| C3EF | JR DrawPicture_FetchByte | Jump to DrawPicture_FetchByte to write the next byte; it comes back to DrawPicture_NextByte. | ||
| DrawPicture_NextByte | C3F1 | POP BC | Restore the byte counter from the stack. | |
| C3F2 | INC DE | Move right to the next screen byte. | ||
| C3F3 | DJNZ DrawPicture_ByteLoop | Decrease the byte counter by one and loop back to DrawPicture_ByteLoop until it is zero. | ||
| C3F5 | POP DE | Restore the screen address of this pixel line from the stack. | ||
| C3F6 | POP BC | Restore the pixel line counter from the stack. | ||
| C3F7 | INC D | Move down to the next pixel line. | ||
| C3F8 | DJNZ DrawPicture_LineLoop | Decrease the pixel line counter by one and loop back to DrawPicture_LineLoop until all 08 pixel lines are done. | ||
| C3FA | LD A,D | Move D back up to the top pixel line of this character row (subtract 08). | ||
| C3FB | SUB $08 | |||
| C3FD | LD D,A | |||
| C3FE | LD A,E | Move down to the next character row (add 20 to E). | ||
| C3FF | ADD A,$20 | |||
| C401 | LD E,A | |||
| C402 | POP BC | Restore the character row counter from the stack. | ||
| C403 | DJNZ DrawPicture_RowLoop | Decrease the character row counter by one and loop back to DrawPicture_RowLoop until all 08 character rows are done. | ||
| C405 | LD A,D | Move down to the next third (add 08 to D). E has gone back round to the same column. | ||
| C406 | ADD A,$08 | |||
| C408 | LD D,A | |||
| C409 | POP BC | Restore the thirds counter from the stack. | ||
| C40A | DJNZ DrawPicture_ThirdLoop | Decrease the thirds counter by one and loop back to DrawPicture_ThirdLoop until all the thirds are done. | ||
| C40C | LD D,C | Move D back up to the top of the picture (D=C). | ||
| C40D | INC E | Move right to the next column. | ||
| C40E | POP BC | Restore the pass counter from the stack. | ||
| C40F | DJNZ DrawPicture_PassLoop | Decrease the pass counter by one and loop back to DrawPicture_PassLoop until all the passes are done. | ||
|
Draw the attributes.
|
||||
| DrawPicture_Attributes | C411 | LD E,$00 | E=00. | |
| DrawPicture_AttributesHighByte | C413 | LD A,$58 | A=58 the high byte of the start of the attribute file. BASIC POKEs this byte to draw into a buffer instead. | |
| C415 | ADD A,(IY+$01) | Add the screen third. | ||
| C418 | LD D,A | D=A, so DE holds the address of the first attribute of the picture. | ||
| C419 | LD B,(IY+$02) | BC=the number of attributes to draw: 256 for each third (B=*DrawPicture_Thirds and C=00). | ||
| C41C | LD C,E | |||
| C41D | SET 3,(IY+$03) | Set bit 3 of *DrawPicture_Flags, so that DrawPicture_FetchByte comes back to DrawPicture_NextAttribute. | ||
| DrawPicture_AttributesLoop | C421 | PUSH BC | Stash the attribute counter on the stack. | |
| C422 | JR DrawPicture_FetchByte | Jump to DrawPicture_FetchByte to write the next attribute; it comes back to DrawPicture_NextAttribute. | ||
| DrawPicture_NextAttribute | C424 | POP BC | Restore the attribute counter from the stack. | |
| C425 | DEC BC | Decrease the attribute counter by one. | ||
| C426 | INC DE | Move on to the next attribute. | ||
| C427 | LD A,B | Jump back to DrawPicture_AttributesLoop until the attribute counter is zero. | ||
| C428 | OR C | |||
| C429 | JR NZ,DrawPicture_AttributesLoop | |||
| C42B | LD (IY+$01),$FF | Write FF to *DrawPicture_Third and *DrawPicture_Thirds. BASIC never POKEs these bytes, so the next picture again takes its screen third and number of thirds from its own record. | ||
| C42F | LD (IY+$02),$FF | |||
| C433 | RET | Return. | ||
|
Write the next byte of picture data to *DE. While a run of repeated bytes is being written, bit 2 of *DrawPicture_Flags is set, B' holds the count and C' holds the value.
|
||||
| DrawPicture_FetchByte | C434 | BIT 2,(IY+$03) | Jump to DrawPicture_ReadByte if no run is in progress. | |
| C438 | JR Z,DrawPicture_ReadByte | |||
| C43A | EXX | Switch to the shadow registers. | ||
| C43B | DEC B | Decrease the run count in B' by one. | ||
| C43C | LD A,C | A=the run value from C'. | ||
| C43D | EXX | Switch back to the normal registers. | ||
| C43E | JR Z,DrawPicture_EndRun | Jump to DrawPicture_EndRun if the run has finished. | ||
| C440 | LD (DE),A | Write the run value to *DE. | ||
| C441 | JR DrawPicture_Continue | Jump to DrawPicture_Continue. | ||
| DrawPicture_EndRun | C443 | RES 2,(IY+$03) | Clear bit 2 of *DrawPicture_Flags, as the run has finished. | |
| DrawPicture_ReadByte | C447 | LD A,(HL) | A=the next byte of picture data, and move HL on. | |
| C448 | INC HL | |||
| C449 | AND A | Jump to DrawPicture_WriteByte if it is not zero, to write it as it is. | ||
| C44A | JR NZ,DrawPicture_WriteByte | |||
| C44C | LD A,(HL) | A zero byte starts a run. B'=the count. | ||
| C44D | EXX | |||
| C44E | LD B,A | |||
| C44F | EXX | |||
| C450 | INC HL | Move HL on to the value. | ||
| C451 | LD A,(HL) | C'=the value (A holds it too). | ||
| C452 | EXX | |||
| C453 | LD C,A | |||
| C454 | EXX | |||
| C455 | INC HL | Move HL on to the next byte of picture data. | ||
| C456 | SET 2,(IY+$03) | Set bit 2 of *DrawPicture_Flags, as a run is in progress. | ||
| DrawPicture_WriteByte | C45A | LD (DE),A | Write the byte to *DE. | |
| DrawPicture_Continue | C45B | BIT 3,(IY+$03) | Jump back to DrawPicture_NextAttribute if the attributes are being drawn. | |
| C45F | JR NZ,DrawPicture_NextAttribute | |||
| C461 | JR DrawPicture_NextByte | Else jump back to DrawPicture_NextByte. | ||
|
View the equivalent code in;
|
||||
| Prev: C352 | Up: Map | Next: C463 |