Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2206132
  • 博文数量: 866
  • 博客积分: 14125
  • 博客等级: 上将
  • 技术积分: 10638
  • 用 户 组: 普通用户
  • 注册时间: 2007-07-27 16:53
个人简介

https://github.com/landuochong

文章分类

全部博文(866)

文章存档

2019年(3)

2018年(1)

2017年(10)

2015年(3)

2014年(8)

2013年(3)

2012年(70)

2011年(103)

2010年(360)

2009年(283)

2008年(22)

分类: C/C++

2010-07-23 16:17:45

在Qt的example里有个例子叫做codeeditor:
http://doc.qt.nokia.com/4.6/widgets-codeeditor.html
codeeditor screenshot

该例子演示QPlainTextEdit类的用法, 其中有个有用的功能是在编辑器的左边margin的位置显示行号。 查看它的代码就会发现, 它用的时候遍历QTextBlock的方法确定行号, 这样就带来一个问题, 也就是实际上显示的所谓“行号”其实是段落号。 这在大多数情况下没什么问题, 但遇到某些bt用户非要狂按“Shift+Enter”问题就来了。

Qt的文档中可以找到对“Shift+Enter”和“Enter”行为的准确定义:

InsertParagraphSeparator Enter Enter Enter Enter (none)
InsertLineSeparator Shift+Enter Meta+Enter Shift+Enter Shift+Enter (none)

所以按下“Shift+Enter”和按下“Enter”结果是不同的。 这种不同从外表看不出来, 但和codeeditor中实现显示行号的代码结合一下, 就明白无误了。

解决的方法比较曲折(当然可能有更好的方法等着大家去探索), 除了要遍历每个block, 还要用QTextBlock的方法去遍历每个QTextLine。 另外一个让人头疼的地方是还要计算出每行的y坐标, 好在合适的地方画上这个行号。 多说无益, 代码说话:


QTextBlock block = document()->begin();
int top = 0;
QTextCursor cursor(block);
cursor.setPosition(0);//move to the beginning of the document
qWarning() << document()->lineCount() << document()->blockCount();
int linenum = 0;
while(linenum < document()->lineCount())
{
for( int i = 0 ; i < block.lineCount(); i ++)
{
QTextLine line = block.layout()->lineAt(i);
//qWarning() << line.rect().toRect() << "x,y:" << line.x() << line.y();
int dx = blockBoundingGeometry(block).x();
int dy = blockBoundingGeometry(block).y();
//qWarning()<< "block offset:" << dx << dy << "content offset:" << contentOffset();
top = line.rect().translated(contentOffset()).translated( dx,dy).y();
painter.setPen(Qt::black);
painter.drawText(0, top, lineNumberArea->width(), fontMetrics().height(),
Qt::AlignRight, QString::number( linenum +1));
linenum ++;
}
block = block.next();
if(!block.isValid())
{
break;
}
}

阅读(2628) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~
评论热议
请登录后评论。

登录 注册