00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "kexidbautofield.h"
00023
00024 #include <qlabel.h>
00025 #include <qlayout.h>
00026 #include <qpainter.h>
00027
00028 #include <kdebug.h>
00029 #include <klocale.h>
00030
00031 #include "kexidbcheckbox.h"
00032 #include "kexidbdateedit.h"
00033 #include "kexidbdatetimeedit.h"
00034 #include "kexidbdoublespinbox.h"
00035 #include "kexidbimagebox.h"
00036 #include "kexidbintspinbox.h"
00037 #include "kexidblabel.h"
00038 #include "kexidblineedit.h"
00039 #include "kexidbtextedit.h"
00040 #include "kexidbtimeedit.h"
00041 #include "kexipushbutton.h"
00042 #include "kexidbform.h"
00043
00044 #include <kexidb/queryschema.h>
00045 #include <formeditor/utils.h>
00046 #include <kexiutils/utils.h>
00047
00048 #define KexiDBAutoField_SPACING 10 //10 pixel for spacing between a label and an editor widget
00049
00050 KexiDBAutoField::KexiDBAutoField(const QString &text, WidgetType type, LabelPosition pos,
00051 QWidget *parent, const char *name, bool designMode)
00052 : QWidget(parent, name)
00053 , KexiFormDataItemInterface()
00054 , KFormDesigner::DesignTimeDynamicChildWidgetHandler()
00055 , m_designMode(designMode)
00056 {
00057 init(text, type, pos);
00058 }
00059
00060 KexiDBAutoField::KexiDBAutoField(QWidget *parent, const char *name, bool designMode)
00061 : QWidget(parent, name)
00062 , KexiFormDataItemInterface()
00063 , KFormDesigner::DesignTimeDynamicChildWidgetHandler()
00064 , m_designMode(designMode)
00065 {
00066 init(QString::null, Auto, Left);
00067 }
00068
00069 KexiDBAutoField::~KexiDBAutoField()
00070 {
00071 }
00072
00073 void
00074 KexiDBAutoField::init(const QString &text, WidgetType type, LabelPosition pos)
00075 {
00076 m_fieldTypeInternal = KexiDB::Field::InvalidType;
00077 m_layout = 0;
00078 m_editor = 0;
00079 m_label = new QLabel(text, this);
00080 QFontMetrics fm( font() );
00081
00082 m_autoCaption = true;
00083 m_focusPolicyChanged = false;
00084 m_widgetType = Auto;
00085 m_widgetType_property = (type==Auto ? Text : type);
00086 setWidgetType(type);
00087 setLabelPosition(pos);
00088 }
00089
00090 void
00091 KexiDBAutoField::setWidgetType(WidgetType type)
00092 {
00093 const bool differ = (type != m_widgetType_property);
00094 m_widgetType_property = type;
00095 if(differ) {
00096 if(type == Auto) {
00097 if (columnInfo())
00098 m_widgetType = KexiDBAutoField::widgetTypeForFieldType(columnInfo()->field->type());
00099 else
00100 m_widgetType = Auto;
00101 }
00102 else
00103 m_widgetType = m_widgetType_property;
00104 createEditor();
00105 }
00106 }
00107
00108 void
00109 KexiDBAutoField::createEditor()
00110 {
00111 if(m_editor)
00112 delete m_editor;
00113
00114 switch( m_widgetType ) {
00115 case Text:
00116 case Enum:
00117 case Double:
00118 case Integer:
00119 m_editor = new KexiDBLineEdit( this );
00120 connect( m_editor, SIGNAL( textChanged( const QString& ) ), this, SLOT( slotValueChanged() ) );
00121 break;
00122 case MultiLineText:
00123 m_editor = new KexiDBTextEdit( this );
00124 connect( m_editor, SIGNAL( textChanged( const QString& ) ), this, SLOT( slotValueChanged() ) );
00125 break;
00126 case Boolean:
00127 m_editor = new KexiDBCheckBox(m_dataSource, this);
00128 connect( m_editor, SIGNAL(stateChanged()), this, SLOT(slotValueChanged()));
00129 break;
00131 case Date:
00132 m_editor = new KexiDBDateEdit(QDate::currentDate(), this);
00133 connect( m_editor, SIGNAL( dateChanged(const QDate&) ), this, SLOT( slotValueChanged() ) );
00134 break;
00135 case DateTime:
00136 m_editor = new KexiDBDateTimeEdit(QDateTime::currentDateTime(), this);
00137 connect( m_editor, SIGNAL(dateTimeChanged()), this, SLOT( slotValueChanged() ) );
00138 break;
00139 case Time:
00140 m_editor = new KexiDBTimeEdit(QTime::currentTime(), this);
00141 connect( m_editor, SIGNAL( valueChanged( const QTime& ) ), this, SLOT( slotValueChanged() ) );
00142 break;
00143
00144
00145
00146
00147
00148
00149
00150
00151 case Image:
00152 m_editor = new KexiDBImageBox(m_designMode, this);
00153 connect( m_editor, SIGNAL(valueChanged()), this, SLOT( slotValueChanged() ) );
00154 break;
00155 default:
00156 m_editor = 0;
00157 changeText(m_caption);
00158
00159 break;
00160 }
00161
00162 if(m_editor) {
00163 m_editor->setName( QCString("KexiDBAutoField_")+m_editor->className() );
00164 dynamic_cast<KexiDataItemInterface*>(m_editor)->setParentDataItemInterface(this);
00165 KFormDesigner::DesignTimeDynamicChildWidgetHandler::childWidgetAdded(this);
00166 m_editor->show();
00167 m_label->setBuddy(m_editor);
00168 if (m_focusPolicyChanged) {
00169 m_editor->setFocusPolicy(focusPolicy());
00170 }
00171 else {
00172 QWidget::setFocusPolicy(m_editor->focusPolicy());
00173 }
00174
00175 }
00176
00177 setLabelPosition(labelPosition());
00178 }
00179
00180 void
00181 KexiDBAutoField::setLabelPosition(LabelPosition position)
00182 {
00183 m_lblPosition = position;
00184 if(m_layout) {
00185 delete m_layout;
00186 m_layout = 0;
00187 }
00188
00189 if(m_editor)
00190 m_editor->show();
00192 if (position==Top || position==Left) {
00193 int align = m_label->alignment();
00194 if(position == Top) {
00195 m_layout = (QBoxLayout*) new QVBoxLayout(this);
00196 align |= AlignVertical_Mask;
00197 align ^= AlignVertical_Mask;
00198 align |= AlignTop;
00199 }
00200 else {
00201 m_layout = (QBoxLayout*) new QHBoxLayout(this);
00202 align |= AlignVertical_Mask;
00203 align ^= AlignVertical_Mask;
00204 align |= AlignVCenter;
00205 }
00206 m_label->setAlignment(align);
00207 if(m_widgetType == Boolean)
00208 m_label->hide();
00209 else
00210 m_label->show();
00211 m_layout->addWidget(m_label);
00212 m_layout->addSpacing(KexiDBAutoField_SPACING);
00213 m_layout->addWidget(m_editor);
00214
00215
00216 }
00217 else {
00218 m_layout = (QBoxLayout*) new QHBoxLayout(this);
00219 m_label->hide();
00220 m_layout->addWidget(m_editor);
00221 }
00222
00223 resize(size()+QSize(1,0));
00224 resize(size()-QSize(1,0));
00225 }
00226
00227 void
00228 KexiDBAutoField::setInvalidState( const QString &text )
00229 {
00230
00231 if (m_designMode)
00232 return;
00233 m_widgetType = Auto;
00234 createEditor();
00235 setFocusPolicy(QWidget::NoFocus);
00236 if (m_editor)
00237 m_editor->setFocusPolicy(QWidget::NoFocus);
00239 m_label->setText( text );
00240 }
00241
00242 bool
00243 KexiDBAutoField::isReadOnly() const
00244 {
00245 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00246 if(iface)
00247 return iface->isReadOnly();
00248 else
00249 return false;
00250 }
00251
00252
00253
00254
00255
00256
00257
00258
00259
00260 void
00261 KexiDBAutoField::setValueInternal(const QVariant& add, bool removeOld)
00262 {
00263 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00264 if(iface)
00265 iface->setValue(m_origValue, add, removeOld);
00266 }
00267
00268 QVariant
00269 KexiDBAutoField::value()
00270 {
00271 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00272 if(iface)
00273 return iface->value();
00274 return QVariant();
00275 }
00276
00277 void
00278 KexiDBAutoField::slotValueChanged()
00279 {
00280 signalValueChanged();
00281 }
00282
00283 bool
00284 KexiDBAutoField::valueIsNull()
00285 {
00286 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00287 if(iface)
00288 return iface->valueIsNull();
00289 return true;
00290 }
00291
00292 bool
00293 KexiDBAutoField::valueIsEmpty()
00294 {
00295 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00296 if(iface)
00297 return iface->valueIsEmpty();
00298 return true;
00299 }
00300
00301 bool
00302 KexiDBAutoField::valueChanged()
00303 {
00304 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00305 kexipluginsdbg << m_origValue << endl;
00306 if(iface)
00307 return iface->valueChanged();
00308 return false;
00309 }
00310
00311 void
00312 KexiDBAutoField::installListener(KexiDataItemChangesListener* listener)
00313 {
00314 KexiFormDataItemInterface::installListener(listener);
00315 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00316 if(iface)
00317 iface->installListener(listener);
00318 }
00319
00320 bool
00321 KexiDBAutoField::cursorAtStart()
00322 {
00323 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00324 if(iface)
00325 return iface->cursorAtStart();
00326 return false;
00327 }
00328
00329 bool
00330 KexiDBAutoField::cursorAtEnd()
00331 {
00332 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00333 if(iface)
00334 return iface->cursorAtEnd();
00335 return false;
00336 }
00337
00338 void
00339 KexiDBAutoField::clear()
00340 {
00341 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00342 if(iface)
00343 iface->clear();
00344 }
00345
00346 void
00347 KexiDBAutoField::setFieldTypeInternal(int kexiDBFieldType)
00348 {
00349 m_fieldTypeInternal = (KexiDB::Field::Type)kexiDBFieldType;
00350 WidgetType type = KexiDBAutoField::widgetTypeForFieldType(
00351 m_fieldTypeInternal==KexiDB::Field::InvalidType ? KexiDB::Field::Text : m_fieldTypeInternal);
00352
00353 if(m_widgetType != type) {
00354 m_widgetType = type;
00355 createEditor();
00356 }
00357 setFieldCaptionInternal(m_fieldCaptionInternal);
00358 }
00359
00360 void
00361 KexiDBAutoField::setFieldCaptionInternal(const QString& text)
00362 {
00363 m_fieldCaptionInternal = text;
00364
00365 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00366 if((!iface || !iface->columnInfo()) && m_autoCaption) {
00367 changeText(m_fieldCaptionInternal);
00368 }
00369 }
00370
00371 void
00372 KexiDBAutoField::setColumnInfo(KexiDB::QueryColumnInfo* cinfo)
00373 {
00374 KexiFormDataItemInterface::setColumnInfo(cinfo);
00375
00376
00377 if(m_widgetType_property == Auto) {
00378 WidgetType newWidgetType = Auto;
00379 KexiDB::Field::Type fieldType;
00380 if (cinfo)
00381 fieldType = cinfo->field->type();
00382 else if (dataSource().isEmpty())
00383 fieldType = KexiDB::Field::InvalidType;
00384 else
00385 fieldType = KexiDB::Field::Text;
00386
00387 if (fieldType != KexiDB::Field::InvalidType) {
00388 newWidgetType = KexiDBAutoField::widgetTypeForFieldType( fieldType );
00389 }
00390 if(m_widgetType != newWidgetType || newWidgetType==Auto) {
00391 m_widgetType = newWidgetType;
00392 createEditor();
00393 }
00394 }
00395
00396 changeText((cinfo && m_autoCaption) ? cinfo->captionOrAliasOrName() : QString::null);
00397
00398 KexiFormDataItemInterface *iface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00399 if(iface)
00400 iface->setColumnInfo(cinfo);
00401 }
00402
00403
00404 KexiDBAutoField::WidgetType
00405 KexiDBAutoField::widgetTypeForFieldType(KexiDB::Field::Type type)
00406 {
00407 switch(type) {
00408 case KexiDB::Field::Integer:
00409 case KexiDB::Field::ShortInteger:
00410 case KexiDB::Field::BigInteger:
00411 return Integer;
00412 case KexiDB::Field::Boolean:
00413 return Boolean;
00414 case KexiDB::Field::Float:
00415 case KexiDB::Field::Double:
00416 return Double;
00417 case KexiDB::Field::Date:
00418 return Date;
00419 case KexiDB::Field::DateTime:
00420 return DateTime;
00421 case KexiDB::Field::Time:
00422 return Time;
00423 case KexiDB::Field::Text:
00424 return Text;
00425 case KexiDB::Field::LongText:
00426 return MultiLineText;
00427 case KexiDB::Field::Enum:
00428 return Enum;
00429 case KexiDB::Field::InvalidType:
00430 return Auto;
00431 case KexiDB::Field::BLOB:
00432 default:
00433 break;
00434 }
00435 return Text;
00436 }
00437
00438 void
00439 KexiDBAutoField::changeText(const QString &text, bool beautify)
00440 {
00441 QString realText;
00442 bool unbound = false;
00443 if (m_autoCaption && (m_widgetType==Auto || dataSource().isEmpty())) {
00444 realText = QString::fromLatin1(name())+" "+i18n("Unbound Auto Field", " (unbound)");
00445 unbound = true;
00446 }
00447 else {
00448 if (beautify) {
00452 if (!text.isEmpty()) {
00453 realText = text[0].upper() + text.mid(1);
00454 if (m_widgetType!=Boolean) {
00456 realText += ": ";
00457 }
00458 }
00459 }
00460 else
00461 realText = text;
00462 }
00463
00464 QWidget* widgetToAlterForegroundColor;
00465 if(m_widgetType == Boolean) {
00466 static_cast<QCheckBox*>(m_editor)->setText(realText);
00467 widgetToAlterForegroundColor = m_editor;
00468 }
00469 else {
00470 m_label->setText(realText);
00471 widgetToAlterForegroundColor = m_label;
00472 }
00473
00474
00475
00476
00477
00478
00479
00480
00481 }
00482
00483 void
00484 KexiDBAutoField::setCaption(const QString &caption)
00485 {
00486 m_caption = caption;
00487 if(!m_autoCaption && !caption.isEmpty())
00488 changeText(m_caption);
00489 }
00490
00491
00492
00493
00494
00495
00496
00497 void
00498 KexiDBAutoField::setAutoCaption(bool autoCaption)
00499 {
00500 m_autoCaption = autoCaption;
00501 if(m_autoCaption) {
00502
00503 if(columnInfo()) {
00504 changeText(columnInfo()->captionOrAliasOrName());
00505 }
00506 else {
00507 changeText(m_fieldCaptionInternal);
00508 }
00509 }
00510 else
00511 changeText(m_caption);
00512
00513
00514
00515 }
00516
00517 void
00518 KexiDBAutoField::setDataSource( const QString &ds ) {
00519 KexiFormDataItemInterface::setDataSource(ds);
00520 if (ds.isEmpty()) {
00521 setColumnInfo(0);
00522 }
00523 }
00524
00525 QSize
00526 KexiDBAutoField::sizeHint() const
00527 {
00528 if (m_lblPosition == NoLabel)
00529 return m_editor ? m_editor->sizeHint() : QWidget::sizeHint();
00530
00531 QSize s1(0,0);
00532 if (m_editor)
00533 s1 = m_editor->sizeHint();
00534 QSize s2(m_label->sizeHint());
00535 if (m_lblPosition == Top)
00536 return QSize(QMAX(s1.width(), s2.width()), s1.height()+KexiDBAutoField_SPACING+s2.height());
00537
00538
00539
00540 return QSize(s1.width()+KexiDBAutoField_SPACING+s2.width(), QMAX(s1.height(), s2.height()));
00541 }
00542
00543 void
00544 KexiDBAutoField::setFocusPolicy( FocusPolicy policy )
00545 {
00546 m_focusPolicyChanged = true;
00547 QWidget::setFocusPolicy(policy);
00548 m_label->setFocusPolicy(policy);
00549 if (m_editor)
00550 m_editor->setFocusPolicy(policy);
00551 }
00552
00553 void
00554 KexiDBAutoField::updateInformationAboutUnboundField()
00555 {
00556 if ( (m_autoCaption && (dataSource().isEmpty() || dataSourceMimeType().isEmpty()))
00557 || (!m_autoCaption && m_caption.isEmpty()) )
00558 {
00559 m_label->setText( QString::fromLatin1(name())+" "+i18n("Unbound Auto Field", " (unbound)") );
00560 }
00561
00562
00563 }
00564
00565
00566
00567
00568
00569
00570
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580
00581
00582 void
00583 KexiDBAutoField::paletteChange( const QPalette& oldPal )
00584 {
00585 Q_UNUSED(oldPal);
00586 m_label->setPalette( palette() );
00587 }
00588
00589
00590 #include "kexidbautofield.moc"