I draw the QLineEdit by paintEnvent(), but the cursor can't move one by one throught the left or right button. I press the right button, it moves to the end, and the beginning when I pressing the left button. But the cursor's real point is right, beacause I can backspace the character by pressing Backspace.

It seems the show problem.

Thanks a lot.
Qt Code:
  1. #include <QtGui>
  2. #include <QtCore>
  3.  
  4. class Edit : public QLineEdit{
  5.  
  6. public:
  7.  
  8. Edit(const QString &t, QWidget *pParent = 0) : QLineEdit(t, pParent){
  9. font = QFont("Sans");
  10. font.setPixelSize(26);
  11. setFixedSize(640, 220);
  12. setTextMargins(4, 0, 4, 0);
  13. }
  14.  
  15. protected:
  16. void paintEvent(QPaintEvent *pEvent){
  17. QPainter painter(this);
  18. QRect r = rect();
  19. //frame
  20. int x2 = r.width() - 1, y2 = r.height() - 1;
  21. painter.fillRect(r, QBrush(QColor(79, 79, 104, 255)));
  22. painter.setPen(QPen(QColor(64, 64, 64, 255), 1));
  23. painter.drawLine(0, 0, x2, 0);
  24.  
  25. painter.drawLine(0, 0, 0, y2);
  26. painter.setPen(QPen(QColor(92, 92, 92, 255), 1));
  27. painter.drawLine(x2, y2, 1, y2);
  28. painter.drawLine(x2, y2, x2, 1);
  29. painter.setPen(QPen(QColor(19, 19, 19, 255), 1));
  30. painter.drawRect(QRect(1, 1, r.width() - 3, r.height() - 3));
  31.  
  32. //set clipping
  33. int lm, tm, rm, bm;
  34. getTextMargins(&lm, &tm, &rm, &bm);
  35. r.setX(r.x() + lm);
  36. r.setY(r.y() + tm);
  37. r.setRight(r.right() - rm);
  38. r.setBottom(r.bottom() - bm);
  39. painter.setClipRect(r);
  40.  
  41. painter.setPen(QPen(QColor(196, 196, 196, 255), 1));
  42. QFontMetrics fm(font);
  43. QTextLayout tl(text(), font, this);
  44. tl.beginLayout();
  45. QTextLine line = tl.createLine();
  46. if( !line.isValid() ){ return; }
  47.  
  48. tl.endLayout();
  49. QRect lineRect(r.x(), r.y() + (r.height() - qRound(line.height()) + 1) / 2,
  50. r.width() - 1, qRound(line.height()));
  51. //painter.drawRect(lineRect);
  52. int ccc = cursorPosition();
  53. int cix = qRound(line.cursorToX(&ccc));
  54. int minLB = qMax(0, -fm.minLeftBearing());
  55. int minRB = qMax(0, -fm.minRightBearing());
  56. int widthUsed = qRound(line.naturalTextWidth()) + 1 + minRB;
  57. int hscroll;
  58.  
  59. if( (minLB + widthUsed) <= lineRect.width() ){
  60. //hscroll = 0;
  61. Qt::Alignment va = QStyle::visualAlignment(layoutDirection(), QFlag(this->alignment()));
  62. va &= ~(Qt::AlignAbsolute|Qt::AlignVertical_Mask);
  63. switch (va) {
  64. case Qt::AlignRight:
  65. hscroll = widthUsed - lineRect.width() + 1;
  66. break;
  67. case Qt::AlignHCenter:
  68. hscroll = (widthUsed - lineRect.width()) / 2;
  69. break;
  70. default:
  71. // Left
  72. hscroll = 0;
  73. break;
  74. }
  75. hscroll -= minLB;
  76. }else if( cix - hscroll >= lineRect.width() ){
  77. hscroll = cix - lineRect.width() + 1;
  78. }else if( cix - hscroll < 0 && hscroll < widthUsed ){
  79. hscroll = cix;
  80. }else if( widthUsed - hscroll < lineRect.width() ){
  81. hscroll = widthUsed - lineRect.width() + 1;
  82. }
  83. QPoint topLeft = lineRect.topLeft() - QPoint(hscroll, line.ascent() - fm.ascent());
  84.  
  85. QVector<QTextLayout::FormatRange> selections;
  86.  
  87. QTextLayout::FormatRange o;
  88. if( hasSelectedText() ){
  89.  
  90. o.start = selectionStart();
  91. o.length = selectedText().length();
  92. o.format.setBackground(QColor(88, 101, 134, 255));
  93. o.format.setForeground(QColor(196, 196, 196, 255));
  94. selections.append(o);
  95. }
  96.  
  97. tl.draw(&painter, topLeft, selections);
  98. painter.setPen(QPen(QColor(200, 0, 0, 255), 2));
  99. //painter.drawLine(cix, lineRect.y(), cix, lineRect.y() + lineRect.height());
  100. tl.drawCursor(&painter, topLeft, cix, 2);
  101.  
  102. }
  103.  
  104. private:
  105. QFont font;
  106. };
  107.  
  108. int main(int argc, char *argv[]){
  109. QApplication a(argc, argv);
  110.  
  111. QWidget *w = new QWidget;
  112.  
  113. w->setPalette(QPalette(QColor(77, 77, 77, 255)));
  114. QHBoxLayout *l = new QHBoxLayout(w);
  115. Edit *e1 = new Edit(QString("test1"));
  116. e1->setAlignment(Qt::AlignCenter);
  117.  
  118. QLineEdit *e2 = new QLineEdit(QString("test2"));
  119.  
  120. e2->setFixedSize(640, 220);
  121.  
  122. e2->setAlignment(Qt::AlignCenter);
  123.  
  124. l->addWidget(e1);
  125. l->addWidget(e2);
  126. w->show();
  127.  
  128. return a.exec();
  129. }
To copy to clipboard, switch view to plain text mode