39 Commits
1.7 ... v1.9

Author SHA1 Message Date
minjaesong
3841611780 1.9 release 2021-03-15 19:56:53 +09:00
minjaesong
06bc8c9e2d forgot to update demo.png 2020-10-16 15:20:07 +09:00
minjaesong
21415c6f8d add: kerning sets for b and d 2020-10-06 16:31:24 +09:00
minjaesong
22c2a7aa52 fix: issue #12 2020-10-06 15:14:57 +09:00
minjaesong
0eb181f315 time to get off so i'll just commit this 2020-09-29 18:04:58 +09:00
minjaesong
45b431f953 fix: partial fix for issue #12 2020-09-29 14:07:35 +09:00
minjaesong
bbee554fec add: error msg for illegal linotype dimension 2020-09-29 11:36:59 +09:00
minjaesong
c4c67f489e fixing idiotic priority cache impl where they won't get younger 2020-05-04 00:09:05 +09:00
minjaesong
4d867d6523 replacing personalised test text 2020-05-03 23:42:06 +09:00
minjaesong
6620c11178 hangul: minor texture changes 2020-05-03 23:28:59 +09:00
minjaesong
db06cab07c cleaning up unnecessary functions 2020-05-03 22:26:45 +09:00
minjaesong
90b11cdd97 hangul: more microkerning shit 2020-05-03 20:34:12 +09:00
minjaesong
7bb92d1b4e hangul: some of the microkerning implemented in dirty way 2020-05-03 18:13:17 +09:00
minjaesong
b5dd744bd5 hangul: WEO to use wider initials just like WI and YI 2020-05-02 00:03:50 +09:00
minjaesong
34903b10d4 more hangul improvements 2020-05-01 17:12:13 +09:00
minjaesong
0c5b7c8b70 more letters for kerning charsets 2020-04-23 02:50:03 +09:00
minjaesong
cdffca98ef even more kerning pairs i can think of WIP 2020-04-23 01:16:18 +09:00
minjaesong
ce30d1d5fd major modification on hangul font 2020-04-23 01:02:57 +09:00
minjaesong
ab067044f8 more kerning pairs i can think of WIP 2020-04-21 05:17:19 +09:00
minjaesong
3e04b8bbe6 more kerning pairs WIP 2020-04-19 15:03:37 +09:00
minjaesong
4556a9e244 very crude kerning impl for Ys and Ts and AV-VA pairs 2020-04-14 23:56:08 +09:00
minjaesong
e5d04de250 character sets to use ints rather than chars 2020-04-14 23:45:35 +09:00
minjaesong
b7df181729 minor improvement on rotund r 2020-04-14 07:25:11 +09:00
minjaesong
2fd3fcfd46 support for LatinExt-D 2020-04-14 06:41:11 +09:00
minjaesong
73251d70fa completely dropping Slick2d stuffs 2020-01-14 16:26:10 +09:00
minjaesong
971f98beb3 shadow inversion to make recessed texts 2020-01-06 15:19:07 +09:00
minjaesong
abe1da35a0 kana minor edits, fixing wrong case 2019-10-03 01:24:39 +09:00
Minjae Song
29885f3ac9 updating demo.png 2019-05-31 04:14:32 +09:00
Minjae Song
56d2a98a5b hangul update 2019-05-30 14:10:27 +09:00
Minjae Song
43342fff00 demo: updating unicode references 2019-05-14 13:33:14 +09:00
Minjae Song
51d4dec6d3 new redesigned hangul 2019-05-14 13:17:20 +09:00
Minjae Song
81dc38d242 support for Compatibility Hangul 0x3130..0x318F 2019-05-13 02:27:56 +09:00
Minjae Song
863f9d91c8 hangul redraw wip -- less "laundry line" 2019-05-12 23:51:50 +09:00
Minjae Song
4c99cca7ff internal test mode 2019-05-12 17:20:22 +09:00
Minjae Song
b807b96b5f hangul redraw and punct adjustments 2019-05-12 17:10:05 +09:00
Minjae Song
91c9a7a99c TextureRegionPack is now Gdx.disposable 2019-03-10 16:43:32 +09:00
Minjae Song
778e2b0afb tweaks on left/right bumper labels 2019-02-23 23:48:18 +09:00
Minjae Song
c9055ef7b8 PUA: LR buttons are now xbox shaped, added xbox one's View and Menu buttons 2019-02-13 17:52:45 +09:00
Minjae Song
e60b95efb8 bgBG: one dark pixel fixed on 'zhe' 2019-02-08 09:54:54 +09:00
74 changed files with 732 additions and 2132 deletions

0
.gitignore vendored Normal file → Executable file
View File

0
.idea/.name generated Normal file → Executable file
View File

0
.idea/artifacts/FontDemoGDX.xml generated Normal file → Executable file
View File

2
.idea/artifacts/TerrarumSansBitmap.xml generated Normal file → Executable file
View File

@@ -1,6 +1,6 @@
<component name="ArtifactManager">
<artifact type="jar" name="TerrarumSansBitmap">
<output-path>$PROJECT_DIR$/FontTestGDX/lib</output-path>
<output-path>$PROJECT_DIR$/lib</output-path>
<root id="archive" name="TerrarumSansBitmap.jar">
<element id="module-output" name="BuildJAR_TerrarumSansBitmap" />
<element id="directory" name="META-INF">

0
.idea/codeStyles/Project.xml generated Normal file → Executable file
View File

0
.idea/codeStyles/codeStyleConfig.xml generated Normal file → Executable file
View File

0
.idea/kotlinc.xml generated Normal file → Executable file
View File

0
.idea/libraries/GdxLib.xml generated Normal file → Executable file
View File

9
.idea/libraries/KotlinJavaRuntime.xml generated Normal file → Executable file
View File

@@ -3,10 +3,19 @@
<CLASSES>
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-runtime.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-reflect.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-stdlib.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-test.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-stdlib-jdk7.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-stdlib-jdk8.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-runtime-sources.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-stdlib-sources.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-reflect-sources.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-test-sources.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-stdlib-jdk7-sources.jar!/" />
<root url="jar://$KOTLIN_BUNDLED$/lib/kotlin-stdlib-jdk8-sources.jar!/" />
</SOURCES>
</library>
</component>

0
.idea/libraries/TesterLib.xml generated Normal file → Executable file
View File

0
.idea/markdown-navigator.xml generated Normal file → Executable file
View File

0
.idea/markdown-navigator/profiles_settings.xml generated Normal file → Executable file
View File

2
.idea/misc.xml generated Normal file → Executable file
View File

@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectRootManager" version="2" languageLevel="JDK_1_8" default="true" project-jdk-name="1.8" project-jdk-type="JavaSDK">
<component name="ProjectRootManager" version="2" languageLevel="JDK_1_8" default="true" project-jdk-name="1.8.0_242" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/out" />
</component>
</project>

0
.idea/modules.xml generated Normal file → Executable file
View File

0
.idea/vcs.xml generated Normal file → Executable file
View File

1064
.idea/workspace.xml generated Normal file → Executable file

File diff suppressed because it is too large Load Diff

0
BuildJAR_TerrarumSansBitmap.iml Normal file → Executable file
View File

0
CONTRIBUTING.md Normal file → Executable file
View File

0
CONTRIBUTORS.txt Normal file → Executable file
View File

Binary file not shown.

1
FontTestGDX/FontTestGDX.iml Normal file → Executable file
View File

