Delphi-PRAXiS
Seite 1 von 6  1 23     Letzte »    

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Delphi Stringlänge parsen (https://www.delphipraxis.net/193739-stringlaenge-parsen.html)

EWeiss 4. Sep 2017 12:35


Stringlänge parsen
 
Wie kann ich am schnellsten die länge von Strings parsen
so das ich dann den längsten verwenden kann um mein Window in der Weite dementsprechend anzupassen.

Ja ich weis Length(string) aber ich suche eine schnelle Methode ;)

Habe mein Grund Menu soweit fertig.. und ich benötige die Berechnung um die Sub Menus (weite) auf den längsten String hin anzupassen.
Anbei ein shot.!
1 ganzer Tag nur für das Grundmenu. LOL

gruss

Neutral General 4. Sep 2017 12:36

AW: Stringlänge parsen
 
Length(string)

Bernhard Geyer 4. Sep 2017 12:37

AW: Stringlänge parsen
 
Du suchst doch nicht die Länge des Strings sondern den benötigten Platz zur Darstellung des Strings auf einem Canvas, oder?
Dazu nimmt man DrawText mit dem Paramter DT_CALCRECT

himitsu 4. Sep 2017 12:43

AW: Stringlänge parsen
 
http://www.delphipraxis.net/11102-la...es-string.html
Wenn Canvas oder HDC schon vorhanden sind, dann natürlich das direkt verwenden.

Zitat:

Zitat von EWeiss (Beitrag 1380255)
Ja ich weis Length(string) aber ich suche eine schnelle Methode ;)

Schneller als das geht es aber nicht.
Man kann noch über Pointer schneller sein, wenn der String nie leer ist, indem man diese Prüfung überpringt. :stupid:

EWeiss 4. Sep 2017 12:44

AW: Stringlänge parsen
 
Zitat:

Zitat von Bernhard Geyer (Beitrag 1380257)
Du suchst doch nicht die Länge des Strings sondern den benötigten Platz zur Darstellung des Strings auf einem Canvas, oder?
Dazu nimmt man DrawText mit dem Paramter DT_CALCRECT

Ich möchte die gesamte länge eines String parsen\vergleichen bsp. von 30 Einträgen und den längsten davon
verwenden um mein Sub Menu auf die weite auszurichten.

DT_CALCRECT hilft mir nicht ist aber auch nicht wichtig da ich es mit meiner Funktion
GDIP_GetTextBound nachher in Pixeln exakt ermittle wenn ich den längsten string habe.

Zitat:

Length(string)
Und ich sagte ja schon das ich weis das es mit Length geht aber ich muss etwas schnelles haben vielleicht in einem rutsch ;)

gruss

Glados 4. Sep 2017 12:44

AW: Stringlänge parsen
 
Zitat:

Ich möchte die gesamte länge eines String parsen\vergleichen bsp. von 30 Einträgen und den längsten davon
verwenden um mein Sub Menu auf die weite auszurichten.
QuickSort und dann das hier vielleicht?

Delphi-Quellcode:
function getTextWidth(aForm: TForm; const aString: string): Integer;
begin
 if aString <> '' then
  Result := aForm.Canvas.TextWidth(aString)
 else
  Result := 0;
end;

jaenicke 4. Sep 2017 12:47

AW: Stringlänge parsen
 
Zitat:

Zitat von EWeiss (Beitrag 1380259)
DT_CALCRECT hilft mir nicht ist aber auch nicht wichtig da ich es mit meiner Funktion
GDIP_GetTextBound nachher in Pixeln exakt ermittle wenn ich den längsten string habe.

Der nach Zeichen längste String ist aber nicht unbedingt der, der den meisten Platz beim Zeichnen benötigt...
Verschiedene Zeichen sind ja unterschiedlich breit.

Zitat:

Zitat von EWeiss (Beitrag 1380259)
Zitat:

Length(string)
Und ich sagte ja schon das ich weis das es mit Length geht aber ich muss etwas schnelles haben vielleicht in einem rutsch ;)

Bei Delphi-Strings geht es kaum schneller als mit Length, denn das liest ja nur die Längenangabe aus, die vor dem String steht.

// EDIT:
Die beim Zeichnen längste Zeile wirst du wohl am einfachsten bekommen, wenn du alle Strings in mehreren Zeilen nimmst und gesammelt an die Funktion zur Größenermittlung gibst. Das ist vermutlich nicht besonders schnell, aber zuverlässig und schneller als jeden Text einzeln anzufragen.

EWeiss 4. Sep 2017 12:49

AW: Stringlänge parsen
 
Zitat:

