app_server: make FontFamily referenceable
FontStyle will be keeping the references, so the family will exist as long as there's a style pointing to it. Change-Id: I639f7914be924a84d5db5882c638a4dac665aa23 Reviewed-on: https://review.haiku-os.org/c/haiku/+/7634 Reviewed-by: Fredrik Holmqvist <fredrik.holmqvist@gmail.com> Reviewed-by: waddlesplash <waddlesplash@gmail.com> Reviewed-by: Adrien Destugues <pulkomandy@pulkomandy.tk> Tested-by: Commit checker robot <no-reply+buildbot@haiku-os.org>
This commit is contained in:
parent
0b8508801b
commit
7866929cf9
|
@ -62,24 +62,6 @@ FontFamily::FontFamily(const char *name, uint16 id)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*!
|
|
||||||
\brief Destructor
|
|
||||||
|
|
||||||
Deletes all attached styles. Note that a FontFamily must only be deleted
|
|
||||||
by the font manager.
|
|
||||||
*/
|
|
||||||
FontFamily::~FontFamily()
|
|
||||||
{
|
|
||||||
for (int32 i = fStyles.CountItems(); i-- > 0;) {
|
|
||||||
FontStyle* style = fStyles.RemoveItemAt(i);
|
|
||||||
|
|
||||||
// we remove us before deleting the style, so that the font manager
|
|
||||||
// is not contacted to remove the style from us
|
|
||||||
style->_SetFontFamily(NULL, -1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
\brief Returns the name of the family
|
\brief Returns the name of the family
|
||||||
\return The family's name
|
\return The family's name
|
||||||
|
|
|
@ -11,6 +11,7 @@
|
||||||
|
|
||||||
|
|
||||||
#include <ObjectList.h>
|
#include <ObjectList.h>
|
||||||
|
#include <Referenceable.h>
|
||||||
#include <String.h>
|
#include <String.h>
|
||||||
|
|
||||||
#include "FontStyle.h"
|
#include "FontStyle.h"
|
||||||
|
@ -23,10 +24,9 @@
|
||||||
FontFamily objects bring together many styles of the same face, such as
|
FontFamily objects bring together many styles of the same face, such as
|
||||||
Arial Roman, Arial Italic, Arial Bold, etc.
|
Arial Roman, Arial Italic, Arial Bold, etc.
|
||||||
*/
|
*/
|
||||||
class FontFamily {
|
class FontFamily : public BReferenceable {
|
||||||
public:
|
public:
|
||||||
FontFamily(const char* name, uint16 id);
|
FontFamily(const char* name, uint16 id);
|
||||||
virtual ~FontFamily();
|
|
||||||
|
|
||||||
const char* Name() const;
|
const char* Name() const;
|
||||||
|
|
||||||
|
|
|
@ -289,15 +289,8 @@ FontManager::RemoveStyle(FontStyle* style)
|
||||||
if (family == NULL)
|
if (family == NULL)
|
||||||
debugger("family is NULL!");
|
debugger("family is NULL!");
|
||||||
|
|
||||||
|
family->RemoveStyle(style);
|
||||||
fDelistedStyleHashTable.Remove(FontKey(family->ID(), style->ID()));
|
fDelistedStyleHashTable.Remove(FontKey(family->ID(), style->ID()));
|
||||||
int count = fDelistedFamilies.Get(family) - 1;
|
|
||||||
if (count == 0)
|
|
||||||
fDelistedFamilies.Remove(family);
|
|
||||||
else if (count > 0)
|
|
||||||
fDelistedFamilies.Put(family, count);
|
|
||||||
|
|
||||||
if (family->CountStyles() == 0 && !fDelistedFamilies.ContainsKey(family))
|
|
||||||
delete family;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -307,22 +300,20 @@ FontManager::_AddFont(FT_Face face, node_ref nodeRef, const char* path,
|
||||||
{
|
{
|
||||||
ASSERT(IsLocked());
|
ASSERT(IsLocked());
|
||||||
|
|
||||||
FontFamily* family = _FindFamily(face->family_name);
|
BReference<FontFamily> family(_FindFamily(face->family_name));
|
||||||
bool isNewFontFamily = family == NULL;
|
bool isNewFontFamily = !family.IsSet();
|
||||||
|
|
||||||
if (family != NULL && family->HasStyle(face->style_name)) {
|
if (family.IsSet() && family->HasStyle(face->style_name)) {
|
||||||
// prevent adding the same style twice
|
// prevent adding the same style twice
|
||||||
// (this indicates a problem with the installed fonts maybe?)
|
// (this indicates a problem with the installed fonts maybe?)
|
||||||
FT_Done_Face(face);
|
FT_Done_Face(face);
|
||||||
return B_NAME_IN_USE;
|
return B_NAME_IN_USE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (family == NULL) {
|
if (!family.IsSet()) {
|
||||||
family = new (std::nothrow) FontFamily(face->family_name, _NextID());
|
family.SetTo(new (std::nothrow) FontFamily(face->family_name, _NextID()), true);
|
||||||
|
|
||||||
if (family == NULL
|
if (!family.IsSet() || !fFamilies.BinaryInsert(family, compare_font_families)) {
|
||||||
|| !fFamilies.BinaryInsert(family, compare_font_families)) {
|
|
||||||
delete family;
|
|
||||||
FT_Done_Face(face);
|
FT_Done_Face(face);
|
||||||
return B_NO_MEMORY;
|
return B_NO_MEMORY;
|
||||||
}
|
}
|
||||||
|
@ -335,10 +326,8 @@ FontManager::_AddFont(FT_Face face, node_ref nodeRef, const char* path,
|
||||||
|
|
||||||
if (style == NULL || !family->AddStyle(style)) {
|
if (style == NULL || !family->AddStyle(style)) {
|
||||||
delete style;
|
delete style;
|
||||||
if (isNewFontFamily) {
|
if (isNewFontFamily)
|
||||||
fFamilies.RemoveItem(family);
|
fFamilies.RemoveItem(family);
|
||||||
delete family;
|
|
||||||
}
|
|
||||||
return B_NO_MEMORY;
|
return B_NO_MEMORY;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -362,7 +351,6 @@ FontManager::_RemoveFont(uint16 familyID, uint16 styleID)
|
||||||
if (style != NULL) {
|
if (style != NULL) {
|
||||||
fDelistedStyleHashTable.Put(key, style);
|
fDelistedStyleHashTable.Put(key, style);
|
||||||
FontFamily* family = style->Family();
|
FontFamily* family = style->Family();
|
||||||
fDelistedFamilies.Put(family, fDelistedFamilies.Get(family) + 1);
|
|
||||||
if (family->RemoveStyle(style) && family->CountStyles() == 0)
|
if (family->RemoveStyle(style) && family->CountStyles() == 0)
|
||||||
fFamilies.RemoveItem(family);
|
fFamilies.RemoveItem(family);
|
||||||
fStyleHashTable.Remove(key);
|
fStyleHashTable.Remove(key);
|
||||||
|
@ -374,20 +362,19 @@ FontManager::_RemoveFont(uint16 familyID, uint16 styleID)
|
||||||
void
|
void
|
||||||
FontManager::_RemoveAllFonts()
|
FontManager::_RemoveAllFonts()
|
||||||
{
|
{
|
||||||
for (int32 i = fFamilies.CountItems(); i-- > 0;) {
|
fFamilies.MakeEmpty();
|
||||||
FontFamily* family = fFamilies.RemoveItemAt(i);
|
|
||||||
fDelistedFamilies.Remove(family);
|
|
||||||
delete family;
|
|
||||||
}
|
|
||||||
|
|
||||||
HashMap<FontKey, FontStyle*>::Iterator it = fDelistedStyleHashTable.GetIterator();
|
// Disconnect the styles from their families before removing them; once we
|
||||||
while (it.HasNext()) {
|
// get to this point, we are in the dtor and don't want them to call back.
|
||||||
FontFamily* family = it.Next().value->Family();
|
|
||||||
fDelistedFamilies.Remove(family);
|
|
||||||
delete family;
|
|
||||||
}
|
|
||||||
|
|
||||||
fDelistedFamilies.Clear();
|
HashMap<FontKey, FontStyle*>::Iterator delisted = fDelistedStyleHashTable.GetIterator();
|
||||||
|
while (delisted.HasNext())
|
||||||
|
delisted.Next().value->_SetFontFamily(NULL, -1);
|
||||||
|
fDelistedStyleHashTable.Clear();
|
||||||
|
|
||||||
|
HashMap<FontKey, BReference<FontStyle> >::Iterator referenced = fStyleHashTable.GetIterator();
|
||||||
|
while (referenced.HasNext())
|
||||||
|
referenced.Next().value->_SetFontFamily(NULL, -1);
|
||||||
fStyleHashTable.Clear();
|
fStyleHashTable.Clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -102,8 +102,6 @@ private:
|
||||||
private:
|
private:
|
||||||
typedef BObjectList<FontFamily> FamilyList;
|
typedef BObjectList<FontFamily> FamilyList;
|
||||||
FamilyList fFamilies;
|
FamilyList fFamilies;
|
||||||
HashMap<HashKeyPointer<FontFamily*>, int>
|
|
||||||
fDelistedFamilies;
|
|
||||||
|
|
||||||
HashMap<FontKey, BReference<FontStyle> > fStyleHashTable;
|
HashMap<FontKey, BReference<FontStyle> > fStyleHashTable;
|
||||||
HashMap<FontKey, FontStyle*> fDelistedStyleHashTable;
|
HashMap<FontKey, FontStyle*> fDelistedStyleHashTable;
|
||||||
|
|
|
@ -96,7 +96,7 @@ FontStyle::FontStyle(node_ref& nodeRef, const char* path, FT_Face face,
|
||||||
FontStyle::~FontStyle()
|
FontStyle::~FontStyle()
|
||||||
{
|
{
|
||||||
// make sure the font server is ours
|
// make sure the font server is ours
|
||||||
if (fFamily != NULL && fFontManager->Lock()) {
|
if (fFamily.IsSet() && fFontManager->Lock()) {
|
||||||
fFontManager->RemoveStyle(this);
|
fFontManager->RemoveStyle(this);
|
||||||
fFontManager->Unlock();
|
fFontManager->Unlock();
|
||||||
}
|
}
|
||||||
|
@ -227,7 +227,10 @@ FontStyle::UpdateFace(FT_Face face)
|
||||||
void
|
void
|
||||||
FontStyle::_SetFontFamily(FontFamily* family, uint16 id)
|
FontStyle::_SetFontFamily(FontFamily* family, uint16 id)
|
||||||
{
|
{
|
||||||
fFamily = family;
|
if (fFamily.IsSet())
|
||||||
|
fFamily->RemoveStyle(this);
|
||||||
|
|
||||||
|
fFamily.SetTo(family);
|
||||||
fID = id;
|
fID = id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -144,6 +144,7 @@ class FontStyle : public BReferenceable {
|
||||||
|
|
||||||
private:
|
private:
|
||||||
friend class FontFamily;
|
friend class FontFamily;
|
||||||
|
friend class FontManager;
|
||||||
uint16 _TranslateStyleToFace(const char *name) const;
|
uint16 _TranslateStyleToFace(const char *name) const;
|
||||||
void _SetFontFamily(FontFamily* family, uint16 id);
|
void _SetFontFamily(FontFamily* family, uint16 id);
|
||||||
private:
|
private:
|
||||||
|
@ -152,7 +153,8 @@ class FontStyle : public BReferenceable {
|
||||||
BPath fPath;
|
BPath fPath;
|
||||||
node_ref fNodeRef;
|
node_ref fNodeRef;
|
||||||
|
|
||||||
FontFamily* fFamily;
|
BReference<FontFamily>
|
||||||
|
fFamily;
|
||||||
uint16 fID;
|
uint16 fID;
|
||||||
|
|
||||||
BRect fBounds;
|
BRect fBounds;
|
||||||
|
|
Loading…
Reference in New Issue