Attachment 'text_pdf.py'

Download

   1 # -*- coding: iso-8859-1 -*-
   2 """
   3     MoinMoin - "text/pdf" Formatter
   4 
   5     Copyright (c) 2005 by OR Soft GmbH, based on other formatters (c) by Jürgen Hermann <jh@web.de>
   6     All rights reserved, see COPYING for details.
   7 
   8     ORS modifications:
   9         14.09.05 RS derived from text_html and text_word
  10         27.09.05 RS upgrade to 1.3.5, old code removed
  11 """
  12 
  13 # Imports
  14 import cgi, string, sys, time, os, copy, traceback
  15 from MoinMoin.formatter.base import FormatterBase
  16 from MoinMoin import wikiutil, config, user, webapi, i18n
  17 
  18 from MoinMoin.Page import Page
  19 #ABP REPORTLAB
  20 from reportlab.platypus import SimpleDocTemplate, Paragraph, Spacer, Frame, Image
  21 from reportlab.lib.units import inch, cm
  22 from reportlab.lib.pagesizes import A4
  23 from reportlab.lib.styles import getSampleStyleSheet
  24 from reportlab.lib.colors import Color
  25 from reportlab.lib.enums import TA_LEFT, TA_RIGHT, TA_CENTER, TA_JUSTIFY
  26 from reportlab.lib.sequencer import Sequencer
  27 from reportlab.lib.utils import ImageReader
  28 from reportlab.pdfgen.canvas import Canvas
  29 
  30 
  31 #from reportlab.rl_config import defaultPageSize
  32 #ABP end
  33 
  34 DOC_SUFFIX = ".pdf"  # perhaps put this in config.py as pdf_suffix?
  35 
  36 #############################################################################
  37 ### PDF Formatter
  38 #############################################################################
  39 
  40 _debug=1
  41 
  42 
  43 class Formatter(FormatterBase):
  44     """
  45         Send HTML data.
  46     """
  47 
  48     hardspace = '&#160;'
  49     hardspace = ' '
  50 
  51 
  52 
  53     def __init__(self, request, **kw):
  54         if _debug:
  55             traceback.print_stack(limit=1,file=sys.stdout)
  56         apply(FormatterBase.__init__, (self, request), kw)
  57 #RS additional property "mimetype"
  58         self.mimetype="text/pdf"
  59         sys.stderr.write("\nThis is the PDF Formatter....\n")
  60 #RS end
  61         self.dead=0
  62         self.store_text=0 # store text in self._text instead of emitting it
  63         self.recordedtext=""
  64         self.recordedcursor=0
  65         # inline tags stack. When an inline tag is called, it goes into
  66         # the stack. When a block element starts, all inline tags in
  67         # the stack are closed.
  68         self._inlineStack = []
  69 
  70         self._in_li = 0
  71         self._first_li = 0
  72         self._first_tr = 0
  73         self._first_td = 0
  74         self._table_start=0
  75         self._ignore_next_paragraph=0
  76         self.list_levels={'ul':0,'ol':0,'dl':0,'table':0,'all':0}
  77         self.last_indent_type=''
  78         self._in_code = 0
  79         self._base_depth = 0
  80         self._in_code_area = 0
  81         self._in_code_line = 0
  82         self._code_area_num = 0
  83         self._code_area_js = 0
  84         self._code_area_state = ['', 0, -1, -1, 0]
  85         self._show_section_numbers = None
  86         self._content_ids = []
  87         self.pagelink_preclosed = False
  88         self._is_included = kw.get('is_included',False)
  89         self.request = request
  90         self.cfg = request.cfg
  91 #        self.targetdir=kw.get('targetdir',config.data_dir)
  92         self.targetdir=kw.get('targetdir',request.cfg.data_dir)
  93 
  94 # pdf style-definitions
  95         self.styles= getSampleStyleSheet()
  96         self.styleTitle= copy.deepcopy(self.styles['Title'])
  97         self.styleH1= copy.deepcopy(self.styles['Heading1'])
  98         self.styleH1.fontSize= 18
  99         self.styleH1.spaceBefore= 12 #is ignored at the top of a frame
 100         self.styleH1.spaceAfter= 7 #is ignored at the bottom of a frame
 101         self.styleH1.leading= 22 #is the spacing between adjacent lines of text
 102         self.styleH2= copy.deepcopy(self.styles['Heading2'])
 103         self.styleH2.fontSize= 16
 104         self.styleH2.spaceBefore= 12
 105         self.styleH2.spaceAfter= 7
 106         self.styleH2.leading= 20
 107         self.styleH3= copy.deepcopy(self.styles['Heading3'])
 108         self.styleH3.fontSize= 14
 109         self.styleH3.spaceBefore= 12
 110         self.styleH3.spaceAfter= 7
 111         self.styleH3.leading= 18
 112         self.styleH4= copy.deepcopy(self.styles['Heading3'])
 113         self.styleH4.fontName= "Times-BoldItalic"
 114         self.styleH4.fontSize= 12
 115         self.styleH4.spaceBefore= 12
 116         self.styleH4.spaceAfter= 7
 117         self.styleH4.leading= 16
 118         self.styleH5= copy.deepcopy(self.styles['Heading3'])
 119         self.styleH5.fontName= "Times-Italic"
 120         self.styleH5.fontSize= 12
 121         self.styleH5.spaceBefore= 12
 122         self.styleH5.spaceAfter= 7
 123         self.styleH5.leading= 14
 124         self.standardstyle= copy.deepcopy(self.styles['Normal'])
 125         self.standardstyle.spaceBefore= 6 
 126         self.standardstyle.spaceAfter= 6 
 127         self.standardstyle.leading= 13
 128         self.styleCode= copy.deepcopy(self.styles['Code'])
 129         self.styleBullet= copy.deepcopy(self.styles['Bullet'])
 130         self.styleBullet.spaceBefore= 6
 131         self.styleBullet.spaceAfter= 6
 132         self.styleBullet.leading= 13
 133         self.styleBullet.bulletFontName= "Symbol"
 134         self.styleBullet.leftIndent= 14
 135         self.styleBullet.bulletIndent= 4
 136         self.styleBullet.firstLineIndent= 0
 137         self.styleItalic= copy.deepcopy(self.styles['Italic'])
 138         self.styleDefinition= copy.deepcopy(self.styles['Definition'])
 139         self.currentstyle= copy.deepcopy(self.standardstyle)
 140 
 141         self.story= []
 142         self.para_story= ""
 143         self.title= ''
 144         self.bulletText= None
 145         self.seq= Sequencer()
 146         self.OLnumber= ""
 147         self.oltype= None
 148         self.olstart= None
 149         self.nobullet= 0
 150         self.li_marker= []
 151         self.p_marker= None
 152         self.styleStack= Privatestack()
 153         self.bulletStack= Privatestack()
 154         self.indenttypeStack= Privatestack()
 155         self.oltypeStack= Privatestack()
 156         self.p_markerStack= Privatestack()
 157 
 158         if not hasattr(request, '_fmt_hd_counters'):
 159             request._fmt_hd_counters = []
 160         self.document=None
 161         self.pdf_host= None
 162         self.doc= None
 163         self.doccount=0
 164         self.tt_start=0
 165         self.PAGE_HEIGHT= A4[1]
 166         self.PAGE_WIDTH= A4[0]
 167 
 168 # not by SimpleDocTemplate        self.f = Frame(inch, inch, 6*inch, 9*inch, showBoundary=1)
 169 
 170     def _reset_indents(self):
 171         if _debug:
 172             traceback.print_stack(limit=1,file=sys.stdout)
 173         self._in_li = 0
 174         self._first_li = 0
 175         self._first_tr = 0
 176         self._first_td = 0
 177         self._table_start=0
 178         self._ignore_next_paragraph=0
 179         self.list_levels={'ul':0,'ol':0,'dl':0,'table':0,'all':0}
 180         self.last_indent_type=''
 181     def FatalEnd(self):
 182         """
 183         make sure we do not leave any ActiveX corpses behind if errors occur
 184         """
 185         if _debug:
 186             traceback.print_stack(limit=1,file=sys.stdout)
 187         try:
 188             if self.document is not None:
 189 #                pass
 190 #TODO
 191 ##                self.pdf_host.drawText(self.document)
 192 ##                self.pdf_host.showPage()
 193 ##                self.pdf_host.save()
 194 #                self.document.Close(-1)
 195 #            if self.pdf_host is not None:
 196 #                self.pdf_host.Quit()
 197                 self.pdf_host.save()
 198 
 199             self.document=None
 200             self.pdf_host=None
 201         except:
 202             pass
 203 #            raise
 204         self.dead=1
 205         
 206     def _save(self):
 207 #RS fatal error handling
 208         if self.dead==1:
 209             return
 210 #RS end
 211         if self.document!=None:
 212             pass
 213         #not doctemplate based
 214 ##        self.pdf_host.save()
 215 
 216     # Primitive formatter functions #####################################
 217 
 218     # all other methods should use these to format tags. This keeps the
 219     # code clean and handle pathological cases like unclosed p and
 220     # inline tags.
 221 
 222     def langAttr(self, lang=None):
 223         """ Return lang and dir attribute
 224 
 225         Must be used on all block elements - div, p, table, etc.
 226         @param lang: if defined, will return attributes for lang. if not
 227             defined, will return attributes only if the current lang is
 228             different from the content lang.
 229         @rtype: dict
 230         @retrun: language attributes
 231         """
 232         if not lang:
 233             lang = self.request.current_lang
 234             # Actions that generate content in user language should change
 235             # the content lang from the default defined in cfg.
 236             if lang == self.request.content_lang:
 237                 # lang is inherited from content div
 238                 return {}
 239 
 240         attr = {'lang': lang, 'dir': i18n.getDirection(lang),}
 241         return attr
 242 
 243     def formatAttributes(self, attr=None):
 244         """ Return formatted attributes string
 245 
 246         @param attr: dict containing keys and values
 247         @rtype: string ?
 248         @return: formated attributes or empty string
 249         """
 250         if attr:
 251             attr = [' %s="%s"' % (k, v) for k, v in attr.items()]           
 252             return ''.join(attr)
 253         return ''
 254 
 255     # TODO: use set when we require Python 2.3
 256     # TODO: The list is not complete, add missing from dtd
 257 #RS Word: use _blocks for all tags that can only be interpreted on close, i.e. text between open and close must be recorded    
 258 ##    _blocks = 'p div pre table tr td ol ul dl li dt dd h1 h2 h3 h4 h5 h6 hr form'
 259     _blocks = 'div pre table tr td ol ul dl li dt dd h1 h2 h3 h4 h5 h6 hr form pagelink'
 260     _blocks = 'div pre dt dd h1 h2 h3 h4 h5 h6 form url pagelink'
 261     _blocks= 'h1 h2 h3 h4 h5'
 262 #RS end
 263     _blocks = dict(zip(_blocks.split(), [1] * len(_blocks)))
 264 
 265 
 266     def open(self, tag, newline=False, attr=None):
 267         """ Open a tag with optional attributes
 268 
 269         @param tag: html tag, string
 270         @param newline: render tag on a separate line
 271         @parm attr: dict with tag attributes
 272         @rtype: string ?
 273         @return: open tag with attributes
 274         """
 275 #        if _debug:
 276 #            traceback.print_stack(limit=1,file=sys.stdout)
 277         if tag in self._blocks:
 278             # Block elements
 279 #RS word            
 280             if _debug:
 281                 print "OPEN %s (recording)" % tag
 282             self.store_text=1
 283             self.recordedtext=""
 284 #TODO
 285 #            if self.word_host:
 286 #                self.recordedcursor=int(self.word_host.Selection.Range.End)
 287 
 288 #RS end
 289             result = []
 290 
 291             # Add language attributes, but let caller overide the default
 292             attributes = self.langAttr()
 293             if attr:
 294                 attributes.update(attr)
 295 
 296             # Format
 297             attributes = self.formatAttributes(attributes)
 298             result.append('<%s%s>' % (tag, attributes))
 299             if newline:
 300                 if _debug:
 301                     print "OPEN with NEWLINE"
 302 #TODO
 303 #                if self.document:
 304 #                    self.word_host.Selection.TypeParagraph()
 305                 
 306                 result.append('\n')
 307             return ''.join(result)
 308         else:
 309             # Inline elements
 310             # Add to inlineStack
 311             if _debug:
 312                 print "OPEN %s (inline)" % tag
 313             self._inlineStack.append(tag)
 314 
 315             self.para_story += '<%s>' % tag
 316             # Format
 317             return '<%s%s>' % (tag, self.formatAttributes(attr))
 318        
 319     def close(self, tag, newline=False):
 320         """ Close tag
 321 
 322         @param tag: html tag, string
 323         @rtype: string ?
 324         @return: closing tag
 325         """
 326 #        if _debug:
 327 #            traceback.print_stack(limit=1,file=sys.stdout)
 328         if tag in self._blocks:
 329             # Block elements
 330             # Close all tags in inline stack
 331             # Work on a copy, because close(inline) manipulate the stack
 332 #RS word            
 333             if _debug:
 334                 try:
 335                     print 'CLOSE %s (recorded="%s")' % (tag,self.recordedtext)
 336                 except:
 337                     print 'CLOSE %s (recorded=???)' % (tag)
 338             self.store_text=0
 339             self.recordedtext=""
 340 #            self.recordedcursor=0
 341 #RS end            
 342             result = []
 343             stack = self._inlineStack[:]
 344             stack.reverse()
 345             for inline in stack:
 346                 result.append(self.close(inline))
 347             # Format with newline
 348             if newline:
 349                 if _debug:
 350                     print "CLOSE with NEWLINE"
 351                 result.append('\n')
 352             result.append('</%s>\n' % (tag))
 353             return ''.join(result)            
 354         else:
 355             # Inline elements 
 356             # Pull from stack, ignore order, that is not our problem.
 357             # The code that calls us should keep correct calling order.
 358             if _debug:
 359                 print "CLOSE %s (inline)" % tag
 360             if tag in self._inlineStack:
 361                 if _debug:
 362                     print "CLOSE %s (inline stack remove)" % tag
 363                 self._inlineStack.remove(tag)
 364 ###bulletlistentag nicht in die para_story
 365 ##            if tag == 'ul':
 366 ##                pass
 367 ##            else:
 368 ##                self.para_story += "</%s>"  % tag
 369             self.para_story += "</%s>"  % tag
 370             return '</%s>' % tag
 371 
 372 
 373     def startDocument(self, pagename):
 374         if _debug:
 375             traceback.print_stack(limit=1,file=sys.stdout)
 376             sys.stderr.write("\nThis is the PDF Formatter::startDocument....")
 377         self.doccount+=1
 378         self.title= self.request.getPragma('title', pagename)
 379 
 380         if self.pdf_host==None:
 381 
 382             try:
 383                 file = wikiutil.quoteWikinameFS(pagename) + DOC_SUFFIX
 384                 filepath = os.path.abspath(os.path.join(self.targetdir, file))
 385                 #not doctemplate based
 386 ##                self.pdf_host = Canvas(filepath)
 387 ##                self.pdf_host.setTitle(title)
 388 ### TODO                self.pdf_host.setAuthor(TODO author)
 389 ###not implemented yet                self.pdf_host.setSubject(notimplementedyet subject)
 390                 #SimpleDocTemplate based
 391                 # pagesize per wikiaction? / showBoundary= 1 only for tests / allowSplitting= 1 allows the split of flowables 
 392                 self.doc= SimpleDocTemplate(filepath, pagesize= A4, showBoundary= 1, allowSplitting= 1, title= self.title, author= '')
 393 #debug                self.request.write( "#SimpleDocTemplate initialised! Title: %s Filename: %s" % (self.title, filepath))
 394 
 395             except:
 396                 self.request.write( "#STARTDOC %s %s failed at Host Initialisation" % (self.doccount,pagename))
 397                 self.pdf_host=None
 398                 raise
 399 
 400         else:
 401             self.request.write("\nPDF HOST already active!\n")
 402         if self.document!=None:
 403             self.request.write("ignore#STARTDOC %s %s" % (self.doccount,pagename))
 404             return "ignore#STARTDOC %s %s" % (self.doccount,pagename)
 405         try:
 406 
 407             self.story = []
 408             self.story.append(Spacer(1, 7* cm))
 409 #            self.story.append(Paragraph(pagename, self.styleTitle)) 
 410 
 411         except:
 412             self.FatalEnd()
 413             self.request.write("#STARTDOC %s %s failed at" % (self.doccount,pagename))            
 414             #self.request.write("#STARTDOC %s %s failed at Documents.Add(%s..." % (self.doccount,pagename,self.doctemplate))
 415             raise
 416         
 417         try:
 418             self._reset_indents()
 419 
 420 
 421 #            self.document.SaveAs(filepath,0)
 422 #            self.request.write("#STARTDOC %s %s" % (self.doccount,pagename)) # identisch der returnanweisung
 423             return "#STARTDOC %s %s" % (self.doccount,pagename)
 424 
 425         except:
 426             self.FatalEnd()
 427             self.request.write("#STARTDOC %s %s failed" % (self.doccount,pagename))
 428             raise
 429 
 430     def endDocument(self):
 431 
 432         def myFirstPage(canvas, doc):
 433             self.request.write( "#myFirstPage reached! ")
 434             canvas.saveState()
 435             rect=(8.8* cm, (self.PAGE_HEIGHT/5*4)-32, 12.2* cm, (self.PAGE_HEIGHT/5*4)-16)
 436             rgb=Color(0,0,1)
 437             url='www.orsoft.de'
 438             canvas.linkURL(url, rect, 1, 1, rgb)
 439             canvas.setFont('Times-Bold', 16)
 440             canvas.drawCentredString(self.PAGE_WIDTH/2, self.PAGE_HEIGHT/5*4, self.title)
 441             canvas.setFont('Times-Roman', 9)
 442             canvas.drawCentredString(self.PAGE_WIDTH/2, (self.PAGE_HEIGHT/5*4)-27, "OR Soft Jänicke GmbH")
 443             canvas.drawCentredString(self.PAGE_WIDTH/2, self.PAGE_HEIGHT-(0.75* inch), '') #eg a pageinfo
 444             canvas.drawCentredString(self.PAGE_WIDTH/2, 0.75* inch, "Page 1")
 445             canvas.restoreState()
 446             self.request.write( "#end of myFirstPage reached! " )
 447 
 448         def myLaterPages(canvas, doc):
 449             self.request.write( "#myLaterPages reached! ")
 450             canvas.saveState()
 451             canvas.setFont('Times-Roman',9)
 452             canvas.drawCentredString(self.PAGE_WIDTH/2, self.PAGE_HEIGHT-(0.75* inch), '') #eg a pageinfo
 453             canvas.drawCentredString(self.PAGE_WIDTH/2, 0.75* inch, "Page %d" % (doc.page))
 454             canvas.restoreState()
 455             self.request.write( "#end of myLaterPages reached! ")
 456 
 457 #RS fatal error handling
 458         if _debug:
 459             traceback.print_stack(limit=1,file=sys.stdout)
 460         if self.dead==1:
 461             return u""
 462 #RS end
 463         self.doccount-=1
 464         if self.doccount==0:
 465             try:
 466 
 467 ###                self.pdf_host.drawText(self.document)
 468 ###                self.pdf_host.showPage()
 469 #                self.f.addFromList(self.story,self.pdf_host)
 470 #                self.pdf_host.save()
 471                 #SimpleDocTemplate based
 472                 self.request.write( "#endDocument reached! len(self.story): %s " %  len(self.story))
 473                 self.doc.build(self.story, onFirstPage= myFirstPage, onLaterPages= myLaterPages)
 474 #                self.document=None
 475 #                self.pdf_host=None
 476                 return u"#ENDDOC"
 477             except:
 478                 return u"#ENDDOC failed"
 479                 raise
 480                 
 481         return u"#ENDDOC %s" % self.doccount
 482 
 483     def startContent(self, content_id='content', **kwargs):
 484         """ Start page content div """
 485         return ""
 486         if _debug:
 487             traceback.print_stack(limit=1,file=sys.stdout)
 488         # Setup id
 489         if content_id!='content':
 490             aid = 'top_%s' % (content_id,)
 491         else:
 492             aid = 'top'
 493         self._content_ids.append(content_id)
 494         result = []
 495         # Use the content language
 496         attr = self.langAttr(self.request.content_lang)
 497         attr['id'] = content_id
 498         result.append(self.open('div', newline=1, attr=attr))
 499         result.append(self.anchordef(aid))
 500         return ''.join(result)
 501         
 502     def endContent(self):
 503         """ Close page content div """
 504         return ""
 505         if _debug:
 506             traceback.print_stack(limit=1,file=sys.stdout)
 507 
 508         # Setup id
 509         try:
 510             cid = self._content_ids.pop()
 511         except:
 512             cid = 'content'
 513         if cid!='content':
 514             aid = 'bottom_%s' % (cid,)
 515         else:
 516             aid = 'bottom'
 517 
 518         result = []
 519         result.append(self.anchordef(aid))
 520         result.append(self.close('div', newline=1))
 521         return ''.join(result)
 522 
 523     def lang(self, on, lang_name):
 524         """ Insert text with specific lang and direction.
 525         
 526             Enclose within span tag if lang_name is different from
 527             the current lang    
 528         """
 529         tag = 'span'
 530         if lang_name != self.request.current_lang:
 531             # Enclose text in span using lang attributes
 532             if on:
 533                 attr = self.langAttr(lang=lang_name)
 534                 ret=self.open(tag, attr=attr)
 535                 return ret
 536             else:
 537                 if self.document!=None:
 538                     pass
 539 #TODO : text with language info?
 540 ###                self.document.XXXX
 541                 ret=self.close(tag)
 542                 return ret
 543 
 544         # Direction did not change, no need for span
 545         return ''            
 546     
 547 
 548     def _langAttr(self):
 549         result = ''
 550         lang = self.request.current_lang
 551         if lang != config.default_lang:
 552             result += ' lang="%s" dir="%s"' % (
 553                 lang, i18n.getDirection(self.request, lang))
 554 
 555         return result
 556 
 557     def sysmsg(self, text, **kw):
 558         if _debug:
 559             traceback.print_stack(limit=1,file=sys.stdout)
 560 #RS fatal error handling
 561         if self.dead==1:
 562             return u""
 563 #RS end
 564         tag = 'div'
 565         if on:
 566             ret=self.open(tag, attr={'class': 'message'})
 567             return ret
 568         else:
 569             text=self.recordedtext
 570             if self.document!=None and text!=None:
 571                 pass 
 572 #TODO
 573 #                self.document.Content.TypeText('#SYSMSG#'+text+'#')
 574             ret=self.close(tag)
 575             return ret
 576 
 577 
 578     def pagelink(self, on, pagename='', page=None, **kw):
 579         """ Link to a page.
 580 
 581             formatter.text_python will use an optimized call with a page!=None
 582             parameter. DO NOT USE THIS YOURSELF OR IT WILL BREAK.
 583 
 584             See wikiutil.link_tag() for possible keyword parameters.
 585         """
 586         if _debug:
 587             traceback.print_stack(limit=1,file=sys.stdout)
 588 #RS fatal error handling
 589         if self.dead==1:
 590             return u""
 591 #RS end
 592         apply(FormatterBase.pagelink, (self, on, pagename, page), kw)
 593         if page is None:
 594             page = Page(self.request, pagename, formatter=self);
 595         tag = 'pagelink'
 596         url = wikiutil.quoteWikinameFS(pagename) + DOC_SUFFIX
 597         if on:
 598             ret=self.open(tag, attr={'class': 'pagelink'})
 599             return ret
 600         else:
 601             text=self.recordedtext
 602             if text==None:
 603                 text=pagename
 604             if self.document!=None:
 605                 pass
 606 #TODO
 607 #                self.word_host.ActiveDocument.Hyperlinks.Add(\
 608 #                    Anchor=self.word_host.Selection.Range, Address=url,\
 609 #                    SubAddress="", ScreenTip="", TextToDisplay=text)
 610             ret=self.close(tag)
 611             return ret
 612             
 613             
 614 
 615     def interwikilink(self, on, interwiki='', pagename='', **kw):
 616         if not on: return '</a>'
 617         
 618         wikitag, wikiurl, wikitail, wikitag_bad = wikiutil.resolve_wiki(self.request, '%s:%s' % (interwiki, pagename))
 619         wikiurl = wikiutil.mapURL(self.request, wikiurl)
 620 
 621         if wikitag == 'Self': # for own wiki, do simple links
 622             import urllib
 623             if wikitail.find('#')>-1:
 624                 wikitail, kw['anchor'] = wikitail.split('#', 1)
 625             wikitail = urllib.unquote(wikitail)
 626             return apply(self.pagelink, (on, wikiutil.AbsPageName(self.request, self.page.page_name, wikitail)), kw)
 627         else: # return InterWiki hyperlink
 628             href = wikiutil.join_wiki(wikiurl, wikitail)
 629             if wikitag_bad:
 630                 html_class = 'badinterwiki'
 631             else:
 632                 html_class = 'interwiki'
 633 
 634             icon = ''
 635             if self.request.user.show_fancy_links:
 636                 icon = self.request.theme.make_icon('interwiki', {'wikitag': wikitag}) 
 637             return (self.url(1, href, title=wikitag, unescaped=0,
 638                 pretty_url=kw.get('pretty_url', 0), css = html_class) +
 639                 icon)
 640             # unescaped=1 was changed to 0 to make interwiki links with pages with umlauts (or other non-ascii) work
 641 
 642 
 643 #SYNC URL
 644 
 645     def url(self, on, url=None, css=None, **kw):
 646         """ render URL
 647 
 648         @keyword type: "www" or "mailto" to use that icon
 649         @keyword title: <a> title attribute
 650         @keyword attrs: just include those <a> attrs "as is"
 651         """
 652         if _debug:
 653             traceback.print_stack(limit=1,file=sys.stdout)
 654 #RS fatal error handling
 655         if self.dead==1:
 656             return u""
 657 #RS end
 658         if url is not None:
 659             url = wikiutil.mapURL(self.request, url)
 660         title = kw.get('title', None)
 661         attrs = kw.get('attrs', None)
 662 #RS 1.1
 663         target = kw.get('target', None)
 664 #RS stop
 665         str = ''
 666         if css: 
 667             str = '%s class="%s"' % (str, css)
 668         if title:
 669             str = '%s title="%s"' % (str, title)
 670         else:
 671             title=""
 672         if attrs:
 673             str = '%s %s' % (str, attrs)
 674 
 675         # create link
 676 #TODO? insert link icons and other pretty stuff?         
 677         tag = 'url'
 678         if on:
 679             #store this for the close action
 680             self.url_url=url
 681             self.url_title=title
 682             
 683             ret=self.open(tag, attr=attrs)
 684             return ret
 685         else:
 686             text=self.recordedtext
 687             url=self.url_url
 688             title=self.url_title
 689             if text is None:
 690                 text = url
 691             if self.document!=None:
 692                 pass
 693 #TODO
 694 #                self.word_host.ActiveDocument.Hyperlinks.Add(\
 695 #                    Anchor=self.word_host.Selection.Range, Address=wikiutil.escape(url, 1),\
 696 #                    SubAddress="", ScreenTip=title, TextToDisplay=text)
 697             
 698 
 699             ret=self.close(tag)
 700             return ret
 701 
 702 
 703     def anchordef(self, id):
 704         if _debug:
 705             traceback.print_stack(limit=1,file=sys.stdout)
 706 #RS fatal error handling
 707         if self.dead==1:
 708             return u""
 709 #RS end
 710         if self.document!=None:
 711             self.document.Bookmarks.Add(Range=self.word_host.Selection.Range,Name=id)
 712         return '<a id="%s"></a>\n' % (id, )
 713 
 714     def anchorlink(self, on, name='', id = None):
 715         if _debug:
 716             traceback.print_stack(limit=1,file=sys.stdout)
 717 ##        if self.document!=None:
 718 ##            self.word_host.Selection.TypeText('_'+text+'_')
 719 #RS fatal error handling
 720         if self.dead==1:
 721             return u""
 722 #RS end
 723         extra = ''
 724         if id:
 725             extra = ' id="%s"' % id
 726         tag = 'a'
 727         if on:
 728             ret=self.open(tag, attr={'id':'%s' % id})
 729             return ret
 730         else:
 731             text=self.recordedtext
 732             if text==None:
 733                 text=name
 734             if self.document!=None:
 735                 pass
 736 #TODO
 737 #                self.word_host.ActiveDocument.Hyperlinks.Add(\
 738 #                    Anchor=self.word_host.Selection.Range, Address="",\
 739 #                    SubAddress=name, ScreenTip="", TextToDisplay=text)
 740             ret=self.close(tag)
 741             return ret
 742 
 743 
 744     def pure(self, text):
 745         """
 746         this handles the "not in any markup" case
 747         used in formatters with "side effects"
 748         """
 749         if _debug:
 750             traceback.print_stack(limit=1,file=sys.stdout)
 751             print "PURE, recording=%s" % self.store_text
 752 #RS fatal error handling
 753         if self.dead==1:
 754             raise
 755             return u""
 756 #RS end
 757         if (self._table_start == 1):
 758             raise
 759             return u''
 760 #        if self.document!=None:
 761 #            pass
 762 #TODO
 763 #            self.word_host.Selection.TypeText(text)
 764         return self._text(text)
 765     
 766     def _text(self, text):
 767 #        return '{'+text+'}'
 768 #RS fatal error handling
 769         if _debug:
 770             traceback.print_stack(limit=2,file=sys.stdout)
 771         if self.dead==1:
 772             raise
 773             return u""
 774 #RS end
 775         tx=self.escapedText(text)
 776         if self._in_code:
 777             tx=string.replace(self.escapedText(text), u' ', self.hardspace)
 778  #       if self.document!=None:
 779  #           self.document.Content.InsertAfter('„#“'+text+'#')
 780         if self.store_text==1:
 781             if _debug:
 782                 print "_TEXT (recording)"
 783             self.recordedtext+=tx
 784             return tx
 785         else:
 786             self.para_story += tx
 787             if _debug:
 788                 print "_TEXT (inline), tx=%s, STORY:%s" % (tx,self.para_story)
 789 
 790         return tx
 791 
 792     # Inline ###########################################################
 793     def strong(self, on):
 794 #RS fatal error handling
 795         if self.dead==1:
 796             return u""
 797 #RS end
 798         tag = 'b'
 799         if on:
 800             ret=self.open(tag)
 801 #            if self.document!=None:
 802 #                pass
 803 #TODO
 804 #                self.word_host.Selection.Font.Bold=\
 805 #                    win32com.client.constants.wdToggle
 806 #                self.word_host.Selection.TypeText('')
 807 
 808 # is now part of open()
 809 ##            self.para_story += "<b>"
 810             return ret
 811         else:
 812 #            if self.document!=None:
 813 #                pass
 814 #TODO
 815 #                self.word_host.Selection.Font.Bold=\
 816 #                    win32com.client.constants.wdToggle
 817 #                self.word_host.Selection.TypeText('')
 818 # is now part of close()
 819 ##            self.para_story += "</b>"
 820             ret=self.close(tag)
 821             return ret
 822 
 823 
 824     def emphasis(self, on):
 825 #RS fatal error handling
 826         if self.dead==1:
 827             return u""
 828 #RS end
 829         tag = 'em'
 830         if on:
 831             ret=self.open(tag)
 832 #            if self.document!=None:
 833 #                pass
 834 #TODO
 835 #                self.word_host.Selection.Font.Italic=\
 836 #                    win32com.client.constants.wdToggle
 837 #                self.word_host.Selection.TypeText('')
 838 # is now part of open()
 839 ##            self.para_story += "<i>"
 840             return ret
 841         else:
 842 #            if self.document!=None:
 843 #                pass
 844 #TODO
 845 #                self.word_host.Selection.Font.Italic=\
 846 #                    win32com.client.constants.wdToggle
 847 #                self.word_host.Selection.TypeText('')
 848 # is now part of close()
 849 ##            self.para_story += "</i>"
 850             ret=self.close(tag)
 851             return ret
 852 
 853     def underline(self, on):
 854         if _debug:
 855             traceback.print_stack(limit=1,file=sys.stdout)
 856 #RS fatal error handling
 857         if self.dead==1:
 858             return u""
 859 #RS end
 860         tag = 'span'
 861 # new tagname for in-paragraph formatting matters
 862         tag = 'u'
 863         if on:
 864             ret=self.open(tag,attr={'class': 'u'})
 865             if self.document!=None:
 866                 pass
 867 #TODO
 868 #                self.word_host.Selection.Font.Underline=\
 869 #                    win32com.client.constants.wdUnderlineSingle
 870 #                self.word_host.Selection.TypeText('')
 871 # is now part of open()
 872 ##            self.para_story += "<u>"
 873             return ret
 874         else:
 875 #            if self.document!=None:
 876 #                pass
 877 #TODO
 878 #                self.word_host.Selection.Font.Underline=\
 879 #                    win32com.client.constants.wdUnderlineNone
 880 #                self.word_host.Selection.TypeText('')
 881 # is now part of close()
 882 ##            self.para_story += "</u>"
 883             ret=self.close(tag)
 884             return ret
 885 
 886     def highlight(self, on):
 887 #RS fatal error handling
 888         if self.dead==1:
 889             return u""
 890 #RS end
 891         tag = 'strong'
 892         if on:
 893             ret=self.open(tag, attr={'class': 'highlight'})
 894             if self.document!=None:
 895                 pass
 896 #TODO
 897 #                self.word_host.Selection.Font.Bold=\
 898 #                    win32com.client.constants.wdToggle
 899 #                self.word_host.Selection.TypeText('')
 900             return ret
 901         else:
 902             if self.document!=None:
 903                 pass
 904 #TODO
 905 #                self.word_host.Selection.Font.Bold=\
 906 #                    win32com.client.constants.wdToggle
 907 #                self.word_host.Selection.TypeText('')
 908             ret=self.close(tag)
 909             return ret
 910 
 911     def sup(self, on):
 912 #RS fatal error handling
 913         if self.dead==1:
 914             return u""
 915 #RS end
 916         tag = 'sup'
 917 # new tagname for in-paragraph formatting matters        
 918         tag = 'super'
 919         if on:
 920             ret=self.open(tag)
 921 #            if self.document!=None:
 922 #                pass
 923 #TODO
 924 #                self.word_host.Selection.Font.Superscript=\
 925 #                    win32com.client.constants.wdToggle
 926 #                self.word_host.Selection.TypeText('')
 927 ##            self.para_story += "<super>"
 928             return ret
 929         else:
 930             if self.document!=None:
 931                 pass
 932 #TODO
 933 #                self.word_host.Selection.Font.Superscript=\
 934 #                    win32com.client.constants.wdToggle
 935 #                self.word_host.Selection.TypeText('')
 936 ##            self.para_story += "</super>"
 937             ret=self.close(tag)
 938             return ret
 939 
 940     def sub(self, on):
 941 #RS fatal error handling
 942         if _debug:
 943             traceback.print_stack(limit=1,file=sys.stdout)
 944         if self.dead==1:
 945             return u""
 946 #RS end
 947         tag = 'sub'
 948         if on:
 949             ret=self.open(tag)
 950 #            if self.document!=None:
 951 #                pass
 952 #TODO
 953 #                self.word_host.Selection.Font.Subscript=\
 954 #                    win32com.client.constants.wdToggle
 955 #                self.word_host.Selection.TypeText('')
 956 ##            self.para_story += "<sub>"
 957             return ret
 958         else:
 959 #            if self.document!=None:
 960 #                pass
 961 #TODO
 962 #                self.word_host.Selection.Font.Subscript=\
 963 #                    win32com.client.constants.wdToggle
 964 #                self.word_host.Selection.TypeText('')
 965 ##            self.para_story += "</sub>"
 966             ret=self.close(tag)
 967             return ret
 968 #RS end
 969 
 970 
 971     def code(self, on):
 972         if _debug:
 973             traceback.print_stack(limit=1,file=sys.stdout)
 974 #RS fatal error handling
 975         if self.dead==1:
 976             return u""
 977 #RS end
 978         tag = 'tt'
 979         tag = 'font'
 980         self._in_code = on
 981         if on:
 982             fontattr={'name': 'Courier','size':8}
 983 ##            self.para_story += '<font name="Courier" size=8>'
 984             ret=self.open(tag,attr=fontattr)
 985             return ret
 986         else:
 987             if self.document!=None:
 988                 pass
 989 #TODO
 990 #                lastend=self.recordedcursor
 991 #                currend=int(self.word_host.Selection.Range.End)
 992 #                if lastend<currend and lastend>0:
 993 #                    ttrange=self.document.Range(lastend,currend)
 994 #                    ttrange.Style=self.tt_style
 995 #                else:
 996 #                    self.request.write("TT formatter error, ignored")
 997 #                self.word_host.Selection.TypeText('')
 998 ##            self.para_story += "</font>"
 999             ret=self.close(tag)
