Jeck - Minor bugfix: prevent garbage characters from appearing in JLBFont.

This commit is contained in:
wagic.jeck
2009-12-10 15:53:23 +00:00
parent ee36281fa0
commit 9b0afb7105
+231 -224
View File
@@ -1,224 +1,231 @@
//------------------------------------------------------------------------------------- //-------------------------------------------------------------------------------------
// //
// JGE++ is a hardware accelerated 2D game SDK for PSP/Windows. // JGE++ is a hardware accelerated 2D game SDK for PSP/Windows.
// //
// Licensed under the BSD license, see LICENSE in JGE root for details. // Licensed under the BSD license, see LICENSE in JGE root for details.
// //
// Copyright (c) 2007 James Hui (a.k.a. Dr.Watson) <jhkhui@gmail.com> // Copyright (c) 2007 James Hui (a.k.a. Dr.Watson) <jhkhui@gmail.com>
// //
//------------------------------------------------------------------------------------- //-------------------------------------------------------------------------------------
#include "../include/JLBFont.h" #include "../include/JLBFont.h"
#include "../include/JFileSystem.h" #include "../include/JFileSystem.h"
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <stdarg.h> #include <stdarg.h>
JRenderer* JLBFont::mRenderer = NULL; JRenderer* JLBFont::mRenderer = NULL;
JLBFont::JLBFont(const char *fontname, int lineheight, bool useVideoRAM) JLBFont::JLBFont(const char *fontname, int lineheight, bool useVideoRAM)
{ {
mRenderer = JRenderer::GetInstance(); mRenderer = JRenderer::GetInstance();
mHeight = 0; mHeight = 0;
mScale = 1.0f; mScale = 1.0f;
mRotation = mSpacing = 0.0f; mRotation = mSpacing = 0.0f;
mTracking = 0.0f; mTracking = 0.0f;
mColor = ARGB(255,255,255,255); mColor = ARGB(255,255,255,255);
mTexture = NULL; mTexture = NULL;
mQuad = NULL; mQuad = NULL;
mBase = 0; mBase = 0;
char filename[256]; char filename[256];
short buffer[1024]; short buffer[1024];
sprintf(filename, "%s.dat", fontname); sprintf(filename, "%s.dat", fontname);
//FILE *file; //FILE *file;
JFileSystem *fileSys = JFileSystem::GetInstance(); JFileSystem *fileSys = JFileSystem::GetInstance();
if (!fileSys->OpenFile(filename)) return; if (!fileSys->OpenFile(filename)) return;
fileSys->ReadFile((u8 *)buffer, 2048); fileSys->ReadFile((u8 *)buffer, 2048);
fileSys->CloseFile(); fileSys->CloseFile();
sprintf(filename, "%s.png", fontname); sprintf(filename, "%s.png", fontname);
mTexture = mRenderer->LoadTexture(filename, useVideoRAM); mTexture = mRenderer->LoadTexture(filename, useVideoRAM);
if (mTexture == NULL) return; if (mTexture == NULL) return;
mHeight = (float) lineheight; mHeight = (float) lineheight;
mQuad = new JQuad(mTexture, 0.0f, 0.0f, 16.0f, mHeight); mQuad = new JQuad(mTexture, 0.0f, 0.0f, 16.0f, mHeight);
float a, b, c; float a, b, c;
float y = 0.0f; float y = 0.0f;
float x; float x;
// there are 16x16 characters in the texture map. // there are 16x16 characters in the texture map.
float cellHeight = mTexture->mHeight/16.0f; float cellHeight = mTexture->mHeight/16.0f;
int n = 0; int n = 0;
for (int i=0;i<16;i++) for (int i=0;i<16;i++)
{ {
for (int j=0;j<16;j++) for (int j=0;j<16;j++)
{ {
x = (float)buffer[n*4]; // x offset x = (float)buffer[n*4]; // x offset
a = (float)buffer[n*4+1]; // character width a = (float)buffer[n*4+1]; // character width
b = (float)buffer[n*4+2]; b = (float)buffer[n*4+2];
c = (float)buffer[n*4+3]; c = (float)buffer[n*4+3];
mXPos[n] = x; mXPos[n] = x;
mYPos[n] = y; mYPos[n] = y;
mCharWidth[n] = a+b+c; mCharWidth[n] = a+b+c;
n++; n++;
} }
y += cellHeight; y += cellHeight;
} }
} }
JLBFont::~JLBFont() JLBFont::~JLBFont()
{ {
if (mQuad) if (mQuad)
delete mQuad; delete mQuad;
if (mTexture) if (mTexture)
delete mTexture; delete mTexture;
// JGERelease(); // JGERelease();
} }
void JLBFont::DrawString(std::string s, float x, float y, int align, float leftOffset, float displayWidth) void JLBFont::DrawString(std::string s, float x, float y, int align, float leftOffset, float displayWidth)
{ {
return DrawString(s.c_str(), x, y, align, leftOffset, displayWidth); return DrawString(s.c_str(), x, y, align, leftOffset, displayWidth);
} }
void JLBFont::DrawString(const char *string, float x, float y, int align, float leftOffset, float displayWidth) void JLBFont::DrawString(const char *string, float x, float y, int align, float leftOffset, float displayWidth)
{ {
char *p = (char*)string; char *p = (char*)string;
float dx0 = x, dy = y; float dx0 = x, dy = y;
if (mQuad == NULL) return; if (mQuad == NULL) return;
float width = GetStringWidth(string); float width = GetStringWidth(string);
if (align == JGETEXT_RIGHT) if (align == JGETEXT_RIGHT)
dx0 -= width; dx0 -= width;
else if (align == JGETEXT_CENTER) else if (align == JGETEXT_CENTER)
dx0 -= width/2; dx0 -= width/2;
float dx = floorf(dx0); float dx = floorf(dx0);
dy = floorf(dy); dy = floorf(dy);
float x0 = dx; float x0 = dx;
int index; int index;
while (*p) while (*p)
{ {
if (*p == '\n') { if (*p == '\n') {
p++; p++;
dy += (mHeight * 1.1 * mScale); dy += (mHeight * 1.1 * mScale);
dy = floorf(dy); dy = floorf(dy);
dx = dx0; dx = dx0;
continue; continue;
} }
index = (*p - 32)+mBase; //Skip characters with no encoding.
float charWidth = mCharWidth[index]; if((*p - 32) < 0 || (*p - 32) > 127){
float delta = (charWidth + mTracking) * mScale; p++;
float xPos = mXPos[index]; continue;
if (leftOffset){ }
if (leftOffset < 0){
dx-=leftOffset; index = (*p - 32)+mBase;
leftOffset = 0;
continue; float charWidth = mCharWidth[index];
}else if (leftOffset - delta > 0){ float delta = (charWidth + mTracking) * mScale;
leftOffset -= delta; float xPos = mXPos[index];
p++; if (leftOffset){
continue; if (leftOffset < 0){
}else{ dx-=leftOffset;
xPos = mXPos[index] + (leftOffset); leftOffset = 0;
delta -= leftOffset; continue;
leftOffset = 0; }else if (leftOffset - delta > 0){
leftOffset -= delta;
charWidth = (delta/mScale) - mTracking; p++;
} continue;
} }else{
else if (displayWidth){ xPos = mXPos[index] + (leftOffset);
if (dx > x0+displayWidth) return; delta -= leftOffset;
if (dx+delta > x0+displayWidth) { leftOffset = 0;
delta = x0 + displayWidth - dx;
charWidth = (delta/mScale) - mTracking; charWidth = (delta/mScale) - mTracking;
} }
} }
mQuad->SetTextureRect(xPos, mYPos[index], charWidth , mHeight); else if (displayWidth){
mRenderer->RenderQuad(mQuad, dx, dy, mRotation, mScale, mScale); if (dx > x0+displayWidth) return;
dx += delta; if (dx+delta > x0+displayWidth) {
p++; delta = x0 + displayWidth - dx;
charWidth = (delta/mScale) - mTracking;
} }
}
} mQuad->SetTextureRect(xPos, mYPos[index], charWidth , mHeight);
mRenderer->RenderQuad(mQuad, dx, dy, mRotation, mScale, mScale);
dx += delta;
void JLBFont::printf(float x, float y, const char *format, ...) p++;
{
char buffer[PRINTF_BUFFER_SIZE]; }
va_list list;
}
va_start(list, format);
vsprintf(buffer, format, list);
va_end(list); void JLBFont::printf(float x, float y, const char *format, ...)
{
DrawString(buffer, x, y); char buffer[PRINTF_BUFFER_SIZE];
} va_list list;
va_start(list, format);
void JLBFont::SetColor(PIXEL_TYPE color) vsprintf(buffer, format, list);
{ va_end(list);
mColor = color;
mQuad->SetColor(mColor); DrawString(buffer, x, y);
} }
void JLBFont::SetColor(PIXEL_TYPE color)
float JLBFont::GetStringWidth(const char *string) const {
{ mColor = color;
float len = 0.0f; mQuad->SetColor(mColor);
}
const char *p = string;
char ch;
while (*p) float JLBFont::GetStringWidth(const char *string) const
{ {
ch = *p - 32; float len = 0.0f;
p++;
if (ch < 0) continue; const char *p = string;
len += mCharWidth[ch+mBase] + mTracking; char ch;
}
len -= mTracking; while (*p)
return len*mScale; {
} ch = *p - 32;
p++;
void JLBFont::SetScale(float scale) { mScale = scale; } if (ch < 0) continue;
void JLBFont::SetRotation(float rot) { mRotation = rot; } len += mCharWidth[ch+mBase] + mTracking;
void JLBFont::SetTracking(float tracking) { mTracking = tracking; } }
PIXEL_TYPE JLBFont::GetColor() const { return mColor; } len -= mTracking;
float JLBFont::GetScale() const { return mScale; } return len*mScale;
float JLBFont::GetRotation() const { return mRotation; } }
float JLBFont::GetTracking() const { return mTracking; }
float JLBFont::GetHeight() const { return mHeight; } void JLBFont::SetScale(float scale) { mScale = scale; }
void JLBFont::SetRotation(float rot) { mRotation = rot; }
void JLBFont::SetBase(int base) void JLBFont::SetTracking(float tracking) { mTracking = tracking; }
{ PIXEL_TYPE JLBFont::GetColor() const { return mColor; }
mBase = (base==0)?0:128; float JLBFont::GetScale() const { return mScale; }
} float JLBFont::GetRotation() const { return mRotation; }
float JLBFont::GetTracking() const { return mTracking; }
float JLBFont::GetHeight() const { return mHeight; }
void JLBFont::SetBase(int base)
{
mBase = (base==0)?0:128;
}