Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   FMX Listview Einträge Richtig Laden (https://www.delphipraxis.net/201616-fmx-listview-eintraege-richtig-laden.html)

jacky213 7. Aug 2019 17:07

FMX Listview Einträge Richtig Laden
 
Ich habe eine Android App mit einer Listview erstellt.

Sobald man die App startet werden alle werte mittels Memo geladen und dann in die Listview mittels folgender Procedure in die Listview eingefügt.

Delphi-Quellcode:
function ReAddBlanks (St:String) : String;
begin
result := StringReplace(St, '§', ' ',[rfReplaceAll, rfIgnoreCase]);
end;

Procedure TfrmMain.AddAllItems(Value : String);
var
VList : TStringlist;
Item : TListViewItem;
AK : Boolean;
begin
Value := StringReplace(Value, ' ', '§',[rfReplaceAll, rfIgnoreCase]);
VList := TStringlist.Create;
VList.Delimiter := '#';
VList.DelimitedText := Value;
Item := LVEinkauf.items.Add;
Item.Objects.FindObjectT<TListItemText>('Anzahl').Text  := ReAddBlanks(VList[0]);
Item.Objects.FindObjectT<TListItemText>('Trenner').Text := 'x';
Item.Objects.FindObjectT<TListItemText>('Laden').Text   := ReAddBlanks(VList[1]);
Item.Objects.FindObjectT<TListItemText>('Produkt').Text := ReAddBlanks(VList[2]);
Item.Objects.FindObjectT<TListItemImage>('LineImage').Bitmap := Image1.Bitmap;

if VList[3]='T' then AK := True else AK := False;
Item.Objects.FindObjectT<TListItemImage>('LineImage').Visible := AK;

LVEinkauf.itemIndex := -1;
end;
Wenn ich diese Procedure zur Laufzeit ausführe funktioniert alles wie es soll.

Zum Beispiel:
Delphi-Quellcode:
AddAllItems('1#Laden1#Nägel 25x2,5#F');
Aber wenn die App startet und die Daten lädt, wird bleibt der TListItemImage Visible stand immer auf False und die daten werden einfach nur eingefügt. Es kommt keine Fehlermeldung.

Kann mir jeman sagen was da schief läuft?

Rollo62 7. Aug 2019 17:22

AW: FMX Listview Einträge Richtig Laden
 
Delphi-Quellcode:
Item.Objects.FindObjectT<TListItemImage>('LineImage').Visible := AK;
...
LObj := Item.Objects.FindObjectT<TListItemImage>('LineImage');
if Assigned( LObj )
    LObj.Visible := AK;
Nenn mich paranoid, aber ich würde solche Abfragen immer in einer Variablen speichern und gegenchecken, denn jeder kleine Typo könnte mit nil zurückkommen.

Dafür baue ich mir in solchen Fällen oft ein paar einfache Wrapper die das Ganze mit TryFindObject absichern
Delphi-Quellcode:
  if TryFindObject<TListItemImage>(Item, 'LineImage', LObj ) then
      LObj.Visible := AK;

jacky213 7. Aug 2019 17:38

AW: FMX Listview Einträge Richtig Laden
 
Also er kann mit TryFindObject nichts anfangen. Was muss dafür in die Uses?

Rollo62 7. Aug 2019 19:10

AW: FMX Listview Einträge Richtig Laden
 
Das war ein genereller Vorschlag um den Zugriff auf die Elemente abzusichern.
Solche Wrapper kannst Du selber schreiben, am Besten in einer eigenen Unit, oder als class helper.
Hier mal schnell hingekritzelt (ungetestet), solange das über deinem Code steht sollte der Zugriff wie unten OK sein.

Das Problem in der App kann aber auch von einer ganz anderer Stelle kommen, mir ging es
nur darum diese möglichen Zugriffsfehler auf nil schonmal ausschliessen.

Delphi-Quellcode:
function TryFindObject(const AItem : TListViewItem;
                       const AName : String;
                       var  AObj : TListItemText ) : Boolean; overload;
begin
    if Assigned( AItem ) then
    begin
        AObj := AItem.Objects.FindObjectT<TListItemText>( AName );
        if Assigned( AObj ) then
            Result := True
        else
            Result := False;  
    end
    else
    begin
        AObj := nil;
        Result := False;
    end;
end;

function TryFindObject(const AItem : TListViewItem;
                       const AName : String;
                       var  AObj : TListItemImage ) : Boolean; overload;
begin
    if Assigned( AItem ) then
    begin
        AObj := AItem.Objects.FindObjectT<TListItemImage>( AName );
        if Assigned( AObj ) then
            Result := True
        else
            Result := False;  
    end
    else
    begin
        AObj := nil;
        Result := False;
    end;
end;

´
//...

procedure InDeinerAnwendungsfunktion;
var
    LItem   : TListViewItem;
    LObjText : TListItemText;
    LObjImg : TListItemImage;

begin
    LItem := LVEinkauf.items.Add;

    if TryFindObject( LItem, 'Anzahl', LObjText) then
      LObjText.Text := ReAddBlanks(VList[0]); // <-- hier kannst Du sicher sein das LObj existiert

    //...

    if TryFindObject( LItem, 'LineImage'', LObjImg) then
      LObjImg.Bitmap := Image1.Bitmap; // <-- hier kannst Du sicher sein das LObj existiert
end;
So ein Zugriff über eine Textsuche ist nicht unbedingt ideal, ich würde versuchen das anders zu lösen.
Geht aber wolh in diesem Fall, wenn die Elemente auch wirklich da sind und gefunden werden können.
Am Besten einfach mal debuggen und sehen was zurückgeliefert wird, bevor man darauf zugreift.

jacky213 7. Aug 2019 19:21

AW: FMX Listview Einträge Richtig Laden
 
Habe nochmal jeden Schritt geprüft. Alle Werte werden richtig gelesen und gespeichert. Er setzt die Image visible einfach nicht auf true, keine Ahnung warum

jacky213 7. Aug 2019 20:12

AW: FMX Listview Einträge Richtig Laden
 
ich konnte mein Problem lösen, indem ich einen Timer auf die Form gesetzt habe welcher nach 1000 ms die gespeicherte Datei lädt. Erst dann wurden die Einträge richtig geladen und auch das Image Object wurde richtig dargestellt.

Incocnito 8. Aug 2019 07:08

AW: FMX Listview Einträge Richtig Laden
 
Hi,

mal so eine Idee hierzu: Wurde deine Methode im FormCreate (gibt es in FMX doch auch, oder?) aufgerufen?
Vielleicht lief das, bevor die Res-Daten (etwas vergleichbares gibt es bei FMX doch sicher auch)
verarbeitet wurden. Oder die Komponente war halt (weil im Create) noch in einer Art "Create-Status",
so dass Änderngen an den Einstellungen ignoriert wurden. ... Ich konnte schon einige Probleme lösen,
indem ich Methoden/Aufrufe/... von FormCreate nach FormShow verschoben habe.
Jeder ist sicherlich schonmal darauf reingefallen im Create "SetFocus" zu schreiben,
oder bin ich der einzige Depp? :wink:

MfG Incocnito

Rollo62 8. Aug 2019 08:30

AW: FMX Listview Einträge Richtig Laden
 
Zitat:

Zitat von Incocnito (Beitrag 1440123)
Hi,
... von FormCreate nach FormShow verschoben habe.

Ja richtig, das sollte man vor Allem bei Mobile-Plattformen, weil sonst das Pohone die App einfach rauswirft, wenn es mal länger daueret.
Und auch Styles könnten noch nicht verfügbar sein.

jacky213 8. Aug 2019 21:29

AW: FMX Listview Einträge Richtig Laden
 
Das dachte ich mir auch und habe es auch mit dem OnShow versucht, doch leider brachte mich das auch nicht weiter. Hab den Timer nun auf 255 ms gesetzt und es funktioniert einwandfrei.

Luckie 8. Aug 2019 21:45

AW: FMX Listview Einträge Richtig Laden
 
OnActivate?


Alle Zeitangaben in WEZ +1. Es ist jetzt 20:49 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz