File indexing completed on 2024-05-12 16:39:54
0001 /* This file is part of the KDE project 0002 Copyright (C) 2006 Jarosław Staniek <staniek@kde.org> 0003 0004 This program is free software; you can redistribute it and/or 0005 modify it under the terms of the GNU Library General Public 0006 License as published by the Free Software Foundation; either 0007 version 2 of the License, or (at your option) any later version. 0008 0009 This program is distributed in the hope that it will be useful, 0010 but WITHOUT ANY WARRANTY; without even the implied warranty of 0011 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 0012 Library General Public License for more details. 0013 0014 You should have received a copy of the GNU Library General Public License 0015 along with this program; see the file COPYING. If not, write to 0016 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 0017 * Boston, MA 02110-1301, USA. 0018 */ 0019 0020 #include "utils.h" 0021 #include "utils_p.h" 0022 #include <KexiIcon.h> 0023 0024 #include <KDb> 0025 0026 #include <KStandardGuiItem> 0027 0028 #include <QThread> 0029 #include <QHeaderView> 0030 #include <QPushButton> 0031 #include <QTabWidget> 0032 #include <QVBoxLayout> 0033 #include <QDebug> 0034 0035 static DebugWindow* debugWindow = 0; 0036 static QTabWidget* debugWindowTab = 0; 0037 static KexiDBDebugTreeWidget* kexiDBDebugPage = 0; 0038 static QTreeWidget* kexiAlterTableActionDebugPage = 0; 0039 0040 static void addKexiDBDebug(const QString& text) 0041 { 0042 // (this is internal code - do not use i18n() here) 0043 if (!debugWindowTab) 0044 return; 0045 if (QThread::currentThread() != debugWindowTab->thread()) { 0046 //! @todo send debug using async. signal 0047 qWarning() << "Debugging from different thread not supported."; 0048 return; 0049 } 0050 if (!kexiDBDebugPage) { 0051 QWidget *page = new QWidget(debugWindowTab); 0052 QVBoxLayout *vbox = new QVBoxLayout(page); 0053 QHBoxLayout *hbox = new QHBoxLayout; 0054 vbox->addLayout(hbox); 0055 hbox->addStretch(1); 0056 QPushButton *btn_copy = new QPushButton(page); 0057 btn_copy->setIcon(koSmallIcon("edit-copy")); 0058 hbox->addWidget(btn_copy); 0059 QPushButton *btn_clear = new QPushButton(KStandardGuiItem::clear().icon(), KStandardGuiItem::clear().text(), page); 0060 hbox->addWidget(btn_clear); 0061 0062 kexiDBDebugPage = new KexiDBDebugTreeWidget(page); 0063 kexiDBDebugPage->setObjectName("kexiDbDebugPage"); 0064 kexiDBDebugPage->setFont(KexiUtils::smallestReadableFont()); 0065 QObject::connect(btn_copy, SIGNAL(clicked()), kexiDBDebugPage, SLOT(copy())); 0066 QObject::connect(btn_clear, SIGNAL(clicked()), kexiDBDebugPage, SLOT(clear())); 0067 vbox->addWidget(kexiDBDebugPage); 0068 kexiDBDebugPage->setHeaderLabel(QString()); 0069 kexiDBDebugPage->header()->hide(); 0070 kexiDBDebugPage->setSortingEnabled(false); 0071 kexiDBDebugPage->setAllColumnsShowFocus(true); 0072 kexiDBDebugPage->header()->setSectionResizeMode(0, QHeaderView::Stretch); 0073 kexiDBDebugPage->header()->setStretchLastSection(true); 0074 kexiDBDebugPage->setRootIsDecorated(true); 0075 kexiDBDebugPage->setWordWrap(true); 0076 kexiDBDebugPage->setAlternatingRowColors(true); 0077 debugWindowTab->addTab(page, "KDb"); 0078 debugWindowTab->setCurrentWidget(page); 0079 kexiDBDebugPage->show(); 0080 } 0081 //add \n after (about) every 30 characters 0082 QTreeWidgetItem * lastItem = kexiDBDebugPage->invisibleRootItem()->child( 0083 kexiDBDebugPage->invisibleRootItem()->childCount()-1); 0084 QTreeWidgetItem* li; 0085 if (lastItem) { 0086 li = new QTreeWidgetItem(kexiDBDebugPage, lastItem); 0087 } 0088 else { 0089 li = new QTreeWidgetItem(kexiDBDebugPage->invisibleRootItem()); 0090 } 0091 li->setText(0, text); 0092 li->setToolTip(0, text); 0093 li->setExpanded(true); 0094 } 0095 0096 static void addAlterTableActionDebug(const QString& text, int nestingLevel) 0097 { 0098 // (this is internal code - do not use i18n() here) 0099 if (!debugWindowTab) 0100 return; 0101 if (!kexiAlterTableActionDebugPage) { 0102 QWidget *page = new QWidget(debugWindowTab); 0103 QVBoxLayout *vbox = new QVBoxLayout(page); 0104 QHBoxLayout *hbox = new QHBoxLayout(page); 0105 vbox->addLayout(hbox); 0106 hbox->addStretch(1); 0107 QPushButton *btn_exec = new QPushButton(KStandardGuiItem::save().icon(), "Real Alter Table", page); 0108 btn_exec->setObjectName("executeRealAlterTable"); 0109 hbox->addWidget(btn_exec); 0110 QPushButton *btn_clear = new QPushButton(KStandardGuiItem::clear().icon(), KStandardGuiItem::clear().text(), page); 0111 hbox->addWidget(btn_clear); 0112 QPushButton *btn_sim = new QPushButton(QIcon::fromTheme("system-run"), "Simulate Execution", page); 0113 btn_sim->setObjectName("simulateAlterTableExecution"); 0114 hbox->addWidget(btn_sim); 0115 0116 kexiAlterTableActionDebugPage = new QTreeWidget(page); 0117 kexiAlterTableActionDebugPage->setFont(KexiUtils::smallestReadableFont()); 0118 kexiAlterTableActionDebugPage->setObjectName("kexiAlterTableActionDebugPage"); 0119 QObject::connect(btn_clear, SIGNAL(clicked()), kexiAlterTableActionDebugPage, SLOT(clear())); 0120 vbox->addWidget(kexiAlterTableActionDebugPage); 0121 kexiAlterTableActionDebugPage->setHeaderLabel(QString()); 0122 kexiAlterTableActionDebugPage->header()->hide(); 0123 kexiAlterTableActionDebugPage->setSortingEnabled(false); 0124 kexiAlterTableActionDebugPage->setAllColumnsShowFocus(true); 0125 kexiAlterTableActionDebugPage->header()->setSectionResizeMode(0, QHeaderView::Stretch); 0126 kexiAlterTableActionDebugPage->setRootIsDecorated(true); 0127 debugWindowTab->addTab(page, "AlterTable Actions"); 0128 debugWindowTab->setCurrentWidget(page); 0129 page->show(); 0130 } 0131 if (text.isEmpty()) //don't move up! 0132 return; 0133 QTreeWidgetItem * li; 0134 int availableNestingLevels = 0; 0135 // compute availableNestingLevels 0136 QTreeWidgetItem * lastItem = kexiAlterTableActionDebugPage->invisibleRootItem()->child( 0137 kexiAlterTableActionDebugPage->invisibleRootItem()->childCount()-1); 0138 //qDebug() << "lastItem: " << (lastItem ? lastItem->text(0) : QString()); 0139 while (lastItem) { 0140 lastItem = lastItem->parent(); 0141 availableNestingLevels++; 0142 } 0143 //qDebug() << "availableNestingLevels: " << availableNestingLevels; 0144 //go up (availableNestingLevels-levelsToGoUp) levels 0145 lastItem = kexiAlterTableActionDebugPage->invisibleRootItem()->child( 0146 kexiAlterTableActionDebugPage->invisibleRootItem()->childCount()-1); 0147 int levelsToGoUp = availableNestingLevels - nestingLevel; 0148 while (levelsToGoUp > 0 && lastItem) { 0149 lastItem = lastItem->parent(); 0150 levelsToGoUp--; 0151 } 0152 //qDebug() << "lastItem2: " << (lastItem ? lastItem->text(0) : QString()); 0153 if (lastItem) { 0154 if (lastItem->childCount() > 0) { 0155 li = new QTreeWidgetItem(lastItem, lastItem->child(lastItem->childCount()-1)); //child, after 0156 } 0157 else { 0158 li = new QTreeWidgetItem(lastItem); //1st child 0159 } 0160 } else { 0161 lastItem = kexiAlterTableActionDebugPage->invisibleRootItem()->child( 0162 kexiAlterTableActionDebugPage->invisibleRootItem()->childCount()-1); 0163 while (lastItem && lastItem->parent()) { 0164 lastItem = lastItem->parent(); 0165 } 0166 //qDebug() << "lastItem2: " << (lastItem ? lastItem->text(0) : QString()); 0167 if (lastItem && lastItem->parent()) 0168 li = new QTreeWidgetItem(lastItem->parent(), lastItem); //after 0169 else if (!lastItem) 0170 li = new QTreeWidgetItem(kexiAlterTableActionDebugPage->invisibleRootItem()); 0171 else if (!lastItem->parent()) 0172 li = new QTreeWidgetItem(kexiAlterTableActionDebugPage->invisibleRootItem(), lastItem); 0173 } 0174 li->setText(0, text); 0175 li->setExpanded(true); 0176 } 0177 0178 QWidget *KexiUtils::createDebugWindow(QWidget *parent) 0179 { 0180 Q_UNUSED(parent); 0181 KDb::setDebugGUIHandler(addKexiDBDebug); 0182 KDb::setAlterTableActionDebugHandler(addAlterTableActionDebug); 0183 0184 // (this is internal code - do not use i18n() here) 0185 debugWindow = new DebugWindow(parent); 0186 QBoxLayout *lyr = new QVBoxLayout(debugWindow); 0187 debugWindowTab = new QTabWidget(debugWindow); 0188 debugWindowTab->setObjectName("debugWindowTab"); 0189 lyr->addWidget(debugWindowTab); 0190 debugWindow->resize(900, 600); 0191 debugWindow->setWindowIcon(koIcon("document-properties")); 0192 debugWindow->setWindowTitle("Kexi Internal Debugger"); 0193 debugWindow->show(); 0194 return debugWindow; 0195 } 0196 0197 void KexiUtils::connectPushButtonActionForDebugWindow(const char* actionName, 0198 const QObject *receiver, const char* slot) 0199 { 0200 if (debugWindow) { 0201 QPushButton* btn = KexiUtils::findFirstChild<QPushButton*>( 0202 debugWindow, "QPushButton", actionName); 0203 if (btn) 0204 QObject::connect(btn, SIGNAL(clicked()), receiver, slot); 0205 } 0206 }