Falkon Develop
Cross-platform Qt-based web browser
verticaltabswidget.cpp
Go to the documentation of this file.
1/* ============================================================
2* VerticalTabs plugin for Falkon
3* Copyright (C) 2018 David Rosca <nowrep@gmail.com>
4*
5* This program is free software: you can redistribute it and/or modify
6* it under the terms of the GNU General Public License as published by
7* the Free Software Foundation, either version 3 of the License, or
8* (at your option) any later version.
9*
10* This program is distributed in the hope that it will be useful,
11* but WITHOUT ANY WARRANTY; without even the implied warranty of
12* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13* GNU General Public License for more details.
14*
15* You should have received a copy of the GNU General Public License
16* along with this program. If not, see <http://www.gnu.org/licenses/>.
17* ============================================================ */
18#include "verticaltabswidget.h"
19#include "tabtreeview.h"
20#include "tablistview.h"
21#include "tabfiltermodel.h"
22
23#include "webtab.h"
24#include "tabmodel.h"
25#include "tabwidget.h"
26#include "toolbutton.h"
27#include "tabtreemodel.h"
28#include "browserwindow.h"
29
30#include <QListView>
31#include <QScrollBar>
32#include <QVBoxLayout>
33#include <QWheelEvent>
34
36 : QWidget()
37 , m_window(window)
38{
39 auto *layout = new QVBoxLayout(this);
40 layout->setSpacing(0);
41 layout->setContentsMargins(0, 0, 0, 0);
42
43 m_pinnedView = new TabListView(m_window, this);
44 auto *model = new TabFilterModel(m_pinnedView);
45 model->setFilterPinnedTabs(false);
46 model->setRejectDropOnLastIndex(true);
47 model->setSourceModel(m_window->tabModel());
48 m_pinnedView->setModel(model);
49 m_pinnedView->setHideWhenEmpty(true);
50
51 m_normalView = new TabTreeView(m_window, this);
52 m_pinnedView->setFocusProxy(m_normalView);
53
54 auto *buttonAddTab = new ToolButton(this);
55 buttonAddTab->setObjectName(QSL("verticaltabs-button-addtab"));
56 buttonAddTab->setAutoRaise(true);
57 buttonAddTab->setFocusPolicy(Qt::NoFocus);
58 buttonAddTab->setToolTip(tr("New Tab"));
59 buttonAddTab->setIcon(QIcon::fromTheme(QSL("list-add")));
60 buttonAddTab->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred);
61 connect(buttonAddTab, &QAbstractButton::clicked, m_window, &BrowserWindow::addTab);
63
64 m_groupMenu = new QMenu(this);
65 buttonAddTab->setMenu(m_groupMenu);
66 connect(m_groupMenu, &QMenu::aboutToShow, this, &VerticalTabsWidget::updateGroupMenu);
67
68 layout->addWidget(m_pinnedView);
69 layout->addWidget(m_normalView);
70 layout->addWidget(buttonAddTab);
71}
72
74{
75 auto *model = new TabFilterModel(m_normalView);
76 model->setFilterPinnedTabs(true);
77
78 delete m_normalView->model();
79
80 switch (type) {
82 model->setSourceModel(m_window->tabModel());
83 m_normalView->setModel(model);
84 m_normalView->setTabsInOrder(true);
85 m_normalView->setHaveTreeModel(false);
86 break;
87
89 m_treeModel = new TabTreeModel(m_window, model);
90 m_treeModel->setSourceModel(m_window->tabModel());
91 model->setSourceModel(m_treeModel);
92 m_normalView->setModel(model);
93 m_normalView->setTabsInOrder(false);
94 m_normalView->setHaveTreeModel(true);
95 break;
96
97 default:
98 break;
99 };
100}
101
103{
104 WebTab *tab = nextTab();
105 if (tab) {
106 tab->makeCurrentTab();
107 }
108}
109
111{
112 WebTab *tab = previousTab();
113 if (tab) {
114 tab->makeCurrentTab();
115 }
116}
117
118WebTab *VerticalTabsWidget::nextTab() const
119{
120 QModelIndex next;
121 if (m_window->tabWidget()->webTab()->isPinned()) {
122 next = m_pinnedView->indexAfter(m_pinnedView->currentIndex());
123 if (!next.isValid()) {
124 next = m_normalView->model()->index(0, 0);
125 }
126 } else {
127 next = m_normalView->indexBelow(m_normalView->currentIndex());
128 if (!next.isValid()) {
129 next = m_pinnedView->model()->index(0, 0);
130 }
131 }
132 return next.data(TabModel::WebTabRole).value<WebTab*>();
133}
134
135WebTab *VerticalTabsWidget::previousTab() const
136{
137 QModelIndex previous;
138 if (m_window->tabWidget()->webTab()->isPinned()) {
139 previous = m_pinnedView->indexBefore(m_pinnedView->currentIndex());
140 if (!previous.isValid()) {
141 previous = m_normalView->model()->index(m_normalView->model()->rowCount() - 1, 0);
142 while (previous.isValid()) {
143 const QModelIndex below = m_normalView->indexBelow(previous);
144 if (below.isValid()) {
145 previous = below;
146 } else {
147 break;
148 }
149 }
150 }
151 } else {
152 previous = m_normalView->indexAbove(m_normalView->currentIndex());
153 if (!previous.isValid()) {
154 previous = m_pinnedView->model()->index(m_pinnedView->model()->rowCount() - 1, 0);
155 }
156 }
157 return previous.data(TabModel::WebTabRole).value<WebTab*>();
158}
159
160void VerticalTabsWidget::wheelEvent(QWheelEvent *event)
161{
162 if (m_normalView->verticalScrollBar()->isVisible()) {
163 return;
164 }
165
166 m_wheelHelper.processEvent(event);
167 while (WheelHelper::Direction direction = m_wheelHelper.takeDirection()) {
168 switch (direction) {
172 break;
173
177 break;
178
179 default:
180 break;
181 }
182 }
183 event->accept();
184}
185
186void VerticalTabsWidget::updateGroupMenu()
187{
188 m_groupMenu->clear();
189
190 for (int i = 0; i < m_window->tabWidget()->count(); ++i) {
191 WebTab *tab = m_window->tabWidget()->webTab(i);
192 if (tab->url().toString(QUrl::RemoveFragment) == QL1S("extension://verticaltabs/group")) {
193 m_groupMenu->addAction(tab->url().fragment(), this, [=]() {
194 QMetaObject::invokeMethod(m_window, "addTab");
195 m_window->tabWidget()->webTab()->setParentTab(tab);
196 });
197 }
198 }
199
200 m_groupMenu->addSeparator();
201 m_groupMenu->addAction(tr("Add New Group..."), this, [this]() {
202 m_window->tabWidget()->addView(QUrl(QSL("extension://verticaltabs/group")), Qz::NT_SelectedTab);
203 });
204}
205
207{
208 WebTab *tab = m_window->tabWidget()->webTab();
209 m_window->addTab();
210 m_window->tabWidget()->webTab()->setParentTab(tab);
211}
TabWidget * tabWidget() const
TabModel * tabModel() const
QModelIndex indexBefore(const QModelIndex &index) const
QModelIndex indexAfter(const QModelIndex &index) const
Definition: tablistview.cpp:98
void setHideWhenEmpty(bool enable)
Definition: tablistview.cpp:57
@ WebTabRole
Definition: tabmodel.h:54
void setModel(QAbstractItemModel *model) override
void setHaveTreeModel(bool enable)
Definition: tabtreeview.cpp:96
void setTabsInOrder(bool enable)
Definition: tabtreeview.cpp:86
WebTab * webTab(int index=-1) const
Definition: tabwidget.cpp:570
void middleMouseClicked()
void setViewType(VerticalTabsPlugin::ViewType type)
VerticalTabsWidget(BrowserWindow *window)
Definition: webtab.h:40
void makeCurrentTab()
Definition: webtab.cpp:689
void setParentTab(WebTab *tab)
Definition: webtab.cpp:474
QUrl url() const
Definition: webtab.cpp:263
bool isPinned() const
Definition: webtab.cpp:414
Direction takeDirection()
Definition: wheelhelper.cpp:74
void processEvent(QWheelEvent *event)
Definition: wheelhelper.cpp:31
@ NT_SelectedTab
Definition: qzcommon.h:97
i
Definition: i18n.py:23
#define QL1S(x)
Definition: qzcommon.h:44
#define QSL(x)
Definition: qzcommon.h:40