00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include <qwidget.h>
00023 #include <qlabel.h>
00024 #include <qobjectlist.h>
00025
00026 #include <kdebug.h>
00027 #include <klocale.h>
00028 #include <kcommand.h>
00029 #include <kaction.h>
00030 #include <kmessagebox.h>
00031
00032 #include "container.h"
00033 #include "objecttree.h"
00034 #include "widgetpropertyset.h"
00035 #include "formIO.h"
00036 #include "formmanager.h"
00037 #include "widgetlibrary.h"
00038 #include "spring.h"
00039 #include "pixmapcollection.h"
00040 #include "events.h"
00041 #include "utils.h"
00042 #include <koproperty/property.h>
00043
00044 #include "form.h"
00045
00046 using namespace KFormDesigner;
00047
00048 FormPrivate::FormPrivate()
00049 {
00050 toplevel = 0;
00051 topTree = 0;
00052 widget = 0;
00053 resizeHandles.setAutoDelete(true);
00054 dirty = false;
00055 interactive = true;
00056 design = true;
00057 autoTabstops = false;
00058 tabstops.setAutoDelete(false);
00059 connBuffer = new ConnectionBuffer();
00060 formatVersion = KFormDesigner::version();
00061 originalFormatVersion = KFormDesigner::version();
00062 }
00063
00064 FormPrivate::~FormPrivate()
00065 {
00066 delete history;
00067 delete topTree;
00068 delete connBuffer;
00069 connBuffer = 0;
00070 resizeHandles.setAutoDelete(false);
00071
00072 }
00073
00074
00075
00076 FormWidget::FormWidget()
00077 : m_form(0)
00078 {
00079 }
00080
00081 FormWidget::~FormWidget()
00082 {
00083 if (m_form) {
00084 m_form->setFormWidget(0);
00085 }
00086 }
00087
00088
00089
00090 Form::Form(WidgetLibrary* library, const char *name, bool designMode)
00091 : QObject(library, name)
00092 , m_lib(library)
00093 {
00094 d = new FormPrivate();
00095
00096 d->design = designMode;
00097
00098
00099 d->collection = new KActionCollection(0, this);
00100 d->history = new KCommandHistory(d->collection, true);
00101 connect(d->history, SIGNAL(commandExecuted()), this, SLOT(slotCommandExecuted()));
00102 connect(d->history, SIGNAL(documentRestored()), this, SLOT(slotFormRestored()));
00103 }
00104
00105 Form::~Form()
00106 {
00107 emit destroying();
00108 delete d;
00109 d = 0;
00110 }
00111
00112 QWidget*
00113 Form::widget() const
00114 {
00115 if(d->topTree)
00116 return d->topTree->widget();
00117 else if(d->toplevel)
00118 return d->toplevel->widget();
00119 else
00120 return d->widget;
00121 }
00122
00124
00125 void
00126 Form::createToplevel(QWidget *container, FormWidget *formWidget, const QCString &)
00127 {
00128 kdDebug() << "Form::createToplevel() container= "<< (container ? container->name() : "<NULL>")
00129 << " formWidget=" << formWidget << "className=" << name() << endl;
00130
00131 setFormWidget( formWidget );
00132 d->toplevel = new Container(0, container, this, name());
00133 d->topTree = new ObjectTree(i18n("Form"), container->name(), container, d->toplevel);
00134 d->toplevel->setObjectTree(d->topTree);
00135 d->toplevel->setForm(this);
00136 d->pixcollection = new PixmapCollection(container->name(), this);
00137
00138 d->topTree->setWidget(container);
00140
00141
00142
00143 connect(container, SIGNAL(destroyed()), this, SLOT(formDeleted()));
00144
00145 kdDebug() << "Form::createToplevel(): d->toplevel=" << d->toplevel << endl;
00146 }
00147
00148
00149 Container*
00150 Form::activeContainer()
00151 {
00152 ObjectTreeItem *it;
00153 if(d->selected.count() == 0)
00154 return d->toplevel;
00155
00156 if(d->selected.count() == 1)
00157 it = d->topTree->lookup(d->selected.last()->name());
00158 else
00159 it = commonParentContainer( &(d->selected) );
00160
00161 if (!it)
00162 return 0;
00163 if(it->container())
00164 return it->container();
00165 else
00166 return it->parent()->container();
00167 }
00168
00169 ObjectTreeItem*
00170 Form::commonParentContainer(WidgetList *wlist)
00171 {
00172 ObjectTreeItem *item = 0;
00173 WidgetList *list = new WidgetList();
00174
00175
00176 for(QWidget *w = wlist->first(); w; w = wlist->next())
00177 {
00178 if(list->findRef(w->parentWidget()) == -1)
00179 list->append(w->parentWidget());
00180 }
00181
00182 removeChildrenFromList(*list);
00183
00184
00185 if(list->count() == 1)
00186 item = d->topTree->lookup(list->first()->name());
00187 else
00188 item = commonParentContainer(list);
00189
00190 delete list;
00191 return item;
00192 }
00193
00194 Container*
00195 Form::parentContainer(QWidget *w)
00196 {
00197 ObjectTreeItem *it;
00198 if(!w)
00199 return 0;
00200
00201
00202 it = d->topTree->lookup(w->name());
00203
00204 if(it->parent()->container())
00205 return it->parent()->container();
00206 else
00207 return it->parent()->parent()->container();
00208 }
00209
00210
00211
00212 void
00213 Form::setDesignMode(bool design)
00214 {
00215 d->design = design;
00216 if(!design)
00217 {
00218 ObjectTreeDict *dict = new ObjectTreeDict( *(d->topTree->dict()) );
00219 ObjectTreeDictIterator it(*dict);
00220 for(; it.current(); ++it)
00221 m_lib->previewWidget(it.current()->widget()->className(), it.current()->widget(), d->toplevel);
00222 delete dict;
00223
00224 d->widget = d->topTree->widget();
00225 delete (d->topTree);
00226 d->topTree = 0;
00227 delete (d->toplevel);
00228 d->toplevel = 0;
00229 }
00230 }
00231
00232
00234
00235 void
00236 Form::setSelectedWidget(QWidget *w, bool add, bool dontRaise, bool moreWillBeSelected)
00237 {
00238 if((d->selected.isEmpty()) || (w == widget()) || (d->selected.first() == widget()))
00239 add = false;
00240
00241 if(!w)
00242 {
00243 setSelectedWidget(widget());
00244 return;
00245 }
00246
00247
00248 QWidget *wtmp = w;
00249 while(!dontRaise && wtmp && wtmp->parentWidget() && (wtmp != widget()))
00250 {
00251 wtmp->raise();
00252 if(d->resizeHandles[ wtmp->name() ])
00253 d->resizeHandles[ wtmp->name() ]->raise();
00254 wtmp = wtmp->parentWidget();
00255 }
00256
00257 if (wtmp)
00258 wtmp->setFocus();
00259
00260 if(!add)
00261 {
00262 d->selected.clear();
00263 d->resizeHandles.clear();
00264 }
00265 d->selected.append(w);
00266 emit selectionChanged(w, add, moreWillBeSelected);
00267 emitActionSignals(false);
00268
00269
00270 if(!FormManager::self()->isTopLevel(w) && w->parentWidget() && w->parentWidget()->isA("QWidgetStack"))
00271 {
00272 w = w->parentWidget();
00273 if(w->parentWidget() && w->parentWidget()->inherits("QTabWidget"))
00274 w = w->parentWidget();
00275 }
00276
00277 if(w && w != widget())
00278 d->resizeHandles.insert(w->name(), new ResizeHandleSet(w, this));
00279 }
00280
00281 ResizeHandleSet*
00282 Form::resizeHandlesForWidget(QWidget* w)
00283 {
00284 return d->resizeHandles[w->name()];
00285 }
00286
00287 void
00288 Form::unSelectWidget(QWidget *w)
00289 {
00290 d->selected.remove(w);
00291 d->resizeHandles.remove(w->name());
00292 }
00293
00294 void
00295 Form::selectFormWidget()
00296 {
00297 setSelectedWidget(widget(), false);
00298 }
00299
00300 void
00301 Form::clearSelection()
00302 {
00303 d->selected.clear();
00304 d->resizeHandles.clear();
00305 emit selectionChanged(0, false);
00306 emitActionSignals(false);
00307 }
00308
00309 void
00310 Form::emitActionSignals(bool withUndoAction)
00311 {
00312
00313 if(d->selected.count() > 1)
00314 FormManager::self()->emitWidgetSelected(this, true);
00315 else if(d->selected.first() != widget())
00316 FormManager::self()->emitWidgetSelected(this, false);
00317 else
00318 FormManager::self()->emitFormWidgetSelected(this);
00319
00320 if(!withUndoAction)
00321 return;
00322
00323 KAction *undoAction = d->collection->action("edit_undo");
00324 if(undoAction)
00325 FormManager::self()->emitUndoEnabled(undoAction->isEnabled(), undoAction->text());
00326
00327 KAction *redoAction = d->collection->action("edit_redo");
00328 if(redoAction)
00329 FormManager::self()->emitRedoEnabled(redoAction->isEnabled(), redoAction->text());
00330 }
00331
00332 void
00333 Form::emitSelectionSignals()
00334 {
00335 emit selectionChanged(selectedWidgets()->first(), false);
00336
00337
00338 for (WidgetListIterator it(*selectedWidgets()); it.current(); ++it)
00339 emit selectionChanged(it.current(), true);
00340 }
00341
00343 void
00344 Form::formDeleted()
00345 {
00346
00347 d->selected.clear();
00348 d->resizeHandles.setAutoDelete(false);
00349 d->resizeHandles.clear();
00350 d->resizeHandles.setAutoDelete(true);
00351
00352
00353
00354 FormManager::self()->deleteForm(this);
00355
00356 deleteLater();
00357 }
00358
00359 void
00360 Form::changeName(const QCString &oldname, const QCString &newname)
00361 {
00362 if(oldname == newname)
00363 return;
00364 if(!d->topTree->rename(oldname, newname))
00365 {
00366 KMessageBox::sorry(widget()->topLevelWidget(),
00367 i18n("Renaming widget \"%1\" to \"%2\" failed.").arg(oldname).arg(newname));
00368
00369
00370
00371
00372 kdDebug() << "Form::changeName() : ERROR : A widget named " << newname << " already exists" << endl;
00373 FormManager::self()->propertySet()->property("name") = QVariant(oldname);
00374 }
00375 else
00376 {
00377 d->connBuffer->fixName(oldname, newname);
00378 ResizeHandleSet *temp = d->resizeHandles.take(oldname);
00379 d->resizeHandles.insert(newname, temp);
00380 }
00381 }
00382
00383 void
00384 Form::emitChildAdded(ObjectTreeItem *item)
00385 {
00386 addWidgetToTabStops(item);
00387 emit childAdded(item);
00388 }
00389
00390 void
00391 Form::emitChildRemoved(ObjectTreeItem *item)
00392 {
00393 d->tabstops.remove(item);
00394 if(d->connBuffer)
00395 d->connBuffer->removeAllConnectionsForWidget(item->name());
00396 emit childRemoved(item);
00397 }
00398
00399 void
00400 Form::addCommand(KCommand *command, bool execute)
00401 {
00402 emit FormManager::self()->dirty(this, true);
00403 d->dirty = true;
00404 d->history->addCommand(command, execute);
00405 if(!execute)
00406 slotCommandExecuted();
00407 }
00408
00409 void
00410 Form::clearCommandHistory()
00411 {
00412 d->history->clear();
00413 FormManager::self()->emitUndoEnabled(false, QString::null);
00414 FormManager::self()->emitRedoEnabled(false, QString::null);
00415 }
00416
00417 void
00418 Form::slotCommandExecuted()
00419 {
00420 emit FormManager::self()->dirty(this, true);
00421 d->dirty = true;
00422
00423 QTimer::singleShot(10, this, SLOT(emitUndoEnabled()));
00424 QTimer::singleShot(10, this, SLOT(emitRedoEnabled()));
00425 }
00426
00427 void
00428 Form::emitUndoEnabled()
00429 {
00430 KAction *undoAction = d->collection->action("edit_undo");
00431 if(undoAction)
00432 FormManager::self()->emitUndoEnabled(undoAction->isEnabled(), undoAction->text());
00433 }
00434
00435 void
00436 Form::emitRedoEnabled()
00437 {
00438 KAction *redoAction = d->collection->action("edit_redo");
00439 if(redoAction)
00440 FormManager::self()->emitRedoEnabled(redoAction->isEnabled(), redoAction->text());
00441 }
00442
00443 void
00444 Form::slotFormRestored()
00445 {
00446 emit FormManager::self()->dirty(this, false);
00447 d->dirty = false;
00448 }
00449
00450
00452
00453 void
00454 Form::addWidgetToTabStops(ObjectTreeItem *c)
00455 {
00456 QWidget *w = c->widget();
00457 if(!w)
00458 return;
00459 if(!(w->focusPolicy() & QWidget::TabFocus))
00460 {
00461 if(!w->children())
00462 return;
00463
00464
00465 QObjectList list = *(w->children());
00466 for(QObject *obj = list.first(); obj; obj = list.next())
00467 {
00468
00469
00470 if(obj->isWidgetType()) {
00471 if(d->tabstops.findRef(c) == -1) {
00472 d->tabstops.append(c);
00473 return;
00474 }
00475 }
00476 }
00477 }
00478 else if(d->tabstops.findRef(c) == -1)
00479 d->tabstops.append(c);
00480 }
00481
00482 void
00483 Form::updateTabStopsOrder()
00484 {
00485 for (ObjectTreeListIterator it(d->tabstops);it.current();) {
00486 if(!(it.current()->widget()->focusPolicy() & QWidget::TabFocus)) {
00487 kexidbg << "Form::updateTabStopsOrder(): widget removed because has no TabFocus: " << it.current()->widget()->name() << endl;
00488 d->tabstops.remove( it.current() );
00489 }
00490 else
00491 ++it;
00492 }
00493 }
00494
00495 void
00496 Form::autoAssignTabStops()
00497 {
00498 VerWidgetList list;
00499 HorWidgetList hlist;
00500
00501 foreach_list(ObjectTreeListIterator, it, d->tabstops) {
00502 if(it.current()->widget())
00503 list.append(it.current()->widget());
00504 }
00505
00506 list.sort();
00507 d->tabstops.clear();
00508
00511 foreach_list(WidgetListIterator, it, list) {
00512
00513 QWidget *w = it.current();
00514 hlist.append(w);
00515
00516 ++it;
00517 QWidget *nextw = it.current();
00518 while(nextw && (nextw->y() < (w->y() + 20))) {
00519 hlist.append(nextw);
00520 ++it; nextw = it.current();
00521 }
00522 hlist.sort();
00523
00524 for(WidgetListIterator it2(hlist); it2.current() != 0; ++it2) {
00525 ObjectTreeItem *tree = d->topTree->lookup(it2.current()->name());
00526 if(tree) {
00527 kdDebug() << "Form::autoAssignTabStops() adding " << tree->name() << endl;
00528 d->tabstops.append(tree);
00529 }
00530 }
00531
00532 --it;
00533 hlist.clear();
00534 }
00535 }
00536
00537 uint Form::formatVersion() const
00538 {
00539 return d->formatVersion;
00540 }
00541
00542 void Form::setFormatVersion(uint ver)
00543 {
00544 d->formatVersion = ver;
00545 }
00546 uint Form::originalFormatVersion() const
00547 {
00548 return d->originalFormatVersion;
00549 }
00550
00551 void Form::setOriginalFormatVersion(uint ver)
00552 {
00553 d->originalFormatVersion = ver;
00554 }
00555
00556 void Form::setFormWidget(FormWidget* w)
00557 {
00558 if (!d)
00559 return;
00560 d->formWidget = w;
00561 if (!d->formWidget)
00562 return;
00563 d->formWidget->m_form = this;
00564 }
00565
00566 #include "form.moc"