mirror of
https://github.com/RGBCube/serenity
synced 2025-05-30 23:48:11 +00:00
DevTools+LibGUI: Make ProcessChooser a general Dialog in LibGUI
Moves ProcessChooser and RunningProcessesModel to LibGUI and generalizes their construction for use by other apps. Updates Profiler to reflect the change and use its new icons.
This commit is contained in:
parent
5cfbf88b4d
commit
6448f94372
7 changed files with 57 additions and 26 deletions
|
@ -1,11 +1,9 @@
|
||||||
set(SOURCES
|
set(SOURCES
|
||||||
DisassemblyModel.cpp
|
DisassemblyModel.cpp
|
||||||
main.cpp
|
main.cpp
|
||||||
ProcessChooser.cpp
|
|
||||||
Profile.cpp
|
Profile.cpp
|
||||||
ProfileModel.cpp
|
ProfileModel.cpp
|
||||||
ProfileTimelineWidget.cpp
|
ProfileTimelineWidget.cpp
|
||||||
RunningProcessesModel.cpp
|
|
||||||
)
|
)
|
||||||
|
|
||||||
serenity_bin(Profiler)
|
serenity_bin(Profiler)
|
||||||
|
|
|
@ -24,13 +24,13 @@
|
||||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "ProcessChooser.h"
|
|
||||||
#include "Profile.h"
|
#include "Profile.h"
|
||||||
#include "ProfileTimelineWidget.h"
|
#include "ProfileTimelineWidget.h"
|
||||||
#include <LibCore/ArgsParser.h>
|
#include <LibCore/ArgsParser.h>
|
||||||
#include <LibCore/ElapsedTimer.h>
|
#include <LibCore/ElapsedTimer.h>
|
||||||
#include <LibCore/EventLoop.h>
|
#include <LibCore/EventLoop.h>
|
||||||
#include <LibCore/Timer.h>
|
#include <LibCore/Timer.h>
|
||||||
|
#include <LibGUI/AboutDialog.h>
|
||||||
#include <LibGUI/Action.h>
|
#include <LibGUI/Action.h>
|
||||||
#include <LibGUI/Application.h>
|
#include <LibGUI/Application.h>
|
||||||
#include <LibGUI/BoxLayout.h>
|
#include <LibGUI/BoxLayout.h>
|
||||||
|
@ -41,6 +41,7 @@
|
||||||
#include <LibGUI/MenuBar.h>
|
#include <LibGUI/MenuBar.h>
|
||||||
#include <LibGUI/MessageBox.h>
|
#include <LibGUI/MessageBox.h>
|
||||||
#include <LibGUI/Model.h>
|
#include <LibGUI/Model.h>
|
||||||
|
#include <LibGUI/ProcessChooser.h>
|
||||||
#include <LibGUI/Splitter.h>
|
#include <LibGUI/Splitter.h>
|
||||||
#include <LibGUI/TableView.h>
|
#include <LibGUI/TableView.h>
|
||||||
#include <LibGUI/TreeView.h>
|
#include <LibGUI/TreeView.h>
|
||||||
|
@ -59,6 +60,7 @@ int main(int argc, char** argv)
|
||||||
args_parser.parse(argc, argv, false);
|
args_parser.parse(argc, argv, false);
|
||||||
|
|
||||||
auto app = GUI::Application::construct(argc, argv);
|
auto app = GUI::Application::construct(argc, argv);
|
||||||
|
auto app_icon = GUI::Icon::default_icon("app-profiler");
|
||||||
|
|
||||||
const char* path = nullptr;
|
const char* path = nullptr;
|
||||||
if (argc != 2) {
|
if (argc != 2) {
|
||||||
|
@ -79,6 +81,7 @@ int main(int argc, char** argv)
|
||||||
auto window = GUI::Window::construct();
|
auto window = GUI::Window::construct();
|
||||||
window->set_title("Profiler");
|
window->set_title("Profiler");
|
||||||
window->set_rect(100, 100, 800, 600);
|
window->set_rect(100, 100, 800, 600);
|
||||||
|
window->set_icon(app_icon.bitmap_for_size(16));
|
||||||
|
|
||||||
auto& main_widget = window->set_main_widget<GUI::Widget>();
|
auto& main_widget = window->set_main_widget<GUI::Widget>();
|
||||||
main_widget.set_fill_with_background_color(true);
|
main_widget.set_fill_with_background_color(true);
|
||||||
|
@ -118,6 +121,11 @@ int main(int argc, char** argv)
|
||||||
percent_action->set_checked(false);
|
percent_action->set_checked(false);
|
||||||
view_menu.add_action(percent_action);
|
view_menu.add_action(percent_action);
|
||||||
|
|
||||||
|
auto& help_menu = menubar->add_menu("Help");
|
||||||
|
help_menu.add_action(GUI::Action::create("About", [&](auto&) {
|
||||||
|
GUI::AboutDialog::show("Profiler", app_icon.bitmap_for_size(32), window);
|
||||||
|
}));
|
||||||
|
|
||||||
app->set_menubar(move(menubar));
|
app->set_menubar(move(menubar));
|
||||||
|
|
||||||
window->show();
|
window->show();
|
||||||
|
@ -128,6 +136,7 @@ bool prompt_to_stop_profiling()
|
||||||
{
|
{
|
||||||
auto window = GUI::Window::construct();
|
auto window = GUI::Window::construct();
|
||||||
window->set_title("Profiling");
|
window->set_title("Profiling");
|
||||||
|
window->set_icon(Gfx::Bitmap::load_from_file("/res/icons/16x16/app-profiler.png"));
|
||||||
Gfx::IntRect window_rect { 0, 0, 320, 200 };
|
Gfx::IntRect window_rect { 0, 0, 320, 200 };
|
||||||
window_rect.center_within(GUI::Desktop::the().rect());
|
window_rect.center_within(GUI::Desktop::the().rect());
|
||||||
window->set_rect(window_rect);
|
window->set_rect(window_rect);
|
||||||
|
@ -154,7 +163,7 @@ bool prompt_to_stop_profiling()
|
||||||
bool generate_profile(pid_t pid)
|
bool generate_profile(pid_t pid)
|
||||||
{
|
{
|
||||||
if (!pid) {
|
if (!pid) {
|
||||||
auto process_chooser = Profiler::ProcessChooser::construct();
|
auto process_chooser = GUI::ProcessChooser::construct("Profiler", "Profile", Gfx::Bitmap::load_from_file("/res/icons/16x16/app-profiler.png"));
|
||||||
if (process_chooser->exec() == GUI::Dialog::ExecCancel)
|
if (process_chooser->exec() == GUI::Dialog::ExecCancel)
|
||||||
return false;
|
return false;
|
||||||
pid = process_chooser->pid();
|
pid = process_chooser->pid();
|
||||||
|
|
|
@ -51,9 +51,11 @@ set(SOURCES
|
||||||
MultiView.cpp
|
MultiView.cpp
|
||||||
Notification.cpp
|
Notification.cpp
|
||||||
Painter.cpp
|
Painter.cpp
|
||||||
|
ProcessChooser.cpp
|
||||||
ProgressBar.cpp
|
ProgressBar.cpp
|
||||||
RadioButton.cpp
|
RadioButton.cpp
|
||||||
ResizeCorner.cpp
|
ResizeCorner.cpp
|
||||||
|
RunningProcessesModel.cpp
|
||||||
ScrollableWidget.cpp
|
ScrollableWidget.cpp
|
||||||
ScrollBar.cpp
|
ScrollBar.cpp
|
||||||
Shortcut.cpp
|
Shortcut.cpp
|
||||||
|
|
|
@ -24,46 +24,58 @@
|
||||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "ProcessChooser.h"
|
|
||||||
#include "RunningProcessesModel.h"
|
|
||||||
#include <LibGUI/BoxLayout.h>
|
#include <LibGUI/BoxLayout.h>
|
||||||
#include <LibGUI/Button.h>
|
#include <LibGUI/Button.h>
|
||||||
#include <LibGUI/Desktop.h>
|
#include <LibGUI/Desktop.h>
|
||||||
#include <LibGUI/MessageBox.h>
|
#include <LibGUI/MessageBox.h>
|
||||||
|
#include <LibGUI/ProcessChooser.h>
|
||||||
|
#include <LibGUI/RunningProcessesModel.h>
|
||||||
#include <LibGUI/SortingProxyModel.h>
|
#include <LibGUI/SortingProxyModel.h>
|
||||||
#include <LibGUI/TableView.h>
|
#include <LibGUI/TableView.h>
|
||||||
|
|
||||||
namespace Profiler {
|
namespace GUI {
|
||||||
|
|
||||||
ProcessChooser::ProcessChooser(GUI::Window* parent_window)
|
ProcessChooser::ProcessChooser(const StringView& window_title, const StringView& button_label, const Gfx::Bitmap* window_icon, GUI::Window* parent_window)
|
||||||
: Dialog(parent_window)
|
: Dialog(parent_window)
|
||||||
|
, m_window_title(window_title)
|
||||||
|
, m_button_label(button_label)
|
||||||
|
, m_window_icon(window_icon)
|
||||||
{
|
{
|
||||||
build();
|
set_title(m_window_title);
|
||||||
}
|
|
||||||
|
|
||||||
void ProcessChooser::build()
|
if (m_window_icon)
|
||||||
{
|
set_icon(m_window_icon);
|
||||||
set_title("Profiler");
|
else if (parent_window)
|
||||||
Gfx::IntRect window_rect { 0, 0, 480, 360 };
|
set_icon(parent_window->icon());
|
||||||
|
|
||||||
|
Gfx::IntRect window_rect { 0, 0, 300, 340 };
|
||||||
window_rect.center_within(GUI::Desktop::the().rect());
|
window_rect.center_within(GUI::Desktop::the().rect());
|
||||||
set_rect(window_rect);
|
set_rect(window_rect);
|
||||||
|
|
||||||
auto& widget = set_main_widget<GUI::Widget>();
|
auto& widget = set_main_widget<GUI::Widget>();
|
||||||
widget.set_fill_with_background_color(true);
|
widget.set_fill_with_background_color(true);
|
||||||
widget.set_layout<GUI::VerticalBoxLayout>();
|
widget.set_layout<GUI::VerticalBoxLayout>();
|
||||||
|
widget.layout()->set_margins({ 0, 0, 0, 2 });
|
||||||
|
|
||||||
auto& table_view = widget.add<GUI::TableView>();
|
auto& table_view = widget.add<GUI::TableView>();
|
||||||
auto sorting_model = GUI::SortingProxyModel::create(Profiler::RunningProcessesModel::create());
|
auto sorting_model = GUI::SortingProxyModel::create(RunningProcessesModel::create());
|
||||||
sorting_model->set_sort_role(GUI::Model::Role::Display);
|
sorting_model->set_sort_role(GUI::Model::Role::Display);
|
||||||
sorting_model->set_key_column_and_sort_order(Profiler::RunningProcessesModel::Column::PID, GUI::SortOrder::Descending);
|
sorting_model->set_key_column_and_sort_order(RunningProcessesModel::Column::PID, GUI::SortOrder::Descending);
|
||||||
table_view.set_model(sorting_model);
|
table_view.set_model(sorting_model);
|
||||||
|
|
||||||
auto& button_container = widget.add<GUI::Widget>();
|
auto& button_container = widget.add<GUI::Widget>();
|
||||||
button_container.set_preferred_size(0, 30);
|
button_container.set_preferred_size(0, 30);
|
||||||
button_container.set_size_policy(GUI::SizePolicy::Fill, GUI::SizePolicy::Fixed);
|
button_container.set_size_policy(GUI::SizePolicy::Fill, GUI::SizePolicy::Fixed);
|
||||||
button_container.set_layout<GUI::HorizontalBoxLayout>();
|
button_container.set_layout<GUI::HorizontalBoxLayout>();
|
||||||
auto& profile_button = button_container.add<GUI::Button>("Profile");
|
button_container.layout()->set_margins({ 0, 0, 4, 0 });
|
||||||
profile_button.on_click = [&](auto) {
|
button_container.layout()->add_spacer();
|
||||||
|
|
||||||
|
auto& select_button = button_container.add<GUI::Button>(m_button_label);
|
||||||
|
select_button.set_size_policy(GUI::SizePolicy::Fixed, GUI::SizePolicy::Fixed);
|
||||||
|
select_button.set_preferred_size(80, 24);
|
||||||
|
select_button.on_click = [&](auto) {
|
||||||
if (table_view.selection().is_empty()) {
|
if (table_view.selection().is_empty()) {
|
||||||
GUI::MessageBox::show(this, "No process selected!", "Profiler", GUI::MessageBox::Type::Error);
|
GUI::MessageBox::show(this, "No process selected!", m_window_title, GUI::MessageBox::Type::Error);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
auto index = table_view.selection().first();
|
auto index = table_view.selection().first();
|
||||||
|
@ -72,6 +84,8 @@ void ProcessChooser::build()
|
||||||
done(ExecOK);
|
done(ExecOK);
|
||||||
};
|
};
|
||||||
auto& cancel_button = button_container.add<GUI::Button>("Cancel");
|
auto& cancel_button = button_container.add<GUI::Button>("Cancel");
|
||||||
|
cancel_button.set_size_policy(GUI::SizePolicy::Fixed, GUI::SizePolicy::Fixed);
|
||||||
|
cancel_button.set_preferred_size(80, 24);
|
||||||
cancel_button.on_click = [this](auto) {
|
cancel_button.on_click = [this](auto) {
|
||||||
done(ExecCancel);
|
done(ExecCancel);
|
||||||
};
|
};
|
||||||
|
@ -79,4 +93,8 @@ void ProcessChooser::build()
|
||||||
table_view.model()->update();
|
table_view.model()->update();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ProcessChooser::~ProcessChooser()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
|
@ -28,20 +28,24 @@
|
||||||
|
|
||||||
#include <LibGUI/Dialog.h>
|
#include <LibGUI/Dialog.h>
|
||||||
|
|
||||||
namespace Profiler {
|
namespace GUI {
|
||||||
|
|
||||||
class ProcessChooser final : public GUI::Dialog {
|
class ProcessChooser final : public GUI::Dialog {
|
||||||
C_OBJECT(ProcessChooser);
|
C_OBJECT(ProcessChooser);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
virtual ~ProcessChooser() override;
|
||||||
|
|
||||||
pid_t pid() const { return m_pid; }
|
pid_t pid() const { return m_pid; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
ProcessChooser(GUI::Window* parent_window = nullptr);
|
ProcessChooser(const StringView& window_title = "Process Chooser", const StringView& button_label = "Select", const Gfx::Bitmap* window_icon = nullptr, GUI::Window* parent_window = nullptr);
|
||||||
|
|
||||||
void build();
|
|
||||||
|
|
||||||
pid_t m_pid { 0 };
|
pid_t m_pid { 0 };
|
||||||
|
|
||||||
|
String m_window_title;
|
||||||
|
String m_button_label;
|
||||||
|
RefPtr<Gfx::Bitmap> m_window_icon;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
|
@ -24,11 +24,11 @@
|
||||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "RunningProcessesModel.h"
|
|
||||||
#include <AK/SharedBuffer.h>
|
#include <AK/SharedBuffer.h>
|
||||||
#include <LibCore/ProcessStatisticsReader.h>
|
#include <LibCore/ProcessStatisticsReader.h>
|
||||||
|
#include <LibGUI/RunningProcessesModel.h>
|
||||||
|
|
||||||
namespace Profiler {
|
namespace GUI {
|
||||||
|
|
||||||
NonnullRefPtr<RunningProcessesModel> RunningProcessesModel::create()
|
NonnullRefPtr<RunningProcessesModel> RunningProcessesModel::create()
|
||||||
{
|
{
|
|
@ -29,7 +29,7 @@
|
||||||
#include <LibGUI/Model.h>
|
#include <LibGUI/Model.h>
|
||||||
#include <LibGfx/Bitmap.h>
|
#include <LibGfx/Bitmap.h>
|
||||||
|
|
||||||
namespace Profiler {
|
namespace GUI {
|
||||||
|
|
||||||
class RunningProcessesModel final : public GUI::Model {
|
class RunningProcessesModel final : public GUI::Model {
|
||||||
public:
|
public:
|
Loading…
Add table
Add a link
Reference in a new issue