Refactoring of secondary device attributes parsing

This commit is contained in:
Markus Gans 2018-01-02 20:38:45 +01:00
parent 2e64c0da32
commit 06bfb8bc64
17 changed files with 459 additions and 333 deletions

View File

@ -1,3 +1,7 @@
2017-01-02 Markus Gans <guru.mail@muenster.de>
* Refactoring of secondary device attributes parsing
* Small menu improvements
2017-12-31 Markus Gans <guru.mail@muenster.de> 2017-12-31 Markus Gans <guru.mail@muenster.de>
* Refactoring of the FListBox mouse event handler * Refactoring of the FListBox mouse event handler
* Refactoring of the FMenuBar mouse event handler * Refactoring of the FMenuBar mouse event handler

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2012-2017 Markus Gans * * Copyright 2012-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -780,7 +780,7 @@ void MyDialog::cb_about (FWidget*, data_ptr)
FMessageBox info ( "About" FMessageBox info ( "About"
, line + L" The Final Cut " + line + "\n\n" , line + L" The Final Cut " + line + "\n\n"
L"Version " + libver + "\n\n" L"Version " + libver + "\n\n"
L"(c) 2017 by Markus Gans" L"(c) 2018 by Markus Gans"
, FMessageBox::Ok, 0, 0, this ); , FMessageBox::Ok, 0, 0, this );
info.setCenterText(); info.setCenterText();
info.show(); info.show();
@ -1006,7 +1006,7 @@ void MyDialog::cb_setInput (FWidget* widget, data_ptr data)
int main (int argc, char* argv[]) int main (int argc, char* argv[])
{ {
FString ver = F_VERSION; // Library version FString ver = F_VERSION; // Library version
FString title = "The FINAL CUT " + ver + " (C) 2017 by Markus Gans"; FString title = "The FINAL CUT " + ver + " (C) 2018 by Markus Gans";
// Create the application object app // Create the application object app
FApplication app(argc, argv); FApplication app(argc, argv);

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2017 Markus Gans * * Copyright 2017-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -174,8 +174,8 @@ class FListViewIterator
FListViewIterator operator ++ (int); // postfix FListViewIterator operator ++ (int); // postfix
FListViewIterator& operator -- (); // prefix FListViewIterator& operator -- (); // prefix
FListViewIterator operator -- (int); // postfix FListViewIterator operator -- (int); // postfix
FListViewIterator& operator += (int); FListViewIterator& operator += (volatile int);
FListViewIterator& operator -= (int); FListViewIterator& operator -= (volatile int);
FObject*& operator * () const; FObject*& operator * () const;
FObject* operator -> () const; FObject* operator -> () const;
bool operator == (const FListViewIterator&) const; bool operator == (const FListViewIterator&) const;

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2015-2017 Markus Gans * * Copyright 2015-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -133,7 +133,7 @@ class FOptiMove
void calculateCharDuration(); void calculateCharDuration();
int capDuration (char[], int); int capDuration (char[], int);
int capDurationToLength (int); int capDurationToLength (int);
int repeatedAppend (const capability&, int, char*); int repeatedAppend (const capability&, volatile int, char*);
int relativeMove (char[], int, int, int, int); int relativeMove (char[], int, int, int, int);
bool isWideMove (int, int, int, int); bool isWideMove (int, int, int, int);
bool isMethod0Faster (int&, int, int); bool isMethod0Faster (int&, int, int);

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2012-2017 Markus Gans * * Copyright 2012-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -414,16 +414,6 @@ class FTerm
uChar blue; uChar blue;
} dacreg; } dacreg;
typedef struct
{
char* string1;
char* string2;
char* string3;
char* string4;
char* string5;
char* string6;
} colorEnv;
// Constants // Constants
static const int NEED_MORE_DATA = -1; // parseKeyString return value static const int NEED_MORE_DATA = -1; // parseKeyString return value
@ -493,12 +483,21 @@ class FTerm
static void init_global_values(); static void init_global_values();
static void detectTerminal(); static void detectTerminal();
static void termtypeAnalysis(); static void termtypeAnalysis();
static bool get256colorEnvString (colorEnv&); static bool get256colorEnvString();
static char* termtype_256color_quirks (colorEnv&); static char* termtype_256color_quirks();
static char* init_256colorTerminal(); static char* init_256colorTerminal();
static char* determineMaxColor (char[]); static char* determineMaxColor (char[]);
static char* parseAnswerbackMsg (char[]); static char* parseAnswerbackMsg (char[]);
static char* parseSecDA (char[]); static char* parseSecDA (char[]);
static char* secDA_Analysis (char[]);
static char* secDA_Analysis_0 (char[]);
static char* secDA_Analysis_1 (char[]);
static char* secDA_Analysis_24 (char[]);
static char* secDA_Analysis_32 (char[]);
static char* secDA_Analysis_77 (char[]);
static char* secDA_Analysis_82 (char[]);
static char* secDA_Analysis_83 (char[]);
static char* secDA_Analysis_85 (char[]);
static void oscPrefix(); static void oscPrefix();
static void oscPostfix(); static void oscPostfix();
static void init_alt_charset(); static void init_alt_charset();
@ -617,6 +616,29 @@ class FTerm
static const FString* answer_back; static const FString* answer_back;
static const FString* sec_da; static const FString* sec_da;
static struct colorEnv
{
char* string1;
char* string2;
char* string3;
char* string4;
char* string5;
char* string6;
} color_env;
static struct secondaryDA
{
secondaryDA()
: terminal_id_type (-1)
, terminal_id_version (-1)
, terminal_id_hardware (-1)
{ }
int terminal_id_type;
int terminal_id_version;
int terminal_id_hardware;
} secondary_da;
struct struct
{ {
dacreg d[16]; dacreg d[16];

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2016-2017 Markus Gans * * Copyright 2016-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2013-2017 Markus Gans * * Copyright 2013-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -335,7 +335,7 @@ void FApplication::showParameterUsage()
<< " --encoding <name> " << " --encoding <name> "
<< " Sets the character encoding mode" << std::endl << " Sets the character encoding mode" << std::endl
<< " " << " "
<< " {UTF8, VT100, PC, ASCII}" << std::endl << " {utf8, vt100, pc, ascii}" << std::endl
<< " --no-optimized-cursor " << " --no-optimized-cursor "
<< " Disable cursor optimization" << std::endl << " Disable cursor optimization" << std::endl
<< " --no-terminal-detection" << " --no-terminal-detection"
@ -433,17 +433,17 @@ void FApplication::cmd_options (const int& argc, char* argv[])
if ( std::strcmp(long_options[idx].name, "encoding") == 0 ) if ( std::strcmp(long_options[idx].name, "encoding") == 0 )
{ {
FString encoding(optarg); FString encoding(optarg);
encoding = encoding.toUpper(); encoding = encoding.toLower();
if ( encoding.includes("UTF8") ) if ( encoding.includes("utf8") )
init_values.encoding = fc::UTF8; init_values.encoding = fc::UTF8;
else if ( encoding.includes("VT100") ) else if ( encoding.includes("vt100") )
init_values.encoding = fc::VT100; init_values.encoding = fc::VT100;
else if ( encoding.includes("PC") ) else if ( encoding.includes("pc") )
init_values.encoding = fc::PC; init_values.encoding = fc::PC;
else if ( encoding.includes("ASCII") ) else if ( encoding.includes("ascii") )
init_values.encoding = fc::ASCII; init_values.encoding = fc::ASCII;
else if ( encoding.includes("HELP") ) else if ( encoding.includes("help") )
showParameterUsage(); showParameterUsage();
else else
exitWithMessage ( "Unknown encoding " exitWithMessage ( "Unknown encoding "

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2012-2017 Markus Gans * * Copyright 2012-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -724,7 +724,7 @@ inline void FButton::drawButtonTextLine (wchar_t button_text[])
} }
} }
if ( txtlength > getWidth() - 2 ) if ( txtlength >= getWidth() - 1 )
{ {
// Print ellipsis // Print ellipsis
setPrintPos (getWidth() + indent - 2, 1); setPrintPos (getWidth() + indent - 2, 1);

View File

@ -4,7 +4,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2014-2017 Markus Gans * * Copyright 2014-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -75,16 +75,14 @@ FButtonGroup::~FButtonGroup() // destructor
FToggleButton* FButtonGroup::getButton (int index) const FToggleButton* FButtonGroup::getButton (int index) const
{ {
constFObjectIterator iter; constFObjectIterator iter;
index--;
if ( buttonlist.empty() ) if ( buttonlist.empty() )
return 0; return 0;
if ( index < 0 || index >= int(getCount()) ) if ( index <= 0 || index > int(getCount()) )
return 0; return 0;
iter = buttonlist.begin(); iter = buttonlist.begin();
std::advance (iter, index); std::advance (iter, index - 1);
return static_cast<FToggleButton*>(*iter); return static_cast<FToggleButton*>(*iter);
} }

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2017 Markus Gans * * Copyright 2017-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -321,7 +321,7 @@ FListViewIterator FListViewIterator::operator -- (int) // postfix
} }
//---------------------------------------------------------------------- //----------------------------------------------------------------------
FListViewIterator& FListViewIterator::operator += (int n) FListViewIterator& FListViewIterator::operator += (volatile int n)
{ {
while ( n > 0 ) while ( n > 0 )
{ {
@ -333,7 +333,7 @@ FListViewIterator& FListViewIterator::operator += (int n)
} }
//---------------------------------------------------------------------- //----------------------------------------------------------------------
FListViewIterator& FListViewIterator::operator -= (int n) FListViewIterator& FListViewIterator::operator -= (volatile int n)
{ {
while ( n > 0 ) while ( n > 0 )
{ {
@ -1093,7 +1093,7 @@ void FListView::onWheel (FWheelEvent* ev)
if ( current_iter.getPosition() == 0 ) if ( current_iter.getPosition() == 0 )
break; break;
if ( first_visible_line.getPosition() - pagesize >= 0 ) if ( first_visible_line.getPosition() >= pagesize )
{ {
current_iter -= pagesize; current_iter -= pagesize;
first_visible_line -= pagesize; first_visible_line -= pagesize;
@ -1116,7 +1116,7 @@ void FListView::onWheel (FWheelEvent* ev)
if ( current_iter.getPosition() + 1 == element_count ) if ( current_iter.getPosition() + 1 == element_count )
break; break;
if ( last_visible_line.getPosition() + pagesize < element_count ) if ( last_visible_line.getPosition() < element_count - pagesize )
{ {
current_iter += pagesize; current_iter += pagesize;
first_visible_line += pagesize; first_visible_line += pagesize;
@ -1197,17 +1197,17 @@ void FListView::adjustViewport()
int difference = first_visible_line.getPosition() int difference = first_visible_line.getPosition()
- (element_count - height); - (element_count - height);
if ( first_visible_line.getPosition() - difference + 1 > 0 ) if ( first_visible_line.getPosition() >= difference )
{ {
first_visible_line -= difference; first_visible_line -= difference;
last_visible_line -= difference; last_visible_line -= difference;
} }
} }
int max_last_visible_line = first_visible_line.getPosition() int after_last_visible_line = first_visible_line.getPosition()
+ height - 1; + height;
if ( last_visible_line.getPosition() > max_last_visible_line ) if ( last_visible_line.getPosition() >= after_last_visible_line )
{ {
last_visible_line = first_visible_line; last_visible_line = first_visible_line;
last_visible_line += height - 1; last_visible_line += height - 1;

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2015-2017 Markus Gans * * Copyright 2015-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -212,8 +212,6 @@ void FMenu::onKeyPress (FKeyEvent* ev)
//---------------------------------------------------------------------- //----------------------------------------------------------------------
void FMenu::onMouseDown (FMouseEvent* ev) void FMenu::onMouseDown (FMouseEvent* ev)
{ {
std::vector<FMenuItem*>::const_iterator iter, last;
FPoint mouse_pos;
shown_sub_menu = 0; shown_sub_menu = 0;
if ( ev->getButton() != fc::LeftButton ) if ( ev->getButton() != fc::LeftButton )

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2015-2017 Markus Gans * * Copyright 2015-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -102,17 +102,15 @@ FObject::~FObject() // destructor
//---------------------------------------------------------------------- //----------------------------------------------------------------------
FObject* FObject::getChild (int index) const FObject* FObject::getChild (int index) const
{ {
index--;
if ( ! hasChildren() ) if ( ! hasChildren() )
return 0; return 0;
if ( index < 0 || index >= numOfChildren() ) if ( index <= 0 || index > numOfChildren() )
return 0; return 0;
constFObjectIterator iter; constFObjectIterator iter;
iter = begin(); iter = begin();
std::advance (iter, index); std::advance (iter, index - 1);
return *iter; return *iter;
} }

View File

@ -1214,12 +1214,10 @@ inline void FOptiAttr::prevent_no_color_video_attributes (char_data*& attr)
switch ( bit & attr_without_color ) switch ( bit & attr_without_color )
{ {
case standout_mode: case standout_mode:
if ( attr->attr.bit.standout )
attr->attr.bit.standout = false; attr->attr.bit.standout = false;
break; break;
case underline_mode: case underline_mode:
if ( attr->attr.bit.underline )
attr->attr.bit.underline = false; attr->attr.bit.underline = false;
break; break;
@ -1234,37 +1232,30 @@ inline void FOptiAttr::prevent_no_color_video_attributes (char_data*& attr)
break; break;
case blink_mode: case blink_mode:
if ( attr->attr.bit.blink )
attr->attr.bit.blink = false; attr->attr.bit.blink = false;
break; break;
case dim_mode: case dim_mode:
if ( attr->attr.bit.dim )
attr->attr.bit.dim = false; attr->attr.bit.dim = false;
break; break;
case bold_mode: case bold_mode:
if ( attr->attr.bit.bold )
attr->attr.bit.bold = false; attr->attr.bit.bold = false;
break; break;
case invisible_mode: case invisible_mode:
if ( attr->attr.bit.invisible )
attr->attr.bit.invisible = false; attr->attr.bit.invisible = false;
break; break;
case protected_mode: case protected_mode:
if ( attr->attr.bit.protect )
attr->attr.bit.protect = false; attr->attr.bit.protect = false;
break; break;
case alt_charset_mode: case alt_charset_mode:
if ( attr->attr.bit.alt_charset )
attr->attr.bit.alt_charset = false; attr->attr.bit.alt_charset = false;
break; break;
case italic_mode: case italic_mode:
if ( attr->attr.bit.italic )
attr->attr.bit.italic = false; attr->attr.bit.italic = false;
break; break;

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2015-2017 Markus Gans * * Copyright 2015-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -639,7 +639,9 @@ int FOptiMove::capDurationToLength (int duration)
} }
//---------------------------------------------------------------------- //----------------------------------------------------------------------
int FOptiMove::repeatedAppend (const capability& o, int count, char* dst) int FOptiMove::repeatedAppend ( const capability& o
, volatile int count
, char* dst )
{ {
register std::size_t src_len; register std::size_t src_len;
register std::size_t dst_len; register std::size_t dst_len;

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2012-2017 Markus Gans * * Copyright 2012-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2012-2017 Markus Gans * * Copyright 2012-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -138,6 +138,8 @@ bool FTermcap::no_utf8_acs_chars = false;
int FTermcap::max_color = 1; int FTermcap::max_color = 1;
int FTermcap::tabstop = 8; int FTermcap::tabstop = 8;
int FTermcap::attr_without_color = 0; int FTermcap::attr_without_color = 0;
FTerm::secondaryDA FTerm::secondary_da;
FTerm::colorEnv FTerm::color_env;
FTerm::initializationValues FTerm::init_values; FTerm::initializationValues FTerm::init_values;
fc::linuxConsoleCursorStyle FTerm::linux_console_cursor_style; fc::linuxConsoleCursorStyle FTerm::linux_console_cursor_style;
fc::freebsdConsoleCursorStyle FTerm::freebsd_console_cursor_style; fc::freebsdConsoleCursorStyle FTerm::freebsd_console_cursor_style;
@ -493,9 +495,7 @@ int FTerm::parseKeyString ( char buffer[]
if ( k && std::strncmp(k, buffer, uInt(len)) == 0 ) // found if ( k && std::strncmp(k, buffer, uInt(len)) == 0 ) // found
{ {
n = len; for (n = len; n < buf_size; n++) // Remove founded entry
for (; n < buf_size; n++) // Remove founded entry
buffer[n - len] = buffer[n]; buffer[n - len] = buffer[n];
for (; n - len < len; n++) // Fill rest with '\0' for (; n - len < len; n++) // Fill rest with '\0'
@ -521,9 +521,8 @@ int FTerm::parseKeyString ( char buffer[]
if ( ! isKeyTimeout(time_keypressed, key_timeout) ) if ( ! isKeyTimeout(time_keypressed, key_timeout) )
return NEED_MORE_DATA; return NEED_MORE_DATA;
} }
n = len;
for (; n < buf_size; n++) // Remove founded entry for (n = len; n < buf_size; n++) // Remove founded entry
buffer[n - len] = buffer[n]; buffer[n - len] = buffer[n];
for (; n - len < len; n++) // Fill rest with '\0' for (; n - len < len; n++) // Fill rest with '\0'
@ -561,9 +560,7 @@ int FTerm::parseKeyString ( char buffer[]
else else
key = uChar(buffer[0] & 0xff); key = uChar(buffer[0] & 0xff);
n = len; for (n = len; n < buf_size; n++) // remove the key from the buffer front
for (; n < buf_size; n++) // remove the key from the buffer front
buffer[n - len] = buffer[n]; buffer[n - len] = buffer[n];
for (n = n - len; n < buf_size; n++) // fill the rest with '\0' bytes for (n = n - len; n < buf_size; n++) // fill the rest with '\0' bytes
@ -1476,9 +1473,6 @@ void FTerm::beep()
//---------------------------------------------------------------------- //----------------------------------------------------------------------
void FTerm::setEncoding (fc::encoding enc) void FTerm::setEncoding (fc::encoding enc)
{ {
if ( FTermcap::no_utf8_acs_chars && isUTF8() && enc == fc::VT100 )
enc = fc::UTF8;
term_encoding = enc; term_encoding = enc;
assert ( term_encoding == fc::UTF8 assert ( term_encoding == fc::UTF8
@ -1486,7 +1480,7 @@ void FTerm::setEncoding (fc::encoding enc)
|| term_encoding == fc::PC || term_encoding == fc::PC
|| term_encoding == fc::ASCII ); || term_encoding == fc::ASCII );
// set the new Fputchar function pointer // Set the new Fputchar function pointer
switch ( term_encoding ) switch ( term_encoding )
{ {
case fc::UTF8: case fc::UTF8:
@ -1573,7 +1567,7 @@ const FString FTerm::getAnswerbackMsg()
struct timeval tv; struct timeval tv;
char temp[10] = {}; char temp[10] = {};
std::putchar (ENQ[0]); // send enquiry character std::putchar (ENQ[0]); // Send enquiry character
std::fflush(stdout); std::fflush(stdout);
FD_ZERO(&ifds); FD_ZERO(&ifds);
@ -1581,7 +1575,7 @@ const FString FTerm::getAnswerbackMsg()
tv.tv_sec = 0; tv.tv_sec = 0;
tv.tv_usec = 150000; // 150 ms tv.tv_usec = 150000; // 150 ms
// read the answerback message // Read the answerback message
if ( select (stdin_no + 1, &ifds, 0, 0, &tv) > 0 ) if ( select (stdin_no + 1, &ifds, 0, 0, &tv) > 0 )
if ( std::fgets (temp, sizeof(temp) - 1, stdin) != 0 ) if ( std::fgets (temp, sizeof(temp) - 1, stdin) != 0 )
answerback = temp; answerback = temp;
@ -1600,7 +1594,7 @@ const FString FTerm::getSecDA()
fd_set ifds; fd_set ifds;
struct timeval tv; struct timeval tv;
// get the secondary device attributes // Get the secondary device attributes
putstring (SECDA); putstring (SECDA);
std::fflush(stdout); std::fflush(stdout);
@ -1609,7 +1603,7 @@ const FString FTerm::getSecDA()
tv.tv_sec = 0; tv.tv_sec = 0;
tv.tv_usec = 600000; // 600 ms tv.tv_usec = 600000; // 600 ms
// read the answer // Read the answer
if ( select (stdin_no + 1, &ifds, 0, 0, &tv) == 1 ) if ( select (stdin_no + 1, &ifds, 0, 0, &tv) == 1 )
if ( std::scanf("\033[>%10d;%10d;%10dc", &a, &b, &c) == 3 ) if ( std::scanf("\033[>%10d;%10d;%10dc", &a, &b, &c) == 3 )
sec_da_str.sprintf("\033[>%d;%d;%dc", a, b, c); sec_da_str.sprintf("\033[>%d;%d;%dc", a, b, c);
@ -2060,7 +2054,7 @@ inline uChar FTerm::getAttributeMode()
} }
//---------------------------------------------------------------------- //----------------------------------------------------------------------
inline void FTerm::setAttributeMode(uChar data) inline void FTerm::setAttributeMode (uChar data)
{ {
// Sets the attribute mode value from the vga attribute controller // Sets the attribute mode value from the vga attribute controller
static const uChar attrib_mode = 0x10; static const uChar attrib_mode = 0x10;
@ -2726,12 +2720,12 @@ void FTerm::init_global_values()
cursor_optimisation = \ cursor_optimisation = \
terminal_detection = true; terminal_detection = true;
// assertion: programm start in cooked mode // Assertion: programm start in cooked mode
raw_mode = \ raw_mode = \
input_data_pending = \ input_data_pending = \
non_blocking_stdin = false; non_blocking_stdin = false;
// init arrays with '\0' // Init arrays with '\0'
std::fill_n (exit_message, sizeof(exit_message), '\0'); std::fill_n (exit_message, sizeof(exit_message), '\0');
if ( ! init_values.terminal_detection ) if ( ! init_values.terminal_detection )
@ -2838,6 +2832,13 @@ void FTerm::termtypeAnalysis()
sun_terminal = true; sun_terminal = true;
} }
// Kterm
if ( std::strncmp(termtype, "kterm", 5) == 0 )
{
terminal_detection = false;
kterm_terminal = true;
}
// Linux console // Linux console
if ( std::strncmp(termtype, C_STR("linux"), 5) == 0 if ( std::strncmp(termtype, C_STR("linux"), 5) == 0
|| std::strncmp(termtype, C_STR("con"), 3) == 0 ) || std::strncmp(termtype, C_STR("con"), 3) == 0 )
@ -2853,39 +2854,39 @@ void FTerm::termtypeAnalysis()
} }
//---------------------------------------------------------------------- //----------------------------------------------------------------------
bool FTerm::get256colorEnvString(colorEnv& env) bool FTerm::get256colorEnvString()
{ {
// Enable 256 color capabilities // Enable 256 color capabilities
env.string1 = std::getenv("COLORTERM"); color_env.string1 = std::getenv("COLORTERM");
env.string2 = std::getenv("VTE_VERSION"); color_env.string2 = std::getenv("VTE_VERSION");
env.string3 = std::getenv("XTERM_VERSION"); color_env.string3 = std::getenv("XTERM_VERSION");
env.string4 = std::getenv("ROXTERM_ID"); color_env.string4 = std::getenv("ROXTERM_ID");
env.string5 = std::getenv("KONSOLE_DBUS_SESSION"); color_env.string5 = std::getenv("KONSOLE_DBUS_SESSION");
env.string6 = std::getenv("KONSOLE_DCOP"); color_env.string6 = std::getenv("KONSOLE_DCOP");
if ( env.string1 != 0 ) if ( color_env.string1 != 0 )
return true; return true;
if ( env.string2 != 0 ) if ( color_env.string2 != 0 )
return true; return true;
if ( env.string3 != 0 ) if ( color_env.string3 != 0 )
return true; return true;
if ( env.string4 != 0 ) if ( color_env.string4 != 0 )
return true; return true;
if ( env.string5 != 0 ) if ( color_env.string5 != 0 )
return true; return true;
if ( env.string6 != 0 ) if ( color_env.string6 != 0 )
return true; return true;
return false; return false;
} }
//---------------------------------------------------------------------- //----------------------------------------------------------------------
char* FTerm::termtype_256color_quirks (colorEnv& env) char* FTerm::termtype_256color_quirks()
{ {
char* new_termtype = 0; char* new_termtype = 0;
@ -2915,19 +2916,19 @@ char* FTerm::termtype_256color_quirks (colorEnv& env)
} }
if ( std::strncmp(termtype, "rxvt", 4) != 0 if ( std::strncmp(termtype, "rxvt", 4) != 0
&& env.string1 && color_env.string1
&& std::strncmp(env.string1, "rxvt-xpm", 8) == 0 ) && std::strncmp(color_env.string1, "rxvt-xpm", 8) == 0 )
{ {
new_termtype = C_STR("rxvt-256color"); new_termtype = C_STR("rxvt-256color");
rxvt_terminal = true; rxvt_terminal = true;
} }
if ( (env.string5 && std::strlen(env.string5) > 0) if ( (color_env.string5 && std::strlen(color_env.string5) > 0)
|| (env.string6 && std::strlen(env.string6) > 0) ) || (color_env.string6 && std::strlen(color_env.string6) > 0) )
kde_konsole = true; kde_konsole = true;
if ( (env.string1 && std::strncmp(env.string1, "gnome-terminal", 14) == 0) if ( (color_env.string1 && std::strncmp(color_env.string1, "gnome-terminal", 14) == 0)
|| env.string2 ) || color_env.string2 )
{ {
gnome_terminal = true; gnome_terminal = true;
// Each gnome-terminal should be able to use 256 colors // Each gnome-terminal should be able to use 256 colors
@ -2944,16 +2945,15 @@ char* FTerm::termtype_256color_quirks (colorEnv& env)
char* FTerm::init_256colorTerminal() char* FTerm::init_256colorTerminal()
{ {
char* new_termtype = 0; char* new_termtype = 0;
colorEnv env;
if ( get256colorEnvString(env) ) if ( get256colorEnvString() )
color256 = true; color256 = true;
else if ( std::strstr (termtype, "256color") ) else if ( std::strstr (termtype, "256color") )
color256 = true; color256 = true;
else else
color256 = false; color256 = false;
new_termtype = termtype_256color_quirks(env); new_termtype = termtype_256color_quirks();
#if DEBUG #if DEBUG
if ( new_termtype ) if ( new_termtype )
@ -3044,11 +3044,9 @@ char* FTerm::parseAnswerbackMsg (char current_termtype[])
//---------------------------------------------------------------------- //----------------------------------------------------------------------
char* FTerm::parseSecDA (char current_termtype[]) char* FTerm::parseSecDA (char current_termtype[])
{ {
char* new_termtype = current_termtype;
// The Linux console knows no Sec_DA // The Linux console knows no Sec_DA
if ( linux_terminal ) if ( linux_terminal )
return new_termtype; return current_termtype;
try try
{ {
@ -3058,13 +3056,11 @@ char* FTerm::parseSecDA (char current_termtype[])
catch (const std::bad_alloc& ex) catch (const std::bad_alloc& ex)
{ {
std::cerr << "not enough memory to alloc " << ex.what() << std::endl; std::cerr << "not enough memory to alloc " << ex.what() << std::endl;
return new_termtype; return current_termtype;
} }
if ( sec_da->getLength() > 5 ) if ( sec_da->getLength() < 6 )
{ return current_termtype;
uLong num_components;
bool sec_da_supported = false;
// remove the first 3 bytes ("\033[>") // remove the first 3 bytes ("\033[>")
FString temp = sec_da->right(sec_da->getLength() - 3); FString temp = sec_da->right(sec_da->getLength() - 3);
@ -3073,71 +3069,79 @@ char* FTerm::parseSecDA (char current_termtype[])
// split into components // split into components
FStringList sec_da_list = temp.split(';'); FStringList sec_da_list = temp.split(';');
num_components = sec_da_list.size(); uLong num_components = sec_da_list.size();
// The second device attribute (SEC_DA) always has 3 parameters, // The second device attribute (SEC_DA) always has 3 parameters,
// otherwise it usually has a copy of the device attribute (primary DA) // otherwise it usually has a copy of the device attribute (primary DA)
if ( num_components == 3 ) if ( num_components < 3 )
sec_da_supported = true; return current_termtype;
if ( num_components >= 2 )
{
const FString* sec_da_components = &sec_da_list[0]; const FString* sec_da_components = &sec_da_list[0];
if ( ! sec_da_components[0].isEmpty() ) if ( sec_da_components[0].isEmpty() )
{ return current_termtype;
int terminal_id_type, terminal_id_version;
// Read the terminal type // Read the terminal type
try try
{ {
terminal_id_type = sec_da_components[0].toInt(); secondary_da.terminal_id_type = sec_da_components[0].toInt();
} }
catch (const std::exception&) catch (const std::exception&)
{ {
terminal_id_type = -1; secondary_da.terminal_id_type = -1;
} }
// Read the terminal (firmware) version // Read the terminal (firmware) version
try try
{ {
if ( sec_da_components[1] ) if ( sec_da_components[1] )
terminal_id_version = sec_da_components[1].toInt(); secondary_da.terminal_id_version = sec_da_components[1].toInt();
else else
terminal_id_version = -1; secondary_da.terminal_id_version = -1;
} }
catch (const std::exception&) catch (const std::exception&)
{ {
terminal_id_version = -1; secondary_da.terminal_id_version = -1;
} }
switch ( terminal_id_type ) // Read the terminal hardware option
try
{
if ( sec_da_components[2] )
secondary_da.terminal_id_hardware = sec_da_components[2].toInt();
else
secondary_da.terminal_id_hardware = -1;
}
catch (const std::exception&)
{
secondary_da.terminal_id_hardware = -1;
}
char* new_termtype = secDA_Analysis(current_termtype);
#if DEBUG
if ( new_termtype )
std::strncpy ( termtype_SecDA
, new_termtype
, std::strlen(new_termtype) + 1 );
#endif
return new_termtype;
}
//----------------------------------------------------------------------
char* FTerm::secDA_Analysis (char current_termtype[])
{
char* new_termtype = current_termtype;
switch ( secondary_da.terminal_id_type )
{ {
case 0: // DEC VT100 case 0: // DEC VT100
if ( terminal_id_version == 115 ) new_termtype = secDA_Analysis_0(current_termtype);
kde_konsole = true;
else if ( terminal_id_version == 136 )
putty_terminal = true; // PuTTY
break; break;
case 1: // DEC VT220 case 1: // DEC VT220
if ( ! sec_da_supported ) new_termtype = secDA_Analysis_1(current_termtype);
{
if ( terminal_id_version == 2 ) // also used by apple terminal
kterm_terminal = true; // kterm
}
else if ( terminal_id_version > 1000 )
{
gnome_terminal = true;
// Each gnome-terminal should be able to use 256 colors
color256 = true;
new_termtype = C_STR("gnome-256color");
gnome_terminal_id = terminal_id_version;
// VTE 0.40.0 or higher and gnome-terminal 3.16 or higher
if ( gnome_terminal_id >= 4000 )
decscusr_support = true;
}
break; break;
case 2: // DEC VT240 case 2: // DEC VT240
@ -3145,8 +3149,97 @@ char* FTerm::parseSecDA (char current_termtype[])
case 19: // DEC VT340 case 19: // DEC VT340
case 24: // DEC VT320 case 24: // DEC VT320
new_termtype = secDA_Analysis_24(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);
break;
case 77: // mintty
new_termtype = secDA_Analysis_77(current_termtype);
break;
case 82: // rxvt
new_termtype = secDA_Analysis_82(current_termtype);
break;
case 83: // screen
new_termtype = secDA_Analysis_83(current_termtype);
break;
case 85: // rxvt-unicode
new_termtype = secDA_Analysis_85(current_termtype);
break;
default:
break;
}
// Correct false assumptions
if ( gnome_terminal && secondary_da.terminal_id_type != 1 )
gnome_terminal = false;
if ( kde_konsole && secondary_da.terminal_id_type != 0 )
kde_konsole = false;
return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTerm::secDA_Analysis_0 (char current_termtype[])
{
// Terminal ID 0 - DEC VT100
char* new_termtype = current_termtype;
if ( secondary_da.terminal_id_version == 115 )
kde_konsole = true;
else if ( secondary_da.terminal_id_version == 136 )
putty_terminal = true; // PuTTY
return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTerm::secDA_Analysis_1 (char current_termtype[])
{
// Terminal ID 1 - DEC VT220
char* new_termtype = current_termtype;
if ( secondary_da.terminal_id_version > 1000 )
{
gnome_terminal = true;
// Each gnome-terminal should be able to use 256 colors
color256 = true;
new_termtype = C_STR("gnome-256color");
gnome_terminal_id = secondary_da.terminal_id_version;
// VTE 0.40.0 or higher and gnome-terminal 3.16 or higher
if ( gnome_terminal_id >= 4000 )
decscusr_support = true;
}
return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTerm::secDA_Analysis_24 (char current_termtype[])
{
// Terminal ID 24 - DEC VT320
char* new_termtype = current_termtype;
#if defined(__NetBSD__) || defined(__OpenBSD__) #if defined(__NetBSD__) || defined(__OpenBSD__)
if ( terminal_id_version == 20 && isWSConsConsole() )
if ( secondary_da.terminal_id_version == 20 && isWSConsConsole() )
{ {
// NetBSD/OpenBSD workstation console // NetBSD/OpenBSD workstation console
if ( std::strncmp(termtype, C_STR("wsvt25"), 6) == 0 ) if ( std::strncmp(termtype, C_STR("wsvt25"), 6) == 0 )
@ -3157,43 +3250,71 @@ char* FTerm::parseSecDA (char current_termtype[])
new_termtype = C_STR("pccon"); new_termtype = C_STR("pccon");
} }
} }
break;
#endif
case 41: // DEC VT420
case 61: // DEC VT510
case 64: // DEC VT520
case 65: // DEC VT525
break;
case 32: // Tera Term #endif
return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTerm::secDA_Analysis_32 (char current_termtype[])
{
// Terminal ID 32 - Tera Term
char* new_termtype = current_termtype;
tera_terminal = true; tera_terminal = true;
new_termtype = C_STR("teraterm"); new_termtype = C_STR("teraterm");
break; return new_termtype;
}
case 77: // mintty //----------------------------------------------------------------------
inline char* FTerm::secDA_Analysis_77 (char current_termtype[])
{
// Terminal ID 77 - mintty
char* new_termtype = current_termtype;
mintty_terminal = true; mintty_terminal = true;
new_termtype = C_STR("xterm-256color"); new_termtype = C_STR("xterm-256color");
// switch to application escape key mode // switch to application escape key mode
putstring (CSI "?7727h"); putstring (CSI "?7727h");
std::fflush(stdout); std::fflush(stdout);
break; return new_termtype;
}
case 83: // screen //----------------------------------------------------------------------
screen_terminal = true; inline char* FTerm::secDA_Analysis_82 (char current_termtype[])
break; {
// Terminal ID 82 - rxvt
case 82: // rxvt char* new_termtype = current_termtype;
rxvt_terminal = true; rxvt_terminal = true;
force_vt100 = true; // this rxvt terminal support on utf-8 force_vt100 = true; // This rxvt terminal does not support utf-8
if ( std::strncmp(termtype, "rxvt-", 5) != 0 if ( std::strncmp(termtype, "rxvt-", 5) != 0
&& std::strncmp(termtype, "rxvt-cygwin-native", 18) == 0 ) && std::strncmp(termtype, "rxvt-cygwin-native", 18) == 0 )
new_termtype = C_STR("rxvt-16color"); new_termtype = C_STR("rxvt-16color");
else else
new_termtype = termtype; new_termtype = termtype;
break;
case 85: // rxvt-unicode return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTerm::secDA_Analysis_83 (char current_termtype[])
{
// Terminal ID 83 - screen
char* new_termtype = current_termtype;
screen_terminal = true;
return new_termtype;
}
//----------------------------------------------------------------------
inline char* FTerm::secDA_Analysis_85 (char current_termtype[])
{
// Terminal ID 85 - rxvt-unicode
char* new_termtype = current_termtype;
rxvt_terminal = true; rxvt_terminal = true;
urxvt_terminal = true; urxvt_terminal = true;
@ -3206,28 +3327,6 @@ char* FTerm::parseSecDA (char current_termtype[])
} }
else else
new_termtype = termtype; new_termtype = termtype;
break;
default:
break;
}
// Correct false assumptions
if ( gnome_terminal && terminal_id_type != 1 )
gnome_terminal = false;
if ( kde_konsole && terminal_id_type != 0 )
kde_konsole = false;
}
}
}
#if DEBUG
if ( new_termtype )
std::strncpy ( termtype_SecDA
, new_termtype
, std::strlen(new_termtype) + 1 );
#endif
return new_termtype; return new_termtype;
} }
@ -3260,7 +3359,7 @@ void FTerm::oscPostfix()
//---------------------------------------------------------------------- //----------------------------------------------------------------------
void FTerm::init_alt_charset() void FTerm::init_alt_charset()
{ {
// read the used vt100 pairs // Read the used vt100 pairs
if ( TCAP(fc::t_acs_chars) ) if ( TCAP(fc::t_acs_chars) )
{ {
@ -3279,7 +3378,7 @@ void FTerm::init_alt_charset()
utf8_char = 1 utf8_char = 1
}; };
// update array 'character' with discovered vt100 pairs // Update array 'character' with discovered vt100 pairs
for (int n = 0; n <= fc::lastKeyItem; n++ ) for (int n = 0; n <= fc::lastKeyItem; n++ )
{ {
uChar keyChar = uChar(fc::vt100_key_to_utf8[n][vt100_key]); uChar keyChar = uChar(fc::vt100_key_to_utf8[n][vt100_key]);
@ -3313,7 +3412,7 @@ void FTerm::init_pc_charset()
if ( gnome_terminal || linux_terminal ) if ( gnome_terminal || linux_terminal )
{ {
// fallback if tcap "S2" is not found // Fallback if tcap "S2" is not found
if ( ! TCAP(fc::t_enter_pc_charset_mode) ) if ( ! TCAP(fc::t_enter_pc_charset_mode) )
{ {
if ( utf8_console ) if ( utf8_console )
@ -3334,7 +3433,7 @@ void FTerm::init_pc_charset()
reinit = true; reinit = true;
} }
// fallback if tcap "S3" is not found // Fallback if tcap "S3" is not found
if ( ! TCAP(fc::t_exit_pc_charset_mode) ) if ( ! TCAP(fc::t_exit_pc_charset_mode) )
{ {
if ( utf8_console ) if ( utf8_console )
@ -4173,6 +4272,10 @@ void FTerm::init_locale()
if ( tera_terminal && ! std::strcmp(nl_langinfo(CODESET), "UTF-8") ) if ( tera_terminal && ! std::strcmp(nl_langinfo(CODESET), "UTF-8") )
locale_name = std::setlocale (LC_ALL, "C"); locale_name = std::setlocale (LC_ALL, "C");
// Kterm
if ( kterm_terminal && ! std::strcmp(nl_langinfo(CODESET), "UTF-8") )
locale_name = std::setlocale (LC_ALL, "C");
// Sun (color) workstation console can't show UTF-8 character // Sun (color) workstation console can't show UTF-8 character
if ( std::strncmp(termtype, "sun", 3) == 0 if ( std::strncmp(termtype, "sun", 3) == 0
&& ! std::strcmp(nl_langinfo(CODESET), "UTF-8") ) && ! std::strcmp(nl_langinfo(CODESET), "UTF-8") )
@ -4265,6 +4368,13 @@ void FTerm::init_encoding()
term_encoding = fc::VT100; term_encoding = fc::VT100;
Fputchar = &FTerm::putchar_ASCII; // function pointer Fputchar = &FTerm::putchar_ASCII; // function pointer
} }
else if ( FTermcap::no_utf8_acs_chars && isUTF8()
&& term_encoding == fc::VT100 )
{
ascii_console = true;
term_encoding = fc::ASCII;
Fputchar = &FTerm::putchar_ASCII; // function pointer
}
// In some alternative character sets, a tab character prints a '○' // In some alternative character sets, a tab character prints a '○'
// on the terminal and does not move the cursor to the next tab stop // on the terminal and does not move the cursor to the next tab stop
@ -4520,7 +4630,9 @@ void FTerm::init()
init_encoding(); init_encoding();
if ( init_values.encoding != fc::UNKNOWN ) if ( init_values.encoding != fc::UNKNOWN )
{
setEncoding(init_values.encoding); setEncoding(init_values.encoding);
}
// Enable the terminal mouse support // Enable the terminal mouse support
enableMouse(); enableMouse();

View File

@ -3,7 +3,7 @@
* * * *
* This file is part of the Final Cut widget toolkit * * This file is part of the Final Cut widget toolkit *
* * * *
* Copyright 2016-2017 Markus Gans * * Copyright 2016-2018 Markus Gans *
* * * *
* The Final Cut is free software; you can redistribute it and/or * * The Final Cut is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public License * * modify it under the terms of the GNU Lesser General Public License *
@ -2639,12 +2639,10 @@ void FVTerm::cursorWrap()
{ {
// Wrap the cursor // Wrap the cursor
term_area*& vt = vterm; term_area*& vt = vterm;
int term_width = vt->width - 1;
int term_height = vt->height - 1;
if ( term_pos->getX() > term_width ) if ( term_pos->getX() >= vt->width )
{ {
if ( term_pos->getY() == term_height ) if ( term_pos->getY() == vt->height - 1 )
term_pos->x_ref()--; term_pos->x_ref()--;
else else
{ {
@ -2846,6 +2844,9 @@ inline void FVTerm::charsetChanges (char_data*& next_char)
{ {
next_char->attr.bit.pc_charset = true; next_char->attr.bit.pc_charset = true;
if ( isPuttyTerminal() )
return;
if ( isXTerminal() && ch_enc < 0x20 ) // Character 0x00..0x1f if ( isXTerminal() && ch_enc < 0x20 ) // Character 0x00..0x1f
{ {
if ( hasUTF8() ) if ( hasUTF8() )