xref: /AOO41X/main/helpauthoring/HelpAuthoring/Validate.xba (revision 707fc0d4d52eb4f69d89a98ffec6918ca5de6326)
1<?xml version="1.0" encoding="UTF-8"?>
2<!DOCTYPE script:module PUBLIC "-//OpenOffice.org//DTD OfficeDocument 1.0//EN" "module.dtd">
3<script:module xmlns:script="http://openoffice.org/2000/script" script:name="Validate" script:language="StarBasic">
4&apos;############################################
5&apos;  VALIDATION ROUTINES
6&apos;
7&apos;  May, 19 2004 - fpe
8&apos;############################################
9
10Dim sSwitchType As String
11Dim sCellSwitchType As String
12Dim sCaseType As String
13Dim sCellCaseType As String
14Dim sDefaultType As String
15Dim sCellDefaultType As String
16Dim bDefaultSet As Boolean
17Dim bCellDefaultSet As Boolean
18Dim bCaseSet As Boolean
19Dim bCellCaseSet As Boolean
20Dim aTagsOpen(0) As String
21Dim aCellTagsOpen(0) As String
22Dim bWarn As Boolean
23Dim bWarnEmptyPara As Boolean
24Dim bWarnParaNoID As Boolean
25
26
27Sub ValidateXHP
28    Validate
29End Sub
30
31Sub Validate
32
33    If not IsHelpFile Then
34        msgbox(strErr_NoHelpFile)
35        Exit Sub
36    End If
37
38    oDoc = StarDesktop.CurrentComponent
39    sSwitchType = &quot;&quot;
40    sCaseType = &quot;&quot;
41    sDefaultType = &quot;&quot;
42    bWarn = TRUE
43    bWarnEmptyPara = TRUE
44    bWarnParaNoID = TRUE
45
46    CheckMetaData(oDoc)
47    CheckHeading(oDoc)
48
49    Enum = oDoc.Text.createEnumeration
50    Do While Enum.hasMoreElements
51
52        TextElement = Enum.nextElement
53        If TextElement.supportsService(&quot;com.sun.star.text.Paragraph&quot;) Then        &apos; we are a paragraph
54
55            CheckSwitches(TextElement)
56            CheckParaID(TextElement)
57            CheckParaFormat(TextElement)
58            CheckTags(TextElement)
59            CheckInlineTags(TextElement)
60
61        ElseIf  TextElement.supportsService(&quot;com.sun.star.text.TextTable&quot;) Then
62
63            If sSwitchType &lt;&gt; &quot;&quot; AND (sCaseType = &quot;&quot; AND sDefaultType = &quot;&quot;) Then &apos;&lt;------
64                Terminate(&quot;Switch must be closed or case/default must be opened before a table starts.&quot;,tmpCellElement)
65            End If
66
67            CheckCell(TextElement)
68        End If
69    Loop
70
71    If sCaseType &lt;&gt; &quot;&quot; Then
72        Terminate(&quot;Previous case (&quot;+sCaseType+&quot;) not closed!&quot;,TextElement)
73    End If
74
75    If sDefaultType &lt;&gt; &quot;&quot; Then
76        Terminate(&quot;Previous default not closed!&quot;,TextElement)
77    End If
78
79    If sSwitchType &lt;&gt; &quot;&quot; Then
80        Terminate(&quot;Previous switch (&quot;+sSwitchType+&quot;) not closed!&quot;,TextElement)
81    End If
82
83    If ubound(aTagsOpen()) &gt; 0 Then
84        Terminate(&quot;Element &quot;+aTagsOpen(ubound(aTagsOpen()))+&quot; not closed&quot;,TextElement)
85    End If
86
87    msgbox(&quot;Validation finished.&quot;)
88
89End Sub
90
91&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
92&apos; CHECKCELL
93&apos; checks a table cell contents
94&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
95
96Sub CheckCell(TE As Object)
97    On Local Error Goto ERRHANDLE:
98
99    CellName = &quot;A1&quot;
100    Cell = TE.getCellByName(CellName)
101    tmpCellEnum = Cell.createEnumeration
102    tmpCellElement = tmpCellEnum.nextElement
103
104    Rows = TE.getRows
105    Cols = TE.getColumns
106
107    ReDim aCellTagsOpen(0)
108
109    For RowIndex = 1 to Rows.getCount()
110
111        For ColIndex = 1 to Cols.getCount()
112
113            CellName = Chr(64 + ColIndex) &amp; RowIndex
114            Cell = TE.getCellByName(CellName)
115            CellEnum = Cell.createEnumeration
116
117            Do While CellEnum.hasMoreElements
118
119                CellElement = CellEnum.nextElement      &apos; &lt;-- MODIFY, check closed switches within cells
120
121                If CellElement.supportsService(&quot;com.sun.star.text.Paragraph&quot;) Then
122                    CheckSwitchesInCell(CellElement)
123                    CheckParaID(CellElement)
124                    CheckParaFormat(CellElement)
125                    CheckTagsInCell(CellElement)
126                    CheckInlineTags(CellElement)
127                EndIf
128
129            Loop
130
131            If sCellCaseType &lt;&gt; &quot;&quot; Then
132                Terminate(&quot;Previous case (&quot;+sCellCaseType+&quot;) not closed!&quot;,CellElement)
133            End If
134
135            If sCellSwitchType &lt;&gt; &quot;&quot; Then
136                Terminate(&quot;Previous switch (&quot;+sCellSwitchType+&quot;) not closed!&quot;,CellElement)
137            End If
138
139            If ubound(aCellTagsOpen()) &gt; 0 Then
140                Terminate(&quot;Element &quot;+aCellTagsOpen(ubound(aCellTagsOpen()))+&quot; not closed&quot;,CellElement)
141            End If
142
143        Next
144    Next
145
146    ERRHANDLE:
147        If Err &lt;&gt; 0 Then
148            msgbox &quot;Error: &quot;+chr(13)+ Error$,48,&quot;D&apos;oh!&quot;
149        End If
150End Sub
151
152&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
153&apos; CHECK PARA ID
154&apos; checks a paragraph for an ID
155&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
156
157Sub CheckParaID(TE As Object)
158
159    If Left(TE.ParaStyleName,4) = &quot;hlp_&quot; AND Not(Left(TE.ParaStyleName,8) = &quot;hlp_aux_&quot;) Then
160
161        sText = TE.GetString
162
163        If sText = &quot;&quot; Then
164            If bWarnEmptyPara Then
165                Warn(&quot;Empty Paragraph&quot;,&quot;Empty paragraphs should be avoided. Do not use empty paragraphs for formatting purpose.&quot;,TE)
166                bWarnEmptyPara = FALSE
167            End If
168        Else
169
170            TP = TE.createEnumeration
171            Ct = 0
172            posID = 0
173
174            While TP.hasmoreElements
175                Ct = Ct+1
176                TPE = TP.nextElement
177                If TPE.TextPortionType=&quot;TextField&quot; Then
178                    If TPE.TextField.TextFieldMaster.Name=&quot;ID&quot; Then
179                        posID = Ct
180                    End If
181                End If
182                &apos; Lets cheat and allow empty strings before the ID -- otherwise we&apos;ll get
183                &apos; a validation error if a paragraph starts at the top of a page after
184                &apos; a page break (for whatever reason)
185                If TPE.String = &quot;&quot; Then
186                    Ct = Ct-1
187                End If
188            Wend
189
190            If posID = 0 Then
191                If bWarnParaNoID Then
192                    Warn(&quot;Paragraph has no id.&quot;,&quot;IDs will be assigned on safe. You can also assign an ID using the Assign Paragraph ID menu item&quot;,TPE)
193                    bWarnParaNoID = FALSE
194                    InsertNewParaData
195                Else
196                    oCur = TE.getText.createTextCursorByRange(TE)
197                    thiscomponent.getcurrentcontroller.select(oCur)
198                    InsertNewParaData
199                End If
200            ElseIf posID &gt; 1 Then
201                Terminate(&quot;Paragraph ID not at the start of the paragraph. The paragraph ID must be the first element of a paragraph. Move the ID to the beginning of the paragraph&quot;,TPE)
202            End If
203
204        End If
205
206    End If
207End Sub
208
209&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
210&apos; CHECK PARA FORMAT
211&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
212Sub CheckParaFormat(TE As Object)
213
214    sText = TE.GetString
215    If Left(TE.ParaStyleName,4) &lt;&gt; &quot;hlp_&quot; AND sText &lt;&gt; &quot;&quot; Then    &apos; just disregard empty paras in wrong formats
216        Warn(&quot;Invalid paragraph format. Contents will be lost.&quot;,_
217             &quot;Use only the paragraph styles starting with &quot;&quot;hlp_&quot;&quot;.&quot;+_
218             &quot; Paragraphs in other formats will be lost on export&quot;,TE)
219    End If
220
221End Sub
222
223&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
224&apos; CHECK SWITCHES
225&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
226Sub CheckSwitches(TE As Object)
227
228    If TE.ParaStyleName=&quot;hlp_aux_switch&quot; Then                 &apos; we are a switch or case or default
229        sText = TE.GetString                                    &apos; get the switch contents
230
231        If Left(sText,8) = &quot;&lt;SWITCH &quot; Then                             &apos; an opening switch tag
232
233            If sSwitchType = &quot;&quot; Then                                  &apos; no other switch is open
234                sSwitchType = Right(sText,Len(sText)-16)
235                sSwitchType = Left(sSwitchType,InStr(sSwitchType,&quot;&quot;&quot;&quot;)-1)
236
237                If (sSwitchType &lt;&gt; &quot;sys&quot; AND sSwitchType &lt;&gt; &quot;appl&quot; AND sSwitchType &lt;&gt; &quot;distrib&quot;) Then
238                    Terminate(&quot;Unknown switch type &quot;&quot;&quot;+sSwitchType+&quot;&quot;&quot;&quot;,TE)
239                End If
240
241            Else
242                Terminate(&quot;Previous switch (&quot;+sSwitchType+&quot;) not closed!&quot;,TE)
243            End If
244
245        End If  &apos; OPENING SWITCH
246
247        If Left(sText,8) = &quot;&lt;/SWITCH&quot; Then                             &apos; a closing switch tag
248
249            If sSwitchType = &quot;&quot; Then                                  &apos; there was no switch open
250                Terminate(&quot;No switch open!&quot;,TE)
251            Else
252                If not(bCaseSet OR bDefaultSet) Then
253                    Terminate(&quot;Empty switch&quot;,TE)
254                End If
255
256                If sCaseType &lt;&gt; &quot;&quot; Then                                 &apos; there is still a case open
257                    Terminate(&quot;Previous case (&quot;+sCaseType+&quot;) not closed!&quot;,TE)
258                End If
259                sSwitchType = &quot;&quot;
260                bDefaultSet = FALSE
261                bCaseSet = FALSE
262            End If
263
264        End If  &apos; CLOSING SWITCH
265
266        If Left(sText,6) = &quot;&lt;CASE &quot; Then                               &apos; an opening case tag
267
268            If bDefaultSet Then
269                Terminate(&quot;No case after default allowed.&quot;,TE)
270            End If
271
272            If sCaseType = &quot;&quot; Then
273                sCaseType = Right(sText,Len(sText)-14)
274                sCaseType = Left(sCaseType,InStr(sCaseType,&quot;&quot;&quot;&quot;)-1)
275                bCaseSet = TRUE
276                If sSwitchType = &quot;&quot; Then
277                    Terminate(&quot;Case without switch&quot;,TE)
278                End If
279            Else
280                Terminate(&quot;Previous case (&quot;+sCaseType+&quot;) not closed!&quot;,TE)
281            End If
282
283        End If  &apos; OPENING CASE
284
285        If Left(sText,6) = &quot;&lt;/CASE&quot; Then                               &apos; a closing case tag
286
287            If sCaseType = &quot;&quot; Then
288                Terminate(&quot;No case open!&quot;,TE)
289            Else
290                sCaseType = &quot;&quot;
291            End If
292
293        End If  &apos; CLOSING  CASE
294
295        If Left(sText,8) = &quot;&lt;DEFAULT&quot; Then                             &apos; an opening default tag
296
297            If sCaseType = &quot;&quot; Then
298                If (sDefaultType &lt;&gt; &quot;&quot; OR bDefaultSet) Then
299                    Terminate(&quot;Multiple default not allowed.&quot;,TE)
300                Else
301                    sDefaultType = &quot;DEFAULT&quot;
302
303                    If sSwitchType = &quot;&quot; Then
304                        Terminate(&quot;Default without switch&quot;,TE)
305                    End If
306                End If
307                sDefaultType = &quot;DEFAULT&quot;
308                bDefaultSet = TRUE
309            Else
310                Terminate(&quot;Previous case (&quot;+sCaseType+&quot;) not closed!&quot;,TE)
311            End If
312
313        End If  &apos; OPENING CASE
314
315        If Left(sText,9) = &quot;&lt;/DEFAULT&quot; Then                                &apos; a closing default tag
316
317            If sDefaultType &lt;&gt; &quot;DEFAULT&quot; Then
318                Terminate(&quot;No default open!&quot;,TE)
319            Else
320                sDefaultType = &quot;&quot;
321            End If
322
323        End If  &apos; CLOSING  CASE
324    Else  &apos; We are not hlp_aux_switch
325        If (sSwitchType &lt;&gt; &quot;&quot; AND sCaseType = &quot;&quot; AND sDefaultType = &quot;&quot;) Then
326            Terminate(&quot;Nothing allowed between switch and case or default or /case or /default and /switch&quot;, TE)
327        End If
328    End If
329
330End Sub
331
332&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
333&apos; CHECK SWITCHES IN A CELL
334&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
335Sub CheckSwitchesInCell(CE As Object)
336
337    If CE.ParaStyleName=&quot;hlp_aux_switch&quot; Then                 &apos; we are a switch or case or default
338        sText = CE.GetString                                    &apos; get the switch contents
339
340        If Left(sText,8) = &quot;&lt;SWITCH &quot; Then                             &apos; an opening switch tag
341
342            If sCellSwitchType = &quot;&quot; Then                                  &apos; no other switch is open
343                sCellSwitchType = Right(sText,Len(sText)-16)
344                sCellSwitchType = Left(sCellSwitchType,InStr(sCellSwitchType,&quot;&quot;&quot;&quot;)-1)
345
346                If (sCellSwitchType &lt;&gt; &quot;sys&quot; AND sCellSwitchType &lt;&gt; &quot;appl&quot; AND sCellSwitchType &lt;&gt; &quot;distrib&quot;) Then
347                    Terminate(&quot;Unknown switch type &quot;&quot;&quot;+sCellSwitchType+&quot;&quot;&quot;&quot;,CE)
348                End If
349
350            Else
351                Terminate(&quot;Previous switch (&quot;+sCellSwitchType+&quot;) not closed!&quot;,CE)
352            End If
353
354        End If  &apos; OPENING SWITCH
355
356        If Left(sText,8) = &quot;&lt;/SWITCH&quot; Then                             &apos; a closing switch tag
357
358            If sCellSwitchType = &quot;&quot; Then                                  &apos; there was no switch open
359                Terminate(&quot;No switch open!&quot;,CE)
360            Else
361                If not(bCellCaseSet OR bCellDefaultSet) Then
362                    Terminate(&quot;Empty switch&quot;,CE)
363                End If
364
365                If sCellCaseType &lt;&gt; &quot;&quot; Then                                 &apos; there is still a case open
366                    Terminate(&quot;Previous case (&quot;+sCellCaseType+&quot;) not closed!&quot;,CE)
367                End If
368                sCellSwitchType = &quot;&quot;
369                bCellDefaultSet = FALSE
370                bCellCaseSet = FALSE
371            End If
372
373        End If  &apos; CLOSING SWITCH
374
375        If Left(sText,6) = &quot;&lt;CASE &quot; Then                               &apos; an opening case tag
376
377            If bCellDefaultSet Then
378                Terminate(&quot;No case after default allowed.&quot;,CE)
379            End If
380
381            If sCellCaseType = &quot;&quot; Then
382                sCellCaseType = Right(sText,Len(sText)-14)
383                sCellCaseType = Left(sCellCaseType,InStr(sCellCaseType,&quot;&quot;&quot;&quot;)-1)
384                bCellCaseSet = TRUE
385                If sCellSwitchType = &quot;&quot; Then
386                    Terminate(&quot;Case without switch&quot;,CE)
387                End If
388            Else
389                Terminate(&quot;Previous case (&quot;+sCellCaseType+&quot;) not closed!&quot;,CE)
390            End If
391
392        End If  &apos; OPENING CASE
393
394        If Left(sText,6) = &quot;&lt;/CASE&quot; Then                               &apos; a closing case tag
395
396            If sCellCaseType = &quot;&quot; Then
397                Terminate(&quot;No case open!&quot;,CE)
398            Else
399                sCellCaseType = &quot;&quot;
400            End If
401
402        End If  &apos; CLOSING  CASE
403
404        If Left(sText,8) = &quot;&lt;DEFAULT&quot; Then                             &apos; an opening default tag
405
406            If sCellCaseType = &quot;&quot; Then
407                If (sCellDefaultType &lt;&gt; &quot;&quot; OR bCellDefaultSet) Then
408                    Terminate(&quot;Multiple default not allowed.&quot;,CE)
409                Else
410                    sCellDefaultType = &quot;DEFAULT&quot;
411
412                    If sCellSwitchType = &quot;&quot; Then
413                        Terminate(&quot;Default without switch&quot;,CE)
414                    End If
415                End If
416                sCellDefaultType = &quot;DEFAULT&quot;
417                bCellDefaultSet = TRUE
418            Else
419                Terminate(&quot;Previous case (&quot;+sCellCaseType+&quot;) not closed!&quot;,CE)
420            End If
421
422        End If  &apos; OPENING CASE
423
424        If Left(sText,9) = &quot;&lt;/DEFAULT&quot; Then                                &apos; a closing default tag
425
426            If sCellDefaultType &lt;&gt; &quot;DEFAULT&quot; Then
427                Terminate(&quot;No default open!&quot;,CE)
428            Else
429                sCellDefaultType = &quot;&quot;
430            End If
431
432        End If  &apos; CLOSING  CASE
433    Else  &apos; We are not hlp_aux_switch
434        If (sCellSwitchType &lt;&gt; &quot;&quot; AND sCellCaseType = &quot;&quot; AND sCellDefaultType = &quot;&quot;) Then
435            Terminate(&quot;Nothing allowed between switch and case or default or /case or /default and /switch&quot;, CE)
436        End If
437    End If
438
439
440End Sub
441
442
443&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
444&apos; TERMINATE VALIDATION WITH AN ERROR MESSAGE
445&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
446Sub Terminate(sStr As String, TE As Object)
447
448    oCur = TE.getText.createTextCursorByRange(TE)
449    thiscomponent.getcurrentcontroller.select(oCur)
450    msgbox sStr,48,&quot;D&apos;oh!&quot;
451    Stop
452
453End Sub
454
455&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
456&apos; SHOW A WARNING
457&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
458Sub Warn(sWarn As String, sSolv As String, Optional TE As Object)
459
460    If bWarn Then
461        BasicLibraries.LoadLibrary(&quot;HelpAuthoring&quot;)
462        oDialog = LoadDialog(&quot;HelpAuthoring&quot;, &quot;dlgWarn&quot;)
463        oTxtWarn = oDialog.GetControl(&quot;txtWarning&quot;)
464        oTxtWarn.Text = sWarn
465        oTxtSolv = oDialog.GetControl(&quot;txtSolution&quot;)
466        oTxtSolv.Text = sSolv
467
468        If not(IsMissing(TE)) Then
469            oCur = TE.getText.createTextCursorByRange(TE)
470            thiscomponent.getcurrentcontroller.select(oCur)
471        End If
472
473        If oDialog.Execute() = 1 Then
474            oCbWarn = oDialog.GetControl(&quot;cbWarn&quot;)
475            If oCbWarn.State = 1 Then
476                bWarn = FALSE
477            End If
478            Exit Sub
479        Else
480            Stop
481        End If
482    End If
483End Sub
484
485&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
486&apos; CHECK DOCUMENT META DATA
487&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
488Sub CheckMetaData(oDoc As Object)
489
490    sTopicID = oDoc.DocumentInfo.GetUserFieldValue(1)
491
492    If sTopicID &lt;&gt; AlphaNum(sTopicID) OR sTopicID=&quot;&quot; Then
493        sTopicID = &quot;topic_&quot;+CreateID &apos; create a topic id
494    End If
495
496    oDoc.DocumentInfo.SetUserFieldValue(1,sTopicID)
497    sCreated = oDoc.DocumentInfo.GetUserFieldValue(2)
498    sEdited = oDoc.DocumentInfo.GetUserFieldValue(3)
499    sTitle = oDoc.DocumentInfo.Title
500
501    If sTitle=&quot;&quot; OR sTitle=&quot;&lt;Set Topic Title&gt;&quot; Then
502        Enum = document.Text.createEnumeration
503        Do While Enum.hasMoreElements
504            TextElement = Enum.nextElement
505            If TextElement.supportsService(&quot;com.sun.star.text.Paragraph&quot;) Then
506                If Left(TextElement.ParaStyleName,8)=&quot;hlp_head&quot; Then
507                    Enum2 = TextElement.createEnumeration
508                    While Enum2.hasMoreElements
509                        TextPortion = Enum2.nextElement
510                        If Not(TextPortion.TextPortionType=&quot;TextField&quot;) Then
511                            strg = strg + TextPortion.String
512                        End If
513                    Wend
514                    document.DocumentInfo.Title = strg
515                    Exit Do
516                End If
517            End If
518        Loop
519    End If
520
521    sIndex = oDoc.DocumentInfo.GetUserFieldValue(0)
522
523End Sub
524
525&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
526&apos; CHECK IF HEADING EXISTS
527&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
528Sub CheckHeading(oDoc As Object)
529
530End Sub
531
532&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
533&apos; CHECK FOR CORRECT INLINE TAGS
534&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
535Sub CheckInlineTags(TE As Object)
536
537
538
539    If Left(TE.ParaStyleName,4)=&quot;hlp_&quot; AND (Left(TE.ParaStyleName,8)&lt;&gt;&quot;hlp_aux_&quot; OR TE.ParaStyleName=&quot;hlp_aux_bookmark&quot;) Then
540
541        Dim aTokens(0) As Object
542        Dim aInlineTagsOpen(0) As String
543        TP = TE.createEnumeration
544
545        While TP.hasmoreElements
546            sDim = ubound(aTokens())+1
547            ReDim Preserve aTokens(sDim) As Object
548            aTokens(sDim) = TP.nextElement
549        Wend
550
551        For i=1 to ubound(aTokens())
552            Token = aTokens(i)
553
554            If Token.supportsService(&quot;com.sun.star.text.TextField&quot;) Then
555                sTag = Token.TextField.TextFieldMaster.Name
556
557                If Right(sTag,1)=&quot;_&quot; Then   &apos; a tag starts
558
559                    sTagName = Left(sTag,Len(sTag)-1)
560
561                    &apos; check for forbidden tags in paragraphs
562                    sTagFormat = TagFormatIsCorrect(sTagName, TE.ParaStyleName)
563                    If sTagFormat &lt;&gt; &quot;&quot; Then
564                        Terminate(sTagName+&quot; element has wrong paragraph style (&quot;+TE.ParaStyleName+&quot;).&quot;+chr(13)+&quot;Must be &quot;+sTagFormat,Token)
565                    End If
566
567                    sDim = ubound(aInlineTagsOpen())+1
568                    Redim Preserve aInlineTagsOpen(sDim) as String
569                    aInlineTagsOpen(sDim)=sTagName
570
571                ElseIf Left(sTag,1)=&quot;_&quot; Then  &apos; a tag ends, all other cases are empty tags
572
573                    sTagName = Right(sTag,Len(sTag)-1)
574
575                    &apos; check for forbidden tags in paragraphs
576                    sTagFormat = TagFormatIsCorrect(sTagName, TE.ParaStyleName)
577                    If sTagFormat &lt;&gt; &quot;&quot; Then
578                        Terminate(sTagName+&quot; element has wrong paragraph style (&quot;+TE.ParaStyleName+&quot;).&quot;+chr(13)+&quot;Must be &quot;+sTagFormat,Token)
579                    End If
580
581                    If ubound(aInlineTagsOpen()) &gt; 0 Then
582                        If aInlineTagsOpen(ubound(aInlineTagsOpen())) &lt;&gt; sTagName Then
583                            Terminate(&quot;Inline Element &quot;+aInlineTagsOpen(ubound(aInlineTagsOpen()))+&quot; not closed&quot;,Token)
584                        End If
585                        sDim = ubound(aInlineTagsOpen())-1
586                    Else
587                        Terminate(&quot;No opening tag for &quot;+sTagName,Token)
588                    End If
589                    Redim Preserve aInlineTagsOpen(sDim) as String
590
591                Else &apos; empty tag
592                    sTagName = sTag
593                    sTagFormat = TagFormatIsCorrect(sTagName, TE.ParaStyleName)
594                    If sTagFormat &lt;&gt; &quot;&quot; Then
595                        Terminate(sTagName+&quot; element has wrong paragraph style (&quot;+TE.ParaStyleName+&quot;).&quot;+chr(13)+&quot;Must be &quot;+sTagFormat,Token)
596                    End If
597
598                EndIf
599            ElseIf (i &gt; 1) AND (Trim(Token.String) &lt;&gt; &quot;&quot;) Then
600                If aInlineTagsOpen(ubound(aInlineTagsOpen())) = &quot;SWITCHINLINE&quot; Then
601                    Terminate(&quot;No text allowed here.&quot;,Token)
602                End If
603            End If
604        Next
605
606    If ubound(aInlineTagsOpen()) &gt; 0 Then
607        Terminate(&quot;Inline Element &quot;+aInlineTagsOpen(ubound(aInlineTagsOpen()))+&quot; not closed&quot;,Token)
608    End If
609
610    End If
611End Sub
612
613&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
614&apos; CHECK FOR CORRECT TAGS
615&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
616Sub CheckTags(TE As Object)
617    If (Left(TE.ParaStyleName,8) = &quot;hlp_aux_&quot; AND TE.ParaStyleName &lt;&gt; &quot;hlp_aux_bookmark&quot;) Then
618
619    TP = TE.createEnumeration
620
621    While TP.hasmoreElements
622        TPE = TP.nextElement
623
624        If TPE.supportsService(&quot;com.sun.star.text.TextField&quot;) Then
625            sTag = TPE.TextField.TextFieldMaster.Name
626            If Right(sTag,1)=&quot;_&quot; Then   &apos; a tag starts
627
628                sTagName = Left(sTag,Len(sTag)-1)
629                sDim = ubound(aTagsOpen())+1
630                Redim Preserve aTagsOpen(sDim) as String
631                aTagsOpen(sDim)=sTagName
632
633            ElseIf Left(sTag,1)=&quot;_&quot; Then  &apos; a tag ends, all other cases are empty tags
634
635                sTagName = Right(sTag,Len(sTag)-1)
636                If ubound(aTagsOpen()) &gt; 0 Then
637                    If aTagsOpen(ubound(aTagsOpen())) &lt;&gt; sTagName Then
638                        Terminate(&quot;No close tag for &quot;+aTagsOpen(ubound(aTagsOpen())),TPE)
639                    Else
640                        sDim = ubound(aTagsOpen())-1
641                    End If
642                Else
643                    Terminate(&quot;No opening tag for &quot;+sTagName,TPE)
644                End If
645                Redim Preserve aTagsOpen(sDim) as String
646
647            Else &apos; empty tags
648
649            EndIf
650        End If
651    Wend
652    End If
653End Sub
654
655&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
656&apos; CHECK FOR CORRECT TAGS IN A TABLE CELL
657&apos;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
658Sub CheckTagsInCell(CE As Object)
659    If (Left(CE.ParaStyleName,8) = &quot;hlp_aux_&quot; AND CE.ParaStyleName &lt;&gt; &quot;hlp_aux_bookmark&quot;) Then
660
661    CP = CE.createEnumeration
662
663    While CP.hasmoreElements
664        CPE = CP.nextElement
665
666        If CPE.supportsService(&quot;com.sun.star.text.TextField&quot;) Then
667            sTag = CPE.TextField.TextFieldMaster.Name
668            If Right(sTag,1)=&quot;_&quot; Then   &apos; a tag starts
669
670                sTagName = Left(sTag,Len(sTag)-1)
671                sDim = ubound(aCellTagsOpen())+1
672                Redim Preserve aCellTagsOpen(sDim) as String
673                aCellTagsOpen(sDim)=sTagName
674
675            ElseIf Left(sTag,1)=&quot;_&quot; Then  &apos; a tag ends, all other cases are empty tags
676
677                sTagName = Right(sTag,Len(sTag)-1)
678                If ubound(aCellTagsOpen()) &gt; 0 Then
679                    If aCellTagsOpen(ubound(aCellTagsOpen())) &lt;&gt; sTagName Then
680                        Terminate(&quot;No close tag for &quot;+aCellTagsOpen(ubound(aCellTagsOpen())),CPE)
681                    Else
682                        sDim = ubound(aCellTagsOpen())-1
683                    End If
684                Else
685                    Terminate(&quot;No opening tag for &quot;+sTagName,CPE)
686                End If
687                Redim Preserve aCellTagsOpen(sDim) as String
688
689            EndIf
690        End If
691    Wend
692    End If
693End Sub
694
695</script:module>