#!/usr/bin/env python
# -*- coding: utf-8 -*-


import os, os.path, sys

import urwid
import urwid.raw_display


ui = None

class InternalView:
    """Internal View class"""

    def __init__(self, title, buf, vcenter=True):
        self.title = title
        self.init_ui()
        self.orig_buf = buf
        self.vcenter = vcenter
        self.__validate_buf()

    def init_ui(self):
        self.size = ui.get_cols_rows()
        palete = [
            ('header', 'yellow', 'dark blue', 'bold'),
            ('footer', 'brown', 'dark blue'),
            ('body2', 'light blue', 'default'),
            ('body', 'light gray', 'default')]
        ui.register_palette(palete)

    def __validate_buf(self, y=0):
        w = self.size[0]
        h = self.size[1]-2
        buf = [(l[:-1][:w-2], 'body') for l in self.orig_buf]
        buf2 = [l for l in buf]
        self.nlines = len(buf2)
        if self.nlines > h:
            self.y0 = 0
            self.large = True
            self.y = y
        else:
            self.y0 = int(((h) - self.nlines)/2)
            self.large = False
            self.y = -1
        if self.vcenter:
            col_max = max(map(len, buf2))
            self.x0 = int((w - col_max)/2)
        else:
            col_max = -1
            self.x0 = 1
        self.buf = buf

    def display(self):
        """show title, file and status bar"""
        w = self.size[0]; h = self.size[1]-2
        title = self.title
        if len(title) - 4 > w:
            title = title[:w-12] + '~' + title[-7:]
        header =  urwid.Text(('header', title), align='center')
        header = urwid.AttrWrap(header, 'footer')
        contents = []
        i = 0
#       self.win_body.addstr(self.y0 + i, self.x0, l)
        if self.large:
            for l, c in self.buf[self.y:self.y+self.size[0]-2]:
                t = urwid.Text((c, l), wrap='clip')
                contents.append(t)
                i += 1
        else:
            for l, c in self.buf:
                t = urwid.Text((c, l), wrap='clip')
                contents.append(t)
                i += 1
        w = urwid.SimpleListWalker(contents)
        body = urwid.AttrWrap(urwid.ListBox(w), 'body')
        if self.large:
            status = ''
        else:
            status = 'Press a key to continue'
        footer = urwid.Text(('footer', status), align='center', wrap='clip')
        footer = urwid.AttrWrap(footer, 'footer')
        frame = urwid.Frame(body, header, footer)
        canvas = frame.render(self.size, focus=1)
        ui.draw_screen(self.size, canvas)


    def run(self):
        self.display()
        ymax = self.nlines - self.size[1] + 3
        w_body = self.size[1] - 2
        if self.large:
            quit = False
            while not quit:
                keys = None
                while not keys:
                    keys = ui.get_input()
                for k in keys:
                    if k in ('p', 'P', 'up'):
                        if self.y != 0:
                            self.y -= 1
                    elif k in ('n', 'N', 'down'):
                        if self.y < ymax:
                            self.y += 1
                    elif k in ('home', ):
                        self.y = 0
                    elif k in ('end', ):
                        self.y = ymax
                    elif k in ('page up', 'backspace'):
                        self.y -= w_body
                        if self.y < 0:
                            self.y = 0
                    elif k in ('page down', ' '):
                        self.y += w_body
                        if self.y > self.nlines - 1:
                            self.y = ymax
                    elif k == 'ctrl o':
                        ui.stop()
                        os.system('sh')
                        ui.start()
                    elif k in ('q', 'Q', 'x', 'X', 'esc', 'f3', 'f10'):
                        quit = True
                    elif k == 'window resize':
                        self.size = ui.get_cols_rows()
                        self.__validate_buf(y=self.y)
                self.display()
        else:
            while not ui.get_input():
                pass

def main():
    global ui
    ui = urwid.raw_display.Screen()
    title = sys.argv[0]
    buf = open(title).readlines()
    v = InternalView(title, buf)
    ui.run_wrapper(v.run)

if __name__ == '__main__':
    main()
