diff --git a/ChangeLog b/ChangeLog index d14b4071..7161d4bb 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,4 +1,8 @@ -2017-11-24 Markus Gans +2017-11-26 Markus Gans + * Better code readability by splitting FOptiMove::moveCursor + into sub-functions + +2017-11-25 Markus Gans * Splitting quirks in serperate methods 2017-11-24 Markus Gans diff --git a/fonts/bdf2c.sh b/fonts/bdf2c.sh index 9e39bfb2..324ae32a 100755 --- a/fonts/bdf2c.sh +++ b/fonts/bdf2c.sh @@ -22,7 +22,7 @@ FONTFILE="8x16graph.bdf" | while IFS=$'\n'; read -r LINE do echo "$LINE /* $N */" - let N++ + (( N++ )) done echo -e "};" diff --git a/fonts/font2c.sh b/fonts/font2c.sh index 1a38d074..3a44bc31 100755 --- a/fonts/font2c.sh +++ b/fonts/font2c.sh @@ -20,7 +20,7 @@ FONTFILE="8x16std" echo "$LINE" else echo "$LINE /* $N */" | sed -e 's/\([0-9]\) \/\*/\1 \/*/' - let N++ + (( N++ )) fi done diff --git a/include/final/foptimove.h b/include/final/foptimove.h index 7ae54c8c..5910085d 100644 --- a/include/final/foptimove.h +++ b/include/final/foptimove.h @@ -121,6 +121,13 @@ class FOptiMove int repeatedAppend (const capability&, int, char*); int relativeMove (char*&, int, int, int, int); bool isWideMove (int, int, int, int); + bool isMethod0Faster (int&, int, int); + bool isMethod1Faster (int&, int, int, int, int); + bool isMethod2Faster (int&, int, int, int); + bool isMethod3Faster (int&, int, int); + bool isMethod4Faster (int&, int, int); + bool isMethod5Faster (int&, int, int, int); + void moveByMethod (int, int, int, int, int); // Data Members capability F_cursor_home; diff --git a/include/final/fterm.h b/include/final/fterm.h index 9593f6a8..13066542 100644 --- a/include/final/fterm.h +++ b/include/final/fterm.h @@ -481,10 +481,14 @@ class FTerm static void init_termcaps_keys (char*&); static void init_OptiMove(); static void init_OptiAttr(); + static void init_font(); static void init_locale(); static void init_encoding(); static void redefineColorPalette(); static void restoreColorPalette(); + static void enableMouse(); + static void disableMouse(); + static void captureXTermFontAndTitle(); void init(); void finish(); static uInt cp437_to_unicode (uChar); diff --git a/scripts/remove_eol_spaces.sh b/scripts/remove_eol_spaces.sh index 791c7c42..c394b7be 100755 --- a/scripts/remove_eol_spaces.sh +++ b/scripts/remove_eol_spaces.sh @@ -4,6 +4,6 @@ find ../src/ \ ../include/final/ \ ../examples/ \ -regextype posix-egrep \ - -regex ".*\.(cpp|h)$" \ + -regex ".*\\.(cpp|h)$" \ -exec sed -i 's/ *$//' "{}" \; diff --git a/scripts/valgrind.sh b/scripts/valgrind.sh index 616f824e..10ceb2d8 100755 --- a/scripts/valgrind.sh +++ b/scripts/valgrind.sh @@ -13,7 +13,7 @@ fi test ! -x "$PROG" && echo "No executable file not found" && exit -1 # ELF executable file? -ELFMAGIC="$(echo -e "\x7fELF")" +ELFMAGIC="$(echo -e "\\x7fELF")" MAGIC="$(dd bs=1 count=4 if="$PROG" 2>/dev/null)" test "$MAGIC" != "$ELFMAGIC" && echo "No ELF executable file" && exit -2 diff --git a/src/foptimove.cpp b/src/foptimove.cpp index a793c263..90ccbdef 100644 --- a/src/foptimove.cpp +++ b/src/foptimove.cpp @@ -488,23 +488,12 @@ int FOptiMove::set_clr_eol (char*& cap) //---------------------------------------------------------------------- char* FOptiMove::moveCursor (int xold, int yold, int xnew, int ynew) { - char null_result[sizeof(move_buf)]; - char* null_ptr = null_result; - char* move_ptr = move_buf; - char* move_xy; - int method = 0 - , new_time - , move_time = LONG_DURATION; + int method = 0; + int move_time = LONG_DURATION; // Method 0: direct cursor addressing - move_xy = tgoto(F_cursor_address.cap, xnew, ynew); - - if ( move_xy ) + if ( isMethod0Faster(move_time, xnew, ynew) ) { - method = 0; - std::strncpy (move_ptr, move_xy, sizeof(move_buf) - 1); - move_time = F_cursor_address.duration; - if ( xold < 0 || yold < 0 || isWideMove (xold, yold, xnew, ynew) ) @@ -514,123 +503,27 @@ char* FOptiMove::moveCursor (int xold, int yold, int xnew, int ynew) } // Method 1: local movement - if ( xold >= 0 && yold >= 0 ) - { - new_time = relativeMove (null_ptr, xold, yold, xnew, ynew); - - if ( new_time < LONG_DURATION && new_time < move_time ) - { - method = 1; - move_time = new_time; - } - } + if ( isMethod1Faster(move_time, xold, yold, xnew, ynew) ) + method = 1; // Method 2: carriage-return + local movement - if ( yold >= 0 && F_carriage_return.cap ) - { - new_time = relativeMove (null_ptr, 0, yold, xnew, ynew); - - if ( new_time < LONG_DURATION - && F_carriage_return.duration + new_time < move_time ) - { - method = 2; - move_time = F_carriage_return.duration + new_time; - } - } + if ( isMethod2Faster(move_time, yold, xnew, ynew) ) + method = 2; // Method 3: home-cursor + local movement - if ( F_cursor_home.cap ) - { - new_time = relativeMove (null_ptr, 0, 0, xnew, ynew); - - if ( new_time < LONG_DURATION - && F_cursor_home.duration + new_time < move_time ) - { - method = 3; - move_time = F_cursor_home.duration + new_time; - } - } + if ( isMethod3Faster(move_time, xnew, ynew) ) + method = 3; // Method 4: home-down + local movement - if ( F_cursor_to_ll.cap ) - { - new_time = relativeMove (null_ptr, 0, screen_height - 1, xnew, ynew); - - if ( new_time < LONG_DURATION - && F_cursor_to_ll.duration + new_time < move_time ) - { - method = 4; - move_time = F_cursor_to_ll.duration + new_time; - } - } + if ( isMethod4Faster(move_time, xnew, ynew) ) + method = 4; // Method 5: left margin for wrap to right-hand side - if ( automatic_left_margin - && ! eat_nl_glitch - && yold > 0 - && F_cursor_left.cap ) - { - new_time = relativeMove (null_ptr, screen_width - 1, yold - 1, xnew, ynew); + if ( isMethod5Faster(move_time, yold, xnew, ynew) ) + method = 5; - if ( new_time < LONG_DURATION - && F_carriage_return.cap - && F_carriage_return.duration - + F_cursor_left.duration + new_time < move_time ) - { - method = 5; - move_time = F_carriage_return.duration - + F_cursor_left.duration + new_time; - } - } - - if ( method ) - { - switch ( method ) - { - case 1: - relativeMove (move_ptr, xold, yold, xnew, ynew); - break; - - case 2: - if ( F_carriage_return.cap ) - { - std::strncpy (move_ptr, F_carriage_return.cap, sizeof(move_buf) - 1); - move_ptr += F_carriage_return.length; - relativeMove (move_ptr, 0, yold, xnew, ynew); - } - break; - - case 3: - std::strncpy (move_ptr, F_cursor_home.cap, sizeof(move_buf) - 1); - move_ptr += F_cursor_home.length; - relativeMove (move_ptr, 0, 0, xnew, ynew); - break; - - case 4: - std::strncpy (move_ptr, F_cursor_to_ll.cap, sizeof(move_buf) - 1); - move_ptr += F_cursor_to_ll.length; - relativeMove (move_ptr, 0, screen_height - 1, xnew, ynew); - break; - - case 5: - move_buf[0] = '\0'; - - if ( xold >= 0 ) - std::strncat ( move_ptr - , F_carriage_return.cap - , sizeof(move_buf) - std::strlen(move_ptr) - 1 ); - - std::strncat ( move_ptr - , F_cursor_left.cap - , sizeof(move_buf) - std::strlen(move_ptr) - 1 ); - move_ptr += std::strlen(move_buf); - relativeMove (move_ptr, screen_width - 1, yold - 1, xnew, ynew); - break; - - default: - break; - } - } + // Copy the escape sequence for the chosen method in move_buf + moveByMethod (method, xold, yold, xnew, ynew); if ( move_time < LONG_DURATION ) return move_buf; @@ -989,3 +882,200 @@ inline bool FOptiMove::isWideMove ( int xold, int yold && std::abs(xnew - xold) + std::abs(ynew - yold) > MOVE_LIMIT ); } + +//---------------------------------------------------------------------- +inline bool FOptiMove::isMethod0Faster ( int& move_time + , int xnew, int ynew ) +{ + // Test method 0: direct cursor addressing + char* move_xy = tgoto(F_cursor_address.cap, xnew, ynew); + + if ( move_xy ) + { + char* move_ptr = move_buf; + std::strncpy (move_ptr, move_xy, sizeof(move_buf) - 1); + move_time = F_cursor_address.duration; + return true; + } + + return false; +} + +//---------------------------------------------------------------------- +inline bool FOptiMove::isMethod1Faster ( int& move_time + , int xold, int yold + , int xnew, int ynew ) +{ + // Test method 1: local movement + + if ( xold >= 0 && yold >= 0 ) + { + char null_result[sizeof(move_buf)]; + char* null_ptr = null_result; + int new_time = relativeMove (null_ptr, xold, yold, xnew, ynew); + + if ( new_time < LONG_DURATION && new_time < move_time ) + { + move_time = new_time; + return true; + } + } + + return false; +} + +//---------------------------------------------------------------------- +inline bool FOptiMove::isMethod2Faster ( int& move_time + , int yold + , int xnew, int ynew ) +{ + // Test method 2: carriage-return + local movement + + if ( yold >= 0 && F_carriage_return.cap ) + { + char null_result[sizeof(move_buf)]; + char* null_ptr = null_result; + int new_time = relativeMove (null_ptr, 0, yold, xnew, ynew); + + if ( new_time < LONG_DURATION + && F_carriage_return.duration + new_time < move_time ) + { + move_time = F_carriage_return.duration + new_time; + return true; + } + } + + return false; +} + +//---------------------------------------------------------------------- +inline bool FOptiMove::isMethod3Faster ( int& move_time + , int xnew, int ynew ) +{ + // Test method 3: home-cursor + local movement + + if ( F_cursor_home.cap ) + { + char null_result[sizeof(move_buf)]; + char* null_ptr = null_result; + int new_time = relativeMove (null_ptr, 0, 0, xnew, ynew); + + if ( new_time < LONG_DURATION + && F_cursor_home.duration + new_time < move_time ) + { + move_time = F_cursor_home.duration + new_time; + return true; + } + } + + return false; +} + +//---------------------------------------------------------------------- +inline bool FOptiMove::isMethod4Faster ( int& move_time + , int xnew, int ynew ) +{ + // Test method 4: home-down + local movement + if ( F_cursor_to_ll.cap ) + { + char null_result[sizeof(move_buf)]; + char* null_ptr = null_result; + int new_time = relativeMove ( null_ptr + , 0, screen_height - 1 + , xnew, ynew ); + + if ( new_time < LONG_DURATION + && F_cursor_to_ll.duration + new_time < move_time ) + { + move_time = F_cursor_to_ll.duration + new_time; + return true; + } + } + + return false; +} + +//---------------------------------------------------------------------- +inline bool FOptiMove::isMethod5Faster ( int& move_time + , int yold + , int xnew, int ynew ) +{ + // Test method 5: left margin for wrap to right-hand side + if ( automatic_left_margin + && ! eat_nl_glitch + && yold > 0 + && F_cursor_left.cap ) + { + char null_result[sizeof(move_buf)]; + char* null_ptr = null_result; + int new_time = relativeMove ( null_ptr + , screen_width - 1, yold - 1 + , xnew, ynew ); + + if ( new_time < LONG_DURATION + && F_carriage_return.cap + && F_carriage_return.duration + + F_cursor_left.duration + new_time < move_time ) + { + move_time = F_carriage_return.duration + + F_cursor_left.duration + new_time; + return true; + } + } + + return false; +} + +//---------------------------------------------------------------------- +void FOptiMove::moveByMethod ( int method + , int xold, int yold + , int xnew, int ynew ) +{ + char* move_ptr = move_buf; + + switch ( method ) + { + case 1: + relativeMove (move_ptr, xold, yold, xnew, ynew); + break; + + case 2: + if ( F_carriage_return.cap ) + { + std::strncpy (move_ptr, F_carriage_return.cap, sizeof(move_buf) - 1); + move_ptr += F_carriage_return.length; + relativeMove (move_ptr, 0, yold, xnew, ynew); + } + break; + + case 3: + std::strncpy (move_ptr, F_cursor_home.cap, sizeof(move_buf) - 1); + move_ptr += F_cursor_home.length; + relativeMove (move_ptr, 0, 0, xnew, ynew); + break; + + case 4: + std::strncpy (move_ptr, F_cursor_to_ll.cap, sizeof(move_buf) - 1); + move_ptr += F_cursor_to_ll.length; + relativeMove (move_ptr, 0, screen_height - 1, xnew, ynew); + break; + + case 5: + move_buf[0] = '\0'; + + if ( xold >= 0 ) + std::strncat ( move_ptr + , F_carriage_return.cap + , sizeof(move_buf) - std::strlen(move_ptr) - 1 ); + + std::strncat ( move_ptr + , F_cursor_left.cap + , sizeof(move_buf) - std::strlen(move_ptr) - 1 ); + move_ptr += std::strlen(move_buf); + relativeMove (move_ptr, screen_width - 1, yold - 1, xnew, ynew); + break; + + default: + break; + } +} diff --git a/src/fterm.cpp b/src/fterm.cpp index 0592b00a..a408bd8b 100644 --- a/src/fterm.cpp +++ b/src/fterm.cpp @@ -3518,7 +3518,7 @@ static void FTerm::init_termcaps_freebsd_quirks() "%?%p9%t\016%e\017%;"); FTermcap::attr_without_color = 18; -} +} #endif //---------------------------------------------------------------------- @@ -4015,6 +4015,26 @@ void FTerm::init_OptiAttr() opti_attr->init(); } +//---------------------------------------------------------------------- +void FTerm::init_font() +{ + if ( init_values.vgafont ) + { + bool ret = setVGAFont(); + + if ( ! ret ) + exitWithMessage ("VGAfont is not supported by this terminal"); + } + + if ( init_values.newfont ) + { + bool ret = setNewFont(); + + if ( ! ret ) + exitWithMessage ("Newfont is not supported by this terminal"); + } +} + //---------------------------------------------------------------------- void FTerm::init_locale() { @@ -4197,6 +4217,54 @@ void FTerm::restoreColorPalette() } } +//---------------------------------------------------------------------- +void FTerm::enableMouse() +{ +#ifdef F_HAVE_LIBGPM + // Enable the linux general purpose mouse (gpm) server + gpm_mouse_enabled = enableGpmMouse(); +#endif + + // Enable xterm mouse support + if ( TCAP(fc::t_key_mouse) && ! linux_terminal ) + { + mouse_support = true; + enableXTermMouse(); + } +} + +//---------------------------------------------------------------------- +void FTerm::disableMouse() +{ + // Disable xterm mouse support + if ( mouse_support ) + disableXTermMouse(); + +#ifdef F_HAVE_LIBGPM + // Disable the linux general purpose mouse (gpm) server + if ( gpm_mouse_enabled ) + disableGpmMouse(); +#endif +} + +//---------------------------------------------------------------------- +void FTerm::captureXTermFontAndTitle() +{ + if ( (xterm_terminal || urxvt_terminal) && ! rxvt_terminal ) + { + struct termios t; + tcgetattr (stdin_no, &t); + t.c_lflag &= uInt(~(ICANON | ECHO)); + tcsetattr (stdin_no, TCSANOW, &t); + + xterm_font = getXTermFont(); + xterm_title = getXTermTitle(); + + t.c_lflag |= uInt(ICANON | ECHO); + tcsetattr (stdin_no, TCSADRAIN, &t); + } +} + //---------------------------------------------------------------------- void FTerm::init() { @@ -4238,18 +4306,24 @@ void FTerm::init() term_name[0] = '\0'; #if defined(__linux__) + // initialize Linux console initLinuxConsole(); + #endif #if defined(__FreeBSD__) || defined(__DragonFly__) + // Initialize BSD console initFreeBSDConsole(); + #endif #if defined(__NetBSD__) || defined(__OpenBSD__) + // Initialize wscons console initWSConsConsole(); + #endif // Save termios settings @@ -4283,19 +4357,8 @@ void FTerm::init() if ( init_values.encoding != fc::UNKNOWN ) setEncoding(init_values.encoding); -#ifdef F_HAVE_LIBGPM - - // Enable the linux general purpose mouse (gpm) server - gpm_mouse_enabled = enableGpmMouse(); - -#endif - - // xterm mouse support - if ( TCAP(fc::t_key_mouse) && ! linux_terminal ) - { - mouse_support = true; - enableXTermMouse(); - } + // Enable the terminal mouse support + enableMouse(); // activate meta key sends escape if ( xterm_terminal ) @@ -4329,19 +4392,8 @@ void FTerm::init() std::fflush(stdout); } - if ( (xterm_terminal || urxvt_terminal) && ! rxvt_terminal ) - { - struct termios t; - tcgetattr (stdin_no, &t); - t.c_lflag &= uInt(~(ICANON | ECHO)); - tcsetattr (stdin_no, TCSANOW, &t); - - xterm_font = getXTermFont(); - xterm_title = getXTermTitle(); - - t.c_lflag |= uInt(ICANON | ECHO); - tcsetattr (stdin_no, TCSADRAIN, &t); - } + // Save the used xterm font and window title + captureXTermFontAndTitle(); if ( kde_konsole ) setKDECursor(fc::UnderlineCursor); @@ -4365,21 +4417,9 @@ void FTerm::init() if ( ! init_values.cursor_optimisation ) setCursorOptimisation (false); - if ( init_values.vgafont ) - { - bool ret = setVGAFont(); - - if ( ! ret ) - exitWithMessage ("VGAfont is not supported by this terminal"); - } - - if ( init_values.newfont ) - { - bool ret = setNewFont(); - - if ( ! ret ) - exitWithMessage ("Newfont is not supported by this terminal"); - } + // Activate the VGA or the new graphic font + // (depending on the initialization values) + init_font(); // turn off hardware echo noHardwareEcho(); @@ -4458,21 +4498,13 @@ void FTerm::finish() resetBeep(); - // Disable xterm mouse support - if ( mouse_support ) - disableXTermMouse(); + // Disable the terminal mouse support + disableMouse(); // Deactivate meta key sends escape if ( xterm_terminal ) xtermMetaSendsESC(false); -#ifdef F_HAVE_LIBGPM - - if ( gpm_mouse_enabled ) - disableGpmMouse(); // Disable gpm server - -#endif - // restores the screen and the cursor position if ( use_alternate_screen && TCAP(fc::t_exit_ca_mode) ) {