Delphi 如何获取TMemo中显示的行数?
我需要获取TMemo中显示的行数(这包括由于WordWrap设置为true而被包装的行)。我需要这个来自动调整Tmemo的高度以适应它的内容 行。计数当然不关心包装行,所以我不能使用它。奇怪的是,TextPosToPos也不关心换行,所以我也不能使用它Delphi 如何获取TMemo中显示的行数?,delphi,firemonkey,Delphi,Firemonkey,我需要获取TMemo中显示的行数(这包括由于WordWrap设置为true而被包装的行)。我需要这个来自动调整Tmemo的高度以适应它的内容 行。计数当然不关心包装行,所以我不能使用它。奇怪的是,TextPosToPos也不关心换行,所以我也不能使用它 我在firemonkey和delphi Berlin的指导下学习了内容边界。我的原始(和过时的)答案在修订版中仍然可见 为什么需要显示行数来调整TMemo的高度?这会将TMemo的大小调整为其内容: Memo1.Height := Memo1.C
我在firemonkey和delphi Berlin的指导下学习了
内容边界
。我的原始(和过时的)答案在修订版中仍然可见
为什么需要显示行数来调整TMemo
的高度?这会将TMemo
的大小调整为其内容:
Memo1.Height := Memo1.ContentBounds.Height + 5; // Small const to allow for rendering margins
它还考虑了单词换行。在我了解
内容边界之后进行编辑。我的原始(和过时的)答案在修订版中仍然可见
为什么需要显示行数来调整TMemo
的高度?这会将TMemo
的大小调整为其内容:
Memo1.Height := Memo1.ContentBounds.Height + 5; // Small const to allow for rendering margins
它还考虑了单词包装。我不知道为什么使用ContentBounds“不是很理想”。我是这样做的:
uses
FMX.TextLayout, FMX.Graphics;
function MeasureTextHeight(const AFont: TFont; const AText: string): Single;
var
LLayout: TTextLayout;
begin
LLayout := TTextLayoutManager.DefaultTextLayout.Create;
try
LLayout.BeginUpdate;
try
LLayout.WordWrap := False;
LLayout.Font.Assign(AFont);
LLayout.Text := AText;
finally
LLayout.EndUpdate;
end;
Result := LLayout.TextHeight;
finally
LLayout.Free;
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
var
LTextHeight: Single;
LLines: Integer;
begin
LTextHeight := MeasureTextHeight(Memo1.TextSettings.Font, Memo1.Text);
LLines := Round(Memo1.ContentBounds.Height / LTextHeight);
end;
我不知道为什么使用ContentBounds“不是很理想”。我是这样做的:
uses
FMX.TextLayout, FMX.Graphics;
function MeasureTextHeight(const AFont: TFont; const AText: string): Single;
var
LLayout: TTextLayout;
begin
LLayout := TTextLayoutManager.DefaultTextLayout.Create;
try
LLayout.BeginUpdate;
try
LLayout.WordWrap := False;
LLayout.Font.Assign(AFont);
LLayout.Text := AText;
finally
LLayout.EndUpdate;
end;
Result := LLayout.TextHeight;
finally
LLayout.Free;
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
var
LTextHeight: Single;
LLines: Integer;
begin
LTextHeight := MeasureTextHeight(Memo1.TextSettings.Font, Memo1.Text);
LLines := Round(Memo1.ContentBounds.Height / LTextHeight);
end;
这是我用来计算firemonkey下TMemo(样式化)的行数的粗略方法:
type
_TStyledMemoProtectedAccess = class(TStyledMemo);
procedure TALStyledMemo.OnApplyStyleLookupImpl(sender: Tobject);
Var I, j, k, l: integer;
begin
// TALStyledMemo
// TStyledMemo
// TLayout
// TActiveStyleObject
// TLayout
// TScrollBar
// TScrollBar
// TLayout
// TSmallScrollBar
// TSmallScrollBar
// TScrollContent
for I := 0 to controls.Count - 1 do begin
if (controls[i] is TStyledMemo) then begin // << TStyledMemo
fStyledMemo := TStyledMemo(controls[i]);
end;
end;
end;
function TALStyledMemo.getLineHeight: Single;
begin
if fStyledMemo <> nil then result := _TStyledMemoProtectedAccess(fStyledMemo).GetLineHeight
else result := 0;
end;
function TALStyledMemo.getLineCount: integer;
var aLineHeight: Single;
begin
aLineHeight := getLineHeight;
if compareValue(aLineHeight, 0, Tepsilon.Position) > 0 then result := round(ContentBounds.Height / aLineHeight)
else result := 0;
end;
类型
_TStyledMemoProtectedAccess=类(TStyledMemo);
过程TALStyledMemo.OnApplyStyleLookupImpl(发送方:ToObject);
变量I,j,k,l:整数;
开始
//TALStyledMemo
//TStyledMemo
//特拉约特
//战术目标
//特拉约特
//滚动条
//滚动条
//特拉约特
//滚动条
//滚动条
//滚动内容
对于I:=0的控件。计数-1不开始
如果(controls[i]是TStyledMemo),则开始//0,然后结果:=round(ContentBounds.Height/alinehight)
其他结果:=0;
结束;
这是我用来计算firemonkey下TMemo(样式化)的行数的粗略方法:
type
_TStyledMemoProtectedAccess = class(TStyledMemo);
procedure TALStyledMemo.OnApplyStyleLookupImpl(sender: Tobject);
Var I, j, k, l: integer;
begin
// TALStyledMemo
// TStyledMemo
// TLayout
// TActiveStyleObject
// TLayout
// TScrollBar
// TScrollBar
// TLayout
// TSmallScrollBar
// TSmallScrollBar
// TScrollContent
for I := 0 to controls.Count - 1 do begin
if (controls[i] is TStyledMemo) then begin // << TStyledMemo
fStyledMemo := TStyledMemo(controls[i]);
end;
end;
end;
function TALStyledMemo.getLineHeight: Single;
begin
if fStyledMemo <> nil then result := _TStyledMemoProtectedAccess(fStyledMemo).GetLineHeight
else result := 0;
end;
function TALStyledMemo.getLineCount: integer;
var aLineHeight: Single;
begin
aLineHeight := getLineHeight;
if compareValue(aLineHeight, 0, Tepsilon.Position) > 0 then result := round(ContentBounds.Height / aLineHeight)
else result := 0;
end;
类型
_TStyledMemoProtectedAccess=类(TStyledMemo);
过程TALStyledMemo.OnApplyStyleLookupImpl(发送方:ToObject);
变量I,j,k,l:整数;
开始
//TALStyledMemo
//TStyledMemo
//特拉约特
//战术目标
//特拉约特
//滚动条
//滚动条
//特拉约特
//滚动条
//滚动条
//滚动内容
对于I:=0的控件。计数-1不开始
如果(controls[i]是TStyledMemo),则开始//0,然后结果:=round(ContentBounds.Height/alinehight)
其他结果:=0;
结束;
谢谢tom,我实际上做了contentbounds/text.size,但不是真正的idealthanks tom,是的,使用contentbounds很容易,但是我想将备忘录的高度限制为4行,这就是为什么我需要行数Hanks tom,我实际上做了contentbounds/text.size,但不是真正的idealthanks tom,是的,使用contentBounds很容易,但是我想将备忘录的高度限制为4行,这就是为什么我需要行数换行怎么办?这没有考虑宽度限制。事实上,您的代码显式地将其关闭,这与OP所寻找的正好相反。@Jerrydoge我没有在备忘录中关闭WordWrap;再次检查代码。当我说“我就是这样做的”时,我的意思是我已经在使用它了。如果它不起作用,我就不会把它发出去了汉克斯·戴夫!是的,就是这样的工作。不过我用了一种稍有不同的方式(我后来发布了我的答案)。那么换行符呢?这没有考虑宽度限制。事实上,您的代码显式地将其关闭,这与OP所寻找的正好相反。@Jerrydoge我没有在备忘录中关闭WordWrap;再次检查代码。当我说“我就是这样做的”时,我的意思是我已经在使用它了。如果它不起作用,我就不会把它发出去了汉克斯·戴夫!是的,就是这样的工作。然而,我用了一种稍微不同的方式(稍后我发布了我的答案)。