When I added my BuyNow screen saver to the image and ran it, the app_server

crashed. Turns out a call I use, BFont.GetBoundingBoxesForStrings was not 
implemented, and worse, there was bug in how the ServerApp read the parameters
from the link. This was easy to fix to stop app_server from crashing, but it 
took me a while to figure out how to implement GetBoundingBoxesForStrings.

Anyhow I implemented an initial version which works fairly well for now. I
don't think the width is quite right, but it seems to match StringWidth(), so
I guess it is good enough for now.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@21652 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Ryan Leavengood
2007-07-19 02:06:32 +00:00
parent 62c65a7fb2
commit 5f43b49ba0
2 changed files with 31 additions and 8 deletions
+3 -5
View File
@@ -1401,8 +1401,7 @@ ServerApp::_DispatchMessage(int32 code, BPrivate::LinkReceiver& link)
int32 lengthArray[numStrings];
char *stringArray[numStrings];
for (int32 i = 0; i < numStrings; i++) {
// TODO: who allocates the strings?!? If the link does it then we are leaking
// everywhere else!!
// This version of ReadString allocates the strings, we free them below
link.ReadString(&stringArray[i], (size_t *)&lengthArray[i]);
}
@@ -1982,9 +1981,9 @@ ServerApp::_DispatchMessage(int32 code, BPrivate::LinkReceiver& link)
char *stringArray[numStrings];
int32 lengthArray[numStrings];
for(int32 i=0; i<numStrings; i++) {
link.Read<int32>(&lengthArray[i]);
// This version of ReadString allocates the strings, we free them below
link.ReadString(&stringArray[i], (size_t *)&lengthArray[i]);
link.Read<escapement_delta>(&deltaArray[i]);
link.ReadString(&stringArray[i]);
}
BRect rectArray[numStrings];
@@ -1999,7 +1998,6 @@ ServerApp::_DispatchMessage(int32 code, BPrivate::LinkReceiver& link)
font.SetSpacing(spacing);
font.SetFlags(flags);
// TODO implement for real
if (font.GetBoundingBoxesForStrings(stringArray, lengthArray,
numStrings, rectArray, mode, deltaArray) == B_OK) {
fLink.StartMessage(B_OK);
+28 -3
View File
@@ -24,6 +24,8 @@
#include <String.h>
#include <UTF8.h>
#include <stdio.h>
#include <string.h>
// functions needed to convert a freetype vector graphics to a BShape
inline BPoint
@@ -496,6 +498,7 @@ ServerFont::GetBoundingBoxesAsString(const char charArray[], int32 numChars,
BRect rectArray[], bool stringEscapement, font_metric_mode mode,
escapement_delta delta)
{
// TODO: The mode is never used
if (!charArray || numChars <= 0 || !rectArray)
return B_BAD_DATA;
@@ -519,12 +522,12 @@ ServerFont::GetBoundingBoxesAsString(const char charArray[], int32 numChars,
+ face->glyph->metrics.horiAdvance / 64.0;
}
rectArray[i].left += float(face->glyph->metrics.horiBearingX) /64.0;
rectArray[i].left += float(face->glyph->metrics.horiBearingX) / 64.0;
rectArray[i].right += float(face->glyph->metrics.horiBearingX
+ face->glyph->metrics.width) / 64.0;
rectArray[i].top = -float(face->glyph->metrics.horiBearingY) / 64.0;
rectArray[i].bottom = float(face->glyph->metrics.height
- face->glyph->metrics.horiBearingY) /64.0;
- face->glyph->metrics.horiBearingY) / 64.0;
}
PutTransformedFace(face);
@@ -536,6 +539,7 @@ status_t
ServerFont::GetBoundingBoxesForStrings(char *charArray[], int32 lengthArray[],
int32 numStrings, BRect rectArray[], font_metric_mode mode, escapement_delta deltaArray[])
{
// TODO: The mode is never used
if (!charArray || !lengthArray|| numStrings <= 0 || !rectArray || !deltaArray)
return B_BAD_DATA;
@@ -544,7 +548,28 @@ ServerFont::GetBoundingBoxesForStrings(char *charArray[], int32 lengthArray[],
return B_ERROR;
for (int32 i = 0; i < numStrings; i++) {
// TODO: ...
int32 numChars = lengthArray[i];
const char *string = charArray[i];
escapement_delta delta = deltaArray[i];
rectArray[i].left = 0.0;
for (int32 j = 0; j < numChars; j++) {
uint32 charCode = UTF8ToCharCode(&string);
FT_Load_Char(face, charCode, FT_LOAD_NO_BITMAP);
// TODO: In my testing the width doesn't seem quite right (a
// little too long), though I need to do more comparisions with BeOS
rectArray[i].right += (face->glyph->advance.x >> 6);
rectArray[i].right += is_white_space(charCode) ? delta.space : delta.nonspace;
float top = -(face->glyph->metrics.horiBearingY >> 6);
if (top < rectArray[i].top)
rectArray[i].top = top;
float bottom = (face->glyph->metrics.height
- face->glyph->metrics.horiBearingY) >> 6;
if (bottom > rectArray[i].bottom)
rectArray[i].bottom = bottom;
}
}
PutTransformedFace(face);