File indexing completed on 2024-04-28 04:42:10

0001 /* This file is part of the KDE project
0002  * Copyright (C) 2001-2007 by OpenMFG, LLC (info@openmfg.com)
0003  * Copyright (C) 2007-2008 by Adam Pigg (adam@piggz.co.uk)
0004  *
0005  * This library is free software; you can redistribute it and/or
0006  * modify it under the terms of the GNU Lesser General Public
0007  * License as published by the Free Software Foundation; either
0008  * version 2.1 of the License, or (at your option) any later version.
0009  *
0010  * This library is distributed in the hope that it will be useful,
0011  * but WITHOUT ANY WARRANTY; without even the implied warranty of
0012  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
0013  * Lesser General Public License for more details.
0014  *
0015  * You should have received a copy of the GNU Lesser General Public
0016  * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
0017  */
0018 
0019 #include "KReportDesignerSectionDetail.h"
0020 #include "KReportDesignerSectionDetailGroup.h"
0021 #include "KReportDesignerSection.h"
0022 #include "KReportDesigner.h"
0023 #include "KReportUtils.h"
0024 #include "kreport_debug.h"
0025 
0026 #include <QVBoxLayout>
0027 #include <QDomDocument>
0028 
0029 //! @internal
0030 class Q_DECL_HIDDEN KReportDesignerSectionDetail::Private
0031 {
0032 public:
0033     explicit Private() {}
0034 
0035     ~Private()
0036     {
0037     }
0038 
0039     QString name;
0040     KReportDesignerSection *detail;
0041     KReportDesigner *reportDesigner;
0042     QList<KReportDesignerSectionDetailGroup*> groupList;
0043     QVBoxLayout *vboxlayout;
0044     KReportDesignerSectionDetail::PageBreak pageBreak = KReportDesignerSectionDetail::PageBreak::None;
0045 };
0046 
0047 KReportDesignerSectionDetail::KReportDesignerSectionDetail(KReportDesigner * rptdes)
0048         : QWidget(rptdes)
0049         , d(new Private())
0050 {
0051     Q_ASSERT(rptdes);
0052     setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
0053     d->vboxlayout = new QVBoxLayout(this);
0054     d->vboxlayout->setSpacing(0);
0055     d->vboxlayout->setMargin(0);
0056     d->reportDesigner = rptdes;
0057     d->detail = d->reportDesigner->createSection();
0058     d->vboxlayout->addWidget(d->detail);
0059 
0060     this->setLayout(d->vboxlayout);
0061 }
0062 
0063 KReportDesignerSectionDetail::~KReportDesignerSectionDetail()
0064 {
0065     delete d;
0066 }
0067 
0068 KReportDesignerSectionDetail::PageBreak KReportDesignerSectionDetail::pageBreak() const
0069 {
0070     return d->pageBreak;
0071 }
0072 void KReportDesignerSectionDetail::setPageBreak(PageBreak pb)
0073 {
0074     d->pageBreak = pb;
0075 }
0076 
0077 KReportDesignerSection * KReportDesignerSectionDetail::detailSection() const
0078 {
0079     return d->detail;
0080 }
0081 
0082 void KReportDesignerSectionDetail::buildXML(QDomDocument *doc, QDomElement *section)
0083 {
0084     if (pageBreak() != KReportDesignerSectionDetail::PageBreak::None) {
0085         QDomElement spagebreak = doc->createElement(QLatin1String("pagebreak"));
0086         if (pageBreak() == KReportDesignerSectionDetail::PageBreak::AtEnd)
0087             spagebreak.setAttribute(QLatin1String("when"), QLatin1String("at end"));
0088         section->appendChild(spagebreak);
0089     }
0090 
0091     foreach(KReportDesignerSectionDetailGroup* rsdg, d->groupList) {
0092         rsdg->buildXML(doc, section);
0093     }
0094 
0095     // detail section
0096     QDomElement gdetail = doc->createElement(QLatin1String("report:section"));
0097     gdetail.setAttribute(QLatin1String("report:section-type"), QLatin1String("detail"));
0098     d->detail->buildXML(doc, &gdetail);
0099     section->appendChild(gdetail);
0100 }
0101 
0102 void KReportDesignerSectionDetail::initFromXML(QDomNode *section)
0103 {
0104     QDomNodeList nl = section->childNodes();
0105     QDomNode node;
0106     QString n;
0107 
0108     for (int i = 0; i < nl.count(); i++) {
0109         node = nl.item(i);
0110         n = node.nodeName();
0111         //kreportDebug() << n;
0112         if (n == QLatin1String("pagebreak")) {
0113             QDomElement eThis = node.toElement();
0114             if (eThis.attribute(QLatin1String("when")) == QLatin1String("at end"))
0115                 setPageBreak(PageBreak::AtEnd);
0116         } else if (n == QLatin1String("report:group")) {
0117             KReportDesignerSectionDetailGroup * rsdg = new KReportDesignerSectionDetailGroup(QLatin1String("unnamed"), this, this);
0118             rsdg->initFromXML( node.toElement() );
0119             insertGroupSection(groupSectionCount(), rsdg);
0120         } else if (n == QLatin1String("report:section")
0121             && KReportUtils::readSectionTypeNameAttribute(node.toElement()) == QLatin1String("detail"))
0122         {
0123             // kreportDebug() << "Creating detail section";
0124             d->detail->initFromXML(node);
0125         } else {
0126             // unknown element
0127             kreportWarning() << "while parsing section encountered and unknown element: " <<  n;
0128         }
0129     }
0130 
0131 }
0132 
0133 KReportDesigner * KReportDesignerSectionDetail::reportDesigner() const
0134 {
0135     return d->reportDesigner;
0136 }
0137 
0138 int KReportDesignerSectionDetail::groupSectionCount() const
0139 {
0140     return d->groupList.count();
0141 }
0142 
0143 KReportDesignerSectionDetailGroup * KReportDesignerSectionDetail::groupSection(int i) const
0144 {
0145     return d->groupList.at(i);
0146 }
0147 
0148 void KReportDesignerSectionDetail::insertGroupSection(int idx, KReportDesignerSectionDetailGroup * rsd)
0149 {
0150     d->groupList.insert(idx, rsd);
0151 
0152     rsd->groupHeader()->setParent(this);
0153     rsd->groupFooter()->setParent(this);
0154 
0155     idx = 0;
0156     int gi = 0;
0157     for (gi = 0; gi < (int) d->groupList.count(); gi++) {
0158         rsd = d->groupList.at(gi);
0159         d->vboxlayout->removeWidget(rsd->groupHeader());
0160         d->vboxlayout->insertWidget(idx, rsd->groupHeader());
0161         idx++;
0162     }
0163     d->vboxlayout->removeWidget(d->detail);
0164     d->vboxlayout->insertWidget(idx, d->detail);
0165     idx++;
0166     for (gi = ((int) d->groupList.count() - 1); gi >= 0; --gi) {
0167         rsd = d->groupList.at(gi);
0168         d->vboxlayout->removeWidget(rsd->groupFooter());
0169         d->vboxlayout->insertWidget(idx, rsd->groupFooter());
0170         idx++;
0171     }
0172 
0173     if (d->reportDesigner) d->reportDesigner->setModified(true);
0174     adjustSize();
0175 }
0176 
0177 int KReportDesignerSectionDetail::indexOfGroupSection(const QString & column) const
0178 {
0179     // find the item by its name
0180     for (uint i = 0; i < (uint)d->groupList.count(); i++) {
0181         KReportDesignerSectionDetailGroup * rsd = d->groupList.at(i);
0182         if (column == rsd->column()) return i;
0183     }
0184     return -1;
0185 }
0186 
0187 void KReportDesignerSectionDetail::removeGroupSection(int idx, bool del)
0188 {
0189     KReportDesignerSectionDetailGroup * rsd = d->groupList.at(idx);
0190 
0191     d->vboxlayout->removeWidget(rsd->groupHeader());
0192     d->vboxlayout->removeWidget(rsd->groupFooter());
0193 
0194     d->groupList.removeAt(idx);
0195 
0196     if (d->reportDesigner) d->reportDesigner->setModified(true);
0197     if (del) delete rsd;
0198     adjustSize();
0199 }
0200 
0201 QSize KReportDesignerSectionDetail::sizeHint() const
0202 {
0203     QSize s;
0204     foreach(KReportDesignerSectionDetailGroup* rsdg, d->groupList) {
0205         if (rsdg->groupHeaderVisible()) s += rsdg->groupHeader()->size();
0206         if (rsdg->groupFooterVisible()) s += rsdg->groupFooter()->size();
0207     }
0208     return s += d->detail->size();
0209 }
0210 
0211 void KReportDesignerSectionDetail::setSectionCursor(const QCursor& c)
0212 {
0213     if (d->detail)
0214         d->detail->setSectionCursor(c);
0215     foreach(KReportDesignerSectionDetailGroup* rsdg, d->groupList) {
0216         if (rsdg->groupHeader())
0217             rsdg->groupHeader()->setSectionCursor(c);
0218         if (rsdg->groupFooter())
0219             rsdg->groupFooter()->setSectionCursor(c);
0220     }
0221 }
0222 
0223 void KReportDesignerSectionDetail::unsetSectionCursor()
0224 {
0225     if (d->detail)
0226         d->detail->unsetSectionCursor();
0227 
0228     foreach(KReportDesignerSectionDetailGroup* rsdg, d->groupList) {
0229         if (rsdg->groupHeader())
0230             rsdg->groupHeader()->unsetSectionCursor();
0231         if (rsdg->groupFooter())
0232             rsdg->groupFooter()->unsetSectionCursor();
0233     }
0234 }