ListIconGadget sort on column
Posted: Mon Jan 29, 2007 8:31 am
This code sorts listicongadget columns. It handles strings, but the compare procedure
rsets() them before comparing, so (integer) numbers will be sorted correctly too.
It also moves the item state with the items, such as checkbox status and if the item is
currently selected or not.
20091115, updated a bit
rsets() them before comparing, so (integer) numbers will be sorted correctly too.
It also moves the item state with the items, such as checkbox status and if the item is
currently selected or not.
Code: Select all
;sort order,0 ascending/listicongadget cols
global order, li = 1 ;listicon id
global cols = 4, max = 6
procedure swapItems(id, item1, item2, cols)
for col = 0 to cols - 1
;swap item text
text.s = getGadgetItemText(id, item1, col)
setGadgetItemText(id, item1, getGadgetItemText(id, item2, col), col)
setGadgetItemText(id, item2, text, col)
;swap item data
dta = getGadgetItemData(id, item1)
setGadgetItemData(id, item1, getGadgetItemData(id, item2))
setGadgetItemData(id, item2, dta)
;swap item fg colors
fg = getGadgetItemColor(id, item1, #PB_GADGET_FRONTCOLOR, col)
setGadgetItemColor(id, item1, #PB_GADGET_FRONTCOLOR, getGadgetItemColor(id, item2, #PB_GADGET_FRONTCOLOR, col), col)
setGadgetItemColor(id, item2, #PB_GADGET_FRONTCOLOR, fg, col)
;swap item bg colors
bg = getGadgetItemColor(id, item1, #PB_GADGET_BACKCOLOR, col)
setGadgetItemColor(id, item1, #PB_GADGET_BACKCOLOR, getGadgetItemColor(id, item2, #PB_GADGET_BACKCOLOR, col), col)
setGadgetItemColor(id, item2, #PB_GADGET_BACKCOLOR, bg, col)
next col
;swap checkbox/selected item states
state = getGadgetItemState(id, item1)
setGadgetItemState(id, item1, getGadgetItemState(id, item2))
setGadgetItemState(id, item2, state)
endProcedure
procedure compare(s1.s, s2.s)
;rsets to compare numbers correctly
sc1.s = ucase(rset(s1, max))
sc2.s = ucase(rset(s2, max))
if sc1 < sc2
procedureReturn -1
elseIf sc1 > sc2
procedureReturn 1
endIf
procedureReturn 0
endProcedure
procedure qSortItems(id, order, col, cols, left, right)
;quicksort kernel, herbert schildt
;comparisons: n * log10(n), swaps: n/6 * log10(n)
lft = left: rgt = right
txt.s = getGadgetItemText(id, (lft + rgt) / 2, col)
while lft <=rgt
if order
;is descending
while compare(getGadgetItemText(id, lft, col), txt) > 0 and lft < right
lft + 1
wend
while compare(getGadgetItemText(id, rgt, col), txt) < 0 and lft < right
rgt - 1
wend
else
while compare(getGadgetItemText(id, lft, col), txt) < 0 and lft < right
lft + 1
wend
while compare(getGadgetItemText(id, rgt, col), txt) > 0 and lft < right
rgt - 1
wend
endIf
if lft <= rgt
swapItems(id, lft, rgt, cols)
lft + 1: rgt - 1
endIf
wend
if left < rgt
qSortItems(id, order, col, cols, left, rgt)
endIf
if lft < right
qSortItems(id, order, col, cols, lft, right)
endIf
endProcedure
procedure quickSortItems(id, order, col, cols)
;quicksort wrapper
qSortItems(id, order, col, cols, 0, countGadgetItems(id) - 1)
procedureReturn order ! 1
endProcedure
procedure windowCallback(win, msg, wParam, lParam)
;code handles column header clicks and initiates sorts
if msg = #WM_NOTIFY
*phdr.HD_NOTIFY = lParam
if *phdr\hdr\code = #HDN_ITEMCLICK
order = quickSortItems(li, order, *phdr\iItem, cols)
endIf
endIf
procedureReturn #PB_PROCESSPUREBASICEVENTS
endProcedure
;-driver
openWindow(0, 0, 0, 620, 500, "Adding items..", 13107201)
setWindowCallback(@windowCallback())
;create the listicongadget
li = 1
listIconGadget(li, 0, 0, 620, 500, "Column 0", 150, 1073807369)
addGadgetColumn(li, 1, "Column 1", 150)
addGadgetColumn(li, 2, "Column 2", 150)
addGadgetColumn(li, 3, "Column 3", 150)
;fill it with random data
for item = 0 to 999
i.s = ""
for n = 0 to max
i + chr('A' + random(25))
next n
i + #LF$
for n = 0 to max
i + chr('A' + random(25))
next n
i + #LF$
for n = 0 to max
i + chr('A' + random(25))
next n
i + #LF$
for n = 0 to max
i.s + chr('A' + random(25))
next n
addGadgetItem(li, -1, i)
;random item colors
col = random(cols - 1)
bgc = rgb(random(192) + 48, random(192) + 48, random(192) + 48)
setGadgetItemColor(li, item, #PB_GADGET_FRONTCOLOR, #WHITE, col)
setGadgetItemColor(li, item, #PB_GADGET_BACKCOLOR, bgc, col)
windowEvent()
next item
;initial sort, ascending on col 0
setWindowTitle(0, "Sorting...")
order = 0
order = quickSortItems(li, order, 0, cols)
i = str(item) + " items, click header to sort in ascending/descending order"
setWindowTitle(0, i)
;loop while the callback handles sorting
repeat
until waitWindowEvent() = #PB_EVENT_CLOSEWINDOW
end