Added some improvements
[flowchart-guider:flowchart-guider.git] / mybase.cpp
1 #include "mybase.h"\r
2 #include "myitem.h"\r
3 \r
4 void myMRU::setItems(const QString itms) {\r
5         p_items = itms.split("|",QString::SkipEmptyParts);\r
6         p_items.removeDuplicates();\r
7         while (p_items.count()>RECENT_COUNT) p_items.removeLast();\r
8 }\r
9 \r
10 void myMRU::addItem(const QString item) {\r
11     if (!item.isEmpty()) {\r
12         p_items.insert(0,QDir::toNativeSeparators(item));\r
13         p_items.removeDuplicates();\r
14         while (p_items.count()>RECENT_COUNT) p_items.removeLast();\r
15         emit refreshMRU();\r
16     }\r
17 }\r
18 \r
19 QStringList myMRU::items() {\r
20         return p_items;\r
21 }\r
22 \r
23 QString myMRU::itemsExport() {\r
24         return p_items.join("|");\r
25 }\r
26 \r
27 //////\r
28 \r
29 QString myBase::assignSuffix(const QString filename, const QString ext, const bool exactly) {\r
30     if (filename.isEmpty()==true)\r
31         return "";\r
32     else if (QFileInfo(filename).suffix()=="" || (exactly==true && QFileInfo(filename).suffix().toLower()!=ext.toLower()))\r
33         return filename+"."+ext;\r
34     else\r
35         return filename;\r
36 }\r
37 \r
38 QPoint decreasePoint(const QPoint i) {\r
39         return QPoint(i.x()/10,i.y()/10);\r
40 }\r
41 \r
42 myBase::myBase(QWidget * parentWidget, myGraphicsView * iViewer, QSettings * s) {\r
43         p_loading = false;\r
44         minItemHeight = BASE_MIN_ITEM_HEIGHT;\r
45         minItemWidth = BASE_MIN_ITEM_WIDTH;\r
46         zoomFactor = BASE_ZOOM_FACTOR;\r
47 \r
48         p_filename = "";\r
49         p_changed = false;\r
50         p_nextLock = false;\r
51 \r
52         parent = parentWidget;\r
53         viewer = iViewer;\r
54         connect(viewer,SIGNAL(openDroppedFile(const QString)),this,SLOT(slotOpenDroppedFile(const QString)));\r
55         finder = new myFinder();\r
56         MRU = new myMRU;\r
57         engine = new QScriptEngine();\r
58 \r
59         scene = new myScene(parent,this);\r
60         viewer->setScene(scene);\r
61         scene->addItem(&circle);\r
62 \r
63         circle.setZValue(9999);\r
64         circle.show();\r
65         circle.setPos(0,0);\r
66         circle.setVisible(false);\r
67 \r
68         ///////////////////////////////////\r
69         p_userBackgroundColor = QColor(s->value("dia/userBackgroundColor","#ffffff").toString());\r
70         p_userLineColor = QColor(s->value("dia/userLineColor","#000000").toString());\r
71         circle.setColor(QColor(s->value("dia/circleColor","#FF0000").toString()));\r
72 \r
73         p_defaultItemColor1 = QColor(s->value("dia/defaultItemColor1","#ffffff").toString());\r
74         p_defaultItemColor2 = QColor(s->value("dia/defaultItemColor2","#49B3E8").toString());\r
75         p_defaultItemBorderColor = QColor(s->value("dia/defaultItemBorderColor","#000000").toString());\r
76         p_defaultItemTextColor = QColor(s->value("dia/defaultItemTextColor","#000000").toString());\r
77         p_defaultItemTextSize = s->value("dia/defaultItemTextSize",10).toInt();\r
78 \r
79         p_selectedItemColor1 = QColor(s->value("dia/selectedItemColor1","#ffffff").toString());\r
80         p_selectedItemColor2 = QColor(s->value("dia/selectedItemColor2","#9FFF39").toString());\r
81         p_selectedItemBorderColor = QColor(s->value("dia/selectedItemBorderColor","#000000").toString());\r
82         p_selectedItemTextColor = QColor(s->value("dia/selectedItemTextColor","#000000").toString());\r
83 \r
84         p_activeItemColor1 = QColor(s->value("dia/activeItemColor1","#ff685d").toString());\r
85         p_activeItemColor2 = QColor(s->value("dia/activeItemColor2","#c90000").toString());\r
86         p_activeItemBorderColor = QColor(s->value("dia/activeItemBorderColor","#af0000").toString());\r
87         p_activeItemTextColor = QColor(s->value("dia/activeItemTextColor","#ffffff").toString());\r
88 \r
89         //////////////////////////////////////\r
90 \r
91         changedDelayTimer.setInterval(CHANGE_DELAY);\r
92         connect(&changedDelayTimer,SIGNAL(timeout()),this,SLOT(slotChangedDelay()));\r
93         p_stepInterval = (s->value("dia/timerInterval",BASE_DEFAULT_INTERVAL).toInt());\r
94         acZoom = 0;\r
95         undoBackIndex = 0;\r
96         scene->redrawBackground();\r
97 \r
98         connect(&animation,SIGNAL(valueChanged(QVariant)),this,SLOT(setToPos(QVariant)));\r
99 \r
100         init();\r
101 \r
102 }\r
103 \r
104 void myBase::init() {\r
105         p_lastID = 0;\r
106         p_activeItem = 0;\r
107         p_nextItem = 0;\r
108         noLines = false;\r
109         p_nextLock = false;\r
110         p_allowDragging = true;\r
111         p_lastContinueNum = 1;\r
112         setStatus(mba_edit);\r
113         setCanvasSize(BASE_CANVAS_WIDTH,BASE_CANVAS_HEIGHT);\r
114 }\r
115 \r
116 myBase::~myBase() {\r
117 \r
118         //newFile();\r
119         stopAnimation();\r
120         setPlayAction(mpa_stop);\r
121 \r
122         QSettings s(APP,APP);\r
123         s.setValue("dia/timerInterval",p_stepInterval);\r
124 \r
125         s.setValue("dia/userBackgroundColor",p_userBackgroundColor.name());\r
126         s.setValue("dia/userLineColor",p_userLineColor.name());\r
127         s.setValue("dia/circleColor",circleColor().name());\r
128 \r
129         s.setValue("dia/defaultItemColor1",p_defaultItemColor1.name());\r
130         s.setValue("dia/defaultItemColor2",p_defaultItemColor2.name());\r
131         s.setValue("dia/defaultItemBorderColor",p_defaultItemBorderColor.name());\r
132         s.setValue("dia/defaultItemTextColor",p_defaultItemTextColor.name());\r
133 \r
134         s.setValue("dia/selectedItemColor1",p_selectedItemColor1.name());\r
135         s.setValue("dia/selectedItemColor2",p_selectedItemColor2.name());\r
136         s.setValue("dia/selectedItemBorderColor",p_selectedItemBorderColor.name());\r
137         s.setValue("dia/selectedItemTextColor",p_selectedItemTextColor.name());\r
138 \r
139         s.setValue("dia/activeItemColor1",p_activeItemColor1.name());\r
140         s.setValue("dia/activeItemColor2",p_activeItemColor2.name());\r
141         s.setValue("dia/activeItemBorderColor",p_activeItemBorderColor.name());\r
142         s.setValue("dia/activeItemTextColor",p_activeItemTextColor.name());\r
143 \r
144         s.sync();\r
145 \r
146         items.clear();\r
147         delete engine;\r
148         delete finder;\r
149         delete MRU;\r
150 }\r
151 \r
152 void myBase::setCanvasSize(const int iWidth,const int iHeight) {\r
153         if (iHeight<BASE_MIN_CANVAS_HEIGHT)\r
154             p_canvasHeight = BASE_MIN_CANVAS_HEIGHT;\r
155         else\r
156             p_canvasHeight = iHeight;\r
157 \r
158         if (iWidth<BASE_MIN_CANVAS_WIDTH)\r
159             p_canvasWidth = BASE_MIN_CANVAS_WIDTH;\r
160         else\r
161             p_canvasWidth = iWidth;\r
162         finder->setNums(canvasWidth(),canvasHeight());\r
163         scene->setSceneRect(0,0,canvasWidth(),canvasHeight());\r
164 }\r
165 \r
166 void myBase::addItem(const myItemType iItemType) {\r
167         if (iItemType==mit_startpoint || iItemType==mit_endpoint)\r
168             if (numOf(iItemType)>0) {\r
169                 QMessageBox::warning(parent,BASE_CANNOT_ADD_TITLE,BASE_CANNOT_ADD,QMessageBox::Ok,NULL);\r
170                 return;\r
171         }\r
172 \r
173         addItemType = iItemType;\r
174         setStatus(mba_add);\r
175 }\r
176 \r
177 void myBase::cancelAddingItem() {\r
178      setStatus(mba_edit);\r
179 }\r
180 \r
181 void myBase::addItemDone(const double iX, const double iY,const QString settings) {\r
182         myItemType itmType;\r
183         if (!settings.isEmpty()) {\r
184                 itmType = myItemType(settings.split("|").at(1).toInt());\r
185                 if (itmType==mit_continue_a) if (findFirst(mit_continue_a,settings.split("|").at(6))!=0) return;\r
186                 if (itmType==mit_continue_b) if (findFirst(mit_continue_b,settings.split("|").at(6))!=0) return;\r
187         } else\r
188                 itmType = addItemType;\r
189 \r
190 \r
191         if (!((itmType==mit_startpoint && numOf(mit_startpoint)>0) || (itmType==mit_endpoint && numOf(mit_endpoint)>0))) {\r
192                 myItem * itm;\r
193                 itm = new myItem(itmType,this,lastID());\r
194                 p_lastID++;\r
195 \r
196                 itm->setSize(0,0);\r
197                 itm->setPos(int(iX/10)*10,int(iY/10)*10);\r
198 \r
199                 if (!settings.isEmpty()) itm->importSettings(settings,false);\r
200 \r
201                 itm->show();\r
202                 scene->addItem(itm);\r
203                 items.append(itm);\r
204 \r
205                 if (itm->itemType()==mit_continue_a && settings.isEmpty()) { // pouze pokud pridavame novy (ne ze souboru ci schranky)\r
206                         addItemType = mit_continue_b;\r
207                         addItemDone(iX+minItemHeight+10,iY);\r
208                         incLastContinueNum();\r
209                 }\r
210                 setChanged(true);\r
211 \r
212         }\r
213         setStatus(mba_edit);\r
214 }\r
215 \r
216 void myBase::addItemWithoutAnyCheck(const QXmlStreamAttributes settings) {\r
217         if (!settings.isEmpty()) {\r
218                 myItemType itmType;\r
219                 itmType = myItemType(settings.value("itemType").toString().toInt());\r
220                 myItem * itm;\r
221                 itm = new myItem(itmType,this,lastID());\r
222                 itm->importSettings(settings);\r
223                 itm->show();\r
224                 scene->addItem(itm);\r
225                 items.append(itm);\r
226         }\r
227 }\r
228 \r
229 void myBase::addItemWithoutAnyCheck(const QString settings) {\r
230         if (!settings.isEmpty()) {\r
231                 myItemType itmType;\r
232                 itmType = myItemType(settings.split("|").at(1).toInt());\r
233                 myItem * itm;\r
234                 itm = new myItem(itmType,this,lastID());\r
235                 itm->importSettings(settings,true);\r
236                 itm->show();\r
237                 scene->addItem(itm);\r
238                 items.append(itm);\r
239         }\r
240 }\r
241 \r
242 void myBase::setMode(const myMode mode) {\r
243         if (mode == mm_edit) setStatus(mba_edit);\r
244         else if (mode == mm_view) {\r
245                 scene->clearSelection();\r
246                 setStatus(mba_noEdit);\r
247         }\r
248         scene->redrawAllItems();\r
249 }\r
250 \r
251 void myBase::setAllowDragging(const bool i) {\r
252         p_allowDragging = i;\r
253         if (i)\r
254                 viewer->setDragMode(QGraphicsView::RubberBandDrag);\r
255         else\r
256                 viewer->setDragMode(QGraphicsView::NoDrag);\r
257 }\r
258 \r
259 myItem * myBase::findItem(const int id) {\r
260         QList<myItem *>::iterator i;\r
261         for (i = items.begin(); i!=items.end(); i++) {\r
262                 myItem * v = *i;\r
263                 if (v->id() == id) return v;\r
264         }\r
265         return 0;\r
266 }\r
267 \r
268 myItem * myBase::findFirstSelected() {\r
269         if (scene->selectedItems().count()==0) return 0;\r
270         int i = 0;\r
271         myItem * itm = dynamic_cast<myItem*>(scene->selectedItems().at(i));\r
272         while (itm==NULL) {\r
273                 i++;\r
274                 itm = dynamic_cast<myItem*>(scene->selectedItems().at(i));\r
275         }\r
276         return itm;\r
277 }\r
278 \r
279 myItem * myBase::findFirst(const myItemType iItemType) {\r
280         QList<myItem *>::iterator i;\r
281         for (i = items.begin(); i!=items.end(); i++) {\r
282                 myItem * v = *i;\r
283                 if (v->itemType()==iItemType) return v;\r
284         }\r
285         return 0;\r
286 }\r
287 \r
288 myItem * myBase::findFirst(const myItemType iItemType, const QString iText) {\r
289         QList<myItem *>::iterator i;\r
290         for (i = items.begin(); i!=items.end(); i++) {\r
291                 myItem * v = *i;\r
292                 if (v->itemType()==iItemType && v->text()==iText) return v;\r
293         }\r
294         return 0;\r
295 }\r
296 \r
297 void myBase::deleteItem(const int id) { // nepoužívat přímo !!! Mazat objekty, přes myItem.delete();\r
298         QList<myItem *>::iterator i;\r
299         for (i = items.begin(); i!=items.end(); i++) {\r
300                 myItem * v = *i;\r
301                 if (v->id() == id) {\r
302                         items.removeAt(items.indexOf(*i));\r
303                         delete v->lineM;\r
304                         delete v->lineP;\r
305                         delete v;\r
306                         return;\r
307                 }\r
308         }\r
309 }\r
310 \r
311 QString myBase::itemTypeToStr(const myItemType iItemType) {\r
312         if (iItemType == mit_command)\r
313                 return BASE_COMMAND;\r
314         else if (iItemType == mit_inout)\r
315                 return BASE_INOUT;\r
316         else if (iItemType == mit_startpoint)\r
317                 return BASE_START;\r
318         else if (iItemType == mit_endpoint)\r
319                 return BASE_END;\r
320         else if (iItemType == mit_condition)\r
321                 return BASE_CONDITION;\r
322         else if (iItemType == mit_continue_a)\r
323                 return BASE_CONTINUE_IN;\r
324         else if (iItemType == mit_continue_b)\r
325                 return BASE_CONTINUE_OUT;\r
326         else if (iItemType == mit_text)\r
327                 return BASE_LABEL;\r
328         else\r
329                 return "";\r
330 }\r
331 \r
332 int myBase::numOf(const myItemType iItemType) {\r
333         int count = 0;\r
334         QList<myItem *>::iterator i;\r
335         for (i = items.begin(); i!=items.end(); i++) {\r
336                 myItem * v = *i;\r
337                 if (v->itemType() == iItemType) count++;\r
338         }\r
339         return count;\r
340 }\r
341 \r
342 void myBase::updateInLinesFrom(const int iID) {\r
343         QList<myItem *>::iterator i;\r
344         for (i = items.begin(); i!=items.end(); i++) {\r
345                 myItem * v = *i;\r
346                 if (v->dest_m() == iID || v->dest_p() == iID) v->updateOutLines();\r
347         }\r
348 }\r
349 \r
350 void myBase::updateLinesForSelected() {\r
351         for (int i=0; i<scene->selectedItems().count(); i++) {\r
352                 myItem * v = dynamic_cast<myItem*>(scene->selectedItems().at(i));\r
353                 if ((v!=NULL) && v->itemType()!=mit_text) v->updateLines();\r
354         }\r
355 }\r
356 \r
357 void myBase::deleteLinesWhereID(const int iID) {\r
358         QList<myItem *>::iterator i;\r
359         for (i = items.begin(); i!=items.end(); i++) {\r
360                 myItem * v = *i;\r
361                 if (v->dest_p() == iID) v->disconnect(false);\r
362                 if (v->dest_m() == iID) v->disconnect(true);\r
363         }\r
364 }\r
365 \r
366 QString myBase::exportSettings() {\r
367         QString settings;\r
368 \r
369         settings.append(QString::number(p_lastID)+"|");         // lastID\r
370         settings.append(QString::number(p_lastContinueNum)+"|"); // lastContinueNum\r
371         settings.append(QString::number(p_canvasHeight)+"|");   // canvasHeight\r
372         settings.append(QString::number(p_canvasWidth)+"|");    // canvasWidth\r
373 \r
374         settings.append(p_userBackgroundColor.name()+"|");      // backgroundColor\r
375         settings.append(p_userLineColor.name()+"|");      // lineColor\r
376 \r
377         settings.append(p_selectedItemBorderColor.name()+"|");  // selectedBorderColor\r
378         settings.append(p_selectedItemColor1.name()+"|");   // selectedItemColor1\r
379         settings.append(p_selectedItemColor2.name()+"|");   // selectedItemColor2\r
380         settings.append(p_selectedItemTextColor.name()+"|");    // selectedTextColor\r
381 \r
382         settings.append(p_defaultItemBorderColor.name()+"|");     // defaultBorderColor\r
383         settings.append(p_defaultItemColor1.name()+"|");      // defaultItemColor1\r
384         settings.append(p_defaultItemColor2.name()+"|");      // defaultItemColor2\r
385         settings.append(p_defaultItemTextColor.name()+"|");       // defaultTextColor\r
386         settings.append(QString::number(p_defaultItemTextSize)+"|");       // defaultTextSize\r
387 \r
388         settings.append(p_activeItemBorderColor.name()+"|"); // ActiveItemBorderColor\r
389         settings.append(p_activeItemColor1.name()+"|");      // ActiveItemColor1\r
390         settings.append(p_activeItemColor2.name()+"|");      // ActiveItemColor2\r
391         settings.append(p_activeItemTextColor.name()+"|");   // userActiveItemTextColor\r
392 \r
393         settings.append(QString::number(p_stepInterval)+"|");   // stepTimer -> interval\r
394         settings.append(circleColor().name()+"|");\r
395 \r
396         return settings;\r
397 }\r
398 \r
399 void myBase::exportSettings(QXmlStreamWriter *xml) {\r
400     xml->writeStartElement("document");\r
401 \r
402     xml->writeAttribute("lastID",QString::number(p_lastID));\r
403     xml->writeAttribute("lastContinueNum",QString::number(p_lastContinueNum));\r
404     xml->writeAttribute("canvasHeight",QString::number(p_canvasHeight));\r
405     xml->writeAttribute("canvasWidth",QString::number(p_canvasWidth));\r
406 \r
407     xml->writeAttribute("userBackgroundColor",p_userBackgroundColor.name());\r
408     xml->writeAttribute("userLineColor",p_userLineColor.name());\r
409     xml->writeAttribute("circleColor",circleColor().name());\r
410 \r
411     xml->writeAttribute("selectedItemBorderColor",p_selectedItemBorderColor.name());\r
412     xml->writeAttribute("selectedItemColor1",p_selectedItemColor1.name());\r
413     xml->writeAttribute("selectedItemColor2",p_selectedItemColor2.name());\r
414     xml->writeAttribute("selectedItemTextColor",p_selectedItemTextColor.name());\r
415 \r
416     xml->writeAttribute("defaultItemBorderColor",p_defaultItemBorderColor.name());\r
417     xml->writeAttribute("defaultItemColor1",p_defaultItemColor1.name());\r
418     xml->writeAttribute("defaultItemColor2",p_defaultItemColor2.name());\r
419     xml->writeAttribute("defaultItemTextColor",p_defaultItemTextColor.name());\r
420     xml->writeAttribute("defaultItemTextSize",QString::number(p_defaultItemTextSize));\r
421 \r
422     xml->writeAttribute("activeItemBorderColor",p_activeItemBorderColor.name());\r
423     xml->writeAttribute("activeItemColor1",p_activeItemColor1.name());\r
424     xml->writeAttribute("activeItemColor2",p_activeItemColor2.name());\r
425     xml->writeAttribute("activeItemTextColor",p_activeItemTextColor.name());\r
426     xml->writeAttribute("stepTimerInterval",QString::number(p_stepInterval));\r
427 \r
428     xml->writeEndElement();\r
429 }\r
430 \r
431 void myBase::importSettings(const QString settings) {\r
432         if (!settings.isEmpty()) {\r
433                 QStringList sl = settings.split("|");\r
434 \r
435                 p_lastID = sl.at(0).toInt();\r
436                 p_lastContinueNum = sl.at(1).toInt();\r
437                 p_canvasHeight = sl.at(2).toInt();\r
438                 p_canvasWidth = sl.at(3).toInt();\r
439 \r
440                 p_userBackgroundColor = QColor(sl.at(4));\r
441                 p_userLineColor = QColor(sl.at(5));\r
442                 circle.setColor(QColor(sl.at(20)));\r
443 \r
444                 p_selectedItemBorderColor = QColor(sl.at(6));\r
445                 p_selectedItemColor1 = QColor(sl.at(7));\r
446                 p_selectedItemColor2 = QColor(sl.at(8));\r
447                 p_selectedItemTextColor = QColor(sl.at(9));\r
448 \r
449                 p_defaultItemBorderColor = QColor(sl.at(10));\r
450                 p_defaultItemColor1 = QColor(sl.at(11));\r
451                 p_defaultItemColor2 = QColor(sl.at(12));\r
452                 p_defaultItemTextColor = QColor(sl.at(13));\r
453                 p_defaultItemTextSize = sl.at(14).toInt();\r
454 \r
455                 p_activeItemBorderColor = QColor(sl.at(15));\r
456                 p_activeItemColor1 = QColor(sl.at(16));\r
457                 p_activeItemColor2 = QColor(sl.at(17));\r
458                 p_activeItemTextColor = QColor(sl.at(18));\r
459 \r
460                 p_stepInterval = (sl.at(19).toInt());\r
461         }\r
462 \r
463 }\r
464 \r
465 void myBase::importSettings(const QXmlStreamAttributes attr) {\r
466     p_lastID = attr.value("lastID").toString().toInt();\r
467     p_lastContinueNum = attr.value("lastContinueNum").toString().toInt();\r
468     p_canvasHeight = attr.value("canvasHeight").toString().toInt();\r
469     p_canvasWidth = attr.value("canvasWidth").toString().toInt();\r
470 \r
471     p_userBackgroundColor = QColor(attr.value("userBackgroundColor").toString());\r
472     p_userLineColor = QColor(attr.value("userLineColor").toString());\r
473     circle.setColor(QColor(attr.value("circleColor").toString()));\r
474 \r
475     p_selectedItemBorderColor = QColor(attr.value("selectedItemBorderColor").toString());\r
476     p_selectedItemColor1 = QColor(attr.value("selectedItemColor1").toString());\r
477     p_selectedItemColor2 = QColor(attr.value("selectedItemColor2").toString());\r
478     p_selectedItemTextColor = QColor(attr.value("selectedItemTextColor").toString());\r
479 \r
480     p_defaultItemBorderColor = QColor(attr.value("defaultItemBorderColor").toString());\r
481     p_defaultItemColor1 = QColor(attr.value("defaultItemColor1").toString());\r
482     p_defaultItemColor2 = QColor(attr.value("defaultItemColor2").toString());\r
483     p_defaultItemTextColor = QColor(attr.value("defaultItemTextColor").toString());\r
484     p_defaultItemTextSize = attr.value("defaultItemTextSize").toString().toInt();\r
485 \r
486     p_activeItemBorderColor = QColor(attr.value("activeItemBorderColor").toString());\r
487     p_activeItemColor1 = QColor(attr.value("activeItemColor1").toString());\r
488     p_activeItemColor2 = QColor(attr.value("activeItemColor2").toString());\r
489     p_activeItemTextColor = QColor(attr.value("activeItemTextColor").toString());\r
490     p_stepInterval = (attr.value("stepTimerInterval").toString().toInt());\r
491 \r
492 }\r
493 \r
494 void myBase::removeAll() {\r
495         for (int i=items.count(); i<items.count() ; i++)\r
496                 items.at(i)->hardDisconnect();\r
497         for (int i=items.count(); i>0 ; i--)\r
498                 items.last()->remove(true);\r
499 }\r
500 \r
501 void myBase::newFile(const bool b_makeUndoPoint) {\r
502         setPlayAction(mpa_stop);\r
503         removeAll();\r
504         undoList.clear();\r
505         undoBackIndex = 0;\r
506         p_filename = "";\r
507         init();\r
508         zoomToDefault();\r
509         setChanged(false);\r
510         if (b_makeUndoPoint) makeUndoPoint(false);\r
511         emit clearVarViewer();\r
512         emit updateDocumentSettings();\r
513         emit updateWindowTitle();\r
514 }\r
515 \r
516 bool myBase::saveFile(const QString filename) {\r
517     QString flname = assignSuffix(filename,"fcg",true);\r
518     QFile data(flname);\r
519     QList<myItem *>::iterator i;\r
520     myItem * v;\r
521     if (data.open(QFile::WriteOnly | QFile::Truncate)) {\r
522             QTextStream out(&data);\r
523             out.setCodec("UTF-8");\r
524             QXmlStreamWriter xml(&data);\r
525             xml.setAutoFormatting(true);\r
526             xml.writeStartDocument();\r
527             xml.writeDTD("<!DOCTYPE "+QString(XML_DOCTYPE)+">");\r
528             xml.writeStartElement(QString(XML_DOCTYPE));\r
529             xml.writeAttribute("version",QString::number(VERSION0)+"."+QString::number(VERSION1)+"."+QString::number(VERSION2));\r
530             exportSettings(&xml);\r
531             for (i = items.begin() ; i<items.end() ; i++) {\r
532                                 v = *i;\r
533                                 v->exportSettings(&xml);\r
534             }\r
535             xml.writeEndElement();\r
536 \r
537             p_filename = QDir::toNativeSeparators(flname);\r
538             MRU->addItem(p_filename);\r
539             setChanged(false);\r
540 \r
541             emit updateWindowTitle();\r
542             emit fileSaved();\r
543             return true;\r
544         } else {\r
545             QMessageBox::warning(parent,ERR,CANT_SAVE,QMessageBox::Close,QMessageBox::Cancel);\r
546             return false;\r
547         }\r
548 \r
549 }\r
550 \r
551 QRectF myBase::objectsFrame() {\r
552     QRectF frame = finder->getActiveRect();\r
553     qreal y1 = frame.top();\r
554     qreal x1 = frame.left();\r
555     qreal y2 = frame.bottom();\r
556     qreal x2 = frame.right();\r
557 \r
558     QList<myItem *>::iterator i;\r
559     QRectF rct;\r
560     for (i = items.begin(); i!=items.end(); i++) {\r
561             myItem * v = *i;\r
562             if (v->itemType()==mit_text) {\r
563                 rct = v->positionRect();\r
564                 if (rct.top()<y1) y1 = rct.top() - 10;\r
565                 if (rct.left()<x1) x1 = rct.left() - 10;\r
566                 if (rct.bottom()>y2) y2 = rct.bottom() + 10;\r
567                 if (rct.right()>x2) x2 = rct.right() + 10;\r
568             }\r
569     }\r
570     if (y1<0) y1 = 0;\r
571     if (x1<0) x1 = 0;\r
572     if (y2>canvasHeight()) y2 = canvasHeight();\r
573     if (x2>canvasWidth()) x2 = canvasWidth();\r
574 \r
575     return QRectF(x1,y1,x2-x1,y2-y1);\r
576 }\r
577 \r
578 void myBase::print() {\r
579         QPrinter printer(QPrinter::HighResolution);\r
580         printer.setDocName(QFileInfo(p_filename).fileName());\r
581         printer.setCreator(BASE_PRINT_CREATOR);\r
582         printer.setOrientation( QPrinter::Landscape );\r
583         QPrintDialog dialog( &printer );\r
584         if ( dialog.exec() ) {\r
585                 QPainter painter( &printer );\r
586                 QRectF frame(objectsFrame());\r
587                 scene->render( &painter,painter.clipRegion().boundingRect(),frame);\r
588         }\r
589 }\r
590 \r
591 void myBase::exportToImage() {\r
592         exportToImage2(QFileDialog::getSaveFileName(viewer, BASE_EXPORT_IMAGE,"", BASE_IMAGE_FILTER));\r
593 }\r
594 \r
595 void myBase::exportToImage2(const QString filename) {\r
596         if (!filename.isEmpty()) {\r
597                 QString filename2 = assignSuffix(filename,"png");\r
598                 QRectF frame(objectsFrame());\r
599                 QImage image(frame.size().toSize(), QImage::Format_RGB32 );\r
600                 QPainter painter(&image);\r
601                 painter.fillRect(frame,QBrush(p_userBackgroundColor));\r
602                 scene->render(&painter,QRectF(QPoint(0,0),frame.size()),frame);\r
603                 if (!image.save(filename2))\r
604                         QMessageBox::information(NULL,ERR,CANT_SAVE,QMessageBox::Cancel,QMessageBox::Cancel);\r
605         }\r
606 }\r
607 \r
608 bool myBase::openFile(const QString flname) {\r
609     if (flname.isEmpty()) return true;\r
610     QFile data(flname);\r
611     if (data.open(QFile::ReadOnly | QIODevice::Text)) {\r
612         p_loading = true;\r
613         QTextStream in(&data);\r
614         in.setCodec("UTF-8");\r
615         newFile(false);\r
616         QXmlStreamReader xml;\r
617         xml.setDevice(&data);\r
618         if (xml.readNextStartElement()) {\r
619             if (xml.name() == XML_DOCTYPE) {\r
620                 QStringList version = xml.attributes().value("version").toString().split(".");\r
621                 if (version.at(0).toInt()==VERSION0 && version.at(1).toInt()<=VERSION1) {\r
622 \r
623                     while (!xml.atEnd()) {\r
624                         xml.readNextStartElement();\r
625                         if (xml.name() == "document")\r
626                         {\r
627                             importSettings(xml.attributes());\r
628                             xml.readNext();\r
629                         }\r
630                         else if (xml.name() == "item")\r
631                         {\r
632                             addItemWithoutAnyCheck(xml.attributes());\r
633                             xml.readNext();\r
634                         }\r
635                         else\r
636                             xml.skipCurrentElement();\r
637 \r
638                     }\r
639 \r
640                 } else QMessageBox::warning(NULL,ERR,QObject::tr("Aplikace je příliš zasralá, tento dokument byl vytvořen v novější verzi."),QMessageBox::Cancel,QMessageBox::Ok);\r
641             }\r
642             else\r
643                  QMessageBox::warning(NULL,ERR,QObject::tr("Nepodporovaný soubor!"),QMessageBox::Cancel,QMessageBox::Ok);\r
644         }\r
645         data.close();\r
646         p_filename = flname;\r
647         setChanged(false);\r
648         undoList.clear();\r
649         undoBackIndex = 0;\r
650         makeUndoPoint(false);\r
651         p_loading = false;\r
652         scene->redrawAllLines();\r
653         scene->redrawBackground();\r
654         updatePathways();\r
655         emit updateDocumentSettings();\r
656         MRU->addItem(flname);\r
657         return true;\r
658     } else return false ;\r
659 }\r
660 \r
661 bool myBase::continueWithFileOp() {\r
662         QMessageBox msgBox;\r
663         msgBox.setWindowTitle(CONTINUE_TITLE);\r
664         msgBox.setText(CONTINUE_TEXT);\r
665         msgBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No);\r
666         msgBox.setDefaultButton(QMessageBox::No);\r
667         return (msgBox.exec() == QMessageBox::Yes);\r
668 }\r
669 \r
670 void myBase::gotoItem() {\r
671     zoomToDefault();\r
672     if (scene->selectedItems().count()>0)\r
673           scene->selectedItems().at(0)->ensureVisible();\r
674     else if (items.count()>0)\r
675       items.at(0)->ensureVisible();\r
676 \r
677 }\r
678 \r
679 void myBase::slotNewFile() {\r
680         if (changed()) if (!continueWithFileOp()) return;\r
681         newFile();\r
682 }\r
683 \r
684 void myBase::slotOpenFile() {\r
685         if (changed()) if (!continueWithFileOp()) return;\r
686 \r
687         QFileDialog dialog(viewer->parentWidget());\r
688         dialog.setAcceptMode(QFileDialog::AcceptOpen);\r
689         dialog.setFileMode(QFileDialog::ExistingFile);\r
690         dialog.setNameFilter(FILE_NAME_FILTER);\r
691         dialog.setViewMode(QFileDialog::Detail);\r
692 \r
693         if (dialog.exec() && dialog.selectedFiles().count()==1)\r
694                 openFile(dialog.selectedFiles().at(0));\r
695         MRU->refresh();\r
696 }\r
697 \r
698 void myBase::slotSaveFile() {\r
699         if (p_filename=="") slotSaveFileAs();\r
700         else saveFile(p_filename);\r
701 }\r
702 \r
703 void myBase::slotSaveFileAs() {\r
704         QFileDialog dialog(viewer->parentWidget());\r
705         dialog.setAcceptMode(QFileDialog::AcceptSave);\r
706         dialog.setFileMode(QFileDialog::AnyFile);\r
707         dialog.setFilter(FILE_NAME_FILTER);\r
708         dialog.setViewMode(QFileDialog::Detail);\r
709 \r
710         if (dialog.exec())\r
711                 saveFile(dialog.selectedFiles().at(0));\r
712 }\r
713 \r
714 \r
715 void myBase::setStatus(const myBaseAction action) {\r
716         if ((!(action==mba_add && status()==mba_noEdit)))\r
717 \r
718         // && (!((action==mba_edit || action==mba_add) && playAction()!=mpa_stop))\r
719         {\r
720                 noLines = false;\r
721                 p_status = action;\r
722                 if (status()==mba_add) {\r
723                         viewer->setAcceptDrops(false);\r
724                         viewer->setDragMode(QGraphicsView::NoDrag);\r
725                 } else if (status()==mba_noEdit) {\r
726                         scene->selectNone();\r
727                         viewer->setAcceptDrops(false);\r
728                         viewer->setDragMode(QGraphicsView::NoDrag);\r
729                 } else if (status()==mba_edit) {\r
730                         setPlayAction(mpa_stop);\r
731                         viewer->setAcceptDrops(true);\r
732                         viewer->setDragMode(QGraphicsView::RubberBandDrag);\r
733                 }\r
734                 emit statusUpdated(status());\r
735         }\r
736 }\r
737 \r
738 // CFNC\r
739 QScriptValue show(QScriptContext *context, QScriptEngine *engine) {\r
740         Q_UNUSED(engine);\r
741         QScriptValue a = context->argument(0);\r
742         QMessageBox::information(NULL,CFNC_show,a.toString(),QMessageBox::Ok,QMessageBox::Ok);\r
743         return "";\r
744 }\r
745 \r
746 QScriptValue getNumber(QScriptContext *context, QScriptEngine *engine) {\r
747         Q_UNUSED(engine);\r
748         QScriptValue a = context->argument(0);\r
749         QString text = CFNC_getNumber;\r
750         if (!a.isUndefined()) text = a.toString();\r
751         double i = QInputDialog::getInteger(NULL,CFNC_getNumber,text);\r
752         return i;\r
753 }\r
754 \r
755 QScriptValue getText(QScriptContext *context, QScriptEngine *engine) {\r
756         Q_UNUSED(engine);\r
757         QScriptValue a = context->argument(0);\r
758         QString text = CFNC_getText;\r
759         if (!a.isUndefined()) text = a.toString();\r
760         return QInputDialog::getText(NULL,CFNC_getText,text);\r
761 }\r
762 \r
763 QScriptValue getFloat(QScriptContext *context, QScriptEngine *engine) {\r
764         Q_UNUSED(engine);\r
765         QScriptValue a = context->argument(0);\r
766         QString text = CFNC_getFloat;\r
767         if (!a.isUndefined()) text = a.toString();\r
768         double d = QInputDialog::getDouble(NULL,CFNC_getFloat,text);\r
769         return d;\r
770 }\r
771 \r
772 QScriptValue addLog(QScriptContext *context, QScriptEngine *engine) {\r
773         Q_UNUSED(engine);\r
774         QScriptValue a = context->argument(0);\r
775         myBase * base = dynamic_cast<myBase*>(engine->parent());\r
776         if (base!=NULL) {\r
777                 base->callLogViewerAdd(a.toString().toAscii());\r
778                 return true;\r
779         } else\r
780                 return false;\r
781 }\r
782 \r
783 QScriptValue ask(QScriptContext *context, QScriptEngine *engine) {\r
784         Q_UNUSED(engine);\r
785         QScriptValue a = context->argument(0);\r
786         return (QMessageBox::question(NULL,CFNC_ask,a.toString(),QMessageBox::Yes | QMessageBox::No,QMessageBox::Yes) == QMessageBox::Yes);\r
787 }\r
788 \r
789 void myBase::setPlayAction(myPlayAction act) {\r
790         if (act!=mpa_stop) setStatus(mba_noEdit);\r
791         p_nextLock  = false;\r
792         if (act==mpa_start && numOf(mit_startpoint)==0)\r
793                 QMessageBox::information(0,ERR,BASE_NO_START,0,0);\r
794         else {\r
795 \r
796                 if (act==mpa_start && playAction()!=mpa_pause && playAction()!=mpa_start) {\r
797                         p_playAction = act;\r
798                         delete engine;\r
799                         engine = new QScriptEngine(this);\r
800 \r
801                         // pridani vlastnich funkci\r
802                         QScriptValue v_show = engine->newFunction(show);\r
803                         engine->globalObject().setProperty("show",v_show);\r
804 \r
805                         QScriptValue v_getNumber = engine->newFunction(getNumber);\r
806                         engine->globalObject().setProperty("getNumber",v_getNumber);\r
807 \r
808                         QScriptValue v_getFloat = engine->newFunction(getFloat);\r
809                         engine->globalObject().setProperty("getFloat",v_getFloat);\r
810 \r
811                         QScriptValue v_getText = engine->newFunction(getText);\r
812                         engine->globalObject().setProperty("getText",v_getText);\r
813 \r
814                         QScriptValue v_addLog = engine->newFunction(addLog);\r
815                         engine->globalObject().setProperty("addLog",v_addLog);\r
816 \r
817                         QScriptValue v_ask = engine->newFunction(ask);\r
818                         engine->globalObject().setProperty("ask",v_ask);\r
819 \r
820                         emit clearVarViewer();\r
821 ;\r
822                         next();\r
823                 } else if (act==mpa_start && playAction()==mpa_pause) {\r
824                         p_playAction = act;\r
825                         next();\r
826                 } else if (act==mpa_stop) {\r
827                         p_playAction = act;\r
828                         animationPath.clear();\r
829                         stopAnimation();\r
830                         deactivateIt();\r
831                         p_activeItem = 0;\r
832                         p_nextItem = 0;\r
833                 } else if (act==mpa_pause && playAction()!=mpa_pause) {\r
834                         p_playAction = act;\r
835                         stopAnimation();\r
836                 } else if (act==mpa_pause && playAction()==mpa_pause) {\r
837                         setPlayAction(mpa_start);\r
838                 }\r
839 \r
840         }\r
841         emit playActionUpdated();\r
842 }\r
843 \r
844 void myBase::deactivateIt() {\r
845         if (p_activeItem!=0) p_activeItem->deactivate();\r
846 }\r
847 \r
848 void myBase::next() {\r
849         p_nextLock = true;\r
850         if (playAction()==mpa_stop) {\r
851                 setPlayAction(mpa_start);\r
852                 if (!p_playNext)\r
853                     setPlayAction(mpa_pause);\r
854                 return;\r
855         }\r
856 \r
857         if (animationPath.count()>1 && p_nextItem!=0) {\r
858             circle.setVisible(true);\r
859             animation.setDuration(p_stepInterval);\r
860 \r
861             if(animationPath.first()==animationPath.at(1)) animationPath.removeFirst();\r
862 \r
863             qreal step;\r
864             if (animationPath.count()>1)\r
865             {\r
866                 step = (100 / (animationPath.count()-1));\r
867                 step = 0.01 * step;\r
868 \r
869                 QVector< QPair <double,QVariant> > values;\r
870                 values.clear();\r
871                 animation.setKeyValues(values);\r
872                 animation.setStartValue(animationPath.at(0));\r
873                 for (int i=1 ; i<(animationPath.count()-1) ; i++)\r
874                 {\r
875                     animation.setKeyValueAt(i*step,QPoint(animationPath.at(i)));\r
876                 }\r
877                 animation.setEndValue(animationPath.last());\r
878 \r
879                 QEventLoop loop;\r
880                 connect(&animation,SIGNAL(finished()),&loop,SLOT(quit()));\r
881                 animation.start();\r
882                 loop.exec();\r
883             }\r
884             circle.setVisible(false);\r
885 \r
886         }\r
887 \r
888         // pokud se teprve spousti > nalezt startpoint\r
889         if (p_activeItem == 0) {\r
890                 p_activeItem = findFirst(mit_startpoint,"Start");\r
891                 animationPath = p_activeItem->lineP->pathCache;\r
892                 return_value = "";\r
893                 emit varViewerAdd(engine,p_activeItem->text(),p_activeItem->userItemColor2(),p_activeItem->userTextColor(),p_activeItem->comment());\r
894 \r
895                 // pokud predchozi byl Endpoint\r
896         } else if (p_activeItem->itemType()==mit_endpoint && p_nextItem!=0) {\r
897                 // neni treba - udela setPlayAction    p_activeItem->deactivate();\r
898                 return_value = "";\r
899                 emit varViewerAdd(engine,p_activeItem->text(),p_activeItem->userItemColor2(),p_activeItem->userTextColor(),p_activeItem->comment());\r
900 \r
901                 // jinak dekativuje predchozi a nastavi aktualni prvek na ten nasledujici\r
902         } else if (p_nextItem==0) {\r
903             QTimer tmr;\r
904             tmr.singleShot(stepInterval(),this,SLOT(slotStop()));\r
905             return;\r
906         } else {\r
907                 p_activeItem->deactivate();\r
908                 p_activeItem = p_nextItem;\r
909         }\r
910 \r
911         p_activeItem->activate();\r
912         if (p_activeItem->itemType()==mit_endpoint) {\r
913                 p_nextItem = 0;\r
914         } else if (p_activeItem->itemType()==mit_continue_a) {\r
915                 p_nextItem = findFirst(mit_continue_b,p_activeItem->text());\r
916         } else {\r
917                 /*if (p_activeItem->itemType()==mit_endpoint) {\r
918                         return_value = "";\r
919                         emit varViewerAdd(engine,p_activeItem->text(),p_activeItem->userItemColor2(),p_activeItem->userTextColor(),p_activeItem->comment());\r
920                 } else */\r
921                     if (p_activeItem->itemType()!=mit_endpoint && p_activeItem->itemType()!=mit_startpoint &&\r
922                            p_activeItem->itemType()!=mit_endpoint &&\r
923                            p_activeItem->itemType()!=mit_continue_a &&\r
924                            p_activeItem->itemType()!=mit_continue_b) {\r
925                         return_value = engine->evaluate(p_activeItem->text()).toString();\r
926                         if (return_value.contains(QRegExp("^[A-Za-z]+(Error:)"))) {\r
927                             QMessageBox::warning(viewer->parentWidget(),ERR,return_value,QMessageBox::Close,QMessageBox::NoButton);\r
928                             setPlayAction(mpa_stop);\r
929                             return;\r
930                         } else {\r
931                             emit varViewerAdd(engine,p_activeItem->text(),p_activeItem->userItemColor2(),p_activeItem->userTextColor(),p_activeItem->comment());\r
932 \r
933                             if (p_activeItem->itemType()==mit_condition) {\r
934                                     if (return_value=="false")\r
935                                     {\r
936                                             p_nextItem = findItem(p_activeItem->dest_m());\r
937                                             animationPath = p_activeItem->lineM->pathCache;\r
938                                     } else {\r
939                                             p_nextItem = findItem(p_activeItem->dest_p());\r
940                                             animationPath = p_activeItem->lineP->pathCache;\r
941                                     }\r
942                                 } else { p_nextItem = findItem(p_activeItem->dest_p()); animationPath = p_activeItem->lineP->pathCache; }\r
943                         }\r
944 \r
945                 } else p_nextItem = findItem(p_activeItem->dest_p());\r
946         }\r
947 \r
948         p_nextLock = false;\r
949         if (p_playNext) next();\r
950 }\r
951 \r
952 void myBase::updatePathways() {\r
953         finder->setNums(canvasWidth(),canvasWidth());\r
954         finder->initCells();\r
955 \r
956         QList< QList<QPoint> > savedPoints;\r
957         short j2;\r
958 \r
959         // naplneni koliznimi objekty\r
960         QList<myItem *>::iterator i;\r
961         myItem * v;\r
962 \r
963         QList<myItem *>::iterator j;\r
964         myItem * w;\r
965         for (i = items.begin(); i!=items.end(); i++) {\r
966                 v = *i;\r
967                 if (v->itemType()!=mit_text) {\r
968                         finder->addRect(v->pos().x()/10,v->pos().y()/10,v->width()/10,v->height()/10);\r
969                         v->setLinesUpdated(false);\r
970                 }\r
971         }\r
972         finder->crop(); // oříznutí\r
973 \r
974         // aktualizace pathCache\r
975         for (i = items.begin(); i!=items.end(); i++) {\r
976                 v = *i;\r
977                 if (v->itemType()!=mit_text) {\r
978 \r
979                         if (v->lineP->visible()==true) {\r
980                                 /////////////////////////////////////////////////\r
981                                 // Odmazání všech spojnic s cílovým bodem\r
982                                 for (j = items.begin(); j!=items.end(); j++) {\r
983                                         w = *j;\r
984                                         if (w->itemType()!=mit_text && w->areLinesUpdated()) {\r
985                                                 if (w->dest_p()==v->dest_p()) {\r
986                                                         savedPoints.append(w->lineP->pathCache);\r
987                                                         finder->unFillLines(w->lineP->pathCache);\r
988                                                 }\r
989 \r
990                                                 if (w->dest_m()==v->dest_p()) {\r
991                                                         savedPoints.append(w->lineM->pathCache);\r
992                                                         finder->unFillLines(w->lineM->pathCache);\r
993                                                 }\r
994                                         }\r
995                                 }\r
996 \r
997                                 if (finder->find(decreasePoint(v->lineP->startPoint().toPoint()),decreasePoint(v->lineP->endPoint().toPoint()))) {\r
998                                         v->lineP->pathCache = finder->points;\r
999                                 } else {\r
1000                                         v->lineP->pathCache.clear();\r
1001                                         v->lineP->pathCache.append(QPoint(0,0));\r
1002                                 }\r
1003 \r
1004 \r
1005                                 /////////////////////////////////////////////////\r
1006                                 //if (v->lineM->visible()==false || v->dest_p()!=v->dest_m())\r
1007                                 // {\r
1008                                 v->lineP->arrow1 = QPoint(-1,-1);\r
1009                                 if (savedPoints.count()>0) {\r
1010                                         finder->unFillLines(v->lineP->pathCache);\r
1011                                         for (j2=0; j2<savedPoints.count(); j2++)\r
1012                                                 finder->fillLines(savedPoints.at(j2));\r
1013                                         savedPoints.clear();\r
1014 \r
1015                                         twoPoints first;\r
1016                                         first = finder->detectCriticalPoint(v->lineP->pathCache);\r
1017                                         if (first.at(0)!=QPoint(-1,-1)) {\r
1018                                                 QPoint point = first[0];\r
1019                                                 QPoint point2 = first[1];\r
1020 \r
1021                                                 if (point.x()==point2.x()) { // smernice 0° nebo 180°\r
1022                                                         if ((point.y()-point2.y()) >= 0) point2 = QPoint(point.x()*10,point.y()*10-10);\r
1023                                                         else point2 = QPoint(point.x()*10,point.y()*10+10);\r
1024 \r
1025                                                 } else { // smernice 90° nebo 270°\r
1026                                                         if ((point.x()-point2.x()) > 0) point2 = QPoint(point.x()*10-10,point.y()*10);\r
1027                                                         else point2 = QPoint(point.x()*10+10,point.y()*10);\r
1028                                                 }\r
1029                                                 point = QPoint(point.x()*10,point.y()*10);\r
1030 \r
1031                                                 v->lineP->arrow1 = point2;\r
1032                                                 v->lineP->arrow2 = point;\r
1033                                             }\r
1034                                 }\r
1035                                 v->lineP->update();\r
1036                                 finder->fillLines(v->lineP->pathCache);\r
1037                                 // }\r
1038                                 /////////////////////////////////////////////////\r
1039                                 finder->clear();\r
1040                         }\r
1041 \r
1042 \r
1043                         if (v->itemType()==mit_condition && v->lineM->visible()==true) {\r
1044                                 /////////////////////////////////////////////////\r
1045                                 // Odmazání všech spojnic s cílovým bodem\r
1046                                 if (v->lineP->visible()==true && v->dest_p()==v->dest_m()) {\r
1047                                         savedPoints.append(v->lineP->pathCache);\r
1048                                         finder->unFillLines(v->lineP->pathCache);\r
1049                                 } else {\r
1050                                         for (j = items.begin(); j!=items.end(); j++) {\r
1051                                                 w = *j;\r
1052                                                 if (w->itemType()!=mit_text && w->areLinesUpdated()) {\r
1053                                                         if (w->dest_p()==v->dest_m()) {\r
1054                                                                 savedPoints.append(w->lineP->pathCache);\r
1055                                                                 finder->unFillLines(w->lineP->pathCache);\r
1056                                                         }\r
1057 \r
1058                                                         if (w->dest_m()==v->dest_m()) {\r
1059                                                                 savedPoints.append(w->lineM->pathCache);\r
1060                                                                 finder->unFillLines(w->lineM->pathCache);\r
1061                                                         }\r
1062                                                 }\r
1063                                         }\r
1064                                 }\r
1065                                 /////////////////////////////////////////////////\r
1066 \r
1067                                 if (finder->find(decreasePoint(v->lineM->startPoint().toPoint()),decreasePoint(v->lineM->endPoint().toPoint()))) {\r
1068                                         v->lineM->pathCache = finder->points;\r
1069                                 } else {\r
1070                                         v->lineM->pathCache.clear();\r
1071                                         v->lineM->pathCache.append(QPoint(0,0));\r
1072                                 }\r
1073 \r
1074 \r
1075                                 /////////////////////////////////////////////////\r
1076                                 v->lineM->arrow1 = QPoint(-1,-1);\r
1077                                 if (savedPoints.count()>0) {\r
1078                                         finder->unFillLines(v->lineM->pathCache);\r
1079                                         for (j2=0; j2<savedPoints.count(); j2++)\r
1080                                                 finder->fillLines(savedPoints.at(j2));\r
1081                                         savedPoints.clear();\r
1082 \r
1083                                         twoPoints first;\r
1084                                         first = finder->detectCriticalPoint(v->lineM->pathCache);\r
1085                                         if (first.at(0)!=QPoint(-1,-1)) {\r
1086                                                 QPoint point2 = first[1];\r
1087                                                 QPoint point = first[0];\r
1088 \r
1089                                                 if (point.x()==point2.x()) { // smernice 0° nebo 180°\r
1090                                                         if ((point.y()-point2.y()) >= 0) point2 = QPoint(point.x()*10,point.y()*10-10);\r
1091                                                         else point2 = QPoint(point.x()*10,point.y()*10+10);\r
1092 \r
1093                                                 } else { // smernice 90° nebo 270°\r
1094                                                         if ((point.x()-point2.x()) > 0) point2 = QPoint(point.x()*10-10,point.y()*10);\r
1095                                                         else point2 = QPoint(point.x()*10+10,point.y()*10);\r
1096                                                 }\r
1097                                                 point = QPoint(point.x()*10,point.y()*10);\r
1098 \r
1099                                                 v->lineM->arrow1 = point2;\r
1100                                                 v->lineM->arrow2 = point;\r
1101                                         }\r
1102                                 }\r
1103                                 v->lineM->update();\r
1104                                 finder->fillLines(v->lineM->pathCache);\r
1105                                 /////////////////////////////////////////////////\r
1106 \r
1107                                 finder->clear();\r
1108                         }\r
1109 \r
1110                         v->setLinesUpdated(true);\r
1111 \r
1112                 }\r
1113 \r
1114         }\r
1115 \r
1116 }\r
1117 \r
1118 bool myBase::canUndo() {\r
1119         return (undoBackIndex>0);\r
1120 }\r
1121 \r
1122 bool myBase::canRedo() {\r
1123         return (undoBackIndex<(undoList.count()-1));\r
1124 }\r
1125 \r
1126 void myBase::undo() {\r
1127         if (canUndo()) {\r
1128                 undoBackIndex = undoBackIndex-1;\r
1129                 loadFromUndoList();\r
1130                 emit checkUndoRedo();\r
1131         }\r
1132 }\r
1133 \r
1134 void myBase::redo() {\r
1135         if (canRedo()) {\r
1136                 undoBackIndex++;\r
1137                 loadFromUndoList();\r
1138                 emit checkUndoRedo();\r
1139         }\r
1140 }\r
1141 \r
1142 void myBase::loadFromUndoList() {\r
1143         setPlayAction(mpa_stop);\r
1144 \r
1145         p_loading = true;\r
1146         removeAll();\r
1147         init();\r
1148         p_changed = true;\r
1149 \r
1150         QStringList list = undoList.at(undoBackIndex);\r
1151         importSettings(list.at(0));\r
1152 \r
1153         for (int i = 1 ; i<list.count() ; i++)\r
1154                 addItemWithoutAnyCheck(list.at(i));\r
1155 \r
1156         scene->redrawAllLines();\r
1157         scene->redrawBackground();\r
1158         updatePathways();\r
1159         p_loading = false;\r
1160 }\r
1161 \r
1162 void myBase::makeUndoPoint(bool incrementUndoBackIndex) {\r
1163         myItem * v;\r
1164         QStringList list;\r
1165         list.append(exportSettings());\r
1166         QList<myItem *>::iterator i;\r
1167         for (i = items.begin() ; i<items.end() ; i++) {\r
1168                 v = *i;\r
1169                 list.append(v->exportSettings());\r
1170         }\r
1171 \r
1172         if (undoBackIndex!=undoList.count())\r
1173                 for (int j = (undoList.count()-1) ; j>undoBackIndex ; j--)\r
1174                         undoList.removeLast();\r
1175 \r
1176         undoList.append(list);\r
1177 \r
1178         if (incrementUndoBackIndex) undoBackIndex++;\r
1179         emit checkUndoRedo();\r
1180 }\r