mirror of
https://github.com/antoinevignau/source.git
synced 2025-01-07 22:32:55 +00:00
1 line
16 KiB
Plaintext
Executable File
1 line
16 KiB
Plaintext
Executable File
|
|
LOAD 'Macros.dump'
|
|
|
|
INCLUDE 'SS.equ'
|
|
|
|
INCLUDE 'Driver.equ'
|
|
INCLUDE 'Heap.aii.i'
|
|
|
|
;-----------------------------------------------
|
|
;
|
|
; Imported addresses
|
|
;
|
|
;-----------------------------------------------
|
|
|
|
IMPORT D_AlertBox
|
|
IMPORT D_CmpStrings
|
|
IMPORT D_MemoryError
|
|
IMPORT D_NeedHand
|
|
IMPORT D_Sort
|
|
|
|
IMPORT S_ActiveWindow
|
|
IMPORT S_BuildSortUndo
|
|
IMPORT S_CalculateSheet
|
|
IMPORT S_CurBRMost
|
|
IMPORT S_CurBRSelect
|
|
IMPORT S_CurEditFlag
|
|
IMPORT S_CurRowBlock
|
|
IMPORT S_CurTLSelect
|
|
IMPORT S_DeltaMove
|
|
IMPORT S_DoSortDlog
|
|
IMPORT S_GetCellIndex
|
|
IMPORT S_InvalidCellStr
|
|
IMPORT S_MoveDestBR
|
|
IMPORT S_MoveDestTL
|
|
IMPORT S_MoveSrcBR
|
|
IMPORT S_MoveSrcTL
|
|
IMPORT S_RedrawCellRange
|
|
IMPORT S_SetBRMostCell
|
|
IMPORT S_SetUndoOn
|
|
IMPORT S_StartSortUndo
|
|
IMPORT S_SwapCell
|
|
IMPORT S_SwapIn
|
|
|
|
;-----------------------------------------------
|
|
;
|
|
; Forward addresses and entries
|
|
;
|
|
;-----------------------------------------------
|
|
|
|
ENTRY S_DoColSort
|
|
ENTRY S_DoRowSort
|
|
ENTRY S_SortCompare
|
|
ENTRY S_SwapColumns
|
|
ENTRY S_SwapRows
|
|
|
|
;-------------------------------------------------------------------------
|
|
;
|
|
;
|
|
|
|
S_SortData PROC EXPORT
|
|
|
|
EXPORT S_SortAscendDescendFlag
|
|
|
|
S_SortAscendDescendFlag DS.B 2
|
|
|
|
ENDP
|
|
|
|
;--------------------------------------------------------------------------
|
|
;
|
|
;
|
|
|
|
S_Sort PROC EXPORT
|
|
;Using S_CurrentData
|
|
;Using S_SortData
|
|
;Using S_MoveData
|
|
;Using S_ErrorData
|
|
|
|
local KeyCell:l,Type:w
|
|
error ErrFlag
|
|
BEGIN +b
|
|
|
|
Call S_SwapIn,in=(S_ActiveWindow:l)
|
|
|
|
; ascend: 0==decending,1==ascending
|
|
; rowcol: 0==col by row,1==row by col
|
|
; cell: 0 == Cancelled, 0 w/carry set == error
|
|
|
|
in S_CurTLSelect:l
|
|
out S_SortAscendDescendFlag:w,Type:w,KeyCell:l
|
|
XCall S_DoSortDlog
|
|
|
|
bcc doOK
|
|
|
|
Call D_AlertBox,in=(#OKBox:w,#S_InvalidCellStr:l),out=(a:w)
|
|
|
|
doOK
|
|
lda KeyCell
|
|
ora KeyCell+2
|
|
jeq Exit
|
|
|
|
lda S_CurEditFlag
|
|
and #S_BRMostBit
|
|
beq BRset
|
|
|
|
Call S_SetBRMostCell,in=(#0:w)
|
|
|
|
BRset
|
|
lda #S_BRMostBit
|
|
tsb S_CurEditFlag
|
|
|
|
MoveWord S_CurTLSelect,S_MoveDestTL
|
|
sta S_MoveSrcTL
|
|
MoveWord S_CurTLSelect+2,S_MoveDestTL+2
|
|
sta S_MoveSrcTL+2
|
|
|
|
MoveWord S_CurBRSelect,S_MoveDestBR
|
|
sta S_MoveSrcBR
|
|
MoveWord S_CurBRSelect+2,S_MoveDestBR+2
|
|
sta S_MoveSrcBR+2
|
|
|
|
lda Type
|
|
bne doRowSort
|
|
|
|
doColSort
|
|
ldx S_CurBRSelect+2
|
|
cpx S_CurBRMost+2
|
|
blt doCol2
|
|
|
|
ldx S_CurBRMost+2
|
|
|
|
doCol2
|
|
in S_CurTLSelect:l,x:w,S_CurBRSelect:w,KeyCell:w
|
|
XCall S_DoColSort,err=ErrFlag
|
|
bcc redraw
|
|
bra memError
|
|
|
|
doRowSort
|
|
ldx S_CurBRSelect
|
|
cpx S_CurBRMost
|
|
blt doRow2
|
|
|
|
ldx S_CurBRMost
|
|
|
|
doRow2
|
|
in S_CurTLSelect:l,S_CurBRSelect+2:w,x:w,KeyCell+2:w
|
|
XCall S_DoRowSort,err=ErrFlag
|
|
bcc redraw
|
|
|
|
memError
|
|
Call D_MemoryError
|
|
|
|
redraw
|
|
CmpWord S_MoveSrcBR+2,S_MoveDestBR+2
|
|
blt chkLeft
|
|
|
|
sta S_MoveDestBR+2
|
|
|
|
chkLeft
|
|
CmpWord S_MoveSrcTL+2,S_MoveDestTL+2
|
|
bge doDraw
|
|
|
|
sta S_MoveDestTL+2
|
|
|
|
doDraw
|
|
in S_MoveDestTL:l,S_MoveDestBR:l
|
|
XCall S_RedrawCellRange
|
|
|
|
Call S_SetUndoOn,in=(#S_UndoSortType:w)
|
|
|
|
lda S_CurEditFlag
|
|
and #S_ManCalcBit
|
|
bne Exit
|
|
|
|
Call S_CalculateSheet
|
|
|
|
Exit
|
|
RETURN
|
|
ENDP
|
|
|
|
;-----------------------------------------------------------------------------
|
|
;
|
|
;
|
|
|
|
S_DoRowSort PROC EXPORT
|
|
;Using S_CurrentData
|
|
|
|
input FCol:w,FRow:w,LCol:w,LRow:w,KeyCol:w
|
|
local ArrayHandle:l,ArrayPtr:l,ArraySize:w,Count:w
|
|
local ArrayOffset:w,TargOffset:w,CurRow:w,CellPtr:l
|
|
local TargRow:w,SrcRow:w
|
|
error ErrorFlag
|
|
BEGIN
|
|
|
|
stz ErrorFlag
|
|
|
|
SubWord LRow,FRow,a
|
|
inc a
|
|
sta Count
|
|
|
|
asl a
|
|
asl a
|
|
sta ArraySize
|
|
|
|
in #0:w,ArraySize:w
|
|
out ArrayHandle:l
|
|
XCall D_NeedHand,err=ErrorFlag
|
|
jcs Exit
|
|
|
|
; Set up the original array, filled with cell indices ;
|
|
|
|
MoveLong [ArrayHandle],ArrayPtr
|
|
|
|
MoveWord FRow,CurRow
|
|
stz ArrayOffset
|
|
bra startInit
|
|
|
|
initLoop
|
|
inc CurRow
|
|
AddWord ArrayOffset,#4,ArrayOffset
|
|
|
|
startInit
|
|
in KeyCol:w,CurRow:w
|
|
out [ArrayPtr]:ArrayOffset:l
|
|
XCall S_GetCellIndex
|
|
|
|
ldy ArrayOffset
|
|
ora [ArrayPtr],y
|
|
bne cmpInit
|
|
|
|
tya
|
|
sta [ArrayPtr],y
|
|
iny
|
|
iny
|
|
MoveWord #$FF00,[ArrayPtr]:y
|
|
|
|
cmpInit
|
|
CmpWord CurRow,LRow
|
|
blt initLoop
|
|
|
|
; Sort the array ;
|
|
|
|
in #0:w,Count:w,ArrayHandle:l,#S_SortCompare:l
|
|
XCall D_Sort,err=ErrorFlag
|
|
jcs memError
|
|
|
|
; Renumber array for easy sorting ;
|
|
|
|
MoveLong [ArrayHandle],ArrayPtr
|
|
|
|
stz ArrayOffset
|
|
|
|
renumLoop
|
|
ldy ArrayOffset
|
|
iny
|
|
iny
|
|
lda [ArrayPtr],y
|
|
bmi cmpRenum
|
|
|
|
H_GetBlockPtr [ArrayPtr]:ArrayOffset,CellPtr
|
|
|
|
SubWord [CellPtr]:#S_CellID,FRow,a
|
|
asl a
|
|
asl a
|
|
MoveWord a,[ArrayPtr]:ArrayOffset
|
|
|
|
cmpRenum
|
|
AddWord ArrayOffset,#4,ArrayOffset
|
|
|
|
CmpWord ArrayOffset,ArraySize
|
|
blt renumLoop
|
|
|
|
|
|
in #0:w,FCol:w,FRow:w,LCol:w,LRow:w
|
|
XCall S_StartSortUndo
|
|
|
|
|
|
; Make Spreadsheet reflect the array ;
|
|
|
|
stz CurRow
|
|
stz ArrayOffset
|
|
|
|
swapLoop
|
|
MoveLong [ArrayHandle],ArrayPtr
|
|
MoveWord [ArrayPtr]:ArrayOffset,TargOffset
|
|
|
|
cmp ArrayOffset
|
|
beq cmpSwapEnd
|
|
bge doSwap
|
|
|
|
targLoop
|
|
MoveWord [ArrayPtr]:TargOffset,TargOffset
|
|
|
|
cmp ArrayOffset
|
|
beq cmpSwapEnd
|
|
blt targLoop
|
|
|
|
doSwap
|
|
lsr a
|
|
lsr a
|
|
AddWord a,FRow,TargRow
|
|
|
|
AddWord CurRow,FRow,SrcRow
|
|
|
|
in FCol:w,SrcRow:w,LCol:w,TargRow:w
|
|
XCall S_BuildSortUndo
|
|
|
|
Call S_SwapRows,in=(FCol:w,SrcRow:w,LCol:w,TargRow:w)
|
|
|
|
cmpSwapEnd
|
|
inc CurRow
|
|
AddWord ArrayOffset,#4,ArrayOffset
|
|
|
|
CmpWord a,ArraySize
|
|
blt swapLoop
|
|
|
|
memError
|
|
Tool _DisposeHandle,in=(ArrayHandle:l)
|
|
|
|
Exit
|
|
RETURN
|
|
ENDP
|
|
|
|
;-----------------------------------------------------------------------------
|
|
;
|
|
;
|
|
|
|
S_DoColSort PROC EXPORT
|
|
;Using S_CurrentData
|
|
|
|
input FCol:w,FRow:w,LCol:w,LRow:w,KeyRow:w
|
|
local ArrayHandle:l,ArrayPtr:l,ArraySize:w,Count:w
|
|
local ArrayOffset:w,TargOffset:w,CurCol:w,CellPtr:l
|
|
local TargCol:w,SrcCol:w
|
|
error ErrorFlag
|
|
BEGIN
|
|
|
|
stz ErrorFlag
|
|
|
|
SubWord LCol,FCol,a
|
|
inc a
|
|
sta Count
|
|
|
|
asl a
|
|
asl a
|
|
sta ArraySize
|
|
|
|
in #0:w,ArraySize:w
|
|
out ArrayHandle:l
|
|
XCall D_NeedHand,err=ErrorFlag
|
|
jcs Exit
|
|
|
|
; Set up the original array, filled with cell indices ;
|
|
|
|
MoveLong [ArrayHandle],ArrayPtr
|
|
|
|
MoveWord FCol,CurCol
|
|
stz ArrayOffset
|
|
bra startInit
|
|
|
|
initLoop
|
|
inc CurCol
|
|
AddWord ArrayOffset,#4,ArrayOffset
|
|
|
|
startInit
|
|
in CurCol:w,KeyRow:w
|
|
out [ArrayPtr]:ArrayOffset:l
|
|
XCall S_GetCellIndex
|
|
|
|
ldy ArrayOffset
|
|
ora [ArrayPtr],y
|
|
bne cmpInit
|
|
|
|
tya
|
|
sta [ArrayPtr],y
|
|
iny
|
|
iny
|
|
MoveWord #$FF00,[ArrayPtr]:y
|
|
|
|
cmpInit
|
|
CmpWord CurCol,LCol
|
|
blt initLoop
|
|
|
|
; Sort the array ;
|
|
|
|
in #0:w,Count:w,ArrayHandle:l,#S_SortCompare:l
|
|
XCall D_Sort,err=ErrorFlag
|
|
jcs memError
|
|
|
|
; Renumber array for easy sorting ;
|
|
|
|
MoveLong [ArrayHandle],ArrayPtr
|
|
|
|
stz ArrayOffset
|
|
|
|
renumLoop
|
|
ldy ArrayOffset
|
|
iny
|
|
iny
|
|
lda [ArrayPtr],y
|
|
bmi cmpRenum
|
|
|
|
H_GetBlockPtr [ArrayPtr]:ArrayOffset,CellPtr
|
|
|
|
SubWord [CellPtr]:#S_CellID+2,FCol,a
|
|
asl a
|
|
asl a
|
|
MoveWord a,[ArrayPtr]:ArrayOffset
|
|
|
|
cmpRenum
|
|
AddWord ArrayOffset,#4,ArrayOffset
|
|
|
|
CmpWord ArrayOffset,ArraySize
|
|
blt renumLoop
|
|
|
|
|
|
Call S_StartSortUndo,in=(#1:w,FCol:w,FRow:w,LCol:w,LRow:w)
|
|
|
|
; Make Spreadsheet reflect the array ;
|
|
|
|
stz CurCol
|
|
stz ArrayOffset
|
|
|
|
swapLoop
|
|
MoveLong [ArrayHandle],ArrayPtr
|
|
MoveWord [ArrayPtr]:ArrayOffset,TargOffset
|
|
|
|
cmp ArrayOffset
|
|
beq cmpSwap
|
|
bge doSwap
|
|
|
|
targLoop
|
|
MoveWord [ArrayPtr]:TargOffset,TargOffset
|
|
|
|
cmp ArrayOffset
|
|
beq cmpSwap
|
|
blt targLoop
|
|
|
|
doSwap
|
|
lsr a
|
|
lsr a
|
|
AddWord a,FCol,TargCol
|
|
|
|
AddWord CurCol,FCol,SrcCol
|
|
|
|
in SrcCol:w,FRow:w,TargCol:w,LRow:w
|
|
XCall S_BuildSortUndo
|
|
|
|
Call S_SwapColumns,in=(SrcCol:w,FRow:w,TargCol:w,LRow:w)
|
|
|
|
cmpSwap
|
|
inc CurCol
|
|
AddWord ArrayOffset,#4,ArrayOffset
|
|
|
|
CmpWord a,ArraySize
|
|
blt swapLoop
|
|
|
|
memError
|
|
Tool _DisposeHandle,in=(ArrayHandle:l)
|
|
|
|
Exit
|
|
RETURN
|
|
ENDP
|
|
|
|
;---------------------------------------------------------------------------
|
|
; S_SortCompare ( CellIndex1:l,CellIndex2:l ) : bool:w
|
|
;
|
|
; This routine compares the two cells contents according to
|
|
; S_SortAscendDescendFlag for the Sort routines.
|
|
|
|
S_SortCompare PROC EXPORT
|
|
;Using S_CurrentData
|
|
;Using S_SortData
|
|
;Using SANEequs
|
|
|
|
input CellIndex1:l,CellIndex2:l
|
|
output OneGreaterFlag:w
|
|
local CellPtr1:l,CellPtr2:l
|
|
local Cell1Error:w,Cell1NA:w,Cell1Value:w,Cell1Text:w
|
|
local Format:w
|
|
BEGIN +b
|
|
|
|
stz Cell1Error
|
|
stz Cell1NA
|
|
stz Cell1Value
|
|
stz Cell1Text
|
|
|
|
lda CellIndex1+2
|
|
bmi getCell2
|
|
|
|
H_GetBlockPtr CellIndex1,CellPtr1
|
|
|
|
MoveWord [CellPtr1]:#S_CellFormat,Format
|
|
bmi getCell2
|
|
|
|
and #S_CellInvalid
|
|
beq cell1OK
|
|
|
|
lda Format
|
|
and #S_CellError
|
|
beq doCell1NA
|
|
|
|
inc Cell1Error
|
|
bra getCell2
|
|
|
|
doCell1NA
|
|
inc Cell1NA
|
|
bra getCell2
|
|
|
|
cell1OK
|
|
lda Format
|
|
and #S_CellTypeValue
|
|
bne doCell1Value
|
|
|
|
inc Cell1Text
|
|
bra getCell2
|
|
|
|
doCell1Value
|
|
inc Cell1Value
|
|
|
|
getCell2
|
|
lda CellIndex2+2
|
|
jmi doTwoGreater
|
|
|
|
H_GetBlockPtr CellIndex2,CellPtr2
|
|
|
|
MoveWord [CellPtr2]:#S_CellFormat,Format
|
|
bmi doTwoGreater
|
|
|
|
and #S_CellInvalid
|
|
beq cell2OK
|
|
|
|
lda Format
|
|
and #S_CellError
|
|
beq doCell2NA
|
|
|
|
lda #0
|
|
bra doCell2Error
|
|
|
|
cell2OK
|
|
lda Format
|
|
and #S_CellTypeValue
|
|
bne chkCell2Value
|
|
|
|
lda Cell1Text
|
|
beq doCell2Text
|
|
|
|
bra doTextCmp
|
|
|
|
chkCell2Value
|
|
lda Cell1Value
|
|
beq doCell2Value
|
|
|
|
AddLong CellPtr1,#S_CellValue,s
|
|
AddLong CellPtr2,#S_CellValue,s
|
|
|
|
lda S_SortAscendDescendFlag
|
|
beq cmpValueAscend
|
|
bra cmpValueDescend
|
|
|
|
doCell2Error ora Cell1Error
|
|
doCell2NA ora Cell1NA
|
|
doCell2Value ora Cell1Value
|
|
doCell2Text ora Cell1Text
|
|
|
|
bne doTwoGreater
|
|
|
|
doOneGreater
|
|
MoveWord #1,OneGreaterFlag
|
|
bra Exit
|
|
|
|
doTwoGreater
|
|
stz OneGreaterFlag
|
|
|
|
Exit
|
|
RETURN
|
|
|
|
cmpValueAscend
|
|
Tool FCPXX,in=(:l,:l)
|
|
|
|
FBGT doOneGreater
|
|
bra doTwoGreater
|
|
|
|
cmpValueDescend
|
|
Tool FCPXX,in=(:l,:l)
|
|
|
|
FBLT doOneGreater
|
|
bra doTwoGreater
|
|
|
|
doTextCmp
|
|
SpaceWord
|
|
H_GetBlockPtr [CellPtr1]:#S_CellValue,s
|
|
H_GetBlockPtr [CellPtr2]:#S_CellValue,s
|
|
Call D_CmpStrings,in=(:l,:l,#0:w) ; out=(:w)
|
|
|
|
lda S_SortAscendDescendFlag
|
|
beq cmpTextAscend
|
|
|
|
cmpTextDescend
|
|
pla
|
|
bmi doOneGreater
|
|
bra doTwoGreater
|
|
|
|
cmpTextAscend
|
|
pla
|
|
bmi doTwoGreater
|
|
beq doTwoGreater
|
|
brl doOneGreater
|
|
|
|
ENDP
|
|
|
|
;---------------------------------------------------------------------------
|
|
; S_SwapColumns (TLCell:l,BRCell:l)
|
|
;
|
|
; This routine traverses the first and last column of this given region
|
|
; and calls S_SwapCell if either of the two cells in a row is non-empty.
|
|
|
|
S_SwapColumns PROC EXPORT
|
|
;Using S_CurrentData
|
|
;Using S_MoveData
|
|
|
|
input Col1:w,FRow:w,Col2:w,LRow:w
|
|
local RowBlock:l,RowHandle:l,RowPtr:l
|
|
local RowBlockPtr:l,RowOffset:w
|
|
local Col1Flag:l,Col2Flag:l
|
|
local MinCol:w,MaxCol:w,MaxRow:w
|
|
error ErrorFlag
|
|
BEGIN
|
|
|
|
stz ErrorFlag
|
|
|
|
stz S_DeltaMove
|
|
SubWord Col2,Col1,S_DeltaMove+2
|
|
|
|
bra startRow
|
|
|
|
; For each row in the range, .... ;
|
|
|
|
nextRow
|
|
inc FRow
|
|
|
|
startRow
|
|
MoveLong S_CurRowBlock,RowBlock
|
|
ora RowBlock
|
|
jeq Exit
|
|
|
|
MoveLong [RowBlock],RowBlockPtr
|
|
MoveWord [RowBlockPtr]:#S_KeyMax,MaxRow
|
|
|
|
CmpWord FRow,[RowBlockPtr]:#S_KeyMin
|
|
blt tooSmall
|
|
|
|
cmp MaxRow
|
|
blt okRow
|
|
|
|
brl Exit
|
|
|
|
tooSmall
|
|
lda [RowBlockPtr],y
|
|
dec a
|
|
sta FRow
|
|
MoveWord #S_KeyArray-4,RowOffset
|
|
bra searchRow
|
|
|
|
okRow
|
|
SubWord a,[RowBlockPtr]:y,a
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,RowOffset
|
|
|
|
searchLoop
|
|
MoveLong [RowBlockPtr]:RowOffset,RowHandle
|
|
ora RowHandle
|
|
bne gotRow
|
|
|
|
searchRow
|
|
inc FRow
|
|
AddWord RowOffset,#4,RowOffset
|
|
|
|
CmpWord FRow,MaxRow
|
|
bge rowQuit
|
|
|
|
CmpWord LRow,FRow
|
|
bge searchLoop
|
|
|
|
rowQuit
|
|
brl Exit
|
|
|
|
gotRow
|
|
MoveLong [RowHandle],RowPtr
|
|
MoveWord [RowPtr]:#S_KeyMax,MaxCol
|
|
MoveWord [RowPtr]:#S_KeyMin,MinCol
|
|
|
|
CmpWord Col1,MinCol
|
|
blt noCol1
|
|
|
|
cmp MaxCol
|
|
bge noCol1
|
|
|
|
CmpWord Col2,MinCol
|
|
blt noCol2
|
|
|
|
cmp MaxCol
|
|
blt okCols
|
|
|
|
; No Col2, but Col1 is in structure ;
|
|
|
|
noCol2
|
|
stz Col2Flag
|
|
bra getCol1
|
|
|
|
noCol1
|
|
CmpWord Col2,MinCol
|
|
blt gotoEnd
|
|
|
|
cmp MaxCol
|
|
blt zeroCol1
|
|
|
|
gotoEnd
|
|
brl cmpRow
|
|
|
|
zeroCol1
|
|
stz Col1Flag
|
|
bra getCol2
|
|
|
|
okCols
|
|
SubWord a,MinCol,a
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,y
|
|
lda [RowPtr],y
|
|
iny
|
|
iny
|
|
ora [RowPtr],y
|
|
sta Col2Flag
|
|
|
|
getCol1
|
|
SubWord Col1,MinCol,a
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,y
|
|
lda [RowPtr],y
|
|
iny
|
|
iny
|
|
ora [RowPtr],y
|
|
sta Col1Flag
|
|
bra chkCols
|
|
|
|
getCol2
|
|
SubWord Col2,MinCol,a
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,y
|
|
lda [RowPtr],y
|
|
iny
|
|
iny
|
|
ora [RowPtr],y
|
|
sta Col2Flag
|
|
|
|
chkCols
|
|
lda Col2Flag
|
|
ora Col1Flag
|
|
beq cmpRow
|
|
|
|
|
|
Call S_SwapCell,in=(Col1:w,FRow:w),err=ErrorFlag
|
|
bcs Exit
|
|
|
|
cmpRow
|
|
CmpWord FRow,LRow
|
|
jlt nextRow
|
|
|
|
Exit
|
|
RETURN
|
|
ENDP
|
|
|
|
;---------------------------------------------------------------------------
|
|
; S_SwapRows (TLCell:l,BRCell:l)
|
|
;
|
|
; This routine traverses the first and last rows of this given region
|
|
; and calls S_SwapCell if either of the two cells in a column is non-empty.
|
|
|
|
S_SwapRows PROC EXPORT
|
|
;Using S_CurrentData
|
|
;Using S_MoveData
|
|
|
|
input FCol:w,Row1:w,LCol:w,Row2:w
|
|
local RowIndex:l,RowPtr:l,ColIndex:l
|
|
local ColOffset:w,MaxCol:w
|
|
local RowBlock:l,RowBlockPtr:l
|
|
local NextCol1:w,NextCol2:w
|
|
error ErrorFlag
|
|
BEGIN
|
|
|
|
stz ErrorFlag
|
|
|
|
lda S_CurRowBlock
|
|
ora S_CurRowBlock+2
|
|
jeq Exit
|
|
|
|
SubWord Row2,Row1,S_DeltaMove
|
|
stz S_DeltaMove+2
|
|
|
|
stz NextCol1
|
|
stz NextCol2
|
|
|
|
bra start
|
|
|
|
; For each cell in the row, .... ;
|
|
|
|
nextCol
|
|
inc FCol
|
|
|
|
start
|
|
CmpWord NextCol1,FCol
|
|
blt getCol1
|
|
|
|
jeq makeCall2
|
|
brl gotNextCol1
|
|
|
|
getCol1
|
|
MoveLong S_CurRowBlock,RowBlock
|
|
MoveLong [RowBlock],RowBlockPtr
|
|
|
|
CmpWord Row1,[RowBlockPtr]:#S_KeyMax
|
|
bge noRow1
|
|
|
|
SubWord a,[RowBlockPtr]:#S_KeyMin,a
|
|
bge row1InRange
|
|
|
|
noRow1
|
|
brl noMoreRow1
|
|
|
|
row1InRange
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,y
|
|
MoveLong [RowBlockPtr]:y,RowIndex
|
|
ora RowIndex
|
|
beq noRow1
|
|
|
|
; Find first used Col Greater/Equal to FCol ;
|
|
|
|
MoveLong [RowIndex],RowPtr
|
|
MoveWord [RowPtr]:#S_KeyMax,MaxCol
|
|
|
|
CmpWord FCol,MaxCol
|
|
bge noRow1
|
|
|
|
sta NextCol1
|
|
|
|
SubWord a,[RowPtr]:#S_KeyMin,a
|
|
bge col1InRange
|
|
|
|
; Try Mincol as NextCol1 ;
|
|
|
|
lda [RowPtr],y
|
|
dec a
|
|
sta nextCol1
|
|
MoveWord #S_KeyArray-4,ColOffset
|
|
bra startCol1Loop
|
|
|
|
col1InRange
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,ColOffset
|
|
|
|
tay
|
|
MoveLong [RowPtr]:y,ColIndex
|
|
ora ColIndex
|
|
beq startCol1Loop
|
|
|
|
brl makeCall2
|
|
|
|
findCol1Loop
|
|
MoveLong [RowPtr]:ColOffset,ColIndex
|
|
ora ColIndex
|
|
bne gotNextCol1
|
|
|
|
startCol1Loop
|
|
inc NextCol1
|
|
AddWord ColOffset,#4,ColOffset
|
|
|
|
CmpWord NextCol1,MaxCol
|
|
bge noMoreRow1
|
|
|
|
CmpWord LCol,NextCol1
|
|
bge findCol1Loop
|
|
|
|
noMoreRow1
|
|
AddWord LCol,#1,NextCol1
|
|
|
|
gotNextCol1
|
|
CmpWord NextCol2,FCol
|
|
jge chkFCol
|
|
|
|
MoveLong S_CurRowBlock,RowBlock
|
|
MoveLong [RowBlock],RowBlockPtr
|
|
|
|
CmpWord Row2,[RowBlockPtr]:#S_KeyMax
|
|
bge noRow2
|
|
|
|
SubWord a,[RowBlockPtr]:#S_KeyMin,a
|
|
bge row2InRange
|
|
|
|
noRow2
|
|
brl noMoreRow2
|
|
|
|
row2InRange
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,y
|
|
MoveLong [RowBlockPtr]:y,RowIndex
|
|
ora RowIndex
|
|
beq noRow2
|
|
|
|
; Find first used Col Greater/Equal to FCol ;
|
|
|
|
MoveLong [RowIndex],RowPtr
|
|
MoveWord [RowPtr]:#S_KeyMax,MaxCol
|
|
|
|
CmpWord FCol,MaxCol
|
|
bge noRow2
|
|
|
|
sta NextCol2
|
|
|
|
SubWord a,[RowPtr]:#S_KeyMin,a
|
|
bge col2InRange
|
|
|
|
; Try MinCol as the next col ;
|
|
|
|
lda [RowPtr],y
|
|
dec a
|
|
sta nextCol2
|
|
MoveWord #S_KeyArray-4,ColOffset
|
|
bra startCol2Loop
|
|
|
|
col2InRange
|
|
asl a
|
|
asl a
|
|
AddWord a,#S_KeyArray,ColOffset
|
|
|
|
tay
|
|
MoveLong [RowPtr]:y,ColIndex
|
|
ora ColIndex
|
|
beq startCol2Loop
|
|
|
|
bra makeCall2
|
|
|
|
findCol2Loop
|
|
MoveLong [RowPtr]:ColOffset,ColIndex
|
|
ora ColIndex
|
|
bne chkFCol
|
|
|
|
startCol2Loop
|
|
inc NextCol2
|
|
AddWord ColOffset,#4,ColOffset
|
|
|
|
CmpWord NextCol2,MaxCol
|
|
bge noMoreRow2
|
|
|
|
CmpWord LCol,NextCol2
|
|
bge findCol2Loop
|
|
|
|
noMoreRow2
|
|
AddWord LCol,#1,NextCol2
|
|
|
|
chkFCol
|
|
CmpWord NextCol1,NextCol2
|
|
bge chkRow2
|
|
|
|
cmp LCol
|
|
beq makeCall1
|
|
blt makeCall1
|
|
bra Exit
|
|
|
|
chkRow2
|
|
CmpWord NextCol2,LCol
|
|
beq makeCall1
|
|
bge Exit
|
|
|
|
makeCall1
|
|
sta FCol
|
|
|
|
makeCall2
|
|
Call S_SwapCell,in=(FCol:w,Row1:w),err=ErrorFlag
|
|
bcs Exit
|
|
|
|
CmpWord FCol,LCol
|
|
bge Exit
|
|
|
|
brl nextCol
|
|
|
|
Exit
|
|
RETURN
|
|
ENDP
|
|
END
|
|
|