Even more font stuff:
* the node monitor is now working - fonts can only be added yet, though * deleting a FontFamily did not work before, as the last style to be removed tried to delete the family again. * "luckily", FontFamilies and FontStyles were not deleted at all before. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@14824 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -10,11 +10,12 @@
|
|||||||
#define FONT_FAMILY_H_
|
#define FONT_FAMILY_H_
|
||||||
|
|
||||||
|
|
||||||
#include <String.h>
|
|
||||||
#include <Rect.h>
|
|
||||||
#include <Font.h>
|
#include <Font.h>
|
||||||
#include <ObjectList.h>
|
|
||||||
#include <Locker.h>
|
#include <Locker.h>
|
||||||
|
#include <Node.h>
|
||||||
|
#include <ObjectList.h>
|
||||||
|
#include <Rect.h>
|
||||||
|
#include <String.h>
|
||||||
|
|
||||||
#include <ft2build.h>
|
#include <ft2build.h>
|
||||||
#include FT_FREETYPE_H
|
#include FT_FREETYPE_H
|
||||||
@@ -22,6 +23,7 @@
|
|||||||
#include "HashTable.h"
|
#include "HashTable.h"
|
||||||
|
|
||||||
|
|
||||||
|
struct node_ref;
|
||||||
class FontFamily;
|
class FontFamily;
|
||||||
class ServerFont;
|
class ServerFont;
|
||||||
|
|
||||||
@@ -66,12 +68,14 @@ class FontKey : public Hashable {
|
|||||||
*/
|
*/
|
||||||
class FontStyle : public SharedObject, public Hashable, public BLocker {
|
class FontStyle : public SharedObject, public Hashable, public BLocker {
|
||||||
public:
|
public:
|
||||||
FontStyle(const char* path, FT_Face face);
|
FontStyle(node_ref& nodeRef, const char* path, FT_Face face);
|
||||||
virtual ~FontStyle();
|
virtual ~FontStyle();
|
||||||
|
|
||||||
virtual uint32 Hash() const;
|
virtual uint32 Hash() const;
|
||||||
virtual bool CompareTo(Hashable& other) const;
|
virtual bool CompareTo(Hashable& other) const;
|
||||||
|
|
||||||
|
const node_ref& NodeRef() const { return fNodeRef; }
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
\fn bool FontStyle::IsFixedWidth(void)
|
\fn bool FontStyle::IsFixedWidth(void)
|
||||||
\brief Determines whether the font's character width is fixed
|
\brief Determines whether the font's character width is fixed
|
||||||
@@ -159,6 +163,7 @@ class FontStyle : public SharedObject, public Hashable, public BLocker {
|
|||||||
FT_Face fFreeTypeFace;
|
FT_Face fFreeTypeFace;
|
||||||
BString fName;
|
BString fName;
|
||||||
BString fPath;
|
BString fPath;
|
||||||
|
node_ref fNodeRef;
|
||||||
|
|
||||||
FontFamily* fFamily;
|
FontFamily* fFamily;
|
||||||
uint16 fID;
|
uint16 fID;
|
||||||
@@ -184,8 +189,8 @@ class FontFamily {
|
|||||||
const char* Name() const;
|
const char* Name() const;
|
||||||
|
|
||||||
bool AddStyle(FontStyle* style);
|
bool AddStyle(FontStyle* style);
|
||||||
bool RemoveStyle(const char* style);
|
bool RemoveStyle(const char* style, bool deleteSelfIfEmpty = true);
|
||||||
bool RemoveStyle(FontStyle* style);
|
bool RemoveStyle(FontStyle* style, bool deleteSelfIfEmpty = true);
|
||||||
|
|
||||||
FontStyle* GetStyle(const char* style) const;
|
FontStyle* GetStyle(const char* style) const;
|
||||||
FontStyle* GetStyleMatchingFace(uint16 face) const;
|
FontStyle* GetStyleMatchingFace(uint16 face) const;
|
||||||
|
|||||||
@@ -73,6 +73,8 @@ class FontManager : public BLooper {
|
|||||||
uint16 fallbackFace);
|
uint16 fallbackFace);
|
||||||
status_t _SetDefaultFonts();
|
status_t _SetDefaultFonts();
|
||||||
void _AddSystemPaths();
|
void _AddSystemPaths();
|
||||||
|
font_directory* _FindDirectory(node_ref& nodeRef);
|
||||||
|
void _RemoveDirectory(font_directory* directory);
|
||||||
status_t _AddPath(const char* path);
|
status_t _AddPath(const char* path);
|
||||||
status_t _AddPath(BEntry& entry, font_directory** _newDirectory = NULL);
|
status_t _AddPath(BEntry& entry, font_directory** _newDirectory = NULL);
|
||||||
|
|
||||||
@@ -82,7 +84,7 @@ class FontManager : public BLooper {
|
|||||||
void _ScanFontsIfNecessary();
|
void _ScanFontsIfNecessary();
|
||||||
void _ScanFonts();
|
void _ScanFonts();
|
||||||
status_t _ScanFontDirectory(font_directory& directory);
|
status_t _ScanFontDirectory(font_directory& directory);
|
||||||
status_t _AddFont(BPath& path);
|
status_t _AddFont(font_directory& directory, BEntry& entry);
|
||||||
|
|
||||||
FT_CharMap _GetSupportedCharmap(const FT_Face &face);
|
FT_CharMap _GetSupportedCharmap(const FT_Face &face);
|
||||||
|
|
||||||
|
|||||||
@@ -27,11 +27,12 @@ const uint32 kInvalidFamilyFlags = ~0UL;
|
|||||||
\param filepath path to a font file
|
\param filepath path to a font file
|
||||||
\param face FreeType handle for the font file after it is loaded - it will be kept open until the FontStyle is destroied
|
\param face FreeType handle for the font file after it is loaded - it will be kept open until the FontStyle is destroied
|
||||||
*/
|
*/
|
||||||
FontStyle::FontStyle(const char *path, FT_Face face)
|
FontStyle::FontStyle(node_ref& nodeRef, const char* path, FT_Face face)
|
||||||
: BLocker(BString("FontStyle_").Append(face->style_name).String()),
|
: BLocker(BString("FontStyle_").Append(face->style_name).String()),
|
||||||
fFreeTypeFace(face),
|
fFreeTypeFace(face),
|
||||||
fName(face->style_name),
|
fName(face->style_name),
|
||||||
fPath(path),
|
fPath(path),
|
||||||
|
fNodeRef(nodeRef),
|
||||||
fFamily(NULL),
|
fFamily(NULL),
|
||||||
fID(0),
|
fID(0),
|
||||||
fBounds(0, 0, 0, 0),
|
fBounds(0, 0, 0, 0),
|
||||||
@@ -55,7 +56,7 @@ FontStyle::~FontStyle()
|
|||||||
{
|
{
|
||||||
// make sure the font server is ours
|
// make sure the font server is ours
|
||||||
if (fFamily != NULL && gFontManager->Lock()) {
|
if (fFamily != NULL && gFontManager->Lock()) {
|
||||||
fFamily->RemoveStyle(this);
|
fFamily->RemoveStyle(this, false);
|
||||||
gFontManager->Unlock();
|
gFontManager->Unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -231,6 +232,7 @@ FontFamily::FontFamily(const char *name, uint16 id)
|
|||||||
// make sure this family can be found using the Be API
|
// make sure this family can be found using the Be API
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
\brief Destructor
|
\brief Destructor
|
||||||
|
|
||||||
@@ -240,8 +242,8 @@ FontFamily::FontFamily(const char *name, uint16 id)
|
|||||||
*/
|
*/
|
||||||
FontFamily::~FontFamily()
|
FontFamily::~FontFamily()
|
||||||
{
|
{
|
||||||
int32 count = fStyles.CountItems();
|
// styles are removing itself when deleted
|
||||||
for (int32 i = 0; i < count; i++)
|
for (int32 i = fStyles.CountItems(); i-- > 0;)
|
||||||
delete fStyles.ItemAt(i);
|
delete fStyles.ItemAt(i);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -286,11 +288,11 @@ FontFamily::AddStyle(FontStyle *style)
|
|||||||
|
|
||||||
|
|
||||||
bool
|
bool
|
||||||
FontFamily::RemoveStyle(const char* styleName)
|
FontFamily::RemoveStyle(const char* styleName, bool deleteSelfIfEmpty)
|
||||||
{
|
{
|
||||||
FontStyle *style = GetStyle(styleName);
|
FontStyle *style = GetStyle(styleName);
|
||||||
if (style != NULL)
|
if (style != NULL)
|
||||||
return RemoveStyle(style);
|
return RemoveStyle(style, deleteSelfIfEmpty);
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -306,7 +308,7 @@ FontFamily::RemoveStyle(const char* styleName)
|
|||||||
\param style The style to be removed from the family
|
\param style The style to be removed from the family
|
||||||
*/
|
*/
|
||||||
bool
|
bool
|
||||||
FontFamily::RemoveStyle(FontStyle* style)
|
FontFamily::RemoveStyle(FontStyle* style, bool deleteSelfIfEmpty)
|
||||||
{
|
{
|
||||||
if (!gFontManager->IsLocked()) {
|
if (!gFontManager->IsLocked()) {
|
||||||
debugger("FontFamily::RemoveStyle() called without having the font manager locked!");
|
debugger("FontFamily::RemoveStyle() called without having the font manager locked!");
|
||||||
@@ -319,7 +321,9 @@ FontFamily::RemoveStyle(FontStyle* style)
|
|||||||
// force a refresh if a request for font flags is needed
|
// force a refresh if a request for font flags is needed
|
||||||
fFlags = kInvalidFamilyFlags;
|
fFlags = kInvalidFamilyFlags;
|
||||||
|
|
||||||
if (CountStyles() == 0)
|
style->_SetFontFamily(NULL, -1);
|
||||||
|
|
||||||
|
if (deleteSelfIfEmpty && CountStyles() == 0)
|
||||||
delete this;
|
delete this;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
+231
-29
@@ -27,8 +27,16 @@
|
|||||||
|
|
||||||
#include <new>
|
#include <new>
|
||||||
|
|
||||||
//#define PRINT_FONT_LIST
|
|
||||||
|
|
||||||
|
//#define TRACE_WATCHING
|
||||||
|
#ifdef TRACE_WATCHING
|
||||||
|
# define WTRACE(x) printf x
|
||||||
|
#else
|
||||||
|
# define WTRACE(x) ;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
// TODO: needs some more work for multi-user support
|
||||||
|
|
||||||
static FTC_Manager ftmanager;
|
static FTC_Manager ftmanager;
|
||||||
FT_Library gFreeTypeLibrary;
|
FT_Library gFreeTypeLibrary;
|
||||||
@@ -42,21 +50,53 @@ struct FontManager::font_directory {
|
|||||||
BObjectList<FontStyle> styles;
|
BObjectList<FontStyle> styles;
|
||||||
|
|
||||||
bool AlreadyScanned() const { return revision != 0; }
|
bool AlreadyScanned() const { return revision != 0; }
|
||||||
|
FontStyle* FindStyle(const node_ref& nodeRef) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct FontManager::font_mapping {
|
struct FontManager::font_mapping {
|
||||||
BString family;
|
BString family;
|
||||||
BString style;
|
BString style;
|
||||||
BPath path;
|
entry_ref ref;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
FontStyle*
|
||||||
|
FontManager::font_directory::FindStyle(const node_ref& nodeRef) const
|
||||||
|
{
|
||||||
|
for (int32 i = styles.CountItems(); i-- > 0;) {
|
||||||
|
FontStyle* style = styles.ItemAt(i);
|
||||||
|
|
||||||
|
if (nodeRef == style->NodeRef())
|
||||||
|
return style;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static status_t
|
||||||
|
set_entry(node_ref& nodeRef, const char* name, BEntry& entry)
|
||||||
|
{
|
||||||
|
entry_ref ref;
|
||||||
|
ref.device = nodeRef.device;
|
||||||
|
ref.directory = nodeRef.node;
|
||||||
|
|
||||||
|
status_t status = ref.set_name(name);
|
||||||
|
if (status != B_OK)
|
||||||
|
return status;
|
||||||
|
|
||||||
|
return entry.SetTo(&ref);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// #pragma mark -
|
// #pragma mark -
|
||||||
|
|
||||||
|
|
||||||
//! Does basic set up so that directories can be scanned
|
//! Does basic set up so that directories can be scanned
|
||||||
FontManager::FontManager()
|
FontManager::FontManager()
|
||||||
: BLooper("Font Manager"),
|
: BLooper("Font Manager"),
|
||||||
|
fDirectories(10, true),
|
||||||
|
fMappings(10, true),
|
||||||
fFamilies(20),
|
fFamilies(20),
|
||||||
fScanned(false),
|
fScanned(false),
|
||||||
fNextID(0)
|
fNextID(0)
|
||||||
@@ -85,12 +125,14 @@ FontManager::FontManager()
|
|||||||
//! Frees items allocated in the constructor and shuts down FreeType
|
//! Frees items allocated in the constructor and shuts down FreeType
|
||||||
FontManager::~FontManager()
|
FontManager::~FontManager()
|
||||||
{
|
{
|
||||||
|
// free families before we're done with FreeType
|
||||||
|
|
||||||
|
for (int32 i = fFamilies.CountItems(); i-- > 0;) {
|
||||||
|
delete fFamilies.ItemAt(i);
|
||||||
|
}
|
||||||
|
|
||||||
FTC_Manager_Done(ftmanager);
|
FTC_Manager_Done(ftmanager);
|
||||||
FT_Done_FreeType(gFreeTypeLibrary);
|
FT_Done_FreeType(gFreeTypeLibrary);
|
||||||
|
|
||||||
// we need to make sure the hash table doesn't delete the font styles;
|
|
||||||
// that's already done by the lists
|
|
||||||
fStyleHashTable.MakeEmpty(false);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -99,8 +141,118 @@ FontManager::MessageReceived(BMessage* message)
|
|||||||
{
|
{
|
||||||
switch (message->what) {
|
switch (message->what) {
|
||||||
case B_NODE_MONITOR:
|
case B_NODE_MONITOR:
|
||||||
// TODO: monitor fonts and update font_directories
|
{
|
||||||
|
// TODO: support removing fonts!
|
||||||
|
|
||||||
|
int32 opcode;
|
||||||
|
if (message->FindInt32("opcode", &opcode) != B_OK)
|
||||||
|
return;
|
||||||
|
|
||||||
|
switch (opcode) {
|
||||||
|
case B_ENTRY_CREATED:
|
||||||
|
{
|
||||||
|
const char* name;
|
||||||
|
node_ref nodeRef;
|
||||||
|
if (message->FindInt32("device", &nodeRef.device) != B_OK
|
||||||
|
|| message->FindInt64("directory", &nodeRef.node) != B_OK
|
||||||
|
|| message->FindString("name", &name) != B_OK)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
BEntry entry;
|
||||||
|
if (set_entry(nodeRef, name, entry) != B_OK)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (entry.IsDirectory()) {
|
||||||
|
// a new directory to watch for us
|
||||||
|
_AddPath(entry);
|
||||||
|
} else {
|
||||||
|
// a new font
|
||||||
|
font_directory* directory = _FindDirectory(nodeRef);
|
||||||
|
if (directory == NULL) {
|
||||||
|
// unknown directory? how come?
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
_AddFont(*directory, entry);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case B_ENTRY_MOVED:
|
||||||
|
{
|
||||||
|
// has the entry been moved into a monitored directory or has
|
||||||
|
// it been removed from one?
|
||||||
|
const char* name;
|
||||||
|
node_ref nodeRef;
|
||||||
|
uint64 fromNode;
|
||||||
|
uint64 node;
|
||||||
|
if (message->FindInt32("device", &nodeRef.device) != B_OK
|
||||||
|
|| message->FindInt64("to directory", &nodeRef.node) != B_OK
|
||||||
|
|| message->FindInt64("from directory", (int64 *)&fromNode) != B_OK
|
||||||
|
|| message->FindInt64("node", (int64 *)&node) != B_OK
|
||||||
|
|| message->FindString("name", &name) != B_OK)
|
||||||
|
break;
|
||||||
|
|
||||||
|
font_directory* directory = _FindDirectory(nodeRef);
|
||||||
|
|
||||||
|
BEntry entry;
|
||||||
|
if (set_entry(nodeRef, name, entry) != B_OK)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (directory != NULL) {
|
||||||
|
// something has been added to our watched font directories
|
||||||
|
if (entry.IsDirectory()) {
|
||||||
|
// there is a new directory to watch for us
|
||||||
|
_AddPath(entry);
|
||||||
|
} else {
|
||||||
|
// test, if the source directory is one of ours as well
|
||||||
|
nodeRef.node = fromNode;
|
||||||
|
font_directory* fromDirectory = _FindDirectory(nodeRef);
|
||||||
|
if (fromDirectory != NULL) {
|
||||||
|
// find style in source and move it to the target
|
||||||
|
nodeRef.node = node;
|
||||||
|
FontStyle* style = fromDirectory->FindStyle(nodeRef);
|
||||||
|
if (style != NULL) {
|
||||||
|
fromDirectory->styles.RemoveItem(style, false);
|
||||||
|
directory->styles.AddItem(style);
|
||||||
|
}
|
||||||
|
WTRACE(("font moved"));
|
||||||
|
} else {
|
||||||
|
WTRACE(("font added: %s\n", name));
|
||||||
|
_AddFont(*directory, entry);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// and entry has been removed from our font directories
|
||||||
|
if (entry.IsDirectory()) {
|
||||||
|
if (entry.GetNodeRef(&nodeRef) == B_OK
|
||||||
|
&& (directory = _FindDirectory(nodeRef)) != NULL)
|
||||||
|
_RemoveDirectory(directory);
|
||||||
|
} else
|
||||||
|
WTRACE(("font removed: %s\n", name));
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case B_ENTRY_REMOVED:
|
||||||
|
{
|
||||||
|
node_ref nodeRef;
|
||||||
|
if (message->FindInt32("device", &nodeRef.device) != B_OK
|
||||||
|
|| message->FindInt64("node", &nodeRef.node) != B_OK)
|
||||||
|
break;
|
||||||
|
|
||||||
|
font_directory* directory = _FindDirectory(nodeRef);
|
||||||
|
if (directory != NULL) {
|
||||||
|
// the directory has been removed, so we remove it as well
|
||||||
|
_RemoveDirectory(directory);
|
||||||
|
} else {
|
||||||
|
// a font was removed?
|
||||||
|
WTRACE(("removed a font?"));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -203,12 +355,12 @@ void
|
|||||||
FontManager::_AddSystemPaths()
|
FontManager::_AddSystemPaths()
|
||||||
{
|
{
|
||||||
BPath path;
|
BPath path;
|
||||||
if (find_directory(B_BEOS_FONTS_DIRECTORY, &path) == B_OK)
|
if (find_directory(B_BEOS_FONTS_DIRECTORY, &path, true) == B_OK)
|
||||||
_AddPath(path.Path());
|
_AddPath(path.Path());
|
||||||
|
|
||||||
// We don't scan these in test mode to help shave off some startup time
|
// We don't scan these in test mode to help shave off some startup time
|
||||||
#if !TEST_MODE
|
#if !TEST_MODE
|
||||||
if (find_directory(B_COMMON_FONTS_DIRECTORY, &path) == B_OK)
|
if (find_directory(B_COMMON_FONTS_DIRECTORY, &path, true) == B_OK)
|
||||||
_AddPath(path.Path());
|
_AddPath(path.Path());
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@@ -246,8 +398,18 @@ FontManager::_ScanFonts()
|
|||||||
\brief Adds the FontFamily/FontStyle that is represented by this path.
|
\brief Adds the FontFamily/FontStyle that is represented by this path.
|
||||||
*/
|
*/
|
||||||
status_t
|
status_t
|
||||||
FontManager::_AddFont(BPath &path)
|
FontManager::_AddFont(font_directory& directory, BEntry& entry)
|
||||||
{
|
{
|
||||||
|
node_ref nodeRef;
|
||||||
|
status_t status = entry.GetNodeRef(&nodeRef);
|
||||||
|
if (status < B_OK)
|
||||||
|
return status;
|
||||||
|
|
||||||
|
BPath path;
|
||||||
|
status = entry.GetPath(&path);
|
||||||
|
if (status < B_OK)
|
||||||
|
return status;
|
||||||
|
|
||||||
FT_Face face;
|
FT_Face face;
|
||||||
FT_Error error = FT_New_Face(gFreeTypeLibrary, path.Path(), 0, &face);
|
FT_Error error = FT_New_Face(gFreeTypeLibrary, path.Path(), 0, &face);
|
||||||
if (error != 0)
|
if (error != 0)
|
||||||
@@ -271,20 +433,51 @@ FontManager::_AddFont(BPath &path)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef PRINT_FONT_LIST
|
WTRACE(("\tadd style: %s, %s\n", face->family_name, face->style_name));
|
||||||
printf("\tFont Style: %s, %s\n", face->family_name, face->style_name);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// the FontStyle takes over ownership of the FT_Face object
|
// the FontStyle takes over ownership of the FT_Face object
|
||||||
FontStyle *style = new FontStyle(path.Path(), face);
|
FontStyle *style = new FontStyle(nodeRef, path.Path(), face);
|
||||||
if (!family->AddStyle(style))
|
if (!family->AddStyle(style))
|
||||||
delete style;
|
delete style;
|
||||||
|
|
||||||
|
directory.styles.AddItem(style);
|
||||||
fStyleHashTable.AddItem(style);
|
fStyleHashTable.AddItem(style);
|
||||||
|
|
||||||
|
if (directory.AlreadyScanned())
|
||||||
|
directory.revision++;
|
||||||
|
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
FontManager::font_directory*
|
||||||
|
FontManager::_FindDirectory(node_ref& nodeRef)
|
||||||
|
{
|
||||||
|
for (int32 i = fDirectories.CountItems(); i-- > 0;) {
|
||||||
|
font_directory* directory = fDirectories.ItemAt(i);
|
||||||
|
|
||||||
|
if (directory->directory == nodeRef)
|
||||||
|
return directory;
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
FontManager::_RemoveDirectory(font_directory* directory)
|
||||||
|
{
|
||||||
|
WTRACE(("FontManager: Remove directory (%Ld)!\n", directory->directory.node));
|
||||||
|
|
||||||
|
fDirectories.RemoveItem(directory, false);
|
||||||
|
|
||||||
|
// TODO: remove styles from this directory!
|
||||||
|
|
||||||
|
watch_node(&directory->directory, B_STOP_WATCHING, this);
|
||||||
|
delete directory;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
FontManager::_AddPath(const char* path)
|
FontManager::_AddPath(const char* path)
|
||||||
{
|
{
|
||||||
@@ -307,19 +500,15 @@ FontManager::_AddPath(BEntry& entry, font_directory** _newDirectory)
|
|||||||
|
|
||||||
// check if we are already know this directory
|
// check if we are already know this directory
|
||||||
|
|
||||||
for (int32 i = fDirectories.CountItems(); i-- > 0;) {
|
font_directory* directory = _FindDirectory(nodeRef);
|
||||||
font_directory* directory = fDirectories.ItemAt(i);
|
if (directory != NULL) {
|
||||||
|
*_newDirectory = directory;
|
||||||
if (directory->directory == nodeRef) {
|
|
||||||
if (_newDirectory)
|
|
||||||
*_newDirectory = NULL;
|
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// it's a new one, so let's add it
|
// it's a new one, so let's add it
|
||||||
|
|
||||||
font_directory* directory = new (nothrow) font_directory;
|
directory = new (nothrow) font_directory;
|
||||||
if (directory == NULL)
|
if (directory == NULL)
|
||||||
return B_NO_MEMORY;
|
return B_NO_MEMORY;
|
||||||
|
|
||||||
@@ -341,6 +530,9 @@ FontManager::_AddPath(BEntry& entry, font_directory** _newDirectory)
|
|||||||
// it's not a critical error
|
// it's not a critical error
|
||||||
printf("could not watch directory %ld:%Ld\n", nodeRef.device, nodeRef.node);
|
printf("could not watch directory %ld:%Ld\n", nodeRef.device, nodeRef.node);
|
||||||
// TODO: should go into syslog()
|
// TODO: should go into syslog()
|
||||||
|
} else {
|
||||||
|
BPath path(&entry);
|
||||||
|
WTRACE(("FontManager: now watching: %s\n", path.Path()));
|
||||||
}
|
}
|
||||||
|
|
||||||
fDirectories.AddItem(directory);
|
fDirectories.AddItem(directory);
|
||||||
@@ -379,11 +571,6 @@ FontManager::_ScanFontDirectory(font_directory& fontDirectory)
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
BPath path;
|
|
||||||
status = entry.GetPath(&path);
|
|
||||||
if (status < B_OK)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
// TODO: Commenting this out makes my "Unicode glyph lookup"
|
// TODO: Commenting this out makes my "Unicode glyph lookup"
|
||||||
// work with our default fonts. The real fix is to select the
|
// work with our default fonts. The real fix is to select the
|
||||||
// Unicode char map (if supported), and/or adjust the
|
// Unicode char map (if supported), and/or adjust the
|
||||||
@@ -400,7 +587,7 @@ FontManager::_ScanFontDirectory(font_directory& fontDirectory)
|
|||||||
face->charmap = charmap;
|
face->charmap = charmap;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
_AddFont(path);
|
_AddFont(fontDirectory, entry);
|
||||||
// takes over ownership of the FT_Face object
|
// takes over ownership of the FT_Face object
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -552,7 +739,22 @@ FontManager::GetFamily(const char* name)
|
|||||||
font_mapping* mapping = fMappings.ItemAt(i);
|
font_mapping* mapping = fMappings.ItemAt(i);
|
||||||
|
|
||||||
if (mapping->family == name) {
|
if (mapping->family == name) {
|
||||||
if (_AddFont(mapping->path) == B_OK)
|
BEntry entry(&mapping->ref);
|
||||||
|
if (entry.InitCheck() != B_OK)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
// find parent directory
|
||||||
|
|
||||||
|
node_ref nodeRef;
|
||||||
|
nodeRef.device = mapping->ref.device;
|
||||||
|
nodeRef.node = mapping->ref.directory;
|
||||||
|
font_directory* directory = _FindDirectory(nodeRef);
|
||||||
|
if (directory == NULL) {
|
||||||
|
// unknown directory, maybe this is a user font
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_AddFont(*directory, entry) == B_OK)
|
||||||
return _FindFamily(name);
|
return _FindFamily(name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user