Skip to content

Commit

Permalink
Adds "smart" line flushing functions.
Browse files Browse the repository at this point in the history
See in-code comments for more details
  • Loading branch information
nokome committed Jul 13, 2015
1 parent 0d02731 commit f697978
Showing 1 changed file with 80 additions and 44 deletions.
124 changes: 80 additions & 44 deletions src/pprint.c
Expand Up @@ -711,6 +711,42 @@ static void PCondFlushLine( TidyDocImpl* doc, uint indent )
}
}

/**
* Two additional "smart" flush line functions which only
* write a newline if `vertical-space no`. See issues #163 and #227.
* These need to be used in the right place. In same cases `PFlushLine`
* and `PCondFlushLine` should still be used.
*/
void TY_(PFlushLineSmart)( TidyDocImpl* doc, uint indent )
{
TidyPrintImpl* pprint = &doc->pprint;

if ( pprint->linelen > 0 )
PFlushLineImpl( doc );

Bool vertical = cfgBool( doc, TidyVertSpace );
if(vertical)
TY_(WriteChar)( '\n', doc->docOut );

pprint->indent[ 0 ].spaces = indent;
}

static void PCondFlushLineSmart( TidyDocImpl* doc, uint indent )
{
TidyPrintImpl* pprint = &doc->pprint;

if ( pprint->linelen > 0 )
{
PFlushLineImpl( doc );

Bool vertical = cfgBool( doc, TidyVertSpace );
if(vertical)
TY_(WriteChar)( '\n', doc->docOut );

pprint->indent[ 0 ].spaces = indent;
}
}

static void PPrintChar( TidyDocImpl* doc, uint c, uint mode )
{
tmbchar entity[128];
Expand Down Expand Up @@ -1164,7 +1200,7 @@ static void PPrintAttribute( TidyDocImpl* doc, uint indent,
if ( TY_(nodeIsElement)(node) && !first )
{
indent += xtra;
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
}
else
indAttrs = no;
Expand Down Expand Up @@ -1471,7 +1507,7 @@ static void PPrintTag( TidyDocImpl* doc,
See bug #996484 */
else if ( mode & NOWRAP ||
nodeIsBR(node) || AfterSpace(doc->lexer, node))
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
}
}

Expand Down Expand Up @@ -1536,7 +1572,7 @@ static void PPrintComment( TidyDocImpl* doc, uint indent, Node* node )
AddString(pprint, "--");
AddChar( pprint, '>' );
if ( node->linebreak && node->next )
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}

static void PPrintDocType( TidyDocImpl* doc, uint indent, Node *node )
Expand All @@ -1550,7 +1586,7 @@ static void PPrintDocType( TidyDocImpl* doc, uint indent, Node *node )
/* todo: handle non-ASCII characters in FPI / SI / node->element */

SetWrap( doc, indent );
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

AddString( pprint, "<!DOCTYPE " );
SetWrap( doc, indent );
Expand All @@ -1573,7 +1609,7 @@ static void PPrintDocType( TidyDocImpl* doc, uint indent, Node *node )
if (!(i>0&&TY_(tmbstrlen)(sys->value)+2+i<wraplen&&i<=(spaces?spaces:2)*2))
i = 0;

PCondFlushLine(doc, i);
PCondFlushLineSmart(doc, i);
if (pprint->linelen)
AddChar(pprint, ' ');
}
Expand All @@ -1591,15 +1627,15 @@ static void PPrintDocType( TidyDocImpl* doc, uint indent, Node *node )

if (node->content)
{
PCondFlushLine(doc, indent);
PCondFlushLineSmart(doc, indent);
AddChar(pprint, '[');
PPrintText(doc, CDATA, 0, node->content);
AddChar(pprint, ']');
}

SetWrap( doc, 0 );
AddChar( pprint, '>' );
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
}

static void PPrintPI( TidyDocImpl* doc, uint indent, Node *node )
Expand Down Expand Up @@ -1664,7 +1700,7 @@ static void PPrintXmlDecl( TidyDocImpl* doc, uint indent, Node *node )
AddChar( pprint, '?' );
AddChar( pprint, '>' );
WrapOn( doc, saveWrap );
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}

