![]() |
AW: Textlänge abschneiden
Zitat:
Man muss sich nur mal diese Aussage anschauen. Zitat:
Somit ist gewährleistet das egal welche Zeichen es sind diese immer eine fixe breite von 7 haben (560 div 80) Wenn ich nun davon ausgehe das bei einer fixen Weite von 560
Delphi-Quellcode:
SongName := PAnsiChar(AnsiString(Ansimidstr(string(SongName),1, 80) + '...'));
80 Zeichen reinpassen dann wird mein SongTitel genau egal welche Zeichen dieser enthält (gleiche Breite pro Char) 100% und immer kurz vor meiner Zeitanzeige gezeichnet. Jetzt ändere mal den Font wo die Zeichen nicht mehr gleich sind. Tja nun dann ist diese Aussage nicht mehr rechtens Zitat:
Das würde dann unweigerlich Fehlschlagen
Delphi-Quellcode:
SongName := PAnsiChar(AnsiString(Ansimidstr(string(SongName),1, 80) + '...'));
gruss |
AW: Textlänge abschneiden
Eventuell noch ein anderer Ansatz:
Delphi-Quellcode:
begin
fMaxLen := 635; // Die maximal zulässige Breite der Zeichenfolge in der Anzeige. fMaxStrLen := tsTextGetWidthA(SongName); // Aktuelle Breite ermitteln. if fMaxStrLen >= fMaxLen then begin // Ist die größer als die Maximalbreite? SongName := SongName + '...'; // dann ... anhängen fMaxStrLen := tsTextGetWidthA(SongName); // und die neue Breite ermitteln. repeat // Solange wiederholen Delete(SongName,Length(SongName) - 4,1); // viertletztes Zeichen entfernen fMaxStrLen := tsTextGetWidthA(SongName); // Neue Breite ermitteln. until fMaxStrLen <= fMaxLen; // Bis die Breite <= der Maximalbreite ist. end; end; |
AW: Textlänge abschneiden
Dank dir werde es mal testen.
gruss |
AW: Textlänge abschneiden
Mit Lossys Hilfe funktioniert es jetzt wie soll.
Nochmals Danke für seine Hilfe.
Delphi-Quellcode:
Mit dem ganzen VCL Kram war das nicht zu bewerkstelligen.
// Only change if Title different
if (CurrentTitle <> OldTmpTitle) then begin // Adding all the characters that are present in the text tsFontAddChars(@SongNameTmp[0]); //Get max length of String fMaxStrLen := tsTextGetWidthA(SongNameTmp); if fMaxStrLen >= 635 then begin // Since we want to '...' have in any case at the end we need these characters to only. CharLen := tsFontGetCharParameteri('.', TS_CHAR_ADVANCE) * 3; // Parse width of Glyph for I := 0 to High(Char) do begin // read and add width of the current character Char[I] := WideChar(SongNameTmp[I]); CharLength := tsFontGetCharParameteri(Char[I], TS_CHAR_ADVANCE); CharLen := CharLen + CharLength; // If the width is greater than the available space, then loop exit if CharLen >= 635 then break; end; // Here is through the loop and our new text is from 1 to i-1. SongName := PAnsiChar(Ansistring(Ansimidstr(string(SongNameTmp), 1, i-1) + '...')); end else SongName := BassSoInfo.SongTitle; CurrentTitle := OldTmpTitle; end; Ist abhängig von der Bibliothek mit der Gezeichnet wird. Zitat:
Und das Handling mit den Fonts in VCL ist eine andere Geschichte als in OpenGL. Aber gut funktioniert ja jetzt auf diese weise. Meine Fehler resultierten daraus weil ich zu wenig Kenntnis über die zu Übergebenden Parameter hatte.
Delphi-Quellcode:
// Display Song Name
SongNameTmp := BassSoInfo.SongTitle; OldTitle := string(BassSoInfo.Songfile); if assigned(SongNameTmp) then begin SetLength(Char, length(SongNameTmp)); // Only change if Title different if (OldTitle <> CurrentTitle) then begin //Get max length of String fMaxStrLen := tsTextGetWidthA(SongNameTmp); if fMaxStrLen >= 635 then begin // Parse width of Glyph for I := 0 to High(Char) do begin Char[I] := WideChar(SongNameTmp[I]); CharLength := tsFontGetCharParameteri(Char[I], TS_CHAR_GLYPHRECT_RIGHT); CharLen := CharLen + CharLength; end; // CharLen = length of all combine Glyph if CharLen >= ((CharLen - fMaxStrLen) + 635) then begin SongName := PAnsiChar(Ansistring(Ansimidstr(string(SongNameTmp), 1, 58) + '...')); end; end else SongName := BassSoInfo.SongTitle; CurrentTitle := OldTitle; end; Ich hatte vergessen die Chars den Aktiven Font zuzuweisen
Delphi-Quellcode:
tsFontAddChars(@SongNameTmp[0]);
die länge des Suffix (...) nicht addiert basierend auf der verwendeten Bibliothek.
Delphi-Quellcode:
CharLen := tsFontGetCharParameteri('.', TS_CHAR_ADVANCE) * 3;
Und hier den falschen Parameter übergeben mit der Annahme das ich die weite über TS_CHAR_GLYPHRECT_RIGHT in Erfahrung bringe. Schien mir am logischsten.
Delphi-Quellcode:
CharLength := tsFontGetCharParameteri(Char[I], TS_CHAR_ADVANCE);
was mich hier gerissen hat weiß ich letztendlich auch nicht.. war wohl mehr oder weniger eine Verzweiflungstat.
Delphi-Quellcode:
if CharLen >= ((CharLen - fMaxStrLen) + 635) then
Ansonsten war die Herangehensweise gar nicht mal so verkehrt. Vielleicht können andere Leute die mit der TextSuite Arbeiten damit jetzt was anfangen. Die müssen sich dann nicht mehr damit rumschlagen. Letztendlich noch ein Satz. Wäre die exakte Anzahl von Chars bekannt, bei nicht Monotonen Fonts die in den Bereich von 5 > 635 hineinpassen, könnte man sich den ganzen Kram sparen denn dafür würde eine einzige Zeile reichen.
Delphi-Quellcode:
SongName := PAnsiChar(Ansistring(Ansimidstr(string(SongNameTmp), 1, 'Meine bekannte Anzahl von Chars') + '...'));
gruss |
AW: Textlänge abschneiden
Tja, diese Lösung von Lossy ist von der Funktionsweise exakt die gleiche, die ich auch gepostet habe. Aber anyway, es gab ja jetzt eine CopyPaste Lösung ohne Mitdenken - und die gab es von mir halt nicht :stupid:
|
AW: Textlänge abschneiden
Zitat:
Weil du einfach nicht verstehst das der Font in OpenGL von der Breite her niemals der gleiche wie unter VCL ist. Hier wird auch nicht in VCL sondern unter OpenGL mit einer extra dafür ausgerichteten Bibliothek gezeichnet. ![]() der Code von mir vorher schon geschrieben war. Du hättest sofort auf Anhieb erkannt das ich TS_CHAR_ADVANCE anstelle von TS_CHAR_GLYPHRECT_RIGHT hätte verwenden müssen? Von der Logik her war dies für mich der richtige weg TS_CHAR_GLYPHRECT_RIGHT. Und nochmal vergiss es einfach zu versuchen OpenGL mit VCL zu kombinieren. Abhängig natürlich von der aktuellen Sachlage. Zu deiner Unterstellung: Vergleich einfach mal die Zeiten oder gehe mal auf DelphiGL dann siehst du wer was hier Copy/Paste hat. Ich zumindest nicht. Mein Post: 17. Jun 2016, 21:00 Hier und bei ![]() Lossys Post: 18. Jun 2016, 18:07 Das Problem war nur ich habe mich von dir breit schlagen lassen es mit der VCL Methode zu versuchen. :stupid: Zitat:
Ich habe versucht dir das mehrmals Klar zu machen... Aber nein manche Leute wollen ihren Standpunkt mit allen Mitteln durchsetzen. Kein Ahnung warum du jetzt sickig bist. Dein Stolz verletzt? Versteh mich nicht falsch ich habe mich über deine Hilfe gefreut, aber jetzt mit solchen Unterstellungen zu kommen, nur weil ich deinen nicht funktionierenden Code nicht verwende, ist unterste Schublade. Und ja deinen ganzen code kann ich mit einer einzelnen Zeile ersetzen und komme auf das gleiche Ergebnis.
Delphi-Quellcode:
SongName := PAnsiChar(Ansistring(Ansimidstr(string(SongNameTmp), 1, 'Meine bekannte Anzahl von Chars') + '...'));
Zitat:
Denn die TextSuite tut nichts anderes. EDIT: Ich habe sogar noch mit meinem Code selber verglichen was ich vergessen bzw. wo meine Fehler waren. Ich verstehe deine Probleme einfach nicht. Habe jetzt allen hier bewiesen das deine Unterstellung Nonsens ist, somit ist es gut für mich. Jetzt können wir wieder Freunde sein. gruss |
AW: Textlänge abschneiden
Da mein Code einfach nur Integer Werte zusammenzählt und anhand der Aufsummierungen derselbigen Entscheidungen trifft, müssen wohl die von OpenGL zurückgelieferten Integer Werte total anders von der Bedeutung sein. So OpenGL-Spezial-Integer Werte.
Schon krass dieses OpenGL - sowas kann ich natürlich nicht berücksichtigen. Vielleicht kann mir das ja der Kryptochef erklären, werde den mal anschreiben :mrgreen: |
AW: Textlänge abschneiden
Zitat:
Dazu habe ich alles gesagt. Diese Antwort... nun ja! Ich verkneife mir darauf zu Antworten. Äußere dich doch mal zu den von dir gemachten Unterstellungen das hätte mir mehr gebracht. gruss |
AW: Textlänge abschneiden
Also ich verstehe das nicht.
Lösung Sir Rufo:
Delphi-Quellcode:
snip...
type
TCharMeasureWidthDelegate = function( const C: Char ): Integer of object; function ShortenText( const Text: string; const MaxLength: Integer; const CharMeasurement: TCharMeasureWidthDelegate; const ShortenSuffix: string = '...' ): string; So jetzt eine function
Delphi-Quellcode:
und das ganze Aufrufen mit
function TmyView.CalculateCharWith( const C: Char ): Integer;
begin Result := tsFontGetCharParameteri(C, TS_CHAR_ADVANCE); end;
Delphi-Quellcode:
fertig.
lDrawText := ShortenText( Edit1.Text, PaintBox1.ClientWidth, myView.CalculateCharWith );
Also in meinen Augen ist die Lösung von Sir Rufo super weil komplett unabhängig und vor allem auch testbar. |
AW: Textlänge abschneiden
Zitat:
Schön und gut für VCL das war's dann. Zudem warum soll ich 5 Seiten Quelltext verwenden wenn ich das gleiche mit 10 Zeilen erledigt habe. Außerdem versuche ich zu vermeiden mein Programm mit Copy/Paste zu verwirklichen und nein brauche auch keine fertigen Lösungen zumal diese hier eh nicht funktioniert. gruss |
Alle Zeitangaben in WEZ +1. Es ist jetzt 05:52 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz