1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-27 23:27:35 +00:00

FontEditor: Add a ListView to sort glyphs by their Unicode block

This commit is contained in:
thankyouverycool 2022-02-13 15:18:39 -05:00 committed by Tim Flynn
parent 6704bc0072
commit aefb2bcf43
4 changed files with 210 additions and 151 deletions

View file

@ -9,6 +9,7 @@
#include "GlyphEditorWidget.h" #include "GlyphEditorWidget.h"
#include "NewFontDialog.h" #include "NewFontDialog.h"
#include <AK/StringBuilder.h> #include <AK/StringBuilder.h>
#include <AK/StringUtils.h>
#include <Applications/FontEditor/FontEditorWindowGML.h> #include <Applications/FontEditor/FontEditorWindowGML.h>
#include <LibConfig/Client.h> #include <LibConfig/Client.h>
#include <LibDesktop/Launcher.h> #include <LibDesktop/Launcher.h>
@ -24,6 +25,7 @@
#include <LibGUI/InputBox.h> #include <LibGUI/InputBox.h>
#include <LibGUI/ItemListModel.h> #include <LibGUI/ItemListModel.h>
#include <LibGUI/Label.h> #include <LibGUI/Label.h>
#include <LibGUI/ListView.h>
#include <LibGUI/Menu.h> #include <LibGUI/Menu.h>
#include <LibGUI/Menubar.h> #include <LibGUI/Menubar.h>
#include <LibGUI/MessageBox.h> #include <LibGUI/MessageBox.h>
@ -39,7 +41,6 @@
#include <LibGfx/Palette.h> #include <LibGfx/Palette.h>
#include <LibGfx/TextDirection.h> #include <LibGfx/TextDirection.h>
#include <LibUnicode/CharacterTypes.h> #include <LibUnicode/CharacterTypes.h>
#include <stdlib.h>
static constexpr int s_pangram_count = 8; static constexpr int s_pangram_count = 8;
static char const* pangrams[s_pangram_count] = { static char const* pangrams[s_pangram_count] = {
@ -132,6 +133,7 @@ FontEditorWidget::FontEditorWidget()
m_baseline_spinbox = *find_descendant_of_type_named<GUI::SpinBox>("baseline_spinbox"); m_baseline_spinbox = *find_descendant_of_type_named<GUI::SpinBox>("baseline_spinbox");
m_fixed_width_checkbox = *find_descendant_of_type_named<GUI::CheckBox>("fixed_width_checkbox"); m_fixed_width_checkbox = *find_descendant_of_type_named<GUI::CheckBox>("fixed_width_checkbox");
m_font_metadata_groupbox = *find_descendant_of_type_named<GUI::GroupBox>("font_metadata_groupbox"); m_font_metadata_groupbox = *find_descendant_of_type_named<GUI::GroupBox>("font_metadata_groupbox");
m_unicode_block_listview = *find_descendant_of_type_named<GUI::ListView>("unicode_block_listview");
m_glyph_editor_widget = m_glyph_editor_container->add<GlyphEditorWidget>(); m_glyph_editor_widget = m_glyph_editor_container->add<GlyphEditorWidget>();
m_glyph_map_widget = glyph_map_container.add<GUI::GlyphMapWidget>(); m_glyph_map_widget = glyph_map_container.add<GUI::GlyphMapWidget>();
@ -210,11 +212,19 @@ FontEditorWidget::FontEditorWidget()
}); });
m_show_metadata_action->set_checked(true); m_show_metadata_action->set_checked(true);
m_show_metadata_action->set_status_tip("Show or hide metadata about the current font"); m_show_metadata_action->set_status_tip("Show or hide metadata about the current font");
m_show_unicode_blocks_action = GUI::Action::create_checkable("&Unicode Blocks", { Mod_Ctrl, Key_U }, [&](auto& action) {
set_show_unicode_blocks(action.is_checked());
});
m_show_unicode_blocks_action->set_checked(true);
m_show_unicode_blocks_action->set_status_tip("Show or hide the Unicode block list");
m_go_to_glyph_action = GUI::Action::create("&Go to Glyph...", { Mod_Ctrl, Key_G }, Gfx::Bitmap::try_load_from_file("/res/icons/16x16/go-to.png").release_value_but_fixme_should_propagate_errors(), [&](auto&) { m_go_to_glyph_action = GUI::Action::create("&Go to Glyph...", { Mod_Ctrl, Key_G }, Gfx::Bitmap::try_load_from_file("/res/icons/16x16/go-to.png").release_value_but_fixme_should_propagate_errors(), [&](auto&) {
String input; String input;
if (GUI::InputBox::show(window(), input, "Hexadecimal:", "Go to Glyph") == GUI::InputBox::ExecOK && !input.is_empty()) { if (GUI::InputBox::show(window(), input, "Hexadecimal:", "Go to glyph") == GUI::InputBox::ExecOK && !input.is_empty()) {
int code_point = strtoul(&input[0], nullptr, 16); auto maybe_code_point = AK::StringUtils::convert_to_uint_from_hex(input);
code_point = clamp(code_point, 0x0000, 0x10FFFF); if (!maybe_code_point.has_value())
return;
auto code_point = maybe_code_point.value();
code_point = clamp(code_point, m_range.first, m_range.last);
m_glyph_map_widget->set_focus(true); m_glyph_map_widget->set_focus(true);
m_glyph_map_widget->set_active_glyph(code_point); m_glyph_map_widget->set_active_glyph(code_point);
m_glyph_map_widget->scroll_to_glyph(code_point); m_glyph_map_widget->scroll_to_glyph(code_point);
@ -424,6 +434,25 @@ FontEditorWidget::FontEditorWidget()
did_modify_font(); did_modify_font();
}; };
auto unicode_blocks = Unicode::block_display_names();
m_unicode_block_listview->on_activation = [this, unicode_blocks](auto& index) {
if (index.row() > 0)
m_range = unicode_blocks[index.row() - 1].code_point_range;
else
m_range = { 0x0000, 0x10FFFF };
m_glyph_map_widget->set_active_range(m_range);
};
m_unicode_block_list.append("Show All");
for (auto& block : unicode_blocks)
m_unicode_block_list.append(block.display_name);
m_unicode_block_model = GUI::ItemListModel<String>::create(m_unicode_block_list);
m_unicode_block_listview->set_model(*m_unicode_block_model);
m_unicode_block_listview->set_activates_on_selection(true);
m_unicode_block_listview->horizontal_scrollbar().set_visible(false);
m_unicode_block_listview->set_cursor(m_unicode_block_model->index(0, 0), GUI::AbstractView::SelectionUpdate::Set);
GUI::Application::the()->on_action_enter = [this](GUI::Action& action) { GUI::Application::the()->on_action_enter = [this](GUI::Action& action) {
auto text = action.status_tip(); auto text = action.status_tip();
if (text.is_empty()) if (text.is_empty())
@ -543,6 +572,7 @@ void FontEditorWidget::initialize_menubar(GUI::Window& window)
view_menu.add_action(*m_open_preview_action); view_menu.add_action(*m_open_preview_action);
view_menu.add_separator(); view_menu.add_separator();
view_menu.add_action(*m_show_metadata_action); view_menu.add_action(*m_show_metadata_action);
view_menu.add_action(*m_show_unicode_blocks_action);
view_menu.add_separator(); view_menu.add_separator();
auto& scale_menu = view_menu.add_submenu("&Scale"); auto& scale_menu = view_menu.add_submenu("&Scale");
scale_menu.add_action(*m_scale_five_action); scale_menu.add_action(*m_scale_five_action);
@ -579,6 +609,14 @@ void FontEditorWidget::set_show_font_metadata(bool show)
m_font_metadata_groupbox->set_visible(m_font_metadata); m_font_metadata_groupbox->set_visible(m_font_metadata);
} }
void FontEditorWidget::set_show_unicode_blocks(bool show)
{
if (m_unicode_blocks == show)
return;
m_unicode_blocks = show;
m_unicode_block_listview->set_visible(m_unicode_blocks);
}
bool FontEditorWidget::open_file(String const& path) bool FontEditorWidget::open_file(String const& path)
{ {
auto bitmap_font = Gfx::BitmapFont::load_from_file(path); auto bitmap_font = Gfx::BitmapFont::load_from_file(path);

View file

@ -35,7 +35,10 @@ public:
void initialize_menubar(GUI::Window&); void initialize_menubar(GUI::Window&);
bool is_showing_font_metadata() { return m_font_metadata; } bool is_showing_font_metadata() { return m_font_metadata; }
void set_show_font_metadata(bool b); void set_show_font_metadata(bool);
bool is_showing_unicode_blocks() { return m_unicode_blocks; }
void set_show_unicode_blocks(bool);
Function<void()> on_initialize; Function<void()> on_initialize;
@ -87,6 +90,7 @@ private:
RefPtr<GUI::Action> m_open_preview_action; RefPtr<GUI::Action> m_open_preview_action;
RefPtr<GUI::Action> m_show_metadata_action; RefPtr<GUI::Action> m_show_metadata_action;
RefPtr<GUI::Action> m_show_unicode_blocks_action;
GUI::ActionGroup m_glyph_editor_scale_actions; GUI::ActionGroup m_glyph_editor_scale_actions;
RefPtr<GUI::Action> m_scale_five_action; RefPtr<GUI::Action> m_scale_five_action;
@ -119,9 +123,14 @@ private:
RefPtr<GUI::TextBox> m_family_textbox; RefPtr<GUI::TextBox> m_family_textbox;
RefPtr<GUI::CheckBox> m_fixed_width_checkbox; RefPtr<GUI::CheckBox> m_fixed_width_checkbox;
RefPtr<GUI::GroupBox> m_font_metadata_groupbox; RefPtr<GUI::GroupBox> m_font_metadata_groupbox;
RefPtr<GUI::ListView> m_unicode_block_listview;
RefPtr<GUI::Model> m_unicode_block_model;
String m_path; String m_path;
Vector<String> m_font_weight_list; Vector<String> m_font_weight_list;
Vector<String> m_font_slope_list; Vector<String> m_font_slope_list;
Vector<String> m_unicode_block_list;
bool m_font_metadata { true }; bool m_font_metadata { true };
bool m_unicode_blocks { true };
Unicode::CodePointRange m_range { 0x0000, 0x10FFFF };
}; };

View file

@ -58,6 +58,11 @@
spacing: 6 spacing: 6
} }
@GUI::HorizontalSplitter {
@GUI::Widget {
layout: @GUI::VerticalBoxLayout {}
@GUI::Widget { @GUI::Widget {
name: "glyph_map_container" name: "glyph_map_container"
layout: @GUI::VerticalBoxLayout {} layout: @GUI::VerticalBoxLayout {}
@ -214,6 +219,13 @@
} }
} }
} }
@GUI::ListView {
name: "unicode_block_listview"
max_width: 175
}
}
}
} }
@GUI::Statusbar { @GUI::Statusbar {

View file

@ -41,7 +41,7 @@ ErrorOr<int> serenity_main(Main::Arguments arguments)
auto window = TRY(GUI::Window::try_create()); auto window = TRY(GUI::Window::try_create());
window->set_icon(app_icon.bitmap_for_size(16)); window->set_icon(app_icon.bitmap_for_size(16));
window->resize(440, 470); window->resize(640, 470);
auto font_editor = TRY(window->try_set_main_widget<FontEditorWidget>()); auto font_editor = TRY(window->try_set_main_widget<FontEditorWidget>());
font_editor->initialize_menubar(*window); font_editor->initialize_menubar(*window);