diff options
author | Andrea Diamantini <adjam7@gmail.com> | 2013-03-10 19:02:12 +0100 |
---|---|---|
committer | Andrea Diamantini <adjam7@gmail.com> | 2013-03-10 19:02:12 +0100 |
commit | 9461c52f07a2bf8b9bc25f037b17805cda51b2b0 (patch) | |
tree | b599e6eff700e65a864bb275c94adc9a6da7e529 /src | |
parent | Add toggle ability to bk folder in bk page (diff) | |
download | rekonq-9461c52f07a2bf8b9bc25f037b17805cda51b2b0.tar.xz |
Supporting panel (again) :)
- Move to a pure QWidget base window (instead of TabWidget one)
(this to properly store panels position)
- Restoring && rewamping panels code
- Restoring actions to activate/deactivate them
BUG: 312354
Diffstat (limited to 'src')
35 files changed, 2616 insertions, 667 deletions
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index d0984c93..6833f27f 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -29,6 +29,7 @@ set(rekonq_KDEINIT_SRCS bookmarks/bookmarkscontextmenu.cpp bookmarks/bookmarksmenu.cpp bookmarks/bookmarkstoolbar.cpp + bookmarks/bookmarkstreemodel.cpp bookmarks/bookmarkowner.cpp #---------------------------------------- download/downloaditem.cpp @@ -41,6 +42,12 @@ set(rekonq_KDEINIT_SRCS icons/iconmanager.cpp icons/webicon.cpp #---------------------------------------- + panels/bookmarkspanel.cpp + panels/historypanel.cpp + panels/paneltreeview.cpp + panels/urlfilterproxymodel.cpp + panels/urlpanel.cpp + #---------------------------------------- rekonqpage/newtabpage.cpp rekonqpage/thumbupdater.cpp #---------------------------------------- @@ -66,11 +73,12 @@ set(rekonq_KDEINIT_SRCS sync/syncgooglesettingswidget.cpp sync/syncoperasettingswidget.cpp #---------------------------------------- + tabwindow/rwindow.cpp tabwindow/rekonqwindow.cpp tabwindow/tabbar.cpp tabwindow/tabhighlighteffect.cpp tabwindow/tabpreviewpopup.cpp - tabwindow/tabwindow.cpp + tabwindow/tabwidget.cpp #---------------------------------------- urlbar/urlbar.cpp urlbar/completionwidget.cpp @@ -170,6 +178,7 @@ INCLUDE_DIRECTORIES ( ${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/download ${CMAKE_CURRENT_SOURCE_DIR}/history ${CMAKE_CURRENT_SOURCE_DIR}/icons + ${CMAKE_CURRENT_SOURCE_DIR}/panels ${CMAKE_CURRENT_SOURCE_DIR}/rekonqpage ${CMAKE_CURRENT_SOURCE_DIR}/settings ${CMAKE_CURRENT_SOURCE_DIR}/sync diff --git a/src/application.cpp b/src/application.cpp index 0c96d986..dfcfc59a 100644 --- a/src/application.cpp +++ b/src/application.cpp @@ -38,7 +38,7 @@ #include "searchengine.h" #include "tabbar.h" -#include "tabwindow.h" +#include "rekonqwindow.h" #include "webwindow.h" #include "webtab.h" @@ -73,6 +73,7 @@ #include <QDBusInterface> #include <QDBusReply> #include <QDir> +#include <QTimer> Application::Application() @@ -194,7 +195,7 @@ int Application::newInstance() } // first argument: 99% of the time we have just that... - if (isFirstLoad || m_tabWindows.count() == 0) + if (isFirstLoad || m_rekonqWindows.count() == 0) { // No windows in the current desktop? No windows at all? // Create a new one and load there sites... @@ -218,8 +219,8 @@ int Application::newInstance() loadUrl(urlList.at(0), Rekonq::NewWindow); } - if (!tabWindow()->isActiveWindow()) - KWindowSystem::demandAttention(tabWindow()->winId(), true); + if (!rekonqWindow()->isActiveWindow()) + KWindowSystem::demandAttention(rekonqWindow()->winId(), true); } // following arguments: what's best behavior here? @@ -282,7 +283,7 @@ int Application::newInstance() break; } default: - newTabWindow()->newTab(); + newWindow()->tabWidget()->newTab(); break; } } @@ -312,8 +313,8 @@ int Application::newInstance() { if (hasToBeRecoveredFromCrash && !incognito) { - if (tabWindow() && tabWindow()->currentWebWindow()) - QTimer::singleShot(1000, tabWindow()->currentWebWindow(), SLOT(showCrashMessageBar())); + if (rekonqWindow() && rekonqWindow()->currentWebWindow()) + QTimer::singleShot(1000, rekonqWindow()->currentWebWindow(), SLOT(showCrashMessageBar())); } else { @@ -321,7 +322,7 @@ int Application::newInstance() } if (ReKonfig::checkDefaultSearchEngine() && !hasToBeRecoveredFromCrash && SearchEngine::defaultEngine().isNull()) - QTimer::singleShot(2000, tabWindow()->currentWebWindow()->tabView(), SLOT(showSearchEngineBar())); + QTimer::singleShot(2000, rekonqWindow()->currentWebWindow()->tabView(), SLOT(showSearchEngineBar())); // updating rekonq configuration updateConfiguration(); @@ -354,21 +355,21 @@ void Application::saveConfiguration() const } -TabWindow *Application::tabWindow() +RekonqWindow *Application::rekonqWindow() { - TabWindow *active = qobject_cast<TabWindow*>(QApplication::activeWindow()); + RekonqWindow *active = qobject_cast<RekonqWindow*>(QApplication::activeWindow()); if (!active) { - if (m_tabWindows.isEmpty()) + if (m_rekonqWindows.isEmpty()) return 0; - Q_FOREACH(const QWeakPointer<TabWindow> &pointer, m_tabWindows) + Q_FOREACH(const QWeakPointer<RekonqWindow> &pointer, m_rekonqWindows) { if (KWindowInfo(pointer.data()->effectiveWinId(), NET::WMDesktop, 0).isOnCurrentDesktop()) return pointer.data(); } - return m_tabWindows.at(0).data(); + return m_rekonqWindows.at(0).data(); } return active; } @@ -390,39 +391,39 @@ void Application::loadUrl(const KUrl& url, const Rekonq::OpenType& type) if (url.url().contains("about:") && url.url().contains("/")) newType = Rekonq::CurrentTab; - TabWindow *w = 0; + RekonqWindow *w = 0; if (newType == Rekonq::NewPrivateWindow) { - w = newTabWindow(true, true); + w = newWindow(true, true); newType = Rekonq::CurrentTab; } else if (newType == Rekonq::NewWindow - || ((newType == Rekonq::NewTab || newType == Rekonq::NewFocusedTab) && tabWindowList().count() == 0)) + || ((newType == Rekonq::NewTab || newType == Rekonq::NewFocusedTab) && rekonqWindowList().count() == 0)) { - w = newTabWindow(); + w = newWindow(); newType = Rekonq::CurrentTab; } else { - w = tabWindow(); + w = rekonqWindow(); } w->loadUrl(url, newType); } -TabWindow *Application::newTabWindow(bool withTab, bool PrivateBrowsingMode) +RekonqWindow *Application::newWindow(bool withTab, bool PrivateBrowsingMode) { - TabWindow *w = new TabWindow(withTab, PrivateBrowsingMode); + RekonqWindow *w = new RekonqWindow(withTab, PrivateBrowsingMode); // set object name - int n = m_tabWindows.count() + 1; + int n = m_rekonqWindows.count() + 1; w->setObjectName(QL1S("win") + QString::number(n)); // This is used to track which window was activated most recently w->installEventFilter(this); - m_tabWindows.prepend(w); + m_rekonqWindows.prepend(w); w->show(); return w; @@ -442,9 +443,9 @@ WebTab *Application::newWebApp() } -TabWindowList Application::tabWindowList() +RekonqWindowList Application::rekonqWindowList() { - return m_tabWindows; + return m_rekonqWindows; } @@ -460,16 +461,16 @@ bool Application::eventFilter(QObject* watched, QEvent* event) // (e.g. when another application opens a link) if (event->type() == QEvent::WindowActivate) { - TabWindow *window = qobject_cast<TabWindow*>(watched); + RekonqWindow *window = qobject_cast<RekonqWindow*>(watched); if (window) { - if (!m_tabWindows.isEmpty() - && m_tabWindows.at(0) - && m_tabWindows.at(0).data() != window) + if (!m_rekonqWindows.isEmpty() + && m_rekonqWindows.at(0) + && m_rekonqWindows.at(0).data() != window) { - int index = m_tabWindows.indexOf(QWeakPointer<TabWindow>(window)); + int index = m_rekonqWindows.indexOf(QWeakPointer<RekonqWindow>(window)); Q_ASSERT(index != -1); - m_tabWindows.prepend(m_tabWindows.takeAt(index)); + m_rekonqWindows.prepend(m_rekonqWindows.takeAt(index)); } } } @@ -478,14 +479,14 @@ bool Application::eventFilter(QObject* watched, QEvent* event) // when we close one of them, remove from tab window list and check if it was last... if (event->type() == QEvent::Close) { - TabWindow *window = qobject_cast<TabWindow*>(watched); + RekonqWindow *window = qobject_cast<RekonqWindow*>(watched); if (window) - m_tabWindows.removeOne(window); + m_rekonqWindows.removeOne(window); WebTab *webApp = qobject_cast<WebTab*>(watched); m_webApps.removeOne(webApp); - if (m_tabWindows.count() == 0 && m_webApps.count() == 0) + if (m_rekonqWindows.count() == 0 && m_webApps.count() == 0) quit(); } @@ -497,7 +498,7 @@ void Application::updateConfiguration() { // ============== Tabs ================== bool b = ReKonfig::closeTabSelectPrevious(); - Q_FOREACH(const QWeakPointer<TabWindow> &w, m_tabWindows) + Q_FOREACH(const QWeakPointer<RekonqWindow> &w, m_rekonqWindows) { if (b) w.data()->tabBar()->setSelectionBehaviorOnRemove(QTabBar::SelectPreviousTab); @@ -519,9 +520,9 @@ void Application::updateConfiguration() // compute font size // (I have to admit I know nothing about these DPI questions..: copied from kwebkitpart, as someone suggested) // font size in pixels = font size in inches × screen dpi - if (tabWindow() && tabWindow()->currentWebWindow()) + if (rekonqWindow() && rekonqWindow()->currentWebWindow()) { - int logDpiY = tabWindow()->currentWebWindow()->logicalDpiY(); + int logDpiY = rekonqWindow()->currentWebWindow()->logicalDpiY(); float toPix = (logDpiY < 96.0) ? 96.0 / 72.0 : logDpiY / 72.0 ; @@ -580,13 +581,13 @@ void Application::updateConfiguration() defaultSettings = 0; - if (!tabWindow()) + if (!rekonqWindow()) return; // FIXME What about this? // ReKonfig::useFavicon() -// ? tabWindow()->changeWindowIcon(tabWindow()->mainView()->currentIndex()) -// : tabWindow()->setWindowIcon(KIcon("rekonq")) +// ? rekonqWindow()->changeWindowIcon(rekonqWindow()->mainView()->currentIndex()) +// : rekonqWindow()->setWindowIcon(KIcon("rekonq")) // ; // // hovering unfocused tabs options @@ -594,23 +595,23 @@ void Application::updateConfiguration() { case 0: // tab previews case 3: // nothing - for (int i = 0; i < tabWindow()->tabBar()->count(); i++) + for (int i = 0; i < rekonqWindow()->tabBar()->count(); i++) { - tabWindow()->tabBar()->setTabToolTip(i, QL1S("")); + rekonqWindow()->tabBar()->setTabToolTip(i, QL1S("")); } break; case 1: // title previews - for (int i = 0; i < tabWindow()->tabBar()->count(); i++) + for (int i = 0; i < rekonqWindow()->tabBar()->count(); i++) { - tabWindow()->tabBar()->setTabToolTip(i, tabWindow()->tabText(i).remove('&')); + rekonqWindow()->tabBar()->setTabToolTip(i, rekonqWindow()->tabWidget()->tabText(i).remove('&')); } break; case 2: // url previews - for (int i = 0; i < tabWindow()->tabBar()->count(); i++) + for (int i = 0; i < rekonqWindow()->tabBar()->count(); i++) { - tabWindow()->tabBar()->setTabToolTip(i, tabWindow()->webWindow(i)->url().toMimeDataString()); + rekonqWindow()->tabBar()->setTabToolTip(i, rekonqWindow()->tabWidget()->webWindow(i)->url().toMimeDataString()); } break; @@ -626,14 +627,14 @@ void Application::queryQuit() { if (m_webApps.count() > 0) { - tabWindow()->close(); + rekonqWindow()->close(); return; } - if (tabWindowList().count() > 1) + if (rekonqWindowList().count() > 1) { int answer = KMessageBox::questionYesNoCancel( - tabWindow(), + rekonqWindow(), i18n("Do you want to close the window or the whole application?"), i18n("Application/Window closing..."), KGuiItem(i18n("C&lose Current Window"), @@ -646,7 +647,7 @@ void Application::queryQuit() switch (answer) { case KMessageBox::Yes: - tabWindow()->close(); + rekonqWindow()->close(); return; case KMessageBox::No: @@ -664,7 +665,7 @@ void Application::queryQuit() void Application::clearPrivateData() { - QPointer<KDialog> dialog = new KDialog(tabWindow()); + QPointer<KDialog> dialog = new KDialog(rekonqWindow()); dialog->setCaption(i18nc("@title:window", "Clear Private Data")); dialog->setButtons(KDialog::Ok | KDialog::Cancel); @@ -741,10 +742,10 @@ void Application::clearPrivateData() void Application::createWebAppShortcut() { - KUrl u = tabWindow()->currentWebWindow()->url(); + KUrl u = rekonqWindow()->currentWebWindow()->url(); QString h = u.host(); - QPointer<KDialog> dialog = new KDialog(tabWindow()); + QPointer<KDialog> dialog = new KDialog(rekonqWindow()); dialog->setCaption(i18nc("@title:window", "Create Application Shortcut")); dialog->setButtons(KDialog::Ok | KDialog::Cancel); dialog->button(KDialog::Ok)->setText(i18n("Create")); @@ -755,7 +756,7 @@ void Application::createWebAppShortcut() QWidget widget; wAppWidget.setupUi(&widget); - QString webAppTitle = tabWindow()->currentWebWindow()->title().remove('&'); + QString webAppTitle = rekonqWindow()->currentWebWindow()->title().remove('&'); wAppWidget.nameLineEdit->setText(webAppTitle); wAppWidget.kcfg_createDesktopAppShortcut->setChecked(ReKonfig::createDesktopAppShortcut()); wAppWidget.kcfg_createMenuAppShortcut->setChecked(ReKonfig::createMenuAppShortcut()); @@ -848,26 +849,26 @@ void Application::newPrivateBrowsingWindow() void Application::pageCreated(WebPage *pg) { - if (m_tabWindows.isEmpty()) + if (m_rekonqWindows.isEmpty()) { - // NOTE: This is "adjusted" from newTabWindow() code... - TabWindow *w = new TabWindow(pg); + // NOTE: This is "adjusted" from newRekonqWindow() code... + RekonqWindow *w = new RekonqWindow(pg); // set object name - int n = m_tabWindows.count() + 1; + int n = m_rekonqWindows.count() + 1; w->setObjectName(QL1S("win") + QString::number(n)); // This is used to track which window was activated most recently w->installEventFilter(this); - m_tabWindows.prepend(w); + m_rekonqWindows.prepend(w); w->show(); return; } - TabWindow *tw = tabWindow(); - tw->newTab(pg); + RekonqWindow *tw = rekonqWindow(); + tw->tabWidget()->newTab(pg); tw->activateWindow(); tw->raise(); diff --git a/src/application.h b/src/application.h index e7153831..5db6b424 100644 --- a/src/application.h +++ b/src/application.h @@ -39,13 +39,13 @@ #include <QWeakPointer> // Forward Declarations -class TabWindow; +class RekonqWindow; class WebWindow; class WebTab; class WebPage; -typedef QList< QWeakPointer<TabWindow> > TabWindowList; +typedef QList< QWeakPointer<RekonqWindow> > RekonqWindowList; typedef QList<WebTab *> WebAppList; // --------------------------------------------------------------------------------------------------------------- @@ -67,8 +67,8 @@ public: int newInstance(); static Application *instance(); - TabWindow *tabWindow(); - TabWindowList tabWindowList(); + RekonqWindow *rekonqWindow(); + RekonqWindowList rekonqWindowList(); WebAppList webAppList(); @@ -92,7 +92,7 @@ public Q_SLOTS: const Rekonq::OpenType& type = Rekonq::CurrentTab ); - TabWindow *newTabWindow(bool withTab = true, bool PrivateBrowsingMode = false); + RekonqWindow *newWindow(bool withTab = true, bool PrivateBrowsingMode = false); WebTab *newWebApp(); @@ -118,7 +118,7 @@ private Q_SLOTS: void pageCreated(WebPage *); private: - TabWindowList m_tabWindows; + RekonqWindowList m_rekonqWindows; WebAppList m_webApps; }; diff --git a/src/bookmarks/bookmarkowner.cpp b/src/bookmarks/bookmarkowner.cpp index 11c3585d..b7fe443b 100644 --- a/src/bookmarks/bookmarkowner.cpp +++ b/src/bookmarks/bookmarkowner.cpp @@ -35,7 +35,8 @@ #include "bookmarkmanager.h" #include "application.h" -#include "tabwindow.h" +#include "rekonqwindow.h" +#include "tabwidget.h" #include "webwindow.h" // KDE Includes @@ -119,20 +120,20 @@ KAction* BookmarkOwner::createAction(const KBookmark &bookmark, const BookmarkAc QString BookmarkOwner::currentTitle() const { - return rApp->tabWindow()->currentWebWindow()->title(); + return rApp->rekonqWindow()->currentWebWindow()->title(); } QString BookmarkOwner::currentUrl() const { - return rApp->tabWindow()->currentWebWindow()->url().url(); + return rApp->rekonqWindow()->currentWebWindow()->url().url(); } QList< QPair<QString, QString> > BookmarkOwner::currentBookmarkList() const { QList< QPair<QString, QString> > bkList; - TabWindow *view = rApp->tabWindow(); + TabWidget *view = rApp->rekonqWindow()->tabWidget(); int tabNumber = view->count(); for (int i = 0; i < tabNumber; ++i) @@ -165,7 +166,7 @@ void BookmarkOwner::openFolderinTabs(const KBookmarkGroup &bkGoup) if (urlList.length() > 8) { if (KMessageBox::warningContinueCancel( - rApp->tabWindow(), + rApp->rekonqWindow(), i18ncp("%1=Number of tabs. Value is always >=8", "You are about to open %1 tabs.\nAre you sure?", "You are about to open %1 tabs.\nAre you sure?", urlList.length())) diff --git a/src/bookmarks/bookmarkstreemodel.cpp b/src/bookmarks/bookmarkstreemodel.cpp new file mode 100644 index 00000000..8a74e3e6 --- /dev/null +++ b/src/bookmarks/bookmarkstreemodel.cpp @@ -0,0 +1,406 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Nils Weigel <nehlsen at gmail dot com> +* Copyright (C) 2010-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "bookmarkstreemodel.h" +#include "bookmarkstreemodel.moc" + +// Local Includes +#include "bookmarkmanager.h" +#include "iconmanager.h" + +// KDE Includes +#include <KBookmarkManager> +#include <KLocalizedString> +#include <KIcon> + +// Qt Includes +#include <QtCore/QMimeData> + + +BtmItem::BtmItem(const KBookmark &bm) + : m_parent(0) + , m_kbm(bm) +{ +} + + +BtmItem::~BtmItem() +{ + qDeleteAll(m_children); +} + + +QVariant BtmItem::data(int role) const +{ + if (m_kbm.isNull()) + return QVariant(); // should only happen for root item + + if (role == Qt::DisplayRole) + return m_kbm.text(); + + if (role == Qt::DecorationRole) + { + // NOTE + // this should be: + // return KIcon(m_kbm.icon()); + // but I cannot let it work :( + // I really cannot understand how let this work properly... + if (m_kbm.isGroup() || m_kbm.isSeparator()) + return KIcon(m_kbm.icon()); + else + return IconManager::self()->iconForUrl(KUrl(m_kbm.url())); + } + + if (role == Qt::UserRole) + return m_kbm.url(); + + if (role == Qt::ToolTipRole) + { + QString tooltip = m_kbm.fullText(); + if (m_kbm.isGroup()) + tooltip += i18ncp("%1=Number of items in bookmark folder", " (1 item)", " (%1 items)", childCount()); + + QString url = m_kbm.url().url(); + if (!url.isEmpty()) + { + if (!tooltip.isEmpty()) + tooltip += '\n'; + tooltip += url; + } + + if (!m_kbm.description().isEmpty()) + { + if (!tooltip.isEmpty()) + tooltip += '\n'; + tooltip += m_kbm.description(); + } + + return tooltip; + } + + return QVariant(); +} + + +int BtmItem::row() const +{ + if (m_parent) + return m_parent->m_children.indexOf(const_cast< BtmItem* >(this)); + return 0; +} + + +int BtmItem::childCount() const +{ + return m_children.count(); +} + + +BtmItem* BtmItem::child(int n) +{ + Q_ASSERT(n >= 0); + Q_ASSERT(n < childCount()); + + return m_children.at(n); +} + + +BtmItem* BtmItem::parent() const +{ + return m_parent; +} + + +void BtmItem::appendChild(BtmItem *child) +{ + if (!child) + return; + + child->m_parent = this; + m_children << child; +} + + +void BtmItem::clear() +{ + qDeleteAll(m_children); + m_children.clear(); +} + +KBookmark BtmItem::getBkm() const +{ + return m_kbm; +} + + +// ------------------------------------------------------------------------------------- + + +BookmarksTreeModel::BookmarksTreeModel(QObject *parent) + : QAbstractItemModel(parent) + , m_root(0) +{ + resetModel(); + connect(BookmarkManager::self()->manager(), SIGNAL(changed(QString, QString)), + this, SLOT(bookmarksChanged(QString))); +} + + +BookmarksTreeModel::~BookmarksTreeModel() +{ + delete m_root; +} + + +int BookmarksTreeModel::rowCount(const QModelIndex &parent) const +{ + BtmItem *parentItem = 0; + if (!parent.isValid()) + { + parentItem = m_root; + } + else + { + parentItem = static_cast<BtmItem*>(parent.internalPointer()); + } + + return parentItem->childCount(); +} + + +int BookmarksTreeModel::columnCount(const QModelIndex& /*parent*/) const +{ + return 1; +} + + +Qt::ItemFlags BookmarksTreeModel::flags(const QModelIndex &index) const +{ + Qt::ItemFlags flags = QAbstractItemModel::flags(index); + + if (!index.isValid()) + return flags | Qt::ItemIsDropEnabled; + + flags = Qt::ItemIsEnabled | Qt::ItemIsSelectable | Qt::ItemIsDragEnabled; + + if (bookmarkForIndex(index).isGroup()) + flags |= Qt::ItemIsDropEnabled; + + return flags; +} + + +QModelIndex BookmarksTreeModel::index(int row, int column, const QModelIndex &parent) const +{ + if (!hasIndex(row, column, parent)) + return QModelIndex(); + + BtmItem *parentItem; + + if (!parent.isValid()) + parentItem = m_root; + else + parentItem = static_cast<BtmItem*>(parent.internalPointer()); + + BtmItem *childItem = parentItem->child(row); + if (childItem) + return createIndex(row, column, childItem); + + return QModelIndex(); +} + + +QModelIndex BookmarksTreeModel::parent(const QModelIndex &index) const +{ + if (!index.isValid()) + return QModelIndex(); + + BtmItem *childItem = static_cast<BtmItem*>(index.internalPointer()); + BtmItem *parentItem = childItem->parent(); + + if (parentItem == m_root) + return QModelIndex(); + + return createIndex(parentItem->row(), 0, parentItem); +} + + +QVariant BookmarksTreeModel::data(const QModelIndex &index, int role) const +{ + if (!index.isValid()) + return QVariant(); + + BtmItem *node = static_cast<BtmItem*>(index.internalPointer()); + if (node && node == m_root) + { + if (role == Qt::DisplayRole) + return i18n("Bookmarks"); + if (role == Qt::DecorationRole) + return KIcon("bookmarks"); + } + else + { + if (node) + return node->data(role); + } + + return QVariant(); +} + + +QStringList BookmarksTreeModel::mimeTypes() const +{ + return QStringList(BookmarkManager::bookmark_mime_type()); +} + + +bool BookmarksTreeModel::dropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column, const QModelIndex &parent) +{ + if (action != Qt::MoveAction || !data->hasFormat(BookmarkManager::bookmark_mime_type())) + return false; + + QByteArray addresses = data->data(BookmarkManager::bookmark_mime_type()); + KBookmark bookmark = BookmarkManager::self()->findByAddress(QString::fromLatin1(addresses.data())); + + KBookmarkGroup root; + if (parent.isValid()) + root = bookmarkForIndex(parent).toGroup(); + else + root = BookmarkManager::self()->rootGroup(); + + QModelIndex destIndex = index(row, column, parent); + + if (destIndex.isValid() && row != -1) + { + root.moveBookmark(bookmark, root.previous(bookmarkForIndex(destIndex))); + } + else + { + root.deleteBookmark(bookmark); + root.addBookmark(bookmark); + } + + BookmarkManager::self()->emitChanged(); + + return true; +} + + +Qt::DropActions BookmarksTreeModel::supportedDropActions() const +{ + return Qt::MoveAction; +} + + +QMimeData* BookmarksTreeModel::mimeData(const QModelIndexList &indexes) const +{ + QMimeData *mimeData = new QMimeData; + + QByteArray address = bookmarkForIndex(indexes.first()).address().toLatin1(); + mimeData->setData(BookmarkManager::bookmark_mime_type(), address); + bookmarkForIndex(indexes.first()).populateMimeData(mimeData); + + return mimeData; +} + + +void BookmarksTreeModel::bookmarksChanged(const QString &groupAddress) +{ + if (groupAddress.isEmpty()) + { + resetModel(); + } + else + { + beginResetModel(); + BtmItem *node = m_root; + QModelIndex nodeIndex; + + QStringList indexChain(groupAddress.split('/', QString::SkipEmptyParts)); + bool ok; + int i; + Q_FOREACH(const QString & sIndex, indexChain) + { + i = sIndex.toInt(&ok); + if (!ok) + break; + + if (i < 0 || i >= node->childCount()) + break; + + node = node->child(i); + nodeIndex = index(i, 0, nodeIndex); + } + populate(node, BookmarkManager::self()->findByAddress(groupAddress).toGroup()); + endResetModel(); + } + + emit bookmarksUpdated(); +} + + +void BookmarksTreeModel::resetModel() +{ + setRoot(BookmarkManager::self()->rootGroup()); +} + + +void BookmarksTreeModel::setRoot(KBookmarkGroup bmg) +{ + beginResetModel(); + delete m_root; + m_root = new BtmItem(KBookmark()); + populate(m_root, bmg); + endResetModel(); +} + + +void BookmarksTreeModel::populate(BtmItem *node, KBookmarkGroup bmg) +{ + node->clear(); + + if (bmg.isNull()) + return; + + KBookmark bm = bmg.first(); + while (!bm.isNull()) + { + BtmItem *newChild = new BtmItem(bm); + if (bm.isGroup()) + populate(newChild, bm.toGroup()); + + node->appendChild(newChild); + bm = bmg.next(bm); + } +} + + +KBookmark BookmarksTreeModel::bookmarkForIndex(const QModelIndex &index) const +{ + return static_cast<BtmItem*>(index.internalPointer())->getBkm(); +} diff --git a/src/bookmarks/bookmarkstreemodel.h b/src/bookmarks/bookmarkstreemodel.h new file mode 100644 index 00000000..d12c898d --- /dev/null +++ b/src/bookmarks/bookmarkstreemodel.h @@ -0,0 +1,116 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Nils Weigel <nehlsen at gmail dot com> +* Copyright (C) 2010-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef BOOKMARKS_TREE_MODEL_H +#define BOOKMARKS_TREE_MODEL_H + + +// Rekonq Includes +#include "rekonq_defines.h" + +// KDE includes +#include <KBookmark> + +// Qt Includes +#include <QtCore/QAbstractItemModel> + + +class BtmItem +{ +public: + BtmItem(const KBookmark &bm); + ~BtmItem(); + + QVariant data(int role = Qt::DisplayRole) const; + int row() const; + int childCount() const; + BtmItem* child(int n); + BtmItem* parent() const; + void appendChild(BtmItem *child); + void clear(); + KBookmark getBkm() const; + +private: + BtmItem *m_parent; + QList< BtmItem* > m_children; + KBookmark m_kbm; +}; + + +// ------------------------------------------------------------------------------------------------- + + +class REKONQ_TESTS_EXPORT BookmarksTreeModel : public QAbstractItemModel +{ + Q_OBJECT + +public: + explicit BookmarksTreeModel(QObject *parent = 0); + virtual ~BookmarksTreeModel(); + + /** + * @return number of rows under the given parent. + */ + virtual int rowCount(const QModelIndex &parent = QModelIndex()) const; + /** + * @return number of columns (always 1). + */ + virtual int columnCount(const QModelIndex &parent = QModelIndex()) const; + + virtual Qt::ItemFlags flags(const QModelIndex &index) const; + + /** + * @return index in the model specified by the given row, column and parent. + */ + virtual QModelIndex index(int row, int column, const QModelIndex &parent = QModelIndex()) const; + /** + * @return parent of the given index. + */ + virtual QModelIndex parent(const QModelIndex &index) const; + virtual QVariant data(const QModelIndex &index, int role) const; + + virtual QStringList mimeTypes() const; + virtual bool dropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column, const QModelIndex &parent); + virtual Qt::DropActions supportedDropActions() const; + virtual QMimeData *mimeData(const QModelIndexList &indexes) const; + +private Q_SLOTS: + void bookmarksChanged(const QString &groupAddress); + +Q_SIGNALS: + void bookmarksUpdated(); + +private: + void resetModel(); + void setRoot(KBookmarkGroup bmg); + void populate(BtmItem *node, KBookmarkGroup bmg); + KBookmark bookmarkForIndex(const QModelIndex &index) const; + + BtmItem *m_root; +}; + +#endif // BOOKMARKS_TREE_MODEL_H diff --git a/src/history/historymodels.cpp b/src/history/historymodels.cpp index 4e1ca01f..76b504d3 100644 --- a/src/history/historymodels.cpp +++ b/src/history/historymodels.cpp @@ -748,20 +748,20 @@ void HistoryTreeModel::sourceRowsRemoved(const QModelIndex &parent, int start, i // ---------------------------------------------------------------------------------------------------------- -UrlFilterProxyModel::UrlFilterProxyModel(QObject *parent) +SortFilterProxyModel::SortFilterProxyModel(QObject *parent) : QSortFilterProxyModel(parent) { setFilterCaseSensitivity(Qt::CaseInsensitive); } -bool UrlFilterProxyModel::filterAcceptsRow(const int source_row, const QModelIndex &source_parent) const +bool SortFilterProxyModel::filterAcceptsRow(const int source_row, const QModelIndex &source_parent) const { return recursiveMatch(sourceModel()->index(source_row, 0, source_parent)); } -bool UrlFilterProxyModel::recursiveMatch(const QModelIndex &index) const +bool SortFilterProxyModel::recursiveMatch(const QModelIndex &index) const { if (index.data().toString().contains(filterRegExp())) return true; diff --git a/src/history/historymodels.h b/src/history/historymodels.h index be0cb442..598c8de3 100644 --- a/src/history/historymodels.h +++ b/src/history/historymodels.h @@ -186,12 +186,12 @@ private: * If a url matches the filter it'll be shown, * even if it's parent doesn't match it. */ -class UrlFilterProxyModel : public QSortFilterProxyModel +class SortFilterProxyModel : public QSortFilterProxyModel { Q_OBJECT public: - explicit UrlFilterProxyModel(QObject *parent = 0); + explicit SortFilterProxyModel(QObject *parent = 0); protected: virtual bool filterAcceptsRow(const int source_row, const QModelIndex &source_parent) const; diff --git a/src/icons/iconmanager.cpp b/src/icons/iconmanager.cpp index e0408577..c8775ed3 100644 --- a/src/icons/iconmanager.cpp +++ b/src/icons/iconmanager.cpp @@ -74,7 +74,7 @@ IconManager::IconManager(QObject *parent) KIcon IconManager::iconForUrl(const KUrl &url) { // first things first.. avoid infinite loop at startup - if (url.isEmpty() || (rApp->tabWindowList().isEmpty() && rApp->webAppList().isEmpty())) + if (url.isEmpty() || (rApp->rekonqWindowList().isEmpty() && rApp->webAppList().isEmpty())) return KIcon("text-html"); QByteArray encodedUrl = url.toEncoded(); @@ -192,7 +192,7 @@ void IconManager::saveDesktopIconForUrl(const KUrl &u) QString IconManager::iconPathForUrl(const KUrl &url) { // first things first.. avoid infinite loop at startup - if (url.isEmpty() || rApp->tabWindowList().isEmpty()) + if (url.isEmpty() || rApp->rekonqWindowList().isEmpty()) { QString icon = QL1S("file://") + KGlobal::dirs()->findResource("icon", "oxygen/16x16/mimetypes/text-html.png"); return icon; diff --git a/src/main.cpp b/src/main.cpp index eabbfde5..0d4527c4 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -30,7 +30,7 @@ // Local Includes #include "application.h" #include "sessionmanager.h" -#include "tabwindow.h" +#include "rekonqwindow.h" #include "urlresolver.h" // KDE Includes @@ -230,12 +230,14 @@ extern "C" KDE_EXPORT int kdemain(int argc, char **argv) QCoreApplication::setApplicationVersion(REKONQ_VERSION); if (app.isSessionRestored()) - for (int i = 1; TabWindow::canBeRestored(i); i++) + { + for (int i = 1; RekonqWindow::canBeRestored(i); i++) { - TabWindow * newTabWindow = app.newTabWindow(false); - if (newTabWindow->restore(i)) - SessionManager::self()->restoreTabWindow(newTabWindow); + RekonqWindow * newRekonqWindow = app.newWindow(false); + if (newRekonqWindow->restore(i)) + SessionManager::self()->restoreWindow(newRekonqWindow); } - + } + return app.exec(); } diff --git a/src/panels/bookmarkspanel.cpp b/src/panels/bookmarkspanel.cpp new file mode 100644 index 00000000..57796a23 --- /dev/null +++ b/src/panels/bookmarkspanel.cpp @@ -0,0 +1,170 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Nils Weigel <nehlsen at gmail dot com> +* Copyright (C) 2010-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* Copyright (C) 2010 by Yoann Laissus <yoann dot laissus at gmail dot com> +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "bookmarkspanel.h" +#include "bookmarkspanel.moc" + +// Auto Includes +#include "rekonq.h" + +// Local Includes +#include "bookmarkmanager.h" +#include "bookmarkstreemodel.h" +#include "bookmarkscontextmenu.h" +#include "bookmarkowner.h" + +#include "paneltreeview.h" +#include "urlfilterproxymodel.h" + + +BookmarksPanel::BookmarksPanel(const QString &title, QWidget *parent, Qt::WindowFlags flags) + : UrlPanel(title, parent, flags) + , _bkTreeModel(new BookmarksTreeModel(this)) + , _loadingState(false) +{ + setObjectName("bookmarksPanel"); + setVisible(ReKonfig::showBookmarksPanel()); + + panelTreeView()->setDragEnabled(true); + panelTreeView()->setAcceptDrops(true); + connect(_bkTreeModel, SIGNAL(bookmarksUpdated()), this, SLOT(loadFoldedState())); +} + + +BookmarksPanel::~BookmarksPanel() +{ + ReKonfig::setShowBookmarksPanel(!isHidden()); +} + + +void BookmarksPanel::loadFoldedState() +{ + _loadingState = true; + loadFoldedState(QModelIndex()); + _loadingState = false; +} + + +void BookmarksPanel::contextMenu(const QPoint &pos) +{ + if (_loadingState) + return; + + BookmarksContextMenu menu(bookmarkForIndex(panelTreeView()->indexAt(pos)), + BookmarkManager::self()->manager(), + BookmarkManager::self()->owner() + ); + + menu.exec(panelTreeView()->mapToGlobal(pos)); +} + + +void BookmarksPanel::deleteBookmark() +{ + QModelIndex index = panelTreeView()->currentIndex(); + if (_loadingState || !index.isValid()) + return; + + BookmarkManager::self()->owner()->deleteBookmark(bookmarkForIndex(index)); +} + + +void BookmarksPanel::onCollapse(const QModelIndex &index) +{ + if (_loadingState) + return; + + bookmarkForIndex(index).internalElement().setAttribute("folded", "yes"); + emit expansionChanged(); +} + + +void BookmarksPanel::onExpand(const QModelIndex &index) +{ + if (_loadingState) + return; + + bookmarkForIndex(index).internalElement().setAttribute("folded", "no"); + emit expansionChanged(); +} + + +void BookmarksPanel::setup() +{ + UrlPanel::setup(); + + connect(panelTreeView(), SIGNAL(delKeyPressed()), this, SLOT(deleteBookmark())); + connect(panelTreeView(), SIGNAL(collapsed(QModelIndex)), this, SLOT(onCollapse(QModelIndex))); + connect(panelTreeView(), SIGNAL(expanded(QModelIndex)), this, SLOT(onExpand(QModelIndex))); + + loadFoldedState(); +} + + +void BookmarksPanel::loadFoldedState(const QModelIndex &root) +{ + QAbstractItemModel *model = panelTreeView()->model(); + if (!model) + return; + + int count = model->rowCount(root); + QModelIndex index; + + for (int i = 0; i < count; ++i) + { + index = model->index(i, 0, root); + if (index.isValid()) + { + KBookmark bm = bookmarkForIndex(index); + if (bm.isGroup()) + { + panelTreeView()->setExpanded(index, bm.toGroup().isOpen()); + loadFoldedState(index); + } + } + } +} + + +KBookmark BookmarksPanel::bookmarkForIndex(const QModelIndex &index) +{ + if (!index.isValid()) + return KBookmark(); + + const UrlFilterProxyModel *proxyModel = static_cast<const UrlFilterProxyModel*>(index.model()); + QModelIndex originalIndex = proxyModel->mapToSource(index); + + BtmItem *node = static_cast<BtmItem*>(originalIndex.internalPointer()); + return node->getBkm(); +} + + +QAbstractItemModel* BookmarksPanel::model() +{ + return _bkTreeModel; +} diff --git a/src/panels/bookmarkspanel.h b/src/panels/bookmarkspanel.h new file mode 100644 index 00000000..8c827c65 --- /dev/null +++ b/src/panels/bookmarkspanel.h @@ -0,0 +1,93 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Nils Weigel <nehlsen at gmail dot com> +* Copyright (C) 2010-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* Copyright (C) 2010 by Yoann Laissus <yoann dot laissus at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef BOOKMARKS_PANEL_H +#define BOOKMARKS_PANEL_H + + +// Rekonq Includes +#include "rekonq_defines.h" + +// Local Includes +#include "urlpanel.h" + +// Forward Declarations +class BookmarksTreeModel; + +class KBookmark; +class QModelIndex; + + +class REKONQ_TESTS_EXPORT BookmarksPanel : public UrlPanel +{ + Q_OBJECT + +public: + explicit BookmarksPanel(const QString &title, QWidget *parent = 0, Qt::WindowFlags flags = 0); + ~BookmarksPanel(); + +public Q_SLOTS: + void loadFoldedState(); + +Q_SIGNALS: + void expansionChanged(); + +private Q_SLOTS: + void contextMenu(const QPoint &pos); + + virtual void contextMenuItem(const QPoint &pos) + { + contextMenu(pos); + } + virtual void contextMenuGroup(const QPoint &pos) + { + contextMenu(pos); + } + virtual void contextMenuEmpty(const QPoint &pos) + { + contextMenu(pos); + } + + void deleteBookmark(); + void onCollapse(const QModelIndex &index); + void onExpand(const QModelIndex &index); + +private: + virtual void setup(); + + void loadFoldedState(const QModelIndex &root); + + KBookmark bookmarkForIndex(const QModelIndex &index); + + virtual QAbstractItemModel* model(); + + BookmarksTreeModel *_bkTreeModel; + bool _loadingState; +}; + +#endif // BOOKMARKS_PANEL_H diff --git a/src/panels/historypanel.cpp b/src/panels/historypanel.cpp new file mode 100644 index 00000000..30d2cb6b --- /dev/null +++ b/src/panels/historypanel.cpp @@ -0,0 +1,214 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com> +* Copyright (C) 2009-2011 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "historypanel.h" +#include "historypanel.moc" + +// Auto Includes +#include "rekonq.h" + +// Local Includes +#include "paneltreeview.h" + +#include "historymanager.h" +#include "historymodels.h" +#include "urlfilterproxymodel.h" + +// KDE Includes +#include <KLocalizedString> +#include <KMenu> +#include <KAction> +#include <KMessageBox> + +// Qt Includes +#include <QHeaderView> + + +HistoryPanel::HistoryPanel(const QString &title, QWidget *parent, Qt::WindowFlags flags) + : UrlPanel(title, parent, flags) +{ + setObjectName("historyPanel"); + setVisible(ReKonfig::showHistoryPanel()); +} + + +HistoryPanel::~HistoryPanel() +{ + ReKonfig::setShowHistoryPanel(!isHidden()); +} + + +void HistoryPanel::contextMenuItem(const QPoint &pos) +{ + KMenu menu; + KAction* action; + + action = new KAction(KIcon("tab-new"), i18n("Open"), this); + connect(action, SIGNAL(triggered()), panelTreeView(), SLOT(openInCurrentTab())); + menu.addAction(action); + + action = new KAction(KIcon("tab-new"), i18n("Open in New Tab"), this); + connect(action, SIGNAL(triggered()), panelTreeView(), SLOT(openInNewTab())); + menu.addAction(action); + + action = new KAction(KIcon("window-new"), i18n("Open in New Window"), this); + connect(action, SIGNAL(triggered()), panelTreeView(), SLOT(openInNewWindow())); + menu.addAction(action); + + action = new KAction(KIcon("edit-copy"), i18n("Copy Link Address"), this); + connect(action, SIGNAL(triggered()), panelTreeView(), SLOT(copyToClipboard())); + menu.addAction(action); + + action = new KAction(KIcon("edit-clear"), i18n("Remove Entry"), this); + connect(action, SIGNAL(triggered()), this, SLOT(deleteEntry())); + menu.addAction(action); + + action = new KAction(KIcon("edit-clear"), i18n("Remove all occurrences"), this); + connect(action, SIGNAL(triggered()), this, SLOT(forgetSite())); + menu.addAction(action); + + menu.exec(panelTreeView()->mapToGlobal(pos)); +} + + +void HistoryPanel::contextMenuGroup(const QPoint &pos) +{ + KMenu menu; + KAction* action; + + action = new KAction(KIcon("tab-new"), i18n("Open Folder in Tabs"), this); + connect(action, SIGNAL(triggered()), this, SLOT(openAll())); + menu.addAction(action); + + action = new KAction(KIcon("edit-clear"), i18n("Remove Folder"), this); + connect(action, SIGNAL(triggered()), this, SLOT(deleteGroup())); + menu.addAction(action); + + menu.exec(panelTreeView()->mapToGlobal(pos)); +} + + +void HistoryPanel::contextMenuEmpty(const QPoint& /*pos*/) +{ +} + + +void HistoryPanel::openAll() +{ + QModelIndex index = panelTreeView()->currentIndex(); + if (!index.isValid()) + return; + + QList<KUrl> allChild; + + for (int i = 0; i < index.model()->rowCount(index); i++) + allChild << qVariantValue<KUrl>(index.child(i, 0).data(Qt::UserRole)); + + if (allChild.length() > 8) + { + if (!(KMessageBox::warningContinueCancel(this, + i18ncp("%1=Number of tabs. Value is always >=8", + "You are about to open %1 tabs.\nAre you sure?", + "You are about to open %1 tabs.\nAre you sure?", + allChild.length())) == KMessageBox::Continue) + ) + return; + } + + for (int i = 0; i < allChild.length(); i++) + emit openUrl(allChild.at(i).url(), Rekonq::NewTab); +} + + +void HistoryPanel::deleteGroup() +{ + QModelIndex index = panelTreeView()->currentIndex(); + if (!index.isValid()) + return; + + //Getting all URLs of sub items. + QList<KUrl> allChild; + for (int i = 0; i < index.model()->rowCount(index); i++) + allChild << qVariantValue<KUrl>(index.child(i, 0).data(Qt::UserRole)); + + for (int i = 0; i < allChild.length(); i++) + HistoryManager::self()->removeHistoryEntry(allChild.at(i)); + +} + + +void HistoryPanel::setup() +{ + UrlPanel::setup(); + + panelTreeView()->header()->hideSection(1); + + const UrlFilterProxyModel *proxy = static_cast<const UrlFilterProxyModel*>(panelTreeView()->model()); + panelTreeView()->expand(proxy->index(0, 0)); +} + + +void HistoryPanel::deleteEntry() +{ + QModelIndex index = panelTreeView()->currentIndex(); + if (!index.isValid()) + return; + removedFolderIndex = index.parent().row(); + + HistoryManager::self()->removeHistoryEntry(qVariantValue< KUrl >(index.data(Qt::UserRole))); + + QModelIndex expandItem = panelTreeView()->model()->index(removedFolderIndex, 0); + if (expandItem.isValid()) + panelTreeView()->expand(expandItem); +} + + +void HistoryPanel::forgetSite() +{ + QModelIndex index = panelTreeView()->currentIndex(); + if (!index.isValid()) + return; + removedFolderIndex = index.row(); + + QString site = qVariantValue< KUrl >(index.data(Qt::UserRole)).host(); + QList<HistoryItem> toRemove = HistoryManager::self()->find(site); + for (int i = 0; i < toRemove.length(); i++) + { + HistoryManager::self()->removeHistoryEntry(KUrl(toRemove.at(i).url)); + } + + QModelIndex expandItem = panelTreeView()->model()->index(removedFolderIndex, 0); + if (expandItem.isValid()) + panelTreeView()->expand(expandItem); +} + + +QAbstractItemModel* HistoryPanel::model() +{ + return HistoryManager::self()->historyTreeModel(); +} diff --git a/src/panels/historypanel.h b/src/panels/historypanel.h new file mode 100644 index 00000000..bae55d76 --- /dev/null +++ b/src/panels/historypanel.h @@ -0,0 +1,63 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com> +* Copyright (C) 2009-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef HISTORYPANEL_H +#define HISTORYPANEL_H + + +// Rekonq Includes +#include "rekonq_defines.h" + +// Local Includes +#include "urlpanel.h" + + +class REKONQ_TESTS_EXPORT HistoryPanel : public UrlPanel +{ + Q_OBJECT + +public: + explicit HistoryPanel(const QString &title, QWidget *parent = 0, Qt::WindowFlags flags = 0); + virtual ~HistoryPanel(); + +private Q_SLOTS: + virtual void contextMenuItem(const QPoint &pos); + virtual void contextMenuGroup(const QPoint &pos); + virtual void contextMenuEmpty(const QPoint &pos); + + void openAll(); + void deleteEntry(); + void deleteGroup(); + void forgetSite(); + +private: + virtual void setup(); + virtual QAbstractItemModel* model(); + int removedFolderIndex; +}; + +#endif // HISTORYPANEL_H diff --git a/src/panels/paneltreeview.cpp b/src/panels/paneltreeview.cpp new file mode 100644 index 00000000..722ba8a9 --- /dev/null +++ b/src/panels/paneltreeview.cpp @@ -0,0 +1,186 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2010 by Yoann Laissus <yoann dot laissus at gmail dot com> +* Copyright (C) 2012-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "paneltreeview.h" +#include "paneltreeview.moc" + +// Local Includes +#include "application.h" + +// KDE Includes +#include <KUrl> + +// Qt Includes +#include <QClipboard> +#include <QMouseEvent> + + +PanelTreeView::PanelTreeView(QWidget *parent) + : QTreeView(parent) +{ + connect(this, SIGNAL(itemHovered(QString)), parent, SIGNAL(itemHovered(QString))); + connect(this, SIGNAL(openUrl(KUrl, Rekonq::OpenType)), parent, SIGNAL(openUrl(KUrl, Rekonq::OpenType))); + + setMouseTracking(true); + setExpandsOnDoubleClick(false); +} + + +void PanelTreeView::mousePressEvent(QMouseEvent *event) +{ + const QModelIndex index = indexAt(event->pos()); + bool expanded = isExpanded(index); + + QTreeView::mousePressEvent(event); + + // A change of an item expansion is handle by mouseReleaseEvent() + // So toggle again the item + if (expanded != isExpanded(index)) + setExpanded(index, !isExpanded(index)); + + if (!index.isValid()) + { + clearSelection(); + setCurrentIndex(QModelIndex()); + + if (event->button() == Qt::RightButton) + emit contextMenuEmptyRequested(event->pos()); + return; + } + + if (event->button() == Qt::RightButton) + { + if (model()->rowCount(index) == 0) + { + // An empty group needs to be handle by the panels + emit contextMenuItemRequested(event->pos()); + } + else + { + emit contextMenuGroupRequested(event->pos()); + } + } +} + + +void PanelTreeView::mouseReleaseEvent(QMouseEvent *event) +{ + QTreeView::mouseReleaseEvent(event); + + const QModelIndex index = indexAt(event->pos()); + if (!index.isValid()) + return; + + if (event->button() == Qt::MidButton || event->modifiers() == Qt::ControlModifier) + emit openUrl(qVariantValue< KUrl >(index.data(Qt::UserRole)), Rekonq::NewTab); + + else if (event->button() == Qt::LeftButton) + { + if (model()->rowCount(index) == 0) + emit openUrl(qVariantValue< KUrl >(index.data(Qt::UserRole))); + else + setExpanded(index, !isExpanded(index)); + } +} + + +void PanelTreeView::keyPressEvent(QKeyEvent *event) +{ + QTreeView::keyPressEvent(event); + QModelIndex index = currentIndex(); + + if (!index.isValid()) + return; + + if (event->key() == Qt::Key_Return) + { + if (model()->rowCount(index) == 0) + openUrl(qVariantValue< KUrl >(index.data(Qt::UserRole))); + else + setExpanded(index, !isExpanded(index)); + } + + else if (event->key() == Qt::Key_Delete) + { + emit delKeyPressed(); + } +} + + +void PanelTreeView::mouseMoveEvent(QMouseEvent *event) +{ + QTreeView::mouseMoveEvent(event); + const QModelIndex index = indexAt(event->pos()); + if (!index.isValid()) + { + emit itemHovered(""); + return; + } + emit itemHovered(qVariantValue< KUrl >(index.data(Qt::UserRole)).url()); +} + + +void PanelTreeView::openInCurrentTab() +{ + QModelIndex index = currentIndex(); + if (!index.isValid()) + return; + + emit openUrl(qVariantValue< KUrl >(index.data(Qt::UserRole))); +} + + +void PanelTreeView::copyToClipboard() +{ + QModelIndex index = currentIndex(); + if (!index.isValid()) + return; + + QClipboard *cb = QApplication::clipboard(); + cb->setText(qVariantValue< KUrl >(index.data(Qt::UserRole)).url()); +} + + +void PanelTreeView::openInNewTab() +{ + QModelIndex index = currentIndex(); + if (!index.isValid()) + return; + + emit openUrl(qVariantValue< KUrl >(index.data(Qt::UserRole)), Rekonq::NewTab); +} + + +void PanelTreeView::openInNewWindow() +{ + QModelIndex index = currentIndex(); + if (!index.isValid()) + return; + + emit openUrl(qVariantValue< KUrl >(index.data(Qt::UserRole)), Rekonq::NewWindow); +} diff --git a/src/panels/paneltreeview.h b/src/panels/paneltreeview.h new file mode 100644 index 00000000..ee8c51d0 --- /dev/null +++ b/src/panels/paneltreeview.h @@ -0,0 +1,69 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2010-2011 by Yoann Laissus <yoann dot laissus at gmail dot com> +* Copyright (C) 2012-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef PANELTREEVIEW_H +#define PANELTREEVIEW_H + +// Rekonq Includes +#include "rekonq_defines.h" + +// Qt Includes +#include <QTreeView> + +// Forward Declarations +class KUrl; + + +class REKONQ_TESTS_EXPORT PanelTreeView : public QTreeView +{ + Q_OBJECT + +public: + PanelTreeView(QWidget *parent = 0); + +Q_SIGNALS: + void openUrl(const KUrl &, const Rekonq::OpenType & = Rekonq::CurrentTab); + void itemHovered(const QString &); + void delKeyPressed(); + void contextMenuItemRequested(const QPoint &pos); + void contextMenuGroupRequested(const QPoint &pos); + void contextMenuEmptyRequested(const QPoint &pos); + +public Q_SLOTS: + void copyToClipboard(); + void openInCurrentTab(); + void openInNewTab(); + void openInNewWindow(); + +protected: + void mouseReleaseEvent(QMouseEvent *event); + void mousePressEvent(QMouseEvent *event); + void mouseMoveEvent(QMouseEvent *event); + void keyPressEvent(QKeyEvent *event); +}; + +#endif // PANELTREEVIEW_H diff --git a/src/panels/urlfilterproxymodel.cpp b/src/panels/urlfilterproxymodel.cpp new file mode 100644 index 00000000..aa9ac7a6 --- /dev/null +++ b/src/panels/urlfilterproxymodel.cpp @@ -0,0 +1,59 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Nils Weigel <nehlsen at gmail dot com> +* Copyright (C) 2010-2011 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "urlfilterproxymodel.h" +#include "urlfilterproxymodel.moc" + + +UrlFilterProxyModel::UrlFilterProxyModel(QObject *parent) + : QSortFilterProxyModel(parent) +{ + setFilterCaseSensitivity(Qt::CaseInsensitive); +} + + +bool UrlFilterProxyModel::filterAcceptsRow(const int source_row, const QModelIndex &source_parent) const +{ + return recursiveMatch(sourceModel()->index(source_row, 0, source_parent)); +} + + +bool UrlFilterProxyModel::recursiveMatch(const QModelIndex &index) const +{ + if (index.data().toString().contains(filterRegExp())) + return true; + + int numChildren = sourceModel()->rowCount(index); + for (int childRow = 0; childRow < numChildren; ++childRow) + { + if (recursiveMatch(sourceModel()->index(childRow, 0, index))) + return true; + } + + return false; +} diff --git a/src/panels/urlfilterproxymodel.h b/src/panels/urlfilterproxymodel.h new file mode 100644 index 00000000..6cb8574e --- /dev/null +++ b/src/panels/urlfilterproxymodel.h @@ -0,0 +1,59 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Nils Weigel <nehlsen at gmail dot com> +* Copyright (C) 2010-2011 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef URLFILTERPROXYMODEL_H +#define URLFILTERPROXYMODEL_H + + +// Rekonq Includes +#include "rekonq_defines.h" + +// Qt Includes +#include <QSortFilterProxyModel> + + +/** + * QSortFilterProxyModel hides all children which parent doesn't + * match the filter. This class is used to change this behavior. + * If a url matches the filter it'll be shown, + * even if it's parent doesn't match it. + */ +class REKONQ_TESTS_EXPORT UrlFilterProxyModel : public QSortFilterProxyModel +{ + Q_OBJECT + +public: + explicit UrlFilterProxyModel(QObject *parent = 0); + +protected: + virtual bool filterAcceptsRow(const int source_row, const QModelIndex &source_parent) const; + + // returns true if index or any of his children match the filter + bool recursiveMatch(const QModelIndex &index) const; +}; + +#endif // URLFILTERPROXYMODEL_H diff --git a/src/panels/urlpanel.cpp b/src/panels/urlpanel.cpp new file mode 100644 index 00000000..7fb75087 --- /dev/null +++ b/src/panels/urlpanel.cpp @@ -0,0 +1,111 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com> +* Copyright (C) 2009-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "urlpanel.h" +#include "urlpanel.moc" + +// Local Includes +#include "paneltreeview.h" +#include "urlfilterproxymodel.h" + +// KDE Includes +#include <KLineEdit> +#include <KLocalizedString> + +// Qt Includes +#include <QLabel> +#include <QHBoxLayout> +#include <QHeaderView> + + +UrlPanel::UrlPanel(const QString &title, QWidget *parent, Qt::WindowFlags flags) + : QDockWidget(title, parent, flags) + , _treeView(new PanelTreeView(this)) + , _loaded(false) +{ + setAllowedAreas(Qt::LeftDockWidgetArea | Qt::RightDockWidgetArea); + + connect(this, SIGNAL(visibilityChanged(bool)), this, SLOT(showing(bool))); +} + + +void UrlPanel::showing(bool b) +{ + if (!_loaded && b) + { + setup(); + _loaded = true; + } +} + + +void UrlPanel::setup() +{ + QWidget *ui = new QWidget(this); + + // setup search bar + QHBoxLayout *searchLayout = new QHBoxLayout; + searchLayout->setContentsMargins(5, 0, 0, 0); + QLabel *searchLabel = new QLabel(i18n("&Search:")); + searchLayout->addWidget(searchLabel); + KLineEdit *search = new KLineEdit; + search->setClearButtonShown(true); + searchLayout->addWidget(search); + searchLabel->setBuddy(search); + + // setup tree view + _treeView->setUniformRowHeights(true); + _treeView->header()->hide(); + + // put everything together + QVBoxLayout *vBoxLayout = new QVBoxLayout; + vBoxLayout->setContentsMargins(0, 0, 0, 0); + vBoxLayout->addLayout(searchLayout); + vBoxLayout->addWidget(_treeView); + + // add it to the UI + ui->setLayout(vBoxLayout); + setWidget(ui); + + UrlFilterProxyModel *proxy = new UrlFilterProxyModel(this); + proxy->setSourceModel(model()); + _treeView->setModel(proxy); + + connect(search, SIGNAL(textChanged(QString)), proxy, SLOT(setFilterFixedString(QString))); + connect(search, SIGNAL(textChanged(QString)), this, SLOT(expandTreeView())); + + connect(_treeView, SIGNAL(contextMenuItemRequested(QPoint)), this, SLOT(contextMenuItem(QPoint))); + connect(_treeView, SIGNAL(contextMenuGroupRequested(QPoint)), this, SLOT(contextMenuGroup(QPoint))); + connect(_treeView, SIGNAL(contextMenuEmptyRequested(QPoint)), this, SLOT(contextMenuEmpty(QPoint))); +} + + +void UrlPanel::expandTreeView() +{ + _treeView->expandAll(); +} diff --git a/src/panels/urlpanel.h b/src/panels/urlpanel.h new file mode 100644 index 00000000..72393c9e --- /dev/null +++ b/src/panels/urlpanel.h @@ -0,0 +1,81 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2009 by Domrachev Alexandr <alexandr.domrachev@gmail.com> +* Copyright (C) 2009-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +#ifndef URLPANEL_H +#define URLPANEL_H + + +// Rekonq Includes +#include "rekonq_defines.h" + +// Qt Includes +#include <QDockWidget> + +// Forward Declarations +class PanelTreeView; + +class QAbstractItemModel; + + +class REKONQ_TESTS_EXPORT UrlPanel : public QDockWidget +{ + Q_OBJECT + +public: + explicit UrlPanel(const QString &title, QWidget *parent = 0, Qt::WindowFlags flags = 0); + +Q_SIGNALS: + void openUrl(const KUrl &, const Rekonq::OpenType &); + void itemHovered(const QString &); + +public Q_SLOTS: + void showing(bool); + +protected: + virtual void setup(); + virtual QAbstractItemModel* model() = 0; + + PanelTreeView* panelTreeView() const + { + return _treeView; + } + +protected Q_SLOTS: + virtual void contextMenuItem(const QPoint &pos) = 0; + virtual void contextMenuGroup(const QPoint &pos) = 0; + virtual void contextMenuEmpty(const QPoint &pos) = 0; + +private Q_SLOTS: + void expandTreeView(); + +private: + PanelTreeView *_treeView; + bool _loaded; +}; + + +#endif // URLPANEL_H diff --git a/src/rekonq.kcfg b/src/rekonq.kcfg index 3e8e07ff..3997587d 100644 --- a/src/rekonq.kcfg +++ b/src/rekonq.kcfg @@ -57,6 +57,12 @@ <entry name="whiteReferer" type="StringList"> <default></default> </entry> + <entry name="showHistoryPanel" type="Bool"> + <default>false</default> + </entry> + <entry name="showBookmarksPanel" type="Bool"> + <default>false</default> + </entry> </group> diff --git a/src/rekonqpage/newtabpage.cpp b/src/rekonqpage/newtabpage.cpp index c1a1f248..48b567de 100644 --- a/src/rekonqpage/newtabpage.cpp +++ b/src/rekonqpage/newtabpage.cpp @@ -34,7 +34,8 @@ // Local Includes #include "application.h" -#include "tabwindow.h" +#include "rekonqwindow.h" +#include "tabwidget.h" #include "previewselectorbar.h" #include "thumbupdater.h" @@ -181,7 +182,7 @@ void NewTabPage::generate(const KUrl &url) { const int tabIndex = url.queryItem(QL1S("tab")).toInt(); - rApp->tabWindow()->restoreClosedTab(tabIndex, false); + rApp->rekonqWindow()->tabWidget()->restoreClosedTab(tabIndex, false); return; } } @@ -430,7 +431,7 @@ void NewTabPage::historyPage(const QString & filter) m_root.document().findFirst(QL1S("#actions")).appendInside(clearHistory); HistoryTreeModel *model = HistoryManager::self()->historyTreeModel(); - UrlFilterProxyModel *proxy = new UrlFilterProxyModel(this); + SortFilterProxyModel *proxy = new SortFilterProxyModel(this); proxy->setSourceModel(model); bool filterIsEmpty = filter.isEmpty(); @@ -563,7 +564,7 @@ void NewTabPage::closedTabsPage() { m_root.addClass(QL1S("closedTabs")); - QList<TabHistory> links = rApp->tabWindow()->recentlyClosedTabs(); + QList<TabHistory> links = rApp->rekonqWindow()->tabWidget()->recentlyClosedTabs(); if (links.isEmpty()) { diff --git a/src/sessionmanager.cpp b/src/sessionmanager.cpp index e9ea5bf5..c4927cbc 100644 --- a/src/sessionmanager.cpp +++ b/src/sessionmanager.cpp @@ -35,7 +35,7 @@ #include "autosaver.h" #include "tabhistory.h" -#include "tabwindow.h" +#include "rekonqwindow.h" #include "tabbar.h" #include "webwindow.h" @@ -74,7 +74,7 @@ bool readSessionDocument(QDomDocument & document, const QString & sessionFilePat } -int loadTabs(TabWindow *tw, QDomElement & window, bool useFirstTab, bool justThePinnedOnes = false) +int loadTabs(RekonqWindow *tw, QDomElement & window, bool useFirstTab, bool justThePinnedOnes = false) { int currentTab = 0; @@ -191,38 +191,39 @@ void SessionManager::save() kDebug() << "Unable to open session file" << sessionFile.fileName(); return; } - TabWindowList wl = rApp->tabWindowList(); + RekonqWindowList wl = rApp->rekonqWindowList(); QDomDocument document("session"); QDomElement session = document.createElement("session"); document.appendChild(session); - Q_FOREACH(const QWeakPointer<TabWindow> &w, wl) + Q_FOREACH(const QWeakPointer<RekonqWindow> &w, wl) { QDomElement window = document.createElement("window"); int tabInserted = 0; window.setAttribute("name", w.data()->objectName()); - - for (signed int tabNo = 0; tabNo < w.data()->count(); tabNo++) + + TabWidget *tw = w.data()->tabWidget(); + for (signed int tabNo = 0; tabNo < tw->count(); tabNo++) { - KUrl u = w.data()->webWindow(tabNo)->url(); + KUrl u = tw->webWindow(tabNo)->url(); tabInserted++; QDomElement tab = document.createElement("tab"); - tab.setAttribute("title", w.data()->webWindow(tabNo)->title()); // redundant, but needed for closedSites() + tab.setAttribute("title", tw->webWindow(tabNo)->title()); // redundant, but needed for closedSites() // as there's not way to read out the historyData tab.setAttribute("url", u.url()); - if (w.data()->currentIndex() == tabNo) + if (tw->currentIndex() == tabNo) { tab.setAttribute("currentTab", 1); } - if (w.data()->tabBar()->tabData(tabNo).toBool()) // pinned tab info + if (tw->tabBar()->tabData(tabNo).toBool()) // pinned tab info { tab.setAttribute("pinned", 1); } QByteArray history; QDataStream historyStream(&history, QIODevice::ReadWrite); - historyStream << *(w.data()->webWindow(tabNo)->page()->history()); + historyStream << *(tw->webWindow(tabNo)->page()->history()); QDomCDATASection historySection = document.createCDATASection(history.toBase64()); tab.appendChild(historySection); @@ -252,11 +253,11 @@ bool SessionManager::restoreSessionFromScratch() { QDomElement window = document.elementsByTagName("window").at(winNo).toElement(); - TabWindow *tw = rApp->newTabWindow(); + RekonqWindow *tw = rApp->newWindow(); int currentTab = loadTabs(tw, window, true, false); - tw->setCurrentIndex(currentTab); + tw->tabWidget()->setCurrentIndex(currentTab); } return true; @@ -279,11 +280,11 @@ bool SessionManager::restoreJustThePinnedTabs() continue; done = true; - TabWindow *tw = rApp->newTabWindow(false); + RekonqWindow *tw = rApp->newWindow(false); int currentTab = loadTabs(tw, window, false, true); - tw->setCurrentIndex(currentTab); + tw->tabWidget()->setCurrentIndex(currentTab); } return done; @@ -301,22 +302,22 @@ void SessionManager::restoreCrashedSession() { QDomElement window = document.elementsByTagName("window").at(winNo).toElement(); - TabWindow *tw = (winNo == 0) - ? rApp->tabWindow() - : rApp->newTabWindow(); + RekonqWindow *tw = (winNo == 0) + ? rApp->rekonqWindow() + : rApp->newWindow(); KUrl u = tw->currentWebWindow()->url(); bool useCurrentTab = (u.isEmpty() || u.protocol() == QL1S("about")); int currentTab = loadTabs(tw, window, useCurrentTab); - tw->setCurrentIndex(currentTab); + tw->tabWidget()->setCurrentIndex(currentTab); } setSessionManagementEnabled(true); } -bool SessionManager::restoreTabWindow(TabWindow* window) +bool SessionManager::restoreWindow(RekonqWindow* window) { QDomDocument document("session"); @@ -334,7 +335,7 @@ bool SessionManager::restoreTabWindow(TabWindow* window) int currentTab = loadTabs(window, savedWindowElement, false); - window->setCurrentIndex(currentTab); + window->tabWidget()->setCurrentIndex(currentTab); return true; } diff --git a/src/sessionmanager.h b/src/sessionmanager.h index 344f3b8a..1cd2ba71 100644 --- a/src/sessionmanager.h +++ b/src/sessionmanager.h @@ -41,7 +41,8 @@ // Forward Declarations class AutoSaver; class TabHistory; -class TabWindow; + +class RekonqWindow; /** @@ -67,8 +68,8 @@ public: QList<TabHistory> closedSitesForWindow(const QString &); - // This method restores a single TabWindow - bool restoreTabWindow(TabWindow * window); + // This method restores a single Window + bool restoreWindow(RekonqWindow * window); private: explicit SessionManager(QObject *parent = 0); diff --git a/src/settings/generalwidget.cpp b/src/settings/generalwidget.cpp index ae08a01f..d64fd8d3 100644 --- a/src/settings/generalwidget.cpp +++ b/src/settings/generalwidget.cpp @@ -33,7 +33,7 @@ // Local Includes #include "application.h" -#include "tabwindow.h" +#include "rekonqwindow.h" #include "webwindow.h" //KDE Includes @@ -91,8 +91,7 @@ void GeneralWidget::hasChanged() void GeneralWidget::setHomeToCurrentPage() { - TabWindow *tw = rApp->tabWindow(); - WebWindow *tab = tw->currentWebWindow(); + WebWindow *tab = rApp->rekonqWindow()->currentWebWindow(); if (tab) { kcfg_homePage->setText(tab->url().url()); diff --git a/src/tabwindow/rekonqwindow.cpp b/src/tabwindow/rekonqwindow.cpp index ee37eba9..a14dcf15 100644 --- a/src/tabwindow/rekonqwindow.cpp +++ b/src/tabwindow/rekonqwindow.cpp @@ -2,7 +2,7 @@ * * This file is a part of the rekonq project * -* Copyright (C) 2012 by Andrea Diamantini <adjam7 at gmail dot com> +* Copyright (C) 2013 by Andrea Diamantini <adjam7 at gmail dot com> * * * This program is free software; you can redistribute it and/or @@ -27,422 +27,163 @@ // Self Includes #include "rekonqwindow.h" #include "rekonqwindow.moc" -#include <rekonq.h> - -// KDE Includes -#include <KApplication> -#include <KCmdLineArgs> -#include <KSessionManager> - -// Qt Includes -#include <QCloseEvent> -#include <QDesktopWidget> - - -static bool s_no_query_exit = false; - - -class KRWSessionManager : public KSessionManager -{ - -public: - KRWSessionManager() - { - } - - ~KRWSessionManager() - { - } - - bool dummyInit() - { - return true; - } - - bool saveState(QSessionManager&) - { - KConfig* config = KApplication::kApplication()->sessionConfig(); - int n = 0; - Q_FOREACH(RekonqWindow * rw, RekonqWindow::windowList()) - { - n++; - rw->savePropertiesInternal(config, n); - } - - KConfigGroup group(config, "Number"); - group.writeEntry("NumberOfWindows", n); - return true; - } - - bool commitData(QSessionManager& sm) - { - // not really a fast method but the only compatible one - if (sm.allowsInteraction()) - { - bool canceled = false; - ::s_no_query_exit = true; - - Q_FOREACH(RekonqWindow * window, RekonqWindow::windowList()) - { - if (!window->testAttribute(Qt::WA_WState_Hidden)) - { - QCloseEvent e; - QApplication::sendEvent(window, &e); - canceled = !e.isAccepted(); - if (canceled) - break; - } - } - ::s_no_query_exit = false; - if (canceled) - return false; - - return true; - } - - // the user wants it, the user gets it - return true; - } -}; +// Auto Includes +#include "rekonq.h" -K_GLOBAL_STATIC(KRWSessionManager, ktwsm) -K_GLOBAL_STATIC(QList<RekonqWindow*>, sWindowList) +// Local Includes +#include "application.h" +#include "tabwidget.h" +#include "tabbar.h" -// ---------------------------------------------------------------------------------------------------- +#include "webpage.h" +#include "webwindow.h" +// KDE Includes +#include <KUrl> +#include <KLocalizedString> -RekonqWindow::RekonqWindow(QWidget* parent) - : KTabWidget(parent) -{ - // This has to be a window... - setWindowFlags(Qt::Window); - - // Setting attributes (just to be sure...) - setAttribute(Qt::WA_DeleteOnClose, true); - setAttribute(Qt::WA_QuitOnClose, true); - - ktwsm->dummyInit(); - sWindowList->append(this); - - QString geometry; - KCmdLineArgs *args = KCmdLineArgs::parsedArgs("kde"); - if (args && args->isSet("geometry")) - geometry = args->getOption("geometry"); - - if (geometry.isNull()) // if there is no geometry, it doesn't matter - { - KSharedConfig::Ptr cf = KGlobal::config(); - KConfigGroup cg(cf, QL1S("TabWindow")); - restoreWindowSize(cg); - } - else - { - parseGeometry(); - } - - setWindowTitle(KGlobal::caption()); -} - - -RekonqWindow::~RekonqWindow() -{ - sWindowList->removeAll(this); - - KSharedConfig::Ptr cf = KGlobal::config(); - KConfigGroup cg(cf, QL1S("TabWindow")); - saveWindowSize(cg); -} - +// Qt Includes +#include <QVBoxLayout> +#include <QSizePolicy> -QSize RekonqWindow::sizeHint() const -{ - QRect desktopRect = QApplication::desktop()->screenGeometry(); - QSize size = desktopRect.size() * 0.8; - return size; -} -QList<RekonqWindow*> RekonqWindow::windowList() +RekonqWindow::RekonqWindow(bool withTab, bool privateBrowsingMode, QWidget *parent) + : RWindow(parent) + , _tabWidget(new TabWidget(withTab, privateBrowsingMode, this)) + , _splitter(new QSplitter(this)) { - return *sWindowList; + init(); } -void RekonqWindow::savePropertiesInternal(KConfig *config, int number) +RekonqWindow::RekonqWindow(WebPage *pg, QWidget *parent) + : RWindow(parent) + , _tabWidget(new TabWidget(pg, this)) + , _splitter(new QSplitter(this)) { - QString s; - s.setNum(number); - s.prepend(QL1S("WindowProperties")); - KConfigGroup cg(config, s); - - // store objectName, className, Width and Height for later restoring - // (Only useful for session management) - cg.writeEntry(QL1S("ObjectName"), objectName()); - cg.writeEntry(QL1S("ClassName"), metaObject()->className()); - - saveWindowSize(cg); - - s.setNum(number); - cg = KConfigGroup(config, s); - saveProperties(cg); + init(); } -bool RekonqWindow::readPropertiesInternal(KConfig *config, int number) +RekonqWindow::~RekonqWindow() { - // in order they are in toolbar list - QString s; - s.setNum(number); - s.prepend(QL1S("WindowProperties")); - - KConfigGroup cg(config, s); - - // restore the object name (window role) - if (cg.hasKey(QL1S("ObjectName"))) - setObjectName(cg.readEntry("ObjectName").toLatin1()); // latin1 is right here - - restoreWindowSize(cg); - - s.setNum(number); - KConfigGroup grp(config, s); - readProperties(grp); - - return true; } -void RekonqWindow::restoreWindowSize(const KConfigGroup & _cg) +void RekonqWindow::init() { - int scnum = QApplication::desktop()->screenNumber(window()); - QRect desktopRect = QApplication::desktop()->screenGeometry(scnum); + setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); - KConfigGroup cg(_cg); + QVBoxLayout *l = new QVBoxLayout(this); + l->setMargin(0); + l->setSpacing(0); - QString geometryKey = QString::fromLatin1("geometry-%1-%2").arg(desktopRect.width()).arg(desktopRect.height()); - QByteArray geometry = cg.readEntry(geometryKey, QByteArray()); + if (ReKonfig::showBookmarksPanel()) + showBookmarksPanel(true); + + if (ReKonfig::showHistoryPanel()) + showHistoryPanel(true); - // if first time run, center window: resize && move.. - if (!restoreGeometry(QByteArray::fromBase64(geometry))) - { - QSize defaultSize = desktopRect.size() * 0.8; - resize(defaultSize); + _splitter->addWidget(_tabWidget); + _tabWidget->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); - move((desktopRect.width() - width()) / 2, (desktopRect.height() - height()) / 2); - } + l->addWidget(_splitter); - checkPosition(); + + // fix focus handling + setFocusProxy(_tabWidget); } - -void RekonqWindow::saveWindowSize(const KConfigGroup & _cg) const -{ - int scnum = QApplication::desktop()->screenNumber(window()); - QRect desktopRect = QApplication::desktop()->screenGeometry(scnum); - - int w, h; - if (isMaximized()) - { - w = desktopRect.width() + 1; - h = desktopRect.height() + 1; - } - else - { - w = width(); - h = height(); - } - - KConfigGroup cg(_cg); - - QString widthString = QString::fromLatin1("Width %1").arg(desktopRect.width()); - cg.writeEntry(widthString, w); - - QString heightString = QString::fromLatin1("Height %1").arg(desktopRect.height()); - cg.writeEntry(heightString, h); - - // geometry is saved separately for each resolution - QString geometryKey = QString::fromLatin1("geometry-%1-%2").arg(desktopRect.width()).arg(desktopRect.height()); - QByteArray geometry = saveGeometry(); - cg.writeEntry(geometryKey, geometry.toBase64()); -} +// -------------------------------------------------------------------------------------------------- -void RekonqWindow::parseGeometry() +TabWidget *RekonqWindow::tabWidget() { - QString cmdlineGeometry; - KCmdLineArgs *args = KCmdLineArgs::parsedArgs("kde"); - if (args->isSet("geometry")) - cmdlineGeometry = args->getOption("geometry"); - - Q_ASSERT(!cmdlineGeometry.isNull()); - -// #if defined Q_WS_X11 -// int x, y; -// int w, h; -// int m = XParseGeometry( cmdlineGeometry.toLatin1(), &x, &y, (unsigned int*)&w, (unsigned int*)&h); -// if (parsewidth) { -// const QSize minSize = minimumSize(); -// const QSize maxSize = maximumSize(); -// if ( !(m & WidthValue) ) -// w = width(); -// if ( !(m & HeightValue) ) -// h = height(); -// w = qMin(w,maxSize.width()); -// h = qMin(h,maxSize.height()); -// w = qMax(w,minSize.width()); -// h = qMax(h,minSize.height()); -// resize(w, h); -// } else { -// if ( (m & XNegative) ) -// x = KApplication::desktop()->width() + x - w; -// else if ( (m & XValue) ) -// x = geometry().x(); -// if ( (m & YNegative) ) -// y = KApplication::desktop()->height() + y - h; -// else if ( (m & YValue) ) -// y = geometry().y(); -// -// move(x, y); -// } -// #endif + return _tabWidget; } -void RekonqWindow::resizeEvent(QResizeEvent *event) +TabBar *RekonqWindow::tabBar() { - if (!isFullScreen()) - saveAutoSaveSettings(); - KTabWidget::resizeEvent(event); + return _tabWidget->tabBar(); } -void RekonqWindow::saveAutoSaveSettings() +WebWindow *RekonqWindow::currentWebWindow() const { - kDebug() << "AUTO SAVING SETTINGS..."; - - KSharedConfig::Ptr cf = KGlobal::config(); - KConfigGroup cg(cf, QL1S("TabWindow")); - saveWindowSize(cg); + return _tabWidget->currentWebWindow(); } -bool RekonqWindow::canBeRestored(int number) -{ - if (!qApp->isSessionRestored()) - return false; - KConfig *config = kapp->sessionConfig(); - if (!config) - return false; - - KConfigGroup group(config, "Number"); - const int n = group.readEntry("NumberOfWindows", 1); - return number >= 1 && number <= n; -} +// -------------------------------------------------------------------------------------------------- -bool RekonqWindow::restore(int number, bool show) +void RekonqWindow::loadUrl(const KUrl &url, Rekonq::OpenType type, TabHistory *history) { - if (!canBeRestored(number)) - return false; - KConfig *config = kapp->sessionConfig(); - if (readPropertiesInternal(config, number)) + switch (type) { - if (show) - RekonqWindow::show(); - return true; - } - return false; -} - - -// NOTE: For internal purpose only ------------------------------------------------------ - - -int RekonqWindow::addTab(QWidget *page, const QString &label) -{ - setUpdatesEnabled(false); - int i = KTabWidget::addTab(page, label); - setUpdatesEnabled(true); - - return i; -} - - -int RekonqWindow::addTab(QWidget *page, const QIcon &icon, const QString &label) -{ - setUpdatesEnabled(false); - int i = KTabWidget::addTab(page, icon, label); - setUpdatesEnabled(true); - - return i; -} - - -int RekonqWindow::insertTab(int index, QWidget *page, const QString &label) -{ - if (! ReKonfig::openNewTabsNextToCurrent()) - index = -1; - setUpdatesEnabled(false); - int i = KTabWidget::insertTab(index, page, label); - setUpdatesEnabled(true); + case Rekonq::NewWindow: + case Rekonq::NewPrivateWindow: + rApp->loadUrl(url, type); + return; - return i; + case Rekonq::NewTab: + case Rekonq::NewBackGroundTab: + case Rekonq::NewFocusedTab: + case Rekonq::CurrentTab: + default: + _tabWidget->loadUrl(url, type, history); + break; + }; } -int RekonqWindow::insertTab(int index, QWidget *page, const QIcon &icon, const QString &label) +void RekonqWindow::showBookmarksPanel(bool on) { - if (! ReKonfig::openNewTabsNextToCurrent()) - index = -1; - setUpdatesEnabled(false); - int i = KTabWidget::insertTab(index, page, icon, label); - setUpdatesEnabled(true); + if (on) + { + if (_bookmarksPanel.isNull()) + { + _bookmarksPanel = new BookmarksPanel(i18n("Bookmarks Panel"), this); + connect(_bookmarksPanel.data(), SIGNAL(openUrl(KUrl, Rekonq::OpenType)), this, SLOT(loadUrl(KUrl, Rekonq::OpenType))); - return i; + QAction *a = _tabWidget->actionByName(QL1S("show_bookmarks_panel")); + connect(_bookmarksPanel.data(), SIGNAL(visibilityChanged(bool)), a, SLOT(setChecked(bool))); + } + _splitter->insertWidget(0, _bookmarksPanel.data()); + _bookmarksPanel.data()->show(); + } + else + { + _bookmarksPanel.data()->hide(); + delete _bookmarksPanel.data(); + _bookmarksPanel.clear(); + } } -// -------------------------------------------------------------------------------------- - - -void RekonqWindow::checkPosition() +void RekonqWindow::showHistoryPanel(bool on) { - // no need to check trivial positions... - if (isMaximized()) - return; - - QList<RekonqWindow*> wList = RekonqWindow::windowList(); - int wNumber = wList.count(); - - // no need to check first window... - if (wNumber <= 1) - return; - - int div = wNumber % 4; - - int scnum = QApplication::desktop()->screenNumber(window()); - QRect desktopRect = QApplication::desktop()->screenGeometry(scnum); + if (on) + { + if (_historyPanel.isNull()) + { + _historyPanel = new HistoryPanel(i18n("History Panel"), this); + connect(_historyPanel.data(), SIGNAL(openUrl(KUrl, Rekonq::OpenType)), this, SLOT(loadUrl(KUrl, Rekonq::OpenType))); + + QAction *a = _tabWidget->actionByName(QL1S("show_history_panel")); + connect(_historyPanel.data(), SIGNAL(visibilityChanged(bool)), a, SLOT(setChecked(bool))); - switch (div) + } + _splitter->insertWidget(0, _historyPanel.data()); + _historyPanel.data()->show(); + } + else { - case 2: - // left down - move(desktopRect.width() - width(), desktopRect.height() - height()); - break; - case 3: - // right down - move(0, desktopRect.height() - height()); - break; - case 0: - // left top - move(desktopRect.width() - width(), 0); - break; - case 1: - // right top - move(0, 0); - break; - default: - kDebug() << "OOPS...THIS SHOULD NEVER HAPPEN!!"; - break; + _historyPanel.data()->hide(); + delete _historyPanel.data(); + _historyPanel.clear(); } } diff --git a/src/tabwindow/rekonqwindow.h b/src/tabwindow/rekonqwindow.h index ed018e4a..1d46faeb 100644 --- a/src/tabwindow/rekonqwindow.h +++ b/src/tabwindow/rekonqwindow.h @@ -2,7 +2,7 @@ * * This file is a part of the rekonq project * -* Copyright (C) 2012 by Andrea Diamantini <adjam7 at gmail dot com> +* Copyright (C) 2013 by Andrea Diamantini <adjam7 at gmail dot com> * * * This program is free software; you can redistribute it and/or @@ -32,109 +32,55 @@ // Rekonq Includes #include "rekonq_defines.h" -// KDE Includes -#include <KTabWidget> -#include <KConfig> -#include <KConfigGroup> +// Local Includes +#include "rwindow.h" +#include "tabwidget.h" + +#include "bookmarkspanel.h" +#include "historypanel.h" // Qt Includes -#include <QTimer> - -/** - * This is rekonq (re)implementation of KMainWindow, - * given that we'd like to NOT use a "real" xMainWindow - * but a widget with the nice mainwindow properties - * (eg: session management, auto save dimension, etc) but - * NOT its peculiar containers (eg: toolbars, menubar, statusbar, - * central widget...) - * - */ -class RekonqWindow : public KTabWidget -{ - friend class KRWSessionManager; +#include <QSplitter> +#include <QWeakPointer> + +// Forward Declarations +class TabBar; + +class WebPage; +class WebWindow; + +class RekonqWindow : public RWindow +{ Q_OBJECT public: - explicit RekonqWindow(QWidget* parent = 0); + explicit RekonqWindow(bool withTab = true, bool PrivateBrowsingMode = false, QWidget *parent = 0); + explicit RekonqWindow(WebPage *pg, QWidget *parent = 0); virtual ~RekonqWindow(); - QSize sizeHint() const; - - /** - * List of members of RekonqWindow class. - */ - static QList<RekonqWindow*> windowList(); - - /** - * If the session did contain so high a @p number, @p true is returned, - * else @p false. - * @see restore() - **/ - static bool canBeRestored(int number); - - /** - * Try to restore the toplevel widget as defined by @p number (1..X). - * - * You should call canBeRestored() first. - * - **/ - bool restore(int number, bool show = true); - - // NOTE: For internal purpose only ------------------------------------------------------ - int addTab(QWidget *page, const QString &label); - int addTab(QWidget *page, const QIcon &icon, const QString &label); - - int insertTab(int index, QWidget *page, const QString &label); - int insertTab(int index, QWidget *page, const QIcon &icon, const QString &label); - // -------------------------------------------------------------------------------------- - -protected: - /** - * Save your instance-specific properties. The function is - * invoked when the session manager requests your application - * to save its state. - * - * Please reimplement these function in childclasses. - * - * Note: No user interaction is allowed - * in this function! - * - */ - virtual void saveProperties(KConfigGroup &) {} - - /** - * Read your instance-specific properties. - * - * Is called indirectly by restore(). - */ - virtual void readProperties(const KConfigGroup &) {} - - void savePropertiesInternal(KConfig*, int); - bool readPropertiesInternal(KConfig*, int); - - /** - * For inherited classes - */ - void saveWindowSize(const KConfigGroup &config) const; - /** - * For inherited classes - * Note that a -geometry on the command line has priority. - */ - void restoreWindowSize(const KConfigGroup & config); - - /// parse the geometry from the geometry command line argument - void parseGeometry(); - - virtual void resizeEvent(QResizeEvent *); + TabWidget *tabWidget(); + TabBar *tabBar(); + WebWindow *currentWebWindow() const; -private Q_SLOTS: - void saveAutoSaveSettings(); +private: + void init(); + +public Q_SLOTS: + void loadUrl(const KUrl &, Rekonq::OpenType type = Rekonq::CurrentTab, TabHistory *history = 0); +private Q_SLOTS: + void showBookmarksPanel(bool); + void showHistoryPanel(bool); + private: - /// This has been added to just fix window position && not let them be overlying - void checkPosition(); + TabWidget *_tabWidget; + + QSplitter *_splitter; + + QWeakPointer<HistoryPanel> _historyPanel; + QWeakPointer<BookmarksPanel> _bookmarksPanel; }; #endif // REKONQ_WINDOW_H diff --git a/src/tabwindow/rwindow.cpp b/src/tabwindow/rwindow.cpp new file mode 100644 index 00000000..f7304da5 --- /dev/null +++ b/src/tabwindow/rwindow.cpp @@ -0,0 +1,397 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2012-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + +// Self Includes +#include "rwindow.h" +#include "rwindow.moc" + +// KDE Includes +#include <KApplication> +#include <KCmdLineArgs> +#include <KSessionManager> + +// Qt Includes +#include <QCloseEvent> +#include <QDesktopWidget> + + +static bool s_no_query_exit = false; + + +class KRWSessionManager : public KSessionManager +{ + +public: + KRWSessionManager() + { + } + + ~KRWSessionManager() + { + } + + bool dummyInit() + { + return true; + } + + bool saveState(QSessionManager&) + { + KConfig* config = KApplication::kApplication()->sessionConfig(); + int n = 0; + Q_FOREACH(RWindow * rw, RWindow::windowList()) + { + n++; + rw->savePropertiesInternal(config, n); + } + + KConfigGroup group(config, "Number"); + group.writeEntry("NumberOfWindows", n); + return true; + } + + bool commitData(QSessionManager& sm) + { + // not really a fast method but the only compatible one + if (sm.allowsInteraction()) + { + bool canceled = false; + ::s_no_query_exit = true; + + Q_FOREACH(RWindow * window, RWindow::windowList()) + { + if (!window->testAttribute(Qt::WA_WState_Hidden)) + { + QCloseEvent e; + QApplication::sendEvent(window, &e); + canceled = !e.isAccepted(); + if (canceled) + break; + } + } + ::s_no_query_exit = false; + if (canceled) + return false; + + return true; + } + + // the user wants it, the user gets it + return true; + } +}; + + +K_GLOBAL_STATIC(KRWSessionManager, ktwsm) +K_GLOBAL_STATIC(QList<RWindow*>, sWindowList) + + +// ---------------------------------------------------------------------------------------------------- + + +RWindow::RWindow(QWidget* parent) + : QWidget(parent) +{ + // This has to be a window... + setWindowFlags(Qt::Window); + + // Setting attributes (just to be sure...) + setAttribute(Qt::WA_DeleteOnClose, true); + setAttribute(Qt::WA_QuitOnClose, true); + + ktwsm->dummyInit(); + sWindowList->append(this); + + QString geometry; + KCmdLineArgs *args = KCmdLineArgs::parsedArgs("kde"); + if (args && args->isSet("geometry")) + geometry = args->getOption("geometry"); + + if (geometry.isNull()) // if there is no geometry, it doesn't matter + { + KSharedConfig::Ptr cf = KGlobal::config(); + KConfigGroup cg(cf, QL1S("RekonqWindow")); + restoreWindowSize(cg); + } + else + { + parseGeometry(); + } + + setWindowTitle(KGlobal::caption()); +} + + +RWindow::~RWindow() +{ + sWindowList->removeAll(this); + + KSharedConfig::Ptr cf = KGlobal::config(); + KConfigGroup cg(cf, QL1S("RekonqWindow")); + saveWindowSize(cg); +} + + +QSize RWindow::sizeHint() const +{ + QRect desktopRect = QApplication::desktop()->screenGeometry(); + QSize size = desktopRect.size() * 0.8; + return size; +} + +QList<RWindow*> RWindow::windowList() +{ + return *sWindowList; +} + + +void RWindow::savePropertiesInternal(KConfig *config, int number) +{ + QString s; + s.setNum(number); + s.prepend(QL1S("WindowProperties")); + KConfigGroup cg(config, s); + + // store objectName, className, Width and Height for later restoring + // (Only useful for session management) + cg.writeEntry(QL1S("ObjectName"), objectName()); + cg.writeEntry(QL1S("ClassName"), metaObject()->className()); + + saveWindowSize(cg); + + s.setNum(number); + cg = KConfigGroup(config, s); + saveProperties(cg); +} + + +bool RWindow::readPropertiesInternal(KConfig *config, int number) +{ + // in order they are in toolbar list + QString s; + s.setNum(number); + s.prepend(QL1S("WindowProperties")); + + KConfigGroup cg(config, s); + + // restore the object name (window role) + if (cg.hasKey(QL1S("ObjectName"))) + setObjectName(cg.readEntry("ObjectName").toLatin1()); // latin1 is right here + + restoreWindowSize(cg); + + s.setNum(number); + KConfigGroup grp(config, s); + readProperties(grp); + + return true; +} + + +void RWindow::restoreWindowSize(const KConfigGroup & _cg) +{ + int scnum = QApplication::desktop()->screenNumber(window()); + QRect desktopRect = QApplication::desktop()->screenGeometry(scnum); + + KConfigGroup cg(_cg); + + QString geometryKey = QString::fromLatin1("geometry-%1-%2").arg(desktopRect.width()).arg(desktopRect.height()); + QByteArray geometry = cg.readEntry(geometryKey, QByteArray()); + + // if first time run, center window: resize && move.. + if (!restoreGeometry(QByteArray::fromBase64(geometry))) + { + QSize defaultSize = desktopRect.size() * 0.8; + resize(defaultSize); + + move((desktopRect.width() - width()) / 2, (desktopRect.height() - height()) / 2); + } + + checkPosition(); +} + + +void RWindow::saveWindowSize(const KConfigGroup & _cg) const +{ + int scnum = QApplication::desktop()->screenNumber(window()); + QRect desktopRect = QApplication::desktop()->screenGeometry(scnum); + + int w, h; + if (isMaximized()) + { + w = desktopRect.width() + 1; + h = desktopRect.height() + 1; + } + else + { + w = width(); + h = height(); + } + + KConfigGroup cg(_cg); + + QString widthString = QString::fromLatin1("Width %1").arg(desktopRect.width()); + cg.writeEntry(widthString, w); + + QString heightString = QString::fromLatin1("Height %1").arg(desktopRect.height()); + cg.writeEntry(heightString, h); + + // geometry is saved separately for each resolution + QString geometryKey = QString::fromLatin1("geometry-%1-%2").arg(desktopRect.width()).arg(desktopRect.height()); + QByteArray geometry = saveGeometry(); + cg.writeEntry(geometryKey, geometry.toBase64()); +} + + +void RWindow::parseGeometry() +{ + QString cmdlineGeometry; + KCmdLineArgs *args = KCmdLineArgs::parsedArgs("kde"); + if (args->isSet("geometry")) + cmdlineGeometry = args->getOption("geometry"); + + Q_ASSERT(!cmdlineGeometry.isNull()); + +// #if defined Q_WS_X11 +// int x, y; +// int w, h; +// int m = XParseGeometry( cmdlineGeometry.toLatin1(), &x, &y, (unsigned int*)&w, (unsigned int*)&h); +// if (parsewidth) { +// const QSize minSize = minimumSize(); +// const QSize maxSize = maximumSize(); +// if ( !(m & WidthValue) ) +// w = width(); +// if ( !(m & HeightValue) ) +// h = height(); +// w = qMin(w,maxSize.width()); +// h = qMin(h,maxSize.height()); +// w = qMax(w,minSize.width()); +// h = qMax(h,minSize.height()); +// resize(w, h); +// } else { +// if ( (m & XNegative) ) +// x = KApplication::desktop()->width() + x - w; +// else if ( (m & XValue) ) +// x = geometry().x(); +// if ( (m & YNegative) ) +// y = KApplication::desktop()->height() + y - h; +// else if ( (m & YValue) ) +// y = geometry().y(); +// +// move(x, y); +// } +// #endif +} + + +void RWindow::resizeEvent(QResizeEvent *event) +{ + if (!isFullScreen()) + saveAutoSaveSettings(); + QWidget::resizeEvent(event); +} + + +void RWindow::saveAutoSaveSettings() +{ + kDebug() << "AUTO SAVING SETTINGS..."; + + KSharedConfig::Ptr cf = KGlobal::config(); + KConfigGroup cg(cf, QL1S("RekonqWindow")); + saveWindowSize(cg); +} + + +bool RWindow::canBeRestored(int number) +{ + if (!qApp->isSessionRestored()) + return false; + KConfig *config = kapp->sessionConfig(); + if (!config) + return false; + + KConfigGroup group(config, "Number"); + const int n = group.readEntry("NumberOfWindows", 1); + return number >= 1 && number <= n; +} + + +bool RWindow::restore(int number, bool show) +{ + if (!canBeRestored(number)) + return false; + KConfig *config = kapp->sessionConfig(); + if (readPropertiesInternal(config, number)) + { + if (show) + RWindow::show(); + return true; + } + return false; +} + + +void RWindow::checkPosition() +{ + // no need to check trivial positions... + if (isMaximized()) + return; + + QList<RWindow*> wList = RWindow::windowList(); + int wNumber = wList.count(); + + // no need to check first window... + if (wNumber <= 1) + return; + + int div = wNumber % 4; + + int scnum = QApplication::desktop()->screenNumber(window()); + QRect desktopRect = QApplication::desktop()->screenGeometry(scnum); + + switch (div) + { + case 2: + // left down + move(desktopRect.width() - width(), desktopRect.height() - height()); + break; + case 3: + // right down + move(0, desktopRect.height() - height()); + break; + case 0: + // left top + move(desktopRect.width() - width(), 0); + break; + case 1: + // right top + move(0, 0); + break; + default: + kDebug() << "OOPS...THIS SHOULD NEVER HAPPEN!!"; + break; + } +} diff --git a/src/tabwindow/rwindow.h b/src/tabwindow/rwindow.h new file mode 100644 index 00000000..871d3788 --- /dev/null +++ b/src/tabwindow/rwindow.h @@ -0,0 +1,131 @@ +/* ============================================================ +* +* This file is a part of the rekonq project +* +* Copyright (C) 2012-2013 by Andrea Diamantini <adjam7 at gmail dot com> +* +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License as +* published by the Free Software Foundation; either version 2 of +* the License or (at your option) version 3 or any later version +* accepted by the membership of KDE e.V. (or its successor approved +* by the membership of KDE e.V.), which shall act as a proxy +* defined in Section 14 of version 3 of the license. +* +* This program is distributed in the hope that it will be useful, +* but WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* ============================================================ */ + + + +#ifndef R_WINDOW_H +#define R_WINDOW_H + + +// Rekonq Includes +#include "rekonq_defines.h" + +// KDE Includes +#include <KConfig> +#include <KConfigGroup> + +// Qt Includes +#include <QWidget> + +/** + * This is rekonq (re)implementation of KMainWindow, + * given that we'd like to NOT use a "real" xMainWindow + * but a widget with the nice mainwindow properties + * (eg: session management, auto save dimension, etc) but + * NOT its peculiar containers (eg: toolbars, menubar, statusbar, + * central widget...) + * + */ +class RWindow : public QWidget +{ + friend class KRWSessionManager; + + Q_OBJECT + +public: + explicit RWindow(QWidget* parent = 0); + + virtual ~RWindow(); + + QSize sizeHint() const; + + /** + * List of members of RekonqWindow class. + */ + static QList<RWindow*> windowList(); + + /** + * If the session did contain so high a @p number, @p true is returned, + * else @p false. + * @see restore() + **/ + static bool canBeRestored(int number); + + /** + * Try to restore the toplevel widget as defined by @p number (1..X). + * + * You should call canBeRestored() first. + * + **/ + bool restore(int number, bool show = true); + +protected: + /** + * Save your instance-specific properties. The function is + * invoked when the session manager requests your application + * to save its state. + * + * Please reimplement these function in childclasses. + * + * Note: No user interaction is allowed + * in this function! + * + */ + virtual void saveProperties(KConfigGroup &) {} + + /** + * Read your instance-specific properties. + * + * Is called indirectly by restore(). + */ + virtual void readProperties(const KConfigGroup &) {} + + void savePropertiesInternal(KConfig*, int); + bool readPropertiesInternal(KConfig*, int); + + /** + * For inherited classes + */ + void saveWindowSize(const KConfigGroup &config) const; + /** + * For inherited classes + * Note that a -geometry on the command line has priority. + */ + void restoreWindowSize(const KConfigGroup & config); + + /// parse the geometry from the geometry command line argument + void parseGeometry(); + + virtual void resizeEvent(QResizeEvent *); + +private Q_SLOTS: + void saveAutoSaveSettings(); + +private: + /// This has been added to just fix window position && not let them be overlying + void checkPosition(); +}; + +#endif // R_WINDOW_H diff --git a/src/tabwindow/tabbar.cpp b/src/tabwindow/tabbar.cpp index bdd07573..7363d965 100644 --- a/src/tabwindow/tabbar.cpp +++ b/src/tabwindow/tabbar.cpp @@ -33,7 +33,8 @@ #include "rekonq.h" // Local Includes -#include "tabwindow.h" +#include "tabwidget.h" + #include "tabhighlighteffect.h" #include "tabpreviewpopup.h" #include "webwindow.h" @@ -186,7 +187,7 @@ void TabBar::detachTab() void TabBar::contextMenu(int tabIndex, const QPoint &pos) { - TabWindow *w = qobject_cast<TabWindow *>(parent()); + TabWidget *w = qobject_cast<TabWidget *>(parent()); QAction *a; @@ -262,7 +263,7 @@ void TabBar::contextMenu(int tabIndex, const QPoint &pos) void TabBar::emptyAreaContextMenu(const QPoint &pos) { - TabWindow *w = qobject_cast<TabWindow *>(parent()); + TabWidget *w = qobject_cast<TabWidget *>(parent()); QAction *a; @@ -355,7 +356,7 @@ void TabBar::tabInserted(int index) if (index < availableIndex) { - TabWindow *w = qobject_cast<TabWindow *>(parent()); + TabWidget *w = qobject_cast<TabWidget *>(parent()); w->moveTab(index, availableIndex); } @@ -446,7 +447,7 @@ void TabBar::mouseReleaseEvent(QMouseEvent *event) { if (!tabData(i).toBool()) { - TabWindow *w = qobject_cast<TabWindow *>(parent()); + TabWidget *w = qobject_cast<TabWidget *>(parent()); w->moveTab(i, pinnedTabs); w->setCurrentIndex(pinnedTabs); } @@ -457,7 +458,7 @@ void TabBar::mouseReleaseEvent(QMouseEvent *event) { if (tabData(i).toBool()) { - TabWindow *w = qobject_cast<TabWindow *>(parent()); + TabWidget *w = qobject_cast<TabWidget *>(parent()); w->moveTab(i, pinnedTabs - 1); w->setCurrentIndex(pinnedTabs - 1); } @@ -482,7 +483,7 @@ void TabBar::showTabPreview() delete m_previewPopup.data(); m_previewPopup.clear(); - TabWindow *tabW = qobject_cast<TabWindow *>(parent()); + TabWidget *tabW = qobject_cast<TabWidget *>(parent()); WebWindow *indexedTab = tabW->webWindow(m_currentTabPreviewIndex); WebWindow *currentTab = tabW->webWindow(currentIndex()); @@ -546,7 +547,7 @@ void TabBar::pinTab() } } - TabWindow *w = qobject_cast<TabWindow *>(parent()); + TabWidget *w = qobject_cast<TabWidget *>(parent()); w->moveTab(index, availableIndex); index = availableIndex; @@ -593,7 +594,7 @@ void TabBar::unpinTab() } } - TabWindow *w = qobject_cast<TabWindow *>(parent()); + TabWidget *w = qobject_cast<TabWidget *>(parent()); w->moveTab(index, availableIndex); index = availableIndex; diff --git a/src/tabwindow/tabwindow.cpp b/src/tabwindow/tabwidget.cpp index 2ade757b..bb62ca27 100644 --- a/src/tabwindow/tabwindow.cpp +++ b/src/tabwindow/tabwidget.cpp @@ -25,14 +25,16 @@ // Self Includes -#include "tabwindow.h" -#include "tabwindow.moc" +#include "tabwidget.h" +#include "tabwidget.moc" // Auto Includes #include "rekonq.h" // Local Includes #include "application.h" +#include "rekonqwindow.h" + #include "webpage.h" #include "webwindow.h" #include "tabbar.h" @@ -70,8 +72,8 @@ #include <QWebSettings> -TabWindow::TabWindow(bool withTab, bool PrivateBrowsingMode, QWidget *parent) - : RekonqWindow(parent) +TabWidget::TabWidget(bool withTab, bool PrivateBrowsingMode, QWidget *parent) + : KTabWidget(parent) , _addTabButton(new QToolButton(this)) , _openedTabsCounter(0) , _isPrivateBrowsing(PrivateBrowsingMode) @@ -79,7 +81,7 @@ TabWindow::TabWindow(bool withTab, bool PrivateBrowsingMode, QWidget *parent) { init(); - // NOTE: we usually create TabWindow with AT LEAST one tab, but + // NOTE: we usually create TabWidget with AT LEAST one tab, but // in one important case... if (withTab) { @@ -90,8 +92,8 @@ TabWindow::TabWindow(bool withTab, bool PrivateBrowsingMode, QWidget *parent) } -TabWindow::TabWindow(WebPage *pg, QWidget *parent) - : RekonqWindow(parent) +TabWidget::TabWidget(WebPage *pg, QWidget *parent) + : KTabWidget(parent) , _addTabButton(new QToolButton(this)) , _openedTabsCounter(0) , _isPrivateBrowsing(false) @@ -105,7 +107,7 @@ TabWindow::TabWindow(WebPage *pg, QWidget *parent) } -void TabWindow::init() +void TabWidget::init() { setContentsMargins(0, 0, 0, 0); @@ -184,6 +186,22 @@ void TabWindow::init() connect(this, SIGNAL(currentChanged(int)), this, SLOT(currentChanged(int))); // ---------------------------------------------------------------------------------------------- + RekonqWindow *rw = qobject_cast<RekonqWindow *>(parent()); + // setup bookmarks panel action + a = new KAction(KIcon("bookmarks-organize"), i18n("Bookmarks Panel"), this); + a->setShortcut(KShortcut(Qt::CTRL + Qt::SHIFT + Qt::Key_B)); + actionCollection()->addAction(QL1S("show_bookmarks_panel"), a); + a->setCheckable(true); + connect(a, SIGNAL(triggered(bool)), rw, SLOT(showBookmarksPanel(bool))); + + // setup history panel action + a = new KAction(KIcon("view-history"), i18n("History Panel"), this); + a->setShortcut(KShortcut(Qt::CTRL + Qt::Key_H)); + actionCollection()->addAction(QL1S("show_history_panel"), a); + a->setCheckable(true); + connect(a, SIGNAL(triggered(bool)), rw, SLOT(showHistoryPanel(bool))); + + // ---------------------------------------------------------------------------------------------- // shortcuts for quickly switching to a tab QSignalMapper *tabSignalMapper = new QSignalMapper(this); for (int i = 0; i < 9; i++) @@ -211,7 +229,7 @@ void TabWindow::init() _ac->readSettings(); // ---------------------------------------------------------------------------------------------- - int n = rApp->tabWindowList().count() + 1; + int n = rApp->rekonqWindowList().count() + 1; QList<TabHistory> list = SessionManager::self()->closedSitesForWindow( QL1S("win") + QString::number(n) ); Q_FOREACH(const TabHistory & tab, list) { @@ -226,32 +244,32 @@ void TabWindow::init() // ---------------------------------------------------------------------------------------------------- -KActionCollection *TabWindow::actionCollection() const +KActionCollection *TabWidget::actionCollection() const { return _ac; } -QAction *TabWindow::actionByName(const QString &name) +QAction *TabWidget::actionByName(const QString &name) { return actionCollection()->action(name); } -TabBar *TabWindow::tabBar() const +TabBar *TabWidget::tabBar() const { TabBar *tabBar = qobject_cast<TabBar *>(QTabWidget::tabBar()); return tabBar; } -WebWindow *TabWindow::currentWebWindow() const +WebWindow *TabWidget::currentWebWindow() const { return webWindow(currentIndex()); } -WebWindow *TabWindow::webWindow(int index) const +WebWindow *TabWidget::webWindow(int index) const { WebWindow *tab = qobject_cast<WebWindow *>(this->widget(index)); if (tab) @@ -264,13 +282,39 @@ WebWindow *TabWindow::webWindow(int index) const } -QList<TabHistory> TabWindow::recentlyClosedTabs() +QList<TabHistory> TabWidget::recentlyClosedTabs() { return m_recentlyClosedTabs; } -WebWindow *TabWindow::prepareNewTab(WebPage *page) +void TabWidget::newTab(WebPage *page) +{ + WebWindow *tab = prepareNewTab(page); + addTab(tab, i18n("new tab")); + setCurrentWidget(tab); + + // no need to load an url if we already have a page... + if (page) + return; + + switch (ReKonfig::newTabsBehaviour()) + { + case 0: // new tab page + tab->load(KUrl("about:home")); + break; + case 2: // homepage + tab->load(KUrl(ReKonfig::homePage())); + break; + case 1: // blank page + default: + tab->load(KUrl("about:blank")); + break; + } +} + + +WebWindow *TabWidget::prepareNewTab(WebPage *page) { WebWindow *tab = new WebWindow(this, _isPrivateBrowsing, page); @@ -289,7 +333,7 @@ WebWindow *TabWindow::prepareNewTab(WebPage *page) } -void TabWindow::loadUrl(const KUrl &url, Rekonq::OpenType type, TabHistory *history) +void TabWidget::loadUrl(const KUrl &url, Rekonq::OpenType type, TabHistory *history) { WebWindow *tab = 0; switch (type) @@ -336,34 +380,7 @@ void TabWindow::loadUrl(const KUrl &url, Rekonq::OpenType type, TabHistory *hist } -void TabWindow::newTab(WebPage *page) -{ - WebWindow *tab = prepareNewTab(page); - addTab(tab, i18n("new tab")); - setCurrentWidget(tab); - - // no need to load an url if we already have a page... - if (page) - return; - - switch (ReKonfig::newTabsBehaviour()) - { - case 0: // new tab page - tab->load(KUrl("about:home")); - break; - case 2: // homepage - tab->load(KUrl(ReKonfig::homePage())); - break; - case 1: // blank page - default: - tab->load(KUrl("about:blank")); - break; - } - -} - - -void TabWindow::pageCreated(WebPage *page) +void TabWidget::pageCreated(WebPage *page) { WebWindow *tab = prepareNewTab(page); @@ -375,7 +392,7 @@ void TabWindow::pageCreated(WebPage *page) } -void TabWindow::currentChanged(int newIndex) +void TabWidget::currentChanged(int newIndex) { _openedTabsCounter = 0; @@ -396,7 +413,7 @@ void TabWindow::currentChanged(int newIndex) } -void TabWindow::updateNewTabButtonPosition() +void TabWidget::updateNewTabButtonPosition() { if (isFullScreen()) return; @@ -421,7 +438,7 @@ void TabWindow::updateNewTabButtonPosition() } -void TabWindow::tabTitleChanged(const QString &title) +void TabWidget::tabTitleChanged(const QString &title) { WebWindow *tab = qobject_cast<WebWindow *>(sender()); if (!tab) @@ -451,7 +468,7 @@ void TabWindow::tabTitleChanged(const QString &title) } -void TabWindow::tabUrlChanged(const QUrl &url) +void TabWidget::tabUrlChanged(const QUrl &url) { WebWindow *tab = qobject_cast<WebWindow *>(sender()); if (!tab) @@ -463,7 +480,7 @@ void TabWindow::tabUrlChanged(const QUrl &url) } -void TabWindow::tabIconChanged() +void TabWidget::tabIconChanged() { WebWindow *tab = qobject_cast<WebWindow *>(sender()); if (!tab) @@ -490,7 +507,7 @@ void TabWindow::tabIconChanged() } -void TabWindow::tabLoadStarted() +void TabWidget::tabLoadStarted() { WebWindow *tab = qobject_cast<WebWindow *>(sender()); if (!tab) @@ -528,7 +545,7 @@ void TabWindow::tabLoadStarted() } -void TabWindow::tabLoadFinished(bool ok) +void TabWidget::tabLoadFinished(bool ok) { Q_UNUSED(ok); @@ -575,7 +592,7 @@ void TabWindow::tabLoadFinished(bool ok) } -void TabWindow::cloneTab(int index) +void TabWidget::cloneTab(int index) { if (index < 0) index = currentIndex(); @@ -590,7 +607,7 @@ void TabWindow::cloneTab(int index) } -void TabWindow::closeTab(int index, bool del) +void TabWidget::closeTab(int index, bool del) { if (index < 0) index = currentIndex(); @@ -635,7 +652,7 @@ void TabWindow::closeTab(int index, bool del) } -void TabWindow::closeOtherTabs(int index) +void TabWidget::closeOtherTabs(int index) { if (index < 0) index = currentIndex(); @@ -654,7 +671,7 @@ void TabWindow::closeOtherTabs(int index) } -void TabWindow::detachTab(int index, TabWindow *toWindow) +void TabWidget::detachTab(int index, RekonqWindow *toWindow) { if (index < 0) index = currentIndex(); @@ -673,13 +690,15 @@ void TabWindow::detachTab(int index, TabWindow *toWindow) closeTab(index, false); - TabWindow *w = 0; + RekonqWindow *w = 0; w = (toWindow == 0) - ? new TabWindow(false) + ? new RekonqWindow(false) : toWindow; - w->addTab(tab, tab->title()); - w->setCurrentWidget(tab); + TabWidget *hostTabWidget = w->tabWidget(); + + hostTabWidget->addTab(tab, tab->title()); + hostTabWidget->setCurrentWidget(tab); // disconnect signals from old tabwindow // WARNING: Code copied from prepareNewTab method. @@ -693,17 +712,17 @@ void TabWindow::detachTab(int index, TabWindow *toWindow) // reconnect signals to new tabwindow // WARNING: Code copied from prepareNewTab method. // Any new changes there should be applied here... - connect(tab, SIGNAL(titleChanged(QString)), w, SLOT(tabTitleChanged(QString))); - connect(tab, SIGNAL(iconChanged()), w, SLOT(tabIconChanged())); - connect(tab, SIGNAL(loadStarted()), w, SLOT(tabLoadStarted())); - connect(tab, SIGNAL(loadFinished(bool)), w, SLOT(tabLoadFinished(bool))); - connect(tab, SIGNAL(pageCreated(WebPage*)), w, SLOT(pageCreated(WebPage*))); + connect(tab, SIGNAL(titleChanged(QString)), hostTabWidget, SLOT(tabTitleChanged(QString))); + connect(tab, SIGNAL(iconChanged()), hostTabWidget, SLOT(tabIconChanged())); + connect(tab, SIGNAL(loadStarted()), hostTabWidget, SLOT(tabLoadStarted())); + connect(tab, SIGNAL(loadFinished(bool)), hostTabWidget, SLOT(tabLoadFinished(bool))); + connect(tab, SIGNAL(pageCreated(WebPage*)), hostTabWidget, SLOT(pageCreated(WebPage*))); w->show(); } -void TabWindow::reloadTab(int index) +void TabWidget::reloadTab(int index) { // When index is -1 index chooses the current tab if (index < 0) @@ -718,7 +737,7 @@ void TabWindow::reloadTab(int index) } -void TabWindow::reloadAllTabs() +void TabWidget::reloadAllTabs() { for (int i = 0; i < count(); ++i) { @@ -727,7 +746,7 @@ void TabWindow::reloadAllTabs() } -void TabWindow::bookmarkAllTabs() +void TabWidget::bookmarkAllTabs() { KBookmarkGroup rGroup = BookmarkManager::self()->rootGroup(); KBookmarkGroup folderGroup = rGroup.createNewFolder(i18n("Bookmarked tabs: ") + QDate::currentDate().toString()); @@ -739,13 +758,13 @@ void TabWindow::bookmarkAllTabs() } -void TabWindow::restoreLastClosedTab() +void TabWidget::restoreLastClosedTab() { restoreClosedTab(0); } -void TabWindow::restoreClosedTab(int index, bool inNewTab) +void TabWidget::restoreClosedTab(int index, bool inNewTab) { if (m_recentlyClosedTabs.isEmpty()) return; @@ -783,7 +802,7 @@ void TabWindow::restoreClosedTab(int index, bool inNewTab) } -void TabWindow::nextTab() +void TabWidget::nextTab() { int next = currentIndex() + 1; if (next == count()) @@ -792,7 +811,7 @@ void TabWindow::nextTab() } -void TabWindow::previousTab() +void TabWidget::previousTab() { int next = currentIndex() - 1; if (next < 0) @@ -801,7 +820,7 @@ void TabWindow::previousTab() } -void TabWindow::setFullScreen(bool makeFullScreen) +void TabWidget::setFullScreen(bool makeFullScreen) { tabBar()->setVisible(!makeFullScreen); _addTabButton->setVisible(!makeFullScreen); @@ -813,13 +832,13 @@ void TabWindow::setFullScreen(bool makeFullScreen) } -bool TabWindow::isPrivateBrowsingWindowMode() +bool TabWidget::isPrivateBrowsingWindowMode() { return _isPrivateBrowsing; } -void TabWindow::loadFavorite(const int index) +void TabWidget::loadFavorite(const int index) { QStringList urls = ReKonfig::previewUrls(); if (index < 0 || index > urls.length()) @@ -829,3 +848,53 @@ void TabWindow::loadFavorite(const int index) loadUrl(url); currentWebWindow()->setFocus(); } + + +// NOTE: For internal purpose only ------------------------------------------------------ + + +int TabWidget::addTab(QWidget *page, const QString &label) +{ + setUpdatesEnabled(false); + int i = KTabWidget::addTab(page, label); + setUpdatesEnabled(true); + + return i; +} + + +int TabWidget::addTab(QWidget *page, const QIcon &icon, const QString &label) +{ + setUpdatesEnabled(false); + int i = KTabWidget::addTab(page, icon, label); + setUpdatesEnabled(true); + + return i; +} + + +int TabWidget::insertTab(int index, QWidget *page, const QString &label) +{ + if (! ReKonfig::openNewTabsNextToCurrent()) + index = -1; + setUpdatesEnabled(false); + int i = KTabWidget::insertTab(index, page, label); + setUpdatesEnabled(true); + + return i; +} + + +int TabWidget::insertTab(int index, QWidget *page, const QIcon &icon, const QString &label) +{ + if (! ReKonfig::openNewTabsNextToCurrent()) + index = -1; + setUpdatesEnabled(false); + int i = KTabWidget::insertTab(index, page, icon, label); + setUpdatesEnabled(true); + + return i; +} + + +// -------------------------------------------------------------------------------------- diff --git a/src/tabwindow/tabwindow.h b/src/tabwindow/tabwidget.h index c72c252b..9c79df11 100644 --- a/src/tabwindow/tabwindow.h +++ b/src/tabwindow/tabwidget.h @@ -24,16 +24,13 @@ * ============================================================ */ -#ifndef TAB_WINDOW -#define TAB_WINDOW +#ifndef TAB_WIDGET +#define TAB_WIDGET // Rekonq Includes #include "rekonq_defines.h" -// Local Includes -#include "rekonqwindow.h" - // KDE Includes #include <KTabWidget> #include <KActionCollection> @@ -51,17 +48,18 @@ class TabBar; class WebPage; class WebWindow; +class RekonqWindow; // -------------------------------------------------------------------------------------- -class TabWindow : public RekonqWindow +class TabWidget : public KTabWidget { Q_OBJECT public: - explicit TabWindow(bool withTab = true, bool PrivateBrowsingMode = false, QWidget *parent = 0); - explicit TabWindow(WebPage *pg, QWidget *parent = 0); + explicit TabWidget(bool withTab = true, bool PrivateBrowsingMode = false, QWidget *parent = 0); + explicit TabWidget(WebPage *pg, QWidget *parent = 0); WebWindow* currentWebWindow() const; WebWindow* webWindow(int index) const; @@ -76,6 +74,14 @@ public: QList<TabHistory> recentlyClosedTabs(); void restoreClosedTab(int index, bool inNewTab = true); + // NOTE: For internal purpose only ------------------------------------------------------ + int addTab(QWidget *page, const QString &label); + int addTab(QWidget *page, const QIcon &icon, const QString &label); + + int insertTab(int index, QWidget *page, const QString &label); + int insertTab(int index, QWidget *page, const QIcon &icon, const QString &label); + // -------------------------------------------------------------------------------------- + public Q_SLOTS: void loadUrl(const KUrl &, Rekonq::OpenType type = Rekonq::CurrentTab, TabHistory *history = 0); void newTab(WebPage *page = 0); @@ -109,7 +115,7 @@ private Q_SLOTS: void cloneTab(int index = -1); void closeTab(int index = -1, bool del = true); void closeOtherTabs(int index = -1); - void detachTab(int index = -1, TabWindow *toWindow = 0); + void detachTab(int index = -1, RekonqWindow *toWindow = 0); void reloadTab(int index = -1); void reloadAllTabs(); @@ -137,4 +143,4 @@ private: KActionCollection *_ac; }; -#endif // TAB_WINDOW +#endif // TAB_WIDGET diff --git a/src/urlbar/rsswidget.cpp b/src/urlbar/rsswidget.cpp index 0d142d19..aeed6218 100644 --- a/src/urlbar/rsswidget.cpp +++ b/src/urlbar/rsswidget.cpp @@ -30,7 +30,8 @@ // Local includes #include "application.h" -#include "tabwindow.h" +#include "rekonqwindow.h" + #include "iconmanager.h" // KDE Includes @@ -132,7 +133,7 @@ void RSSWidget::accept() void RSSWidget::addWithGoogleReader(const QString &url) { KUrl toLoad = KUrl("http://www.google.com/ig/add?feedurl=" + url); - rApp->tabWindow()->loadUrl(toLoad); + rApp->rekonqWindow()->loadUrl(toLoad); } diff --git a/src/webwindow/rekonqui.rc b/src/webwindow/rekonqui.rc index 190111d9..90c5c192 100644 --- a/src/webwindow/rekonqui.rc +++ b/src/webwindow/rekonqui.rc @@ -1,6 +1,6 @@ <?xml version="1.0"?> <!DOCTYPE gui SYSTEM "kpartgui.dtd"> -<gui name="rekonq" version="68"> +<gui name="rekonq" version="69"> <!--- =========== Rekonq Menu ============= --> <Menu name="rekonqMenu" noMerge="1"> @@ -45,6 +45,13 @@ <Action name="open_history_page" /> <Action name="open_downloads_page" /> + + <Menu name="panelsMenu" noMerge="1"> + <text>&Panels</text> + <Action name="show_bookmarks_panel" /> + <Action name="show_history_panel" /> + </Menu> + <Separator/> <Action name="fullscreen" /> <Separator/> diff --git a/src/webwindow/webwindow.cpp b/src/webwindow/webwindow.cpp index 864c79b5..ab002459 100644 --- a/src/webwindow/webwindow.cpp +++ b/src/webwindow/webwindow.cpp @@ -31,7 +31,9 @@ #include "rekonq.h" #include "application.h" -#include "tabwindow.h" +#include "rekonqwindow.h" + +#include "tabwidget.h" #include "adblockmanager.h" #include "bookmarkmanager.h" @@ -994,7 +996,7 @@ void WebWindow::keyBindings() QPointer<KShortcutsDialog> dialog = new KShortcutsDialog(KShortcutsEditor::AllActions, KShortcutsEditor::LetterShortcutsAllowed, this); dialog->addCollection(actionCollection(), i18n("web window")); - TabWindow *tw = rApp->tabWindow(); + TabWidget *tw = rApp->rekonqWindow()->tabWidget(); if (tw) { dialog->addCollection(tw->actionCollection(), i18n("tab window")); |