2011-10-04 17 views
6

Cuando un widget padre se define con:No hay entrada de teclado si QLineEdit en la ventana emergente sin marco

setWindowFlags(Qt::FramelessWindowHint | Qt::Popup); 

Cualquier widget de cuadro de edición colocado en la parte superior de la misma, no recibirán la entrada del teclado. El mouse funcionará, haga clic derecho, el menú contextual, pegar funcionará, pero no la entrada directa del teclado. ¿Alguna idea de por qué y cómo se puede solucionar?

+0

No puedo reproducir su problema, en Windows 7, con Qt Creator 2.3.1 y Qt 4.7.4. Todo lo que tengo es QMainWindow, con un widget que es un QLineEdit, y llamé a setWindowFlags (línea) en QMainWindow. Funcionó bien, pude escribir texto, no hay problema. –

+0

La ventana del contenedor en mi aplicación no es la ventana principal. Tal vez eso hace la diferencia. Una persona en otro foro sugirió que tenía un problema similar que se resolvió cuando activó la ventana del contenedor. Lo probaré y publicaré mis resultados aquí. – JasonGenX

+0

Tengo el mismo problema. Tengo una clase simple derivada de QDialog y en el constructor configuré Qt :: WindowFlags en Qt :: Popup. Parece que esto es un error de Qt. Windows 7, Qt 4.8 => funciona bien. Windows 7, Qt 5.4 => no funciona. Windows 8, Qt 5.4 => no funciona. Sin embargo, si configuro un punto de interrupción y pause la ejecución por un tiempo (en showEvent (QShowEvent *)) y luego continúo la ejecución, puedo usar ese QLineEdit de la manera deseada. –

Respuesta

0
#include "StdAfx.h" 
#include "qfindedit.h" 

QFindEdit::QFindEdit(QWidget *parent) 
: QLineEdit(parent) 
, m_bEditFocus(true) 
{ 
    setPlaceholderText("please input find word"); 

m_stringListmodel = new QStringListModel(this); 
m_pFindWnd = new QListView(this); 
//m_pFindWnd->setWindowFlags(Qt::Popup); 
m_pFindWnd->setEditTriggers(QAbstractItemView::NoEditTriggers); 
m_pFindWnd->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); 
m_pFindWnd->setSelectionBehavior(QAbstractItemView::SelectRows); 
m_pFindWnd->setSelectionMode(QAbstractItemView::SingleSelection); 
m_pFindWnd->setParent(0, Qt::Popup); 
m_pFindWnd->setFocusPolicy(Qt::NoFocus); 
m_pFindWnd->setFocusProxy(this); 

connect(this, SIGNAL(textEdited(const QString&)), this, SLOT(textEditedSlot(const QString&))); 
QObject::connect(m_pFindWnd, SIGNAL(clicked(QModelIndex)), 
    this, SLOT(clickedSlot(QModelIndex))); 
QObject::connect(this, SIGNAL(activated(QModelIndex)), 
    m_pFindWnd, SLOT(hide())); 

this->installEventFilter(this); 
m_pFindWnd->installEventFilter(this); 

} 

QFindEdit::~QFindEdit() 
{ 
    delete m_pFindWnd; 
} 

QStringList& QFindEdit::stringList() 
{ 
    return m_stringList; 
} 

void QFindEdit::showFindWnd(const QString& text) 
{ 
QStringList sl; 
foreach(QString word, m_stringList) { 
    if (word.contains(text)) { 
     sl << word; 
    } 
} 

if (sl.size() == 0) 
{ 
    hideFineWnd(); 
    return; 
} 
m_stringListmodel->setStringList(sl); 
m_pFindWnd->setModel(m_stringListmodel); 

m_pFindWnd->resize(rect().width(), 200); 
QPoint pTopleft = mapToGlobal(rect().bottomLeft()); 
m_pFindWnd->move(pTopleft.x(), pTopleft.y()); 
m_pFindWnd->show(); 
} 

void QFindEdit::textEditedSlot(const QString& text) 
{ 
    QString strText = text.trimmed(); 
    if (!strText.isEmpty()) 
    { 
     showFindWnd(strText); 
    } 
    else 
    { 
     hideFineWnd(); 
    } 
} 

