view frontends/src/primitivus/progress.py @ 489:f36c705a5310

core: sendMessage refactoring: - "auto" message type which autodetect XMPP message type according to context - added "sendMessage" trigger so plugins can hook messages
author Goffi <goffi@goffi.org>
date Fri, 17 Aug 2012 03:11:03 +0200
parents 2a072735e459
children 2c4016921403
line wrap: on
line source

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

"""
Primitivus: a SAT frontend
Copyright (C) 2009, 2010, 2011, 2012  Jérôme Poisson (goffi@goffi.org)

This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

This program 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 Affero General Public License for more details.

You should have received a copy of the GNU Affero General Public License
along with this program.  If not, see <http://www.gnu.org/licenses/>.
"""

import urwid
from urwid_satext import sat_widgets
from sat.tools.jid import JID


class Progress(urwid.WidgetWrap):

    def __init__(self, host):
        self.host = host
        self.progress_list = urwid.SimpleListWalker([])
        self.progress_dict = {}
        listbox = urwid.ListBox(self.progress_list)
        buttons = []
        buttons.append(sat_widgets.CustomButton(_('Clear progress list'), self.__onClear))
        max_len = max([button.getSize() for button in buttons])
        buttons_wid = urwid.GridFlow(buttons,max_len,1,0,'center')
        main_wid = sat_widgets.FocusFrame(listbox, footer=buttons_wid)
        urwid.WidgetWrap.__init__(self, main_wid)

    def addProgress(self, id, message):
        mess_wid = urwid.Text(message)
        progr_wid = urwid.ProgressBar('progress_normal', 'progress_complete')
        column = urwid.Columns([mess_wid, progr_wid])
        self.progress_dict[id] = {'full':column,'progress':progr_wid,'state':'init'}
        self.progress_list.append(column)
        self.progressCB(self.host.loop, (id, message))

    def progressCB(self, loop, data):
        id, message = data
        data = self.host.bridge.getProgress(id)
        pbar = self.progress_dict[id]['progress']
        if data:
            if self.progress_dict[id]['state'] == 'init':
                #first answer, we must construct the bar
                self.progress_dict[id]['state'] = 'progress'
                pbar.done = float(data['size'])
                
            pbar.set_completion(float(data['position']))
            self.updateNotBar()
        else:
            if self.progress_dict[id]['state'] == 'progress':
                self.progress_dict[id]['state'] = 'done'
                pbar.set_completion(pbar.done)
                self.updateNotBar()
                return

        loop.set_alarm_in(1,self.progressCB, (id, message))

    def __removeBar(self, id):
        wid = self.progress_dict[id]['full']
        self.progress_list.remove(wid)
        del(self.progress_dict[id])

    def __onClear(self, button):
       to_remove = []
       for id in self.progress_dict:
           if self.progress_dict[id]['state'] == 'done':
               to_remove.append(id)
       for id in to_remove:
           self.__removeBar(id)
       self.updateNotBar()

    def updateNotBar(self):
        if not self.progress_dict:
            self.host.setProgress(None)
            return
        progress = 0
        nb_bars = 0
        for id in self.progress_dict:
            pbar = self.progress_dict[id]['progress']
            progress += pbar.current/pbar.done*100
            nb_bars+=1
        av_progress = progress/float(nb_bars)
        self.host.setProgress(av_progress)