mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2024-08-15 08:20:39 +03:00
Ladybird: Add a context menu to the tab bar
This shows the following actions: * Reload Tab * Duplicate Tab * Move Tab * Move to Start * Move to End * Close Tab * Close Other Tabs * Close Tabs to Left * Close Tabs to Right * Close Other Tabs
This commit is contained in:
parent
56ed3d5e21
commit
17fc995ee4
Notes:
sideshowbarker
2024-07-17 05:21:12 +09:00
Author: https://github.com/jamierocks Commit: https://github.com/SerenityOS/serenity/commit/17fc995ee4 Pull-request: https://github.com/SerenityOS/serenity/pull/24148
@ -625,6 +625,11 @@ void BrowserWindow::close_tab(int index)
|
|||||||
close();
|
close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void BrowserWindow::move_tab(int old_index, int new_index)
|
||||||
|
{
|
||||||
|
m_tabs_container->tabBar()->moveTab(old_index, new_index);
|
||||||
|
}
|
||||||
|
|
||||||
void BrowserWindow::open_file()
|
void BrowserWindow::open_file()
|
||||||
{
|
{
|
||||||
m_current_tab->open_file();
|
m_current_tab->open_file();
|
||||||
|
@ -34,6 +34,7 @@ public:
|
|||||||
|
|
||||||
WebContentView& view() const { return m_current_tab->view(); }
|
WebContentView& view() const { return m_current_tab->view(); }
|
||||||
|
|
||||||
|
int tab_count() { return m_tabs_container->count(); }
|
||||||
int tab_index(Tab*);
|
int tab_index(Tab*);
|
||||||
Tab& create_new_tab(Web::HTML::ActivateTab activate_tab);
|
Tab& create_new_tab(Web::HTML::ActivateTab activate_tab);
|
||||||
|
|
||||||
@ -98,6 +99,7 @@ public slots:
|
|||||||
Tab& new_child_tab(Web::HTML::ActivateTab, Tab& parent, Web::HTML::WebViewHints, Optional<u64> page_index);
|
Tab& new_child_tab(Web::HTML::ActivateTab, Tab& parent, Web::HTML::WebViewHints, Optional<u64> page_index);
|
||||||
void activate_tab(int index);
|
void activate_tab(int index);
|
||||||
void close_tab(int index);
|
void close_tab(int index);
|
||||||
|
void move_tab(int old_index, int new_index);
|
||||||
void close_current_tab();
|
void close_current_tab();
|
||||||
void open_next_tab();
|
void open_next_tab();
|
||||||
void open_previous_tab();
|
void open_previous_tab();
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (c) 2022, Andreas Kling <kling@serenityos.org>
|
* Copyright (c) 2022, Andreas Kling <kling@serenityos.org>
|
||||||
* Copyright (c) 2022, Matthew Costa <ucosty@gmail.com>
|
* Copyright (c) 2022, Matthew Costa <ucosty@gmail.com>
|
||||||
|
* Copyright (c) 2024, Jamie Mansfield <jmansfield@cadixdev.org>
|
||||||
*
|
*
|
||||||
* SPDX-License-Identifier: BSD-2-Clause
|
* SPDX-License-Identifier: BSD-2-Clause
|
||||||
*/
|
*/
|
||||||
@ -405,6 +406,69 @@ Tab::Tab(BrowserWindow* window, WebContentOptions const& web_content_options, St
|
|||||||
emit navigation_buttons_state_changed(tab_index());
|
emit navigation_buttons_state_changed(tab_index());
|
||||||
};
|
};
|
||||||
|
|
||||||
|
auto* reload_tab_action = new QAction("&Reload Tab", this);
|
||||||
|
QObject::connect(reload_tab_action, &QAction::triggered, this, [this]() {
|
||||||
|
reload();
|
||||||
|
});
|
||||||
|
|
||||||
|
auto* duplicate_tab_action = new QAction("&Duplicate Tab", this);
|
||||||
|
QObject::connect(duplicate_tab_action, &QAction::triggered, this, [this]() {
|
||||||
|
m_window->new_tab_from_url(view().url(), Web::HTML::ActivateTab::Yes);
|
||||||
|
});
|
||||||
|
|
||||||
|
auto* move_to_start_action = new QAction("Move to &Start", this);
|
||||||
|
QObject::connect(move_to_start_action, &QAction::triggered, this, [this]() {
|
||||||
|
m_window->move_tab(tab_index(), 0);
|
||||||
|
});
|
||||||
|
|
||||||
|
auto* move_to_end_action = new QAction("Move to &End", this);
|
||||||
|
QObject::connect(move_to_end_action, &QAction::triggered, this, [this]() {
|
||||||
|
m_window->move_tab(tab_index(), m_window->tab_count() - 1);
|
||||||
|
});
|
||||||
|
|
||||||
|
auto* close_tab_action = new QAction("&Close Tab", this);
|
||||||
|
QObject::connect(close_tab_action, &QAction::triggered, this, [this]() {
|
||||||
|
view().on_close();
|
||||||
|
});
|
||||||
|
|
||||||
|
auto* close_tabs_to_left_action = new QAction("C&lose Tabs to Left", this);
|
||||||
|
QObject::connect(close_tabs_to_left_action, &QAction::triggered, this, [this]() {
|
||||||
|
for (auto i = tab_index() - 1; i >= 0; i--) {
|
||||||
|
m_window->close_tab(i);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
auto* close_tabs_to_right_action = new QAction("Close Tabs to R&ight", this);
|
||||||
|
QObject::connect(close_tabs_to_right_action, &QAction::triggered, this, [this]() {
|
||||||
|
for (auto i = m_window->tab_count() - 1; i > tab_index(); i--) {
|
||||||
|
m_window->close_tab(i);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
auto* close_other_tabs_action = new QAction("Cl&ose Other Tabs", this);
|
||||||
|
QObject::connect(close_other_tabs_action, &QAction::triggered, this, [this]() {
|
||||||
|
for (auto i = m_window->tab_count() - 1; i >= 0; i--) {
|
||||||
|
if (i == tab_index())
|
||||||
|
continue;
|
||||||
|
|
||||||
|
m_window->close_tab(i);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
m_context_menu = new QMenu("Context menu", this);
|
||||||
|
m_context_menu->addAction(reload_tab_action);
|
||||||
|
m_context_menu->addAction(duplicate_tab_action);
|
||||||
|
m_context_menu->addSeparator();
|
||||||
|
auto* move_tab_menu = m_context_menu->addMenu("Mo&ve Tab");
|
||||||
|
move_tab_menu->addAction(move_to_start_action);
|
||||||
|
move_tab_menu->addAction(move_to_end_action);
|
||||||
|
m_context_menu->addSeparator();
|
||||||
|
m_context_menu->addAction(close_tab_action);
|
||||||
|
auto* close_multiple_tabs_menu = m_context_menu->addMenu("Close &Multiple Tabs");
|
||||||
|
close_multiple_tabs_menu->addAction(close_tabs_to_left_action);
|
||||||
|
close_multiple_tabs_menu->addAction(close_tabs_to_right_action);
|
||||||
|
close_multiple_tabs_menu->addAction(close_other_tabs_action);
|
||||||
|
|
||||||
auto* search_selected_text_action = new QAction("&Search for <query>", this);
|
auto* search_selected_text_action = new QAction("&Search for <query>", this);
|
||||||
search_selected_text_action->setIcon(load_icon_from_uri("resource://icons/16x16/find.png"sv));
|
search_selected_text_action->setIcon(load_icon_from_uri("resource://icons/16x16/find.png"sv));
|
||||||
QObject::connect(search_selected_text_action, &QAction::triggered, this, [this]() {
|
QObject::connect(search_selected_text_action, &QAction::triggered, this, [this]() {
|
||||||
|
@ -54,6 +54,8 @@ public:
|
|||||||
QIcon const& favicon() const { return m_favicon; }
|
QIcon const& favicon() const { return m_favicon; }
|
||||||
QString const& title() const { return m_title; }
|
QString const& title() const { return m_title; }
|
||||||
|
|
||||||
|
QMenu* context_menu() const { return m_context_menu; }
|
||||||
|
|
||||||
void update_navigation_buttons_state();
|
void update_navigation_buttons_state();
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
@ -91,6 +93,8 @@ private:
|
|||||||
QLabel* m_hover_label { nullptr };
|
QLabel* m_hover_label { nullptr };
|
||||||
QIcon m_favicon;
|
QIcon m_favicon;
|
||||||
|
|
||||||
|
QMenu* m_context_menu { nullptr };
|
||||||
|
|
||||||
QMenu* m_page_context_menu { nullptr };
|
QMenu* m_page_context_menu { nullptr };
|
||||||
Optional<String> m_page_context_menu_search_text;
|
Optional<String> m_page_context_menu_search_text;
|
||||||
|
|
||||||
|
@ -1,16 +1,25 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (c) 2024, Tim Flynn <trflynn89@serenityos.org>
|
* Copyright (c) 2024, Tim Flynn <trflynn89@serenityos.org>
|
||||||
|
* Copyright (c) 2024, Jamie Mansfield <jmansfield@cadixdev.org>
|
||||||
*
|
*
|
||||||
* SPDX-License-Identifier: BSD-2-Clause
|
* SPDX-License-Identifier: BSD-2-Clause
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "Tab.h"
|
||||||
#include <AK/StdLibExtras.h>
|
#include <AK/StdLibExtras.h>
|
||||||
|
#include <AK/TypeCasts.h>
|
||||||
#include <Ladybird/Qt/TabBar.h>
|
#include <Ladybird/Qt/TabBar.h>
|
||||||
|
#include <QContextMenuEvent>
|
||||||
#include <QEvent>
|
#include <QEvent>
|
||||||
#include <QPushButton>
|
#include <QPushButton>
|
||||||
|
|
||||||
namespace Ladybird {
|
namespace Ladybird {
|
||||||
|
|
||||||
|
TabBar::TabBar(QWidget* parent)
|
||||||
|
: QTabBar(parent)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
QSize TabBar::tabSizeHint(int index) const
|
QSize TabBar::tabSizeHint(int index) const
|
||||||
{
|
{
|
||||||
auto width = this->width() / count();
|
auto width = this->width() / count();
|
||||||
@ -22,11 +31,19 @@ QSize TabBar::tabSizeHint(int index) const
|
|||||||
return hint;
|
return hint;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void TabBar::contextMenuEvent(QContextMenuEvent* event)
|
||||||
|
{
|
||||||
|
auto* tab_widget = verify_cast<QTabWidget>(this->parent());
|
||||||
|
auto* tab = verify_cast<Tab>(tab_widget->widget(tabAt(event->pos())));
|
||||||
|
if (tab)
|
||||||
|
tab->context_menu()->exec(event->globalPos());
|
||||||
|
}
|
||||||
|
|
||||||
TabWidget::TabWidget(QWidget* parent)
|
TabWidget::TabWidget(QWidget* parent)
|
||||||
: QTabWidget(parent)
|
: QTabWidget(parent)
|
||||||
{
|
{
|
||||||
// This must be called first, otherwise several of the options below have no effect.
|
// This must be called first, otherwise several of the options below have no effect.
|
||||||
setTabBar(new TabBar());
|
setTabBar(new TabBar(this));
|
||||||
|
|
||||||
setDocumentMode(true);
|
setDocumentMode(true);
|
||||||
setElideMode(Qt::TextElideMode::ElideRight);
|
setElideMode(Qt::TextElideMode::ElideRight);
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (c) 2024, Tim Flynn <trflynn89@serenityos.org>
|
* Copyright (c) 2024, Tim Flynn <trflynn89@serenityos.org>
|
||||||
|
* Copyright (c) 2024, Jamie Mansfield <jmansfield@cadixdev.org>
|
||||||
*
|
*
|
||||||
* SPDX-License-Identifier: BSD-2-Clause
|
* SPDX-License-Identifier: BSD-2-Clause
|
||||||
*/
|
*/
|
||||||
@ -10,6 +11,7 @@
|
|||||||
#include <QTabBar>
|
#include <QTabBar>
|
||||||
#include <QTabWidget>
|
#include <QTabWidget>
|
||||||
|
|
||||||
|
class QContextMenuEvent;
|
||||||
class QEvent;
|
class QEvent;
|
||||||
class QIcon;
|
class QIcon;
|
||||||
class QWidget;
|
class QWidget;
|
||||||
@ -20,7 +22,10 @@ class TabBar : public QTabBar {
|
|||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
explicit TabBar(QWidget* parent = nullptr);
|
||||||
|
|
||||||
virtual QSize tabSizeHint(int index) const override;
|
virtual QSize tabSizeHint(int index) const override;
|
||||||
|
virtual void contextMenuEvent(QContextMenuEvent* event) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
class TabWidget : public QTabWidget {
|
class TabWidget : public QTabWidget {
|
||||||
|
Loading…
Reference in New Issue
Block a user