#!/data/data/com.termux/files/usr/bin/python

import os
import pickle
import re
import sys

# TODO: tech-debt
# better dependency check
# xml parsing
# use html2text python api
# windows compatibility?

class Book:
    def __init__(self):
        self.chapters = []
        self.chapter = 0
        self.paragraph = 0
        self.character = 0

    def chars_total(self):
        l=0
        for c in self.chapters:
            for p in c:
                for s in p:
                    l+=len(s)
        return l

    def chars_partial(self, chapter, paragraph):
        l=0
        for c in self.chapters[:chapter]:
            for p in c:
                for s in p:
                    l+=len(s)
        for p in self.chapters[chapter]:
            for s in p[:paragraph]:
                l+=len(s)
        return l

# Hacky way to test dependencies
try:
    import html2text
except: # and install them
    os.system('pip install --upgrade pip')
    os.system('pip install epub')
    os.system('pip install html2text')
    os.system('pip install blessed')

import blessed
import epub

# Get book name as argument
filename = sys.argv[1]

# Prepare needed file paths
cwd=os.getcwd()
book_path = cwd + '/' + filename
work_path = cwd + '/' + filename + '-ebook'
save_file = cwd + '/' + filename + '.pickle'

# Check if pickle file exist
if os.path.isfile(save_file):
    # Load data from pickle file
    book = pickle.load(open(save_file, 'rb'))
    chapter = book.chapter
    paragraph = book.paragraph
    character = book.character
    chapters = book.chapters

else:
    # Create tmp directory
    # To use when unpacking epub
    os.system('rm -rf ' + work_path)
    os.makedirs(work_path)
    os.chdir(work_path)

    # Open the book
    ebook = epub.open(book_path)
    ebook.extractall()
    os.chdir(work_path + '/OEBPS')

    # Find all files and their order from content.opf
    # TODO: This might be any .opf file anywhere in the package
    content = open('content.opf', 'r')
    content_xml = content.readlines()
    content.close()

    content_dict = {}
    content_list = []
    for line in content_xml:
        if line.find('item ') > 0:
            id = re.findall(r'id="[^"]*"', line)[0][4:-1]
            href = re.findall(r'href="[^"]*"', line)[0][6:-1]
            content_dict[id] = href
        elif line.find('itemref ') > 0:
            idref = re.findall(r'idref="[^"]*"', line)[0][7:-1]
            content_list.append(idref)

    # Use html2text to convert one by one
    # Store all chapters as lists of strings in a list

    book = Book()
    chapters = []
    for idref in content_list:
        textbuffer = os.popen('html2text --unicode-snob --ignore-emphasis --body-width=0 ' + content_dict[idref])
        book.chapters.append(textbuffer.read().split('\n'))
        textbuffer.close()
        while book.chapters[-1].count('') > 0:
            book.chapters[-1].remove('')

    # Clean up all files again
    os.system('rm -rf ' + work_path)

    # Set up terminal and navigation coords.
    chapter = 0
    paragraph = 0
    character = 0

# Set up terminal window
t = blessed.Terminal()

print(t.enter_fullscreen)

# Display a first page.
# Then look for key input.

# TODO: features
# skip char
# skip word
# print page
# jump to specific chapter
# auto save

totchar = book.chars_total()
parachar = book.chars_partial(chapter, paragraph)

with t.cbreak():
    prev_key = None
    while 1:
        curchar=parachar+character
        para = book.chapters[chapter][paragraph]
        size = (t.height - 1) * t.width
        center = int(size / 2)
        start = max(min(character - center, len(para) - size), 0)
        end = min(start + size, len(para))
        chapstr = 'Chapter: '+str(chapter+1)+'/'+str(len(book.chapters))
        parastr = 'Paragraph: '+str(paragraph+1)+'/'+str(len(book.chapters[chapter]))
        charstr = 'Progress: '+str(int(curchar*100/totchar))+'%'
        print(t.clear())
        print(chapstr + ' ' + parastr + ' ' + charstr)
        print(t.green(para[start:character]) + t.red(para[character:end]))
        if prev_key:
            with t.location(0, t.height - 1):
                print('Last key: ', prev_key)
        next_char = para[character]
        key = t.inkey()
        if key == next_char:
            character += 1
        elif key == '1':
            print(t.exit_fullscreen)
            print('Quit: 1 pressed')
            break
        elif key == '6':
            character += 1
        elif key == '5':
            character -= 1
        elif key == '7':
            character += 1 #todo reach next whitespacr
        elif key == '4':
            character -= 1
            character = max(character, 0)
        elif key == '8':
            paragraph += 1
            character = 0
        elif key == '3':
            paragraph -= 1
            character = 0
        elif key == '9':
            chapter += 1
            paragraph = 0
            character = 0
        elif key == '2':
            chapter -= 1
            paragraph = 0
            character = 0
        else:
           prev_key = key
        if chapter >= len(book.chapters):
            print(t.exit_fullscreen)
            print('Quit: book over')
            break
        if character >= len(para):
            paragraph += 1
            character = 0
        if paragraph >= len(book.chapters[chapter]):
            chapter += 1
            paragraph = 0
            character = 0
        if chapter >= len(book.chapters):
            print(t.exit_fullscreen)
            print('Quit: book over')
            break
        if character == 0:
            parachar = book.chars_partial(chapter, paragraph)

        # Save data to pickle file
#        data = {}
#        data['chapter'] = chapter
#        data['paragraph'] = paragraph
#        data['character'] = character
#        data['chapters'] = chapters
        book.chapter = chapter
        book.paragraph = paragraph
        book.character = character

pickle.dump(book, open(save_file, 'wb'))
