It's not very difficult to do it "right" (meaning: "as you want it to work").
I'll agree here, ones interpretation how something should work is often tainted by how one would want it to work or what one wants it to do at the moment.
I have to disagree as to the quotes working as described. From the page you linked:
"Portions of text that are between single or double quotes will be considered single words and the text will not be broken between the quotes."
Nothing in the example text is BETWEEN quotes. Apostrophes are much more common in textual data than Quoted text.
That said, I've done as you suggested and written my own wrapping routine with some added features:
(1). Wraps at the space immediately BEFORE the max length
(2). Width is based on Canvas Width instead of character count making it work better with modern fonts.
(3). Totally ignores quotes.
(4). Allows the caller to chose if the want STRICT breaks at the specified length or if it's OK for the data to overrun the field with should no break opportunity be found.
It's doesn't handle the '-' break, but for my use I actually didn't want that. I may add that back in later to make a more general routine but for now...
It's not extensively tested yet, but I've run some data thru it and it seems to work as I need it to.
function RPTWrapText(
const nValue: string; // The Text to be folded
const nMax: longint; // Max Length of field IN PIXELS not Characters
const nDelim: char; // Delimeter to replace space character
C: TCanvas; // Canvas to base the length on.
const Strict: boolean = false // Enable Strict Breaks
): string;
var
LastSpace: longint;
NewValue: string;
TestValue: string;
StartPos: longint;
IDX: longint;
L: longint;
CH: char;
begin
NewValue := nValue;
StartPos := 1;
LastSpace := 0;
IDX := 1;
while IDX <= length( NewValue ) do
begin
CH := NewValue[ IDX ];
if ( CH in [' ', #9 ] ) then LastSpace := IDX;
if ( CH = nDelim ) then begin
// A forced break from the original data
StartPos := IDX + 1;
LastSpace := 0;
end else begin
// Calculate the length of the string from the last break (StartPos)
// to the Current position (IDX).
TestValue := copy( newValue, StartPos, (IDX-StartPos)+1 );
L := C.TextWidth( TestValue );
//showmessage(inttostr(IDX)+':'+inttostr(L)+':'+inttostr(nMax)+':'+TestValue);
if ( L > nMax ) then begin
if ( LastSpace > 0 ) then begin
NewValue[ LastSpace ] := nDelim; // Set the Break Character
StartPos := LastSpace + 1; // Set Start Position to the Next Character
LastSpace := 0;
end else begin
if Strict then begin
NewValue := copy( NewValue, 1, IDX-1 )
+ nDelim
+ copy( NewValue, IDX, length(NewValue) );
StartPos := IDX+1;
end; { Strict }
end;
end;
end;
inc( IDX );
end; { while }
exit(NewValue);
end;