@@ -8,7 +8,7 @@ import { InputHandler } from 'common/InputHandler';
88import { IBufferLine , IAttributeData } from 'common/Types' ;
99import { DEFAULT_ATTR_DATA } from 'common/buffer/BufferLine' ;
1010import { CellData } from 'common/buffer/CellData' ;
11- import { Attributes } from 'common/buffer/Constants' ;
11+ import { Attributes , UnderlineStyle } from 'common/buffer/Constants' ;
1212import { AttributeData } from 'common/buffer/AttributeData' ;
1313import { Params } from 'common/parser/Params' ;
1414import { MockCoreService , MockBufferService , MockDirtyRowService , MockOptionsService , MockLogService , MockCoreMouseService , MockCharsetService , MockUnicodeService } from 'common/TestUtils.test' ;
@@ -1468,6 +1468,181 @@ describe('InputHandler', () => {
14681468 } ) ;
14691469 } ) ;
14701470
1471+ describe ( 'extended underline style support (SGR 4)' , ( ) => {
1472+ beforeEach ( ( ) => {
1473+ bufferService . resize ( 10 , 5 ) ;
1474+ } ) ;
1475+ it ( '4 | 24' , ( ) => {
1476+ inputHandler . parse ( '\x1b[4m' ) ;
1477+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . SINGLE ) ;
1478+ inputHandler . parse ( '\x1b[24m' ) ;
1479+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1480+ } ) ;
1481+ it ( '21 | 24' , ( ) => {
1482+ inputHandler . parse ( '\x1b[21m' ) ;
1483+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DOUBLE ) ;
1484+ inputHandler . parse ( '\x1b[24m' ) ;
1485+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1486+ } ) ;
1487+ it ( '4:1 | 4:0' , ( ) => {
1488+ inputHandler . parse ( '\x1b[4:1m' ) ;
1489+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . SINGLE ) ;
1490+ inputHandler . parse ( '\x1b[4:0m' ) ;
1491+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1492+ inputHandler . parse ( '\x1b[4:1m' ) ;
1493+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . SINGLE ) ;
1494+ inputHandler . parse ( '\x1b[24m' ) ;
1495+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1496+ } ) ;
1497+ it ( '4:2 | 4:0' , ( ) => {
1498+ inputHandler . parse ( '\x1b[4:2m' ) ;
1499+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DOUBLE ) ;
1500+ inputHandler . parse ( '\x1b[4:0m' ) ;
1501+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1502+ inputHandler . parse ( '\x1b[4:2m' ) ;
1503+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DOUBLE ) ;
1504+ inputHandler . parse ( '\x1b[24m' ) ;
1505+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1506+ } ) ;
1507+ it ( '4:3 | 4:0' , ( ) => {
1508+ inputHandler . parse ( '\x1b[4:3m' ) ;
1509+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . CURLY ) ;
1510+ inputHandler . parse ( '\x1b[4:0m' ) ;
1511+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1512+ inputHandler . parse ( '\x1b[4:3m' ) ;
1513+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . CURLY ) ;
1514+ inputHandler . parse ( '\x1b[24m' ) ;
1515+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1516+ } ) ;
1517+ it ( '4:4 | 4:0' , ( ) => {
1518+ inputHandler . parse ( '\x1b[4:4m' ) ;
1519+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DOTTED ) ;
1520+ inputHandler . parse ( '\x1b[4:0m' ) ;
1521+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1522+ inputHandler . parse ( '\x1b[4:4m' ) ;
1523+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DOTTED ) ;
1524+ inputHandler . parse ( '\x1b[24m' ) ;
1525+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1526+ } ) ;
1527+ it ( '4:5 | 4:0' , ( ) => {
1528+ inputHandler . parse ( '\x1b[4:5m' ) ;
1529+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DASHED ) ;
1530+ inputHandler . parse ( '\x1b[4:0m' ) ;
1531+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1532+ inputHandler . parse ( '\x1b[4:5m' ) ;
1533+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DASHED ) ;
1534+ inputHandler . parse ( '\x1b[24m' ) ;
1535+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . NONE ) ;
1536+ } ) ;
1537+ it ( '4:x --> 4 should revert to single underline' , ( ) => {
1538+ inputHandler . parse ( '\x1b[4:5m' ) ;
1539+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . DASHED ) ;
1540+ inputHandler . parse ( '\x1b[4m' ) ;
1541+ assert . equal ( inputHandler . curAttrData . getUnderlineStyle ( ) , UnderlineStyle . SINGLE ) ;
1542+ } ) ;
1543+ } ) ;
1544+ describe ( 'underline colors (SGR 58 & SGR 59)' , ( ) => {
1545+ beforeEach ( ( ) => {
1546+ bufferService . resize ( 10 , 5 ) ;
1547+ } ) ;
1548+ it ( 'defaults to FG color' , ( ) => {
1549+ for ( const s of [ '' , '\x1b[30m' , '\x1b[38;510m' , '\x1b[38;2;1;2;3m' ] ) {
1550+ inputHandler . parse ( s ) ;
1551+ assert . equal ( inputHandler . curAttrData . getUnderlineColor ( ) , inputHandler . curAttrData . getFgColor ( ) ) ;
1552+ assert . equal ( inputHandler . curAttrData . getUnderlineColorMode ( ) , inputHandler . curAttrData . getFgColorMode ( ) ) ;
1553+ assert . equal ( inputHandler . curAttrData . isUnderlineColorRGB ( ) , inputHandler . curAttrData . isFgRGB ( ) ) ;
1554+ assert . equal ( inputHandler . curAttrData . isUnderlineColorPalette ( ) , inputHandler . curAttrData . isFgPalette ( ) ) ;
1555+ assert . equal ( inputHandler . curAttrData . isUnderlineColorDefault ( ) , inputHandler . curAttrData . isFgDefault ( ) ) ;
1556+ }
1557+ } ) ;
1558+ it ( 'correctly sets P256/RGB colors' , ( ) => {
1559+ inputHandler . parse ( '\x1b[4m' ) ;
1560+ inputHandler . parse ( '\x1b[58;5;123m' ) ;
1561+ assert . equal ( inputHandler . curAttrData . getUnderlineColor ( ) , 123 ) ;
1562+ assert . equal ( inputHandler . curAttrData . getUnderlineColorMode ( ) , Attributes . CM_P256 ) ;
1563+ assert . equal ( inputHandler . curAttrData . isUnderlineColorRGB ( ) , false ) ;
1564+ assert . equal ( inputHandler . curAttrData . isUnderlineColorPalette ( ) , true ) ;
1565+ assert . equal ( inputHandler . curAttrData . isUnderlineColorDefault ( ) , false ) ;
1566+ inputHandler . parse ( '\x1b[58;2::1:2:3m' ) ;
1567+ assert . equal ( inputHandler . curAttrData . getUnderlineColor ( ) , ( 1 << 16 ) | ( 2 << 8 ) | 3 ) ;
1568+ assert . equal ( inputHandler . curAttrData . getUnderlineColorMode ( ) , Attributes . CM_RGB ) ;
1569+ assert . equal ( inputHandler . curAttrData . isUnderlineColorRGB ( ) , true ) ;
1570+ assert . equal ( inputHandler . curAttrData . isUnderlineColorPalette ( ) , false ) ;
1571+ assert . equal ( inputHandler . curAttrData . isUnderlineColorDefault ( ) , false ) ;
1572+ } ) ;
1573+ it ( 'P256/RGB persistence' , ( ) => {
1574+ const cell = new CellData ( ) ;
1575+ inputHandler . parse ( '\x1b[4m' ) ;
1576+ inputHandler . parse ( '\x1b[58;5;123m' ) ;
1577+ assert . equal ( inputHandler . curAttrData . getUnderlineColor ( ) , 123 ) ;
1578+ assert . equal ( inputHandler . curAttrData . getUnderlineColorMode ( ) , Attributes . CM_P256 ) ;
1579+ assert . equal ( inputHandler . curAttrData . isUnderlineColorRGB ( ) , false ) ;
1580+ assert . equal ( inputHandler . curAttrData . isUnderlineColorPalette ( ) , true ) ;
1581+ assert . equal ( inputHandler . curAttrData . isUnderlineColorDefault ( ) , false ) ;
1582+ inputHandler . parse ( 'ab' ) ;
1583+ bufferService . buffer ! . lines . get ( 0 ) ! . loadCell ( 1 , cell ) ;
1584+ assert . equal ( cell . getUnderlineColor ( ) , 123 ) ;
1585+ assert . equal ( cell . getUnderlineColorMode ( ) , Attributes . CM_P256 ) ;
1586+ assert . equal ( cell . isUnderlineColorRGB ( ) , false ) ;
1587+ assert . equal ( cell . isUnderlineColorPalette ( ) , true ) ;
1588+ assert . equal ( cell . isUnderlineColorDefault ( ) , false ) ;
1589+
1590+ inputHandler . parse ( '\x1b[4:0m' ) ;
1591+ assert . equal ( inputHandler . curAttrData . getUnderlineColor ( ) , inputHandler . curAttrData . getFgColor ( ) ) ;
1592+ assert . equal ( inputHandler . curAttrData . getUnderlineColorMode ( ) , inputHandler . curAttrData . getFgColorMode ( ) ) ;
1593+ assert . equal ( inputHandler . curAttrData . isUnderlineColorRGB ( ) , inputHandler . curAttrData . isFgRGB ( ) ) ;
1594+ assert . equal ( inputHandler . curAttrData . isUnderlineColorPalette ( ) , inputHandler . curAttrData . isFgPalette ( ) ) ;
1595+ assert . equal ( inputHandler . curAttrData . isUnderlineColorDefault ( ) , inputHandler . curAttrData . isFgDefault ( ) ) ;
1596+ inputHandler . parse ( 'a' ) ;
1597+ bufferService . buffer ! . lines . get ( 0 ) ! . loadCell ( 1 , cell ) ;
1598+ assert . equal ( cell . getUnderlineColor ( ) , 123 ) ;
1599+ assert . equal ( cell . getUnderlineColorMode ( ) , Attributes . CM_P256 ) ;
1600+ assert . equal ( cell . isUnderlineColorRGB ( ) , false ) ;
1601+ assert . equal ( cell . isUnderlineColorPalette ( ) , true ) ;
1602+ assert . equal ( cell . isUnderlineColorDefault ( ) , false ) ;
1603+ bufferService . buffer ! . lines . get ( 0 ) ! . loadCell ( 2 , cell ) ;
1604+ assert . equal ( cell . getUnderlineColor ( ) , inputHandler . curAttrData . getFgColor ( ) ) ;
1605+ assert . equal ( cell . getUnderlineColorMode ( ) , inputHandler . curAttrData . getFgColorMode ( ) ) ;
1606+ assert . equal ( cell . isUnderlineColorRGB ( ) , inputHandler . curAttrData . isFgRGB ( ) ) ;
1607+ assert . equal ( cell . isUnderlineColorPalette ( ) , inputHandler . curAttrData . isFgPalette ( ) ) ;
1608+ assert . equal ( cell . isUnderlineColorDefault ( ) , inputHandler . curAttrData . isFgDefault ( ) ) ;
1609+
1610+ inputHandler . parse ( '\x1b[4m' ) ;
1611+ inputHandler . parse ( '\x1b[58;2::1:2:3m' ) ;
1612+ assert . equal ( inputHandler . curAttrData . getUnderlineColor ( ) , ( 1 << 16 ) | ( 2 << 8 ) | 3 ) ;
1613+ assert . equal ( inputHandler . curAttrData . getUnderlineColorMode ( ) , Attributes . CM_RGB ) ;
1614+ assert . equal ( inputHandler . curAttrData . isUnderlineColorRGB ( ) , true ) ;
1615+ assert . equal ( inputHandler . curAttrData . isUnderlineColorPalette ( ) , false ) ;
1616+ assert . equal ( inputHandler . curAttrData . isUnderlineColorDefault ( ) , false ) ;
1617+ inputHandler . parse ( 'a' ) ;
1618+ inputHandler . parse ( '\x1b[24m' ) ;
1619+ bufferService . buffer ! . lines . get ( 0 ) ! . loadCell ( 1 , cell ) ;
1620+ assert . equal ( cell . getUnderlineColor ( ) , 123 ) ;
1621+ assert . equal ( cell . getUnderlineColorMode ( ) , Attributes . CM_P256 ) ;
1622+ assert . equal ( cell . isUnderlineColorRGB ( ) , false ) ;
1623+ assert . equal ( cell . isUnderlineColorPalette ( ) , true ) ;
1624+ assert . equal ( cell . isUnderlineColorDefault ( ) , false ) ;
1625+ bufferService . buffer ! . lines . get ( 0 ) ! . loadCell ( 3 , cell ) ;
1626+ assert . equal ( cell . getUnderlineColor ( ) , ( 1 << 16 ) | ( 2 << 8 ) | 3 ) ;
1627+ assert . equal ( cell . getUnderlineColorMode ( ) , Attributes . CM_RGB ) ;
1628+ assert . equal ( cell . isUnderlineColorRGB ( ) , true ) ;
1629+ assert . equal ( cell . isUnderlineColorPalette ( ) , false ) ;
1630+ assert . equal ( cell . isUnderlineColorDefault ( ) , false ) ;
1631+
1632+ // eAttrs in buffer pos 0 and 1 should be the same object
1633+ assert . equal (
1634+ ( bufferService . buffer ! . lines . get ( 0 ) ! as any ) . _extendedAttrs [ 0 ] ,
1635+ ( bufferService . buffer ! . lines . get ( 0 ) ! as any ) . _extendedAttrs [ 1 ]
1636+ ) ;
1637+ // should not have written eAttr for pos 2 in the buffer
1638+ assert . equal ( ( bufferService . buffer ! . lines . get ( 0 ) ! as any ) . _extendedAttrs [ 2 ] , undefined ) ;
1639+ // eAttrs in buffer pos 1 and pos 3 must be different objs
1640+ assert . notEqual (
1641+ ( bufferService . buffer ! . lines . get ( 0 ) ! as any ) . _extendedAttrs [ 1 ] ,
1642+ ( bufferService . buffer ! . lines . get ( 0 ) ! as any ) . _extendedAttrs [ 3 ]
1643+ ) ;
1644+ } ) ;
1645+ } ) ;
14711646 describe ( 'DECSTR' , ( ) => {
14721647 beforeEach ( ( ) => {
14731648 bufferService . resize ( 10 , 5 ) ;
0 commit comments