diff --git a/source/common/fonts/font.cpp b/source/common/fonts/font.cpp index c8964accf..dd619ac10 100644 --- a/source/common/fonts/font.cpp +++ b/source/common/fonts/font.cpp @@ -328,14 +328,14 @@ FFont::FFont (const char *name, const char *nametemplate, const char *filetempla auto orig = pic->GetTexture(); auto tex = MakeGameTexture(orig, nullptr, ETextureType::FontChar); - tex->CopySize(pic); + tex->CopySize(pic, true); TexMan.AddGameTexture(tex); Chars[i].OriginalPic = tex; if (!noTranslate) { Chars[i].TranslatedPic = MakeGameTexture(new FImageTexture(new FFontChar1(orig->GetImage())), nullptr, ETextureType::FontChar); - Chars[i].TranslatedPic->CopySize(pic); + Chars[i].TranslatedPic->CopySize(pic, true); TexMan.AddGameTexture(Chars[i].TranslatedPic); } else @@ -441,9 +441,9 @@ void FFont::ReadSheetFont(TArray &folderdata, int width, int height auto pic = (*lump)->GetTexture(); Chars[i].OriginalPic = (*lump)->GetUseType() == ETextureType::FontChar? (*lump) : MakeGameTexture(pic, nullptr, ETextureType::FontChar); Chars[i].OriginalPic->SetUseType(ETextureType::FontChar); - Chars[i].OriginalPic->CopySize(*lump); + Chars[i].OriginalPic->CopySize(*lump, true); Chars[i].TranslatedPic = MakeGameTexture(new FImageTexture(new FFontChar1(pic->GetImage())), nullptr, ETextureType::FontChar); - Chars[i].TranslatedPic->CopySize(*lump); + Chars[i].TranslatedPic->CopySize(*lump, true); Chars[i].TranslatedPic->SetUseType(ETextureType::FontChar); if (Chars[i].OriginalPic != *lump) TexMan.AddGameTexture(Chars[i].OriginalPic); TexMan.AddGameTexture(Chars[i].TranslatedPic); diff --git a/source/common/fonts/specialfont.cpp b/source/common/fonts/specialfont.cpp index 4dca54d3f..7e9c0778d 100644 --- a/source/common/fonts/specialfont.cpp +++ b/source/common/fonts/specialfont.cpp @@ -105,13 +105,13 @@ FSpecialFont::FSpecialFont (const char *name, int first, int count, FGameTexture { auto pic = charlumps[i]; Chars[i].OriginalPic = MakeGameTexture(pic->GetTexture(), nullptr, ETextureType::FontChar); - Chars[i].OriginalPic->CopySize(pic); + Chars[i].OriginalPic->CopySize(pic, true); TexMan.AddGameTexture(Chars[i].OriginalPic); if (!noTranslate) { Chars[i].TranslatedPic = MakeGameTexture(new FImageTexture(new FFontChar1 (charlumps[i]->GetTexture()->GetImage())), nullptr, ETextureType::FontChar); - Chars[i].TranslatedPic->CopySize(charlumps[i]); + Chars[i].TranslatedPic->CopySize(charlumps[i], true); TexMan.AddGameTexture(Chars[i].TranslatedPic); } else Chars[i].TranslatedPic = Chars[i].OriginalPic; diff --git a/source/common/textures/gametexture.h b/source/common/textures/gametexture.h index e1283e6de..db2153de9 100644 --- a/source/common/textures/gametexture.h +++ b/source/common/textures/gametexture.h @@ -58,6 +58,7 @@ enum EGameTexFlags GTexf_DisableFullbrightSprites = 64, // This texture will not be displayed as fullbright sprite GTexf_BrightmapChecked = 128, // Check for a colormap-based brightmap was already done. GTexf_AutoMaterialsAdded = 256, // AddAutoMaterials has been called on this texture. + GTexf_OffsetsNotForFont = 512, // The offsets must be ignored when using this texture in a font. }; // Refactoring helper to allow piece by piece adjustment of the API @@ -156,6 +157,7 @@ public: void SetWorldPanning(bool on) { if (on) flags |= GTexf_WorldPanning; else flags &= ~GTexf_WorldPanning; } bool allowNoDecals() const { return !!(flags & GTexf_NoDecals); } void SetNoDecals(bool on) { if (on) flags |= GTexf_NoDecals; else flags &= ~GTexf_NoDecals; } + void SetOffsetsNotForFont() { flags |= GTexf_OffsetsNotForFont; } bool isValid() const { return UseType != ETextureType::Null; } int isWarped() { return warped; } @@ -208,12 +210,15 @@ public: float GetGlossiness() const { return Glossiness; } float GetSpecularLevel() const { return SpecularLevel; } - void CopySize(FGameTexture* BaseTexture) + void CopySize(FGameTexture* BaseTexture, bool forfont = false) { Base->CopySize(BaseTexture->Base.get()); SetDisplaySize(BaseTexture->GetDisplayWidth(), BaseTexture->GetDisplayHeight()); - SetOffsets(0, BaseTexture->GetTexelLeftOffset(0), BaseTexture->GetTexelTopOffset(0)); - SetOffsets(1, BaseTexture->GetTexelLeftOffset(1), BaseTexture->GetTexelTopOffset(1)); + if (!forfont || !(BaseTexture->flags & GTexf_OffsetsNotForFont)) + { + SetOffsets(0, BaseTexture->GetTexelLeftOffset(0), BaseTexture->GetTexelTopOffset(0)); + SetOffsets(1, BaseTexture->GetTexelLeftOffset(1), BaseTexture->GetTexelTopOffset(1)); + } } // Glowing is a pure material property that should not filter down to the actual texture objects. diff --git a/source/games/duke/src/2d_d.cpp b/source/games/duke/src/2d_d.cpp index d0865071a..4d612e70b 100644 --- a/source/games/duke/src/2d_d.cpp +++ b/source/games/duke/src/2d_d.cpp @@ -84,7 +84,11 @@ void InitFonts_d() fontdata.Insert('`', tileGetTexture(BIGAPPOS)); fontdata.Insert('"', tileGetTexture(BIGAPPOS)); fontdata.Insert('\'', tileGetTexture(BIGAPPOS)); - BigFont = new ::FFont("BigFont", nullptr, "defbigfont", 0, 0, 0, -1, -1, false, false, false, &fontdata); + // The texture offsets in this font are useless for font printing. This should only apply to these glyphs, not for international extensions, though. + GlyphSet::Iterator it(fontdata); + GlyphSet::Pair* pair; + while (it.NextPair(pair)) pair->Value->SetOffsetsNotForFont(); + BigFont = new ::FFont("BigFont", nullptr, "defbigfont", 0, 0, 0, -1, 5, false, false, false, &fontdata); fontdata.Clear(); // Tiny font @@ -663,14 +667,22 @@ public: class DEpisode4Text : public DScreenJob { + + void centertext(double y, const char* text) + { + text = GStrings(text); + auto width = BigFont->StringWidth(text); + DrawText(twod, BigFont, CR_RED, 160. - width/2, y - 12, text, DTA_FullscreenScale, 3, DTA_VirtualWidth, 320, DTA_VirtualHeight, 200, TAG_DONE); + } + int Frame(uint64_t clock, bool skiprequest) { twod->ClearScreen(); - menutext_center(60, GStrings("Thanks to all our")); - menutext_center(60 + 16, GStrings("fans for giving")); - menutext_center(60 + 16 + 16, GStrings("us big heads.")); - menutext_center(70 + 16 + 16 + 16, GStrings("Look for a Duke Nukem 3D")); - menutext_center(70 + 16 + 16 + 16 + 16, GStrings("sequel soon.")); + centertext(60, "Thanks to all our"); + centertext(60 + 16, "fans for giving"); + centertext(60 + 16 + 16, "us big heads."); + centertext(70 + 16 + 16 + 16, "Look for a Duke Nukem 3D"); + centertext(70 + 16 + 16 + 16 + 16, "sequel soon."); return skiprequest ? -1 : 1; } };