/* note ASP and JSTE share <% ... %> syntax */
Expand Down Expand Up @@ -1729,14 +1765,14 @@ static void PPrintCDATA( TidyDocImpl* doc, uint indent, Node *node )
if ( !indentCData )
indent = 0;

PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
saveWrap = WrapOff( doc ); /* disable wrapping */

AddString( pprint, "<![CDATA[" );
PPrintText( doc, COMMENT, indent, node );
AddString( pprint, "]]>" );

PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
WrapOn( doc, saveWrap ); /* restore wrapping */
}

Expand Down Expand Up @@ -1889,9 +1925,9 @@ void PPrintScriptStyle( TidyDocImpl* doc, uint mode, uint indent, Node *node )
Bool xhtmlOut = cfgBool( doc, TidyXhtmlOut );

if ( InsideHead(doc, node) )
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );

PCondFlushLine( doc, indent ); /* Issue #56 - long oustanding bug - flush any existing closing tag */
PCondFlushLineSmart( doc, indent ); /* Issue #56 - long oustanding bug - flush any existing closing tag */

PPrintTag( doc, mode, indent, node );

Expand Down Expand Up @@ -1928,7 +1964,7 @@ void PPrintScriptStyle( TidyDocImpl* doc, uint mode, uint indent, Node *node )
AddString( pprint, commentStart );
AddString( pprint, CDATA_START );
AddString( pprint, commentEnd );
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

WrapOn( doc, saveWrap );
}
Expand All @@ -1952,7 +1988,7 @@ void PPrintScriptStyle( TidyDocImpl* doc, uint mode, uint indent, Node *node )

if ( contentIndent < 0 )
{
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
contentIndent = 0;
}

Expand All @@ -1967,7 +2003,7 @@ void PPrintScriptStyle( TidyDocImpl* doc, uint mode, uint indent, Node *node )
AddString( pprint, commentEnd );

WrapOn( doc, saveWrap );
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
}
}

Expand All @@ -1979,7 +2015,7 @@ void PPrintScriptStyle( TidyDocImpl* doc, uint mode, uint indent, Node *node )
if ( cfgAutoBool(doc, TidyIndentContent) == TidyNoState
&& node->next != NULL &&
!( TY_(nodeHasCM)(node, CM_INLINE) || TY_(nodeIsText)(node) ) )
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}


Expand Down Expand Up @@ -2112,20 +2148,20 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
or remove the CM_INLINE from the tag
*/
if ( ! TY_(nodeHasCM)(node, CM_INLINE) )
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

if ( nodeIsBR(node) && node->prev &&
!(nodeIsBR(node->prev) || (mode & PREFORMATTED)) &&
cfgBool(doc, TidyBreakBeforeBR) )
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );

if ( nodeIsHR(node) )
{
/* insert extra newline for classic formatting */
Bool classic = cfgBool( doc, TidyVertSpace );
if (classic && node->parent && node->parent->content != node)
{
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}
}

Expand All @@ -2134,10 +2170,10 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
if (node->next)
{
if (nodeIsPARAM(node) || nodeIsAREA(node))
PCondFlushLine(doc, indent);
PCondFlushLineSmart(doc, indent);
else if ((nodeIsBR(node) && !(mode & PREFORMATTED))
|| nodeIsHR(node))
TY_(PFlushLine)(doc, indent);
TY_(PFlushLineSmart)(doc, indent);
}
}
else /* some kind of container element */
Expand All @@ -2150,32 +2186,32 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
{
Bool classic = cfgBool( doc, TidyVertSpace );
uint indprev = indent;
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

/* insert extra newline for classic formatting */
if (classic && node->parent && node->parent->content != node)
{
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}
PPrintTag( doc, mode, indent, node );

indent = 0;
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );

for ( content = node->content; content; content = content->next )
{
TY_(PPrintTree)( doc, (mode | PREFORMATTED | NOWRAP),
indent, content );
}
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
indent = indprev;
PPrintEndTag( doc, mode, indent, node );

