mirror of
				https://github.com/RGBCube/serenity
				synced 2025-10-31 21:52:45 +00:00 
			
		
		
		
	LibGUI+LibGfx+LibTTF: Make fontpicker handle TTF fonts
This commit is contained in:
		
							parent
							
								
									5a70ccecb3
								
							
						
					
					
						commit
						0f41f5d9ba
					
				
					 6 changed files with 46 additions and 21 deletions
				
			
		|  | @ -113,22 +113,22 @@ FontPicker::FontPicker(Window* parent_window, const Gfx::Font* current_font, boo | ||||||
|     m_sample_text_label = *widget.find_descendant_of_type_named<Label>("sample_text_label"); |     m_sample_text_label = *widget.find_descendant_of_type_named<Label>("sample_text_label"); | ||||||
| 
 | 
 | ||||||
|     m_families.clear(); |     m_families.clear(); | ||||||
|     Gfx::FontDatabase::the().for_each_font([&](auto& font) { |     Gfx::FontDatabase::the().for_each_typeface([&](auto& typeface) { | ||||||
|         if (m_fixed_width_only && !font.is_fixed_width()) |         if (m_fixed_width_only && !typeface.is_fixed_width()) | ||||||
|             return; |             return; | ||||||
|         if (!m_families.contains_slow(font.family())) |         if (!m_families.contains_slow(typeface.family())) | ||||||
|             m_families.append(font.family()); |             m_families.append(typeface.family()); | ||||||
|     }); |     }); | ||||||
|     quick_sort(m_families); |     quick_sort(m_families); | ||||||
| 
 | 
 | ||||||
|     m_family_list_view->on_selection = [this](auto& index) { |     m_family_list_view->on_selection = [this](auto& index) { | ||||||
|         m_family = index.data().to_string(); |         m_family = index.data().to_string(); | ||||||
|         m_weights.clear(); |         m_weights.clear(); | ||||||
|         Gfx::FontDatabase::the().for_each_font([&](auto& font) { |         Gfx::FontDatabase::the().for_each_typeface([&](auto& typeface) { | ||||||
|             if (m_fixed_width_only && !font.is_fixed_width()) |             if (m_fixed_width_only && !typeface.is_fixed_width()) | ||||||
|                 return; |                 return; | ||||||
|             if (font.family() == m_family.value() && !m_weights.contains_slow(font.weight())) { |             if (typeface.family() == m_family.value() && !m_weights.contains_slow(typeface.weight())) { | ||||||
|                 m_weights.append(font.weight()); |                 m_weights.append(typeface.weight()); | ||||||
|             } |             } | ||||||
|         }); |         }); | ||||||
|         quick_sort(m_weights); |         quick_sort(m_weights); | ||||||
|  | @ -144,11 +144,18 @@ FontPicker::FontPicker(Window* parent_window, const Gfx::Font* current_font, boo | ||||||
|     m_weight_list_view->on_selection = [this](auto& index) { |     m_weight_list_view->on_selection = [this](auto& index) { | ||||||
|         m_weight = index.data(ModelRole::Custom).to_i32(); |         m_weight = index.data(ModelRole::Custom).to_i32(); | ||||||
|         m_sizes.clear(); |         m_sizes.clear(); | ||||||
|         Gfx::FontDatabase::the().for_each_font([&](auto& font) { |         dbgln("Selected weight: {}", m_weight.value()); | ||||||
|             if (m_fixed_width_only && !font.is_fixed_width()) |         Gfx::FontDatabase::the().for_each_typeface([&](auto& typeface) { | ||||||
|  |             if (m_fixed_width_only && !typeface.is_fixed_width()) | ||||||
|                 return; |                 return; | ||||||
|             if (font.family() == m_family.value() && font.weight() == m_weight.value()) { |             if (typeface.family() == m_family.value() && (int)typeface.weight() == m_weight.value()) { | ||||||
|                 m_sizes.append(font.presentation_size()); |                 if (typeface.is_fixed_size()) { | ||||||
|  |                     typeface.for_each_fixed_size_font([&](auto& font) { | ||||||
|  |                         m_sizes.append(font.presentation_size()); | ||||||
|  |                     }); | ||||||
|  |                 } else { | ||||||
|  |                     m_sizes.append(12); | ||||||
|  |                 } | ||||||
|             } |             } | ||||||
|         }); |         }); | ||||||
|         quick_sort(m_sizes); |         quick_sort(m_sizes); | ||||||
|  | @ -206,14 +213,18 @@ void FontPicker::set_font(const Gfx::Font* font) | ||||||
|     m_weight = font->weight(); |     m_weight = font->weight(); | ||||||
|     m_size = font->presentation_size(); |     m_size = font->presentation_size(); | ||||||
| 
 | 
 | ||||||
|     size_t family_index = m_families.find_first_index(m_font->family()).value(); |     auto family_index = m_families.find_first_index(m_font->family()); | ||||||
|     m_family_list_view->set_cursor(m_family_list_view->model()->index(family_index), GUI::AbstractView::SelectionUpdate::Set); |     if (family_index.has_value()) | ||||||
|  |         m_family_list_view->set_cursor(m_family_list_view->model()->index(family_index.value()), GUI::AbstractView::SelectionUpdate::Set); | ||||||
| 
 | 
 | ||||||
|     size_t weight_index = m_weights.find_first_index(m_font->weight()).value(); |     auto weight_index = m_weights.find_first_index(m_font->weight()); | ||||||
|     m_weight_list_view->set_cursor(m_weight_list_view->model()->index(weight_index), GUI::AbstractView::SelectionUpdate::Set); |     if (weight_index.has_value()) { | ||||||
|  |         m_weight_list_view->set_cursor(m_weight_list_view->model()->index(weight_index.value()), GUI::AbstractView::SelectionUpdate::Set); | ||||||
|  |     } | ||||||
| 
 | 
 | ||||||
|     size_t size_index = m_sizes.find_first_index(m_font->presentation_size()).value(); |     auto size_index = m_sizes.find_first_index(m_font->presentation_size()); | ||||||
|     m_size_list_view->set_cursor(m_size_list_view->model()->index(size_index), GUI::AbstractView::SelectionUpdate::Set); |     if (size_index.has_value()) | ||||||
|  |         m_size_list_view->set_cursor(m_size_list_view->model()->index(size_index.value()), GUI::AbstractView::SelectionUpdate::Set); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void FontPicker::update_font() | void FontPicker::update_font() | ||||||
|  |  | ||||||
|  | @ -159,6 +159,7 @@ RefPtr<Gfx::Font> FontDatabase::get_by_name(const StringView& name) | ||||||
| 
 | 
 | ||||||
| RefPtr<Gfx::Font> FontDatabase::get(const String& family, unsigned size, unsigned weight) | RefPtr<Gfx::Font> FontDatabase::get(const String& family, unsigned size, unsigned weight) | ||||||
| { | { | ||||||
|  |     dbgln("FontDatabase: Request font {} {} {}", family, size, weight); | ||||||
|     for (auto typeface : m_private->typefaces) { |     for (auto typeface : m_private->typefaces) { | ||||||
|         if (typeface->family() == family && typeface->weight() == weight) |         if (typeface->family() == family && typeface->weight() == weight) | ||||||
|             return typeface->get_font(size); |             return typeface->get_font(size); | ||||||
|  |  | ||||||
|  | @ -38,6 +38,16 @@ unsigned Typeface::weight() const | ||||||
|     return m_ttf_font->weight(); |     return m_ttf_font->weight(); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | bool Typeface::is_fixed_width() const | ||||||
|  | { | ||||||
|  |     ASSERT(m_ttf_font || m_bitmap_fonts.size() > 0); | ||||||
|  | 
 | ||||||
|  |     if (is_fixed_size()) | ||||||
|  |         return m_bitmap_fonts[0]->is_fixed_width(); | ||||||
|  | 
 | ||||||
|  |     return m_ttf_font->is_fixed_width(); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| void Typeface::add_bitmap_font(RefPtr<BitmapFont> font) | void Typeface::add_bitmap_font(RefPtr<BitmapFont> font) | ||||||
| { | { | ||||||
|     m_bitmap_fonts.append(font); |     m_bitmap_fonts.append(font); | ||||||
|  |  | ||||||
|  | @ -48,6 +48,7 @@ public: | ||||||
|     String variant() const { return m_variant; } |     String variant() const { return m_variant; } | ||||||
|     unsigned weight() const; |     unsigned weight() const; | ||||||
| 
 | 
 | ||||||
|  |     bool is_fixed_width() const; | ||||||
|     bool is_fixed_size() const { return !m_bitmap_fonts.is_empty(); } |     bool is_fixed_size() const { return !m_bitmap_fonts.is_empty(); } | ||||||
|     void for_each_fixed_size_font(Function<void(const Font&)>) const; |     void for_each_fixed_size_font(Function<void(const Font&)>) const; | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -341,7 +341,7 @@ RefPtr<Font> Font::load_from_offset(ByteBuffer&& buffer, u32 offset) | ||||||
|     auto head = opt_head.value(); |     auto head = opt_head.value(); | ||||||
| 
 | 
 | ||||||
|     if (!opt_name_slice.has_value() || !(opt_name = Name::from_slice(opt_name_slice.value())).has_value()) { |     if (!opt_name_slice.has_value() || !(opt_name = Name::from_slice(opt_name_slice.value())).has_value()) { | ||||||
|         dbg() << "Could not load Name"; |         dbgln("Could not load Name"); | ||||||
|         return nullptr; |         return nullptr; | ||||||
|     } |     } | ||||||
|     auto name = opt_name.value(); |     auto name = opt_name.value(); | ||||||
|  |  | ||||||
|  | @ -77,6 +77,8 @@ public: | ||||||
|     u32 glyph_id_for_codepoint(u32 codepoint) const { return m_cmap.glyph_id_for_codepoint(codepoint); } |     u32 glyph_id_for_codepoint(u32 codepoint) const { return m_cmap.glyph_id_for_codepoint(codepoint); } | ||||||
|     String family() const; |     String family() const; | ||||||
|     String variant() const; |     String variant() const; | ||||||
|  |     u16 weight() const; | ||||||
|  |     bool is_fixed_width() const { return false; } /* TODO */ | ||||||
| 
 | 
 | ||||||
| private: | private: | ||||||
|     enum class Offsets { |     enum class Offsets { | ||||||
|  | @ -119,7 +121,7 @@ private: | ||||||
| 
 | 
 | ||||||
| class ScaledFont : public Gfx::Font { | class ScaledFont : public Gfx::Font { | ||||||
| public: | public: | ||||||
|     ScaledFont(RefPtr<Font> font, float point_width, float point_height, unsigned dpi_x = DEFAULT_DPI, unsigned dpi_y = DEFAULT_DPI) |     ScaledFont(RefPtr<TTF::Font> font, float point_width, float point_height, unsigned dpi_x = DEFAULT_DPI, unsigned dpi_y = DEFAULT_DPI) | ||||||
|         : m_font(font) |         : m_font(font) | ||||||
|     { |     { | ||||||
|         float units_per_em = m_font->units_per_em(); |         float units_per_em = m_font->units_per_em(); | ||||||
|  | @ -149,7 +151,7 @@ public: | ||||||
|     virtual int width(const Utf8View&) const override; |     virtual int width(const Utf8View&) const override; | ||||||
|     virtual int width(const Utf32View&) const override; |     virtual int width(const Utf32View&) const override; | ||||||
|     virtual String name() const override { return String::formatted("{} {}", family(), variant()); } |     virtual String name() const override { return String::formatted("{} {}", family(), variant()); } | ||||||
|     virtual bool is_fixed_width() const override { return false; }  /* TODO */ |     virtual bool is_fixed_width() const override { return m_font->is_fixed_width(); } | ||||||
|     virtual u8 glyph_spacing() const override { return m_x_scale; } /* TODO */ |     virtual u8 glyph_spacing() const override { return m_x_scale; } /* TODO */ | ||||||
|     virtual int glyph_count() const override { return m_font->glyph_count(); } |     virtual int glyph_count() const override { return m_font->glyph_count(); } | ||||||
|     virtual String family() const override { return m_font->family(); } |     virtual String family() const override { return m_font->family(); } | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Stephan Unverwerth
						Stephan Unverwerth