source: trunk/src/gui/widgets/qlineedit_p.cpp@ 642

Last change on this file since 642 was 561, checked in by Dmitry A. Kuminov, 15 years ago

trunk: Merged in qt 4.6.1 sources.

  • Property svn:eol-style set to native
File size: 8.8 KB
Line 
1/****************************************************************************
2**
3** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
4** All rights reserved.
5** Contact: Nokia Corporation ([email protected])
6**
7** This file is part of the QtGui module of the Qt Toolkit.
8**
9** $QT_BEGIN_LICENSE:LGPL$
10** Commercial Usage
11** Licensees holding valid Qt Commercial licenses may use this file in
12** accordance with the Qt Commercial License Agreement provided with the
13** Software or, alternatively, in accordance with the terms contained in
14** a written agreement between you and Nokia.
15**
16** GNU Lesser General Public License Usage
17** Alternatively, this file may be used under the terms of the GNU Lesser
18** General Public License version 2.1 as published by the Free Software
19** Foundation and appearing in the file LICENSE.LGPL included in the
20** packaging of this file. Please review the following information to
21** ensure the GNU Lesser General Public License version 2.1 requirements
22** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
23**
24** In addition, as a special exception, Nokia gives you certain additional
25** rights. These rights are described in the Nokia Qt LGPL Exception
26** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
27**
28** GNU General Public License Usage
29** Alternatively, this file may be used under the terms of the GNU
30** General Public License version 3.0 as published by the Free Software
31** Foundation and appearing in the file LICENSE.GPL included in the
32** packaging of this file. Please review the following information to
33** ensure the GNU General Public License version 3.0 requirements will be
34** met: http://www.gnu.org/copyleft/gpl.html.
35**
36** If you have questions regarding the use of this file, please contact
37** Nokia at [email protected].
38** $QT_END_LICENSE$
39**
40****************************************************************************/
41
42#include "qlineedit.h"
43#include "qlineedit_p.h"
44
45#ifndef QT_NO_LINEEDIT
46
47#include "qabstractitemview.h"
48#include "qclipboard.h"
49#ifndef QT_NO_ACCESSIBILITY
50#include "qaccessible.h"
51#endif
52#ifndef QT_NO_IM
53#include "qinputcontext.h"
54#include "qlist.h"
55#endif
56
57QT_BEGIN_NAMESPACE
58
59const int QLineEditPrivate::verticalMargin(1);
60const int QLineEditPrivate::horizontalMargin(2);
61
62int QLineEditPrivate::xToPos(int x, QTextLine::CursorPosition betweenOrOn) const
63{
64 QRect cr = adjustedContentsRect();
65 x-= cr.x() - hscroll + horizontalMargin;
66 return control->xToPos(x, betweenOrOn);
67}
68
69QRect QLineEditPrivate::cursorRect() const
70{
71 QRect cr = adjustedContentsRect();
72 int cix = cr.x() - hscroll + horizontalMargin;
73 QRect crect = control->cursorRect();
74 crect.moveTo(crect.topLeft() + QPoint(cix, vscroll));
75 return crect;
76}
77
78#ifndef QT_NO_COMPLETER
79
80void QLineEditPrivate::_q_completionHighlighted(QString newText)
81{
82 Q_Q(QLineEdit);
83 if (control->completer()->completionMode() != QCompleter::InlineCompletion) {
84 q->setText(newText);
85 } else {
86 int c = control->cursor();
87 QString text = control->text();
88 q->setText(text.left(c) + newText.mid(c));
89 control->moveCursor(control->end(), false);
90 control->moveCursor(c, true);
91 }
92}
93
94#endif // QT_NO_COMPLETER
95
96void QLineEditPrivate::_q_handleWindowActivate()
97{
98 Q_Q(QLineEdit);
99 if (!q->hasFocus() && control->hasSelectedText())
100 control->deselect();
101}
102
103void QLineEditPrivate::_q_textEdited(const QString &text)
104{
105 Q_Q(QLineEdit);
106 emit q->textEdited(text);
107#ifndef QT_NO_COMPLETER
108 if (control->completer()
109 && control->completer()->completionMode() != QCompleter::InlineCompletion)
110 control->complete(-1); // update the popup on cut/paste/del
111#endif
112}
113
114void QLineEditPrivate::_q_cursorPositionChanged(int from, int to)
115{
116 Q_Q(QLineEdit);
117 q->update();
118 emit q->cursorPositionChanged(from, to);
119}
120
121#ifdef QT_KEYPAD_NAVIGATION
122void QLineEditPrivate::_q_editFocusChange(bool e)
123{
124 Q_Q(QLineEdit);
125 q->setEditFocus(e);
126}
127#endif
128
129void QLineEditPrivate::_q_selectionChanged()
130{
131 Q_Q(QLineEdit);
132 if (control->preeditAreaText().isEmpty()) {
133 QStyleOptionFrameV2 opt;
134 q->initStyleOption(&opt);
135 bool showCursor = control->hasSelectedText() ?
136 q->style()->styleHint(QStyle::SH_BlinkCursorWhenTextSelected, &opt, q):
137 true;
138 setCursorVisible(showCursor);
139 }
140
141 emit q->selectionChanged();
142}
143
144void QLineEditPrivate::init(const QString& txt)
145{
146 Q_Q(QLineEdit);
147 control = new QLineControl(txt);
148 control->setFont(q->font());
149 QObject::connect(control, SIGNAL(textChanged(QString)),
150 q, SIGNAL(textChanged(QString)));
151 QObject::connect(control, SIGNAL(textEdited(QString)),
152 q, SLOT(_q_textEdited(QString)));
153 QObject::connect(control, SIGNAL(cursorPositionChanged(int,int)),
154 q, SLOT(_q_cursorPositionChanged(int,int)));
155 QObject::connect(control, SIGNAL(selectionChanged()),
156 q, SLOT(_q_selectionChanged()));
157 QObject::connect(control, SIGNAL(accepted()),
158 q, SIGNAL(returnPressed()));
159 QObject::connect(control, SIGNAL(editingFinished()),
160 q, SIGNAL(editingFinished()));
161#ifdef QT_KEYPAD_NAVIGATION
162 QObject::connect(control, SIGNAL(editFocusChange(bool)),
163 q, SLOT(_q_editFocusChange(bool)));
164#endif
165 QObject::connect(control, SIGNAL(cursorPositionChanged(int,int)),
166 q, SLOT(updateMicroFocus()));
167
168 QObject::connect(control, SIGNAL(textChanged(const QString &)),
169 q, SLOT(updateMicroFocus()));
170
171 // for now, going completely overboard with updates.
172 QObject::connect(control, SIGNAL(selectionChanged()),
173 q, SLOT(update()));
174
175 QObject::connect(control, SIGNAL(displayTextChanged(QString)),
176 q, SLOT(update()));
177
178 QObject::connect(control, SIGNAL(updateNeeded(QRect)),
179 q, SLOT(update()));
180
181 QStyleOptionFrameV2 opt;
182 q->initStyleOption(&opt);
183 control->setPasswordCharacter(q->style()->styleHint(QStyle::SH_LineEdit_PasswordCharacter, &opt, q));
184#ifndef QT_NO_CURSOR
185 q->setCursor(Qt::IBeamCursor);
186#endif
187 q->setFocusPolicy(Qt::StrongFocus);
188 q->setAttribute(Qt::WA_InputMethodEnabled);
189 // Specifies that this widget can use more, but is able to survive on
190 // less, horizontal space; and is fixed vertically.
191 q->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed, QSizePolicy::LineEdit));
192 q->setBackgroundRole(QPalette::Base);
193 q->setAttribute(Qt::WA_KeyCompression);
194 q->setMouseTracking(true);
195 q->setAcceptDrops(true);
196
197 q->setAttribute(Qt::WA_MacShowFocusRect);
198}
199
200QRect QLineEditPrivate::adjustedContentsRect() const
201{
202 Q_Q(const QLineEdit);
203 QStyleOptionFrameV2 opt;
204 q->initStyleOption(&opt);
205 QRect r = q->style()->subElementRect(QStyle::SE_LineEditContents, &opt, q);
206 r.setX(r.x() + leftTextMargin);
207 r.setY(r.y() + topTextMargin);
208 r.setRight(r.right() - rightTextMargin);
209 r.setBottom(r.bottom() - bottomTextMargin);
210 return r;
211}
212
213void QLineEditPrivate::setCursorVisible(bool visible)
214{
215 Q_Q(QLineEdit);
216 if ((bool)cursorVisible == visible)
217 return;
218 cursorVisible = visible;
219 QRect r = cursorRect();
220 if (control->inputMask().isEmpty())
221 q->update(r);
222 else
223 q->update();
224}
225
226void QLineEditPrivate::updatePasswordEchoEditing(bool editing)
227{
228 Q_Q(QLineEdit);
229 control->updatePasswordEchoEditing(editing);
230 q->setAttribute(Qt::WA_InputMethodEnabled, shouldEnableInputMethod());
231}
232
233/*!
234 This function is not intended as polymorphic usage. Just a shared code
235 fragment that calls QInputContext::mouseHandler for this
236 class.
237*/
238bool QLineEditPrivate::sendMouseEventToInputContext( QMouseEvent *e )
239{
240#if !defined QT_NO_IM
241 Q_Q(QLineEdit);
242 if ( control->composeMode() ) {
243 int tmp_cursor = xToPos(e->pos().x());
244 int mousePos = tmp_cursor - control->cursor();
245 if ( mousePos < 0 || mousePos > control->preeditAreaText().length() ) {
246 mousePos = -1;
247 // don't send move events outside the preedit area
248 if ( e->type() == QEvent::MouseMove )
249 return true;
250 }
251
252 QInputContext *qic = q->inputContext();
253 if ( qic )
254 // may be causing reset() in some input methods
255 qic->mouseHandler(mousePos, e);
256 if (!control->preeditAreaText().isEmpty())
257 return true;
258 }
259#else
260 Q_UNUSED(e);
261#endif
262
263 return false;
264}
265
266#ifndef QT_NO_DRAGANDDROP
267void QLineEditPrivate::drag()
268{
269 Q_Q(QLineEdit);
270 dndTimer.stop();
271 QMimeData *data = new QMimeData;
272 data->setText(control->selectedText());
273 QDrag *drag = new QDrag(q);
274 drag->setMimeData(data);
275 Qt::DropAction action = drag->start();
276 if (action == Qt::MoveAction && !control->isReadOnly() && drag->target() != q)
277 control->removeSelection();
278}
279
280#endif // QT_NO_DRAGANDDROP
281
282QT_END_NAMESPACE
283
284#endif
Note: See TracBrowser for help on using the repository browser.