Isis 3 Programmer Reference
ControlList.cpp
1
7/* SPDX-License-Identifier: CC0-1.0 */
8
9#include "ControlList.h"
10
11#include <QAction>
12#include <QColorDialog>
13#include <QDebug>
14#include <QDir>
15#include <QFile>
16#include <QFuture>
17#include <QInputDialog>
18#include <QLabel>
19#include <QProgressDialog>
20#include <QtConcurrentMap>
21#include <QXmlStreamWriter>
22
23#include "Color.h"
24#include "FileName.h"
25#include "IException.h"
26#include "Project.h"
27#include "XmlStackedHandlerReader.h"
28
29namespace Isis {
37 ControlList::ControlList(QString name, QString path, QObject *parent) : QObject(parent) {
38 m_name = name;
39 m_path = path;
40 }
41
42
49 }
50
51
58 ControlList::ControlList(QList<Control *> controls, QObject *parent) : QObject(parent) {
59 append(controls);
60 }
61
62
71 QObject(parent) {
72 xmlReader->pushContentHandler(new XmlHandler(this, project));
73 }
74
75
82 QList<Control *>(other) {
83 m_name = other.m_name;
84 m_path = other.m_path;
85 }
86
87
95 foreach (QString fileName, fileNames) {
96 try {
97 Control *control = new Control(fileName);
98 append(control);
99 }
100 catch (IException &) {
101 }
102 }
103 }
104
105
110 emit deletingList(this);
111 }
112
113
121 void ControlList::append(Control * const &value) {
123 emit countChanged(count());
124 }
125
126
134 void ControlList::append(const QList<Control *> &value) {
136 emit countChanged(count());
137 }
138
139
146 bool countChanging = count();
148 if (countChanging) {
149 emit countChanged(count());
150 }
151 }
152
153
164 iterator result = QList<Control *>::erase(pos);
165 emit countChanged(count());
166 return result;
167 }
168
169
180 QList<Control *>::iterator ControlList::erase(iterator begin, iterator end) {
181 iterator result = QList<Control *>::erase(begin, end);
182 emit countChanged(count());
183 return result;
184 }
185
186
195 void ControlList::insert(int i, Control * const &value) {
196 QList<Control *>::insert(i, value);
197
198 emit countChanged(count());
199 }
200
201
212 QList<Control *>::iterator ControlList::insert(iterator before, Control * const &value) {
213 iterator result = QList<Control *>::insert(before, value);
214 emit countChanged(count());
215 return result;
216 }
217
218
226 void ControlList::prepend(Control * const &value) {
228 emit countChanged(count());
229 }
230
231
240 void ControlList::push_back(Control * const &value) {
242 emit countChanged(count());
243 }
244
245
254 void ControlList::push_front(Control * const &value) {
256 emit countChanged(count());
257 }
258
259
269 int ControlList::removeAll(Control * const &value) {
270 int result = QList<Control *>::removeAll(value);
271
272 if (result != 0) {
273 emit countChanged(count());
274 }
275
276 return result;
277 }
278
279
289 emit countChanged(count());
290 }
291
292
300 emit countChanged(count());
301 }
302
303
311 emit countChanged(count());
312 }
313
314
324 bool ControlList::removeOne(Control * const &value) {
325 bool result = QList<Control *>::removeOne(value);
326
327 if (result) {
328 emit countChanged(count());
329 }
330
331 return result;
332 }
333
334
342 void ControlList::swap(QList<Control *> &other) {
344
345 if (count() != other.count()) {
346 emit countChanged(count());
347 }
348 }
349
350
361 Control * result = QList<Control *>::takeAt(i);
362 emit countChanged(count());
363 return result;
364 }
365
366
376 emit countChanged(count());
377 return result;
378 }
379
380
390 emit countChanged(count());
391 return result;
392 }
393
394
404 ControlList &ControlList::operator+=(const QList<Control *> &other) {
406
407 if (other.count()) {
408 emit countChanged(count());
409 }
410
411 return *this;
412 }
413
414
426 emit countChanged(count());
427 return *this;
428 }
429
430
440 ControlList &ControlList::operator<<(const QList<Control *> &other) {
442
443 if (other.count()) {
444 emit countChanged(count());
445 }
446
447 return *this;
448 }
449
450
462 emit countChanged(count());
463 return *this;
464 }
465
466
476 ControlList &ControlList::operator=(const QList<Control *> &rhs) {
477 bool countChanging = (rhs.count() != count());
479
480 if (countChanging) {
481 emit countChanged(count());
482 }
483
484 return *this;
485 }
486
487
498 bool countChanging = (rhs.count() != count());
500
501 m_name = rhs.m_name;
502 m_path = rhs.m_path;
503
504 if (countChanging) {
505 emit countChanged(count());
506 }
507
508 return *this;
509 }
510
511
518 void ControlList::setName(QString newName) {
519 m_name = newName;
520 }
521
522
529 void ControlList::setPath(QString newPath) {
530 m_path = newPath;
531 }
532
533
539 QString ControlList::name() const {
540 return m_name;
541 }
542
543
550 QString ControlList::path() const {
551 return m_path;
552 }
553
554
563 foreach (Control *control, *this) {
564 control->deleteFromDisk();
565 }
566
567 if (!m_path.isEmpty()) {
568 QFile::remove(project->cnetRoot() + "/" + m_path + "/controlNetworks.xml");
569
570 QDir dir;
571 dir.rmdir(project->cnetRoot() + "/" + m_path);
572 }
573 }
574
575
599 void ControlList::save(QXmlStreamWriter &stream, const Project *project, FileName newProjectRoot)
600 const {
601 stream.writeStartElement("controlList");
602 stream.writeAttribute("name", m_name);
603 stream.writeAttribute("path", m_path);
604
605 FileName settingsFileName(
606 Project::cnetRoot(newProjectRoot.toString()) + "/" + m_path +
607 "/controlNetworks.xml");
608
609 if (!settingsFileName.dir().mkpath(settingsFileName.path())) {
611 QString("Failed to create directory [%1]")
612 .arg(settingsFileName.path()),
613 _FILEINFO_);
614 }
615
616 QFile controlListContentsFile(settingsFileName.toString());
617
618 if (!controlListContentsFile.open(QIODevice::ReadWrite | QIODevice::Truncate)) {
620 QString("Unable to save control information for [%1] because [%2] could not be opened "
621 "for writing")
622 .arg(m_name).arg(settingsFileName.original()),
623 _FILEINFO_);
624 }
625
626 QXmlStreamWriter controlDetailsWriter(&controlListContentsFile);
627 controlDetailsWriter.setAutoFormatting(true);
628 controlDetailsWriter.writeStartDocument();
629
630 int countWidth = QString("%1L").arg(count()).size() - 1;
631 QChar paddingChar('0');
632
633 QLabel *progressLabel = new QLabel;
634
635 QProgressDialog progressDialog;
636 progressDialog.setLabel(progressLabel);
637 progressDialog.setRange(-1, count());
638 progressDialog.setValue(-1);
639
640 controlDetailsWriter.writeStartElement("controls");
641
642 // Only copy controls if saving to new location
643 if (project->newProjectRoot() != project->projectRoot()) {
644 QFuture<void *> future = QtConcurrent::mapped(*this,
645 CopyControlDataFunctor(project, newProjectRoot));
646 for (int i = 0; i < count(); i++) {
647 int newProgressValue = progressDialog.value() + 1;
648 progressLabel->setText(
649 tr("Saving Control Information for [%1] - %L2/%L3 done")
650 .arg(m_name)
651 .arg(newProgressValue, countWidth, 10, paddingChar)
652 .arg(count()));
653 progressDialog.setValue(newProgressValue);
654 future.resultAt(i);
655 }
656
657 progressLabel->setText(tr("Finalizing..."));
658 progressDialog.setRange(0, 0);
659 progressDialog.setValue(0);
660 }
661
662 foreach (Control *control, *this) {
663 control->save(controlDetailsWriter, project, newProjectRoot);
664 }
665
666 controlDetailsWriter.writeEndElement();
667
668 controlDetailsWriter.writeEndDocument();
669
670 stream.writeEndElement();
671 }
672
673
681 FileName newProjectRoot) {
682 m_project = project;
683 m_newProjectRoot = newProjectRoot;
684 }
685
686
693 m_project = other.m_project;
694 m_newProjectRoot = other.m_newProjectRoot;
695 }
696
697
703
704
711 controlToCopy->copyToNewProjectRoot(m_project, m_newProjectRoot);
712 return NULL;
713 }
714
715
724 const CopyControlDataFunctor &rhs) {
725 m_project = rhs.m_project;
726 m_newProjectRoot = rhs.m_newProjectRoot;
727 return *this;
728 }
729
730
739 m_controlList = controlList;
740 m_project = project;
741 }
742
743
755 bool ControlList::XmlHandler::startElement(const QString &namespaceURI, const QString &localName,
756 const QString &qName, const QXmlAttributes &atts) {
757 if (XmlStackedHandler::startElement(namespaceURI, localName, qName, atts)) {
758 if (localName == "controlList") {
759 QString name = atts.value("name");
760 QString path = atts.value("path");
761
762 if (!name.isEmpty()) {
763 m_controlList->setName(name);
764 }
765
766 if (!path.isEmpty()) {
767 m_controlList->setPath(path);
768 }
769 }
770 else if (localName == "controlNet") {
771 m_controlList->append(new Control(m_project->cnetRoot() + "/" +
772 m_controlList->path(), reader()));
773 }
774 }
775
776 return true;
777 }
778
779
793 bool ControlList::XmlHandler::endElement(const QString &namespaceURI, const QString &localName,
794 const QString &qName) {
795 if (localName == "controlList") {
796 XmlHandler handler(m_controlList, m_project);
797
799 reader.pushContentHandler(&handler);
800 reader.setErrorHandler(&handler);
801
802 QString controlListXmlPath = m_project->cnetRoot() + "/" + m_controlList->path() +
803 "/controlNetworks.xml";
804 QFile file(controlListXmlPath);
805
806 if (!file.open(QFile::ReadOnly)) {
808 QString("Unable to open [%1] with read access")
809 .arg(controlListXmlPath),
810 _FILEINFO_);
811 }
812
813 QXmlInputSource xmlInputSource(&file);
814 if (!reader.parse(xmlInputSource))
816 tr("Failed to open control list XML [%1]").arg(controlListXmlPath),
817 _FILEINFO_);
818 }
819
820 return XmlStackedHandler::endElement(namespaceURI, localName, qName);
821 }
822}
This represents an ISIS control net in a project-based GUI interface.
Definition Control.h:66
void deleteFromDisk()
Delete the control net from disk.
Definition Control.cpp:334
void save(QXmlStreamWriter &stream, const Project *project, FileName newProjectRoot) const
Method to write this Control object's member data to an XML stream.
Definition Control.cpp:373
This functor is used for copying the control nets between two projects quickly.
CopyControlDataFunctor & operator=(const CopyControlDataFunctor &rhs)
CopyControlDataFunctor assignment operator.
~CopyControlDataFunctor()
CopyControlDataFunctor destructor.
void * operator()(Control *const &controlToCopy)
Copies the Control from one project to another.
const Project * m_project
Project to copy the control list to.
FileName m_newProjectRoot
The filename of the destination project's root.
CopyControlDataFunctor(const Project *project, FileName newProjectRoot)
CopyControlDataFunctor constructor.
Nested class used to write the ControlList object information to an XML file for the purposes of savi...
virtual bool endElement(const QString &namespaceURI, const QString &localName, const QString &qName)
Handle an XML end element.
XmlHandler(ControlList *controlList, Project *project)
Create an XML Handler (reader/writer) that can populate the ControlList class data.
virtual bool startElement(const QString &namespaceURI, const QString &localName, const QString &qName, const QXmlAttributes &atts)
Handle an XML start element.
Maintains a list of Controls so that control nets can easily be copied from one Project to another,...
Definition ControlList.h:44
void deleteFromDisk(Project *project)
Delete all of the contained Controls from disk.
void removeLast()
Removes the last control pointer from the control list.
iterator erase(iterator pos)
Erases a control pointer from the control list at the specified position.
void append(Control *const &value)
Appends a control pointer to the control list.
~ControlList()
Destructor.
void push_back(Control *const &value)
Equivalent to append(value)
ControlList & operator+=(const QList< Control * > &other)
Appends control pointers from the other list to this control list.
void insert(int i, Control *const &value)
Inserts a control pointer at the specified position in the control list.
QString path() const
Get the path to these controls in the control list (relative to project root).
QString name() const
Get the human-readable name of this control list.
void setName(QString newName)
Set the human-readable name of this control list.
void removeAt(int i)
Removes the control pointer at the specified index.
bool removeOne(Control *const &value)
Removes the first occurence of the control pointer from the control list.
void push_front(Control *const &value)
Equivalent to prepend(value)
Control * takeAt(int i)
Remove the control pointer at the specified index and returns it.
Control * takeFirst()
Removes the first control pointer from the control list and returns it.
ControlList & operator=(const QList< Control * > &rhs)
Assigns another list of control pointers to this control list.
int removeAll(Control *const &value)
Removes all occurences of the control pointer in the control list.
void save(QXmlStreamWriter &stream, const Project *project, FileName newProjectRoot) const
Convert this control list into XML format for saving/restoring capabilities.
void setPath(QString newPath)
Set the relative path (from the project root) to this control list's folder.
void prepend(Control *const &value)
Prepends a control pointer to the control list.
QString m_name
Name of the ControlList.
ControlList & operator<<(const QList< Control * > &other)
Appends a list of other control pointers to this control list.
void swap(QList< Control * > &other)
Swaps this control list's control pointers with the other list of control pointers.
void clear()
Clears the control list.
QString m_path
This stores the directory name that contains the controls in this control list.
Control * takeLast()
Removes the last control pointer from the control list and returns it.
void removeFirst()
Removes the first control pointer from the control list.
ControlList(QString name, QString path, QObject *parent=NULL)
Create an control list from a control list name and path (does not read Controls).
File name manipulation and expansion.
Definition FileName.h:100
QString path() const
Returns the path of the file name.
Definition FileName.cpp:103
QDir dir() const
Returns the path of the file's parent directory as a QDir object.
Definition FileName.cpp:465
QString original() const
Returns the full file name including the file path.
Definition FileName.cpp:212
QString toString() const
Returns a QString of the full file name including the file path, excluding the attributes with any Is...
Definition FileName.cpp:515
Isis exception class.
Definition IException.h:91
@ Io
A type of error that occurred when performing an actual I/O operation.
Definition IException.h:155
The main project for ipce.
Definition Project.h:289
static QString cnetRoot(QString projectRoot)
Appends the root directory name 'cnets' to the project.
Definition Project.cpp:2018
QString newProjectRoot() const
Get the top-level folder of the new project.
Definition Project.cpp:1674
QString cnetRoot() const
Get where control networks ought to be stored inside the project.
Definition Project.cpp:2028
QString projectRoot() const
Get the top-level folder of the project.
Definition Project.cpp:1665
Manage a stack of content handlers for reading XML files.
virtual void pushContentHandler(XmlStackedHandler *newHandler)
Push a contentHandler and maybe continue parsing...
This is free and unencumbered software released into the public domain.
This is free and unencumbered software released into the public domain.
Definition Apollo.h:16