mirror of
https://github.com/curioustorvald/Terrarum.git
synced 2026-06-11 19:14:05 +09:00
more btex tests
This commit is contained in:
@@ -9,41 +9,61 @@
|
|||||||
|
|
||||||
<manuscript>
|
<manuscript>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>What Is a Book</chapter>
|
<chapter>What Is a Book</chapter>
|
||||||
|
|
||||||
<p>This example book is designed to give you the exampe of the Book Language.</p>
|
<p>This example book is designed to give you the example of the Book Language.</p>
|
||||||
|
|
||||||
<section>What Really Is a Book</section>
|
<section>What Really Is a Book</section>
|
||||||
|
|
||||||
<p>A book is a collection of texts printed in a special way that allows them to be read easily, with enumerable pages and insertion of other helpful resources, such as illustrations and hyperlinks.</p>
|
<p>A book is a collection of texts printed in a special way that allows them to be read easily, with
|
||||||
|
enumerable pages and insertion of other helpful resources, such as illustrations and hyperlinks.</p>
|
||||||
|
|
||||||
<newpage />
|
<newpage />
|
||||||
|
|
||||||
<fullpagebox>
|
<fullpagebox>
|
||||||
<span colour="grey">
|
<p><span colour="grey">
|
||||||
<p>this page is intentionally left blank</p>
|
this page is intentionally left blank
|
||||||
</span>
|
</span></p>
|
||||||
</fullpagebox>
|
</fullpagebox>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>Writing Book Using Pen and Papers</chapter>
|
<chapter>Writing Book Using Pen and Papers</chapter>
|
||||||
|
|
||||||
<p>If you open a book on a writing table, you will be welcomed with a toolbar used to put other book elements, such as chapters, sections.</p>
|
<p><index id="pen and paper" />If you open a book on a writing table, you will be welcomed with a
|
||||||
|
toolbar used to put other book elements, such as chapters, sections.</p>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>Writing Book Using Typewriter</chapter>
|
<chapter>Writing Book Using Typewriter</chapter>
|
||||||
|
|
||||||
<p>Typewriters can only write single style of font, therefore chapters and sections are not available.</p>
|
<p><index id="typewriter" />Typewriters can only write single style of font, therefore chapters and
|
||||||
|
sections are not available.</p>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>Writing Book using Computer</chapter>
|
<chapter>Writing Book using Computer</chapter>
|
||||||
|
|
||||||
<p>Writing book using a computer requires a use of the Book Typesetting Engine Extended, or <BTeX /></p>
|
<p>Writing book using a computer requires a use of the Book Typesetting Engine Extended, or <btex /></p>
|
||||||
|
|
||||||
<section>Full Control of the Shape</section>
|
<section>Full Control of the Shape</section>
|
||||||
|
|
||||||
<p>With <BTeX /> you can fully control how your publishing would look like, from a pile of papers that look like they have been typed out using typewriter, a pile of papers but a fully-featured printouts that have illustrations in it, to a fully-featured hardcover book.</p>
|
<p><index id="btex language" />With <btex /> you can fully control how your publishing would look like,
|
||||||
|
from a pile of papers that look like they have been typed out using typewriter, a pile of papers but a
|
||||||
|
fully-featured printouts that have illustrations in it, to a fully-featured hardcover book.</p>
|
||||||
|
|
||||||
<p>This style is controlled using the <code>cover</code> attribute on the root tag, with following values: <code>typewriter</code>, <code>printout</code>, <code>hardcover</code></p>
|
<p><index id="cover" />This style is controlled using the <code>cover</code> attribute on the root tag,
|
||||||
|
with following values: <code>typewriter</code>, <code>printout</code>, <code>hardcover</code></p>
|
||||||
|
|
||||||
<p>Typewriter and Printout are considered not bound and readers will only see one page at a time, while Hardcover is considered bound and two pages are presented to the readers.</p>
|
<p>Typewriter and Printout are considered not bound and readers will only see one page at a time,
|
||||||
|
while Hardcover is considered bound and two pages are presented to the readers.</p>
|
||||||
|
|
||||||
</manuscript>
|
</manuscript>
|
||||||
|
|
||||||
|
<indexpage><tableofindices /></indexpage>
|
||||||
</btexdoc>
|
</btexdoc>
|
||||||
|
|||||||
BIN
lib/TerrarumSansBitmap.jar
LFS
BIN
lib/TerrarumSansBitmap.jar
LFS
Binary file not shown.
@@ -1,10 +1,8 @@
|
|||||||
package net.torvald.terrarum.btex
|
package net.torvald.terrarum.btex
|
||||||
|
|
||||||
import com.badlogic.gdx.graphics.Color
|
import com.badlogic.gdx.graphics.Color
|
||||||
import com.badlogic.gdx.graphics.g2d.BitmapFont
|
|
||||||
import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
||||||
import com.badlogic.gdx.graphics.g2d.TextureRegion
|
import com.badlogic.gdx.graphics.g2d.TextureRegion
|
||||||
import net.torvald.terrarum.App
|
|
||||||
import net.torvald.terrarum.ui.Toolkit
|
import net.torvald.terrarum.ui.Toolkit
|
||||||
import net.torvald.terrarumsansbitmap.MovableType
|
import net.torvald.terrarumsansbitmap.MovableType
|
||||||
|
|
||||||
@@ -18,9 +16,9 @@ class BTeXDocument {
|
|||||||
var papersize = "standard"
|
var papersize = "standard"
|
||||||
|
|
||||||
var pageWidth = 420
|
var pageWidth = 420
|
||||||
var lineHeight = 24
|
var lineHeightInPx = 24
|
||||||
var pageLines = 25
|
var pageLines = 25
|
||||||
var pageHeight = pageLines * lineHeight
|
var pageHeight = pageLines * lineHeightInPx
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
val DEFAULT_PAGE_BACK = Color(0xe1e1d7ff.toInt())
|
val DEFAULT_PAGE_BACK = Color(0xe1e1d7ff.toInt())
|
||||||
@@ -29,14 +27,26 @@ class BTeXDocument {
|
|||||||
|
|
||||||
private val pages = ArrayList<BTeXPage>()
|
private val pages = ArrayList<BTeXPage>()
|
||||||
|
|
||||||
|
val currentPage: Int
|
||||||
|
get() = pages.size - 1
|
||||||
|
|
||||||
|
var currentLine: Int = 0
|
||||||
|
private set
|
||||||
|
|
||||||
fun addNewPage(back: Color = DEFAULT_PAGE_BACK) {
|
fun addNewPage(back: Color = DEFAULT_PAGE_BACK) {
|
||||||
pages.add(BTeXPage(back, pageWidth, pageHeight))
|
pages.add(BTeXPage(back, pageWidth, pageHeight))
|
||||||
|
currentLine = 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Appends draw call to the list. The draw call must be prepared manually so that they would not overflow.
|
||||||
|
* Use `addNewPage` to append the overflowing text to the next page.
|
||||||
|
*
|
||||||
|
* `currentLine` *will* be updated automatically.
|
||||||
|
*/
|
||||||
fun appendDrawCall(drawCall: BTeXDrawCall) {
|
fun appendDrawCall(drawCall: BTeXDrawCall) {
|
||||||
pages.last().appendDrawCall(drawCall)
|
pages.last().appendDrawCall(drawCall)
|
||||||
|
currentLine += drawCall.lineCount
|
||||||
}
|
}
|
||||||
|
|
||||||
fun render(frameDelta: Float, batch: SpriteBatch, page: Int, x: Int, y: Int) {
|
fun render(frameDelta: Float, batch: SpriteBatch, page: Int, x: Int, y: Int) {
|
||||||
@@ -64,21 +74,37 @@ class BTeXPage(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
data class MovableTypeDrawCall(val movableType: MovableType, val rowStart: Int, val rowEnd: Int) {
|
interface BTeXTextDrawCall {
|
||||||
fun draw(batch: SpriteBatch, x: Float, y: Float) {
|
val rowStart: Int
|
||||||
|
val rowEnd: Int
|
||||||
|
fun draw(batch: SpriteBatch, x: Float, y: Float)
|
||||||
|
}
|
||||||
|
|
||||||
|
data class MovableTypeDrawCall(val movableType: MovableType, override val rowStart: Int, override val rowEnd: Int): BTeXTextDrawCall {
|
||||||
|
override fun draw(batch: SpriteBatch, x: Float, y: Float) {
|
||||||
movableType.draw(batch, x, y, rowStart, rowEnd)
|
movableType.draw(batch, x, y, rowStart, rowEnd)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*data class RaggedLeftDrawCall(val raggedType: RaggedType, override val rowStart: Int, override val rowEnd: Int): BTeXTextDrawCall {
|
||||||
|
override fun draw(batch: SpriteBatch, x: Float, y: Float) {
|
||||||
|
raggedType.draw(batch, x, y, rowStart, rowEnd)
|
||||||
|
}
|
||||||
|
}*/
|
||||||
|
|
||||||
class BTeXDrawCall(
|
class BTeXDrawCall(
|
||||||
val posX: Int,
|
val posX: Int, // position relative to the page start (excluding page margin)
|
||||||
val posY: Int,
|
val posY: Int, // position relative to the page start (excluding page margin)
|
||||||
val theme: String,
|
val theme: String,
|
||||||
val colour: Color,
|
val colour: Color,
|
||||||
val text: MovableTypeDrawCall? = null,
|
val text: BTeXTextDrawCall? = null,
|
||||||
val texture: TextureRegion? = null,
|
val texture: TextureRegion? = null,
|
||||||
) {
|
) {
|
||||||
|
|
||||||
|
init {
|
||||||
|
if (text != null && texture != null) throw IllegalArgumentException("Text and Texture are both non-null")
|
||||||
|
}
|
||||||
|
|
||||||
fun draw(batch: SpriteBatch, x: Int, y: Int) {
|
fun draw(batch: SpriteBatch, x: Int, y: Int) {
|
||||||
val px = (posX + x).toFloat()
|
val px = (posX + x).toFloat()
|
||||||
val py = (posY + y).toFloat()
|
val py = (posY + y).toFloat()
|
||||||
@@ -98,4 +124,9 @@ class BTeXDrawCall(
|
|||||||
else throw Error("Text and Texture are both non-null")
|
else throw Error("Text and Texture are both non-null")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
internal val lineCount = if (text != null)
|
||||||
|
text.rowEnd - text.rowStart
|
||||||
|
else
|
||||||
|
TODO()
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -4,7 +4,11 @@ import com.badlogic.gdx.files.FileHandle
|
|||||||
import com.badlogic.gdx.graphics.Color
|
import com.badlogic.gdx.graphics.Color
|
||||||
import net.torvald.terrarum.App
|
import net.torvald.terrarum.App
|
||||||
import net.torvald.terrarum.btex.BTeXDocument
|
import net.torvald.terrarum.btex.BTeXDocument
|
||||||
|
import net.torvald.terrarum.btex.BTeXDrawCall
|
||||||
|
import net.torvald.terrarum.btex.MovableTypeDrawCall
|
||||||
import net.torvald.terrarum.gameitems.ItemID
|
import net.torvald.terrarum.gameitems.ItemID
|
||||||
|
import net.torvald.terrarumsansbitmap.MovableType
|
||||||
|
import net.torvald.terrarumsansbitmap.gdx.TerrarumSansBitmap
|
||||||
import org.xml.sax.Attributes
|
import org.xml.sax.Attributes
|
||||||
import org.xml.sax.InputSource
|
import org.xml.sax.InputSource
|
||||||
import org.xml.sax.helpers.DefaultHandler
|
import org.xml.sax.helpers.DefaultHandler
|
||||||
@@ -20,6 +24,9 @@ import kotlin.reflect.full.findAnnotation
|
|||||||
*/
|
*/
|
||||||
object BTeXParser {
|
object BTeXParser {
|
||||||
|
|
||||||
|
internal val textTags = hashSetOf("P", "TITLE", "AUTHOR", "EDITION", "CHAPTER", "SECTION")
|
||||||
|
internal val textDecorTags = hashSetOf("SPAN", "CODE")
|
||||||
|
|
||||||
operator fun invoke(file: FileHandle) = invoke(file.file())
|
operator fun invoke(file: FileHandle) = invoke(file.file())
|
||||||
|
|
||||||
operator fun invoke(file: File): BTeXDocument {
|
operator fun invoke(file: File): BTeXDocument {
|
||||||
@@ -39,7 +46,7 @@ object BTeXParser {
|
|||||||
|
|
||||||
internal class BTeXHandler(val doc: BTeXDocument) : DefaultHandler() {
|
internal class BTeXHandler(val doc: BTeXDocument) : DefaultHandler() {
|
||||||
private val DEFAULT_FONTCOL = Color(0x222222ff)
|
private val DEFAULT_FONTCOL = Color(0x222222ff)
|
||||||
private val LINE_HEIGHT = doc.lineHeight
|
private val LINE_HEIGHT = doc.lineHeightInPx
|
||||||
|
|
||||||
private var cover = ""
|
private var cover = ""
|
||||||
private var inner = ""
|
private var inner = ""
|
||||||
@@ -56,7 +63,7 @@ object BTeXParser {
|
|||||||
|
|
||||||
private val tagStack = ArrayList<String>() // index zero should be "btex"
|
private val tagStack = ArrayList<String>() // index zero should be "btex"
|
||||||
|
|
||||||
|
private var currentTheme = ""
|
||||||
private var spanColour: String? = null
|
private var spanColour: String? = null
|
||||||
|
|
||||||
|
|
||||||
@@ -66,6 +73,8 @@ object BTeXParser {
|
|||||||
private val elemOpeners: HashMap<String, KFunction<*>> = HashMap()
|
private val elemOpeners: HashMap<String, KFunction<*>> = HashMap()
|
||||||
private val elemClosers: HashMap<String, KFunction<*>> = HashMap()
|
private val elemClosers: HashMap<String, KFunction<*>> = HashMap()
|
||||||
|
|
||||||
|
private val paragraphBuffer = StringBuilder()
|
||||||
|
|
||||||
init {
|
init {
|
||||||
BTeXHandler::class.declaredFunctions.filter { it.findAnnotation<OpenTag>() != null }.forEach {
|
BTeXHandler::class.declaredFunctions.filter { it.findAnnotation<OpenTag>() != null }.forEach {
|
||||||
println("Tag opener: ${it.name}")
|
println("Tag opener: ${it.name}")
|
||||||
@@ -101,14 +110,21 @@ object BTeXParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
override fun startElement(uri: String, localName: String, qName: String, attributes: Attributes) {
|
override fun startElement(uri: String, localName: String, qName: String, attributes: Attributes) {
|
||||||
val tag = qName; if (tagStack.isEmpty() && tag.lowercase() != "btexdoc") throw BTeXParsingException("Document is not BTeX")
|
val tag = qName
|
||||||
tagStack.add(tag)
|
if (tagStack.isEmpty() && tag.lowercase() != "btexdoc") throw BTeXParsingException("Document is not BTeX")
|
||||||
|
val theTag = tag.uppercase()
|
||||||
|
|
||||||
|
if (tagStack.isNotEmpty() && tagStack.any { textTags.contains(it) } && textTags.contains(theTag))
|
||||||
|
throw IllegalStateException("Text tag '$theTag' used inside of text tags (tag stack is ${tagStack.joinToString()})")
|
||||||
|
if (tagStack.isNotEmpty() && !textTags.contains(tagStack.last()) && textDecorTags.contains(theTag))
|
||||||
|
throw IllegalStateException("Text decoration tag '$theTag' used outside of a text tag (tag stack is ${tagStack.joinToString()})")
|
||||||
|
|
||||||
|
tagStack.add(theTag)
|
||||||
|
|
||||||
val attribs = HashMap<String, String>().also {
|
val attribs = HashMap<String, String>().also {
|
||||||
it.putAll((0 until attributes.length).map { attributes.getQName(it) to attributes.getValue(it) })
|
it.putAll((0 until attributes.length).map { attributes.getQName(it) to attributes.getValue(it) })
|
||||||
}
|
}
|
||||||
|
|
||||||
val theTag = tag.uppercase()
|
|
||||||
|
|
||||||
elemOpeners["processElem$theTag"].let {
|
elemOpeners["processElem$theTag"].let {
|
||||||
if (it == null)
|
if (it == null)
|
||||||
@@ -123,7 +139,7 @@ object BTeXParser {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// printdbg("Start element \t($tag)")
|
// printdbg("Start element \t($theTag)")
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun endElement(uri: String, localName: String, qName: String) {
|
override fun endElement(uri: String, localName: String, qName: String) {
|
||||||
@@ -147,8 +163,9 @@ object BTeXParser {
|
|||||||
val str =
|
val str =
|
||||||
String(ch.sliceArray(start until start + length)).replace('\n', ' ').replace(Regex(" +"), " ")//.trim()
|
String(ch.sliceArray(start until start + length)).replace('\n', ' ').replace(Regex(" +"), " ")//.trim()
|
||||||
|
|
||||||
if (str.isNotBlank()) {
|
if (str.isNotEmpty()) {
|
||||||
printdbg("Characters \t\"$str\"")
|
// printdbg("Characters \t\"$str\"")
|
||||||
|
paragraphBuffer.append(str)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -170,16 +187,212 @@ object BTeXParser {
|
|||||||
typeY += h
|
typeY += h
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private lateinit var testFont: TerrarumSansBitmap
|
||||||
|
|
||||||
private fun getFont() = when (cover) {
|
private fun getFont() = when (cover) {
|
||||||
"typewriter" -> TODO()
|
"typewriter" -> TODO()
|
||||||
else -> App.fontGame
|
else -> App.fontGame ?: let {
|
||||||
|
if (!::testFont.isInitialized) testFont = TerrarumSansBitmap(App.FONT_DIR)
|
||||||
|
testFont
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getSpanColour(): Color = spanColourMap.getOrDefault(spanColour, DEFAULT_FONTCOL)
|
private val hexColRegexRGBshort = Regex("#[0-9a-fA-F]{3,3}")
|
||||||
|
private val hexColRegexRGB = Regex("#[0-9a-fA-F]{6,6}")
|
||||||
|
|
||||||
|
private fun getSpanColour(): Color = if (spanColour == null) DEFAULT_FONTCOL
|
||||||
|
else if (spanColour!!.matches(hexColRegexRGB)) {
|
||||||
|
val rs = spanColour!!.substring(1,3)
|
||||||
|
val gs = spanColour!!.substring(3,5)
|
||||||
|
val bs = spanColour!!.substring(5,7)
|
||||||
|
|
||||||
|
val r = rs.toInt(16) / 255f
|
||||||
|
val g = gs.toInt(16) / 255f
|
||||||
|
val b = bs.toInt(16) / 255f
|
||||||
|
|
||||||
|
Color(r, g, b, 1f)
|
||||||
|
}
|
||||||
|
else if (spanColour!!.matches(hexColRegexRGBshort)) {
|
||||||
|
val rs = spanColour!!.substring(1,2)
|
||||||
|
val gs = spanColour!!.substring(2,3)
|
||||||
|
val bs = spanColour!!.substring(3,4)
|
||||||
|
|
||||||
|
val r = rs.toInt(16) / 15f
|
||||||
|
val g = gs.toInt(16) / 15f
|
||||||
|
val b = bs.toInt(16) / 15f
|
||||||
|
|
||||||
|
Color(r, g, b, 1f)
|
||||||
|
}
|
||||||
|
else
|
||||||
|
spanColourMap.getOrDefault(spanColour, DEFAULT_FONTCOL)
|
||||||
|
|
||||||
|
// list of CSS named colours (list supports up to CSS Colors Level 4)
|
||||||
private val spanColourMap = hashMapOf(
|
private val spanColourMap = hashMapOf(
|
||||||
"grey" to Color.LIGHT_GRAY
|
"black" to Color(0x000000ff.toInt()),
|
||||||
|
"silver" to Color(0xc0c0c0ff.toInt()),
|
||||||
|
"gray" to Color(0x808080ff.toInt()),
|
||||||
|
"white" to Color(0xffffffff.toInt()),
|
||||||
|
"maroon" to Color(0x800000ff.toInt()),
|
||||||
|
"red" to Color(0xff0000ff.toInt()),
|
||||||
|
"purple" to Color(0x800080ff.toInt()),
|
||||||
|
"fuchsia" to Color(0xff00ffff.toInt()),
|
||||||
|
"green" to Color(0x008000ff.toInt()),
|
||||||
|
"lime" to Color(0x00ff00ff.toInt()),
|
||||||
|
"olive" to Color(0x808000ff.toInt()),
|
||||||
|
"yellow" to Color(0xffff00ff.toInt()),
|
||||||
|
"navy" to Color(0x000080ff.toInt()),
|
||||||
|
"blue" to Color(0x0000ffff.toInt()),
|
||||||
|
"teal" to Color(0x008080ff.toInt()),
|
||||||
|
"aqua" to Color(0x00ffffff.toInt()),
|
||||||
|
"aliceblue" to Color(0xf0f8ffff.toInt()),
|
||||||
|
"antiquewhite" to Color(0xfaebd7ff.toInt()),
|
||||||
|
"aqua" to Color(0x00ffffff.toInt()),
|
||||||
|
"aquamarine" to Color(0x7fffd4ff.toInt()),
|
||||||
|
"azure" to Color(0xf0ffffff.toInt()),
|
||||||
|
"beige" to Color(0xf5f5dcff.toInt()),
|
||||||
|
"bisque" to Color(0xffe4c4ff.toInt()),
|
||||||
|
"black" to Color(0x000000ff.toInt()),
|
||||||
|
"blanchedalmond" to Color(0xffebcdff.toInt()),
|
||||||
|
"blue" to Color(0x0000ffff.toInt()),
|
||||||
|
"blueviolet" to Color(0x8a2be2ff.toInt()),
|
||||||
|
"brown" to Color(0xa52a2aff.toInt()),
|
||||||
|
"burlywood" to Color(0xdeb887ff.toInt()),
|
||||||
|
"cadetblue" to Color(0x5f9ea0ff.toInt()),
|
||||||
|
"chartreuse" to Color(0x7fff00ff.toInt()),
|
||||||
|
"chocolate" to Color(0xd2691eff.toInt()),
|
||||||
|
"coral" to Color(0xff7f50ff.toInt()),
|
||||||
|
"cornflowerblue" to Color(0x6495edff.toInt()),
|
||||||
|
"cornsilk" to Color(0xfff8dcff.toInt()),
|
||||||
|
"crimson" to Color(0xdc143cff.toInt()),
|
||||||
|
"cyan" to Color(0x00ffffff.toInt()),
|
||||||
|
"darkblue" to Color(0x00008bff.toInt()),
|
||||||
|
"darkcyan" to Color(0x008b8bff.toInt()),
|
||||||
|
"darkgoldenrod" to Color(0xb8860bff.toInt()),
|
||||||
|
"darkgray" to Color(0xa9a9a9ff.toInt()),
|
||||||
|
"darkgreen" to Color(0x006400ff.toInt()),
|
||||||
|
"darkgrey" to Color(0xa9a9a9ff.toInt()),
|
||||||
|
"darkkhaki" to Color(0xbdb76bff.toInt()),
|
||||||
|
"darkmagenta" to Color(0x8b008bff.toInt()),
|
||||||
|
"darkolivegreen" to Color(0x556b2fff.toInt()),
|
||||||
|
"darkorange" to Color(0xff8c00ff.toInt()),
|
||||||
|
"darkorchid" to Color(0x9932ccff.toInt()),
|
||||||
|
"darkred" to Color(0x8b0000ff.toInt()),
|
||||||
|
"darksalmon" to Color(0xe9967aff.toInt()),
|
||||||
|
"darkseagreen" to Color(0x8fbc8fff.toInt()),
|
||||||
|
"darkslateblue" to Color(0x483d8bff.toInt()),
|
||||||
|
"darkslategray" to Color(0x2f4f4fff.toInt()),
|
||||||
|
"darkslategrey" to Color(0x2f4f4fff.toInt()),
|
||||||
|
"darkturquoise" to Color(0x00ced1ff.toInt()),
|
||||||
|
"darkviolet" to Color(0x9400d3ff.toInt()),
|
||||||
|
"deeppink" to Color(0xff1493ff.toInt()),
|
||||||
|
"deepskyblue" to Color(0x00bfffff.toInt()),
|
||||||
|
"dimgray" to Color(0x696969ff.toInt()),
|
||||||
|
"dimgrey" to Color(0x696969ff.toInt()),
|
||||||
|
"dodgerblue" to Color(0x1e90ffff.toInt()),
|
||||||
|
"firebrick" to Color(0xb22222ff.toInt()),
|
||||||
|
"floralwhite" to Color(0xfffaf0ff.toInt()),
|
||||||
|
"forestgreen" to Color(0x228b22ff.toInt()),
|
||||||
|
"fuchsia" to Color(0xff00ffff.toInt()),
|
||||||
|
"gainsboro" to Color(0xdcdcdcff.toInt()),
|
||||||
|
"ghostwhite" to Color(0xf8f8ffff.toInt()),
|
||||||
|
"gold" to Color(0xffd700ff.toInt()),
|
||||||
|
"goldenrod" to Color(0xdaa520ff.toInt()),
|
||||||
|
"gray" to Color(0x808080ff.toInt()),
|
||||||
|
"green" to Color(0x008000ff.toInt()),
|
||||||
|
"greenyellow" to Color(0xadff2fff.toInt()),
|
||||||
|
"grey" to Color(0x808080ff.toInt()),
|
||||||
|
"honeydew" to Color(0xf0fff0ff.toInt()),
|
||||||
|
"hotpink" to Color(0xff69b4ff.toInt()),
|
||||||
|
"indianred" to Color(0xcd5c5cff.toInt()),
|
||||||
|
"indigo" to Color(0x4b0082ff.toInt()),
|
||||||
|
"ivory" to Color(0xfffff0ff.toInt()),
|
||||||
|
"khaki" to Color(0xf0e68cff.toInt()),
|
||||||
|
"lavender" to Color(0xe6e6faff.toInt()),
|
||||||
|
"lavenderblush" to Color(0xfff0f5ff.toInt()),
|
||||||
|
"lawngreen" to Color(0x7cfc00ff.toInt()),
|
||||||
|
"lemonchiffon" to Color(0xfffacdff.toInt()),
|
||||||
|
"lightblue" to Color(0xadd8e6ff.toInt()),
|
||||||
|
"lightcoral" to Color(0xf08080ff.toInt()),
|
||||||
|
"lightcyan" to Color(0xe0ffffff.toInt()),
|
||||||
|
"lightgoldenrodyellow" to Color(0xfafad2ff.toInt()),
|
||||||
|
"lightgray" to Color(0xd3d3d3ff.toInt()),
|
||||||
|
"lightgreen" to Color(0x90ee90ff.toInt()),
|
||||||
|
"lightgrey" to Color(0xd3d3d3ff.toInt()),
|
||||||
|
"lightpink" to Color(0xffb6c1ff.toInt()),
|
||||||
|
"lightsalmon" to Color(0xffa07aff.toInt()),
|
||||||
|
"lightseagreen" to Color(0x20b2aaff.toInt()),
|
||||||
|
"lightskyblue" to Color(0x87cefaff.toInt()),
|
||||||
|
"lightslategray" to Color(0x778899ff.toInt()),
|
||||||
|
"lightslategrey" to Color(0x778899ff.toInt()),
|
||||||
|
"lightsteelblue" to Color(0xb0c4deff.toInt()),
|
||||||
|
"lightyellow" to Color(0xffffe0ff.toInt()),
|
||||||
|
"lime" to Color(0x00ff00ff.toInt()),
|
||||||
|
"limegreen" to Color(0x32cd32ff.toInt()),
|
||||||
|
"linen" to Color(0xfaf0e6ff.toInt()),
|
||||||
|
"magenta" to Color(0xff00ffff.toInt()),
|
||||||
|
"maroon" to Color(0x800000ff.toInt()),
|
||||||
|
"mediumaquamarine" to Color(0x66cdaaff.toInt()),
|
||||||
|
"mediumblue" to Color(0x0000cdff.toInt()),
|
||||||
|
"mediumorchid" to Color(0xba55d3ff.toInt()),
|
||||||
|
"mediumpurple" to Color(0x9370dbff.toInt()),
|
||||||
|
"mediumseagreen" to Color(0x3cb371ff.toInt()),
|
||||||
|
"mediumslateblue" to Color(0x7b68eeff.toInt()),
|
||||||
|
"mediumspringgreen" to Color(0x00fa9aff.toInt()),
|
||||||
|
"mediumturquoise" to Color(0x48d1ccff.toInt()),
|
||||||
|
"mediumvioletred" to Color(0xc71585ff.toInt()),
|
||||||
|
"midnightblue" to Color(0x191970ff.toInt()),
|
||||||
|
"mintcream" to Color(0xf5fffaff.toInt()),
|
||||||
|
"mistyrose" to Color(0xffe4e1ff.toInt()),
|
||||||
|
"moccasin" to Color(0xffe4b5ff.toInt()),
|
||||||
|
"navajowhite" to Color(0xffdeadff.toInt()),
|
||||||
|
"navy" to Color(0x000080ff.toInt()),
|
||||||
|
"oldlace" to Color(0xfdf5e6ff.toInt()),
|
||||||
|
"olive" to Color(0x808000ff.toInt()),
|
||||||
|
"olivedrab" to Color(0x6b8e23ff.toInt()),
|
||||||
|
"orange" to Color(0xffa500ff.toInt()),
|
||||||
|
"orangered" to Color(0xff4500ff.toInt()),
|
||||||
|
"orchid" to Color(0xda70d6ff.toInt()),
|
||||||
|
"palegoldenrod" to Color(0xeee8aaff.toInt()),
|
||||||
|
"palegreen" to Color(0x98fb98ff.toInt()),
|
||||||
|
"paleturquoise" to Color(0xafeeeeff.toInt()),
|
||||||
|
"palevioletred" to Color(0xdb7093ff.toInt()),
|
||||||
|
"papayawhip" to Color(0xffefd5ff.toInt()),
|
||||||
|
"peachpuff" to Color(0xffdab9ff.toInt()),
|
||||||
|
"peru" to Color(0xcd853fff.toInt()),
|
||||||
|
"pink" to Color(0xffc0cbff.toInt()),
|
||||||
|
"plum" to Color(0xdda0ddff.toInt()),
|
||||||
|
"powderblue" to Color(0xb0e0e6ff.toInt()),
|
||||||
|
"purple" to Color(0x800080ff.toInt()),
|
||||||
|
"rebeccapurple" to Color(0x663399ff.toInt()),
|
||||||
|
"red" to Color(0xff0000ff.toInt()),
|
||||||
|
"rosybrown" to Color(0xbc8f8fff.toInt()),
|
||||||
|
"royalblue" to Color(0x4169e1ff.toInt()),
|
||||||
|
"saddlebrown" to Color(0x8b4513ff.toInt()),
|
||||||
|
"salmon" to Color(0xfa8072ff.toInt()),
|
||||||
|
"sandybrown" to Color(0xf4a460ff.toInt()),
|
||||||
|
"seagreen" to Color(0x2e8b57ff.toInt()),
|
||||||
|
"seashell" to Color(0xfff5eeff.toInt()),
|
||||||
|
"sienna" to Color(0xa0522dff.toInt()),
|
||||||
|
"silver" to Color(0xc0c0c0ff.toInt()),
|
||||||
|
"skyblue" to Color(0x87ceebff.toInt()),
|
||||||
|
"slateblue" to Color(0x6a5acdff.toInt()),
|
||||||
|
"slategray" to Color(0x708090ff.toInt()),
|
||||||
|
"slategrey" to Color(0x708090ff.toInt()),
|
||||||
|
"snow" to Color(0xfffafaff.toInt()),
|
||||||
|
"springgreen" to Color(0x00ff7fff.toInt()),
|
||||||
|
"steelblue" to Color(0x4682b4ff.toInt()),
|
||||||
|
"tan" to Color(0xd2b48cff.toInt()),
|
||||||
|
"teal" to Color(0x008080ff.toInt()),
|
||||||
|
"thistle" to Color(0xd8bfd8ff.toInt()),
|
||||||
|
"tomato" to Color(0xff6347ff.toInt()),
|
||||||
|
"transparent" to Color(0),
|
||||||
|
"turquoise" to Color(0x40e0d0ff.toInt()),
|
||||||
|
"violet" to Color(0xee82eeff.toInt()),
|
||||||
|
"wheat" to Color(0xf5deb3ff.toInt()),
|
||||||
|
"white" to Color(0xffffffff.toInt()),
|
||||||
|
"whitesmoke" to Color(0xf5f5f5ff.toInt()),
|
||||||
|
"yellow" to Color(0xffff00ff.toInt()),
|
||||||
|
"yellowgreen" to Color(0x9acd32ff.toInt())
|
||||||
)
|
)
|
||||||
|
|
||||||
private val pageWidthMap = hashMapOf(
|
private val pageWidthMap = hashMapOf(
|
||||||
@@ -239,14 +452,35 @@ object BTeXParser {
|
|||||||
// TODO add post-parsing hook to the handler
|
// TODO add post-parsing hook to the handler
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
|
fun processElemBTEX(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
||||||
|
handler.paragraphBuffer.append("BTeX")
|
||||||
|
}
|
||||||
|
|
||||||
@OpenTag // reflective access is impossible with 'private'
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
fun processElemBR(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
fun processElemCOVER(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
||||||
|
doc.addNewPage(Color(0x6f4a45ff))
|
||||||
|
}
|
||||||
|
|
||||||
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
|
fun processElemTOC(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
||||||
|
doc.addNewPage()
|
||||||
|
}
|
||||||
|
|
||||||
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
|
fun processElemMANUSCRIPT(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
||||||
|
doc.addNewPage()
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
|
fun processElemBR(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
||||||
|
handler.paragraphBuffer.append("\n")
|
||||||
}
|
}
|
||||||
|
|
||||||
@OpenTag // reflective access is impossible with 'private'
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
@@ -256,12 +490,63 @@ object BTeXParser {
|
|||||||
|
|
||||||
@OpenTag // reflective access is impossible with 'private'
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
fun processElemP(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
fun processElemP(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String, attribs: HashMap<String, String>) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@CloseTag // reflective access is impossible with 'private'
|
@CloseTag // reflective access is impossible with 'private'
|
||||||
fun closeElemP(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String) {
|
fun closeElemP(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String) {
|
||||||
|
printdbg("Par: ${handler.paragraphBuffer}")
|
||||||
|
|
||||||
|
val font = getFont()
|
||||||
|
val slugs = MovableType(font, handler.paragraphBuffer.toString(), doc.pageWidth)
|
||||||
|
|
||||||
|
|
||||||
|
var remainder = doc.pageLines - doc.currentLine
|
||||||
|
var slugHeight = slugs.height
|
||||||
|
var linesOut = 0
|
||||||
|
|
||||||
|
if (slugHeight > remainder) {
|
||||||
|
val subset = linesOut to linesOut + remainder
|
||||||
|
|
||||||
|
val drawCall = BTeXDrawCall(
|
||||||
|
0,
|
||||||
|
remainder * doc.pageLines,
|
||||||
|
handler.currentTheme,
|
||||||
|
handler.getSpanColour(),
|
||||||
|
MovableTypeDrawCall(slugs, subset.first, subset.second)
|
||||||
|
)
|
||||||
|
|
||||||
|
doc.appendDrawCall(drawCall)
|
||||||
|
|
||||||
|
linesOut += remainder
|
||||||
|
slugHeight -= remainder
|
||||||
|
|
||||||
|
doc.addNewPage()
|
||||||
|
}
|
||||||
|
|
||||||
|
while (slugHeight > 0) {
|
||||||
|
remainder = minOf(slugHeight, doc.pageLines)
|
||||||
|
|
||||||
|
val subset = linesOut to linesOut + remainder
|
||||||
|
|
||||||
|
val drawCall = BTeXDrawCall(
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
handler.currentTheme,
|
||||||
|
handler.getSpanColour(),
|
||||||
|
MovableTypeDrawCall(slugs, subset.first, subset.second)
|
||||||
|
)
|
||||||
|
|
||||||
|
doc.appendDrawCall(drawCall)
|
||||||
|
|
||||||
|
linesOut += remainder
|
||||||
|
slugHeight -= remainder
|
||||||
|
|
||||||
|
if (remainder == doc.pageLines) {
|
||||||
|
doc.addNewPage()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
handler.paragraphBuffer.clear()
|
||||||
}
|
}
|
||||||
|
|
||||||
@OpenTag // reflective access is impossible with 'private'
|
@OpenTag // reflective access is impossible with 'private'
|
||||||
@@ -275,6 +560,7 @@ object BTeXParser {
|
|||||||
fun closeElemSPAN(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String) {
|
fun closeElemSPAN(handler: BTeXHandler, doc: BTeXDocument, theTag: String, uri: String) {
|
||||||
spanColour = null
|
spanColour = null
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,18 +1,18 @@
|
|||||||
package net.torvald.terrarum.tests
|
package net.torvald.terrarum.tests
|
||||||
|
|
||||||
|
import com.badlogic.gdx.ApplicationAdapter
|
||||||
|
import com.badlogic.gdx.backends.lwjgl3.Lwjgl3Application
|
||||||
|
import com.badlogic.gdx.backends.lwjgl3.Lwjgl3ApplicationConfiguration
|
||||||
|
import com.badlogic.gdx.graphics.glutils.ShaderProgram
|
||||||
import net.torvald.btex.BTeXParser
|
import net.torvald.btex.BTeXParser
|
||||||
import org.xml.sax.Attributes
|
import net.torvald.terrarum.btex.BTeXDocument
|
||||||
import org.xml.sax.HandlerBase
|
|
||||||
import org.xml.sax.helpers.DefaultHandler
|
|
||||||
import java.io.ByteArrayInputStream
|
|
||||||
import java.io.InputStream
|
|
||||||
import javax.xml.parsers.SAXParserFactory
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Created by minjaesong on 2023-10-28.
|
* Created by minjaesong on 2023-10-28.
|
||||||
*/
|
*/
|
||||||
fun main() {
|
class BTeXTest : ApplicationAdapter() {
|
||||||
|
|
||||||
val csiR = "\u001B[31m"
|
val csiR = "\u001B[31m"
|
||||||
val csiG = "\u001B[32m"
|
val csiG = "\u001B[32m"
|
||||||
val csi0 = "\u001B[m"
|
val csi0 = "\u001B[m"
|
||||||
@@ -28,31 +28,43 @@ fun main() {
|
|||||||
|
|
||||||
<manuscript>
|
<manuscript>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>What Is a Book</chapter>
|
<chapter>What Is a Book</chapter>
|
||||||
|
|
||||||
<p>This example book is designed to give you the exampe of the Book Language.</p>
|
<p>This example book is designed to give you the example of the Book Language.</p>
|
||||||
|
|
||||||
<section>What Really Is a Book</section>
|
<section>What Really Is a Book</section>
|
||||||
|
|
||||||
<p>A book is a collection of texts printed in a special way that allows them to be read easily, with
|
<p>A book is a collection of texts printed in a special way that allows them to be read easily, with
|
||||||
enumerable pages and insertion of other helpful resources, such as illustrations and hyperlinks.</p>
|
enumerable pages and insertion of other helpful resources, such as illustrations and hyperlinks.</p>
|
||||||
|
|
||||||
<newpage />
|
<newpage />
|
||||||
|
|
||||||
<fullpagebox>
|
<fullpagebox>
|
||||||
<span colour="grey">
|
<p><span colour="grey">
|
||||||
<p>this page is intentionally left blank</p>
|
this page is intentionally left blank
|
||||||
</span>
|
</span></p>
|
||||||
</fullpagebox>
|
</fullpagebox>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>Writing Book Using Pen and Papers</chapter>
|
<chapter>Writing Book Using Pen and Papers</chapter>
|
||||||
|
|
||||||
<p>If you open a book on a writing table, you will be welcomed with a toolbar used to put other book
|
<p><index id="pen and paper" />If you open a book on a writing table, you will be welcomed with a
|
||||||
elements, such as chapters, sections.</p>
|
toolbar used to put other book elements, such as chapters, sections.</p>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>Writing Book Using Typewriter</chapter>
|
<chapter>Writing Book Using Typewriter</chapter>
|
||||||
|
|
||||||
<p>Typewriters can only write single style of font, therefore chapters and sections are not available.</p>
|
<p><index id="typewriter" />Typewriters can only write single style of font, therefore chapters and
|
||||||
|
sections are not available.</p>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<chapter>Writing Book using Computer</chapter>
|
<chapter>Writing Book using Computer</chapter>
|
||||||
|
|
||||||
@@ -60,21 +72,42 @@ fun main() {
|
|||||||
|
|
||||||
<section>Full Control of the Shape</section>
|
<section>Full Control of the Shape</section>
|
||||||
|
|
||||||
<p>With <btex /> you can fully control how your publishing would look like, from a pile of papers that
|
<p><index id="btex language" />With <btex /> you can fully control how your publishing would look like,
|
||||||
look like they have been typed out using typewriter, a pile of papers but a fully-featured printouts that
|
from a pile of papers that look like they have been typed out using typewriter, a pile of papers but a
|
||||||
have illustrations in it, to a fully-featured hardcover book.</p>
|
fully-featured printouts that have illustrations in it, to a fully-featured hardcover book.</p>
|
||||||
|
|
||||||
<p>This style is controlled using the <code>cover</code> attribute on the root tag, with following
|
<p><index id="cover" />This style is controlled using the <code>cover</code> attribute on the root tag,
|
||||||
values: <code>typewriter</code>, <code>printout</code>, <code>hardcover</code></p>
|
with following values: <code>typewriter</code>, <code>printout</code>, <code>hardcover</code></p>
|
||||||
|
|
||||||
<p>Typewriter and Printout are considered not bound and readers will only see one page at a time,
|
<p>Typewriter and Printout are considered not bound and readers will only see one page at a time,
|
||||||
while Hardcover is considered bound and two pages are presented to the readers.</p>
|
while Hardcover is considered bound and two pages are presented to the readers.</p>
|
||||||
|
|
||||||
</manuscript>
|
</manuscript>
|
||||||
</btexdoc>
|
|
||||||
|
|
||||||
|
<indexpage><tableofindices /></indexpage>
|
||||||
|
</btexdoc>
|
||||||
|
|
||||||
"""
|
"""
|
||||||
|
|
||||||
val doku = BTeXParser(tex)
|
private lateinit var document: BTeXDocument
|
||||||
|
|
||||||
|
override fun create() {
|
||||||
|
document = BTeXParser.invoke(tex)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
fun main() {
|
||||||
|
ShaderProgram.pedantic = false
|
||||||
|
|
||||||
|
val appConfig = Lwjgl3ApplicationConfiguration()
|
||||||
|
appConfig.useVsync(false)
|
||||||
|
appConfig.setResizable(false)
|
||||||
|
appConfig.setWindowedMode(1280, 720)
|
||||||
|
appConfig.setForegroundFPS(60)
|
||||||
|
appConfig.setOpenGLEmulation(Lwjgl3ApplicationConfiguration.GLEmulation.GL30, 3, 2)
|
||||||
|
|
||||||
|
Lwjgl3Application(BTeXTest(), appConfig)
|
||||||
}
|
}
|
||||||
Reference in New Issue
Block a user