在自定义绘制控件时,经常遇到文本超过绘制区域的情况,容易想到的办法显示部分文字和换行,一下介绍如何实现换行
方式一
//drawText(const QRectF &rectangle, int flags, const QString &text, QRectF *boundingRect = nullptr)
/*
The flags argument is a bitwise OR of the following flags:
Qt::AlignLeft
Qt::AlignRight
Qt::AlignHCenter
Qt::AlignJustify
Qt::AlignTop
Qt::AlignBottom
Qt::AlignVCenter
Qt::AlignCenter
Qt::TextDontClip
Qt::TextSingleLine
Qt::TextExpandTabs
Qt::TextShowMnemonic
Qt::TextWordWrap
Qt::TextIncludeTrailingSpaces
*/
//适合固定区域文字自动换行模式
//eg:
QRectF rect(0,0,300,300);
QString text = "this is text";
painter->drawText(rect, Qt::TextWordWrap, text);
方式二
/*
void drawText(const QRectF &rectangle, const QString &text, const QTextOption &option = QTextOption())
这种方式可以指定文本换行的位置,比如任意位置换行,或者单词末尾换行
QTextOption::NoWrap
QTextOption::WordWrap
QTextOption::ManualWrap
QTextOption::WrapAnywhere
QTextOption::WrapAtWordBoundaryOrAnywhere
*/
//eg:
QRectF rect(0,0,300,300);
QString text = "this is text";
QTextOption option;
option.setWrapMode(QTextOption::WrapAnywhere)
painter->drawText(rect, Qt::TextWordWrap, option);
方式三
QPainter painter(this);
QTextOption option;
option.setWrapMode(QTextOption::WrapAtWordBoundaryOrAnywhere); // 设置自动换行模式
QString text = "This is a long text that needs to be broken into multiple lines.";
QTextDocument doc;
doc.setDefaultTextOption(option);
doc.setPlainText(text);
QTextLayout layout(doc);
layout.beginLayout();
QTextLine line = layout.createLine();
int y = 0;
while (line.isValid())
{
line.setLineWidth(200);
line.setPosition(QPointF(0, y));
y += line.height();
line = layout.createLine();
}
layout.endLayout();
layout.draw(&painter, QPointF(0, 0));
扩展
根据给定的文字长度,以固定的宽度区域,自适应高度绘制文本
//先计算出文本的宽度,和指定宽度比较,小于自定宽度直接绘制,否则需要计算换几行,指定高度
QPainter painter(this);
QFontMetrics metrics(painter.font());
QString text = "This is a long text that needs to be broken into multiple lines";
int textwidth = metrics.horizontalAdvance(text); //获取文本的宽度
int rectWidth = 300; //指定绘制宽度
int height = metrics.height(); //获取字体高度
if(textwidth <= rectwidth)
{//能够容纳,直接绘制
QRect rect(0,0,rectwidth,height);
painter.drawText(rect,Qt::AlignCenter,text);
}
else
{
//计算需要显示几行
int index = 0;
QString temp = text;
while(true)
{
auto temp1 = metrics.elidedText(temp,Qt::ElideRight,rectwidth); //截断文字
if(temp1.isEmpty()) break;
index++;
temp1 = temp1.remove("…"); //删除截断符号
temp = temp.remove(temp1);
}
int _height = index*height;
QRect rect(0,0,rectwidth,_height);
QTextOption option;
option.setWrapMode(QTextOption::WrapAnywhere)
painter->drawText(rect, Qt::TextWordWrap, option);
}