1000             return ret
1001 
1002        
1003     def small(self, on):
1004         tag = 'small'
1005         if on:
1006             ret=self.open(tag)
1007             if self.document!=None:
1008                 pass
1009 #TODO
1010 #                self.word_host.Selection.Font.Subscript=\
1011 #                    win32com.client.constants.wdToggle
1012 #                self.word_host.Selection.TypeText('')
1013             return ret
1014         else:
1015             if self.document!=None:
1016                 pass
1017 #TODO
1018 #                self.word_host.Selection.Font.Subscript=\
1019 #                    win32com.client.constants.wdToggle
1020 #                self.word_host.Selection.TypeText('')
1021             ret=self.close(tag)
1022             return ret
1023                                                                                 
1024     def big(self, on):
1025         tag = 'big'
1026         if on:
1027             ret=self.open(tag)
1028             if self.document!=None:
1029                 pass
1030 #TODO
1031 #                self.word_host.Selection.Font.Subscript=\
1032 #                    win32com.client.constants.wdToggle
1033 #                self.word_host.Selection.TypeText('')
1034             return ret
1035         else:
1036             if self.document!=None:
1037                 pass
1038 #TODO
1039 #                self.word_host.Selection.Font.Subscript=\
1040 #                    win32com.client.constants.wdToggle
1041 #                self.word_host.Selection.TypeText('')
1042             ret=self.close(tag)
1043             return ret
1044 
1045 
1046     # Block elements ####################################################
1047 
1048     def preformatted(self, on):
1049         if _debug:
1050             traceback.print_stack(limit=1,file=sys.stdout)
1051 #RS fatal error handling
1052         if self.dead==1:
1053             return u""
1054 #RS end
1055         self.in_pre = on != 0
1056         tag = 'pre'
1057         if on:
1058             ret=self.open(tag,newline=1)
1059             return ret
1060         else:
1061             if self.document!=None:
1062                 pass
1063 #TODO
1064 #                lastend=self.recordedcursor
1065 #                currend=int(self.word_host.Selection.Range.End)
1066 #                if lastend<currend and lastend>0:
1067 #                    ttrange=self.document.Range(lastend,currend)
1068 #                    ttrange.Style=self.pre_style
1069 #                else:
1070 #                    self.request.write("PRE formatter error, ignored")
1071 #                self.word_host.Selection.TypeParagraph()
1072 #                self.word_host.Selection.Style=self.defpara_style
1073             ret=self.close(tag)
1074             return ret
1075 
1076 # special markup for syntax highlighting #############################
1077 
1078     def code_area(self, on, code_id, code_type='code', show=0, start=-1, step=-1):
1079 #RS word: for now, just use preformatted?
1080         if on:
1081             # Open a code area
1082             self._in_code_area = 1
1083             self._in_code_line = 0
1084         else:
1085             # Close code area
1086             self._in_code_area = 0
1087             self._code_area_num += 1
1088         return self.preformatted(on)
1089 #RS end    
1090         res = []
1091         ci = self.request.makeUniqueID('CA-%s_%03d' % (code_id, self._code_area_num))
1092         if on:
1093             # Open a code area
1094             self._in_code_area = 1
1095             self._in_code_line = 0
1096             self._code_area_state = [ci, show, start, step, start]
1097 
1098             # Open the code div - using left to right always!
1099             attr = {'class': 'codearea', 'lang': 'en', 'dir': 'ltr'}
1100             res.append(self.open('div', attr=attr))
1101 
1102             # Add the script only in the first code area on the page
1103             if self._code_area_js == 0 and self._code_area_state[1] >= 0:
1104                 res.append(self._toggleLineNumbersScript)
1105                 self._code_area_js = 1
1106 
1107             # Add line number link, but only for JavaScript enabled browsers.
1108             if self._code_area_state[1] >= 0:
1109                 toggleLineNumbersLink = r'''
1110 <script type="text/javascript">
1111 document.write('<a href="#" onClick="return togglenumber(\'%s\', %d, %d);" \
1112                 class="codenumbers">Toggle line numbers<\/a>');
1113 </script>
1114 ''' % (self._code_area_state[0], self._code_area_state[2], self._code_area_state[3])
1115                 res.append(toggleLineNumbersLink)
1116 
1117             # Open pre - using left to right always!
1118             attr = {'id': self._code_area_state[0], 'lang': 'en', 'dir': 'ltr'}
1119             res.append(self.open('pre', newline=True, attr=attr))
1120         else:
1121             # Close code area
1122             res = []
1123             if self._in_code_line:
1124                 res.append(self.code_line(0))
1125             res.append(self.close('pre'))
1126             res.append(self.close('div'))
1127 
1128             # Update state
1129             self._in_code_area = 0
1130             self._code_area_num += 1
1131 
1132         return ''.join(res)
1133 
1134     def code_line(self, on):
1135 #RS word: for now, just use preformatted?
1136         self._in_code_line = on != 0
1137         return self.preformatted(on)
1138 #RS end    
1139 #RS end    
1140         res = ''
1141         if not on or (on and self._in_code_line):
1142             res += '</span>\n'
1143         if on:
1144             res += '<span class="line">'
1145             if self._code_area_state[1] > 0:
1146                 res += '<span class="LineNumber">%4d </span>' % (self._code_area_state[4], )
1147                 self._code_area_state[4] += self._code_area_state[3]
1148         self._in_code_line = on != 0
1149         return res
1150 
1151     def code_token(self, on, tok_type):
1152 #RS word: for now, just use code?
1153         return self.code(on)
1154 #RS end
1155         return ['<span class="%s">' % tok_type, '</span>'][not on]
1156 
1157 
1158     # Paragraphs, Lines, Rules ###########################################
1159     
1160     def linebreak(self, preformatted=1):
1161         if _debug:
1162             traceback.print_stack(limit=1,file=sys.stdout)
1163 #RS fatal error handling
1164         if self.dead==1:
1165             return u""
1166 #RS end
1167         if self._in_code_area:
1168             preformatted = 1
1169 #TODO
1170 #        self.word_host.Selection.TypeText("\x0B ")
1171 #        self.document.Content.InsertAfter("\x0B ")
1172         
1173         return ['\n', '<br>\n'][not preformatted]
1174 
1175     def paragraph(self, on):
1176         if _debug:
1177             traceback.print_stack(limit=1,file=sys.stdout)
1178 #RS fatal error handling
1179         if self.dead==1:
1180             return u""
1181 #RS end
1182         if self._terse:
1183             return ''
1184         FormatterBase.paragraph(self, on)
1185 ##        if self._in_li:
1186 ##            self._in_li = self._in_li + 1
1187         tag = 'p'
1188         if on:
1189             ret=self.open(tag)
1190 #versuch indents
1191             if self.li_marker!= [] and self.li_marker[-1]> 0 and self.last_indent_type=='ul':
1192                 if self.p_marker== None:
1193                     self.p_marker= 0
1194                 self.p_marker+=1
1195 # versuch ende
1196 ##            if self.document!=None:
1197 ##                if self._ignore_next_paragraph: #we already inserted a paragraph
1198 ##                    self._ignore_next_paragraph=0
1199 ##                    return u''
1200 ##                else:
1201 ###TODO
1202 ###                    self.word_host.Selection.TypeParagraph()
1203 ##                    return u'<pli>'
1204             return ret
1205         else:
1206 ##            text=self.recordedtext
1207 ##            if self.document!=None:
1208 ##                if self._ignore_next_paragraph: #we already inserted a paragraph
1209 ##                    self._ignore_next_paragraph=0
1210 ##                    return u''
1211 ##                else:
1212 ###TODO
1213 ###                    self.word_host.Selection.TypeParagraph()
1214 ##                    return u'<pli>'
1215             self.para_story += ""
1216 # versuch indents
1217             if self.li_marker!= [] and self.li_marker[-1] > 0 and self.p_marker > 1 and self.last_indent_type=='ul':
1218                 self.bulletStack.ppush(self.bulletText)
1219                 self.bulletText= ''
1220 #versuch pause
1221             self.story.append(Paragraph(str(self.para_story), self.currentstyle, self.bulletText))
1222 #versuch weiter
1223             if self.li_marker!= [] and self.li_marker[-1] > 0 and self.p_marker > 1 and self.last_indent_type=='ul':
1224                 self.bulletText= self.bulletStack.ppop()
1225 #versuch ende
1226             if _debug:
1227                 sys.stderr.write(self.para_story+"\n")
1228                 print "\nSTORY: %s" % self.para_story
1229             self.para_story = ""
1230             ret=self.close(tag)
1231             return ret
1232         
1233 
1234     def rule(self, size=None):
1235         if _debug:
1236             traceback.print_stack(limit=1,file=sys.stdout)
1237 #RS fatal error handling
1238         if self.dead==1:
1239             return u""
1240 #RS end
1241 #TODO RS draw a line?
1242         if size:
1243             # Add hr class: hr1 - hr6
1244             return self.open('hr', newline=1, attr={'class': 'hr%d' % size})
1245         return self.open('hr', newline=1)
1246 
1247     def icon(self, type):
1248 #TODO RS or just ignore (probably just wiki control icons)?        
1249         return self.request.theme.make_icon(type)
1250 
1251     def img_url(self, img):
1252         """ Generate an image href
1253 
1254         @param img: the image filename
1255         @rtype: string
1256         @return: the image href
1257         """
1258         return "%s%s\\img\\%s" % (self.cfg.url_prefix_dir, self.request.theme.name, img)
1259 
1260 
1261     def smiley(self, text):
1262         w, h, b, img = config.smileys[text.strip()]
1263         href = img
1264         if not href.startswith('/'):
1265             href = self.img_url(img)
1266         return self.image(src=href, alt=text, width=str(w), height=str(h))
1267 
1268     # Lists ##############################################################
1269 
1270 
1271 
1272 
1273     def number_list(self, on, type=None, start=None):
1274         if _debug:
1275             traceback.print_stack(limit=1,file=sys.stdout)
1276 #RS fatal error handling
1277         if self.dead==1:
1278             return u""
1279 #RS end
1280         tag = 'ol'
1281         self.request.write("<number_list>:on=%s,type=%s,start=%s" % (str(on),str(type),str(start)))
1282         if on:
1283             self.oltypeStack.ppush(self.oltype)
1284             self.oltype= type
1285             self.olstart= start
1286             self.list_levels['ol']=self.list_levels['ol']+1
1287             self.list_levels['all']=self.list_levels['all']+1
1288             attr = {}
1289             if _debug:
1290                 print "   oltype (ol=on):  %s    \n" % self.oltype
1291                 print "   olstart:  %s   \n" % self.olstart
1292             if type is not None:
1293                 attr['type'] = type
1294             if start is not None:
1295                 attr['start'] = start
1296             ret=self.open(tag, newline=1, attr=attr)
1297 
1298             if self.document!=None:
1299 #                self.word_host.Selection.TypeParagraph()
1300                 self.request.write("<OL> List type was: %s" % str(self.word_host.Selection.Range.ListFormat.ListType))
1301 #TODO
1302 #                if self.list_levels['ol']==1: #only first 
1303 #                    if self.word_host.Selection.Range.ListFormat.ListType != self.ol_type:
1304 #                        self.word_host.Selection.Range.ListFormat.ApplyNumberDefault(win32com.client.constants.wdWord9ListBehavior)
1305 #                        if self.last_indent_type=='ul':
1306 #                            #need more indent
1307 #                            self.request.write("UL->OL 1")
1308 #                            self.word_host.Selection.Range.ListFormat.ListIndent()
1309 #                else:
1310 #                    if self.word_host.Selection.Range.ListFormat.ListType != self.ol_type:
1311 #                        self.word_host.Selection.TypeText("{bulleton}")
1312 #                        self.word_host.Selection.Range.ListFormat.ApplyNumberDefault(win32com.client.constants.wdWord9ListBehavior)
1313 #                        if self.last_indent_type=='ul':
1314 #                            #need more indent
1315 #                            self.request.write("UL->OL 2")
1316 #                            self.word_host.Selection.Range.ListFormat.ListIndent()
1317 #                    self.word_host.Selection.Range.ListFormat.ListIndent()
1318                 
1319             #self._ignore_next_paragraph=1
1320             self._first_li = 1
1321             self.indenttypeStack.ppush(self.last_indent_type)
1322             self.last_indent_type='ol'
1323             self.bulletStack.ppush(self.bulletText)
1324             self.styleStack.ppush(self.currentstyle)
1325 
1326             self.styleBullet.bulletFontName= "Times-Roman"
1327             self.styleBullet.bulletFontSize= 10
1328             self.currentstyle= copy.deepcopy(self.styleBullet)
1329 
1330             self.styleBullet.leftIndent+= 14
1331             self.styleBullet.bulletIndent+= 14
1332             return ret
1333 
1334         else:
1335             self.seq.reset("OL%s" % self.list_levels['ol'])  #reset current OLnumber
1336             self.list_levels['ol']=self.list_levels['ol']-1
1337             self.list_levels['all']=self.list_levels['all']-1
1338 
1339             if self.document!=None:
1340                 pass
1341 #TODO
1342 #                self.word_host.Selection.TypeParagraph()
1343 #                self.request.write("</OL> List type was: %s" % str(self.word_host.Selection.Range.ListFormat.ListType))
1344 #                if self.list_levels['ul']==0: 
1345 #                    if self.word_host.Selection.Range.ListFormat.ListType == self.ol_type:
1346 #                        self.word_host.Selection.Range.ListFormat.ApplyNumberDefault(win32com.client.constants.wdWord9ListBehavior)
1347 #                        if self.last_indent_type=='ul':
1348 #                            #need more outdent
1349 #                            self.request.write("UL->OL ??1??")
1350 #                            self.word_host.Selection.Range.ListFormat.ListOutdent()
1351 
1352 #                else:
1353 #                    if self.word_host.Selection.Range.ListFormat.ListType == self.ol_type:
1354 #                        self.word_host.Selection.Range.ListFormat.ApplyNumberDefault(win32com.client.constants.wdWord9ListBehavior)
1355 #                    self.word_host.Selection.Range.ListFormat.ListOutdent()
1356             #self._ignore_next_paragraph=1
1357             self.last_indent_type='' #obsolete
1358             ret=self.close(tag)
1359 
1360             self.bulletText= self.bulletStack.ppop()
1361             self.currentstyle= self.styleStack.ppop()
1362             self.last_indent_type= self.indenttypeStack.ppop()
1363             self.oltype= self.oltypeStack.ppop()
1364             if _debug:
1365                 print "   oltype (ol=off): %s    " % self.oltype
1366             self.styleBullet.leftIndent-= 14
1367             self.styleBullet.bulletIndent-= 14
1368             #styleStack returns None; set currentstyle
1369             if self.currentstyle==None:
1370                 self.currentstyle= self.standardstyle
1371 
1372             return ret
1373             
1374 
1375     def bullet_list(self, on):
1376         if _debug:
1377             traceback.print_stack(limit=1,file=sys.stdout)
1378 #RS fatal error handling
1379         if self.dead==1:
1380             return u""
1381 #RS end
1382         tag = 'ul'
1383         self.request.write("<bullet_list>:on=%s" % (str(on)))
1384         if on:
1385             ret=self.open(tag, newline=1)
1386             self.list_levels['ul']=self.list_levels['ul']+1
1387             self.list_levels['all']=self.list_levels['all']+1
1388 ##            if self.document!=None:
1389 #TODO
1390 ##                self.request.write("<UL> List type was: %s" % str(self.word_host.Selection.Range.ListFormat.ListType))
1391 #                if self.list_levels['ul']==1: #only first 
1392 #                    if self.word_host.Selection.Range.ListFormat.ListType != self.ul_type:
1393 #                        self.word_host.Selection.Range.ListFormat.ApplyBulletDefault(win32com.client.constants.wdWord9ListBehavior)
1394 #                else:
1395 #                    if self.word_host.Selection.Range.ListFormat.ListType != self.ul_type:
1396 #                        self.word_host.Selection.Range.ListFormat.ApplyBulletDefault(win32com.client.constants.wdWord9ListBehavior)
1397 #                    self.word_host.Selection.Range.ListFormat.ListIndent()
1398             #self._ignore_next_paragraph=1
1399 
1400             self.indenttypeStack.ppush(self.last_indent_type)
1401             self.last_indent_type='ul'
1402             self.bulletStack.ppush(self.bulletText)
1403             self.styleStack.ppush(self.currentstyle)
1404             if self.list_levels['ul'] == 1:
1405                 self.bulletText= '\267'
1406                 self.styleBullet.bulletFontSize= 11
1407 #            elif elf.list_levels['ul'] == 2:
1408             else:
1409                 self.bulletText= '\267'
1410                 self.styleBullet.bulletFontSize= 8
1411             self.styleBullet.bulletFontName= "Symbol"
1412             self.currentstyle= copy.deepcopy(self.styleBullet)
1413             self.styleBullet.leftIndent+= 14
1414             self.styleBullet.bulletIndent+= 14
1415 
1416             return ret
1417         else:
1418             self.list_levels['ul']=self.list_levels['ul']-1
1419             self.list_levels['all']=self.list_levels['all']-1
1420             if self.document!=None:
1421                 self.request.write("<bullet_list>:on=%s" % (str(on)))
1422 #                pass
1423 #TODO
1424 #                self.word_host.Selection.TypeParagraph()
1425 #                self.request.write("</UL> List type was: %s" % str(self.word_host.Selection.Range.ListFormat.ListType))
1426 #                if self.list_levels['ul']==0: 
1427 #                    if self.word_host.Selection.Range.ListFormat.ListType == self.ul_type:
1428 #                        self.word_host.Selection.Range.ListFormat.ApplyBulletDefault(win32com.client.constants.wdWord9ListBehavior)
1429 #                else:
1430 #                    if self.word_host.Selection.Range.ListFormat.ListType == self.ul_type:
1431 #                        self.word_host.Selection.Range.ListFormat.ApplyBulletDefault(win32com.client.constants.wdWord9ListBehavior)
1432 #                    self.word_host.Selection.Range.ListFormat.ListOutdent()
1433 
1434             self._ignore_next_paragraph=1
1435             self.last_indent_type=''
1436             ret=self.close(tag)
1437 
1438             self.bulletText= self.bulletStack.ppop()
1439             self.currentstyle= self.styleStack.ppop()
1440             self.last_indent_type= self.indenttypeStack.ppop()
1441             self.styleBullet.leftIndent-= 14
1442             self.styleBullet.bulletIndent-= 14
1443             #styleStack returns None; set currentstyle
1444             if self.currentstyle==None:
1445                 self.currentstyle= self.standardstyle
1446 #verusch indents
1447             if self.list_levels['ul']== 0:
1448                 while self.p_marker>0:
1449                     self.p_marker= self.p_markerStack.ppop()
1450                 del self.li_marker[0:]
1451 # versuch ende                
1452             return ret
1453 
1454     def listitem(self, on, **kw):
1455         if _debug:
1456             traceback.print_stack(limit=1,file=sys.stdout)
1457 #RS fatal error handling
1458         if self.dead==1:
1459             return u""
1460 #RS end
1461 ##        self._in_li = on != 0
1462         tag = 'li'
1463         self._in_li = on != 0
1464         if on:
1465 #versuch indents
1466             if self.last_indent_type=='ul':
1467                 self.li_marker.append(1)
1468                 self.p_markerStack.ppush(self.p_marker)
1469                 self.p_marker= None
1470 #versuch ende
1471             attr = {}
1472             css_class = kw.get('css_class', None)
1473             if css_class:
1474                 attr['class'] = css_class
1475             style = kw.get('style', None)
1476             if style:
1477                 attr['style'] = style
1478                 if style=="list-style-type:none" : # ? or css_class == 'gap':
1479                     self.nobullet= 1
1480                     self.bulletStack.ppush(self.bulletText)
1481                     self.bulletText= ''
1482                     #this is indent, not bullet
1483             ret=self.open(tag, attr=attr)
1484             #only by numbered lists - OLnumber depends on the ol indent;set the sequence-format
1485             if self.last_indent_type=='ol':
1486                 self.OLnumber="OL%s" % self.list_levels['ol']
1487                 self.seq.setFormat(self.OLnumber, self.oltype)
1488                 # difference between the default and a nondefault startvalue
1489                 if self.olstart>0:
1490                     self.seq.reset(self.OLnumber)  #reset current OLnumber (nondefault startvalue)
1491                     i= 0
1492                     while i< (self.olstart-1): #increase to startvalue-1
1493                         self.seq.nextf(self.OLnumber)
1494                         i+= 1
1495                     self.olstart= None
1496                 # increase the sequence of the current OLnumber and store it in self.bulletText
1497                 self.bulletText= "%s." % self.seq.nextf(self.OLnumber)
1498 ##                if not self.oltype == "1":
1499 ##                    self.seq.setFormat(self.OLnumber, self.oltype)
1500 ##                    self.bulletText= "%s" % self.seq.nextf(self.OLnumber)
1501 ##                else:
1502 ##                    self.bulletText= "%d." % self.seq.next(self.OLnumber)
1503 #            return
1504             return ret
1505         else:
1506 #versuch indents
1507             if self.last_indent_type=='ul':
1508                 del self.li_marker[-1]
1509                 self.p_marker= self.p_markerStack.ppop()
1510 #versuch ende
1511             if self.nobullet == 1:
1512                 self.bulletText= self.bulletStack.ppop()
1513                 self.nobullet= 0
1514             ret=self.close(tag)
1515 #            return
1516             return ret
1517 #RS end
1518 
1519     def definition_list(self, on):
1520         if _debug:
1521             traceback.print_stack(limit=1,file=sys.stdout)
1522 #RS fatal error handling
1523         if self.dead==1:
1524             return u""
1525 #RS end
1526         tag = 'dl'
1527         if on:
1528             ret=self.open(tag, newline=1)
1529             self.list_levels['dl']=self.list_levels['dl']+1
1530             self.list_levels['all']=self.list_levels['all']+1
1531             return ret
1532         else:
1533             self.list_levels['dl']=self.list_levels['dl']-1
1534             self.list_levels['all']=self.list_levels['all']-1
1535             ret=self.close(tag)
1536             return ret
1537 
1538     def definition_term(self, on):
1539         if _debug:
1540             traceback.print_stack(limit=1,file=sys.stdout)
1541 #RS fatal error handling
1542         if self.dead==1:
1543             return u""
1544 #RS end
1545         tag = 'dt'
1546         if on:
1547             ret=self.open(tag)
1548             return ret
1549         else:
1550             ret=self.close(tag)
1551             return ret
1552         
1553 
1554     def definition_desc(self, on):
1555         if _debug:
1556             traceback.print_stack(limit=1,file=sys.stdout)
1557 #RS fatal error handling
1558         if self.dead==1:
1559             return u""
1560 #RS end
1561         tag = 'dd'
1562         if on:
1563             ret=self.open(tag)
1564             return ret
1565         else:
1566             ret=self.close(tag)
1567             return ret
1568 
1569 
1570 
1571     def heading(self, on, depth, id = None, **kw):
1572         # remember depth of first heading, and adapt current depth accordingly
1573         if _debug:
1574             traceback.print_stack(limit=1,file=sys.stdout)
1575 #RS fatal error handling
1576         if self.dead==1:
1577             return u""
1578 #RS end
1579         tag= 'h'
1580 
1581         self._reset_indents()
1582         if not self._base_depth:
1583             self._base_depth = depth
1584 #RS adapt base depth if included
1585             self._base_depth=long(self.request.getPragma('_base_depth',str(self._base_depth)))
1586         oridepth=depth
1587 
1588 #RS isn't this nonsense???
1589 #        depth = max(depth - (self._base_depth - 1), 1)
1590         count_depth = max(depth - (self._base_depth - 1), 1)
1591 
1592 #?        depth = max(depth + (self._base_depth - 1), self._base_depth)
1593 #RS 1.1
1594         # check numbering, possibly changing the default
1595         if self._show_section_numbers is None:
1596             self._show_section_numbers = self.cfg.show_section_numbers
1597             numbering = self.request.getPragma('section-numbers', '').lower()
1598             if numbering in ['0', 'off']:
1599                 self._show_section_numbers = 0
1600             elif numbering in ['1', 'on']:
1601                 self._show_section_numbers = 1
1602             elif numbering in ['2', '3', '4', '5', '6']:
1603                 # explicit base level for section number display
1604                 self._show_section_numbers = int(numbering)
1605 #RS stop
1606 
1607         heading_depth = depth + 1
1608         if on:
1609             # create section number
1610             number = ''
1611             if self._show_section_numbers:
1612                 # count headings on all levels
1613                 self.request._fmt_hd_counters = self.request._fmt_hd_counters[:count_depth]
1614                 while len(self.request._fmt_hd_counters) < count_depth:
1615                     self.request._fmt_hd_counters.append(0)
1616                 self.request._fmt_hd_counters[-1] = self.request._fmt_hd_counters[-1] + 1
1617                 number = '.'.join(map(str, self.request._fmt_hd_counters[self._show_section_numbers-1:]))
1618                 if number: number += ". "
1619             attr = {}
1620             if id:
1621                 attr['id'] = id
1622             # Add space before heading, easier to check source code
1623             ret='\n' +self.open('h%d' % depth, attr=attr)
1624             return "%s%s" % (ret,number)
1625             
1626         else:
1627 ##            # closing tag, with empty line after, to make source more readable
1628             title=self.recordedtext
1629 #            if self.document!=None:
1630 #                pass
1631 #TODO
1632 #                self.word_host.Selection.TypeParagraph()
1633 #                style=win32com.client.constants.wdStyleHeading1 - depth +1
1634 #                self.word_host.Selection.Paragraphs.Last.Style=style
1635 #                self.word_host.Selection.TypeText('%s' % (title))
1636 #                self.word_host.Selection.TypeParagraph()
1637 #                self.word_host.Selection.Paragraphs.Last.Style=win32com.client.constants.wdStyleNormal
1638             self.currentstyle= copy.deepcopy(self.standardstyle)
1639             heading=""
1640             if depth == 1:
1641                 self.currentstyle=self.styleH1
1642                 for i in range(2,6):
1643                     self.seq.reset("H%s" % i)  # reset all deeper heading numbers
1644                 heading= "%(H1+)s " % self.seq # increase the current depth and write heading numbers till the current depth
1645             elif depth == 2:
1646                 self.currentstyle=self.styleH2
1647                 for i in range(3,6):
1648                     self.seq.reset("H%s" % i)  # reset all deeper heading numbers
1649                 heading= "%(H1)s.%(H2+)s " % self.seq # increase the current depth and write heading numbers till the current depth
1650             elif depth == 3:
1651                 self.currentstyle=self.styleH3
1652                 for i in range(4,6):
1653                     self.seq.reset("H%s" % i) # reset all deeper heading numbers
1654                 heading= "%(H1)s.%(H2)s.%(H3+)s " % self.seq # increase the current depth and write heading numbers till the current depth
1655             elif depth == 4:
1656                 self.currentstyle=self.styleH4
1657                 for i in range(5,6):
1658                     self.seq.reset("H%s" % i) # reset all deeper heading numbers
1659                 heading= "%(H1)s.%(H2)s.%(H3)s.%(H4+)s " % self.seq # increase the current depth and write heading numbers till the current depth
1660             elif depth == 5:
1661                 self.currentstyle=self.styleH5
1662                 for i in range(5,6):
1663                     self.seq.reset("H%s" % i) # reset all deeper heading numbers
1664                 heading= "%(H1)s.%(H2)s.%(H3)s.%(H4)s.%(H5+)s " % self.seq # increase the current depth and write heading numbers till the current depth
1665             heading += title
1666 #            self.story.append(Paragraph("[%s]%s" % (depth,title),self.currentstyle))
1667             self.story.append(Paragraph("%s" % (heading),self.currentstyle))
1668             if _debug:
1669                 sys.stderr.write(self.para_story+"\n")            
1670             self.currentstyle= copy.deepcopy(self.standardstyle)
1671 
1672             ret=self.close('h%d' % depth)
1673             return ret
1674 
1675 
1676 
1677     # Tables #############################################################
1678 
1679     _allowed_table_attrs = {
1680         'table': ['class', 'id', 'style'],
1681         'row': ['class', 'id', 'style'],
1682         '': ['colspan', 'rowspan', 'class', 'id', 'style'],
1683     }
1684 
1685     def _checkTableAttr(self, attrs, prefix):
1686         if _debug:
1687             traceback.print_stack(limit=1,file=sys.stdout)
1688         if not attrs: return u''
1689 
1690         result = ''
1691         for key, val in attrs.items():
1692             if prefix and key[:len(prefix)] != prefix: continue
1693             key = key[len(prefix):]
1694             if key not in self._allowed_table_attrs[prefix]: continue
1695             result = '%s %s=%s' % (result, key, val)
1696 
1697         return result
1698 
1699     def table(self, on, attrs=None):
1700         """ Create table
1701 
1702         @param on: start table
1703         @param attrs: table attributes
1704         @rtype: string
1705         @return start or end tag of a table
1706         """
1707         if _debug:
1708             traceback.print_stack(limit=1,file=sys.stdout)
1709 #RS fatal error handling
1710         if self.dead==1:
1711             return u""
1712 #RS end
1713         result = []
1714         if on:
1715             # Open div to get correct alignment with table width smaller
1716             # than 100%
1717 #            ret=self.open('div', newline=1)
1718 #            result.append(ret)
1719 
1720             # Open table
1721             if not attrs:
1722                 attrs = {}
1723             else:
1724                 attrs = self._checkTableAttr(attrs, 'table')
1725             ret= self.open('table', newline=1, attr=attrs)
1726 
1727             self.list_levels['table']=self.list_levels['table']+1
1728             self.list_levels['all']=self.list_levels['all']+1
1729             if self.document!=None:
1730                 pass
1731 #TODO
1732 #                if self.word_host.Selection.Range.ListFormat.ListType == win32com.client.constants.wdListBullet:
1733 #                    self.word_host.Selection.Range.ListFormat.ApplyBulletDefault(win32com.client.constants.wdWord9ListBehavior)
1734 #                self.word_host.Selection.TypeParagraph()
1735 #                self.document.Tables.Add(Range=self.word_host.Selection.Range,
1736 #                    NumRows=1, NumColumns= 1, DefaultTableBehavior=win32com.client.constants.wdWord9TableBehavior,
1737 #                    AutoFitBehavior= win32com.client.constants.wdAutoFitContent)
1738             self._first_tr = 1
1739             self._first_td = 1
1740             self._table_start=1
1741             return ret
1742         else:
1743             self.list_levels['table']=self.list_levels['table']-1
1744             self.list_levels['all']=self.list_levels['all']-1
1745             if self.document!=None:
1746                 pass
1747 #TODO
1748 #                self.word_host.Selection.MoveDown(Unit=win32com.client.constants.wdLine, Count=1)
1749 #                self.word_host.Selection.TypeParagraph()
1750 
1751             ret=self.close('table')
1752 #            ret=self.close('div')
1753             
1754             return ret
1755 
1756     def table_row(self, on, attrs=None):
1757         if _debug:
1758             traceback.print_stack(limit=1,file=sys.stdout)
1759 #RS fatal error handling
1760         if self.dead==1:
1761             return u""
1762 #RS end
1763         tag = 'tr'
1764         if on:
1765             if not attrs:
1766                 attrs = {}
1767             else:
1768                 attrs = self._checkTableAttr(attrs, 'row')
1769             ret=self.open(tag, newline=1, attr=attrs)
1770             if self._first_tr == 0:
1771                 #first row always existing
1772                 if self.document!=None:
1773                     pass
1774 #TODO
1775 #                    self.word_host.Selection.InsertRowsBelow(1)
1776                 self._first_td = 1
1777             elif self._first_td == 1:
1778 #                if self.document!=None:
1779 #                    self.word_host.Selection.TypeText('#')
1780                 self._table_start = 0
1781             return ret
1782         else:
1783             self._first_tr = 0
1784             ret=self.close(tag)
1785             return ret
1786             
1787 
1788     def table_cell(self, on, attrs=None):
1789         if _debug:
1790             traceback.print_stack(limit=1,file=sys.stdout)
1791 #RS fatal error handling
1792         if self.dead==1:
1793             return u""
1794 #RS end
1795         tag = 'tr'
1796         if on:
1797             if not attrs:
1798                 attrs = {}
1799             else:
1800                 attrs = self._checkTableAttr(attrs, 'row')
1801             ret=self.open(tag, newline=1, attr=attrs)
1802             if self.document!=None:
1803                 pass
1804 #TODO
1805 #                self.word_host.Selection.Style=self.defchar_style
1806             if self._first_tr == 1:
1807                 if self._first_td == 0:
1808                     #first cell always existing
1809                     if self.document!=None:
1810                         pass
1811 #TODO
1812 #                        self.word_host.Selection.InsertColumnsRight()
1813 #                        self.word_host.Selection.Style=self.defchar_style
1814                         
1815             else:
1816                 #jump into cell
1817                 if self.document!=None:
1818                     pass
1819 #TODO
1820 #                    self.word_host.Selection.MoveRight(Unit=win32com.client.constants.wdCell)
1821 #                    self.word_host.Selection.Style=self.defchar_style
1822                 self._first_td = 0
1823             return ret
1824         else:
1825             self._first_td = 0
1826             ret=self.close(tag)
1827             return ret
1828 
1829     def macro(self, macro_obj, name, args):
1830         #not implemented yet
1831         return ""
1832         # call the macro
1833         if name in ['TableOfContents',]:
1834             #skip call, emulate behavior
1835 ##    With ActiveDocument
1836 ##        .TablesOfContents.Add Range:=Selection.Range, RightAlignPageNumbers:= _
1837 ##            True, UseHeadingStyles:=True, UpperHeadingLevel:=1, _
1838 ##            LowerHeadingLevel:=3, IncludePageNumbers:=True, AddedStyles:="", _
1839 ##            UseHyperlinks:=True, HidePageNumbersInWeb:=True
1840 ##        .TablesOfContents(1).TabLeader = wdTabLeaderSpaces
1841 ##        .TablesOfContents.Format = wdIndexIndent
1842             try:
1843                 self.mindepth = max(int(self.request.getPragma('section-numbers', 1)),1)
1844             except (ValueError, TypeError):
1845                 self.mindepth = 1
1846 
1847             try:
1848                 self.maxdepth = max(int(args), 1)
1849             except (ValueError, TypeError):
1850                 self.maxdepth = 9
1851             sys.stdout.write("TOCrange:%s-%s" % (self.mindepth,self.maxdepth))
1852             if self.document!=None:
1853                 self.word_host.ActiveDocument.TablesOfContents.Add(\
1854                     Range=self.word_host.Selection.Range, UpperHeadingLevel=self.mindepth,\
1855                     LowerHeadingLevel=self.maxdepth,UseHyperlinks=vbTrue)
1856             return "<TOC/>"
1857         
1858         return macro_obj.execute(name, args) 
1859 
1860 
1861 
1862     def escapedText(self, text):
1863         return text
1864         return wikiutil.escape(text)
1865 
1866 
1867     def _img(self,imgurl,**kw):
1868 
1869         imageWidth= 0
1870         imageHeight= 0
1871         if _debug:
1872             traceback.print_stack(limit=1,file=sys.stdout)
1873 #RS fatal error handling
1874         if self.dead==1:
1875             return u""
1876 #RS end
1877         trusted=1
1878         scheme = string.split(imgurl, ":", 1)[0]
1879         if scheme in tuple(string.split('http|https|ftp|nntp','|')):
1880             trusted=0
1881             filepath=imgurl
1882             self.request.write("adding http picture, filepath=%s  " % (filepath))
1883             #retrieve remote file to temp
1884             try:
1885                 (filename, headers)=urllib.urlretrieve( imgurl)
1886                 print "remote url %s retrieved to %s" % (imgurl,filename)
1887                 filepath=filename
1888             except:
1889                 filepath=imgurl
1890             self.request.write("adding http picture, filepath=%s" % (filepath))
1891         elif scheme in tuple(string.split('file|self|wiki','|')):
1892             trusted=0
1893             #filepath=imgurl
1894 ##            filepath= string.split(imgurl, ':', 1)[1]
1895 ##            if filepath[3]==':': # eg: (file:)//C:\bla
1896 ##                filepath= string.split(filepath, '//', 1)[1]
1897 ##            self.request.write("adding file|self|wiki picture, filepath=%s  " % (filepath))
1898 #RS
1899             if scheme=="file":
1900                 filepath = string.split(imgurl, ":", 1)[1]
1901                 if filepath.find(":")!=-1:
1902                     filepath=filepath[2:]
1903                     self.request.write("adding file picture with drive, filepath=%s" % (filepath))
1904                 else:
1905                     filepath='\\\\'+filepath[2:]
1906                     self.request.write("adding file picture with UNC, filepath=%s" % (filepath))
1907             else:
1908                 filepath=imgurl
1909                 self.request.write("adding self|wiki picture, filepath=%s" % (filepath))
1910         else:
1911             trusted=1
1912             if imgurl.startswith("./"):
1913                 imgfile=imgurl[2:]        
1914                 filepath = os.path.abspath(os.path.join(self.cfg.url_prefix_dir, imgfile))
1915             elif imgurl.startswith(".\\"):
1916                 imgfile=imgurl[2:]
1917                 print "attachment?"
1918                 filepath = os.path.abspath(os.path.join(self.cfg.data_dir,"pages", imgfile))
1919             else:
1920                 imgfile=imgurl
1921                 filepath = os.path.abspath(os.path.join(self.cfg.url_prefix_dir, imgfile))
1922             self.request.write("\n adding .. picture, imgfile=%s, targetdir=%s, filepath=%s" % (imgfile,self.targetdir,filepath))
1923         if self.document!=None:
1924             pass 
1925 
1926         imageReader=ImageReader(filepath)
1927         imageWidth, imageHeight= imageReader.getSize()
1928         #scale imagesize (only a fixed maximum size at present : (PAGE_WIDTH- 6* cm):(PAGE_HEIGHT- 8* cm))
1929         if imageWidth > (self.PAGE_WIDTH- 6* cm) or imageHeight > (self.PAGE_HEIGHT- 8* cm):
1930             if imageWidth/ (self.PAGE_WIDTH- 6* cm) < imageHeight/ (self.PAGE_HEIGHT- 8* cm):
1931                 imageWidth= imageWidth/ (imageHeight/ (self.PAGE_HEIGHT- 8* cm))
1932                 imageHeight= imageHeight/ (imageHeight/ (self.PAGE_HEIGHT- 8* cm))
1933             else:
1934                 imageHeight= imageHeight/ (imageWidth/ (self.PAGE_WIDTH- 6* cm))
1935                 imageWidth= imageWidth/ (imageWidth/ (self.PAGE_WIDTH- 6* cm))
1936         self.story.append(Image(filepath, width= imageWidth, height= imageHeight))
1937 
1938 #word
1939 #            if self.word_host.Selection.Range.ListFormat.ListType == win32com.client.constants.wdListBullet:
1940 #                self.word_host.Selection.Range.ListFormat.ApplyBulletDefault(win32com.client.constants.wdWord9ListBehavior)
1941 #            try:
1942 #                self.word_host.Selection.InlineShapes.AddPicture(FileName=filepath,\
1943 #                  LinkToFile=False, SaveWithDocument=True)
1944 #            except:
1945 #                if trusted:
1946 #                    self.request.write("error in img, imgfile=%s, docpath=%s" % (filepath,str(self.document.Path)))
1947 #                    self.request.write("Active %s" % str(self.word_host.Selection.Active))
1948 #                    raise
1949 #                    errtext='[internal image not found:%s]' % filepath
1950 #                    self.document.Undo()
1951 #                    try:
1952 #                        self.word_host.Selection.TypeText(errtext)
1953 #                    except:
1954 #                        self.request.write("error reset did not work, may need Office 2000 SP3?")
1955 #                        raise "error reset did not work, may need Office 2000 SP3?"
1956 #                else:
1957 #                    self.request.write("warning in img, imgfile=%s, docpath=%s" % (filepath,str(self.document.Path)))
1958 #                    self.word_host.Selection.TypeText('[external image not found:%s]' % filepath)
1959 #                    
1960 #            self.word_host.Selection.TypeText(' ')
1961 #            self._save()
1962 
1963 
1964     def image(self, **kw):
1965         """ Take HTML <IMG> tag attributes in `attr`.
1966 
1967             Attribute names have to be lowercase!
1968         """
1969         #self.request.write("#def image" )
1970         if _debug:
1971             traceback.print_stack(limit=1,file=sys.stdout)
1972 #RS fatal error handling
1973         if self.dead==1:
1974             return u""
1975 #RS end
1976         attrstr = u''
1977         for attr, value in kw.items():
1978             if attr=='html_class':
1979                 attr='class'
1980             attrstr = attrstr + u' %s="%s"' % (attr, wikiutil.escape(value))
1981         imgurl=kw.get('src','')
1982         self.request.write("\ntry image, imgurl=%s  " % (imgurl))
1983         if imgurl!='':
1984             self._img(imgurl,**kw)
1985         result= u'<img%s/>' % attrstr
1986         return result
1987 
1988 
1989 
1990     def rawHTML(self, markup):
1991         """ This allows emitting pre-formatted HTML markup, and should be
1992             used wisely (i.e. very seldom).
1993 
1994             Using this event while generating content results in unwanted
1995             effects, like loss of markup or insertion of CDATA sections
1996             when output goes to XML formats.
1997         """
1998         return '<<'+markup+'>>'
1999 
2000 class Privatestack:
2001     '''a private LIFO Stack
2002     you can ppush an element on and ppop it from'''
2003 
2004     def __init__(self):
2005         self.__privatestack_= []
2006     def ppush(self, element):
2007         '''push an element on the stack'''
2008         self.__privatestack_.append(element)
2009         return
2010     def ppop(self):
2011         '''returns the last element from the stack
2012         (returns None for an empty stack)'''
2013         if not len(self.__privatestack_):
2014             return None
2015         element= self.__privatestack_.pop()
2016         return element
2017 
2018 ###abp flow start
2019 ##styles = getSampleStyleSheet()
2020 ###Title = wikiutil.quoteFilename(pagename)
2021 ###Author = self.request.user.name
2022 ###goFile = Title + DOC_SUFFIX
2023 ###goFilePath = os.path.abspath(os.path.join(self.targetdir, goFile))
2024 ##goFilePath = ''
2025 ##
2026 ##def myFirstPage(canvas, doc):
2027 ##    canvas.saveState()
2028 ##    canvas.restoreState()
2029 ##
2030 ##def myLaterPages(canvas, doc):
2031 ##    canvas.saveState()
2032 ##    canvas.setFont('Times-Roman',9)
2033 ##    canvas.drawString(inch, 0.75 * inch, "Page %d" % doc.page)
2034 ##    canvas.restoreState()
2035 ##
2036 ##def go(goFilePath):
2037 ##    doc = SimpleDocTemplate(goFilePath,showBoundary='showboundary' in sys.argv)
2038 ##    doc.allowSplitting = not 'nosplitting' in sys.argv
2039 ##    doc.build(Elements,myFirstPage,myLaterPages)
2040 ##
2041 ##Elements = []
2042 ##
2043 ##ChapterStyle = copy.copy(styles["Heading1"])
2044 ##ChapterStyle.alignment = TA_CENTER
2045 ##ChapterStyle.fontsize = 16
2046 ##InitialStyle = copy.deepcopy(ChapterStyle)
2047 ##InitialStyle.fontsize = 16
2048 ##InitialStyle.leading = 20
2049 ##PreStyle = styles["Code"]
2050 ##
2051 ##def newPage():
2052 ##    Elements.append(PageBreak())
2053 ##
2054 ##def chapter(txt, style=ChapterStyle):
2055 ##    newPage()
2056 ##    Elements.append(Paragraph(txt, style))
2057 ##    Elements.append(Spacer(0.2*inch, 0.3*inch))
2058 ##
2059 ##def fTitle(txt,style=InitialStyle):
2060 ##    Elements.append(Paragraph(txt, style))
2061 ##
2062 ##ParaStyle = copy.deepcopy(styles["Normal"])
2063 ##ParaStyle.spaceBefore = 0.1*inch
2064 ##
2065 ##if 'right' in sys.argv:
2066 ##    ParaStyle.alignment = TA_RIGHT
2067 ##elif 'left' in sys.argv:
2068 ##    ParaStyle.alignment = TA_LEFT
2069 ##elif 'justify' in sys.argv:
2070 ##    ParaStyle.alignment = TA_JUSTIFY
2071 ##elif 'center' in sys.argv or 'centre' in sys.argv:
2072 ##    ParaStyle.alignment = TA_CENTER
2073 ##else:
2074 ##    ParaStyle.alignment = TA_JUSTIFY
2075 ##
2076 ##def spacer(inches):
2077 ##    Elements.append(Spacer(0.1*inch, inches*inch))
2078 ##
2079 ##def p(txt, style=ParaStyle):
2080 ##    Elements.append(Paragraph(txt, style))
2081 ##
2082 ##def pre(txt, style=PreStyle):
2083 ##    spacer(0.1)
2084 ##    p = Preformatted(txt, style)
2085 ##    Elements.append(p)
2086 ##
2087 ##def parseOdyssey(output, pfilepath, ptitle, pauthor):
2088 ##
2089 ###    from time import time
2090 ##    E = []
2091 ###    t0=time()
2092 ###   L = open(fn,'r').readlines()
2093 ##    L = []
2094 ##    #L.append(output)
2095 ##    #for a in output:
2096 ##    #    L.append(a)
2097 ##    L=output.split("\n")  #jedes Listenelement ist eine Textzeile ohne \n
2098 ###    L.insert(0,'')
2099 ###    L.insert(0,'-----')
2100 ##    L.insert(0,'')
2101 ##    global goFilePath
2102 ##    goFilePath = pfilepath
2103 ##    Title = ptitle
2104 ##    Author = pauthor
2105 ###    t1 = time()
2106 ###    print "open stream took %.4f seconds" %(t1-t0)
2107 ####    L=replace(L,'\012','')
2108 ####	L=map(lambda x:x+"\012",L)
2109 ####	for i in xrange(len(L)):
2110 ####		if L[i][-1]=='\012':
2111 ####			L[i] = L[i][:-1]
2112 ###    t2 = time()
2113 ###    print "Removing all linefeeds took %.4f seconds" %(t2-t1)
2114 ###    L.append('')
2115 ###    L.append('-----')
2116 ###    lo=L[0]
2117 ###    lp=L[1]
2118 ###    print testen,lo,lp
2119 ##
2120 ####    def findNext(L, i):
2121 ####        kind=1
2122 ####        while 1: #moegliche abbruchbedingungen fuer die schleife:
2123 ####                 # -> es existiert eine Leerzeile
2124 ####                 # a) und dann keine weitere zeile -> ende (Leerzeile und dann nichts mehr)
2125 ####                 # b) weitere zeilen, dann werden
2126 ####                     #anschliessende leerzeilen entfernt
2127 ####                     # b) dann existiert keine weitere zeile -> ende (Leerzeilen und dann nichts mehr)
2128 ####                     # c) weitere zeilen existieren
2129 ####                         # naechste zeile beginnt und endet mit -?
2130 ####                             # c) ja: dann wird die zeile geloescht
2131 ####                             # c) danach keine weitere Zeile? -> ende (Leerzeile(n) direkt danach von '-' umrahmte zeile und dann nichts mehr)
2132 ####                                 # d) danach weitere zeilen: loesche nachfolgende leerzeilen und dann -> ende (Leerzeile(n) direkt danach von '-' umrahmte zeile)
2133 ####                             # e) nein: -> ende mit kind=0 und sofortiger neubeginn mit index 0
2134 ####            if string.strip(L[i])=='': #ist zeile i ohne sonderzeichen leer?
2135 ####                del L[i] #dann loesche die zeile i (zeilenanzahl verringert sich um 1)
2136 ####                kind = 1
2137 ####                if i<len(L): #index i kleiner als die neue Zeilengesamtzahl?
2138 ####                    while string.strip(L[i])=='': #solange zeile i ohne sonderzeichen leer?;loescht nach der leerzeile jetzt alle nachfolgenden leerzeilen
2139 ####                        del L[i] # loesche zeile i
2140 ####
2141 ####                    if i<len(L): #index i kleiner als die neue Zeilengesamtzahl?
2142 ####                        #kind = L[i][-1]=='-' and L[i][0]=='-'
2143 ####                        if L[i][-1]=='-' and L[i][0]=='-': #letzte und erste zeichen der zeile i ein '-'?
2144 ####                            kind = 1
2145 ####                        else:
2146 ####                            kind = 0
2147 ####                        if kind: #wenn kind wahr, also zeile i von '-' eingerahmt, dann:
2148 ####                            del L[i]  #loesche diese zeile
2149 ####                            if i<len(L):#index i kleiner als die neue Zeilengesamtzahl?
2150 ####                                while string.strip(L[i])=='':#solange zeile i ohne sonderzeichen leer?
2151 ####                                    del L[i] #loesche zeile i
2152 ####                break
2153 ####            else:
2154 ####                i = i + 1
2155 ####
2156 ####        return i, kind
2157 ##
2158 ##    def findNext(L, i):
2159 ##        while 1: 
2160 ####            if string.strip(L[i])=='': #ist zeile i ohne sonderzeichen leer?
2161 ####                del L[i] #dann loesche die zeile i (zeilenanzahl verringert sich um 1)
2162 ####                kind = 1
2163 ##            kind=1
2164 ##            if i>=len(L): #index i groesser als die neue Zeilengesamtzahl?
2165 ##                break
2166 ##            else:
2167 ##                while string.strip(L[i])=='': #solange zeile i ohne sonderzeichen leer?
2168 ##                    del L[i] # loesche zeile i
2169 ##                    if i>=len(L): #index i groesser als die neue Zeilengesamtzahl?
2170 ##                        break
2171 ##
2172 ##                if i>len(L): #index i groesser als die neue Zeilengesamtzahl?
2173 ##                    break
2174 ##                else:
2175 ##                    if L[i][0:9] == '#STARTDOC' or L[i][-7:] == '#ENDDOC':
2176 ##                        kind = 1
2177 ##                    else:
2178 ##                        kind = 0
2179 ##                    if kind: 
2180 ##                       # del L[i]  #loesche diese zeile
2181 ##                        if i<=len(L):#index i kleiner gleich die neue Zeilengesamtzahl?
2182 ##                            while string.strip(L[i])=='':#solange zeile i ohne sonderzeichen leer?
2183 ##                                del L[i] #loesche zeile i
2184 ##                        break
2185 ##            i = i + 1
2186 ##
2187 ##        return i, kind
2188 ##
2189 ##
2190 ##    f = s = 0
2191 ##    while 1:
2192 ##        f, k = findNext(L,0)
2193 ##        if k: break
2194 ##
2195 ##    E.append([spacer,2])
2196 ##    E.append([fTitle, Title, InitialStyle])
2197 ##    E.append([fTitle,'<font size=-4>translated by</font> %s' % Author, InitialStyle])
2198 ###    print testen,L,E,f,k
2199 ##
2200 ##    while 1:
2201 ##        if f>=len(L): break
2202 ###        print testen,L,E,f,k
2203 ##        if string.upper(L[f].strip()[0:5])=='BOOK ':
2204 ##            E.append([chapter,L[f]])
2205 ##            f=f+1
2206 ##            while string.strip(L[f])=='': del L[f]
2207 ##            style = ParaStyle
2208 ##            func = p
2209 ##        else:
2210 ##            style = PreStyle
2211 ##            func = pre
2212 ##
2213 ##        while 1:
2214 ##            s=f
2215 ##            f, k=findNext(L,s)
2216 ##            sep= (func is pre) and '\012' or ' '
2217 ##            #print testen,L,E,s,f
2218 ##
2219 ##            E.append([func,string.join(L[s:f],sep),style])
2220 ##            if k: break
2221 ###    t3 = time()
2222 ###    print "Parsing into memory took %.4f seconds" %(t3-t2)
2223 ###    print testen,L,E
2224 ##    del L
2225 ###    t4 = time()
2226 ###    print "Deleting list of lines took %.4f seconds" %(t4-t3)
2227 ##    for i in xrange(len(E)):
2228 ##        apply(E[i][0],E[i][1:])
2229 ###    t5 = time()
2230 ###    print "Moving into platypus took %.4f seconds" %(t5-t4)
2231 ##    del E
2232 ###    t6 = time()
2233 ###    print "Deleting list of actions took %.4f seconds" %(t6-t5)
2234 ##    go(goFilePath)
2235 ###    t7 = time()
2236 ###    print "saving to PDF took %.4f seconds" %(t7-t6)
2237 ###    print "Total run took %.4f seconds"%(t7-t0)
2238 ##
2239 ###    for fn in ('odyssey.full.txt','odyssey.txt'):
2240 ###        if os.path.isfile(fn):
2241 ###            break
2242 ##
2243 ##
2244 ###abp flow pause

Attached Files

To refer to attachments on a page, use attachment:filename, as shown below in the list of files. Do NOT use the URL of the [get] link, since this is subject to change and can break easily.
  • [get | view] (2005-10-24 16:41:36, 3.6 KB) [[attachment:FrontPage.pdf]]
  • [get | view] (2005-10-20 23:45:56, 124.5 KB) [[attachment:SyntaxReference.doc]]
  • [get | view] (2005-10-20 23:27:53, 19.0 KB) [[attachment:moin_export.py]]
  • [get | view] (2005-10-24 14:06:32, 3.9 KB) [[attachment:request_ors.py]]
  • [get | view] (2005-10-27 14:27:18, 81.6 KB) [[attachment:text_pdf.py]]
  • [get | view] (2005-10-20 23:29:45, 66.2 KB) [[attachment:text_word.py]]
  • [get | view] (2005-11-03 17:30:17, 53.9 KB) [[attachment:wiki_word.py]]
 All files | Selected Files: delete move to page copy to page

You are not allowed to attach a file to this page.