Seite 1 von 3

[gelöst] ListIconGadget schneller füllen

Verfasst: 18.01.2008 17:50
von scholly
moin, moin...

Ich fülle das Main-ListIconGadget meiner Video-Verwaltung mit folgender Subroutine:

Code: Alles auswählen

loadDB:
;#############################################                                      ;bearbeitet, Fehler => End
;{
HideGadget(#main_list,1) ; dürfte die Sache etwas beschleunigen
HideGadget(#main_text,0)
HideGadget(#main_prbar,0)
DisableGadget(#main_list,1)
DisableGadget(#main_tree,1) ; damit da nicht drinrumgeklickt werden kann
SendMessage_(#main_list, #WM_SETREDRAW, #False, 0 )
DisableExplicit
BufferSize.l = 2500 * 400
;SendMessage_(#main_list,#LB_INITSTORAGE,0,BufferSize)
z1=ElapsedMilliseconds() 
If DBref

  maintable.SQ3_TABLEMAP
      
  If SQliteGetTable(DBref, "SELECT * FROM maintable order by Titel ASC", maintable) = #False
    MessageRequester("Error beim Laden des maintable von "+DBName, SQliteErrorMsg(DBref))
    End
  Else
    mainDBsatzanzahl = maintable\Rows
    sbarfeld1 = "erfaßte Filme: "+Str(mainDBsatzanzahl)
    StatusBarText(#main_stbar, 1, sbarfeld1)
    SetGadgetAttribute(#main_prbar, #PB_ProgressBar_Maximum, mainDBsatzanzahl)

    If maintable\Cols <> feldercount +1
      MessageRequester("Datenbankfehler", "Die SQLLIte-Datenbank hat "+ Str(maintable\Cols) +" statt "+Str(feldercount+1)+" :(", 0)
    Else
      spaltencounter = 0
      zeilencounter = 0
      If maintable
        While SQLiteNextRow(maintable)
          eintrag = ""
          While SQLiteNextCol(maintable)
            eintrag = eintrag + SQLiteValue(maintable) + Chr(10)
            spaltencounter + 1
          Wend

          AddGadgetItem(#main_list,-1,eintrag)
          sbarfeld2 = "geladene Filme: " + Str(Zeilencounter + 1)
          StatusBarText(#main_stbar, 2, sbarfeld2)
          SetGadgetState(#main_prbar,Zeilencounter)
          ; ohne die Schleife refresht das Window nicht korrekt, siehe meinen Thread im PB-Forum
          While WindowEvent(): Wend
          Zeilencounter + 1
          ;Debug Zeilencounter
        Wend
      EndIf  
    EndIf
      
  EndIf
  SQliteFreeTable(maintable)
Else
  MessageRequester("Error beim Laden von "+DBName, SQliteErrorMsg(DBref))
  End
EndIf

;jede 2. Zeile hellgrau unterlegen ;
;hierfür muß von Gnozal "PureCOLOR" installiert sein
PureCOLOR_SetGadgetColorEx(#main_list, RGB(0,0,0), RGB(255, 255, 255), RGB(222, 222, 222), #PureCOLOR_LV_AlternateColors)

;Spaltenbreiten einrichten
PureLVSORT_SetColumnWidth(#main_list, 0, ugs_PLVS_ColMaxWidth(#main_list, 0)) ;UID          ;
PureLVSORT_SetColumnWidth(#main_list, 1, 200)                                 ;Titel        ; 0.10
PureLVSORT_SetColumnWidth(#main_list, 2, 120)                                 ;Genre        ; 0.10
PureLVSORT_SetColumnWidth(#main_list, 3, ugs_PLVS_ColMaxWidth(#main_list, 3)) ;Jahr         ;
PureLVSORT_SetColumnWidth(#main_list, 4, ugs_PLVS_ColMaxWidth(#main_list, 4)) ;MediumTyp    ;
PureLVSORT_SetColumnWidth(#main_list, 5, ugs_PLVS_ColMaxWidth(#main_list, 5)) ;MediumName   ;
PureLVSORT_SetColumnWidth(#main_list, 6, ugs_PLVS_ColMaxWidth(#main_list, 6)) ;Owner        ;
PureLVSORT_SetColumnWidth(#main_list, 7, ugs_PLVS_ColMaxWidth(#main_list, 7)) ;Quelle       ;
PureLVSORT_SetColumnWidth(#main_list, 8, ugs_PLVS_ColMaxWidth(#main_list, 8)) ;Dauer        ;
PureLVSORT_SetColumnWidth(#main_list, 9, ugs_PLVS_ColMaxWidth(#main_list, 9)) ;Qualität     ;
PureLVSORT_SetColumnWidth(#main_list,10, ugs_PLVS_ColMaxWidth(#main_list,10)) ;Infos        ;
PureLVSORT_SetColumnWidth(#main_list,11, ugs_PLVS_ColMaxWidth(#main_list,11)) ;Path         ;
PureLVSORT_SetColumnWidth(#main_list,12, ugs_PLVS_ColMaxWidth(#main_list,12)) ;Filename     ;
PureLVSORT_SetColumnWidth(#main_list,13, ugs_PLVS_ColMaxWidth(#main_list,13)) ;FileSize     ; 
PureLVSORT_SetColumnWidth(#main_list,14, ugs_PLVS_ColMaxWidth(#main_list,14)) ;Videocodec   ; 
PureLVSORT_SetColumnWidth(#main_list,15, ugs_PLVS_ColMaxWidth(#main_list,15)) ;VideoBitrate ;
PureLVSORT_SetColumnWidth(#main_list,16, ugs_PLVS_ColMaxWidth(#main_list,16)) ;Auflösung    ; 
PureLVSORT_SetColumnWidth(#main_list,17, ugs_PLVS_ColMaxWidth(#main_list,17)) ;fps          ;
PureLVSORT_SetColumnWidth(#main_list,18, ugs_PLVS_ColMaxWidth(#main_list,18)) ;Audiocodec   ; 
PureLVSORT_SetColumnWidth(#main_list,19, ugs_PLVS_ColMaxWidth(#main_list,19)) ;AudioBitrate ;
PureLVSORT_SetColumnWidth(#main_list,20, ugs_PLVS_ColMaxWidth(#main_list,20)) ;AudioKanäle  ;
PureLVSORT_SetColumnWidth(#main_list,21, ugs_PLVS_ColMaxWidth(#main_list,21)) ;SamplingRate ;

z2=ElapsedMilliseconds()
EnableDebugger
  Debug  "Dauer: " +Str(z2 - z1)+" Millisekunden"
DisableDebugger 
HideGadget(#main_list,0)
HideGadget(#main_text,1)
HideGadget(#main_prbar,1)
DisableGadget(#main_tree,0)
DisableGadget(#main_list,0)
SendMessage_(#main_list, #WM_SETREDRAW, #True, 0 )
LIGinhalt="Alles"
;}
Return; loadDB
Das ist allerdings schon bei den jetzt vorhandenen 2500 Filmen mit ca. 20 Sekunden recht langsam, und wenn dann noch meine >20000 Musik-Video-Clips mit rein kommen, seh ich schwarz für die Performance.

Wie bekomme ich das schneller ?

Ich bin bei einer Suche über #lb_initstorage und #wm_setredraw gestolpert, hab aber keine Idee, wie mir das weiterhelfen könnte.

Mag das vielleicht jemand an dem Code oben erklären/einpflegen ?

Meine zusätzliche Idee:
Während der Nutzung der DB kann man in das LIG auch Teilmengen einlesen, z.B. Filterungen nach einzelnen Medien, Genres, o.Ä.

Wäre es da nicht besser, den kompletten Datenbestand in das "erste" LIG einzulesen und dann für diese Teilmengen ein zusätzliches zweites LIG drüberzulegen, welches gelöscht wird, wenn der User wieder eine andere Ansichtsmenge erwartet ?

interessante Vorschläge erwartend... scholly

Verfasst: 18.01.2008 19:41
von FGK
@Scholly

lies deine Datenbank aus und schreib es in ne Linkedlist
und von dort aus in deinen Listview. Sortiern und filtern kannst
du die LinkedList dann und befüllst dein Listiconview wieder.
Geht recht zackig - hab ne Include für das Problem. Hab das für mein Suchprogramm für meine CAM Software gebraucht. Da sind das gleich mal 5000 Progammeinträge aus mehreren Datenbanken und geht
sehr schnell. Unbegrenzte Suchtiefe (d.H. du kannst die gefundene Liste immer wieder weiter filtern und auch immer wieder zurück gehen)


PM wenn du Interesse hast.

Gruß FGK

Verfasst: 18.01.2008 20:22
von scholly
FGK hat geschrieben:Geht recht zackig - hab ne Include für das Problem
Ich hab mittlerweile auch die Befürchtung, daß es an dem SQLite-Zugriff liegt. :(
Allerdings hab ich bisher noch nie mit Linkedlists gearbeitet :?

Muß ich 'ne NDA für das Include unterschreiben ?
Bzw. andersherum:
Darf ich es hinterher mit dem Source meiner Video-Verwaltung veröffentlichen ?

anyway... Danke für Dein Angebot... scholly

Verfasst: 18.01.2008 20:29
von milan1612
Ohne deinen Code jetzt angeschaut zu haben, man kann die Geschwindigkeit
beim Befüllen eines ListIconsGadgets erhöhen, indem man es vor dem Befüllen
versteckt (HideGadget) und danach wieder anzeigt. Das verhindert dass nach jeden
einzelnen Item das ganze Gadget neu gezeichnet werden muss...

Verfasst: 18.01.2008 20:34
von scholly
Deutlicher wie in der 4. Zeile (HideGadget(#main_list,1) ) kann es doch wohl nicht stehen.
Grummel... scholly

Update:
Ich hab da was mit #WM_SETREDRAW versucht, aber irgendwie ergibt die Zeitmessung immer was zwischen 21563 und 23000 Millisekunden.
SendMessage_(#main_list,#LB_INITSTORAGE,0,BufferSize) wird wegen unbekannter Konstante angemeckert :(

Mein vorwitziger Schluß:
Es liegt am Zugriff auf die SQLite-DB :(

Wat Nu ?

Kiffiiiiiiiii........, hilf ;)

Verfasst: 18.01.2008 20:42
von Thomas
Gibt es eigentlich eine Möglichkeit das ListiconGadget sozusagen im Hintergrund zu füllen und dann auf die "sichtbare Ebene" zu bringen?

Verfasst: 18.01.2008 20:52
von milan1612
scholly hat geschrieben:Deutlicher wie in der 4. Zeile (HideGadget(#main_list,1) ) kann es doch wohl nicht stehen.
Grummel... scholly
Schon blöd wenn man die Codes nicht liest...*duck und weg* :oops:

Verfasst: 18.01.2008 20:53
von scholly
Thomas hat geschrieben:Gibt es eigentlich eine Möglichkeit das ListiconGadget sozusagen im Hintergrund zu füllen und dann auf die "sichtbare Ebene" zu bringen?
Ja, genau wie milan1612 es empfohlen hat und ich es schon praktiziere:

Code: Alles auswählen

HideGadget(#main_list,1)
...do some stuff....
HideGadget(#main_list,0)
wer lesen kann, ist klar im Vorteil, stell Dich zu milan in die Ecke :twisted:

Verfasst: 18.01.2008 20:58
von Fluid Byte

Code: Alles auswählen

DisableDebugger

OpenWindow(0,0,0,320,240,"void",#PB_Window_SystemMenu | #PB_Window_ScreenCentered)
CreateGadgetList(WindowID(0))
ListIconGadget(0,0,0,320,240,"Name",250)

StartTime = ElapsedMilliseconds()
For i=1 To 10000
	AddGadgetItem(0,-1,"List-View Item #" + Str(i))
Next
MessageRequester("Zeit",Str(ElapsedMilliseconds() - StartTime) + " MS",64)

ClearGadgetItemList(0)

SendMessage_(GadgetID(0),#WM_SETREDRAW,0,0)

StartTime = ElapsedMilliseconds()
For i=1 To 10000
	AddGadgetItem(0,-1,"List-View Item #" + Str(i))
Next
MessageRequester("Zeit",Str(ElapsedMilliseconds() - StartTime) + " MS",64)

SendMessage_(GadgetID(0),#WM_SETREDRAW,1,0)

While WaitWindowEvent() ! #PB_Event_CloseWindow : Wend

Verfasst: 18.01.2008 21:17
von scholly
Hab ich doch schon längst probiert, siehe mein Posting von 19:34:20.

Jetzt seit ihr zu dritt in der Ecke und könnt Skat spielen :lol: