Added prototype #7 and test application to tree

git-svn-id: file:///srv/svn/repos/haiku/trunk/current@1863 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
DarkWyrm
2002-11-06 22:52:04 +00:00
parent 54b288ebda
commit fc8dfd798a
4 changed files with 633 additions and 0 deletions
+38
View File
@@ -0,0 +1,38 @@
#ifndef COLORSET_H_
#define COLORSET_H_
#include "RGBColor.h"
class ColorSet
{
public:
ColorSet(void);
ColorSet(const ColorSet &cs);
ColorSet & operator=(const ColorSet &cs);
void SetColors(const ColorSet &cs);
void PrintToStream(void);
RGBColor panel_background,
panel_text,
document_background,
document_text,
control_background,
control_text,
control_border,
control_highlight,
tooltip_background,
tooltip_text,
menu_background,
menu_selected_background,
menu_text,
menu_selected_text,
menu_separator_high,
menu_separator_low,
menu_triggers,
window_tab,
window_tab_text,
keyboard_navigation,
desktop;
};
#endif
+486
View File
@@ -0,0 +1,486 @@
#include <String.h>
#include <Directory.h>
#include <Entry.h>
#include <Path.h>
#include <File.h>
#include <Message.h>
#include <String.h>
#include "FontFamily.h"
#include "FontServer.h"
#include "ServerFont.h"
#include "ServerProtocol.h"
//#define DEBUG_FONTSERVER
//#define DEBUG_SCANDIR
#ifdef DEBUG_FONTSERVER
#include <stdio.h>
#else
#ifdef DEBUG_SCANDIR
#include <stdio.h>
#endif
#endif
FTC_Manager ftmanager;
FT_Library ftlib;
FontServer *fontserver;
static FT_Error face_requester(FTC_FaceID face_id, FT_Library library,
FT_Pointer request_data, FT_Face *aface)
{
CachedFace face = (CachedFace) face_id;
return FT_New_Face(ftlib,face->file_path.String(),face->face_index,aface);
}
FontServer::FontServer(void)
{
lock=create_sem(1,"fontserver_lock");
init=(FT_Init_FreeType(&ftlib)==0)?true:false;
/*
Fire up the font caching subsystem.
The three zeros tell FreeType to use the defaults, which are 2 faces,
4 face sizes, and a maximum of 200000 bytes. I will probably change
these numbers in the future to maximize performance for your "average"
application.
*/
if(FTC_Manager_New(ftlib,0,0,0,&face_requester,NULL,&ftmanager)!=0
&& init)
init=false;
families=new BList(0);
plain=NULL;
bold=NULL;
fixed=NULL;
#ifdef DEBUG_FONTSERVER
if(!init)
printf("Couldn't initialize FreeType library\n");
#endif
}
FontServer::~FontServer(void)
{
delete_sem(lock);
delete families;
FTC_Manager_Done(ftmanager);
FT_Done_FreeType(ftlib);
}
void FontServer::Lock(void)
{
acquire_sem(lock);
}
void FontServer::Unlock(void)
{
release_sem(lock);
}
int32 FontServer::CountFamilies(void)
{
if(init)
return families->CountItems();
return 0;
}
int32 FontServer::CountStyles(const char *family)
{
FontFamily *f=_FindFamily(family);
if(f)
{
return f->CountStyles();
}
return 0;
}
void FontServer::RemoveFamily(const char *family)
{
FontFamily *f=_FindFamily(family);
if(f)
{
families->RemoveItem(f);
delete f;
}
#ifdef DEBUG_FONTSERVER
else
printf("FontServer::RemoveFamily(): Couldn't remove %s\n",family);
#endif
}
FontFamily *FontServer::_FindFamily(const char *name)
{
if(!init)
return NULL;
int32 count=families->CountItems(), i;
FontFamily *family;
for(i=0; i<count; i++)
{
family=(FontFamily*)families->ItemAt(i);
if(strcmp(family->GetName(),name)==0)
return family;
}
//#ifdef DEBUG_FONTSERVER
//printf("FontServer::_FindFamily(): Couldn't find %s\n",name);
//#endif
return NULL;
}
status_t FontServer::ScanDirectory(const char *fontspath)
{
// This bad boy does all the real work. It loads each entry in the
// directory. If a valid font file, it adds both the family and the style.
// Both family and style are stored internally as BStrings. Once everything
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(%s)\n",fontspath);
#endif
BDirectory dir;
BEntry entry;
BPath path;
entry_ref ref;
status_t stat;
int32 refcount,i, validcount=0;
FT_Face face;
FT_Error error;
FT_CharMap charmap;
FontFamily *family;
// int32 familycount;
stat=dir.SetTo(fontspath);
if(stat!=B_OK)
{
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(): couldn't open path\n");
#endif
return stat;
}
refcount=dir.CountEntries();
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(): %ld entries\n",refcount);
#endif
for(i=0;i<refcount;i++)
{
if(dir.GetNextEntry(&entry)==B_ENTRY_NOT_FOUND)
{
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(): ran out of entries\n");
#endif
break;
}
stat=entry.GetPath(&path);
if(stat!=B_OK)
{
#ifdef DEBUG_SCANDIR
if(stat==B_NO_INIT)
printf("FontServer::ScanDirectory(): BEntry not initialized\n");
if(stat==B_BUSY)
printf("FontServer::ScanDirectory(): BEntry busy\n");
#endif
continue;
}
error=FT_New_Face(ftlib,path.Path(),0,&face);
if (error!=0)
{
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(): FreeType couldn't load %s\n", path.Path());
#endif
continue;
}
charmap=_GetSupportedCharmap(face);
if(!charmap)
{
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(): %s has no supported charmaps\n", path.Path());
#endif
FT_Done_Face(face);
continue;
}
face->charmap=charmap;
family=_FindFamily(face->family_name);
if(!family)
{
family=new FontFamily(face->family_name);
families->AddItem(family);
}
if(family->HasStyle(face->style_name))
{
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(): %s : %s already loaded\n", face->family_name,face->style_name);
#endif
FT_Done_Face(face);
continue;
}
// Has vertical metrics?
#ifdef DEBUG_SCANDIR
if(FT_HAS_VERTICAL(face))
printf("%s : %s has vertical metrics\n",face->family_name, face->style_name);
#endif
family->AddStyle(path.Path(),face);
validcount++;
#ifdef DEBUG_SCANDIR
printf( "FontServer::ScanDirectory: Added %s : %s\n", face->family_name, face->style_name);
if(face->num_fixed_sizes>0)
{
for(int32 j=0;j<face->num_fixed_sizes;++j)
printf( " Fixed size #%ld : %dx%d\n", j, face->available_sizes[j].width, face->available_sizes[j].height );
}
#endif
FT_Done_Face(face);
} // end for(i<refcount)
#ifdef DEBUG_SCANDIR
printf("Directory %s contains %ld supported fonts\n", fontspath, validcount);
#endif
dir.Unset();
// This step is in the AtheOS code, but I doubt it will be necessary here
// because of implementation differences between this and AtheOS.
// cull empty families from family list
/* familycount=families->CountItems();
for(i=0;i<familycount;i++)
{
family=(FontFamily*)families->ItemAt(i);
if(family)
{
if(family->CountStyles()<1)
{
#ifdef DEBUG_SCANDIR
printf("FontServer::ScanDirectory(): deleting empty family %s\n", family->GetName());
#endif
families->RemoveItem(family);
delete family;
}
}
}
*/
need_update=true;
return B_OK;
}
FT_CharMap FontServer::_GetSupportedCharmap(const FT_Face &face)
{
int32 i;
FT_CharMap charmap;
for(i=0; i< face->num_charmaps; i++)
{
charmap=face->charmaps[i];
switch(charmap->platform_id)
{
case 3:
{
// if Windows Symbol or Windows Unicode
if(charmap->encoding_id==0 || charmap->encoding_id==1)
return charmap;
break;
}
case 1:
{
// if Apple Unicode
if(charmap->encoding_id==0)
return charmap;
break;
}
case 0:
{
// if Apple Roman
if(charmap->encoding_id==0)
return charmap;
break;
}
default:
{
#ifdef DEBUG_SCANDIR
printf("Font %s:%s has unknown platform id %d\n",face->family_name,face->style_name, charmap->platform_id);
#endif
break;
}
}
}
return NULL;
}
/*
This saves all family names and styles to the file
/boot/home/config/app_server/fontlist as a flattened BMessage
This operation is not done very often because the access to disk adds a significant
performance hit.
The format for storage consists of two things: an array of strings with the name 'family'
and a number of small string arrays which have the name of the font family. These are
the style lists.
Additionally, any fonts which have bitmap strikes contained in them or any fonts which
are fixed-width are named in the arrays 'tuned' and 'fixed'
*/
void FontServer::SaveList(void)
{
#ifdef DEBUG_FONTSERVER
printf("FontServer::SaveList()\n");
#endif
int32 famcount=0, stycount=0,i=0,j=0;
FontFamily *fam;
FontStyle *sty;
BMessage fontmsg, familymsg('FONT');
BString famname, styname, extraname;
bool fixed,tuned;
famcount=families->CountItems();
for(i=0; i<famcount; i++)
{
fam=(FontFamily*)families->ItemAt(i);
fixed=false;
tuned=false;
if(!fam)
continue;
famname=fam->GetName();
// Add the family to the message
familymsg.AddString("name",famname);
stycount=fam->CountStyles();
for(j=0;j<stycount;j++)
{
styname.SetTo(fam->GetStyle(j));
if(styname.CountChars()>0)
{
// Add to list
familymsg.AddString("styles", styname);
// Check to see if it has prerendered strikes (has "tuned" fonts)
sty=fam->GetStyle(styname.String());
if(sty->HasTuned() && sty->IsScalable())
tuned=true;
// Check to see if it is fixed-width
if(sty->IsFixedWidth())
fixed=true;
}
}
if(tuned)
familymsg.AddBool("tuned",true);
if(fixed)
familymsg.AddBool("fixed",true);
fontmsg.AddMessage("family",&familymsg);
#ifdef DEBUG_FONTSERVER
familymsg.PrintToStream();
#endif
familymsg.MakeEmpty();
}
BFile file(SERVER_FONT_LIST,B_READ_WRITE | B_CREATE_FILE | B_ERASE_FILE);
if(file.InitCheck()==B_OK)
fontmsg.Flatten(&file);
#ifdef DEBUG_FONTSERVER
else
{
printf("FontServer::SaveList(): Couldn't open %s for write\n",SERVER_FONT_LIST);
}
#endif
}
FontStyle *FontServer::GetStyle(font_family family, font_style face)
{
FontFamily *ffam=_FindFamily(family);
if(ffam)
{
FontStyle *fsty=ffam->GetStyle(face);
return fsty;
}
return NULL;
}
ServerFont *FontServer::GetSystemPlain(void)
{
if(plain)
{
ServerFont *f=new ServerFont(*plain);
return f;
}
return NULL;
}
ServerFont *FontServer::GetSystemBold(void)
{
if(bold)
{
ServerFont *f=new ServerFont(*bold);
return f;
}
return NULL;
}
ServerFont *FontServer::GetSystemFixed(void)
{
if(fixed)
{
ServerFont *f=new ServerFont(*fixed);
return f;
}
return NULL;
}
bool FontServer::SetSystemPlain(const char *family, const char *style, float size)
{
FontFamily *fam=_FindFamily(family);
if(!fam)
return false;
FontStyle *sty=fam->GetStyle(style);
if(!sty)
return false;
if(plain)
delete plain;
plain=sty->Instantiate(size);
return true;
}
bool FontServer::SetSystemBold(const char *family, const char *style, float size)
{
FontFamily *fam=_FindFamily(family);
if(!fam)
return false;
FontStyle *sty=fam->GetStyle(style);
if(!sty)
return false;
if(bold)
delete bold;
bold=sty->Instantiate(size);
return true;
}
bool FontServer::SetSystemFixed(const char *family, const char *style, float size)
{
FontFamily *fam=_FindFamily(family);
if(!fam)
return false;
FontStyle *sty=fam->GetStyle(style);
if(!sty)
return false;
if(fixed)
delete fixed;
fixed=sty->Instantiate(size);
return true;
}
+100
View File
@@ -0,0 +1,100 @@
#ifndef _SCREENDRIVER_H_
#define _SCREENDRIVER_H_
#include <Application.h>
#include <WindowScreen.h>
#include <View.h>
#include <GraphicsCard.h>
#include <Message.h>
#include <OS.h>
#include <Locker.h>
#include <Region.h> // for clipping_rect definition
#include <Bitmap.h>
#include "DisplayDriver.h"
class VDWindow;
class ServerCursor;
class ServerBitmap;
class RGBColor;
class PortLink;
class FrameBuffer : public BWindowScreen
{
public:
FrameBuffer(const char *title, uint32 space, status_t *st,bool debug);
~FrameBuffer(void);
void ScreenConnected(bool connected);
void MessageReceived(BMessage *msg);
bool IsConnected(void) const { return is_connected; }
bool QuitRequested(void);
graphics_card_info gcinfo;
protected:
bool is_connected;
PortLink *serverlink;
BPoint mousepos;
int32 buttons;
};
class ScreenDriver : public DisplayDriver
{
public:
ScreenDriver(void);
~ScreenDriver(void);
bool Initialize(void);
void Shutdown(void);
// Settings functions
// virtual void CopyBits(BRect src, BRect dest);
virtual void DrawBitmap(ServerBitmap *bmp, BRect src, BRect dest);
// virtual void DrawChar(char c, BPoint pt);
// virtual void DrawPicture(SPicture *pic, BPoint pt);
// virtual void DrawString(const char *string, int32 length, BPoint pt, LayerData *d, escapement_delta *delta=NULL);
// virtual void FillArc(BRect r, float angle, float span, LayerData *d, int8 *pat);
// virtual void FillBezier(BPoint *pts, LayerData *d, int8 *pat);
virtual void FillEllipse(BRect r, LayerData *d, int8 *pat);
// virtual void FillPolygon(BPoint *ptlist, int32 numpts, BRect rect, LayerData *d, int8 *pat);
virtual void FillRect(BRect r, LayerData *d, int8 *pat);
virtual void FillRoundRect(BRect r, float xrad, float yrad, LayerData *d, int8 *pat);
// virtual void FillShape(SShape *sh, LayerData *d, int8 *pat);
virtual void FillTriangle(BPoint *pts, BRect r, LayerData *d, int8 *pat);
virtual void HideCursor(void);
virtual void MoveCursorTo(float x, float y);
virtual void InvertRect(BRect r);
virtual void ShowCursor(void);
virtual void ObscureCursor(void);
// virtual void SetCursor(ServerBitmap *cursor);
// virtual void StrokeArc(BRect r, float angle, float span, LayerData *d, int8 *pat);
// virtual void StrokeBezier(BPoint *pts, LayerData *d, int8 *pat);
virtual void StrokeEllipse(BRect r, LayerData *d, int8 *pat);
virtual void StrokeLine(BPoint start, BPoint end, LayerData *d, int8 *pat);
virtual void StrokePolygon(BPoint *ptlist, int32 numpts, BRect rect, LayerData *d, int8 *pat, bool is_closed=true);
virtual void StrokeRect(BRect r, LayerData *d, int8 *pat);
virtual void StrokeRoundRect(BRect r, float xrad, float yrad, LayerData *d, int8 *pat);
// virtual void StrokeShape(SShape *sh, LayerData *d, int8 *pat);
virtual void StrokeTriangle(BPoint *pts, BRect r, LayerData *d, int8 *pat);
// virtual void StrokeLineArray(BPoint *pts, int32 numlines, RGBColor *colors, LayerData *d);
virtual void SetMode(int32 mode);
// virtual bool DumpToFile(const char *path);
protected:
void BlitBitmap(ServerBitmap *sourcebmp, BRect sourcerect, BRect destrect);
void SetPixelPattern(int x, int y, uint8 *pattern, uint8 patternindex);
void Line(BPoint start, BPoint end, LayerData *d, int8 *pat);
void HLine(int32 x1, int32 x2, int32 y, RGBColor color);
void SetPixel(int x, int y, RGBColor col);
void SetPixel32(int x, int y, rgb_color col);
void SetPixel16(int x, int y, uint16 col);
void SetPixel8(int x, int y, uint8 col);
FrameBuffer *fbuffer;
int hide_cursor;
ServerBitmap *cursor, *under_cursor;
int32 drawmode;
BRect cursorframe, oldcursorframe;
};
#endif
+9
View File
@@ -0,0 +1,9 @@
#ifndef _SYSTEM_PALETTE_H_
#define _SYSTEM_PALETTE_H_
#include <GraphicsDefs.h>
void GenerateSystemPalette(rgb_color *palette);
extern rgb_color system_palette[];
#endif