fancy error printing done

This commit is contained in:
alexander.nutz
2024-03-29 12:21:09 +01:00
parent 355289716b
commit 19414c084c
12 changed files with 439 additions and 31 deletions

View File

@@ -0,0 +1,21 @@
package blitz.str
import blitz.term.AnsiiMode
import blitz.term.Terminal
class ColoredChar(
val char: Char,
val style: AnsiiMode = AnsiiMode(mutableListOf())
) {
override fun equals(other: Any?): Boolean =
char == other
override fun hashCode(): Int =
char.hashCode()
override fun toString(): String =
Terminal.encodeString("$char", style)
}
fun Iterable<ColoredChar>.convToString(): String =
joinToString(separator = "")

View File

@@ -0,0 +1,109 @@
package blitz.str
import blitz.term.AnsiiMode
class MutMultiColoredMultiLineString(
var fill: ColoredChar
) {
val lines = mutableListOf<MutMultiColoredString>()
// TODO: wrap at \n
override fun equals(other: Any?): Boolean =
lines == other
override fun hashCode(): Int =
lines.hashCode()
/** if out of bounds, extends with @see fill */
operator fun get(row: Int, col: Int): ColoredChar {
if (row >= lines.size) {
repeat(row - lines.size + 1) {
lines.add(MutMultiColoredString(fill = fill))
}
}
return lines[row][col]
}
/** if out of bounds, extends with @see fill */
operator fun get(row: Int): MutMultiColoredString {
if (row >= lines.size) {
repeat(row - lines.size + 1) {
lines.add(MutMultiColoredString(fill = fill))
}
}
return lines[row]
}
/** if out of bounds, extends with @see fill */
operator fun set(row: Int, col: Int, value: ColoredChar) {
if (row >= lines.size) {
repeat(row - lines.size + 1) {
lines.add(MutMultiColoredString(fill = fill))
}
} else {
lines[row].fill = fill
}
lines[row][col] = value
}
/** if out of bounds, extends with @see fill */
operator fun set(row: Int, col: Int, value: Char) =
set(row, col, ColoredChar(value))
/** if out of bounds, extends with @see fill */
operator fun set(row: Int, colStart: Int, value: CharSequence) {
if (row >= lines.size) {
repeat(row - lines.size + 1) {
lines.add(MutMultiColoredString(fill = fill))
}
} else {
lines[row].fill = fill
}
lines[row][colStart] = value
}
/** if out of bounds, extends with @see fill */
operator fun set(row: Int, colStart: Int, value: MutMultiColoredString) {
if (row >= lines.size) {
repeat(row - lines.size + 1) {
lines.add(MutMultiColoredString(fill = fill))
}
} else {
lines[row].fill = fill
}
lines[row][colStart] = value
}
/** if out of bounds, extends with @see fill */
fun set(row: Int, colStart: Int, va: Char, style: AnsiiMode) =
set(row, colStart, ColoredChar(va, style))
/** if out of bounds, extends with @see fill */
fun set(row: Int, colStart: Int, va: String, style: AnsiiMode) =
set(row, colStart, MutMultiColoredString.from(va, style))
/** if out of bounds, extends with @see fill */
operator fun set(rowStart: Int, colStart: Int, value: MutMultiLineString) {
value.lines.forEachIndexed { index, line ->
this[index + rowStart, colStart] = line
}
}
/** if out of bounds, extends with @see fill */
operator fun set(rowStart: Int, colStart: Int, value: MutMultiLineString, style: AnsiiMode) {
value.lines.forEachIndexed { index, line ->
this.set(index + rowStart, colStart, line.toString(), style)
}
}
/** if out of bounds, extends with @see fill */
operator fun set(rowStart: Int, colStart: Int, value: MutMultiColoredMultiLineString) {
value.lines.forEachIndexed { index, line ->
this[index + rowStart, colStart] = line
}
}
override fun toString(): String =
lines.joinToString(separator = "\n")
}

View File

@@ -0,0 +1,92 @@
package blitz.str
import blitz.collections.mergeNeighbors
import blitz.term.AnsiiMode
import blitz.term.Terminal
class MutMultiColoredString(var fill: ColoredChar) {
val chars = mutableListOf<ColoredChar>()
val length
get() = chars.size
override fun equals(other: Any?): Boolean =
chars == other
override fun hashCode(): Int =
chars.hashCode()
override fun toString(): String {
val byColors = chars.mergeNeighbors { it.style }
val res = MutString(fill = ' ')
byColors.forEach {
val style = it.first
val str = it.second.convToString()
res.append(Terminal.encodeString(str, style))
}
return res.toString()
}
fun add(str: String, style: AnsiiMode = AnsiiMode(mutableListOf())) {
str.mapTo(chars) { ColoredChar(it, style) }
}
fun add(str: Iterable<ColoredChar>) {
chars.addAll(str)
}
fun add(ch: ColoredChar) {
chars.add(ch)
}
operator fun get(index: Int): ColoredChar {
if (index >= length) {
repeat(index - length + 1) {
chars.add(fill)
}
}
return chars[index]
}
operator fun set(index: Int, value: ColoredChar) {
if (index >= length) {
repeat(index - length + 1) {
chars.add(fill)
}
}
chars[index] = value
}
fun set(start: Int, str: CharSequence, style: AnsiiMode) {
if (start + str.length >= length) {
repeat(start + str.length - length + 1) {
chars.add(fill)
}
}
str.forEachIndexed { index, c ->
chars[start + index] = ColoredChar(c, style)
}
}
operator fun set(start: Int, str: CharSequence) {
set(start, str, AnsiiMode(mutableListOf()))
}
operator fun set(start: Int, str: MutMultiColoredString) {
if (start + str.length >= length) {
repeat(start + str.length - length + 1) {
chars.add(fill)
}
}
str.chars.forEachIndexed { index, c ->
chars[start + index] = c
}
}
companion object {
fun from(str: String, style: AnsiiMode = AnsiiMode(mutableListOf())) =
MutMultiColoredString(fill = ColoredChar(' ')).also {
it.add(str, style)
}
}
}

View File

@@ -7,6 +7,12 @@ class MutMultiLineString(
// TODO: wrap at \n
override fun equals(other: Any?): Boolean =
lines == other
override fun hashCode(): Int =
lines.hashCode()
/** if out of bounds, extends with @see fill */
operator fun get(row: Int, col: Int): Char {
if (row >= lines.size) {

View File

@@ -1,11 +1,19 @@
package blitz.str
import java.util.stream.IntStream
class MutString(
init: String = "",
var fill: Char
): CharSequence, Appendable {
private val builder = StringBuilder(init)
override fun chars(): IntStream =
builder.chars()
override fun codePoints(): IntStream =
builder.codePoints()
override val length: Int
get() = builder.length
@@ -30,12 +38,12 @@ class MutString(
/** if out of bounds, extends with @see fill */
operator fun set(start: Int, str: CharSequence) {
if (start >= length) {
repeat(start - length + 1) {
if (start + str.length >= length) {
repeat(start + str.length - length + 1) {
builder.append(fill)
}
}
builder.insert(start, str)
builder.replace(start, start + str.length, str.toString())
}
override fun toString(): String =