Class TerminalTextUtils

java.lang.Object
com.googlecode.lanterna.TerminalTextUtils

public class TerminalTextUtils extends Object
This class contains a number of utility methods for analyzing characters and strings in a terminal context. The main purpose is to make it easier to work with text that may or may not contain double-width text characters, such as CJK (Chinese, Japanese, Korean) and other special symbols. This class assumes those are all double-width and in case the terminal (-emulator) chooses to draw them (somehow) as single-column then all the calculations in this class will be wrong. It seems safe to assume what this class considers double-width really is taking up two columns though.
  • Constructor Summary

    Constructors
    Modifier
    Constructor
    Description
    private
     
  • Method Summary

    Modifier and Type
    Method
    Description
    static String
    fitString(String string, int availableColumnSpace)
    Given a string that may or may not contain CJK characters, returns the substring which will fit inside availableColumnSpace columns.
    static String
    fitString(String string, int fromColumn, int availableColumnSpace)
    Given a string that may or may not contain CJK characters, returns the substring which will fit inside availableColumnSpace columns.
    static String
    getANSIControlSequenceAt(String string, int index)
    Given a string and an index in that string, returns the ANSI control sequence beginning on this index.
    static int
    Given a string and an index in that string, returns the number of characters starting at index that make up a complete ANSI control sequence.
    static int
    getColumnIndex(String s, int stringCharacterIndex)
    Given a string and a character index inside that string, find out what the column index of that character would be if printed in a terminal.
    static int
    getColumnIndex(String s, int stringCharacterIndex, TabBehaviour tabBehaviour, int firstCharacterColumnPosition)
    Given a string and a character index inside that string, find out what the column index of that character would be if printed in a terminal.
    static int
    Given a string, returns how many columns this string would need to occupy in a terminal, taking into account that CJK characters takes up two columns.
    static int
    getStringCharacterIndex(String s, int columnIndex)
    This method does the reverse of getColumnIndex, given a String and imagining it has been printed out to the top-left corner of a terminal, in the column specified by columnIndex, what is the index of that character in the string.
    static List<String>
    getWordWrappedText(int maxWidth, String... lines)
    This method will calculate word wrappings given a number of lines of text and how wide the text can be printed.
    static boolean
    isCharCJK(char c)
    Given a character, is this character considered to be a CJK character? Shamelessly stolen from StackOverflow where it was contributed by user Rakesh N
    static boolean
    Checks if a character is expected to be taking up two columns if printed to a terminal.
    static boolean
    isCharThai(char c)
    Given a character, is this character considered to be a Thai character?
    static boolean
    Checks if a particular character is a control character, in Lanterna this currently means it's 0-31 or 127 in the ascii table.
    static boolean
    Checks if a particular character is printable.
    private static Integer[]
     
    static void
    updateModifiersFromCSICode(String controlSequence, StyleSet<?> target, StyleSet<?> original)
     

    Methods inherited from class java.lang.Object

    clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
  • Constructor Details

    • TerminalTextUtils

      private TerminalTextUtils()
  • Method Details

    • getANSIControlSequenceAt

      public static String getANSIControlSequenceAt(String string, int index)
      Given a string and an index in that string, returns the ANSI control sequence beginning on this index. If there is no control sequence starting there, the method will return null. The returned value is the complete escape sequence including the ESC prefix.
      Parameters:
      string - String to scan for control sequences
      index - Index in the string where the control sequence begins
      Returns:
      null if there was no control sequence starting at the specified index, otherwise the entire control sequence
    • getANSIControlSequenceLength

      public static int getANSIControlSequenceLength(String string, int index)
      Given a string and an index in that string, returns the number of characters starting at index that make up a complete ANSI control sequence. If there is no control sequence starting there, the method will return 0.
      Parameters:
      string - String to scan for control sequences
      index - Index in the string where the control sequence begins
      Returns:
      0 if there was no control sequence starting at the specified index, otherwise the length of the entire control sequence
    • isCharCJK

      public static boolean isCharCJK(char c)
      Given a character, is this character considered to be a CJK character? Shamelessly stolen from StackOverflow where it was contributed by user Rakesh N
      Parameters:
      c - Character to test
      Returns:
      true if the character is a CJK character
    • isCharThai

      public static boolean isCharThai(char c)
      Given a character, is this character considered to be a Thai character?
      Parameters:
      c - Character to test
      Returns:
      true if the character is a Thai character
    • isCharDoubleWidth

      public static boolean isCharDoubleWidth(char c)
      Checks if a character is expected to be taking up two columns if printed to a terminal. This will generally be true for CJK (Chinese, Japanese and Korean) characters. Notice that emoji generally takes up more than a single char and can't be tested properly with this method.
      Parameters:
      c - Character to test if it's double-width when printed to a terminal
      Returns:
      true if this character is expected to be taking up two columns when printed to the terminal, otherwise false
    • isControlCharacter

      public static boolean isControlCharacter(char c)
      Checks if a particular character is a control character, in Lanterna this currently means it's 0-31 or 127 in the ascii table.
      Parameters:
      c - character to test
      Returns:
      true if the character is a control character, false otherwise
    • isPrintableCharacter

      public static boolean isPrintableCharacter(char c)
      Checks if a particular character is printable. This generally means that the code is not a control character that isn't able to be printed to the terminal properly. For example, NULL, ENQ, BELL and ESC and all control codes that has no proper character associated with it so the behaviour is undefined and depends completely on the terminal what happens if you try to print them. However, certain control characters have a particular meaning to the terminal and are as such considered printable. In Lanterna, we consider these control characters printable:
      • Backspace
      • Horizontal Tab
      • Line feed
      Parameters:
      c - character to test
      Returns:
      true if the character is considered printable, false otherwise
    • getColumnWidth

      public static int getColumnWidth(String s)
      Given a string, returns how many columns this string would need to occupy in a terminal, taking into account that CJK characters takes up two columns.
      Parameters:
      s - String to check length
      Returns:
      Number of actual terminal columns the string would occupy
    • getColumnIndex

      public static int getColumnIndex(String s, int stringCharacterIndex) throws StringIndexOutOfBoundsException
      Given a string and a character index inside that string, find out what the column index of that character would be if printed in a terminal. If the string only contains non-CJK characters then the returned value will be same as stringCharacterIndex, but if there are CJK characters the value will be different due to CJK characters taking up two columns in width. If the character at the index in the string is a CJK character itself, the returned value will be the index of the left-side of character. The tab character is counted as four spaces.
      Parameters:
      s - String to translate the index from
      stringCharacterIndex - Index within the string to get the terminal column index of
      Returns:
      Index of the character inside the String at stringCharacterIndex when it has been writted to a terminal
      Throws:
      StringIndexOutOfBoundsException - if the index given is outside the String length or negative
    • getColumnIndex

      public static int getColumnIndex(String s, int stringCharacterIndex, TabBehaviour tabBehaviour, int firstCharacterColumnPosition) throws StringIndexOutOfBoundsException
      Given a string and a character index inside that string, find out what the column index of that character would be if printed in a terminal. If the string only contains non-CJK characters then the returned value will be same as stringCharacterIndex, but if there are CJK characters the value will be different due to CJK characters taking up two columns in width. If the character at the index in the string is a CJK character itself, the returned value will be the index of the left-side of character.
      Parameters:
      s - String to translate the index from
      stringCharacterIndex - Index within the string to get the terminal column index of
      tabBehaviour - The behavior to use when encountering the tab character
      firstCharacterColumnPosition - Where on the screen the first character in the string would be printed, this applies only when you have an alignment-based TabBehaviour
      Returns:
      Index of the character inside the String at stringCharacterIndex when it has been writted to a terminal
      Throws:
      StringIndexOutOfBoundsException - if the index given is outside the String length or negative
    • getStringCharacterIndex

      public static int getStringCharacterIndex(String s, int columnIndex)
      This method does the reverse of getColumnIndex, given a String and imagining it has been printed out to the top-left corner of a terminal, in the column specified by columnIndex, what is the index of that character in the string. If the string contains no CJK characters, this will always be the same as columnIndex. If the index specified is the right column of a CJK character, the index is the same as if the column was the left column. So calling getStringCharacterIndex("英", 0) and getStringCharacterIndex("英", 1) will both return 0.
      Parameters:
      s - String to translate the index to
      columnIndex - Column index of the string written to a terminal
      Returns:
      The index in the string of the character in terminal column columnIndex
    • fitString

      public static String fitString(String string, int availableColumnSpace)
      Given a string that may or may not contain CJK characters, returns the substring which will fit inside availableColumnSpace columns. This method does not handle special cases like tab or new-line.

      Calling this method is the same as calling fitString(string, 0, availableColumnSpace).

      Parameters:
      string - The string to fit inside the availableColumnSpace
      availableColumnSpace - Number of columns to fit the string inside
      Returns:
      The whole or part of the input string which will fit inside the supplied availableColumnSpace
    • fitString

      public static String fitString(String string, int fromColumn, int availableColumnSpace)
      Given a string that may or may not contain CJK characters, returns the substring which will fit inside availableColumnSpace columns. This method does not handle special cases like tab or new-line.

      This overload has a fromColumn parameter that specified where inside the string to start fitting. Please notice that fromColumn is not a character index inside the string, but a column index as if the string has been printed from the left-most side of the terminal. So if the string is "日本語", fromColumn set to 1 will not starting counting from the second character ("本") in the string but from the CJK filler character belonging to "日". If you want to count from a particular character index inside the string, please pass in a substring and use fromColumn set to 0.

      Parameters:
      string - The string to fit inside the availableColumnSpace
      fromColumn - From what column of the input string to start fitting (see description above!)
      availableColumnSpace - Number of columns to fit the string inside
      Returns:
      The whole or part of the input string which will fit inside the supplied availableColumnSpace
    • getWordWrappedText

      public static List<String> getWordWrappedText(int maxWidth, String... lines)
      This method will calculate word wrappings given a number of lines of text and how wide the text can be printed. The result is a list of new rows where word-wrapping was applied.
      Parameters:
      maxWidth - Maximum number of columns that can be used before word-wrapping is applied, if <= 0 then the lines will be returned unchanged
      lines - Input text
      Returns:
      The input text word-wrapped at maxWidth; this may contain more rows than the input text
    • mapCodesToIntegerArray

      private static Integer[] mapCodesToIntegerArray(String[] codes)
    • updateModifiersFromCSICode

      public static void updateModifiersFromCSICode(String controlSequence, StyleSet<?> target, StyleSet<?> original)