PDA

View Full Version : field() method of QWizard returning currentIndex of combo-boxes, not values. Help



stevebakh
26th February 2010, 00:35
Hi!

As the title suggests, I'm attempting to get the selected value from a QComboBox on a wizard page. I have a bunch of combo-boxes which are populated with data from a relational model's relations. I was struggling trying to insert a record into the database with the selected values and have discovered that calling value() is returning the currentIndex of the combo-boxes, rather than the selected value.

I should point out here that I'm both very new to Qt and C++, so go easy on me. :)

My code thus far:

The Patient object is derived from QSqlRelationalTableModel. I have a bunch of methods in that class to return the relations of the model, hence the "patient->gender()" type calls. They return a object of type QSqlRelation.



/***
* Register all of the necessary fields with this
* wizard form page.
*/
void NewPatientPageTwo::registerFields()
{
registerField("doctor", ui->doctor);
registerField("gender", ui->gender);
registerField("sexual_orientation", ui->sexual_orientation);
registerField("marital_status", ui->marital_status);
registerField("employment_status", ui->employment_status);
registerField("performance_status", ui->performance_status);
registerField("alcohol_consumption", ui->alcohol_consumption);
registerField("clinical_group", ui->clinical_group);
registerField("ethnic_category", ui->ethnic_category);
}

/***
* Each of the fields on this wizard page are
* combo-boxes that need to be populated with
* information held in the database.
*/
void NewPatientPageTwo::populateFields()
{
Patient *patientModel = new Patient(this);

// doctor
ui->doctor->setModel(patientModel->doctor());
ui->doctor->setModelColumn(patientModel->doctor()->fieldIndex("lastname"));

// gender
ui->gender->setModel(patientModel->gender());
ui->gender->setModelColumn(patientModel->gender()->fieldIndex("description"));

// sexual orientation
ui->sexual_orientation->setModel(patientModel->sexualOrientation());
ui->sexual_orientation->setModelColumn(patientModel->sexualOrientation()->fieldIndex("description"));

// marital status
ui->marital_status->setModel(patientModel->maritalStatus());
ui->marital_status->setModelColumn(patientModel->maritalStatus()->fieldIndex("description"));

// employment status
ui->employment_status->setModel(patientModel->employmentStatus());
ui->employment_status->setModelColumn(patientModel->employmentStatus()->fieldIndex("description"));

// performance status
ui->performance_status->setModel(patientModel->performanceStatus());
ui->performance_status->setModelColumn(patientModel->performanceStatus()->fieldIndex("description"));

// alcohol consumption
ui->alcohol_consumption->setModel(patientModel->alcoholStatus());
ui->alcohol_consumption->setModelColumn(patientModel->alcoholStatus()->fieldIndex("description"));

// clinical group
ui->clinical_group->setModel(patientModel->clinicalGroup());
ui->clinical_group->setModelColumn(patientModel->clinicalGroup()->fieldIndex("description"));

// ethnic category
ui->ethnic_category->setModel(patientModel->ethnicCategory());
ui->ethnic_category->setModelColumn(patientModel->ethnicCategory()->fieldIndex("description"));
}


This is the imlpementation of the accept method in the wizard class. It's called when I hit the finish button.


void NewPatient::accept()
{
Patient *model = new Patient(this);
unsigned int row = model->rowCount();

if (model->insertRow(row)) {
model->setData(model->index(row, Patient::NHSNumber), field("nhsnumber"));
model->setData(model->index(row, Patient::EmploymentStatus), field("employment_status"));
model->setData(model->index(row, Patient::Gender), field("gender"));
model->setData(model->index(row, Patient::MaritalStatus), field("marital_status"));
model->setData(model->index(row, Patient::PerformanceStatus), field("performance_status"));
model->setData(model->index(row, Patient::SexualOrientation), field("sexual_orientation"));
model->setData(model->index(row, Patient::ClinicalGroup), field("clinical_group"));
model->setData(model->index(row, Patient::EthnicCategory), field("ethnic_category"));
model->setData(model->index(row, Patient::AlcoholStatus), field("alcohol_consumption"));
model->setData(model->index(row, Patient::Doctor), field("doctor"));
model->setData(model->index(row, Patient::Salutation), field("title"));
model->setData(model->index(row, Patient::BirthDate), field("dob").toDate().toString(Qt::ISODate));
model->setData(model->index(row, Patient::FirstName), field("firstname"));
model->setData(model->index(row, Patient::LastName), field("lastname"));
model->setData(model->index(row, Patient::RegisteredDate), QDate::currentDate().toString(Qt::ISODate));

model->database().transaction();

if (model->submitAll()) {
model->database().commit();
} else {
model->database().rollback();
}
}

close();
}


The insert is failing because the calls to field("inputname") aren't returning the value, as expected. They're returning the currentIndex. Any help would be really appreciated.

Thanks!

norobro
26th February 2010, 20:07
Disclaimer: I have never used the QWizard or the QWizardPage classes but your post piqued my curiosity. So I took a look at the docs. Check this out: setDefaultProperty (http://doc.trolltech.com/4.6/qwizard.html#setDefaultProperty).

QComboBox:getText() might work too:
model->setData(model->index(row, Patient::MaritalStatus), ui->marital_status->getText());

Lykurg
26th February 2010, 20:44
Damn, what a database is that: sexual orientation, alcohol consumption, ethnic category! I hope I don't get an ethical dilemma if I help you;)

Have a look at QWizard::setDefaultProperty(). There you can change to return type to currentText.

stevebakh
26th February 2010, 22:37
Thank you both for your responses!

As it happens, the setDefaultProperty isn't useful to me in this instance. I was assuming that the combo-box would be similar to a HTML select-box. I'm very new to desktop application development. I figured that each selectable item could have a value assigned to it but a different text label. In this case, the QComboBoxes were being populated by QSqlTableModel objects, so I was hoping that I could display one table column as the text and have the primary key 'id' column, for example, as the "value" of the item. Unfortunately, that doesn't appear to be the case.

norobro, your answer is the similar to the solution I found! I ended up having to pull the data back from the table model, based on the currentIndex of the QComboBox and the column I wanted to access, using a QModelIndex. Essentially, I'm doing the following:



model->setData(model->index(row, Patient::EmploymentStatus),
model->employmentStatus()->index(field("employment_status").toInt(), model->employmentStatus()->fieldIndex("code")).data());


I don't have direct access to the QComboBox object at the stage I'm trying to access the values, which is why I couldn't do ui->comboBox->blahblah and instead had to pull from the model again.

I'm pretty sure that what I'm doing is fairly inefficient, so if there's a better way of doing this, I'd love to know. In general, if there are any in-depth examples of working with QSql*Models then I'd love to know about them.

By the way, Lykurg, the database makes up part of a patient management system for general practice clinics (built for my university project) and those attributes are a small sample of the details that the NHS stores. ;)

Thanks again, guys.