@@ -23,74 +23,7 @@ import { DocNoteBox } from '../nodes/DocNoteBox';
2323import { DocTable } from '../nodes/DocTable' ;
2424import { DocTableCell } from '../nodes/DocTableCell' ;
2525import { DocEmphasisSpan } from '../nodes/DocEmphasisSpan' ;
26-
27- /**
28- * Helper class used by MarkdownPageRenderer
29- */
30- class SimpleWriter {
31- private _builder : StringBuilder ;
32- private _latestChunk : string | undefined = undefined ;
33- private _previousChunk : string | undefined = undefined ;
34-
35- public constructor ( builder : StringBuilder ) {
36- this . _builder = builder ;
37- }
38-
39- public write ( s : string ) : void {
40- if ( s . length > 0 ) {
41- this . _previousChunk = this . _latestChunk ;
42- this . _latestChunk = s ;
43- this . _builder . append ( s ) ;
44- }
45- }
46-
47- public writeLine ( s : string = '' ) : void {
48- this . write ( s ) ;
49- this . write ( '\n' ) ;
50- }
51-
52- /**
53- * Adds a newline if the file pointer is not already at the start of the line
54- */
55- public ensureNewLine ( ) : void {
56- if ( this . peekLastCharacter ( ) !== '\n' ) {
57- this . write ( '\n' ) ;
58- }
59- }
60-
61- /**
62- * Adds up to two newlines to ensure that there is a blank line above the current line.
63- */
64- public ensureSkippedLine ( ) : void {
65- this . ensureNewLine ( ) ;
66- if ( this . peekSecondLastCharacter ( ) !== '\n' ) {
67- this . write ( '\n' ) ;
68- }
69- }
70-
71- public peekLastCharacter ( ) : string {
72- if ( this . _latestChunk !== undefined ) {
73- return this . _latestChunk . substr ( - 1 , 1 ) ;
74- }
75- return '' ;
76- }
77-
78- public peekSecondLastCharacter ( ) : string {
79- if ( this . _latestChunk !== undefined ) {
80- if ( this . _latestChunk . length > 1 ) {
81- return this . _latestChunk . substr ( - 2 , 1 ) ;
82- }
83- if ( this . _previousChunk !== undefined ) {
84- return this . _previousChunk . substr ( - 1 , 1 ) ;
85- }
86- }
87- return '' ;
88- }
89-
90- public toString ( ) : string {
91- return this . _builder . toString ( ) ;
92- }
93- }
26+ import { SimpleWriter } from './SimpleWriter' ;
9427
9528export interface IMarkdownEmitterOptions {
9629 /**
@@ -100,7 +33,7 @@ export interface IMarkdownEmitterOptions {
10033 onResolveTargetForCodeDestination : ( docLinkTag : DocLinkTag ) => string | undefined ;
10134}
10235
103- interface IRenderContext {
36+ interface IMarkdownEmitterContext {
10437 writer : SimpleWriter ;
10538 insideTable : boolean ;
10639
@@ -119,11 +52,11 @@ interface IRenderContext {
11952 */
12053export class MarkdownEmitter {
12154
122- public static renderNode ( stringBuilder : StringBuilder , docNode : DocNode , options : IMarkdownEmitterOptions ) : string {
55+ public emit ( stringBuilder : StringBuilder , docNode : DocNode , options : IMarkdownEmitterOptions ) : string {
12356 const writer : SimpleWriter = new SimpleWriter ( stringBuilder ) ;
12457
125- const context : IRenderContext = {
126- writer : writer ,
58+ const context : IMarkdownEmitterContext = {
59+ writer,
12760 insideTable : false ,
12861
12962 boldRequested : false ,
@@ -135,14 +68,14 @@ export class MarkdownEmitter {
13568 options
13669 } ;
13770
138- MarkdownEmitter . _writeNode ( docNode , context ) ;
71+ this . _writeNode ( docNode , context ) ;
13972
14073 writer . ensureNewLine ( ) ; // finish the last line
14174
14275 return writer . toString ( ) ;
14376 }
14477
145- private static _getEscapedText ( text : string ) : string {
78+ private _getEscapedText ( text : string ) : string {
14679 const textWithBackslashes : string = text
14780 . replace ( / \\ / g, '\\\\' ) // first replace the escape character
14881 . replace ( / [ * # [ \] _ | ` ~ ] / g, ( x ) => '\\' + x ) // then escape any special characters
@@ -153,13 +86,13 @@ export class MarkdownEmitter {
15386 return textWithBackslashes ;
15487 }
15588
156- private static _writeNode ( docNode : DocNode , context : IRenderContext ) : void {
89+ private _writeNode ( docNode : DocNode , context : IMarkdownEmitterContext ) : void {
15790 const writer : SimpleWriter = context . writer ;
15891
15992 switch ( docNode . kind ) {
16093 case DocNodeKind . PlainText : {
16194 const docPlainText : DocPlainText = docNode as DocPlainText ;
162- MarkdownEmitter . _writePlainText ( docPlainText . text , context ) ;
95+ this . _writePlainText ( docPlainText . text , context ) ;
16396 break ;
16497 }
16598 case DocNodeKind . HtmlStartTag :
@@ -184,7 +117,7 @@ export class MarkdownEmitter {
184117 case DocNodeKind . LinkTag : {
185118 const docLinkTag : DocLinkTag = docNode as DocLinkTag ;
186119 if ( docLinkTag . linkText !== undefined && docLinkTag . linkText . length > 0 ) {
187- const encodedLinkText : string = MarkdownEmitter . _getEscapedText ( docLinkTag . linkText . replace ( / \s + / g, ' ' ) ) ;
120+ const encodedLinkText : string = this . _getEscapedText ( docLinkTag . linkText . replace ( / \s + / g, ' ' ) ) ;
188121 let destination : string | undefined = undefined ;
189122 if ( docLinkTag . codeDestination ) {
190123 destination = context . options . onResolveTargetForCodeDestination ( docLinkTag ) ;
@@ -208,10 +141,10 @@ export class MarkdownEmitter {
208141 const trimmedParagraph : DocParagraph = DocNodeTransforms . trimSpacesInParagraph ( docParagraph ) ;
209142 if ( context . insideTable ) {
210143 writer . write ( '<p>' ) ;
211- MarkdownEmitter . _writeNodes ( trimmedParagraph . nodes , context ) ;
144+ this . _writeNodes ( trimmedParagraph . nodes , context ) ;
212145 writer . write ( '</p>' ) ;
213146 } else {
214- MarkdownEmitter . _writeNodes ( trimmedParagraph . nodes , context ) ;
147+ this . _writeNodes ( trimmedParagraph . nodes , context ) ;
215148 writer . ensureNewLine ( ) ;
216149 writer . writeLine ( ) ;
217150 }
@@ -230,7 +163,7 @@ export class MarkdownEmitter {
230163 prefix = '####' ;
231164 }
232165
233- writer . writeLine ( prefix + ' ' + MarkdownEmitter . _getEscapedText ( docHeading . title ) ) ;
166+ writer . writeLine ( prefix + ' ' + this . _getEscapedText ( docHeading . title ) ) ;
234167 writer . writeLine ( ) ;
235168 break ;
236169 }
@@ -250,7 +183,7 @@ export class MarkdownEmitter {
250183 writer . ensureNewLine ( ) ;
251184 writer . write ( '> ' ) ;
252185 // TODO: Handle newlines
253- MarkdownEmitter . _writeNode ( docNoteBox . content , context ) ;
186+ this . _writeNode ( docNoteBox . content , context ) ;
254187 writer . ensureNewLine ( ) ;
255188 writer . writeLine ( ) ;
256189 break ;
@@ -281,7 +214,7 @@ export class MarkdownEmitter {
281214 if ( docTable . header ) {
282215 const cell : DocTableCell | undefined = docTable . header . cells [ i ] ;
283216 if ( cell ) {
284- MarkdownEmitter . _writeNode ( cell . content , context ) ;
217+ this . _writeNode ( cell . content , context ) ;
285218 }
286219 }
287220 writer . write ( ' |' ) ;
@@ -299,7 +232,7 @@ export class MarkdownEmitter {
299232 writer . write ( '| ' ) ;
300233 for ( const cell of row . cells ) {
301234 writer . write ( ' ' ) ;
302- MarkdownEmitter . _writeNode ( cell . content , context ) ;
235+ this . _writeNode ( cell . content , context ) ;
303236 writer . write ( ' |' ) ;
304237 }
305238 writer . writeLine ( ) ;
@@ -312,7 +245,7 @@ export class MarkdownEmitter {
312245 }
313246 case DocNodeKind . Section : {
314247 const docSection : DocSection = docNode as DocSection ;
315- MarkdownEmitter . _writeNodes ( docSection . nodes , context ) ;
248+ this . _writeNodes ( docSection . nodes , context ) ;
316249 break ;
317250 }
318251 case CustomDocNodeKind . EmphasisSpan : {
@@ -321,7 +254,7 @@ export class MarkdownEmitter {
321254 const oldItalic : boolean = context . italicRequested ;
322255 context . boldRequested = docEmphasisSpan . bold ;
323256 context . italicRequested = docEmphasisSpan . italic ;
324- MarkdownEmitter . _writeNodes ( docEmphasisSpan . nodes , context ) ;
257+ this . _writeNodes ( docEmphasisSpan . nodes , context ) ;
325258 context . boldRequested = oldBold ;
326259 context . italicRequested = oldItalic ;
327260 break ;
@@ -334,20 +267,20 @@ export class MarkdownEmitter {
334267 }
335268 case DocNodeKind . EscapedText : {
336269 const docEscapedText : DocEscapedText = docNode as DocEscapedText ;
337- MarkdownEmitter . _writePlainText ( docEscapedText . decodedText , context ) ;
270+ this . _writePlainText ( docEscapedText . decodedText , context ) ;
338271 break ;
339272 }
340273 case DocNodeKind . ErrorText : {
341274 const docErrorText : DocErrorText = docNode as DocErrorText ;
342- MarkdownEmitter . _writePlainText ( docErrorText . text , context ) ;
275+ this . _writePlainText ( docErrorText . text , context ) ;
343276 break ;
344277 }
345278 default :
346279 throw new Error ( 'Unsupported element kind: ' + docNode . kind ) ;
347280 }
348281 }
349282
350- private static _writePlainText ( text : string , context : IRenderContext ) : void {
283+ private _writePlainText ( text : string , context : IMarkdownEmitterContext ) : void {
351284 const writer : SimpleWriter = context . writer ;
352285
353286 // split out the [ leading whitespace, content, trailing whitespace ]
@@ -381,7 +314,7 @@ export class MarkdownEmitter {
381314 writer . write ( '<i>' ) ;
382315 }
383316
384- writer . write ( MarkdownEmitter . _getEscapedText ( middle ) ) ;
317+ writer . write ( this . _getEscapedText ( middle ) ) ;
385318
386319 if ( context . italicRequested ) {
387320 writer . write ( '</i>' ) ;
@@ -394,9 +327,9 @@ export class MarkdownEmitter {
394327 writer . write ( parts [ 3 ] ) ; // write trailing whitespace
395328 }
396329
397- private static _writeNodes ( docNodes : ReadonlyArray < DocNode > , context : IRenderContext ) : void {
330+ private _writeNodes ( docNodes : ReadonlyArray < DocNode > , context : IMarkdownEmitterContext ) : void {
398331 for ( const docNode of docNodes ) {
399- MarkdownEmitter . _writeNode ( docNode , context ) ;
332+ this . _writeNode ( docNode , context ) ;
400333 }
401334 }
402335
0 commit comments