Skip to navigation

Elite on the BBC Micro and NES

Drawing lines: EDGES

[NES version, Bank 1]

Name: EDGES [Show more] Type: Subroutine Category: Drawing lines Summary: Draw a horizontal line given a centre and a half-width
Context: See this subroutine in context in the source code References: This subroutine is called as follows: * SUN (Part 2 of 2) calls EDGES * SUN (Part 2 of 2) calls via EDGES-2

Set X1 and X2 to the x-coordinates of the ends of the horizontal line with centre x-coordinate YY(1 0), and length A in either direction from the centre (so a total line length of 2 * A). In other words, this line: X1 YY(1 0) X2 +-----------------+-----------------+ <- A -> <- A -> The resulting line gets clipped to the edges of the screen, if needed. If the calculation doesn't overflow, we return with the C flag clear, otherwise the C flag gets set to indicate failure.
Arguments: A The half-length of the line YY(1 0) The centre x-coordinate
Returns: C flag Clear if the line fits on-screen, set if it doesn't X1, X2 The x-coordinates of the clipped line Y Y is preserved
Other entry points: EDGES-2 Return the C flag set if argument A is 0
.ED3 BPL ED1 ; We jump here with the status flags set to the result ; of the high byte of this subtraction, and only if the ; high byte is non-zero: ; ; (A X1) = YY(1 0) - argument A ; ; If the result of the subtraction is positive and ; non-zero then the coordinate is not on-screen, so jump ; to ED1 to return the C flag set LDA #0 ; The result of the subtraction is negative, so we have STA X1 ; have gone past the left edge of the screen, so we clip ; the x-coordinate in X1 to 0 CLC ; Clear the C flag to indicate that the clipped line ; fits on-screen RTS ; Return from the subroutine .ED1 SETUP_PPU_FOR_ICON_BAR ; If the PPU has started drawing the icon bar, configure ; the PPU to use nametable 0 and pattern table 0 SEC ; Set the C flag to indicate that the line does not fit ; on-screen RTS ; Return from the subroutine BEQ ED1 ; If we call the routine at EDGES-2, this checks whether ; the argument in A is zero, and if it is, it jumps to ; ED1 to return the C flag set .EDGES STA T ; Set T to the line's half-length in argument A CLC ; We now calculate: ADC YY ; STA X2 ; (A X2) = YY(1 0) + A ; ; to set X2 to the x-coordinate of the right end of the ; line, starting with the low bytes LDA YY+1 ; And then adding the high bytes ADC #0 BMI ED1 ; If the addition is negative then the calculation has ; overflowed, so jump to ED1 to return a failure BEQ P%+6 ; If the high byte A from the result is 0, skip the ; next two instructions, as the result already fits on ; the screen LDA #253 ; The high byte is positive and non-zero, so we went STA X2 ; past the right edge of the screen, so clip X2 to the ; x-coordinate of the right edge of the screen LDA YY ; We now calculate: SEC ; SBC T ; (A X1) = YY(1 0) - argument A STA X1 ; ; to set X1 to the x-coordinate of the left end of the ; line, starting with the low bytes LDA YY+1 ; And then subtracting the high bytes SBC #0 BNE ED3 ; If the high byte of the subtraction is non-zero, then ; jump to ED3 to return a failure if the subtraction has ; taken us off the left edge of the screen LDA X1 ; Set the C flag if X1 >= X2, clear it if X1 < X2 CMP X2 ; ; So this sets the C flag if the line doesn't fit on ; the screen RTS ; Return from the subroutine