if ( cfgAutoBool(doc, TidyIndentContent) == TidyNoState
&& node->next != NULL )
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}
else if ( nodeIsSTYLE(node) || nodeIsSCRIPT(node) )
{
Expand Down Expand Up @@ -2204,15 +2240,15 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
if ( ShouldIndent(doc, node) )
{
indent += spaces;
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

for ( content = node->content;
content != NULL;
content = content->next )
TY_(PPrintTree)( doc, mode, indent, content );

indent -= spaces;
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
/* PCondFlushLine( doc, indent ); */
}
else
Expand All @@ -2236,21 +2272,21 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
/* insert extra newline for classic formatting */
if (classic && node->parent && node->parent->content != node && !nodeIsHTML(node))
{
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}

if ( ShouldIndent(doc, node) )
contentIndent += spaces;

PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

/*\
* Issue #180 - with the above PCondFlushLine,
* this adds an uneccessary additional line!
* Maybe only if 'classic' ie --vertical-space yes
\*/
if ( indsmart && node->prev != NULL && classic)
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );

/* do not omit elements with attributes */
if ( !hideend || !TY_(nodeHasCM)(node, CM_OMITST) ||
Expand All @@ -2263,11 +2299,11 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
/* fix for bug 530791, don't wrap after */
/* <li> if first child is text node */
if (!(nodeIsLI(node) && TY_(nodeIsText)(node->content)))
PCondFlushLine( doc, contentIndent );
PCondFlushLineSmart( doc, contentIndent );
}
else if ( TY_(nodeHasCM)(node, CM_HTML) || nodeIsNOFRAMES(node) ||
(TY_(nodeHasCM)(node, CM_HEAD) && !nodeIsTITLE(node)) )
TY_(PFlushLine)( doc, contentIndent );
TY_(PFlushLineSmart)( doc, contentIndent );
}

last = NULL;
Expand All @@ -2278,7 +2314,7 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
content->tag && !TY_(nodeHasCM)(content, CM_INLINE) )
{
/* TY_(PFlushLine)(fout, indent); */
TY_(PFlushLine)( doc, contentIndent );
TY_(PFlushLineSmart)( doc, contentIndent );
}

TY_(PPrintTree)( doc, mode, contentIndent, content );
Expand All @@ -2295,7 +2331,7 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
)
)
{
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
if ( !hideend || !TY_(nodeHasCM)(node, CM_OPT) )
{
PPrintEndTag( doc, mode, indent, node );
Expand All @@ -2308,15 +2344,15 @@ void TY_(PPrintTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
{
/* newline before endtag for classic formatting */
if ( classic && !HasMixedContent(node) )
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
PPrintEndTag( doc, mode, indent, node );
}
}

if (!indcont && !hideend && !nodeIsHTML(node) && !classic)
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
else if (classic && node->next != NULL && TY_(nodeHasCM)(node, CM_LIST|CM_DEFLIST|CM_TABLE|CM_BLOCK/*|CM_HEADING*/))
TY_(PFlushLine)( doc, indent );
TY_(PFlushLineSmart)( doc, indent );
}
}
}
Expand All @@ -2333,7 +2369,7 @@ void TY_(PPrintXMLTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
}
else if ( node->type == CommentTag )
{
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
PPrintComment( doc, indent, node);
/* PCondFlushLine( doc, 0 ); */
}
Expand Down Expand Up @@ -2364,7 +2400,7 @@ void TY_(PPrintXMLTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
else if ( TY_(nodeHasCM)(node, CM_EMPTY) ||
(node->type == StartEndTag && !xhtmlOut) )
{
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );
PPrintTag( doc, mode, indent, node );
/* TY_(PFlushLine)( doc, indent ); */
}
Expand All @@ -2384,7 +2420,7 @@ void TY_(PPrintXMLTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )
}
}

PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

if ( TY_(XMLPreserveWhiteSpace)(doc, node) )
{
Expand All @@ -2399,13 +2435,13 @@ void TY_(PPrintXMLTree)( TidyDocImpl* doc, uint mode, uint indent, Node *node )

PPrintTag( doc, mode, indent, node );
if ( !mixed && node->content )
TY_(PFlushLine)( doc, cindent );
TY_(PFlushLineSmart)( doc, cindent );

for ( content = node->content; content; content = content->next )
TY_(PPrintXMLTree)( doc, mode, cindent, content );

if ( !mixed && node->content )
PCondFlushLine( doc, indent );
PCondFlushLineSmart( doc, indent );

PPrintEndTag( doc, mode, indent, node );
/* PCondFlushLine( doc, indent ); */
Expand Down

0 comments on commit f697978

Please sign in to comment.