Как использовать валидатор с QTableWidgetItem?

Предполагая, что у меня есть элемент QTableWidgetItem, и я просто хочу проверить данные, которые вводят пользователи. Например, пользователи вводят в этот элемент только число, иначе программа покажет диалоговое окно с предупреждением.

Я также выполняю поиск на этой странице документа, но не не найти аналогичную функцию с функцией setValidator().

Как я могу использовать валидатор для этого элемента QTableWidgetItem?

Спасибо!


person Tan Viet    schedule 19.08.2013    source источник


Ответы (4)


Предполагая, что вы действительно хотите иметь QValidate-способные ячейки, вместо этого вы можете заполнить ячейку экземпляром QLineEdit. Вот пример, в котором используется QDoubleValidator, но подойдет любой QValidator:

QLineEdit *edit = new QLineEdit(ui->myTable);
edit->setValidator(new QDoubleValidator(edit));
ui->myTable->setCellWidget(row, col, edit);

По умолчанию QLineEdit заполняет ячейку и рисуется с рамкой. Чтобы сохранить внешний вид таблицы, вы можете отключить фрейм, вызвав априори следующую функцию:

QLineEdit::setFrame(false);

Одна раздражающая вещь в этом решении заключается в том, что вам придется звонить

QWidget* QTableWidget::cellWidget(row, col) const

чтобы впоследствии получить доступ к экземпляру QLineEdit в каждой ячейке, что означает, что вам также придется привести указатель к QLineEdit*. (См. qobject_cast()). Это немного многословно, но работоспособно.

person Terrabits    schedule 25.02.2014
comment
Хороший обходной путь! Хотя первая ячейка lineedit (0, 0) немного неуместна. Все остальные ячейки выглядят великолепно, но самая первая кажется слишком высокой, слишком левой, слишком широкой и слишком высокой. - person Uroc327; 30.10.2014

Я могу придумать два разных способа справиться с этим. Могут быть и другие решения.

Вы можете создать подкласс QTableWidgetItem и повторно реализовать функцию setData. Если вы выберете недопустимое значение, вы можете выдать сообщение об ошибке.

Вы можете создать подкласс QStyledItemDelegate и либо добавить QValidator в редактор QWidget, повторно реализовав createEditor, либо повторно реализовать setModelData и изучить пользовательский ввод. Еще раз, вы можете выдать сообщение об ошибке, если есть недопустимые данные.

Проверьте документацию каждого, чтобы увидеть, какой из них больше подходит для вашего проекта.

QTableWidgetItem

QStyledItemDelegate

person RobbieE    schedule 19.08.2013

Я использую это решение, когда у вас есть QLineEdit в каждой ячейке. валидатор предназначен для научных чисел (например, 2e-17)

for(int trow=0; trow <= 2; trow++ )
{
    for(int tcolumn=0; tcolumn <= 3; tcolumn++ )
    {
        QLineEdit * tableline = new QLineEdit;
        tableline->setValidator( new QDoubleValidator(0, 100, 2, this) );
        ui->tableWidget->setCellWidget ( trow, tcolumn,  tableline);
    }
person MrMaavin    schedule 28.09.2016

Есть простой способ добиться этого.

Просто используйте один из сигналов QTableWidget - cellChanged(int,int);

QObject::connect(m_pTableWidget, SIGNAL(cellChanged(int,int)),
                         this, SLOT(OnTableWidgetCellChanged(int,int)));

Функция внутреннего слота (OnTableWidgetCellChanged (int row, int column)), используйте случай переключения со столбцом для проверки каждого столбца отдельно.

Получите входной текст от пользователя этого конкретного столбца и сохраните его как QString. Теперь преобразуйте эту QString в int, передав логическую переменную и проверив состояние логической переменной. Если это ложь, то введенный пользователем недействительный номер. пример показан ниже:

bool bRetValue = false;
QString strValue = m_pTableWidget->item(row, VALUE_INDEX)->text();

int nValue = strValue.toInt(&bRetValue);
if(bRetValue == false)
{
  // show dialog to user to enter only numbers
}

Если вы хотите преобразовать в двойной или другой тип, просто преобразуйте значение в qvariant и выполните ту же процедуру.

QVariant qvarValue(strValue);
double dVal = qvarValue.toDouble(&bRetValue);
if(bRetValue == false)
{
  // show dialog to user to enter only numbers
}

Если вы хотите быть более конкретным, вы можете использовать QRegExp или QRegularExpression (Qt5)

QRegularExpression regexp("enter regx here",
                              QRegularExpression::CaseInsensitiveOption);
QRegularExpressionMatch regxmatch = regexp.match(strValue);
if (regxmatch.hasMatch())
{
    // your functionality
}
else
{
    // show dialog to user to enter only numbers
}
person Sairam krishna    schedule 19.07.2020