void QFindEdit::clickedSlot(QModelIndex modelIndex) 
{ 
    setText(m_pFindWnd->model()->data(modelIndex).toString()); 
    hideFineWnd(); 
} 

void QFindEdit::hideFineWnd() 
{ 
    m_pFindWnd->hide(); 
} 

bool QFindEdit::eventFilter(QObject *o, QEvent *e) 
{ 
if (m_bEditFocus && (o == this) && e->type() == QEvent::FocusOut) 
{ 
    if (m_pFindWnd && m_pFindWnd->isVisible()) 
     return true; 
} 

if (o != m_pFindWnd) 
    return __super::eventFilter(o, e); 

switch (e->type()) 
{ 
case QEvent::KeyPress: 
    { 
     QKeyEvent *ke = static_cast<QKeyEvent *>(e); 
     QModelIndex curIndex = m_pFindWnd->currentIndex(); 
     QModelIndexList selList = m_pFindWnd->selectionModel()->selectedIndexes(); 
     const int key = ke->key(); 

     if ((key == Qt::Key_Up || key == Qt::Key_Down) && selList.isEmpty() && curIndex.isValid()) 
     { 
      m_pFindWnd->setCurrentIndex(curIndex); 
      return true; 
     } 

     switch (key) 
     { 
     case Qt::Key_End: 
     case Qt::Key_Home: 
      if (ke->modifiers() & Qt::ControlModifier) 
       return false; 
      break; 

     case Qt::Key_Up: 
      if (!curIndex.isValid()) 
      { 
       int rowCount = m_pFindWnd->model()->rowCount(); 
       QModelIndex lastIndex = m_pFindWnd->model()->index(rowCount - 1, m_pFindWnd->modelColumn()); 
       m_pFindWnd->setCurrentIndex(lastIndex); 
       return true; 
      } 
      else if (curIndex.row() == 0) 
      { 
       return true; 
      } 
      return false; 

     case Qt::Key_Down: 
      if (!curIndex.isValid()) 
      { 
       QModelIndex firstIndex = m_pFindWnd->model()->index(0, m_pFindWnd->modelColumn()); 
       m_pFindWnd->setCurrentIndex(firstIndex); 
       return true; 
      } 
      else if (curIndex.row() == m_pFindWnd->model()->rowCount() - 1) 
      { 
       return true; 
      } 
      return false; 
     } 

     m_bEditFocus = false; 
     this->event(ke); 
     m_bEditFocus = true; 
     if (e->isAccepted() || !m_pFindWnd->isVisible()) { 
      if (!this->hasFocus()) 
       hideFineWnd(); 
      if (e->isAccepted()) 
       return true; 
     } 

     switch (key) 
     { 
     case Qt::Key_Return: 
     case Qt::Key_Enter: 
     case Qt::Key_Tab: 
      hideFineWnd(); 
      if (curIndex.isValid()) 
      { 
       QString text = m_pFindWnd->currentIndex().data().toString(); 
       setText(text); 
      } 
      break; 

     case Qt::Key_F4: 
      if (ke->modifiers() & Qt::AltModifier) 
       hideFineWnd(); 
      break; 

     case Qt::Key_Backtab: 
     case Qt::Key_Escape: 
      hideFineWnd(); 
      break; 

     default: 
      break; 
     } 

     return true; 
    } 
case QEvent::MouseButtonPress: 
    if (!m_pFindWnd->underMouse()) 
    { 
     hideFineWnd(); 
     return true; 
    } 
    return false; 
case QEvent::InputMethod: 
case QEvent::ShortcutOverride: 
    QApplication::sendEvent(this, e); 
    break; 

default: 
    return false; 
} 
return false; 
} 
1

como he mencionado anteriormente en un comentario que tenía el mismo problema, pero ahora se fija con el siguiente código:

// virtual override 
void MyDialog::showEvent(QShowEvent* aShowEvent) 
{ 
    QDialog::showEvent(aShowEvent); 
    activateWindow(); 
} 

Después añadí la llamada de función activateWindow() que podría utilizar QLineEdit en mi cuadro de diálogo emergente.

Uso Visual Studio 2013 y Qt 5.4.1 en Windows 8.1.

+0

Gracias !!! También funciona para widget en una acción de menú. Sin esto, no podría activar el método de entrada. – tamlok

Cuestiones relacionadas