Zitat von Glados (Beitrag 1380260)
Zitat:

Ich möchte die gesamte länge eines String parsen\vergleichen bsp. von 30 Einträgen und den längsten davon
verwenden um mein Sub Menu auf die weite auszurichten.
QuickSort und dann das hier vielleicht?

Delphi-Quellcode:
function getTextWidth(aForm: TForm; const aString: string): Integer;
begin
 if aString <> '' then
  Result := aForm.Canvas.TextWidth(aString)
 else
  Result := 0;
end;

Sorry irgendwie werde ich nicht verstanden.. das nutzt mir nichts und ist auch nicht wichtig.
Da ich den Text mit GDI+ zeichne und ein mix mit der Winapi ist da nicht das wahre.

Denke werde es dann wohl doch mit Length(string) in einer schleife machen müssen.

Zitat:

Verschiedene Zeichen sind ja unterschiedlich breit.
ja das ist klar ;)

Ich mache es hier mit aber erst dann wenn ich den längsten String ermittelt habe. (einmalig..)

Delphi-Quellcode:
function GetTextBound(UseText: WideString; UseFont: WideString; UseSize: single; var bW: integer;
  var bH: integer; UseStrFormat: integer): GPSTATUS; stdcall;
var
  Graphics: cardinal;
  Fam: GpFontFamily;
  TempFont: GpFont;
  DC: HDC;
begin

  result := GenericError;
  strFormat := nil;
  Fam := nil;
  // Create matching font
  try
    GdipCheck(GdipCreateFontFamilyFromName(UseFont, nil, Fam));
    if Assigned(Fam) then
    begin
      GdipCheck(GdipCreateFont(Fam, UseSize, 0, 2, TempFont));
      if Assigned(TempFont) then
      begin
        DC := GetDC(GetDesktopWindow);

        GdipCheck(GdipCreateStringFormat(0, 0, strFormat));
        GdipCheck(GdipCreateFromHDC(DC, Graphics));

        GdipCheck(GdipMeasureString(Graphics, PWideChar(UseText), length(UseText), TempFont,
            @layoutRect, strFormat, @boundingBox, nil, nil));

        if Assigned(strFormat) then
          GdipCheck(GdipDeleteStringFormat(strFormat));

        bW := round(boundingBox.Width - boundingBox.X);
        bH := round(boundingBox.Height - boundingBox.Y);

        if UseStrFormat <> 0 then
          Swap(bW, bH);

        ReleaseDc(GetDesktopWindow, DC);
      end;
    end;
  finally
    if Graphics <> 0 then
      GdipCheck(GdipDeleteGraphics(Graphics));
    if Assigned(TempFont) then
      GdipCheck(GdipDeleteFont(TempFont)); // Lösche das Font Object
    if Assigned(Fam) then
      GdipCheck(GdipDeleteFontFamily(Fam)); // Lösche das Font Family Object
  end;

end;
gruss

Neutral General 4. Sep 2017 12:52

AW: Stringlänge parsen
 
Zitat:

Zitat von EWeiss (Beitrag 1380259)
Ich möchte die gesamte länge eines String parsen\vergleichen bsp. von 30 Einträgen und den längsten davon
verwenden um mein Sub Menu auf die weite auszurichten.

Und ich sagte ja schon das ich weis das es mit Length geht aber ich muss etwas schnelles haben vielleicht in einem rutsch ;)

Length(string) in Assembler (Delphi 7):
Delphi-Quellcode:
  test eax, eax
  jz +$03
  mov eax, [eax-$04]
  ret
Schneller wirds nicht.
Außerdem in extremen Fällen können kürzere Strings (Anzahl der Zeichen) länger (in Pixeln) sein als andere längere Strings (Anzahl der Zeichen) (<-- Verwirrender Satz aber ich hoffe du weißt was ich meine :mrgreen: )

z.B.

WWWW (Length = 4)
iiiiiiiiiiii (Length = 12)

Glados 4. Sep 2017 12:53

AW: Stringlänge parsen
 
Zitat:

Sorry irgendwie werde ich nicht verstanden..
Doch wirst du.

Zitat:

Denke werde es dann wohl doch mit Length(string) in einer schleife machen müssen.
Auf Systemen mit einer anderen DPI als deine eigene wirst du Probleme bekommen.

Meine oben genannte Funktion gibt die Länge eines Strings in Pixeln zurück.
Mit QuickSort kannst du dann sehr einfach den längsten String raussuchen.


Alle Zeitangaben in WEZ +1. Es ist jetzt 01:47 Uhr.
Seite 1 von 6  1 23     Letzte »    

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