diff --git a/ChangeLog b/ChangeLog index 647140f8..462ca5fc 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,7 @@ +2017-04-02 Markus Gans + * Improved cygwin terminal quirks + * Optimized character set switching in FOptiAttr + 2017-03-30 Markus Gans * Added unit test for FOptiMove diff --git a/include/final/foptiattr.h b/include/final/foptiattr.h index 8bdec076..faca1c13 100644 --- a/include/final/foptiattr.h +++ b/include/final/foptiattr.h @@ -169,7 +169,7 @@ class FOptiAttr static bool isNormal (char_data*&); // Methods - void init(); + void initialize(); static short vga2ansi (register short); char* changeAttribute (char_data*&, char_data*&); @@ -272,7 +272,7 @@ class FOptiAttr // Methods bool colorChange (char_data*&, char_data*&); void resetColor (char_data*&); - void prevent_no_color_video_attributes (char_data*&); + void prevent_no_color_video_attributes (char_data*&, bool = false); void preProcessing_cygwin_quirks (char_data*&); void postProcessing_cygwin_quirks (char_data*&, char_data*&); void deactivateAttributes (char_data*&, char_data*&); @@ -284,6 +284,7 @@ class FOptiAttr void resetAttribute (char_data*&); void reset (char_data*&); bool caused_reset_attributes (char[], uChar = all_tests); + bool hasCharsetEquivalence(); void detectSwitchOn (char_data*&, char_data*&); void detectSwitchOff (char_data*&, char_data*&); bool switchOn(); @@ -330,10 +331,12 @@ class FOptiAttr char_data on; char_data off; + char_data reset_byte_mask; int max_color; int attr_without_color; bool ansi_default_color; + bool alt_equal_pc_charset; bool monochron; bool fake_reverse; bool cygwin_terminal; diff --git a/src/foptiattr.cpp b/src/foptiattr.cpp index 31f754b0..f6abbd2a 100644 --- a/src/foptiattr.cpp +++ b/src/foptiattr.cpp @@ -68,15 +68,27 @@ FOptiAttr::FOptiAttr() , F_orig_colors() , on() , off() + , reset_byte_mask() , max_color(1) , attr_without_color(0) , ansi_default_color(false) + , alt_equal_pc_charset(false) , monochron(true) , fake_reverse(false) , cygwin_terminal(false) , attr_ptr(attr_buf) { attr_buf[0] = '\0'; + // Set to 0 to reset + reset_byte_mask.attr.byte[0] = 0; + reset_byte_mask.attr.byte[1] = 0; + reset_byte_mask.attr.byte[2] = 0; + // Set bits that must not be reset + reset_byte_mask.attr.bit.transparent = true; + reset_byte_mask.attr.bit.trans_shadow = true; + reset_byte_mask.attr.bit.inherit_bg = true; + reset_byte_mask.attr.bit.no_changes = true; + reset_byte_mask.attr.bit.printed = true; } //---------------------------------------------------------------------- @@ -442,7 +454,7 @@ bool FOptiAttr::isNormal (char_data*& ch) } //---------------------------------------------------------------------- -void FOptiAttr::init() +void FOptiAttr::initialize() { if ( max_color < 8 ) monochron = true; @@ -483,6 +495,9 @@ void FOptiAttr::init() if ( caused_reset_attributes ( F_exit_standout_mode.cap , all_tests & ~same_like_se) ) F_exit_standout_mode.caused_reset = true; + + if ( hasCharsetEquivalence() ) + alt_equal_pc_charset = true; } //---------------------------------------------------------------------- @@ -525,12 +540,14 @@ short FOptiAttr::vga2ansi (register short color) //---------------------------------------------------------------------- char* FOptiAttr::changeAttribute (char_data*& term, char_data*& next) { + const bool next_has_color = hasColor(next); fake_reverse = false; attr_buf[0] = '\0'; if ( ! (term && next) ) return attr_buf; + prevent_no_color_video_attributes (term, next_has_color); prevent_no_color_video_attributes (next); detectSwitchOn (term, next); detectSwitchOff (term, next); @@ -569,8 +586,10 @@ char* FOptiAttr::changeAttribute (char_data*& term, char_data*& next) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermBold (char_data*& term) { + term->attr.bit.bold = true; + if ( term && append_sequence(F_enter_bold_mode.cap) ) - return (term->attr.bit.bold = true ); + return true; else return false; } @@ -579,18 +598,17 @@ inline bool FOptiAttr::setTermBold (char_data*& term) inline bool FOptiAttr::unsetTermBold (char_data*& term) { // Back to normal intensity (turns off bold + dim) - if ( term && append_sequence(F_exit_bold_mode.cap) ) - { - if ( F_exit_bold_mode.caused_reset ) - reset(term); - else - { - term->attr.bit.bold = false; - term->attr.bit.dim = false; - } - return true; + if ( F_exit_bold_mode.caused_reset ) + reset(term); + else + { + term->attr.bit.bold = false; + term->attr.bit.dim = false; } + + if ( term && append_sequence(F_exit_bold_mode.cap) ) + return true; else return false; } @@ -598,8 +616,10 @@ inline bool FOptiAttr::unsetTermBold (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermDim (char_data*& term) { + term->attr.bit.dim = true; + if ( term && append_sequence(F_enter_dim_mode.cap) ) - return (term->attr.bit.dim = true); + return true; else return false; } @@ -608,18 +628,17 @@ inline bool FOptiAttr::setTermDim (char_data*& term) inline bool FOptiAttr::unsetTermDim (char_data*& term) { // Back to normal intensity (turns off bold + dim) - if ( term && append_sequence(F_exit_dim_mode.cap) ) - { - if ( F_exit_dim_mode.caused_reset ) - reset(term); - else - { - term->attr.bit.bold = false; - term->attr.bit.dim = false; - } - return true; + if ( F_exit_dim_mode.caused_reset ) + reset(term); + else + { + term->attr.bit.bold = false; + term->attr.bit.dim = false; } + + if ( term && append_sequence(F_exit_dim_mode.cap) ) + return true; else return false; } @@ -627,8 +646,10 @@ inline bool FOptiAttr::unsetTermDim (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermItalic (char_data*& term) { + term->attr.bit.italic = true; + if ( term && append_sequence(F_enter_italics_mode.cap) ) - return (term->attr.bit.italic = true); + return true; else return false; } @@ -636,15 +657,13 @@ inline bool FOptiAttr::setTermItalic (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermItalic (char_data*& term) { - if ( term && append_sequence(F_exit_italics_mode.cap) ) - { - if ( F_exit_italics_mode.caused_reset ) - reset(term); - else - term->attr.bit.italic = false; + if ( F_exit_italics_mode.caused_reset ) + reset(term); + else + term->attr.bit.italic = false; + if ( term && append_sequence(F_exit_italics_mode.cap) ) return true; - } else return false; } @@ -652,8 +671,10 @@ inline bool FOptiAttr::unsetTermItalic (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermUnderline (char_data*& term) { + term->attr.bit.underline = true; + if ( term && append_sequence(F_enter_underline_mode.cap) ) - return (term->attr.bit.underline = true); + return true; else return false; } @@ -662,18 +683,16 @@ inline bool FOptiAttr::setTermUnderline (char_data*& term) inline bool FOptiAttr::unsetTermUnderline (char_data*& term) { // Turns off every underlining - if ( term && append_sequence(F_exit_underline_mode.cap) ) + if ( F_exit_underline_mode.caused_reset ) + reset(term); + else { - if ( F_exit_underline_mode.caused_reset ) - reset(term); - else - { - term->attr.bit.underline = false; - term->attr.bit.dbl_underline = false; - } - - return true; + term->attr.bit.underline = false; + term->attr.bit.dbl_underline = false; } + + if ( term && append_sequence(F_exit_underline_mode.cap) ) + return true; else return false; } @@ -681,8 +700,10 @@ inline bool FOptiAttr::unsetTermUnderline (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermBlink (char_data*& term) { + term->attr.bit.blink = true; + if ( term && append_sequence(F_enter_blink_mode.cap) ) - return (term->attr.bit.blink = true); + return true; else return false; } @@ -690,15 +711,13 @@ inline bool FOptiAttr::setTermBlink (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermBlink (char_data*& term) { - if ( term && append_sequence(F_exit_blink_mode.cap) ) - { - if ( F_exit_blink_mode.caused_reset ) - reset(term); - else - term->attr.bit.blink = false; + if ( F_exit_blink_mode.caused_reset ) + reset(term); + else + term->attr.bit.blink = false; + if ( term && append_sequence(F_exit_blink_mode.cap) ) return true; - } else return false; } @@ -706,8 +725,10 @@ inline bool FOptiAttr::unsetTermBlink (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermReverse (char_data*& term) { + term->attr.bit.reverse = true; + if ( term && append_sequence(F_enter_reverse_mode.cap) ) - return (term->attr.bit.reverse = true); + return true; else return false; } @@ -715,15 +736,13 @@ inline bool FOptiAttr::setTermReverse (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermReverse (char_data*& term) { - if ( term && append_sequence(F_exit_reverse_mode.cap) ) - { - if ( F_exit_reverse_mode.caused_reset ) - reset(term); - else - term->attr.bit.reverse = false; + if ( F_exit_reverse_mode.caused_reset ) + reset(term); + else + term->attr.bit.reverse = false; + if ( term && append_sequence(F_exit_reverse_mode.cap) ) return true; - } else return false; } @@ -731,8 +750,10 @@ inline bool FOptiAttr::unsetTermReverse (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermStandout (char_data*& term) { + term->attr.bit.standout = true; + if ( term && append_sequence(F_enter_standout_mode.cap) ) - return (term->attr.bit.standout = true); + return true; else return false; } @@ -740,15 +761,13 @@ inline bool FOptiAttr::setTermStandout (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermStandout (char_data*& term) { - if ( term && append_sequence(F_exit_standout_mode.cap) ) - { - if ( F_exit_standout_mode.caused_reset ) - reset(term); - else - term->attr.bit.standout = false; + if ( F_exit_standout_mode.caused_reset ) + reset(term); + else + term->attr.bit.standout = false; + if ( term && append_sequence(F_exit_standout_mode.cap) ) return true; - } else return false; } @@ -756,8 +775,10 @@ inline bool FOptiAttr::unsetTermStandout (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermInvisible (char_data*& term) { + term->attr.bit.invisible = true; + if ( term && append_sequence(F_enter_secure_mode.cap) ) - return (term->attr.bit.invisible = true); + return true; else return false; } @@ -765,15 +786,13 @@ inline bool FOptiAttr::setTermInvisible (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermInvisible (char_data*& term) { - if ( term && append_sequence(F_exit_secure_mode.cap) ) - { - if ( F_exit_secure_mode.caused_reset ) - reset(term); - else - term->attr.bit.invisible = false; + if ( F_exit_secure_mode.caused_reset ) + reset(term); + else + term->attr.bit.invisible = false; + if ( term && append_sequence(F_exit_secure_mode.cap) ) return true; - } else return false; } @@ -781,8 +800,10 @@ inline bool FOptiAttr::unsetTermInvisible (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermProtected (char_data*& term) { + term->attr.bit.protect = true; + if ( term && append_sequence(F_enter_protected_mode.cap) ) - return (term->attr.bit.protect = true); + return true; else return false; } @@ -790,15 +811,13 @@ inline bool FOptiAttr::setTermProtected (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermProtected (char_data*& term) { - if ( term && append_sequence(F_exit_protected_mode.cap) ) - { - if ( F_exit_protected_mode.caused_reset ) - reset(term); - else - term->attr.bit.protect = false; + if ( F_exit_protected_mode.caused_reset ) + reset(term); + else + term->attr.bit.protect = false; + if ( term && append_sequence(F_exit_protected_mode.cap) ) return true; - } else return false; } @@ -806,8 +825,10 @@ inline bool FOptiAttr::unsetTermProtected (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermCrossedOut (char_data*& term) { + term->attr.bit.crossed_out = true; + if ( term && append_sequence(F_enter_crossed_out_mode.cap) ) - return (term->attr.bit.crossed_out = true); + return true; else return false; } @@ -815,15 +836,13 @@ inline bool FOptiAttr::setTermCrossedOut (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermCrossedOut (char_data*& term) { - if ( term && append_sequence(F_exit_crossed_out_mode.cap) ) - { - if ( F_exit_crossed_out_mode.caused_reset ) - reset(term); - else - term->attr.bit.crossed_out = false; + if ( F_exit_crossed_out_mode.caused_reset ) + reset(term); + else + term->attr.bit.crossed_out = false; + if ( term && append_sequence(F_exit_crossed_out_mode.cap) ) return true; - } else return false; } @@ -831,8 +850,10 @@ inline bool FOptiAttr::unsetTermCrossedOut (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermDoubleUnderline (char_data*& term) { + term->attr.bit.dbl_underline = true; + if ( term && append_sequence(F_enter_dbl_underline_mode.cap) ) - return (term->attr.bit.dbl_underline = true); + return true; else return false; } @@ -841,18 +862,17 @@ inline bool FOptiAttr::setTermDoubleUnderline (char_data*& term) inline bool FOptiAttr::unsetTermDoubleUnderline (char_data*& term) { // Turns off every underlining - if ( term && append_sequence(F_exit_dbl_underline_mode.cap) ) - { - if ( F_exit_dbl_underline_mode.caused_reset ) - reset(term); - else - { - term->attr.bit.underline = false; - term->attr.bit.dbl_underline = false; - } - return true; + if ( F_exit_dbl_underline_mode.caused_reset ) + reset(term); + else + { + term->attr.bit.underline = false; + term->attr.bit.dbl_underline = false; } + + if ( term && append_sequence(F_exit_dbl_underline_mode.cap) ) + return true; else return false; } @@ -867,7 +887,6 @@ bool FOptiAttr::setTermAttributes ( char_data*& term { char* sgr = tparm ( F_set_attributes.cap , p1, p2, p3, p4, p5, p6, p7, p8, p9 ); - append_sequence (sgr); resetColor(term); @@ -894,11 +913,10 @@ bool FOptiAttr::setTermAttributes ( char_data*& term //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermAttributes (char_data*& term) { + reset(term); + if ( term && replace_sequence(F_exit_attribute_mode.cap) ) - { - reset(term); return true; - } else return false; } @@ -906,11 +924,13 @@ inline bool FOptiAttr::unsetTermAttributes (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermAltCharset (char_data*& term) { + term->attr.bit.alt_charset = true; + + if ( alt_equal_pc_charset && term->attr.bit.pc_charset ) + return false; + if ( term && append_sequence(F_enter_alt_charset_mode.cap) ) - { - term->attr.bit.alt_charset = true; return true; - } else return false; } @@ -918,11 +938,13 @@ inline bool FOptiAttr::setTermAltCharset (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermAltCharset (char_data*& term) { + term->attr.bit.alt_charset = false; + + if ( alt_equal_pc_charset && term->attr.bit.pc_charset ) + return false; + if ( term && append_sequence(F_exit_alt_charset_mode.cap) ) - { - term->attr.bit.alt_charset = false; return true; - } else return false; } @@ -930,11 +952,13 @@ inline bool FOptiAttr::unsetTermAltCharset (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::setTermPCcharset (char_data*& term) { + term->attr.bit.pc_charset = true; + + if ( alt_equal_pc_charset && term->attr.bit.alt_charset ) + return false; + if ( term && append_sequence(F_enter_pc_charset_mode.cap) ) - { - term->attr.bit.pc_charset = true; return true; - } else return false; } @@ -942,11 +966,13 @@ inline bool FOptiAttr::setTermPCcharset (char_data*& term) //---------------------------------------------------------------------- inline bool FOptiAttr::unsetTermPCcharset (char_data*& term) { + term->attr.bit.pc_charset = false; + + if ( alt_equal_pc_charset && term->attr.bit.alt_charset ) + return false; + if ( term && append_sequence(F_exit_pc_charset_mode.cap) ) - { - term->attr.bit.pc_charset = false; return true; - } else return false; } @@ -954,27 +980,20 @@ inline bool FOptiAttr::unsetTermPCcharset (char_data*& term) //---------------------------------------------------------------------- bool FOptiAttr::setTermDefaultColor (char_data*& term) { + term->fg_color = Default; + term->bg_color = Default; + if ( ! term ) return false; if ( append_sequence(F_orig_pair.cap) ) - { - term->fg_color = Default; - term->bg_color = Default; return true; - } else if ( append_sequence(F_orig_colors.cap) ) - { - term->fg_color = Default; - term->bg_color = Default; return true; - } else if ( ansi_default_color ) { char sgr_39_49[] = CSI "39;49m"; append_sequence (sgr_39_49); - term->fg_color = Default; - term->bg_color = Default; return true; } else @@ -1101,7 +1120,9 @@ bool FOptiAttr::hasAttribute (char_data*& attr) //---------------------------------------------------------------------- bool FOptiAttr::hasNoAttribute (char_data*& attr) -{ return ! hasAttribute(attr); } +{ + return ! hasAttribute(attr); +} //---------------------------------------------------------------------- inline bool FOptiAttr::colorChange (char_data*& term, char_data*& next) @@ -1127,11 +1148,14 @@ inline void FOptiAttr::resetColor (char_data*& attr) } //---------------------------------------------------------------------- -inline void FOptiAttr::prevent_no_color_video_attributes (char_data*& attr) +inline void FOptiAttr::prevent_no_color_video_attributes ( char_data*& attr + , bool next_has_color ) { // Ignore attributes which can not combined with a color - if ( ! attr || ! hasColor(attr) || attr_without_color <= 0 ) + if ( ! attr + || ! (hasColor(attr) || next_has_color) + || attr_without_color <= 0 ) return; for (int bit = 1; bit < no_mode; bit <<= 1) @@ -1238,9 +1262,6 @@ inline void FOptiAttr::deactivateAttributes ( char_data*& term if ( off.attr.bit.pc_charset ) unsetTermPCcharset(term); - - if ( off.attr.bit.alt_charset ) - unsetTermAltCharset(term); } else setAttributesOff(term); @@ -1254,6 +1275,8 @@ inline void FOptiAttr::deactivateAttributes ( char_data*& term inline void FOptiAttr::changeAttributeSGR ( char_data*& term , char_data*& next ) { + bool pc_charset_usable = true; + if ( switchOn() || switchOff() ) setTermAttributes ( term , next->attr.bit.standout @@ -1266,6 +1289,13 @@ inline void FOptiAttr::changeAttributeSGR ( char_data*& term , next->attr.bit.protect , next->attr.bit.alt_charset ); + if ( alt_equal_pc_charset && next->attr.bit.alt_charset ) + { + term->attr.bit.pc_charset = true; + off.attr.bit.pc_charset = false; + pc_charset_usable = false; + } + if ( off.attr.bit.pc_charset ) unsetTermPCcharset(term); @@ -1278,7 +1308,7 @@ inline void FOptiAttr::changeAttributeSGR ( char_data*& term if ( next->attr.bit.dbl_underline ) setTermDoubleUnderline(term); - if ( next->attr.bit.pc_charset ) + if ( next->attr.bit.pc_charset && pc_charset_usable ) setTermPCcharset(term); if ( colorChange(term, next) ) @@ -1293,15 +1323,14 @@ inline void FOptiAttr::changeAttributeSeparately ( char_data*& term , char_data*& next ) { setAttributesOff(term); - detectSwitchOff (term, next); - - if ( switchOff() ) - unsetTermAttributes(term); if ( colorChange(term, next) ) + { change_color (term, next); + postProcessing_cygwin_quirks(term, next); + } - detectSwitchOn (term, next); + detectSwitchOn (term, next); // After reset all attributes setAttributesOn(term); } @@ -1313,6 +1342,8 @@ void FOptiAttr::change_color (char_data*& term, char_data*& next) if ( monochron || ! (term && next) ) return; + next->fg_color %= max_color; + next->bg_color %= max_color; fg = next->fg_color; bg = next->bg_color; @@ -1425,19 +1456,8 @@ inline void FOptiAttr::resetAttribute (char_data*& attr) { if ( attr ) { - attr->attr.bit.bold = \ - attr->attr.bit.dim = \ - attr->attr.bit.italic = \ - attr->attr.bit.underline = \ - attr->attr.bit.blink = \ - attr->attr.bit.reverse = \ - attr->attr.bit.standout = \ - attr->attr.bit.invisible = \ - attr->attr.bit.protect = \ - attr->attr.bit.crossed_out = \ - attr->attr.bit.dbl_underline = \ - attr->attr.bit.alt_charset = \ - attr->attr.bit.pc_charset = 0; + attr->attr.byte[0] = 0; + attr->attr.byte[1] &= reset_byte_mask.attr.byte[1]; } } @@ -1480,6 +1500,25 @@ bool FOptiAttr::caused_reset_attributes (char cap[], uChar test) return false; } +//---------------------------------------------------------------------- +inline bool FOptiAttr::hasCharsetEquivalence() +{ + // Detect if alt charset and pc charset are the same sequences + + char* alt_on = F_enter_alt_charset_mode.cap; + char* alt_off = F_enter_pc_charset_mode.cap; + char* pc_on = F_enter_pc_charset_mode.cap; + char* pc_off = F_exit_pc_charset_mode.cap; + + if ( alt_on && pc_on && std::strcmp (alt_on, pc_on) == 0 ) + return true; + + if ( alt_off && pc_off && std::strcmp (alt_off, pc_off) == 0 ) + return true; + + return false; +} + //---------------------------------------------------------------------- inline void FOptiAttr::detectSwitchOn (char_data*& term, char_data*& next) { diff --git a/src/fterm.cpp b/src/fterm.cpp index f03702a8..c00a03ee 100644 --- a/src/fterm.cpp +++ b/src/fterm.cpp @@ -2920,8 +2920,8 @@ char* FTerm::parseAnswerbackMsg (char current_termtype[]) //---------------------------------------------------------------------- char* FTerm::parseSecDA (char current_termtype[]) { - // The Linux console knows no Sec_DA - if ( linux_terminal ) + // The Linux console and older cygwin terminals knows no Sec_DA + if ( linux_terminal || cygwin_terminal ) return current_termtype; try @@ -3028,14 +3028,15 @@ char* FTerm::secDA_Analysis (char current_termtype[]) new_termtype = secDA_Analysis_24(current_termtype); break; + case 32: // Tera Term + new_termtype = secDA_Analysis_32(current_termtype); + break; + case 41: // DEC VT420 case 61: // DEC VT510 case 64: // DEC VT520 case 65: // DEC VT525 - break; - - case 32: // Tera Term - new_termtype = secDA_Analysis_32(current_termtype); + case 67: // Cygwin break; case 77: // mintty @@ -3332,7 +3333,7 @@ void FTerm::init_pc_charset() } if ( reinit ) - opti_attr->init(); + opti_attr->initialize(); } //---------------------------------------------------------------------- @@ -3627,7 +3628,15 @@ void FTerm::init_termcaps_cygwin_quirks() // Set background color erase for cygwin terminal FTermcap::background_color_erase = true; + // Include the Linux console quirks init_termcaps_linux_quirks(); + + // Avoid underline, blink and dim mode + FTermcap::attr_without_color = 26; + + // Invisible mode is not supported + TCAP(fc::t_enter_secure_mode) = 0; + TCAP(fc::t_exit_secure_mode) = 0; } //---------------------------------------------------------------------- @@ -3654,7 +3663,7 @@ void FTerm::init_termcaps_linux_quirks() TCAP(fc::t_orig_pair) = \ C_STR(CSI "39;49;25m"); - // Avoid dim + underline + // Avoid underline and dim mode TCAP(fc::t_enter_dim_mode) = 0; TCAP(fc::t_exit_dim_mode) = 0; TCAP(fc::t_enter_underline_mode) = 0; @@ -4090,7 +4099,7 @@ void FTerm::init_OptiAttr() if ( cygwin_terminal ) opti_attr->setCygwinTerminal(); - opti_attr->init(); + opti_attr->initialize(); } //---------------------------------------------------------------------- diff --git a/src/test/Makefile.am b/src/test/Makefile.am index 815fbbc2..4351469a 100644 --- a/src/test/Makefile.am +++ b/src/test/Makefile.am @@ -10,6 +10,7 @@ noinst_PROGRAMS = \ fobject_test \ fmouse_test \ foptimove_test \ + foptiattr_test \ fstring_test \ fpoint_test \ frect_test @@ -17,6 +18,7 @@ noinst_PROGRAMS = \ fobject_test_SOURCES = fobject-test.cpp fmouse_test_SOURCES = fmouse-test.cpp foptimove_test_SOURCES = foptimove-test.cpp +foptiattr_test_SOURCES = foptiattr-test.cpp fstring_test_SOURCES = fstring-test.cpp fpoint_test_SOURCES = fpoint-test.cpp frect_test_SOURCES = frect-test.cpp @@ -24,6 +26,7 @@ frect_test_SOURCES = frect-test.cpp TESTS = fobject_test \ fmouse_test \ foptimove_test \ + foptiattr_test \ fstring_test \ fpoint_test \ frect_test diff --git a/src/test/Makefile.in b/src/test/Makefile.in index 0beac013..e174dde2 100644 --- a/src/test/Makefile.in +++ b/src/test/Makefile.in @@ -85,10 +85,12 @@ host_triplet = @host@ @CPPUNIT_TEST_TRUE@noinst_PROGRAMS = fobject_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ fmouse_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ foptimove_test$(EXEEXT) \ +@CPPUNIT_TEST_TRUE@ foptiattr_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ fstring_test$(EXEEXT) fpoint_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ frect_test$(EXEEXT) @CPPUNIT_TEST_TRUE@TESTS = fobject_test$(EXEEXT) fmouse_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ foptimove_test$(EXEEXT) \ +@CPPUNIT_TEST_TRUE@ foptiattr_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ fstring_test$(EXEEXT) fpoint_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ frect_test$(EXEEXT) @CPPUNIT_TEST_TRUE@check_PROGRAMS = $(am__EXEEXT_1) @@ -110,6 +112,7 @@ CONFIG_CLEAN_VPATH_FILES = @CPPUNIT_TEST_TRUE@am__EXEEXT_1 = fobject_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ fmouse_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ foptimove_test$(EXEEXT) \ +@CPPUNIT_TEST_TRUE@ foptiattr_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ fstring_test$(EXEEXT) fpoint_test$(EXEEXT) \ @CPPUNIT_TEST_TRUE@ frect_test$(EXEEXT) PROGRAMS = $(noinst_PROGRAMS) @@ -125,6 +128,11 @@ am__fobject_test_SOURCES_DIST = fobject-test.cpp @CPPUNIT_TEST_TRUE@am_fobject_test_OBJECTS = fobject-test.$(OBJEXT) fobject_test_OBJECTS = $(am_fobject_test_OBJECTS) fobject_test_LDADD = $(LDADD) +am__foptiattr_test_SOURCES_DIST = foptiattr-test.cpp +@CPPUNIT_TEST_TRUE@am_foptiattr_test_OBJECTS = \ +@CPPUNIT_TEST_TRUE@ foptiattr-test.$(OBJEXT) +foptiattr_test_OBJECTS = $(am_foptiattr_test_OBJECTS) +foptiattr_test_LDADD = $(LDADD) am__foptimove_test_SOURCES_DIST = foptimove-test.cpp @CPPUNIT_TEST_TRUE@am_foptimove_test_OBJECTS = \ @CPPUNIT_TEST_TRUE@ foptimove-test.$(OBJEXT) @@ -177,10 +185,12 @@ am__v_CXXLD_ = $(am__v_CXXLD_@AM_DEFAULT_V@) am__v_CXXLD_0 = @echo " CXXLD " $@; am__v_CXXLD_1 = SOURCES = $(fmouse_test_SOURCES) $(fobject_test_SOURCES) \ - $(foptimove_test_SOURCES) $(fpoint_test_SOURCES) \ - $(frect_test_SOURCES) $(fstring_test_SOURCES) + $(foptiattr_test_SOURCES) $(foptimove_test_SOURCES) \ + $(fpoint_test_SOURCES) $(frect_test_SOURCES) \ + $(fstring_test_SOURCES) DIST_SOURCES = $(am__fmouse_test_SOURCES_DIST) \ $(am__fobject_test_SOURCES_DIST) \ + $(am__foptiattr_test_SOURCES_DIST) \ $(am__foptimove_test_SOURCES_DIST) \ $(am__fpoint_test_SOURCES_DIST) $(am__frect_test_SOURCES_DIST) \ $(am__fstring_test_SOURCES_DIST) @@ -544,6 +554,7 @@ top_srcdir = @top_srcdir@ @CPPUNIT_TEST_TRUE@fobject_test_SOURCES = fobject-test.cpp @CPPUNIT_TEST_TRUE@fmouse_test_SOURCES = fmouse-test.cpp @CPPUNIT_TEST_TRUE@foptimove_test_SOURCES = foptimove-test.cpp +@CPPUNIT_TEST_TRUE@foptiattr_test_SOURCES = foptiattr-test.cpp @CPPUNIT_TEST_TRUE@fstring_test_SOURCES = fstring-test.cpp @CPPUNIT_TEST_TRUE@fpoint_test_SOURCES = fpoint-test.cpp @CPPUNIT_TEST_TRUE@frect_test_SOURCES = frect-test.cpp @@ -608,6 +619,10 @@ fobject_test$(EXEEXT): $(fobject_test_OBJECTS) $(fobject_test_DEPENDENCIES) $(EX @rm -f fobject_test$(EXEEXT) $(AM_V_CXXLD)$(CXXLINK) $(fobject_test_OBJECTS) $(fobject_test_LDADD) $(LIBS) +foptiattr_test$(EXEEXT): $(foptiattr_test_OBJECTS) $(foptiattr_test_DEPENDENCIES) $(EXTRA_foptiattr_test_DEPENDENCIES) + @rm -f foptiattr_test$(EXEEXT) + $(AM_V_CXXLD)$(CXXLINK) $(foptiattr_test_OBJECTS) $(foptiattr_test_LDADD) $(LIBS) + foptimove_test$(EXEEXT): $(foptimove_test_OBJECTS) $(foptimove_test_DEPENDENCIES) $(EXTRA_foptimove_test_DEPENDENCIES) @rm -f foptimove_test$(EXEEXT) $(AM_V_CXXLD)$(CXXLINK) $(foptimove_test_OBJECTS) $(foptimove_test_LDADD) $(LIBS) @@ -632,6 +647,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/fmouse-test.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/fobject-test.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/foptiattr-test.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/foptimove-test.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/fpoint-test.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/frect-test.Po@am__quote@ @@ -878,6 +894,13 @@ foptimove_test.log: foptimove_test$(EXEEXT) --log-file $$b.log --trs-file $$b.trs \ $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ "$$tst" $(AM_TESTS_FD_REDIRECT) +foptiattr_test.log: foptiattr_test$(EXEEXT) + @p='foptiattr_test$(EXEEXT)'; \ + b='foptiattr_test'; \ + $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) fstring_test.log: fstring_test$(EXEEXT) @p='fstring_test$(EXEEXT)'; \ b='fstring_test'; \ diff --git a/src/test/foptiattr-test.cpp b/src/test/foptiattr-test.cpp new file mode 100644 index 00000000..474c15bb --- /dev/null +++ b/src/test/foptiattr-test.cpp @@ -0,0 +1,662 @@ +/*********************************************************************** +* foptiattr_test.cpp - FOptiAttr unit tests * +* * +* This file is part of the Final Cut widget toolkit * +* * +* Copyright 2018 Markus Gans * +* * +* The Final Cut is free software; you can redistribute it and/or * +* modify it under the terms of the GNU Lesser General Public License * +* as published by the Free Software Foundation; either version 3 of * +* the License, or (at your option) any later version. * +* * +* The Final Cut is distributed in the hope that it will be useful, * +* but WITHOUT ANY WARRANTY; without even the implied warranty of * +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * +* GNU Lesser General Public License for more details. * +* * +* You should have received a copy of the GNU Lesser General Public * +* License along with this program. If not, see * +* . * +***********************************************************************/ + +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include + + +#define CPPUNIT_ASSERT_CSTRING(expected, actual) \ + check_c_string (expected, actual, CPPUNIT_SOURCELINE()) + +//---------------------------------------------------------------------- +void check_c_string ( const char* s1 + , const char* s2 + , CppUnit::SourceLine sourceLine ) +{ + if ( s1 == 0 && s2 == 0 ) + return; + + if ( s1 && s2 && std::strcmp (s1, s2) == 0 ) + return; + + ::CppUnit::Asserter::fail ("Strings are not equal", sourceLine); +} + + +//---------------------------------------------------------------------- +// class FOptiAttrTest +//---------------------------------------------------------------------- + +#pragma pack(push) +#pragma pack(1) + +class FOptiAttrTest : public CPPUNIT_NS::TestFixture +{ + public: + FOptiAttrTest() + { } + + protected: + void classNameTest(); + void noArgumentTest(); + void vga2ansi(); + void ansiTest(); + + private: + std::string printSequence (char*); + + // Adds code needed to register the test suite + CPPUNIT_TEST_SUITE (FOptiAttrTest); + + // Add a methods to the test suite + CPPUNIT_TEST (classNameTest); + CPPUNIT_TEST (noArgumentTest); + CPPUNIT_TEST (vga2ansi); + CPPUNIT_TEST (ansiTest); + + // End of test suite definition + CPPUNIT_TEST_SUITE_END(); +}; +#pragma pack(pop) + + +//---------------------------------------------------------------------- +void FOptiAttrTest::classNameTest() +{ + FOptiAttr opti_attr; + const char* const classname = opti_attr.getClassName(); + CPPUNIT_ASSERT_CSTRING ( classname, "FOptiAttr"); +} + +//---------------------------------------------------------------------- +void FOptiAttrTest::noArgumentTest() +{ + FOptiAttr oa; + oa.initialize(); + + // isNormal test + FOptiAttr::char_data* ch = new FOptiAttr::char_data(); + CPPUNIT_ASSERT ( ! oa.isNormal(ch) ); + ch->fg_color = fc::Default; + CPPUNIT_ASSERT ( ! oa.isNormal(ch) ); + ch->bg_color = fc::Default; + CPPUNIT_ASSERT ( oa.isNormal(ch) ); + delete ch; +} + +//---------------------------------------------------------------------- +void FOptiAttrTest::vga2ansi() +{ + FOptiAttr oa; + CPPUNIT_ASSERT (oa.vga2ansi(0) == 0); + CPPUNIT_ASSERT (oa.vga2ansi(1) == 4); + CPPUNIT_ASSERT (oa.vga2ansi(2) == 2); + CPPUNIT_ASSERT (oa.vga2ansi(3) == 6); + CPPUNIT_ASSERT (oa.vga2ansi(4) == 1); + CPPUNIT_ASSERT (oa.vga2ansi(5) == 5); + CPPUNIT_ASSERT (oa.vga2ansi(6) == 3); + CPPUNIT_ASSERT (oa.vga2ansi(7) == 7); + CPPUNIT_ASSERT (oa.vga2ansi(8) == 8); + CPPUNIT_ASSERT (oa.vga2ansi(9) == 12); + CPPUNIT_ASSERT (oa.vga2ansi(10) == 10); + CPPUNIT_ASSERT (oa.vga2ansi(11) == 14); + CPPUNIT_ASSERT (oa.vga2ansi(12) == 9); + CPPUNIT_ASSERT (oa.vga2ansi(13) == 13); + CPPUNIT_ASSERT (oa.vga2ansi(14) == 11); + CPPUNIT_ASSERT (oa.vga2ansi(15) == 15); +} + +//---------------------------------------------------------------------- +void FOptiAttrTest::ansiTest() +{ + FOptiAttr oa; + bool AX = true; // ANSI default color + bool cygwin = false; // Cygwin bold color fix + + if ( AX ) + oa.setDefaultColorSupport(); + + if ( cygwin ) + oa.setCygwinTerminal(); + + oa.setNoColorVideo (3); // Advid standout (1) + underline mode (2) + oa.setMaxColor (8); + oa.set_enter_bold_mode (C_STR(CSI "1m")); + oa.set_exit_bold_mode (C_STR(CSI "0m")); + oa.set_enter_dim_mode (0); + oa.set_exit_dim_mode (C_STR(CSI "0m")); + oa.set_enter_italics_mode (0); + oa.set_exit_italics_mode (0); + oa.set_enter_underline_mode (C_STR(CSI "4m")); + oa.set_exit_underline_mode (C_STR(CSI "1m")); + oa.set_enter_blink_mode (C_STR(CSI "5m")); + oa.set_exit_blink_mode (C_STR(CSI "0m")); + oa.set_enter_reverse_mode (C_STR(CSI "7m")); + oa.set_exit_reverse_mode (C_STR(CSI "0m")); + oa.set_enter_standout_mode (C_STR(CSI "7m")); + oa.set_exit_standout_mode (C_STR(CSI "m")); + oa.set_enter_secure_mode (C_STR(CSI "8m")); + oa.set_exit_secure_mode (C_STR(CSI "0m")); + oa.set_enter_protected_mode (0); + oa.set_exit_protected_mode (C_STR(CSI "0m")); + oa.set_enter_crossed_out_mode (0); + oa.set_exit_crossed_out_mode (C_STR(CSI "0m")); + oa.set_enter_dbl_underline_mode (0); + oa.set_exit_dbl_underline_mode (0); + oa.set_set_attributes (C_STR(CSI "0;10" + "%?%p1%t;7%;" + "%?%p2%t;4%;" + "%?%p3%t;7%;" + "%?%p4%t;5%;" + "%?%p6%t;1%;" + "%?%p7%t;8%;" + "%?%p9%t;11%;m")); + oa.set_exit_attribute_mode (C_STR(CSI "0m")); + oa.set_enter_alt_charset_mode (C_STR(CSI "11m")); + oa.set_exit_alt_charset_mode (C_STR(CSI "10m")); + oa.set_enter_pc_charset_mode (C_STR(CSI "11m")); + oa.set_exit_pc_charset_mode (C_STR(CSI "10m")); + oa.set_a_foreground_color (C_STR(CSI "3%p1%dm")); + oa.set_a_background_color (C_STR(CSI "4%p1%dm")); + oa.set_foreground_color (0); + oa.set_background_color (0); + oa.set_term_color_pair (0); + oa.set_orig_pair (C_STR(CSI "39;49m")); + oa.set_orig_orig_colors (0); + oa.initialize(); + + FOptiAttr::char_data* from = new FOptiAttr::char_data(); + FOptiAttr::char_data* to = new FOptiAttr::char_data(); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Default color + bold + from->fg_color = fc::Default; + from->bg_color = fc::Default; + to->attr.bit.bold = true; + to->fg_color = fc::Default; + to->bg_color = fc::Default; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;1m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Blue text on white background + dim + italic + to->fg_color = fc::Blue; + to->bg_color = fc::White; + to->attr.bit.dim = true; + to->attr.bit.italic = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;1m" CSI "34m" CSI "47m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Reset attributes + default background + to->attr.bit.bold = false; + to->attr.bit.dim = false; + to->attr.bit.italic = false; + to->bg_color = fc::Default; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "34m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Red text on black background + to->fg_color = fc::Red; + to->bg_color = fc::Black; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "31m" CSI "40m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // 256 color text and background + to->fg_color = fc::SpringGreen3; + to->bg_color = fc::NavyBlue; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "32m" CSI "44m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Bold on (with default colors) + to->fg_color = fc::Default; + to->bg_color = fc::Default; + to->attr.bit.bold = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;1m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Bold off (with default colors) + to->attr.bit.bold = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Dim on (with default colors) + to->attr.bit.dim = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Dim off (with default colors) + to->attr.bit.dim = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Italic on (with default colors) + to->attr.bit.italic = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Italic off (with default colors) + to->attr.bit.italic = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Underline on (with default colors) + to->attr.bit.underline = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;4m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Underline off (with default colors) + to->attr.bit.underline = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Blink on (with default colors) + to->attr.bit.blink = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;5m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Blink off (with default colors) + to->attr.bit.blink = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Reverse on (with default colors) + to->attr.bit.reverse = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;7m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Reverse off (with default colors) + to->attr.bit.reverse = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Standout on (with default colors) + to->attr.bit.standout = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;7m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Standout off (with default colors) + to->attr.bit.standout = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Invisible on (with default colors) + to->attr.bit.invisible = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;8m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Invisible off (with default colors) + to->attr.bit.invisible = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Protect on (with default colors) + to->attr.bit.protect = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Protect off (with default colors) + to->attr.bit.protect = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Crossed out on (with default colors) + to->attr.bit.crossed_out = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Crossed out off (with default colors) + to->attr.bit.crossed_out = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Double underline on (with default colors) + to->attr.bit.dbl_underline = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Double underline off (with default colors) + to->attr.bit.dbl_underline = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Alternate character set on (with default colors) + to->attr.bit.alt_charset = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;11m") ); + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to), C_STR("") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Alternate character set off (with default colors) + to->attr.bit.alt_charset = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // PC character set on (with default colors) + to->attr.bit.pc_charset = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10m" CSI "11m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // PC character set off (with default colors) + to->attr.bit.pc_charset = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "10m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Turn on all attributes (with default colors) + to->attr.bit.pc_charset = true; + to->attr.bit.bold = true; + to->attr.bit.dim = true; + to->attr.bit.italic = true; + to->attr.bit.underline = true; + to->attr.bit.blink = true; + to->attr.bit.reverse = true; + to->attr.bit.standout = true; + to->attr.bit.invisible = true; + to->attr.bit.protect = true; + to->attr.bit.crossed_out = true; + to->attr.bit.dbl_underline = true; + to->attr.bit.alt_charset = true; + to->attr.bit.pc_charset = true; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0;10;7;4;7;5;1;8;11m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Cyan text on blue background + to->fg_color = fc::Cyan; + to->bg_color = fc::Blue; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "36m" CSI "44m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Bold off + to->attr.bit.bold = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "36m" CSI "44m" CSI "11m" + CSI "5m" CSI "7m" CSI "8m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Dim off + to->attr.bit.dim = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "36m" CSI "44m" CSI "11m" + CSI "5m" CSI "7m" CSI "8m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Italic off + to->attr.bit.italic = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to), C_STR("") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Underline off + to->attr.bit.underline = false; + CPPUNIT_ASSERT ( *from == *to ); // because of noColorVideo = 3 + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Blink off + to->attr.bit.blink = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "36m" CSI "44m" + CSI "11m" CSI "7m" CSI "8m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Reverse off + to->attr.bit.reverse = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "36m" CSI "44m" + CSI "11m" CSI "8m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Standout off + to->attr.bit.standout = false; + CPPUNIT_ASSERT ( *from == *to ); // because of noColorVideo = 3 + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Invisible off + to->attr.bit.invisible = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "36m" CSI "44m" CSI "11m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Protect off + to->attr.bit.protect = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "36m" CSI "44m" CSI "11m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Crossed out off + to->attr.bit.crossed_out = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "36m" CSI "44m" CSI "11m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Double underline off + to->attr.bit.dbl_underline = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to), C_STR("") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Alternate character set off + to->attr.bit.alt_charset = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to), C_STR("") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // PC character set off + to->attr.bit.pc_charset = false; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to) + , C_STR(CSI "0m" CSI "10m" CSI "36m" CSI "44m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Green text color + to->fg_color = fc::Green; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( oa.changeAttribute(from, to), C_STR(CSI "32m") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + // Default text color + to->fg_color = fc::Default; + CPPUNIT_ASSERT ( *from != *to ); + CPPUNIT_ASSERT_CSTRING ( printSequence(oa.changeAttribute(from, to)).c_str() + , C_STR("Esc [ 3 9 m ") ); + CPPUNIT_ASSERT ( *from == *to ); + CPPUNIT_ASSERT ( oa.changeAttribute(from, to) == 0 ); + + delete to; + delete from; +} + +//---------------------------------------------------------------------- +std::string FOptiAttrTest::printSequence (char* str) +{ + std::ostringstream sequence; + + if ( ! str ) + return ""; + + const std::string& s(str); + + for (std::string::size_type i = 0; i < s.length(); ++i) + { + switch ( int(s[i]) ) + { + case 0x08: + sequence << "BS "; + break; + + case 0x09: + sequence << "TAB "; + break; + + case 0x0a: + sequence << "LF "; + break; + + case 0x0d: + sequence << "CR "; + break; + + case 0x1b: + sequence << "Esc "; + break; + + default: + sequence << s[i]; + sequence << ' '; + } + } + + return sequence.str(); +} + + +// Put the test suite in the registry +CPPUNIT_TEST_SUITE_REGISTRATION (FOptiAttrTest); + +// The general unit test main part +#include diff --git a/src/test/foptimove-test.cpp b/src/test/foptimove-test.cpp index 0b14878b..fe8568a1 100644 --- a/src/test/foptimove-test.cpp +++ b/src/test/foptimove-test.cpp @@ -43,6 +43,12 @@ void check_c_string ( const char* s1 , const char* s2 , CppUnit::SourceLine sourceLine ) { + if ( s1 == 0 && s2 == 0 ) + return; + + if ( s1 && s2 && std::strcmp (s1, s2) == 0 ) + return; + if ( std::strcmp (s1, s2) == 0 ) return; @@ -97,8 +103,6 @@ class FOptiMoveTest : public CPPUNIT_NS::TestFixture CPPUNIT_TEST (puttyTest); CPPUNIT_TEST (teratermTest); -// gnome-terminal - // End of test suite definition CPPUNIT_TEST_SUITE_END(); };