2 // applicationwindow.cpp: Architektonas
4 // Part of the Architektonas Project
5 // (C) 2011 Underground Software
6 // See the README and GPLv3 files for licensing and warranty information
8 // JLH = James Hammons <jlhamm@acm.org>
11 // --- ---------- -------------------------------------------------------------
12 // JLH 03/22/2011 Created this file
13 // JLH 09/29/2011 Added simple zoom in/out functionality
14 // JLH 10/03/2011 Fixed zoom tool to zoom in/out from center of screen
24 // Uncomment this for debugging...
26 //#define DEBUGFOO // Various tool debugging...
27 //#define DEBUGTP // Toolpalette debugging...
29 #include "applicationwindow.h"
32 #include "blockwidget.h"
33 #include "drawingview.h"
34 #include "drawarcaction.h"
35 #include "drawcircleaction.h"
36 #include "drawdimensionaction.h"
37 #include "drawlineaction.h"
39 #include "generaltab.h"
40 #include "layerwidget.h"
41 #include "mirroraction.h"
43 #include "settingsdialog.h"
46 ApplicationWindow::ApplicationWindow():
47 baseUnitInput(new QLineEdit),
48 dimensionSizeInput(new QLineEdit),
49 settings("Underground Software", "Architektonas")
51 drawing = new DrawingView(this);
52 drawing->setMouseTracking(true); // We want *all* mouse events...!
53 drawing->setFocusPolicy(Qt::StrongFocus);
54 setCentralWidget(drawing);
56 aboutWin = new AboutWindow(this);
58 // ((TTEdit *)qApp)->charWnd = new CharWindow(this);
60 setWindowIcon(QIcon(":/res/atns-icon.png"));
61 setWindowTitle("Architektonas");
67 // Create Dock widgets
68 QDockWidget * dock1 = new QDockWidget(tr("Layers"), this);
69 LayerWidget * lw = new LayerWidget;
71 addDockWidget(Qt::RightDockWidgetArea, dock1);
72 QDockWidget * dock2 = new QDockWidget(tr("Blocks"), this);
73 BlockWidget * bw = new BlockWidget;
75 addDockWidget(Qt::RightDockWidgetArea, dock2);
76 // Needed for saveState()
77 dock1->setObjectName("Layers");
78 dock2->setObjectName("Blocks");
81 zoomIndicator = new QLabel("Grid: 12.0\" Zoom: 12.5%");
82 statusBar()->addPermanentWidget(zoomIndicator);
83 statusBar()->showMessage(tr("Ready"));
86 setUnifiedTitleAndToolBarOnMac(true);
87 Object::SetFont(new QFont("Verdana", 15, QFont::Bold));
89 connect(lw, SIGNAL(LayerSelected(int)), drawing, SLOT(SetCurrentLayer(int)));
93 void ApplicationWindow::closeEvent(QCloseEvent * event)
96 event->accept(); // Use ignore() if can't close for some reason
97 //Do we have a memory leak here if we don't delete the font in the Object???
101 void ApplicationWindow::FileNew(void)
103 // Should warn the user if drawing hasn't been saved...
104 drawing->document.Clear();
106 documentName.clear();
107 setWindowTitle("Architektonas - Untitled");
108 statusBar()->showMessage(tr("New drawing is ready."));
112 void ApplicationWindow::FileOpen(void)
114 QString filename = QFileDialog::getOpenFileName(this, tr("Open Drawing"),
115 "", tr("Architektonas files (*.drawing)"));
116 FILE * file = fopen(filename.toAscii().data(), "r");
121 msg.setText(QString(tr("Could not open file \"%1\" for loading!")).arg(filename));
122 msg.setIcon(QMessageBox::Critical);
127 Container container(Vector(0, 0));
128 bool successful = FileIO::LoadAtnsFile(file, &container);
134 msg.setText(QString(tr("Could not load file \"%1\"!")).arg(filename));
135 msg.setIcon(QMessageBox::Critical);
140 printf("FileOpen: container size = %li\n", container.objects.size());
141 drawing->document = container;
143 documentName = filename;
144 setWindowTitle(QString("Architektonas - %1").arg(documentName));
145 statusBar()->showMessage(tr("Drawing loaded."));
149 void ApplicationWindow::FileSave(void)
151 if (documentName.isEmpty())
152 documentName = QFileDialog::getSaveFileName(this, tr("Save Drawing"),
153 "", tr("Architektonas drawings (*.drawing)"));
155 FILE * file = fopen(documentName.toAscii().data(), "w");
160 msg.setText(QString(tr("Could not open file \"%1\" for saving!")).arg(documentName));
161 msg.setIcon(QMessageBox::Critical);
166 bool successful = FileIO::SaveAtnsFile(file, &drawing->document);
172 msg.setText(QString(tr("Could not save file \"%1\"!")).arg(documentName));
173 msg.setIcon(QMessageBox::Critical);
175 // In this case, we should unlink the created file, since it's not right...
176 unlink(documentName.toAscii().data());
180 setWindowTitle(QString("Architektonas - %1").arg(documentName));
181 statusBar()->showMessage(tr("Drawing saved."));
185 void ApplicationWindow::FileSaveAs(void)
187 QString filename = QFileDialog::getSaveFileName(this, tr("Save Drawing As"),
188 documentName, tr("Architektonas drawings (*.drawing)"));
190 if (!filename.isEmpty())
192 documentName = filename;
198 void ApplicationWindow::SnapToGridTool(void)
200 Object::SetSnapMode(snapToGridAct->isChecked());
204 void ApplicationWindow::FixAngle(void)
206 Object::SetFixedAngle(fixAngleAct->isChecked());
210 void ApplicationWindow::FixLength(void)
212 Object::SetFixedLength(fixLengthAct->isChecked());
216 // We want certain tools to be exclusive, and this approach isn't working correctly...
217 void ApplicationWindow::DeleteTool(void)
219 // For this tool, we check first to see if anything is selected. If so, we
220 // delete those and *don't* select the delete tool.
221 if (drawing->document.ItemsSelected() > 0)
223 drawing->document.DeleteSelectedItems();
225 deleteAct->setChecked(false);
229 // Otherwise, toggle the state of the tool
230 ClearUIToolStatesExcept(deleteAct);
231 SetInternalToolStates();
235 void ApplicationWindow::DimensionTool(void)
237 ClearUIToolStatesExcept(addDimensionAct);
238 SetInternalToolStates();
242 void ApplicationWindow::RotateTool(void)
244 ClearUIToolStatesExcept(rotateAct);
245 SetInternalToolStates();
249 void ApplicationWindow::MirrorTool(void)
251 ClearUIToolStatesExcept(mirrorAct);
252 SetInternalToolStates();
256 void ApplicationWindow::AddLineTool(void)
258 ClearUIToolStatesExcept(addLineAct);
259 SetInternalToolStates();
263 void ApplicationWindow::AddCircleTool(void)
265 ClearUIToolStatesExcept(addCircleAct);
266 SetInternalToolStates();
270 void ApplicationWindow::AddArcTool(void)
272 ClearUIToolStatesExcept(addArcAct);
273 SetInternalToolStates();
277 void ApplicationWindow::AddPolygonTool(void)
279 ClearUIToolStatesExcept(addPolygonAct);
280 SetInternalToolStates();
284 void ApplicationWindow::ZoomInTool(void)
286 double zoomFactor = 2.0;
288 We need to find the center of the screen, then figure out where the new corner
289 will be in the zoomed in window.
291 So we know in Qt coords, the center is found via:
292 size.width() / 2 --> xCenter
293 size.height() / 2 --> yCenter
295 transform x/yCenter to Cartesian coordinates. So far, so good.
297 when zooming in, new origin will be (xCenter - origin.x) / 2, (yCenter - origin.y) / 2
298 (after subtracting from center, that is...)
300 QSize size = drawing->size();
301 Vector center(size.width() / 2.0, size.height() / 2.0);
302 //printf("Zoom in... Center=%.2f,%.2f; ", center.x, center.y);
303 center = Painter::QtToCartesianCoords(center);
304 //printf("(%.2f,%.2f); origin=%.2f,%.2f; ", center.x, center.y, Painter::origin.x, Painter::origin.y);
305 Vector newOrigin = center - ((center - Painter::origin) / zoomFactor);
306 //printf("newOrigin=%.2f,%.2f;\n", newOrigin.x, newOrigin.y);
307 Painter::origin = newOrigin;
309 //printf("Zoom in... level going from %02f to ", Painter::zoom);
310 // This just zooms leaving origin intact... should zoom in at the current center! [DONE]
311 // This should actually be calculated by drawing->gridPixels / grid size.
312 Painter::zoom *= zoomFactor;
313 // drawing->gridSpacing = drawing->gridPixels / Painter::zoom;
314 Object::gridSpacing = drawing->gridPixels / Painter::zoom;
315 // zoomIndicator->setText(QString("Grid: %2\" Zoom: %1%").arg(Painter::zoom * 100.0 * SCREEN_ZOOM).arg(drawing->gridSpacing));
316 // zoomIndicator->setText(QString("Grid: %1\", BU: Inch").arg(drawing->gridSpacing));
317 zoomIndicator->setText(QString("Grid: %1\", BU: Inch").arg(Object::gridSpacing));
318 drawing->UpdateGridBackground();
321 // baseUnitInput->setText(QString("%1").arg(drawing->gridSpacing));
322 baseUnitInput->setText(QString("%1").arg(Object::gridSpacing));
326 void ApplicationWindow::ZoomOutTool(void)
331 origin = (223, 160.5)
332 newOrigin should be (-10, -10)
335 center - origin = (213, 150.5)
336 origin - center = (-213, -150.5)
338 + center = (-10, -10)
341 double zoomFactor = 2.0;
342 QSize size = drawing->size();
343 Vector center(size.width() / 2.0, size.height() / 2.0);
344 //printf("Zoom out... Center=%.2f,%.2f; ", center.x, center.y);
345 center = Painter::QtToCartesianCoords(center);
346 //printf("(%.2f,%.2f); origin=%.2f,%.2f; ", center.x, center.y, Painter::origin.x, Painter::origin.y);
347 // Vector newOrigin = (center - Painter::origin) * zoomFactor;
348 // Vector newOrigin = center - (Painter::origin * zoomFactor);
349 Vector newOrigin = center + ((Painter::origin - center) * zoomFactor);
350 //printf("newOrigin=%.2f,%.2f;\n", newOrigin.x, newOrigin.y);
351 Painter::origin = newOrigin;
352 //printf("Zoom out...\n");
353 // This just zooms leaving origin intact... should zoom out at the current center! [DONE]
354 Painter::zoom /= zoomFactor;
355 // drawing->gridSpacing = drawing->gridPixels / Painter::zoom;
356 Object::gridSpacing = drawing->gridPixels / Painter::zoom;
357 // zoomIndicator->setText(QString("Grid: %2\" Zoom: %1%").arg(Painter::zoom * 100.0 * SCREEN_ZOOM).arg(drawing->gridSpacing));
358 // zoomIndicator->setText(QString("Grid: %1\", BU: Inch").arg(drawing->gridSpacing));
359 zoomIndicator->setText(QString("Grid: %1\", BU: Inch").arg(Object::gridSpacing));
360 drawing->UpdateGridBackground();
363 // baseUnitInput->setText(QString("%1").arg(drawing->gridSpacing));
364 baseUnitInput->setText(QString("%1").arg(Object::gridSpacing));
368 void ApplicationWindow::ClearUIToolStatesExcept(QAction * exception)
370 if (exception != addArcAct)
371 addArcAct->setChecked(false);
373 if (exception != addCircleAct)
374 addCircleAct->setChecked(false);
376 if (exception != addDimensionAct)
377 addDimensionAct->setChecked(false);
379 if (exception != addLineAct)
380 addLineAct->setChecked(false);
382 if (exception != addPolygonAct)
383 addPolygonAct->setChecked(false);
385 if (exception != deleteAct)
386 deleteAct->setChecked(false);
388 if (exception != rotateAct)
389 rotateAct->setChecked(false);
391 if (exception != mirrorAct)
392 mirrorAct->setChecked(false);
396 void ApplicationWindow::SetInternalToolStates(void)
398 Object::SetDeleteActive(deleteAct->isChecked());
399 Object::SetDimensionActive(addDimensionAct->isChecked());
400 drawing->SetRotateToolActive(rotateAct->isChecked());
402 // We can be sure that if we've come here, then either an active tool is
403 // being deactivated, or a new tool is being created. In either case, the
404 // old tool needs to be deleted.
405 if (drawing->toolAction)
407 delete drawing->toolAction;
408 drawing->toolAction = NULL;
412 drawing->SetAddLineToolActive(addLineAct->isChecked());
413 drawing->SetAddCircleToolActive(addCircleAct->isChecked());
414 drawing->SetAddArcToolActive(addArcAct->isChecked());
415 drawing->SetAddDimensionToolActive(addDimensionAct->isChecked());
417 drawing->SetToolActive(addLineAct->isChecked() ? new DrawLineAction() : NULL);
418 drawing->SetToolActive(addCircleAct->isChecked() ? new DrawCircleAction() : NULL);
419 drawing->SetToolActive(addArcAct->isChecked() ? new DrawArcAction() : NULL);
420 drawing->SetToolActive(addDimensionAct->isChecked() ? new DrawDimensionAction() : NULL);
421 drawing->SetToolActive(mirrorAct->isChecked() ? new MirrorAction() : NULL);
428 void ApplicationWindow::HelpAbout(void)
434 void ApplicationWindow::Settings(void)
436 SettingsDialog dlg(this);
437 dlg.generalTab->antialiasChk->setChecked(drawing->useAntialiasing);
439 if (dlg.exec() == false)
442 // Deal with stuff here (since user hit "OK" button...)
443 drawing->useAntialiasing = dlg.generalTab->antialiasChk->isChecked();
449 // Group a bunch of selected objects (which can include other groups) together
450 // or ungroup a selected group.
452 void ApplicationWindow::HandleGrouping(void)
454 int itemsSelected = drawing->document.ItemsSelected();
456 // If nothing selected, do nothing
457 if (itemsSelected == 0)
459 statusBar()->showMessage(tr("No objects selected to make a group from."));
463 // If it's a group that's selected, ungroup it and leave the objects in a
465 if (itemsSelected == 1)
467 Object * object = drawing->document.SelectedItem(0);
471 printf("SelectedItem = NULL!\n");
473 printf("SelectedItem = %08X, type = %i\n", object, object->type);
476 if (object == NULL || object->type != OTContainer)
478 statusBar()->showMessage(tr("A group requires two or more selected objects."));
482 // Need the parent of the group, we're assuming here that the parent is
483 // the drawing's document. Does it matter? Maybe...
484 // Could just stipulate that grouping like this only takes place where the
485 // parent of the group is the drawing's document. Makes life much simpler.
486 ((Container *)object)->SelectAll();
487 ((Container *)object)->MoveContentsTo(&(drawing->document));
488 drawing->document.Delete(object);
489 statusBar()->showMessage(tr("Objects ungrouped."));
491 // Otherwise, if it's a group of 2 or more objects (which can be groups too)
492 // group them and select the group
493 else if (itemsSelected > 1)
495 Container * container = new Container(Vector(), &(drawing->document));
496 drawing->document.MoveSelectedContentsTo(container);
497 drawing->document.Add(container);
498 container->DeselectAll();
499 container->state = OSSelected;
500 statusBar()->showMessage(QString(tr("Grouped %1 objects.")).arg(itemsSelected));
507 void ApplicationWindow::HandleGridSizeInPixels(int size)
509 drawing->SetGridSize(size);
514 void ApplicationWindow::HandleGridSizeInBaseUnits(QString text)
518 double value = text.toDouble(&ok);
520 // Nothing parsable to a double, so quit...
521 if (!ok || value == 0)
524 // drawing->gridSpacing = value;
525 // Painter::zoom = drawing->gridPixels / drawing->gridSpacing;
526 Object::gridSpacing = value;
527 Painter::zoom = drawing->gridPixels / Object::gridSpacing;
528 drawing->UpdateGridBackground();
533 void ApplicationWindow::HandleDimensionSize(QString text)
537 double value = text.toDouble(&ok);
539 // Nothing parsable to a double, so quit...
540 if (!ok || value == 0)
543 drawing->document.ResizeAllDimensions(value);
544 // drawing->gridSpacing = value;
545 // Painter::zoom = drawing->gridPixels / drawing->gridSpacing;
546 // drawing->UpdateGridBackground();
551 void ApplicationWindow::CreateActions(void)
553 exitAct = CreateAction(tr("&Quit"), tr("Quit"), tr("Exits the application."),
554 QIcon(":/res/quit.png"), QKeySequence(tr("Ctrl+q")));
555 connect(exitAct, SIGNAL(triggered()), this, SLOT(close()));
557 snapToGridAct = CreateAction(tr("Snap To &Grid"), tr("Snap To Grid"), tr("Snaps mouse cursor to the visible grid when moving/creating objects."), QIcon(":/res/snap-to-grid-tool.png"), QKeySequence(tr("S")), true);
558 connect(snapToGridAct, SIGNAL(triggered()), this, SLOT(SnapToGridTool()));
560 fixAngleAct = CreateAction(tr("Fix &Angle"), tr("Fix Angle"), tr("Fixes the angle of an object."),
561 QIcon(":/res/fix-angle.png"), QKeySequence(tr("F,A")), true);
562 connect(fixAngleAct, SIGNAL(triggered()), this, SLOT(FixAngle()));
564 fixLengthAct = CreateAction(tr("Fix &Length"), tr("Fix Length"), tr("Fixes the length of an object."),
565 QIcon(":/res/fix-length.png"), QKeySequence(tr("F,L")), true);
566 connect(fixLengthAct, SIGNAL(triggered()), this, SLOT(FixLength()));
568 deleteAct = CreateAction(tr("&Delete"), tr("Delete Object"), tr("Deletes selected objects."), QIcon(":/res/delete-tool.png"), QKeySequence(tr("Delete")), true);
569 connect(deleteAct, SIGNAL(triggered()), this, SLOT(DeleteTool()));
571 addDimensionAct = CreateAction(tr("Add &Dimension"), tr("Add Dimension"), tr("Adds a dimension to the drawing."), QIcon(":/res/dimension-tool.png"), QKeySequence("D,I"), true);
572 connect(addDimensionAct, SIGNAL(triggered()), this, SLOT(DimensionTool()));
574 addLineAct = CreateAction(tr("Add &Line"), tr("Add Line"), tr("Adds lines to the drawing."), QIcon(":/res/add-line-tool.png"), QKeySequence("A,L"), true);
575 connect(addLineAct, SIGNAL(triggered()), this, SLOT(AddLineTool()));
577 addCircleAct = CreateAction(tr("Add &Circle"), tr("Add Circle"), tr("Adds circles to the drawing."), QIcon(":/res/add-circle-tool.png"), QKeySequence("A,C"), true);
578 connect(addCircleAct, SIGNAL(triggered()), this, SLOT(AddCircleTool()));
580 addArcAct = CreateAction(tr("Add &Arc"), tr("Add Arc"), tr("Adds arcs to the drawing."), QIcon(":/res/add-arc-tool.png"), QKeySequence("A,A"), true);
581 connect(addArcAct, SIGNAL(triggered()), this, SLOT(AddArcTool()));
583 addPolygonAct = CreateAction(tr("Add &Polygon"), tr("Add Polygon"), tr("Add polygons to the drawing."), QIcon(":/res/add-polygon-tool.png"), QKeySequence("A,P"), true);
584 connect(addPolygonAct, SIGNAL(triggered()), this, SLOT(AddPolygonTool()));
586 aboutAct = CreateAction(tr("About &Architektonas"), tr("About Architektonas"), tr("Gives information about this program."), QIcon(":/res/generic-tool.png"), QKeySequence());
587 connect(aboutAct, SIGNAL(triggered()), this, SLOT(HelpAbout()));
589 rotateAct = CreateAction(tr("&Rotate Objects"), tr("Rotate"), tr("Rotate object(s) around an arbitrary center."), QIcon(":/res/rotate-tool.png"), QKeySequence(tr("R,O")), true);
590 connect(rotateAct, SIGNAL(triggered()), this, SLOT(RotateTool()));
592 zoomInAct = CreateAction(tr("Zoom &In"), tr("Zoom In"), tr("Zoom in on the document."), QIcon(":/res/zoom-in.png"), QKeySequence(tr("+")), QKeySequence(tr("=")));
593 connect(zoomInAct, SIGNAL(triggered()), this, SLOT(ZoomInTool()));
595 zoomOutAct = CreateAction(tr("Zoom &Out"), tr("Zoom Out"), tr("Zoom out of the document."), QIcon(":/res/zoom-out.png"), QKeySequence(tr("-")));
596 connect(zoomOutAct, SIGNAL(triggered()), this, SLOT(ZoomOutTool()));
598 fileNewAct = CreateAction(tr("&New Drawing"), tr("New Drawing"), tr("Creates a new drawing."), QIcon(":/res/file-new.png"), QKeySequence(tr("Ctrl+n")));
599 connect(fileNewAct, SIGNAL(triggered()), this, SLOT(FileNew()));
601 fileOpenAct = CreateAction(tr("&Open Drawing"), tr("Open Drawing"), tr("Opens an existing drawing from a file."), QIcon(":/res/file-open.png"), QKeySequence(tr("Ctrl+o")));
602 connect(fileOpenAct, SIGNAL(triggered()), this, SLOT(FileOpen()));
604 fileSaveAct = CreateAction(tr("&Save Drawing"), tr("Save Drawing"), tr("Saves the current drawing to a file."), QIcon(":/res/file-save.png"), QKeySequence(tr("Ctrl+s")));
605 connect(fileSaveAct, SIGNAL(triggered()), this, SLOT(FileSave()));
607 fileSaveAsAct = CreateAction(tr("Save Drawing &As"), tr("Save As"), tr("Saves the current drawing to a file with a different name."), QIcon(":/res/file-save-as.png"), QKeySequence(tr("Ctrl+Shift+s")));
608 connect(fileSaveAsAct, SIGNAL(triggered()), this, SLOT(FileSaveAs()));
610 fileCloseAct = CreateAction(tr("&Close Drawing"), tr("Close Drawing"), tr("Closes the current drawing."), QIcon(":/res/file-close.png"), QKeySequence(tr("Ctrl+w")));
612 settingsAct = CreateAction(tr("&Settings"), tr("Settings"), tr("Change certain defaults for Architektonas."), QIcon(":/res/settings.png"), QKeySequence());
613 connect(settingsAct, SIGNAL(triggered()), this, SLOT(Settings()));
615 groupAct = CreateAction(tr("&Group"), tr("Group"), tr("Group/ungroup selected objects."), QIcon(":/res/group-tool.png"), QKeySequence("g"));
616 connect(groupAct, SIGNAL(triggered()), this, SLOT(HandleGrouping()));
618 connectAct = CreateAction(tr("&Connect"), tr("Connect"), tr("Connect objects at point."), QIcon(":/res/connect-tool.png"), QKeySequence("c,c"));
620 disconnectAct = CreateAction(tr("&Disconnect"), tr("Disconnect"), tr("Disconnect objects joined at point."), QIcon(":/res/disconnect-tool.png"), QKeySequence("d,d"));
622 mirrorAct = CreateAction(tr("&Mirror"), tr("Mirror"), tr("Mirror selected objects around a line."), QIcon(":/res/mirror-tool.png"), QKeySequence("m,i"), true);
623 connect(mirrorAct, SIGNAL(triggered()), this, SLOT(MirrorTool()));
626 //Hm. I think we'll have to have separate logic to do the "Radio Group Toolbar" thing...
627 // Yup, in order to turn them off, we'd have to have an "OFF" toolbar button. Ick.
628 /* QActionGroup * group = new QActionGroup(this);
629 group->addAction(deleteAct);
630 group->addAction(addDimensionAct);
631 group->addAction(addLineAct);
632 group->addAction(addCircleAct);
633 group->addAction(addArcAct);//*/
638 // Consolidates action creation from a multi-step process to a single-step one.
640 QAction * ApplicationWindow::CreateAction(QString name, QString tooltip, QString statustip,
641 QIcon icon, QKeySequence key, bool checkable/*= false*/)
643 QAction * action = new QAction(icon, name, this);
644 action->setToolTip(tooltip);
645 action->setStatusTip(statustip);
646 action->setShortcut(key);
647 action->setCheckable(checkable);
654 // This is essentially the same as the previous function, but this allows more
655 // than one key sequence to be added as key shortcuts.
657 QAction * ApplicationWindow::CreateAction(QString name, QString tooltip, QString statustip,
658 QIcon icon, QKeySequence key1, QKeySequence key2, bool checkable/*= false*/)
660 QAction * action = new QAction(icon, name, this);
661 action->setToolTip(tooltip);
662 action->setStatusTip(statustip);
663 QList<QKeySequence> keyList;
664 keyList.append(key1);
665 keyList.append(key2);
666 action->setShortcuts(keyList);
667 action->setCheckable(checkable);
673 void ApplicationWindow::CreateMenus(void)
675 QMenu * menu = menuBar()->addMenu(tr("&File"));
676 menu->addAction(fileNewAct);
677 menu->addAction(fileOpenAct);
678 menu->addAction(fileSaveAct);
679 menu->addAction(fileSaveAsAct);
680 menu->addAction(fileCloseAct);
681 menu->addSeparator();
682 menu->addAction(exitAct);
684 menu = menuBar()->addMenu(tr("&View"));
685 menu->addAction(zoomInAct);
686 menu->addAction(zoomOutAct);
688 menu = menuBar()->addMenu(tr("&Edit"));
689 menu->addAction(snapToGridAct);
690 menu->addAction(groupAct);
691 menu->addAction(fixAngleAct);
692 menu->addAction(fixLengthAct);
693 menu->addAction(rotateAct);
694 menu->addAction(mirrorAct);
695 menu->addAction(connectAct);
696 menu->addAction(disconnectAct);
697 menu->addSeparator();
698 menu->addAction(deleteAct);
699 menu->addSeparator();
700 menu->addAction(addLineAct);
701 menu->addAction(addCircleAct);
702 menu->addAction(addArcAct);
703 menu->addAction(addPolygonAct);
704 menu->addAction(addDimensionAct);
705 menu->addSeparator();
706 menu->addAction(settingsAct);
708 menu = menuBar()->addMenu(tr("&Help"));
709 menu->addAction(aboutAct);
713 void ApplicationWindow::CreateToolbars(void)
715 QToolBar * toolbar = addToolBar(tr("File"));
716 toolbar->setObjectName("File"); // Needed for saveState()
717 toolbar->addAction(fileNewAct);
718 toolbar->addAction(fileOpenAct);
719 toolbar->addAction(fileSaveAct);
720 toolbar->addAction(fileSaveAsAct);
721 toolbar->addAction(fileCloseAct);
722 // toolbar->addAction(exitAct);
724 toolbar = addToolBar(tr("View"));
725 toolbar->setObjectName("View");
726 toolbar->addAction(zoomInAct);
727 toolbar->addAction(zoomOutAct);
729 QSpinBox * spinbox = new QSpinBox;
730 toolbar->addWidget(spinbox);
731 // QLineEdit * lineedit = new QLineEdit;
732 toolbar->addWidget(baseUnitInput);
733 toolbar->addWidget(dimensionSizeInput);
735 toolbar = addToolBar(tr("Edit"));
736 toolbar->setObjectName("Edit");
737 toolbar->addAction(snapToGridAct);
738 toolbar->addAction(groupAct);
739 toolbar->addAction(fixAngleAct);
740 toolbar->addAction(fixLengthAct);
741 toolbar->addAction(rotateAct);
742 toolbar->addAction(mirrorAct);
743 toolbar->addAction(deleteAct);
744 toolbar->addAction(connectAct);
745 toolbar->addAction(disconnectAct);
746 toolbar->addSeparator();
747 toolbar->addAction(addLineAct);
748 toolbar->addAction(addCircleAct);
749 toolbar->addAction(addArcAct);
750 toolbar->addAction(addPolygonAct);
751 toolbar->addAction(addDimensionAct);
753 spinbox->setRange(4, 256);
754 spinbox->setValue(12);
755 baseUnitInput->setText("12");
756 connect(spinbox, SIGNAL(valueChanged(int)), this, SLOT(HandleGridSizeInPixels(int)));
757 connect(baseUnitInput, SIGNAL(textChanged(QString)), this, SLOT(HandleGridSizeInBaseUnits(QString)));
758 connect(dimensionSizeInput, SIGNAL(textChanged(QString)), this, SLOT(HandleDimensionSize(QString)));
762 void ApplicationWindow::ReadSettings(void)
764 QPoint pos = settings.value("pos", QPoint(200, 200)).toPoint();
765 QSize size = settings.value("size", QSize(400, 400)).toSize();
766 drawing->useAntialiasing = settings.value("useAntialiasing", true).toBool();
767 snapToGridAct->setChecked(settings.value("snapToGrid", true).toBool());
770 restoreState(settings.value("windowState").toByteArray());
774 void ApplicationWindow::WriteSettings(void)
776 settings.setValue("pos", pos());
777 settings.setValue("size", size());
778 settings.setValue("windowState", saveState());
779 settings.setValue("useAntialiasing", drawing->useAntialiasing);
780 settings.setValue("snapToGrid", snapToGridAct->isChecked());