# copyright 2003-2011 LOGILAB S.A. (Paris, FRANCE), all rights reserved.
# contact http://www.logilab.fr/ -- mailto:contact@logilab.fr
#
# This file is part of logilab-common.
#
# logilab-common is free software: you can redistribute it and/or modify it under
# the terms of the GNU Lesser General Public License as published by the Free
# Software Foundation, either version 2.1 of the License, or (at your option) any
# later version.
#
# logilab-common is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public License for more
# details.
#
# You should have received a copy of the GNU Lesser General Public License along
# with logilab-common.  If not, see <http://www.gnu.org/licenses/>.
"""Text formatting drivers for ureports"""

from __future__ import print_function

__docformat__ = "restructuredtext en"

from six.moves import range

from logilab.common.textutils import linesep
from logilab.common.ureports import BaseWriter


TITLE_UNDERLINES = [u'', u'=', u'-', u'`', u'.', u'~', u'^']
BULLETS = [u'*', u'-']

class TextWriter(BaseWriter):
    """format layouts as text
    (ReStructured inspiration but not totally handled yet)
    """
    def begin_format(self, layout):
        super(TextWriter, self).begin_format(layout)
        self.list_level = 0
        self.pending_urls = []

    def visit_section(self, layout):
        """display a section as text
        """
        self.section += 1
        self.writeln()
        self.format_children(layout)
        if self.pending_urls:
            self.writeln()
            for label, url in self.pending_urls:
                self.writeln(u'.. _`%s`: %s' % (label, url))
            self.pending_urls = []
        self.section -= 1
        self.writeln()

    def visit_title(self, layout):
        title = u''.join(list(self.compute_content(layout)))
        self.writeln(title)
        try:
            self.writeln(TITLE_UNDERLINES[self.section] * len(title))
        except IndexError:
            print("FIXME TITLE TOO DEEP. TURNING TITLE INTO TEXT")

    def visit_paragraph(self, layout):
        """enter a paragraph"""
        self.format_children(layout)
        self.writeln()

    def visit_span(self, layout):
        """enter a span"""
        self.format_children(layout)

    def visit_table(self, layout):
        """display a table as text"""
        table_content = self.get_table_content(layout)
        # get columns width
        cols_width = [0]*len(table_content[0])
        for row in table_content:
            for index in range(len(row)):
                col = row[index]
                cols_width[index] = max(cols_width[index], len(col))
        if layout.klass == 'field':
            self.field_table(layout, table_content, cols_width)
        else:
            self.default_table(layout, table_content, cols_width)
        self.writeln()

    def default_table(self, layout, table_content, cols_width):
        """format a table"""
        cols_width = [size+1 for size in cols_width]
        format_strings = u' '.join([u'%%-%ss'] * len(cols_width))
        format_strings = format_strings % tuple(cols_width)
        format_strings = format_strings.split(' ')
        table_linesep = u'\n+' + u'+'.join([u'-'*w for w in cols_width]) + u'+\n'
        headsep = u'\n+' + u'+'.join([u'='*w for w in cols_width]) + u'+\n'
        # FIXME: layout.cheaders
        self.write(table_linesep)
        for i in range(len(table_content)):
            self.write(u'|')
            line = table_content[i]
            for j in range(len(line)):
                self.write(format_strings[j] % line[j])
                self.write(u'|')
            if i == 0 and layout.rheaders:
                self.write(headsep)
            else:
                self.write(table_linesep)

    def field_table(self, layout, table_content, cols_width):
        """special case for field table"""
        assert layout.cols == 2
        format_string = u'%s%%-%ss: %%s' % (linesep, cols_width[0])
        for field, value in table_content:
            self.write(format_string % (field, value))


    def visit_list(self, layout):
        """display a list layout as text"""
        bullet = BULLETS[self.list_level % len(BULLETS)]
        indent = '  ' * self.list_level
        self.list_level += 1
        for child in layout.children:
            self.write(u'%s%s%s ' % (linesep, indent, bullet))
            child.accept(self)
        self.list_level -= 1

    def visit_link(self, layout):
        """add a hyperlink"""
        if layout.label != layout.url:
            self.write(u'`%s`_' % layout.label)
            self.pending_urls.append( (layout.label, layout.url) )
        else:
            self.write(layout.url)

    def visit_verbatimtext(self, layout):
        """display a verbatim layout as text (so difficult ;)
        """
        self.writeln(u'::\n')
        for line in layout.data.splitlines():
            self.writeln(u'    ' + line)
        self.writeln()

    def visit_text(self, layout):
        """add some text"""
        self.write(u'%s' % layout.data)