@@ -10,5 +10,6 @@
<orderEntry type="library" name="KotlinJavaRuntime" level="project" />
<orderEntry type="library" name="GdxLib" level="project" />
<orderEntry type="library" name="TesterLib" level="project" />
<orderEntry type="module" module-name="BuildJAR_TerrarumSansBitmap" />
</component>
</module>

2
FontTestGDX/META-INF/MANIFEST.MF Normal file → Executable file
View File

@@ -1,6 +1,6 @@
Manifest-Version: 1.0
Class-Path: lib/gdx.jar lib/gdx-backend-lwjgl.jar lib/gdx-backend-lwjg
l-natives.jar lib/gdx-natives.jar lib/kotlin-stdlib.jar TerrarumSansB
l-natives.jar lib/gdx-natives.jar lib/kotlin-stdlib.jar lib/TerrarumSansB
itmap.jar
Main-Class: FontTestGDXKt

5
FontTestGDX/src/FontTestGDX.kt Normal file → Executable file
View File

@@ -22,9 +22,10 @@ class FontTestGDX : Game() {
lateinit var camera: OrthographicCamera
private val testing = false
private val demotextName = "demotext.txt"
private val outimageName = "demo.png"
private val demotextName = if (testing) "testtext.txt" else "demotext.txt"
private val outimageName = if (testing) "testing.PNG" else "demo.PNG"
override fun create() {
font = GameFontBase("./assets", flipY = false, errorOnUnknownChar = false) // must test for two flipY cases

4
LICENSE.md Normal file → Executable file
View File

@@ -1,6 +1,4 @@
Terrarum Sans Bitmap
Copyright (c) 2017-2019 Minjae Song (Torvald) and the contributors
Copyright (c) 2017-2020 see CONTRIBUTORS.txt
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal

0
META-INF/MANIFEST.MF Normal file → Executable file
View File

0
PUA_allocation_chart.xlsx Normal file → Executable file
View File

12
README.md Normal file → Executable file
View File

@@ -1,8 +1,8 @@
# Terrarum Sans Bitmap
![Font sample](demo.PNG)
![Font sample — necessary information in this image is also provided below.](demo.PNG)
This font is a bitmap font used in [my game project called Terrarum](https://github.com/minjaesong/Terrarum) (hence the name). The font supports more than 90 % of european languages, as well as Chinese, Japanese and Korean. More technical side, it supports Latin-1 Supplement, Latin Ext-A, Latin Ext-B, IPA Extension (required by some languages), Greek, Cyrillic (+ Bulgarian, Serbian variants) and the supplement, Armenian, Thai (beta version), Georgian, Unicode Punctuations, CJK Punctuations, Kana, Chinese (limited to Unihan and Ext-A), Hangul (all 11 172 possible syllables) and Fullwidth forms.
This font is a bitmap font used in [my game project called Terrarum](https://github.com/minjaesong/Terrarum) (hence the name). The font supports more than 90 % of european languages, as well as Chinese, Japanese and Korean. More technical side, it supports Latin-1 Supplement, Latin Ext-A/B/C, IPA Extension, Greek, Cyrillic (+ Bulgarian, Serbian variants) and the supplement, Armenian, Devanagari, Bengali, Thai, Georgian (Mkhedruli and Mtavruli), General Punctuations, Super/Subscrips, CJK Punctuations, All of the Kana (minus the Hentaigana), Chinese (limited to Unihan and Ext-A), Hangul (every possible syllables) and Fullwidth forms.
The JAR package is meant to be used with LibGDX (extends ```BitmapFont``` class). If you are not using the framework, please refer to the __Font metrics__ section to implement the font metrics correctly on your system.
@@ -10,8 +10,8 @@ The issue page is open. If you have some issues to submit, or have a question, p
#### Little notes
- To display Bulgarian/Serbian variants, you need special Control Characters. (GameFontBase.charsetOverrideBulgarian -- U+FFFC1; GameFontBase.charsetOverrideSerbian -- U+FFFC2)
- All Han characters are in Chinese variant, no other variants are to be supported as most Chinese, Japanese and Korean can understand other's variant and to be honest, we don't bother anyway.
- Indian script in general is not perfect: this font will never do the proper ligatures (I can't draw all the 1 224 possible combinations). Hopefully it's still be able to understand without them.
- All Han characters are in Chinese variant, no other variants are to be supported as most Chinese, Japanese and Korean people can understand other's variant and as long as I can, we don't bother anyway.
- Indian script in general is not perfect: right now this font will never do the proper ligatures (I can't draw all the 1 224 possible combinations). Hopefully it's still be able to understand without them.
- Slick2d versions are now unsupported. I couldn't extend myself to work on both versions, but I'm still welcome to merge your pull requests.
### Design Goals
@@ -72,7 +72,7 @@ On your code (Java):
}
### Using on Slick2d
### Using on Slick2d (legacy version only)
On your code (Kotlin):
@@ -130,4 +130,4 @@ Please refer to [CONTRIBUTING.md](https://github.com/minjaesong/Terrarum-sans-bi
Thanks to kind people of [/r/Typography](https://www.reddit.com/r/typography/) for amazing feedbacks.
CJK Ideographs are powered by [WenQuanYi Font](http://wenq.org/wqy2/index.cgi?BitmapSong). The font is distributed under the GNU GPL version 2. Although, in some countries including where I'm based on, the shapes of typefaces are not copyrightable (the program codes—e.g. TTF—do), we would like to give a credit for the font and the people behind it.
CJK Ideographs are powered by [WenQuanYi Font](http://wenq.org/wqy2/index.cgi?BitmapSong). The font is distributed under the GNU GPL version 2. Although the shapes of typefaces are not copyrightable (the program codes—e.g. TTF—do), we would like to give a credit for the font and the people behind it.

0
alignment_illustration.jpg Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 59 KiB

After

Width:  |  Height:  |  Size: 59 KiB

BIN
assets/ascii_variable.tga Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 320 KiB

After

Width:  |  Height:  |  Size: 320 KiB

0
assets/cjkpunct.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 50 KiB

After

Width:  |  Height:  |  Size: 50 KiB

BIN
assets/cyrilic_bulgarian_variable.tga Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 120 KiB

After

Width:  |  Height:  |  Size: 120 KiB

0
assets/cyrilic_serbian_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 120 KiB

After

Width:  |  Height:  |  Size: 120 KiB

0
assets/cyrilic_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 380 KiB

After

Width:  |  Height:  |  Size: 380 KiB

0
assets/devanagari_bengali_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 320 KiB

After

Width:  |  Height:  |  Size: 320 KiB

0
assets/diacritical_marks_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 140 KiB

After

Width:  |  Height:  |  Size: 140 KiB

BIN
assets/fullwidth_forms.tga Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 40 KiB

After

Width:  |  Height:  |  Size: 40 KiB

0
assets/futhark.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 68 KiB

After

Width:  |  Height:  |  Size: 68 KiB

0
assets/greek_polytonic_xyswap_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 320 KiB

After

Width:  |  Height:  |  Size: 320 KiB

0
assets/greek_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 120 KiB

After

Width:  |  Height:  |  Size: 120 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.3 MiB

After

Width:  |  Height:  |  Size: 2.6 MiB

0
assets/hayeren_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 120 KiB

After

Width:  |  Height:  |  Size: 120 KiB

BIN
assets/insular_variable.tga Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 40 KiB

After

Width:  |  Height:  |  Size: 1.8 KiB

0
assets/ipa_ext_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 220 KiB

After

Width:  |  Height:  |  Size: 220 KiB

BIN
assets/kana.tga Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 210 KiB

After

Width:  |  Height:  |  Size: 210 KiB

0
assets/kartuli_allcaps_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 60 KiB

After

Width:  |  Height:  |  Size: 60 KiB

0
assets/kartuli_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 60 KiB

After

Width:  |  Height:  |  Size: 60 KiB

View File

Before

Width:  |  Height:  |  Size: 160 KiB

After

Width:  |  Height:  |  Size: 160 KiB

View File

Before

Width:  |  Height:  |  Size: 260 KiB

After

Width:  |  Height:  |  Size: 260 KiB

View File

Before

Width:  |  Height:  |  Size: 40 KiB

After

Width:  |  Height:  |  Size: 40 KiB

Binary file not shown.

0
assets/latinExt_additional_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 320 KiB

After

Width:  |  Height:  |  Size: 320 KiB

BIN
assets/puae000-e0ff.tga Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 324 KiB

After

Width:  |  Height:  |  Size: 324 KiB

0
assets/richtext_furigana.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 24 KiB

After

Width:  |  Height:  |  Size: 24 KiB

0
assets/thai_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 120 KiB

After

Width:  |  Height:  |  Size: 120 KiB

0
assets/tsalagi_variable.tga Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 120 KiB

After

Width:  |  Height:  |  Size: 120 KiB

BIN
assets/unipunct_variable.tga Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 200 KiB

After

Width:  |  Height:  |  Size: 200 KiB

0
assets/wenquanyi.tga.gz Normal file → Executable file
View File

BIN
demo.PNG Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 145 KiB

After

Width:  |  Height:  |  Size: 146 KiB

17
demotext.txt Normal file → Executable file
View File

@@ -3,16 +3,16 @@
There are many bitmap fonts on the internet. You care for the multilingual support, but alas!
most of them do not support your language, vector fonts take too much time to load, and even
then their legibility suffers because fuck built-in antialias.
then their legibility suffers because screw built-in antialias.
You somehow found a multilingual one, and it makes your game look like an old computer, and you say:
“Well, better than nothing… no, its ugly.”
You speak japanese and you wish to support it, but then このクソなfont only goot for displaying
Japanese, its not even multilingual, and their English look uncanny and inconsistent as hell.
You speak japanese and you wish to support it, but then このクソなfont only good for displaying
Japanese, its not even truly multilingual, and their English look uncanny and inconsistent.
Eventually you just mix different fonts together, and the results were always infuriating.
Eventually you just mix different fonts together, and the results were always mildly infuriating.
No more suffering. This font has everything you need.
@@ -41,11 +41,11 @@ How multilingual? Real multilingual!
􏻬სწრაფი ყავისფერი მელა გადაახტა ზარმაც ძაღლს ᲘᲜᲢᲔᲚ ᲞᲔᲜᲢᲘᲣᲛᲘ ᲛᲘᲙᲠᲝᲞᲠᲝᲪᲔᲡᲝᲠᲘ􀀀
􏻬ऋषियों को सताने वाले दुष्ट राक्षसों के राजा रावण का सर्वनाश करने वाले विष्णुवतार भगवान श्रीराम अयोध्या के महाराज दशरथ के􀀀
􏻬Kæmi ný öxi hér, ykist þjófum nú bæði víl og ádrepa􀀀
􏻬Ċuaiġ bé ṁórṡáċ le dlúṫspád fíorḟinn trí hata mo ḋea-ṗorcáin ḃig􀀀
􏻬Ċuaiġ bé ṁórṡáċ le dlúṫspád fíoḟinn trí hata mo ḋea-ṗocáin ḃig􀀀
􏻬あめつちほしそら やまかはみねたに くもきりむろこけ ひといぬうへすゑ ゆわさるおふせよ えの𛀁をなれゐて􀀀
􏻬トリナクコヱス ユメサマセ ミヨアケワタル ヒンカシヲ ソライロハエテ オキツヘニ ホフネムレヰヌ モヤノウチ􀀀
􏻬田居に出で 菜摘むわれをぞ 君召すと 求食り追ひゆく 山城の 打酔へる子ら 藻葉干せよ え舟繋けぬ􀀀
􏻬정 참판 양반댁 규수 큰 교자 타고 혼례 치른 날 하얬다 도럄직한 퀡봹퉪헰ꥸᅦퟗꥸᅦퟗᄋힳᆫ􀀀
􏻬정 참판 양반댁 규수 큰 교자 타고 혼례 치른 날 하얬다 도럄직한 퀡봹퉪헰ꥸᅦퟗꥸᅦퟗᄋힳᆫㅗㅜㅑㄷ􀀀
􏻬Četri psihi faķīri vēlu vakarā zāģēja guļbūvei durvis, fonā šņācot mežam􀀀
􏻬Įlinkdama fechtuotojo špaga sublykčiojusi pragręžė apvalų arbūzą􀀀
􏻬Ѕидарски пејзаж: шугав билмез со чудење џвака ќофте и кељ на туѓ цех􀀀
@@ -108,8 +108,9 @@ How multilingual? Real multilingual!
Basic Latin Latin-1 Supplement Latin Extended-A Latin Extended-B IPA Extension Greek Cyrillic
Cyrillic Supplement Armenian Devanagari Bengali Thai Georgian Hangul Jamo Cherokee Runic
Georgian Extended Greek Extended General Punctuations Superscripts and Subscripts CJK Symbols
Latin Extended-C Kana Kana Phonetic Extension CJK Unihan Extension A CJK Unihan
Hangul Jamo Extended-A Hangul Syllables Hangul Jamo Extended-B Fullwidth Forms Kana Supplement
Latin Extended-C Kana Hangul Compatibility Jamo Kana Phonetic Extensions CJK Unihan Extension A
CJK Unihan Latin Extended-D Hangul Jamo Extended-A Hangul Syllables Hangul Jamo Extended-B
Fullwidth Forms Kana Supplement
GitHubs issue page is open! You can report any 􏽕errors􀀀, or leave 􏽕suggestions􀀀.
You can help this font to be more versatile. (for more languages, more frameworks) 􏽕Clone􀀀 this repo, make

0
font_drawing_template.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 2.4 KiB

After

Width:  |  Height:  |  Size: 2.4 KiB

0
glyph_height_pos_annotation.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 18 KiB

After

Width:  |  Height:  |  Size: 18 KiB

0
samples/README.md Normal file → Executable file
View File

0
samples/wikipedia_x86.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 75 KiB

After

Width:  |  Height:  |  Size: 75 KiB

0
src/net/torvald/terrarumsansbitmap/GlyphProps.kt Normal file → Executable file
View File

888
src/net/torvald/terrarumsansbitmap/gdx/GameFontBase.kt Normal file → Executable file

File diff suppressed because it is too large Load Diff

View File

@@ -25,14 +25,15 @@
package net.torvald.terrarumsansbitmap.gdx
import com.badlogic.gdx.files.FileHandle
import com.badlogic.gdx.graphics.Color
import com.badlogic.gdx.graphics.Pixmap
/**
* Breaks one pixmap atlas into many child pixmaps
*
* Created by minjaesong on 2018-09-17.
*/
class PixmapRegionPack(
pixmap: Pixmap,
pixmapAtlas: Pixmap,
val tileW: Int,
val tileH: Int,
val hGap: Int = 0,
@@ -47,8 +48,8 @@ class PixmapRegionPack(
constructor(fileHandle: FileHandle, tileW: Int, tileH: Int, hGap: Int = 0, vGap: Int = 0, hFrame: Int = 0, vFrame: Int = 0, xySwapped: Boolean = false) :
this(Pixmap(fileHandle), tileW, tileH, hGap, vGap, hFrame, vFrame, xySwapped)
val horizontalCount = (pixmap.width - 2 * hFrame + hGap) / (tileW + hGap)
val verticalCount = (pixmap.height - 2 * vFrame + vGap) / (tileH + vGap)
val horizontalCount = (pixmapAtlas.width - 2 * hFrame + hGap) / (tileW + hGap)
val verticalCount = (pixmapAtlas.height - 2 * vFrame + vGap) / (tileH + vGap)
val regions: Array<Pixmap>
@@ -70,10 +71,10 @@ class PixmapRegionPack(
pixmap.pixels.rewind()
pixmapAtlas.pixels.rewind()
if (!xySwapped) {
regions = Array<Pixmap>(horizontalCount * verticalCount, {
regions = Array<Pixmap>(horizontalCount * verticalCount) {
val rx = (it % horizontalCount * (tileW + hGap)) + hFrame // pixel, not index
val ry = (it / horizontalCount * (tileH + vGap)) + vFrame // pixel, not index
@@ -84,15 +85,15 @@ class PixmapRegionPack(
// for every "scanline"
for (y in 0 until tileH) {
val offsetY = (ry + y) * (pixmap.width * 4) + (vFrame * pixmap.width * 4)
val offsetY = (ry + y) * (pixmapAtlas.width * 4) + (vFrame * pixmapAtlas.width * 4)
val offsetX = rx * 4 + hFrame * 4
//println("offset: ${offsetX + offsetY}")
val bytesBuffer = ByteArray(4 * tileW)
pixmap.pixels.position(offsetY + offsetX)
pixmap.pixels.get(bytesBuffer, 0, bytesBuffer.size)
pixmapAtlas.pixels.position(offsetY + offsetX)
pixmapAtlas.pixels.get(bytesBuffer, 0, bytesBuffer.size)
// test print bytesbuffer
/*bytesBuffer.forEachIndexed { index, it ->
@@ -112,10 +113,10 @@ class PixmapRegionPack(
// todo globalFlipY ?
/*return*/region
})
}
}
else {
regions = Array<Pixmap>(horizontalCount * verticalCount, {
regions = Array<Pixmap>(horizontalCount * verticalCount) {
val rx = (it / verticalCount * (tileW + hGap)) + hFrame
val ry = (it % verticalCount * (tileH + vGap)) + vFrame
@@ -126,15 +127,15 @@ class PixmapRegionPack(
// for every "scanline"
for (y in 0 until tileH) {
val offsetY = (ry + y) * (pixmap.width * 4) + (vFrame * pixmap.width * 4)
val offsetY = (ry + y) * (pixmapAtlas.width * 4) + (vFrame * pixmapAtlas.width * 4)
val offsetX = rx * 4 + hFrame * 4
//println("offset: ${offsetX + offsetY}")
val bytesBuffer = ByteArray(4 * tileW)
pixmap.pixels.position(offsetY + offsetX)
pixmap.pixels.get(bytesBuffer, 0, bytesBuffer.size)
pixmapAtlas.pixels.position(offsetY + offsetX)
pixmapAtlas.pixels.get(bytesBuffer, 0, bytesBuffer.size)
// test print bytesbuffer
/*bytesBuffer.forEachIndexed { index, it ->
@@ -154,7 +155,7 @@ class PixmapRegionPack(
// todo globalFlipY ?
/*return*/region
})
}
}
}

View File

@@ -27,6 +27,7 @@ package net.torvald.terrarumsansbitmap.gdx
import com.badlogic.gdx.files.FileHandle
import com.badlogic.gdx.graphics.Texture
import com.badlogic.gdx.graphics.g2d.TextureRegion
import com.badlogic.gdx.utils.Disposable
/**
* Created by minjaesong on 2017-06-15.
@@ -40,7 +41,7 @@ class TextureRegionPack(
val hFrame: Int = 0,
val vFrame: Int = 0,
val xySwapped: Boolean = false // because Unicode chart does, duh
) {
): Disposable {
constructor(ref: String, tileW: Int, tileH: Int, hGap: Int = 0, vGap: Int = 0, hFrame: Int = 0, vFrame: Int = 0, xySwapped: Boolean = false) :
this(Texture(ref), tileW, tileH, hGap, vGap, hFrame, vFrame, xySwapped)
@@ -61,7 +62,7 @@ class TextureRegionPack(
//println("texture: $texture, dim: ${texture.width} x ${texture.height}, grid: $horizontalCount x $verticalCount, cellDim: $tileW x $tileH")
if (!xySwapped) {
regions = Array<TextureRegion>(horizontalCount * verticalCount, {
regions = Array<TextureRegion>(horizontalCount * verticalCount) {
val region = TextureRegion()
val rx = (it % horizontalCount * (tileW + hGap)) + hFrame
val ry = (it / horizontalCount * (tileH + vGap)) + vFrame
@@ -72,10 +73,10 @@ class TextureRegionPack(
region.flip(false, globalFlipY)
/*return*/region
})
}
}
else {
regions = Array<TextureRegion>(horizontalCount * verticalCount, {
regions = Array<TextureRegion>(horizontalCount * verticalCount) {
val region = TextureRegion()
val rx = (it / verticalCount * (tileW + hGap)) + hFrame
val ry = (it % verticalCount * (tileH + vGap)) + vFrame
@@ -86,13 +87,13 @@ class TextureRegionPack(
region.flip(false, globalFlipY)
/*return*/region
})
}
}
}
fun get(x: Int, y: Int) = regions[y * horizontalCount + x]
fun dispose() {
override fun dispose() {
texture.dispose()
}

0
src/net/torvald/terrarumsansbitmap/readme.md Normal file → Executable file
View File

View File

@@ -1,790 +0,0 @@
/*
* Terrarum Sans Bitmap
*
* Copyright (c) 2017 Minjae Song (Torvald)
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
package net.torvald.terrarumsansbitmap.slick2d
/*import net.torvald.terrarumsansbitmap.gdx.GameFontBase
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.JUNG_COUNT
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.JONG_COUNT
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.W_ASIAN_PUNCT
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.W_HANGUL
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.W_KANA
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.W_UNIHAN
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.W_LATIN_WIDE
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.W_VAR_INIT
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.HGAP_VAR
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.H
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.H_UNIHAN
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SIZE_CUSTOM_SYM
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_ASCII_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_HANGUL
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_EXTA_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_EXTB_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_KANA
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_CJK_PUNCT
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_UNIHAN
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_CYRILIC_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_FW_UNI
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_UNI_PUNCT_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_GREEK_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_THAI_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_HAYEREN_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_KARTULI_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_IPA_VARW
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_CUSTOM_SYM
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_UNKNOWN
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_RUNIC
import net.torvald.terrarumsansbitmap.gdx.GameFontBase.Companion.SHEET_LATIN_EXT_ADD_VARW
import org.newdawn.slick.Color
import org.newdawn.slick.Font
import org.newdawn.slick.Image
import org.newdawn.slick.SpriteSheet
import org.newdawn.slick.opengl.Texture
import java.io.BufferedOutputStream
import java.io.File
import java.io.FileInputStream
import java.io.FileOutputStream
import java.util.*
import java.util.zip.GZIPInputStream
/**
* LibGDX->Slick2D back-port of Terrarum Sans Bitmap implementation
*
* Filename and Extension for the spritesheet is hard-coded, which are:
*
* - ascii_variable.tga
* - hangul_johab.tga
* - LatinExtA_variable.tga
* - LatinExtB_variable.tga
* - kana.tga
* - cjkpunct.tga
* - wenquanyi.tga.gz
* - cyrillic_variable.tga
* - fullwidth_forms.tga
* - unipunct_variable.tga
* - greek_variable.tga
* - thai_variable.tga
* - puae000-e0ff.tga
*
*
* Glyphs are drawn lazily (calculated on-the-fly, rather than load up all), which is inevitable as we just can't load
* up 40k+ characters on the machine, which will certainly make loading time painfully long.
*
* Color Codes have following Unicode mapping: U+10RGBA, A must be non-zero to be visible. U+100000 reverts any colour code effects.
*
* @param noShadow Self-explanatory
* @param flipY If you have Y-down coord system implemented on your GDX (e.g. legacy codebase), set this to ```true``` so that the shadow won't be upside-down. For glyph getting upside-down, set ```TextureRegionPack.globalFlipY = true```.
*
* Created by minjaesong on 2017-06-15.
*/
class GameFontBase(fontDir: String, val noShadow: Boolean = false) : Font {
private fun getHanChosung(hanIndex: Int) = hanIndex / (JUNG_COUNT * JONG_COUNT)
private fun getHanJungseong(hanIndex: Int) = hanIndex / JONG_COUNT % JUNG_COUNT
private fun getHanJongseong(hanIndex: Int) = hanIndex % JONG_COUNT
private val jungseongWide = arrayOf(8, 12, 13, 17, 18, 21)
private val jungseongComplex = arrayOf(9, 10, 11, 14, 15, 16, 22)
private fun isJungseongWide(hanIndex: Int) = jungseongWide.contains(getHanJungseong(hanIndex))
private fun isJungseongComplex(hanIndex: Int) = jungseongComplex.contains(getHanJungseong(hanIndex))
private fun getHanInitialRow(hanIndex: Int): Int {
val ret: Int
if (isJungseongWide(hanIndex))
ret = 2
else if (isJungseongComplex(hanIndex))
ret = 4
else
ret = 0
return if (getHanJongseong(hanIndex) == 0) ret else ret + 1
}
private fun getHanMedialRow(hanIndex: Int) = if (getHanJongseong(hanIndex) == 0) 6 else 7
private fun getHanFinalRow(hanIndex: Int): Int {
val jungseongIndex = getHanJungseong(hanIndex)
return if (jungseongWide.contains(jungseongIndex))
8
else
9
}
private fun isHangul(c: Char) = c.toInt() in codeRange[SHEET_HANGUL]
private fun isAscii(c: Char) = c.toInt() in codeRange[SHEET_ASCII_VARW]
private fun isRunic(c: Char) = c.toInt() in codeRange[SHEET_RUNIC]
private fun isExtA(c: Char) = c.toInt() in codeRange[SHEET_EXTA_VARW]
private fun isExtB(c: Char) = c.toInt() in codeRange[SHEET_EXTB_VARW]
private fun isKana(c: Char) = c.toInt() in codeRange[SHEET_KANA]
private fun isCJKPunct(c: Char) = c.toInt() in codeRange[SHEET_CJK_PUNCT]
private fun isUniHan(c: Char) = c.toInt() in codeRange[SHEET_UNIHAN]
private fun isCyrilic(c: Char) = c.toInt() in codeRange[SHEET_CYRILIC_VARW]
private fun isFullwidthUni(c: Char) = c.toInt() in codeRange[SHEET_FW_UNI]
private fun isUniPunct(c: Char) = c.toInt() in codeRange[SHEET_UNI_PUNCT_VARW]
private fun isGreek(c: Char) = c.toInt() in codeRange[SHEET_GREEK_VARW]
private fun isThai(c: Char) = c.toInt() in codeRange[SHEET_THAI_VARW]
private fun isDiacritics(c: Char) = c.toInt() in 0xE34..0xE3A
|| c.toInt() in 0xE47..0xE4E
|| c.toInt() == 0xE31
private fun isCustomSym(c: Char) = c.toInt() in codeRange[SHEET_CUSTOM_SYM]
private fun isArmenian(c: Char) = c.toInt() in codeRange[SHEET_HAYEREN_VARW]
private fun isKartvelian(c: Char) = c.toInt() in codeRange[SHEET_KARTULI_VARW]
private fun isIPA(c: Char) = c.toInt() in codeRange[SHEET_IPA_VARW]
private fun isColourCodeHigh(c: Char) = c.toInt() in 0b110110_1111000000..0b110110_1111111111 // only works with JVM (which uses UTF-16 internally)
private fun isColourCodeLow(c: Char) = c.toInt() in 0b110111_0000000000..0b110111_1111111111 // only works with JVM (which uses UTF-16 internally)
private fun isLatinExtAdd(c: Char) = c.toInt() in 0x1E00..0x1EFF
private fun extAindexX(c: Char) = (c.toInt() - 0x100) % 16
private fun extAindexY(c: Char) = (c.toInt() - 0x100) / 16
private fun extBindexX(c: Char) = (c.toInt() - 0x180) % 16
private fun extBindexY(c: Char) = (c.toInt() - 0x180) / 16
private fun runicIndexX(c: Char) = (c.toInt() - 0x16A0) % 16
private fun runicIndexY(c: Char) = (c.toInt() - 0x16A0) / 16
private fun kanaIndexX(c: Char) = (c.toInt() - 0x3040) % 16
private fun kanaIndexY(c: Char) = (c.toInt() - 0x3040) / 16
private fun cjkPunctIndexX(c: Char) = (c.toInt() - 0x3000) % 16
private fun cjkPunctIndexY(c: Char) = (c.toInt() - 0x3000) / 16
private fun cyrilicIndexX(c: Char) = (c.toInt() - 0x400) % 16
private fun cyrilicIndexY(c: Char) = (c.toInt() - 0x400) / 16
private fun fullwidthUniIndexX(c: Char) = (c.toInt() - 0xFF00) % 16
private fun fullwidthUniIndexY(c: Char) = (c.toInt() - 0xFF00) / 16
private fun uniPunctIndexX(c: Char) = (c.toInt() - 0x2000) % 16
private fun uniPunctIndexY(c: Char) = (c.toInt() - 0x2000) / 16
private fun unihanIndexX(c: Char) = (c.toInt() - 0x3400) % 256
private fun unihanIndexY(c: Char) = (c.toInt() - 0x3400) / 256
private fun greekIndexX(c: Char) = (c.toInt() - 0x370) % 16
private fun greekIndexY(c: Char) = (c.toInt() - 0x370) / 16
private fun thaiIndexX(c: Char) = (c.toInt() - 0xE00) % 16
private fun thaiIndexY(c: Char) = (c.toInt() - 0xE00) / 16
private fun symbolIndexX(c: Char) = (c.toInt() - 0xE000) % 16
private fun symbolIndexY(c: Char) = (c.toInt() - 0xE000) / 16
private fun armenianIndexX(c: Char) = (c.toInt() - 0x530) % 16
private fun armenianIndexY(c: Char) = (c.toInt() - 0x530) / 16
private fun kartvelianIndexX(c: Char) = (c.toInt() - 0x10D0) % 16
private fun kartvelianIndexY(c: Char) = (c.toInt() - 0x10D0) / 16
private fun ipaIndexX(c: Char) = (c.toInt() - 0x250) % 16
private fun ipaIndexY(c: Char) = (c.toInt() - 0x250) / 16
private fun latinExtAddX(c: Char) = (c.toInt() - 0x1E00) % 16
private fun latinExtAddY(c: Char) = (c.toInt() - 0x1E00) / 16
private fun getColour(charHigh: Char, charLow: Char): Color { // input: 0x10ARGB, out: RGBA8888
val codePoint = Character.toCodePoint(charHigh, charLow)
if (colourBuffer.containsKey(codePoint))
return colourBuffer[codePoint]!!
val r = codePoint.and(0xF000).ushr(12)
val g = codePoint.and(0x0F00).ushr(8)
val b = codePoint.and(0x00F0).ushr(4)
val a = codePoint.and(0x000F)
val col = Color(a.shl(28) or a.shl(24) or r.shl(20) or r.shl(16) or g.shl(12) or g.shl(8) or b.shl(4) or b)
colourBuffer[codePoint] = col
return col
}
private val colourBuffer = HashMap<Int, Color>()
private val unihanWidthSheets = arrayOf(
SHEET_UNIHAN,
SHEET_FW_UNI
)
private val variableWidthSheets = arrayOf(
SHEET_ASCII_VARW,
SHEET_EXTA_VARW,
SHEET_EXTB_VARW,
SHEET_CYRILIC_VARW,
SHEET_UNI_PUNCT_VARW,
SHEET_GREEK_VARW,
SHEET_THAI_VARW,
SHEET_HAYEREN_VARW,
SHEET_KARTULI_VARW,
SHEET_IPA_VARW,
SHEET_LATIN_EXT_ADD_VARW
)
private val fontParentDir = if (fontDir.endsWith('/') || fontDir.endsWith('\\')) fontDir else "$fontDir/"
private val fileList = arrayOf( // MUST BE MATCHING WITH SHEET INDICES!!
"ascii_variable.tga",
"hangul_johab.tga",
"latinExtA_variable.tga",
"latinExtB_variable.tga",
"kana.tga",
"cjkpunct.tga",
"wenquanyi.tga.gz",
"cyrilic_variable.tga",
"fullwidth_forms.tga",
"unipunct_variable.tga",
"greek_variable.tga",
"thai_variable.tga",
"hayeren_variable.tga",
"kartuli_variable.tga",
"ipa_ext_variable.tga",
"futhark.tga",
"latinExt_additional_variable.tga",
"puae000-e0ff.tga"
)
private val cyrilic_bg = "cyrilic_bulgarian_variable.tga"
private val cyrilic_sr = "cyrilic_serbian_variable.tga"
private val codeRange = arrayOf( // MUST BE MATCHING WITH SHEET INDICES!!
0..0xFF,
0xAC00..0xD7A3,
0x100..0x17F,
0x180..0x24F,
0x3040..0x30FF,
0x3000..0x303F,
0x3400..0x9FFF,
0x400..0x52F,
0xFF00..0xFF1F,
0x2000..0x205F,
0x370..0x3CE,
0xE00..0xE5F,
0x530..0x58F,
0x10D0..0x10FF,
0x250..0x2AF,
0x16A0..0x16FF,
0x1E00..0x1EFF,
0xE000..0xE0FF
)
private val glyphWidths: HashMap<Int, Int> = HashMap() // if the value is negative, it's diacritics
private val sheets: Array<SpriteSheet>
init {
val sheetsPack = ArrayList<SpriteSheet>()
// first we create pixmap to read pixels, then make texture using pixmap
fileList.forEachIndexed { index, it ->
val isVariable1 = it.endsWith("_variable.tga")
val isVariable2 = variableWidthSheets.contains(index)
val isVariable = isVariable1 && isVariable2
// idiocity check
if (isVariable1 && !isVariable2)
throw Error("[TerrarumSansBitmap] font is named as variable on the name but not enlisted as")
else if (!isVariable1 && isVariable2)
throw Error("[TerrarumSansBitmap] font is enlisted as variable on the name but not named as")
val image: Image
// unpack gz if applicable
if (it.endsWith(".gz")) {
val gzi = GZIPInputStream(FileInputStream(fontParentDir + it))
val wholeFile = gzi.readBytes()
gzi.close()
val fos = BufferedOutputStream(FileOutputStream("tmp_wenquanyi.tga"))
fos.write(wholeFile)
fos.flush()
fos.close()
image = Image("tmp_wenquanyi.tga")
File("tmp_wenquanyi.tga").delete()
}
else {
image = Image(fontParentDir + it)
}
val texture = image.texture
if (isVariable) {
println("[TerrarumSansBitmap] loading texture $it [VARIABLE]")
buildWidthTable(texture, codeRange[index], 16)
}
else {
println("[TerrarumSansBitmap] loading texture $it")
}
val texRegPack = if (isVariable) {
SpriteSheet(image, W_VAR_INIT, H - 1, HGAP_VAR)
}
else if (index == SHEET_UNIHAN) {
SpriteSheet(image, W_UNIHAN, H_UNIHAN) // the only exception that is height is 16
}
// below they all have height of 20 'H'
else if (index == SHEET_FW_UNI) {
SpriteSheet(image, W_UNIHAN, H)
}
else if (index == SHEET_CJK_PUNCT) {
SpriteSheet(image, W_ASIAN_PUNCT, H)
}
else if (index == SHEET_KANA) {
SpriteSheet(image, W_KANA, H)
}
else if (index == SHEET_HANGUL) {
SpriteSheet(image, W_HANGUL, H)
}
else if (index == SHEET_CUSTOM_SYM) {
SpriteSheet(image, SIZE_CUSTOM_SYM, SIZE_CUSTOM_SYM) // TODO variable
}
else if (index == SHEET_RUNIC) {
SpriteSheet(image, W_LATIN_WIDE, H)
}
else throw IllegalArgumentException("[TerrarumSansBitmap] Unknown sheet index: $index")
sheetsPack.add(texRegPack)
}
sheets = sheetsPack.toTypedArray()
}
private var localeBuffer = ""
fun reload(locale: String) {
if (!localeBuffer.startsWith("ru") && locale.startsWith("ru")) {
val image = Image(fontParentDir + fileList[SHEET_CYRILIC_VARW])
sheets[SHEET_CYRILIC_VARW].destroy()
sheets[SHEET_CYRILIC_VARW] = SpriteSheet(image, W_VAR_INIT, H, HGAP_VAR, 0)
}
else if (!localeBuffer.startsWith("bg") && locale.startsWith("bg")) {
val image = Image(fontParentDir + cyrilic_bg)
sheets[SHEET_CYRILIC_VARW].destroy()
sheets[SHEET_CYRILIC_VARW] = SpriteSheet(image, W_VAR_INIT, H, HGAP_VAR, 0)
}
else if (!localeBuffer.startsWith("sr") && locale.startsWith("sr")) {
val image = Image(fontParentDir + cyrilic_sr)
sheets[SHEET_CYRILIC_VARW].destroy()
sheets[SHEET_CYRILIC_VARW] = SpriteSheet(image, W_VAR_INIT, H, HGAP_VAR, 0)
}
localeBuffer = locale
}
override fun getLineHeight(): Int = H
override fun getHeight(p0: String) = lineHeight
private val offsetUnihan = (H - H_UNIHAN) / 2
private val offsetCustomSym = (H - SIZE_CUSTOM_SYM) / 2
private var textBuffer: CharSequence = ""
private var textBWidth = intArrayOf() // absolute posX of glyphs from print-origin
private var textBGSize = intArrayOf() // width of each glyph
override fun drawString(x: Float, y: Float, str: String) {
drawString(x, y, str, Color.white)
}
override fun drawString(p0: Float, p1: Float, p2: String?, p3: Color?, p4: Int, p5: Int) {
throw UnsupportedOperationException()
}
override fun drawString(x: Float, y: Float, str: String, color: Color) {
// always draw at integer position; this is bitmap font after all
val x = Math.round(x).toFloat()
val y = Math.round(y).toFloat()
if (textBuffer != str) {
textBuffer = str
val widths = getWidthOfCharSeq(str)
textBGSize = widths
textBWidth = IntArray(str.length, { charIndex ->
if (charIndex == 0)
0
else {
var acc = 0
(0..charIndex - 1).forEach { acc += maxOf(0, widths[it]) } // don't accumulate diacrtics (which has negative value)
/*return*/acc
}
})
}
//print("[TerrarumSansBitmap] widthTable for $textBuffer: ")
//textBWidth.forEach { print("$it ") }; println()
var mainCol = color
var shadowCol = color.darker(0.5f)
var index = 0
while (index <= textBuffer.lastIndex) {
val c = textBuffer[index]
val sheetID = getSheetType(c)
val sheetXY = getSheetwisePosition(c)
//println("[TerrarumSansBitmap] sprite: $sheetID:${sheetXY[0]}x${sheetXY[1]}")
if (isColourCodeHigh(c)) {
val cchigh = c
val cclow = textBuffer[index + 1]
if (Character.toCodePoint(cchigh, cclow) == 0x100000) {
mainCol = color
shadowCol = color.darker(0.5f)
}
else {
mainCol = getColour(cchigh, cclow)
shadowCol = mainCol.darker(0.5f)
}
index += 1
}
else if (isColourCodeLow(c)) {
throw Error("Unexpected encounter of ColourCodeLow at index $index of String '$textBuffer'")
}
else if (sheetID == SHEET_HANGUL) {
val hangulSheet = sheets[SHEET_HANGUL]
val hIndex = c.toInt() - 0xAC00
val indexCho = getHanChosung(hIndex)
val indexJung = getHanJungseong(hIndex)
val indexJong = getHanJongseong(hIndex)
val choRow = getHanInitialRow(hIndex)
val jungRow = getHanMedialRow(hIndex)
val jongRow = getHanFinalRow(hIndex)
if (!noShadow) {
hangulSheet.getSubImage(indexCho, choRow ).draw(x + textBWidth[index] + 1, y, shadowCol)
hangulSheet.getSubImage(indexCho, choRow ).draw(x + textBWidth[index] , y, shadowCol)
hangulSheet.getSubImage(indexCho, choRow ).draw(x + textBWidth[index] + 1, y, shadowCol)
hangulSheet.getSubImage(indexJung, jungRow).draw(x + textBWidth[index] + 1, y, shadowCol)
hangulSheet.getSubImage(indexJung, jungRow).draw(x + textBWidth[index] , y, shadowCol)
hangulSheet.getSubImage(indexJung, jungRow).draw(x + textBWidth[index] + 1, y, shadowCol)
hangulSheet.getSubImage(indexJong, jongRow).draw(x + textBWidth[index] + 1, y, shadowCol)
hangulSheet.getSubImage(indexJong, jongRow).draw(x + textBWidth[index] , y, shadowCol)
hangulSheet.getSubImage(indexJong, jongRow).draw(x + textBWidth[index] + 1, y, shadowCol)
}
hangulSheet.getSubImage(indexCho, choRow ).draw(x + textBWidth[index], y, mainCol)
hangulSheet.getSubImage(indexJung, jungRow).draw(x + textBWidth[index], y, mainCol)
hangulSheet.getSubImage(indexJong, jongRow).draw(x + textBWidth[index], y, mainCol)
}
else {
try {
val offset = if (!isDiacritics(c)) 0 else {
if (index > 0) // LIMITATION: does not support double (or more) diacritics properly
(textBGSize[index] - textBGSize[index - 1]) / 2
else
textBGSize[index]
}
if (!noShadow) {
sheets[sheetID].getSubImage(sheetXY[0], sheetXY[1]).draw(
x + textBWidth[index] + 1 + offset,
y + (if (sheetID == SHEET_UNIHAN) // evil exceptions
offsetUnihan
else if (sheetID == SHEET_CUSTOM_SYM)
offsetCustomSym
else
0),
shadowCol
)
sheets[sheetID].getSubImage(sheetXY[0], sheetXY[1]).draw(
x + textBWidth[index] + offset,
y + (if (sheetID == SHEET_UNIHAN) // evil exceptions
offsetUnihan + 1
else if (sheetID == SHEET_CUSTOM_SYM)
offsetCustomSym + 1
else
1),
shadowCol
)
sheets[sheetID].getSubImage(sheetXY[0], sheetXY[1]).draw(
x + textBWidth[index] + 1 + offset,
y + (if (sheetID == SHEET_UNIHAN) // evil exceptions
offsetUnihan + 1
else if (sheetID == SHEET_CUSTOM_SYM)
offsetCustomSym + 1
else
1),
shadowCol
)
}
sheets[sheetID].getSubImage(sheetXY[0], sheetXY[1]).draw(
x + textBWidth[index] + offset,
y + if (sheetID == SHEET_UNIHAN) // evil exceptions
offsetUnihan
else if (sheetID == SHEET_CUSTOM_SYM)
offsetCustomSym
else 0,
mainCol
)
}
catch (noSuchGlyph: ArrayIndexOutOfBoundsException) {
}
}
index += 1
}
}
fun dispose() {
sheets.forEach { it.destroy() }
}
private fun getWidthOfCharSeq(s: CharSequence): IntArray {
val len = IntArray(s.length)
for (i in 0..s.lastIndex) {
val chr = s[i]
val ctype = getSheetType(s[i])
if (variableWidthSheets.contains(ctype)) {
if (!glyphWidths.containsKey(chr.toInt())) {
println("[TerrarumSansBitmap] no width data for glyph number ${Integer.toHexString(chr.toInt()).toUpperCase()}")
len[i] = W_LATIN_WIDE
}
len[i] = glyphWidths[chr.toInt()]!!
}
else if (isColourCodeHigh(chr) || isColourCodeLow(chr))
len[i] = 0
else if (ctype == SHEET_CJK_PUNCT)
len[i] = W_ASIAN_PUNCT
else if (ctype == SHEET_HANGUL)
len[i] = W_HANGUL
else if (ctype == SHEET_KANA)
len[i] = W_KANA
else if (unihanWidthSheets.contains(ctype))
len[i] = W_UNIHAN
else if (ctype == SHEET_CUSTOM_SYM)
len[i] = SIZE_CUSTOM_SYM
else
len[i] = W_LATIN_WIDE
if (scale > 1) len[i] *= scale
if (i < s.lastIndex) len[i] += interchar
}
return len
}
private fun getSheetType(c: Char): Int {
if (isHangul(c))
return SHEET_HANGUL
else if (isKana(c))
return SHEET_KANA
else if (isUniHan(c))
return SHEET_UNIHAN
else if (isAscii(c))
return SHEET_ASCII_VARW
else if (isExtA(c))
return SHEET_EXTA_VARW
else if (isExtB(c))
return SHEET_EXTB_VARW
else if (isCyrilic(c))
return SHEET_CYRILIC_VARW
else if (isUniPunct(c))
return SHEET_UNI_PUNCT_VARW
else if (isCJKPunct(c))
return SHEET_CJK_PUNCT
else if (isFullwidthUni(c))
return SHEET_FW_UNI
else if (isGreek(c))
return SHEET_GREEK_VARW
else if (isThai(c))
return SHEET_THAI_VARW
else if (isCustomSym(c))
return SHEET_CUSTOM_SYM
else if (isArmenian(c))
return SHEET_HAYEREN_VARW
else if (isKartvelian(c))
return SHEET_KARTULI_VARW
else if (isIPA(c))
return SHEET_IPA_VARW
else if (isRunic(c))
return SHEET_RUNIC
else if (isLatinExtAdd(c))
return SHEET_LATIN_EXT_ADD_VARW
else
return SHEET_UNKNOWN
// fixed width
// fallback
}
private fun getSheetwisePosition(ch: Char): IntArray {
val sheetX: Int; val sheetY: Int
when (getSheetType(ch)) {
SHEET_UNIHAN -> {
sheetX = unihanIndexX(ch)
sheetY = unihanIndexY(ch)
}
SHEET_EXTA_VARW -> {
sheetX = extAindexX(ch)
sheetY = extAindexY(ch)
}
SHEET_EXTB_VARW -> {
sheetX = extBindexX(ch)
sheetY = extBindexY(ch)
}
SHEET_KANA -> {
sheetX = kanaIndexX(ch)
sheetY = kanaIndexY(ch)
}
SHEET_CJK_PUNCT -> {
sheetX = cjkPunctIndexX(ch)
sheetY = cjkPunctIndexY(ch)
}
SHEET_CYRILIC_VARW -> {
sheetX = cyrilicIndexX(ch)
sheetY = cyrilicIndexY(ch)
}
SHEET_FW_UNI -> {
sheetX = fullwidthUniIndexX(ch)
sheetY = fullwidthUniIndexY(ch)
}
SHEET_UNI_PUNCT_VARW -> {
sheetX = uniPunctIndexX(ch)
sheetY = uniPunctIndexY(ch)
}
SHEET_GREEK_VARW -> {
sheetX = greekIndexX(ch)
sheetY = greekIndexY(ch)
}
SHEET_THAI_VARW -> {
sheetX = thaiIndexX(ch)
sheetY = thaiIndexY(ch)
}
SHEET_CUSTOM_SYM -> {
sheetX = symbolIndexX(ch)
sheetY = symbolIndexY(ch)
}
SHEET_HAYEREN_VARW -> {
sheetX = armenianIndexX(ch)
sheetY = armenianIndexY(ch)
}
SHEET_KARTULI_VARW -> {
sheetX = kartvelianIndexX(ch)
sheetY = kartvelianIndexY(ch)
}
SHEET_IPA_VARW -> {
sheetX = ipaIndexX(ch)
sheetY = ipaIndexY(ch)
}
SHEET_RUNIC -> {
sheetX = runicIndexX(ch)
sheetY = runicIndexY(ch)
}
SHEET_LATIN_EXT_ADD_VARW -> {
sheetX = latinExtAddX(ch)
sheetY = latinExtAddY(ch)
}
else -> {
sheetX = ch.toInt() % 16
sheetY = ch.toInt() / 16
}
}
return intArrayOf(sheetX, sheetY)
}
fun buildWidthTable(texture: Texture, codeRange: IntRange, cols: Int = 16) {
val binaryCodeOffset = W_VAR_INIT
val cellW = W_VAR_INIT + 1
val cellH = H
for (code in codeRange) {
val cellX = ((code - codeRange.start) % cols) * cellW
val cellY = ((code - codeRange.start) / cols) * cellH
val codeStartX = cellX + binaryCodeOffset
val codeStartY = cellY
var glyphWidth = 0
for (downCtr in 0..3) {
// if ALPHA is not zero, assume it's 1
if (texture.textureData[4 * (codeStartX + (codeStartY + downCtr) * texture.textureWidth) + 3] != 0.toByte()) {
glyphWidth = glyphWidth or (1 shl downCtr)
}
}
val isDiacritics = texture.textureData[4 * (codeStartX + (codeStartY + H - 1) * texture.textureWidth) + 3] != 0.toByte()
if (isDiacritics)
glyphWidth = -glyphWidth
glyphWidths[code] = glyphWidth
}
}
override fun getWidth(text: String): Int {
return getWidthOfCharSeq(text).sum()
}
var interchar = 0
var scale = 1
set(value) {
if (value > 0) field = value
else throw IllegalArgumentException("Font scale cannot be zero or negative (input: $value)")
}
fun toColorCode(rgba4444: Int): String = GameFontBase.toColorCode(rgba4444)
fun toColorCode(r: Int, g: Int, b: Int, a: Int = 0x0F): String = toColorCode(r.shl(12) or g.shl(8) or b.shl(4) or a)
val noColorCode = toColorCode(0x0000)
companion object {
fun toColorCode(rgba4444: Int): String = Character.toChars(0x100000 + rgba4444).toColCode()
fun toColorCode(r: Int, g: Int, b: Int, a: Int = 0x0F): String = toColorCode(r.shl(12) or g.shl(8) or b.shl(4) or a)
private fun CharArray.toColCode(): String = "${this[0]}${this[1]}"
val noColorCode = toColorCode(0x0000)
}
}*/

0
terrarum_sans_cyrillic_2.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 22 KiB

After

Width:  |  Height:  |  Size: 22 KiB

BIN
testing.PNG Normal file → Executable file

Binary file not shown.

Before

Width:  |  Height:  |  Size: 18 KiB

After

Width:  |  Height:  |  Size: 58 KiB

24
testtext.txt Normal file → Executable file
View File

@@ -1,10 +1,16 @@
re ʘ, ʇ, ʗ, and ʖ, al
ɓ ɗ ɠ
ɐ ɔ ə ɟ ɥ ɯ ɹ ʇ ʌ ʍ ʎ
Vʷ[kʰuˣt̪s̟] and Vʷ[kʰʉˣt͜ʃ].
To
uu
Td
mm
Ye
Yd
ʡ̆
Labiodental flap [ⱱ] U+2C71
acegijmnopqrsuvwxyzɱɳʙɾɽʒʂʐʋɹɻɥɟɡɢʛȵɲŋɴʀɕʑçʝxɣχʁʜʍɰʟɨʉɯuʊøɘɵɤəɛœɜɞʌɔæɐɶɑɒɚɝɩɪʅʈʏʞⱥⱦⱱⱳⱴⱶⱷⱸⱺⱻ
/œ̃/
/ɛ̃/
/ẽ
when the line ends with a diacritics, whole letter wont render
if the line starts with a letter-with-diacritic, it will error out

0
width_bit_encoding_annotated.png Normal file → Executable file
View File

Before

Width:  |  Height:  |  Size: 18 KiB

After

Width:  |  Height:  |  Size: 18 KiB