Exemplo n.º 1
0
    def get_table_summary(self, mi, ar):
        if ar is None:
            return ''
        sar = self.request_from(ar, master_instance=mi)

        def fmt(obj):
            return str(obj)

        elems = []
        for obj in sar:
            # if len(elems) > 0:
            #     elems.append(', ')

            lbl = fmt(obj)
            # if obj.state.button_text:
            #     lbl = "{0}{1}".format(lbl, obj.state.button_text)
            elems.append(ar.obj2html(obj, lbl))
        elems = join_elems(elems, sep=', ')
        toolbar = []
        ar2 = self.insert_action.request_from(sar)
        if ar2.get_permission():
            btn = ar2.ar2button()
            toolbar.append(btn)

        if len(toolbar):
            toolbar = join_elems(toolbar, sep=' ')
            elems.append(E.p(*toolbar))

        return ar.html_text(E.div(*elems))
Exemplo n.º 2
0
    def as_html(self, ar):
        elems = []
        events = list(self.used_events)
        invoiced = events[self.invoiced_events:]
        coming = events[:self.invoiced_events]

        def fmt(ev):
            txt = day_and_month(ev.start_date)
            if ar is None:
                return txt
            return ar.obj2html(ev, txt)
        if len(invoiced) > 0:
            elems.append("{0} : ".format(_("Invoiced")))
            if len(invoiced) > MAX_SHOWN:
                elems.append("(...) ")
                invoiced = invoiced[-MAX_SHOWN:]
            elems += join_elems(map(fmt, invoiced), sep=', ')
            # s += ', '.join(map(fmt, invoiced))
            # elems.append(E.p(s))
        if len(coming) > 0:
            if len(elems) > 0:
                elems.append(E.br())
            elems.append("{0} : ".format(_("Not invoiced")))
            elems += join_elems(map(fmt, coming), sep=', ')
            # s += ', '.join(map(fmt, coming))
            # elems.append(E.p(s))
        return E.p(*elems)
Exemplo n.º 3
0
    def get_table_summary(self, mi, ar):
        if ar is None:
            return ''
        sar = self.request_from(ar, master_instance=mi)

        def fmt(obj):
            return str(obj)

        elems = []
        for obj in sar:
            # if len(elems) > 0:
            #     elems.append(', ')

            lbl = fmt(obj)
            # if obj.state.button_text:
            #     lbl = "{0}{1}".format(lbl, obj.state.button_text)
            elems.append(ar.obj2html(obj, lbl))
        elems = join_elems(elems, sep=', ')
        toolbar = []
        ar2 = self.insert_action.request_from(sar)
        if ar2.get_permission():
            btn = ar2.ar2button()
            toolbar.append(btn)

        if len(toolbar):
            toolbar = join_elems(toolbar, sep=' ')
            elems.append(E.p(*toolbar))

        return ar.html_text(E.div(*elems))
Exemplo n.º 4
0
    def get_table_summary(self, obj, ar):
        """Customized :meth:`summary view
        <lino.core.actors.Actor.get_table_summary>` for this table.

        """
        sar = self.request_from(ar, master_instance=obj)

        html = []
        states = {}
        for s, d in VoteStates.choices:
            states[s] = []

        u = ar.get_user()

        for o in sar:
            states[o.state].append(
                ar.obj2html(o, o.user.initials or str(o.user), title=o.state))
            if u == o.user:
                html.insert(
                    0,
                    E.span(
                        E.b(str(o.state)), u" \u2192 ",
                        *join_elems([
                            sar.action_button(ba, o)
                            for ba in sar.actor.get_actions()
                            if ba.action.show_in_workflow and
                            sar.actor.get_row_permission(o, sar, o.state, ba)
                            and isinstance(ba.action, dd.ChangeStateAction)
                        ], " ")))

        html.append(
            E.ul(*[
                E.li(*([str(s.text), ": "] + join_elems(states[s], sep=", ")))
                for s, c in VoteStates.choices if states[s]
            ]))
        # print(tostring(html))
        # items = [
        #     ar.obj2html(o, o.user.username or str(o.user))
        #     for o in rt.models.votes.Vote.objects.filter(
        #             votable=obj).order_by('-id')]
        # sar.get_user() == v.user
        sar = self.insert_action.request_from(sar)
        if sar.get_permission():
            # btn = sar.ar2button(None, _("Add voter"), icon_name=None)
            btn = sar.ar2button()
            # btn = sar.ar2button(None, u"⏍", icon_name=None)  # 23CD SQUARE FOOT
            # btn = sar.ar2button(None, u"⊞", icon_name=None) # 229e SQUARED PLUS

            html.append(E.div(btn))

        return ar.html_text(E.div(*html))
Exemplo n.º 5
0
    def get_table_summary(self, obj, ar):
        """Customized :meth:`summary view
        <lino.core.actors.Actor.get_table_summary>` for this table.

        """
        sar = self.request_from(ar, master_instance=obj)

        html = []
        states = {}
        for s, d in VoteStates.choices:
            states[s] = []

        u = ar.get_user()

        for o in sar:
            states[o.state].append(ar.obj2html(o, o.user.initials or str(o.user), title=o.state))
            if u == o.user:
                html.insert(0, E.span(
                    E.b(str(o.state)),
                    u" \u2192 ",
                    *join_elems([sar.action_button(ba, o) for ba in sar.actor.get_actions()
                                 if ba.action.show_in_workflow and
                                 sar.actor.get_row_permission(o, sar, o.state, ba) and
                                 isinstance(ba.action, dd.ChangeStateAction)],
                                " ")
                ))


        html.append(E.ul(
            *[E.li(*([str(s.text),  ": "] + join_elems(states[s], sep=", "))) for s, c in VoteStates.choices
              if states[s]
              ]
        ))
        # print(tostring(html))
        # items = [
        #     ar.obj2html(o, o.user.username or str(o.user))
        #     for o in rt.models.votes.Vote.objects.filter(
        #             votable=obj).order_by('-id')]
        # sar.get_user() == v.user
        sar = self.insert_action.request_from(sar)
        if sar.get_permission():
            # btn = sar.ar2button(None, _("Add voter"), icon_name=None)
            btn = sar.ar2button()
            # btn = sar.ar2button(None, u"⏍", icon_name=None)  # 23CD SQUARE FOOT
            # btn = sar.ar2button(None, u"⊞", icon_name=None) # 229e SQUARED PLUS
            
            html.append(E.div(btn))

            
        return ar.html_text(E.div(*html))
Exemplo n.º 6
0
 def get_overview_elems(self, ar):
     elems = []
     buttons = self.get_mti_buttons(ar)
     buttons = join_elems(buttons, ', ')
     elems.append(E.p(unicode(_("See as ")), *buttons,
                      style="font-size:8px;text-align:right;padding:3pt;"))
     elems += self.get_name_elems(ar)
     elems.append(E.br())
     elems += join_elems(list(self.address_location_lines()), sep=E.br)
     elems = [
         E.div(*elems,
               style="font-size:18px;font-weigth:bold;"
               "vertical-align:bottom;text-align:middle")]
     return elems
Exemplo n.º 7
0
def get_calendar_summary(cls, obj, ar):
    # print("20181121 get_calendar_summary", cls)
    # note that objects can be either Event or Guest. if the view
    # is called for Guest, we waht to display the guest states
    # (not the event states). But when user clicks on a date they
    # want to show the event even when we are calling from Guest.
    if ar is None or obj is None:
        return ''
    state_coll = {}
    cal = CalendarRenderer(cls.model)
    # sar = ar.spawn(parent=ar, master_instance=obj)
    # sar = ar.actor.request(parent=ar, master_instance=obj)
    sar = cls.request_from(ar, master_instance=obj)
    # sar = cls.request(parent=ar, master_instance=obj)
    # print("20181121 {}".format(ar.actor))
    # print("20181121 {}".format(cls.get_filter_kw(sar)))
    # print("20181121 {}".format(len(list(sar))))
    for obj in sar:
        if obj.state in state_coll:
            state_coll[obj.state] += 1
        else:
            state_coll[obj.state] = 1
        cal.collect(obj)

    elems = [cal.to_html(ar)]
    # choicelist = EntryStates
    choicelist = cls.workflow_state_field.choicelist
    ul = []
    for st in choicelist.get_list_items():
        ul.append(_("{} : {}").format(st, state_coll.get(st, 0)))
    toolbar = []
    toolbar += join_elems(ul, sep=', ')
    # elems = join_elems(ul, sep=E.br)
    if isinstance(obj, rt.models.cal.EventGenerator):
        ar1 = obj.do_update_events.request_from(sar)
        if ar1.get_permission():
            btn = ar1.ar2button(obj)
            toolbar.append(btn)

    ar2 = cls.insert_action.request_from(sar)
    if ar2.get_permission():
        btn = ar2.ar2button()
        toolbar.append(btn)

    if len(toolbar):
        toolbar = join_elems(toolbar, sep=' ')
        elems.append(E.p(*toolbar))

    return ar.html_text(E.div(*elems))
Exemplo n.º 8
0
Arquivo: ui.py Projeto: einarfelix/xl
def get_calendar_summary(cls, obj, ar):
    # print("20181121 get_calendar_summary", cls)
    # note that objects can be either Event or Guest. if the view
    # is called for Guest, we waht to display the guest states
    # (not the event states). But when user clicks on a date they
    # want to show the event even when we are calling from Guest.
    if ar is None or obj is None:
        return ''
    state_coll = {}
    cal = CalendarRenderer(cls.model)
    # sar = ar.spawn(parent=ar, master_instance=obj)
    # sar = ar.actor.request(parent=ar, master_instance=obj)
    sar = cls.request_from(ar, master_instance=obj)
    # sar = cls.request(parent=ar, master_instance=obj)
    # print("20181121 {}".format(ar.actor))
    # print("20181121 {}".format(cls.get_filter_kw(sar)))
    # print("20181121 {}".format(len(list(sar))))
    for obj in sar:
        if obj.state in state_coll:
            state_coll[obj.state] += 1
        else:
            state_coll[obj.state] = 1
        cal.collect(obj)

    elems = [cal.to_html(ar)]
    # choicelist = EntryStates
    choicelist = cls.workflow_state_field.choicelist
    ul = []
    for st in choicelist.get_list_items():
        ul.append(_("{} : {}").format(st, state_coll.get(st, 0)))
    toolbar = []
    toolbar += join_elems(ul, sep=', ')
    # elems = join_elems(ul, sep=E.br)
    if isinstance(obj, rt.models.cal.EventGenerator):
        ar1 = obj.do_update_events.request_from(sar)
        if ar1.get_permission():
            btn = ar1.ar2button(obj)
            toolbar.append(btn)

    ar2 = cls.insert_action.request_from(sar)
    if ar2.get_permission():
        btn = ar2.ar2button()
        toolbar.append(btn)

    if len(toolbar):
        toolbar = join_elems(toolbar, sep=' ')
        elems.append(E.p(*toolbar))

    return ar.html_text(E.div(*elems))
Exemplo n.º 9
0
Arquivo: ui.py Projeto: khchine5/xl
    def get_table_summary(self, master, ar):
        # master is None when called on a master table.
        if master is None:
            sar = ar
        else:
            sar = self.request_from(ar, master_instance=master)
            
        # every element of `items` is a tuple `(state,
        # list-of-objects)`.  in ar are ordered by state. we just group
        # them 
        items = []
        ci = None
            
        for obj in sar:  # self.get_request_queryset(ar):
            btn = obj.obj2href(ar)
            if ci is not None and ci[0] is obj.state:
                ci[1].append(btn)
            else:
                ci = (obj.state, [btn])
                items.append(ci)

        # now render them as a UL containing on LI per item
        items = [E.li(str(i[0]), ' : ', *join_elems(i[1], ", "))
                 for i in items]

        return E.ul(*items)
Exemplo n.º 10
0
        def suppliers(self, ar):
            """Displays a list of candidate suppliers.

            This means: all suppliers who have at least one of the
            skills required by this object.

            """
            if ar is None:
                return ''

            if not isinstance(self, dd.plugins.skills.demander_model):
                return ''
            
            Offer = rt.models.skills.Competence
            Demand = rt.models.skills.Demand
            skills = set()
            for dem in Demand.objects.filter(demander=self):
                skills.add(dem.skill)
                # skills |= set(dem.skill.get_parental_line())

            elems = []
            for spl in Offer.objects.filter(faculty__in=skills):
                if spl.end_user is not None:
                    elems.append(spl.end_user.obj2href(ar))
            elems = join_elems(elems, ', ')
            return E.p(*elems)
Exemplo n.º 11
0
    def get_table_summary(self, obj, ar):
        sar = self.request_from(ar, master_instance=obj)
        items = [o.detail_type.as_html(o, sar) for o in sar if not o.end_date]

        html = []
        if len(items) == 0:
            html += _("No contact details")
        else:
            html += join_elems(items, sep=', ')

        ins = self.insert_action.request_from(sar)
        if ins.get_permission():
            # kw = dict(label=u"⊕") # 2295 circled plus
            # kw.update(icon_name=None)
            # # kw.update(
            # #     style="text-decoration:none; font-size:120%;")
            # btn = ins.ar2button(**kw)
            btn = ins.ar2button()

            # if len(items) > 0:
            #     html.append(E.br())
            html.append(' ')
            html.append(btn)

        if True:
            html.append(' ')
            html.append(sar.as_button(icon_name="wrench"))  # GEAR
            # html.append(sar.as_button(u"⚙"))  # GEAR
            # html.append(sar.as_button(
            #     u"⚙", style="text-decoration:none; font-size:140%;"))  # GEAR
        else:
            html.append(E.br())
            html.append(sar.as_button(_("Manage contact details")))

        return E.p(*html)
Exemplo n.º 12
0
    def get_slave_summary(self, obj, ar):
        """Displays a summary of all responses for a given partner using a
        bullet list grouped by poll.

        """
        if obj is None:
            return

        visible_polls = Poll.objects.filter(state__in=(PollStates.published, PollStates.closed)).order_by("ref")

        qs = Response.objects.filter(partner=obj).order_by("date")
        polls_responses = {}
        for resp in qs:
            polls_responses.setdefault(resp.poll.pk, []).append(resp)

        items = []
        for poll in visible_polls:
            iar = self.insert_action.request_from(ar, obj, known_values=dict(poll=poll))
            elems = [unicode(poll), " : "]
            responses = polls_responses.get(poll.pk, [])
            elems += join_elems([ar.obj2html(r, dd.fds(r.date)) for r in responses], sep=", ")
            if poll.state == PollStates.published:
                elems += [" ", iar.ar2button()]
                # elems += [' ', iar.insert_button()]
            items.append(E.li(*elems))
        return E.div(E.ul(*items))
Exemplo n.º 13
0
Arquivo: ui.py Projeto: einarfelix/xl
            def func(fld, week, ar):
                pv = ar.param_values
                if pv is None:
                    return
                qs = Event.objects.all()
                qs = Event.calendar_param_filter(qs, pv)
                offset = int(ar.rqdata.get('mk', 0)
                             or 0) if ar.rqdata else ar.master_instance.pk
                today = dd.today()
                current_date = dd.today(offset)
                target_day = week[int(pc.value) - 1]
                qs = qs.filter(start_date=target_day)
                qs = qs.order_by('start_time')
                chunks = [
                    E.p(e.obj2href(ar, e.colored_calendar_fmt(pv))) for e in qs
                ]

                pk = date2pk(target_day)
                daily, weekly, monthly = make_link_funcs(ar)
                daily_link = daily(Day(pk), str(target_day.day))
                if target_day == today:
                    daily_link = E.b(daily_link)

                header_items = [daily_link]
                header_items = gen_insert_button(cls, header_items, Event, ar,
                                                 target_day)

                header = E.div(*header_items, align="center", CLASS="header")
                return E.table(
                    E.tr(E.td(*[header, E.div(*join_elems(chunks))])),
                    CLASS="fixed-table cal-month-cell {} {} {}".format(
                        "current-month" if current_date.month
                        == target_day.month else "other-month",
                        "current-day" if target_day == today else "",
                        "cal-in-past" if target_day < today else ""))
Exemplo n.º 14
0
    def tables(self, obj, ar):
        # tables = obj._lino_slaves.values()
        def fmt(tbl):
            url = tbl.__module__ + '.' + tbl.__name__
            return E.a(tbl.__name__, href=url)

        return join_elems([fmt(tbl) for tbl in obj._lino_tables])
Exemplo n.º 15
0
Arquivo: html.py Projeto: DarioGT/lino
def lines2p(lines, min_height=0, **attrs):
    """Convert the given list of text lines `lines` into a paragraph
(``<p>``) with one ``<br>`` between each line. If optional
`min_height` is given, add empty lines if necessary.

    Examples:

    >>> print(E.tostring(lines2p(['first', 'second'])))
    <p>first<br />second</p>

    >>> print(E.tostring(lines2p(['first', 'second'], min_height=5)))
    <p>first<br />second<br /><br /><br /></p>

    If `min_height` is specified, and `lines` contains more items,
    then we don't truncate:

    >>> print(E.tostring(lines2p(['a', 'b', 'c', 'd', 'e'], min_height=4)))
    <p>a<br />b<br />c<br />d<br />e</p>

    This also works:

    >>> print(E.tostring(lines2p([], min_height=5)))
    <p><br /><br /><br /><br /></p>

    """
    while len(lines) < min_height:
        lines.append('')
    lines = join_elems(lines, E.br)
    return E.p(*lines, **attrs)
Exemplo n.º 16
0
    def get_slave_summary(self, obj, ar):
        """Displays a summary of all responses for a given partner using a
        bullet list grouped by poll.

        """
        if obj is None:
            return

        visible_polls = Poll.objects.filter(
            state__in=(PollStates.published,
                       PollStates.closed)).order_by('ref')

        qs = Response.objects.filter(partner=obj).order_by('date')
        polls_responses = {}
        for resp in qs:
            polls_responses.setdefault(resp.poll.pk, []).append(resp)

        items = []
        for poll in visible_polls:
            iar = self.insert_action.request_from(ar,
                                                  obj,
                                                  known_values=dict(poll=poll))
            elems = [unicode(poll), ' : ']
            responses = polls_responses.get(poll.pk, [])
            elems += join_elems(
                [ar.obj2html(r, dd.fds(r.date)) for r in responses], sep=', ')
            if poll.state == PollStates.published:
                elems += [' ', iar.ar2button()]
                #elems += [' ', iar.insert_button()]
            items.append(E.li(*elems))
        return E.div(E.ul(*items))
Exemplo n.º 17
0
Arquivo: html.py Projeto: sandeez/lino
def lines2p(lines, min_height=0, **attrs):
    """Convert the given list of text lines `lines` into a paragraph
(``<p>``) with one ``<br>`` between each line. If optional
`min_height` is given, add empty lines if necessary.

    Examples:

    >>> print(E.tostring(lines2p(['first', 'second'])))
    <p>first<br />second</p>

    >>> print(E.tostring(lines2p(['first', 'second'], min_height=5)))
    <p>first<br />second<br /><br /><br /></p>

    If `min_height` is specified, and `lines` contains more items,
    then we don't truncate:

    >>> print(E.tostring(lines2p(['a', 'b', 'c', 'd', 'e'], min_height=4)))
    <p>a<br />b<br />c<br />d<br />e</p>

    This also works:

    >>> print(E.tostring(lines2p([], min_height=5)))
    <p><br /><br /><br /><br /></p>

    """
    while len(lines) < min_height:
        lines.append('')
    lines = join_elems(lines, E.br)
    return E.p(*lines, **attrs)
Exemplo n.º 18
0
        def suppliers(self, ar):
            """Displays a list of candidate suppliers.

            This means: all suppliers who have at least one of the
            skills required by this object.

            """
            if ar is None:
                return ''

            if not isinstance(self, dd.plugins.skills.demander_model):
                return ''

            Offer = rt.models.skills.Competence
            Demand = rt.models.skills.Demand
            skills = set()
            for dem in Demand.objects.filter(demander=self):
                skills.add(dem.skill)
                # skills |= set(dem.skill.get_parental_line())

            elems = []
            for spl in Offer.objects.filter(faculty__in=skills):
                if spl.end_user is not None:
                    elems.append(spl.end_user.obj2href(ar))
            elems = join_elems(elems, ', ')
            return E.p(*elems)
Exemplo n.º 19
0
    def get_table_summary(self, obj, ar):
        if obj is None:
            return

        visible_polls = Poll.objects.filter(state__in=(
            PollStates.active, PollStates.closed)).order_by('ref')

        qs = Response.objects.filter(partner=obj).order_by('date')
        polls_responses = {}
        for resp in qs:
            polls_responses.setdefault(resp.poll.pk, []).append(resp)

        items = []
        for poll in visible_polls:
            iar = self.insert_action.request_from(
                ar, obj, known_values=dict(poll=poll))
            elems = [str(poll), ' : ']
            responses = polls_responses.get(poll.pk, [])
            elems += join_elems(
                [ar.obj2html(r, dd.fds(r.date))
                 for r in responses], sep=', ')
            if poll.state == PollStates.active:
                elems += [' ', iar.ar2button()]
                #elems += [' ', iar.insert_button()]
            items.append(E.li(*elems))
        return E.div(E.ul(*items))
Exemplo n.º 20
0
Arquivo: ui.py Projeto: forexblog/xl
        def func(fld, obj, ar):
            # obj is the first day of the week to show
            # pv = ar.param_values
            today = dd.today()
            # if pv is None:
            #     return
            qs = cls.get_calendar_entries(ar, None)
            # qs = Event.objects.all()
            # qs = Event.calendar_param_filter(qs, pv)
            mi = ar.master_instance
            if mi is None:
                return
            target_day = cls.get_row_by_pk(ar, obj.pk + int(wd.value) - 1)
            current_month = mi.date.month
            nav = mi.planner

            # offset = ar.master_instance.pk
            # offset = int(ar.rqdata.get('mk', 0) or 0) if ar.rqdata else ar.master_instance.pk
            # current_date = dd.today(offset)
            # pk = offset + int(wd.value) - 1
            # target_day = cls.get_row_by_pk(ar, pk)
            # if target_day is None:
            #     return
            # target_day = week[int(wd.value)-1]
            qs = qs.filter(start_date=target_day.date)
            qs = qs.order_by('start_time')
            chunks = [
                E.p(e.obj2href(ar, cls.get_calview_div(e, ar))) for e in qs
            ]

            # pk = date2pk(target_day)

            # nav.daily_view
            # sar = ar.spawn_request(actor=actor, param_values=ar.param_values)
            # rnd = settings.SITE.kernel.default_renderer
            # def func(day, text):
            #     # day.navigation_mode = actor.navigation_mode
            #     return rnd.ar2button(sar, day, text, style="", icon_name=None, title=str(day))
            #

            daily = nav.daily_button_func(ar)
            daily_link = daily(target_day, str(target_day.date.day))
            if target_day.date == today:
                daily_link = E.b(daily_link)

            # header_items = [daily_link]
            # header_items = Event.gen_insert_button(cls, header_items, ar, target_day)
            header_items = [daily_link]
            btn = ar.gen_insert_button(Events, start_date=target_day.date)
            if btn:
                header_items.append(btn)

            header = E.div(*header_items, align="center", CLASS="header")
            return E.table(
                E.tr(E.td(*[header, E.div(*join_elems(chunks))])),
                CLASS="fixed-table cal-month-cell {} {} {}".format(
                    "current-month" if current_month == target_day.date.month
                    else "other-month",
                    "current-day" if target_day.date == today else "",
                    "cal-in-past" if target_day.date < today else ""))
Exemplo n.º 21
0
    def get_table_summary(self, obj, ar):
        if obj is None:
            return

        visible_polls = Poll.objects.filter(
            state__in=(PollStates.active, PollStates.closed)).order_by('ref')

        qs = Response.objects.filter(partner=obj).order_by('date')
        polls_responses = {}
        for resp in qs:
            polls_responses.setdefault(resp.poll.pk, []).append(resp)

        items = []
        for poll in visible_polls:
            iar = self.insert_action.request_from(ar,
                                                  obj,
                                                  known_values=dict(poll=poll))
            elems = [str(poll), ' : ']
            responses = polls_responses.get(poll.pk, [])
            elems += join_elems(
                [ar.obj2html(r, dd.fds(r.date)) for r in responses], sep=', ')
            if poll.state == PollStates.active:
                elems += [' ', iar.ar2button()]
                #elems += [' ', iar.insert_button()]
            items.append(E.li(*elems))
        return E.div(E.ul(*items))
Exemplo n.º 22
0
Arquivo: ui.py Projeto: forexblog/xl
 def func(fld, obj, ar):
     # obj is a DailyPlannerRow instance
     mi = ar.master_instance
     if mi is None:  # e.g. when using DailySlave from dashboard.
         mi = cls.calendar_view.get_row_by_pk(ar, 0)
     qs = cls.get_calendar_entries(ar, obj)
     qs = qs.filter(event_type__planner_column=pc)
     qs = qs.filter(start_date=mi.date)
     # pv = ar.param_values
     # qs = Event.calendar_param_filter(qs, pv)
     # current_day = pv.get('date', dd.today())
     # if current_day:
     #     qs = qs.filter(start_date=current_day)
     # if obj is cls.model.HEADER_ROW:
     #     qs = qs.filter(start_time__isnull=True)
     # else:
     #     get_plannable_entries
     #     if obj.start_time:
     #         qs = qs.filter(start_time__gte=obj.start_time,
     #                        start_time__isnull=False)
     #     if obj.end_time:
     #         qs = qs.filter(start_time__lt=obj.end_time,
     #                        start_time__isnull=False)
     qs = qs.order_by('start_time')
     chunks = [e.obj2href(ar, cls.get_calview_div(e, ar)) for e in qs]
     return E.p(*join_elems(chunks))
Exemplo n.º 23
0
 def partners(self, ar):
     if ar is None:
         return ''
     elems = []
     qs = rt.modules.sepa.Account.objects.filter(iban=self.iban)
     for obj in qs:
         elems.append(ar.obj2html(obj.partner))
     return E.p(*join_elems(elems, ', '))
Exemplo n.º 24
0
 def get_overview_elems(self, ar):
     elems = self.get_name_elems(ar)
     elems += join_elems(list(self.address_location_lines()), sep=E.br)
     elems = [
         E.div(*elems,
               style="font-size:18px;font-weigth:bold;"
               "vertical-align:bottom;text-align:middle")]
     return elems
Exemplo n.º 25
0
 def partners(self, ar):
     if ar is None:
         return ''
     elems = []
     qs = rt.models.sepa.Account.objects.filter(iban=self.iban)
     for obj in qs:
         elems.append(ar.obj2html(obj.partner))
     return E.p(*join_elems(elems, ', '))
Exemplo n.º 26
0
 def pupil_info(cls, self, ar):
     elems = [ar.obj2html(self.pupil,
                          self.pupil.get_full_name(nominative=True))]
     elems += [', ']
     elems += join_elems(
         list(self.pupil.address_location_lines()),
         sep=', ')
     return E.div(*elems)
Exemplo n.º 27
0
def welcome_messages(ar):
    """Yield messages for the welcome page."""

    Notification = rt.modules.notifier.Notification
    qs = Notification.objects.filter(user=ar.get_user(), seen__isnull=True)
    if qs.count() > 0:
        chunks = [str(_("You have %d unseen notifications: ")) % qs.count()]
        chunks += join_elems([ar.obj2html(obj, str(obj.owner)) for obj in qs])
        yield E.span(*chunks)
Exemplo n.º 28
0
 def print_actions(self, ar):
     if ar is None:
         return ''
     elems = []
     elems.append(ar.instance_action_button(
         self.print_presence_sheet))
     elems.append(ar.instance_action_button(
         self.print_presence_sheet_html))
     return E.p(*join_elems(elems, sep=", "))
Exemplo n.º 29
0
        def f(obj, ar):
            if obj is None or ar is None:
                return E.div()
            try:
                utype = UploadType.objects.get(shortcut=i)
            except UploadType.DoesNotExist:
                return E.div()
            items = []
            target = sender.modules.resolve(i.target)
            sar = ar.spawn_request(actor=target,
                                   master_instance=obj,
                                   known_values=dict(type=utype))
            # param_values=dict(pupload_type=et))
            n = sar.get_total_count()
            if n == 0:
                iar = target.insert_action.request_from(sar,
                                                        master_instance=obj)
                btn = iar.ar2button(
                    None,
                    _("Upload"),
                    icon_name="page_add",
                    title=_("Upload a file from your PC to the server."))
                items.append(btn)
            elif n == 1:
                after_show = ar.get_status()
                obj = sar.data_iterator[0]
                items.append(
                    sar.renderer.href_button(dd.build_media_url(obj.file.name),
                                             _("show"),
                                             target='_blank',
                                             icon_name='page_go',
                                             style="vertical-align:-30%;",
                                             title=_(
                                                 "Open the uploaded file in a "
                                                 "new browser window")))
                after_show.update(record_id=obj.pk)
                items.append(
                    sar.window_action_button(
                        sar.ah.actor.detail_action,
                        after_show,
                        _("Edit"),
                        icon_name='application_form',
                        title=_("Edit metadata of the uploaded file.")))
            else:
                obj = sar.sliced_data_iterator[0]
                items.append(
                    ar.obj2html(obj, pgettext("uploaded file", "Last")))

                btn = sar.renderer.action_button(obj,
                                                 sar,
                                                 sar.bound_action,
                                                 _("All {0} files").format(n),
                                                 icon_name=None)
                items.append(btn)

            return E.div(*join_elems(items, ', '))
Exemplo n.º 30
0
 def description(cls, self, ar):
     if ar is None:
         return ''
     elems = []
     voucher = self.voucher.get_mti_leaf()
     if voucher is not None:
         elems.extend(voucher.get_movement_description(self, ar))
     if self.project:
         elems.append(ar.obj2html(self.project))
     return E.p(*join_elems(elems, " / "))
Exemplo n.º 31
0
 def get_table_summary(self, obj, ar):
     chunks = []
     for other in ar.spawn(self, master_instance=obj):
         chunks.append(ar.obj2html(other))
     if len(chunks):
         s = getattr(obj, obj.dupable_words_field)
         words = ', '.join(obj.get_dupable_words(s))
         chunks.append(_("Phonetic words: {0}").format(words))
         return E.p(*join_elems(chunks))
     return ''
Exemplo n.º 32
0
 def get_slave_summary(self, obj, ar):
     chunks = []
     for other in ar.spawn(self, master_instance=obj):
         chunks.append(ar.obj2html(other))
     if len(chunks):
         s = getattr(obj, obj.dupable_words_field)
         words = ', '.join(obj.get_dupable_words(s))
         chunks.append(_("Phonetic words: {0}").format(words))
         return E.p(*join_elems(chunks))
     return ''
Exemplo n.º 33
0
 def description(cls, self, ar):
     # raise Exception("20191003")
     if ar is None:
         return ''
     elems = []
     elems.append(ar.obj2html(self.account))
     voucher = self.voucher.get_mti_leaf()
     if voucher is not None:
         elems.extend(voucher.get_movement_description(self, ar))
     return E.p(*join_elems(elems, " / "))
Exemplo n.º 34
0
 def answer_buttons(self,obj,ar):
     l = []
     if obj.question.get_multiple_choices():
         l.append("MC not yet implemented")
     else:
         kw = dict(title=_("Select this value"))
         for c in obj.question.get_choiceset().choices.all():
             l.append(unicode(c))
             #~ l.append(ar.put_button(obj.question,unicode(c),dict(choice=c),**kw))
             #~ l.append(self.select_choice.as_button_elem(ar.request,unicode(c)))
     return E.p(*join_elems(l))
Exemplo n.º 35
0
    def get_slave_summary(self, obj, ar):
        """Displays the uploads related to this controller as a list grouped
by uploads type.

Note that this also works on
:class:`lino_welfare.modlib.uploads.models.UploadsByClient` and their
subclasses for the different `_upload_area`.

        """
        UploadType = rt.modules.uploads.UploadType
        # Upload = rt.modules.uploads.Upload
        elems = []
        types = []

        for ut in UploadType.objects.filter(
                upload_area=self._upload_area):
            sar = ar.spawn(
                self, master_instance=obj,
                known_values=dict(type_id=ut.id))
            # logger.info("20140430 %s", sar.data_iterator.query)
            files = []
            for m in sar:
                text = self.format_row_in_slave_summary(ar, m)
                if text is None:
                    continue
                edit = ar.obj2html(
                    m,  text,  # _("Edit"),
                    # icon_name='application_form',
                    title=_("Edit metadata of the uploaded file."))
                if m.file.name:
                    show = ar.renderer.href_button(
                        settings.SITE.build_media_url(m.file.name),
                        _(" [show]"),  # fmt(m),
                        target='_blank',
                        icon_name='../xsite/link',
                        # icon_name='page_go',
                        # style="vertical-align:-30%;",
                        title=_("Open the uploaded file in a new browser window"))
                    # logger.info("20140430 %s", E.tostring(e))
                    files.append(E.span(edit, ' ', show))
                else:
                    files.append(edit)
            if ut.wanted and (
                    ut.max_number < 0 or len(files) < ut.max_number):
                files.append(sar.insert_button())
            if len(files) > 0:
                e = E.p(unicode(ut), ': ', *join_elems(files, ', '))
                types.append(e)
        # logger.info("20140430 %s", [E.tostring(e) for e in types])
        if len(types) == 0:
            elems.append(E.ul(E.li(ar.no_data_text)))
        else:
            elems.append(E.ul(*[E.li(e) for e in types]))
        return E.div(*elems)
Exemplo n.º 36
0
 def get_overview_elems(self, ar):
     elems = super(Client, self).get_overview_elems(ar)
     # elems.append(E.br())
     elems.append(ar.get_data_value(self, 'eid_info'))
     notes = []
     for obj in rt.models.cal.Task.objects.filter(
             project=self, state=TaskStates.important):
         notes.append(E.b(ar.obj2html(obj, obj.summary)))
     if len(notes):
         notes = join_elems(notes, " / ")
         elems.append(E.p(*notes, **{'class': "lino-info-yellow"}))
     return elems
Exemplo n.º 37
0
def welcome_messages(ar):
    """Yield messages for the welcome page."""

    Notification = rt.modules.notifier.Notification
    qs = Notification.objects.filter(user=ar.get_user(), seen__isnull=True)
    if qs.count() > 0:
        chunks = [
            unicode(_("You have %d unseen notifications: ")) % qs.count()
        ]
        chunks += join_elems(
            [ar.obj2html(obj, unicode(obj.owner)) for obj in qs])
        yield E.span(*chunks)
Exemplo n.º 38
0
Arquivo: ui.py Projeto: khchine5/xl
    def get_table_summary(self, obj, ar):
        if ar is None:
            return ''
        sar = self.request_from(ar, master_instance=obj)

        state_coll = {}
        cal = CalendarRenderer()
        for evt in sar:
            # if len(elems) > 0:
            #     elems.append(', ')
            if evt.state in state_coll:
                state_coll[evt.state] += 1
            else:
                state_coll[evt.state] = 1

            cal.collect(evt.start_date, evt)

        elems = [cal.to_html(ar)]

        ul = []
        for st in EntryStates.get_list_items():
            ul.append(_("{} : {}").format(st, state_coll.get(st, 0)))
        toolbar = []
        toolbar += join_elems(ul, sep=', ')
        # elems = join_elems(ul, sep=E.br)
        ar1 = obj.do_update_events.request_from(sar)
        if ar1.get_permission():
            btn = ar1.ar2button(obj)
            toolbar.append(btn)

        ar2 = self.insert_action.request_from(sar)
        if ar2.get_permission():
            btn = ar2.ar2button()
            toolbar.append(btn)

        if len(toolbar):
            toolbar = join_elems(toolbar, sep=' ')
            elems.append(E.p(*toolbar))

        return ar.html_text(E.div(*elems))
Exemplo n.º 39
0
 def info(self, row, ar):
     elems = []
     if row.project:
         elems.append(ar.obj2html(row.project))
     if row.partner:
         elems.append(ar.obj2html(row.partner))
         # elems.append(row.partner.address)
     if row.bank_account:
         elems.append(ar.obj2html(row.bank_account))
     if row.account:
         elems.append(ar.obj2html(row.account))
     # return E.span(*join_elems(elems, ' / '))
     return E.span(*join_elems(elems, E.br))
Exemplo n.º 40
0
Arquivo: ui.py Projeto: khchine5/xl
 def info(self, row, ar):
     elems = []
     if row.project:
         elems.append(ar.obj2html(row.project))
     if row.partner:
         elems.append(ar.obj2html(row.partner))
         # elems.append(row.partner.address)
     if row.bank_account:
         elems.append(ar.obj2html(row.bank_account))
     if row.account:
         elems.append(ar.obj2html(row.account))
     # return E.span(*join_elems(elems, ' / '))
     return E.span(*join_elems(elems, E.br))
Exemplo n.º 41
0
        def f(obj, ar):
            if obj is None or ar is None:
                return E.div()
            try:
                utype = UploadType.objects.get(shortcut=i)
            except UploadType.DoesNotExist:
                return E.div()
            items = []
            target = sender.modules.resolve(i.target)
            sar = ar.spawn_request(
                actor=target,
                master_instance=obj,
                known_values=dict(type=utype))
                # param_values=dict(pupload_type=et))
            n = sar.get_total_count()
            if n == 0:
                iar = target.insert_action.request_from(
                    sar, master_instance=obj)
                btn = iar.ar2button(
                    None, _("Upload"), icon_name="page_add",
                    title=_("Upload a file from your PC to the server."))
                items.append(btn)
            elif n == 1:
                after_show = ar.get_status()
                obj = sar.data_iterator[0]
                items.append(sar.renderer.href_button(
                    dd.build_media_url(obj.file.name),
                    _("show"),
                    target='_blank',
                    icon_name='page_go',
                    style="vertical-align:-30%;",
                    title=_("Open the uploaded file in a "
                            "new browser window")))
                after_show.update(record_id=obj.pk)
                items.append(sar.window_action_button(
                    sar.ah.actor.detail_action,
                    after_show,
                    _("Edit"), icon_name='application_form',
                    title=_("Edit metadata of the uploaded file.")))
            else:
                obj = sar.sliced_data_iterator[0]
                items.append(ar.obj2html(
                    obj, pgettext("uploaded file", "Last")))

                btn = sar.renderer.action_button(
                    obj, sar, sar.bound_action,
                    _("All {0} files").format(n),
                    icon_name=None)
                items.append(btn)

            return E.div(*join_elems(items, ', '))
Exemplo n.º 42
0
Arquivo: ui.py Projeto: khchine5/cosi
 def description(cls, self, ar):
     if ar is None:
         return ''
     elems = []
     elems.append(ar.obj2html(self.account))
     if self.voucher.narration:
         elems.append(self.voucher.narration)
     voucher = self.voucher.get_mti_leaf()
     p = voucher.get_partner()
     if p is not None and p != ar.master_instance:
         elems.append(ar.obj2html(p))
     if self.project:
         elems.append(ar.obj2html(self.project))
     return E.p(*join_elems(elems, " / "))
Exemplo n.º 43
0
Arquivo: ui.py Projeto: khchine5/cosi
 def description(cls, self, ar):
     if ar is None:
         return ''
     elems = []
     elems.append(ar.obj2html(self.account))
     voucher = self.voucher.get_mti_leaf()
     if voucher.narration:
         elems.append(voucher.narration)
     p = voucher.get_partner()
     if p is not None:
         elems.append(ar.obj2html(p))
     if self.partner and self.partner != p:
         elems.append(ar.obj2html(self.partner))
     return E.p(*join_elems(elems, " / "))
Exemplo n.º 44
0
 def get_overview_elems(self, ar):
     if ar is None:
         return []
     elems = super(Client, self).get_overview_elems(ar)
     # elems.append(E.br())
     elems.append(ar.get_data_value(self, 'eid_info'))
     notes = []
     for note in rt.modules.notes.Note.objects.filter(
             project=self, important=True):
         notes.append(E.b(ar.obj2html(note, note.subject)))
     if len(notes):
         notes = join_elems(notes, " / ")
         elems += E.p(*notes, class_="lino-info-red")
     return elems
Exemplo n.º 45
0
Arquivo: ui.py Projeto: TonisPiip/cosi
 def description(cls, self, ar):
     if ar is None:
         return ''
     elems = []
     elems.append(ar.obj2html(self.account))
     voucher = self.voucher.get_mti_leaf()
     if voucher.narration:
         elems.append(voucher.narration)
     p = voucher.get_partner()
     if p is not None:
         elems.append(ar.obj2html(p))
     if self.partner and self.partner != p:
         elems.append(ar.obj2html(self.partner))
     return E.p(*join_elems(elems, " / "))
Exemplo n.º 46
0
Arquivo: ui.py Projeto: TonisPiip/cosi
 def description(cls, self, ar):
     if ar is None:
         return ''
     elems = []
     elems.append(ar.obj2html(self.account))
     if self.voucher.narration:
         elems.append(self.voucher.narration)
     voucher = self.voucher.get_mti_leaf()
     p = voucher.get_partner()
     if p is not None and p != ar.master_instance:
         elems.append(ar.obj2html(p))
     if self.project:
         elems.append(ar.obj2html(self.project))
     return E.p(*join_elems(elems, " / "))
Exemplo n.º 47
0
Arquivo: ui.py Projeto: einarfelix/xl
 def func(fld, obj, ar):
     # obj is a Plannable instance
     qs = Event.objects.all()
     qs = Event.calendar_param_filter(qs, ar.param_values)
     delta_days = int(ar.rqdata.get('mk', 0)
                      or 0) if ar.rqdata else ar.master_instance.pk
     # current_day = dd.today() + timedelta(days=delta_days)
     current_day = dd.today(delta_days)
     current_week_day = current_day + \
         timedelta(days=int(week_day.value) - current_day.weekday() - 1)
     qs = qs.filter(start_date=current_week_day)
     qs = qs.order_by('start_time')
     chunks = obj.get_weekly_chunks(ar, qs, current_week_day)
     return E.table(E.tr(E.td(E.div(*join_elems(chunks)))),
                    CLASS="fixed-table")
Exemplo n.º 48
0
 def get_welcome_messages(cls,ar):
     guests = []
     sar = ar.spawn(cls)
     for g in sar:
         guests.append(g)
     #~ print "20130909 MyBusyVisitors get_welcome_messages", guests
     if len(guests) > 0:
         #~ print 20130909, guests[0].get_default_table()
         chunks = [ unicode(_("You are busy with ")) ]
         def f(g):
             #~ return sar.obj2html(g,unicode(g.partner))
             return sar.row_action_button(g,cls.detail_action,unicode(g.partner),icon_name=None)
         chunks += join_elems([f(g) for g in guests],sep=unicode(_(" and ")))
         chunks.append('.')
         yield E.span(*chunks)
Exemplo n.º 49
0
        def needed_skills(self, ar):
            """Displays a list of needed skills.

            This means: all skill demands for this object.

            """
            if ar is None:
                return ''
            if not isinstance(self, dd.plugins.skills.demander_model):
                return ''
            Demand = rt.models.skills.Demand
            elems = []
            for dem in Demand.objects.filter(demander=self):
                elems.append(dem.skill.obj2href(ar))
            elems = join_elems(elems, ', ')
            return E.span(*elems)
Exemplo n.º 50
0
 def find_links(self, ar, child, parent):
     types = {}  # mapping LinkType -> list of parents
     for lnk in humanlinks.Link.objects.filter(child=child):
             # child=child, parent=p):
         tt = lnk.type.as_child(lnk.child)
         l = types.setdefault(tt, [])
         l.append(lnk.parent)
     elems = []
     for tt, parents in types.items():
         if len(elems):
             elems.append(', ')
         text = join_elems(
             [parent.format_family_member(ar, p) for p in parents],
             sep=_(" and "))
         elems += [tt, _(" of ")] + text
     return elems
Exemplo n.º 51
0
        def needed_skills(self, ar):
            """Displays a list of needed skills.

            This means: all skill demands for this object.

            """
            if ar is None:
                return ''
            if not isinstance(self, dd.plugins.skills.demander_model):
                return ''
            Demand = rt.models.skills.Demand
            elems = []
            for dem in Demand.objects.filter(demander=self):
                elems.append(dem.skill.obj2href(ar))
            elems = join_elems(elems, ', ')
            return E.span(*elems)
Exemplo n.º 52
0
def welcome_messages(ar):
    """Yield a message "Your stars are X, Y, ..." for the welcome page.

    This message mentions all starred objects of the requesting user
    and whose :attr:`nickname <Star.nickname>` is not empty.

    """
    Star = rt.models.stars.Star
    qs = Star.objects.filter(user=ar.get_user()).exclude(nickname='')
    if qs.count() > 0:
        chunks = [unicode(_("Your stars are "))]
        chunks += join_elems([
            ar.obj2html(obj.owner, obj.nickname or unicode(obj.owner))
            for obj in qs])
        chunks.append('.')
        yield E.span(*chunks)
Exemplo n.º 53
0
    def get_table_summary(self, obj, ar):
        """Customized :meth:`summary view
        <lino.core.actors.Actor.get_table_summary>` for this table.

        """
        sar = self.request_from(ar, master_instance=obj)

        html = []

        items = [
            ar.obj2html(o, str(o.end_user)) for o in sar]

        if len(items) > 0:
            html += join_elems(items, sep=', ')
            
        return E.p(*html)
Exemplo n.º 54
0
 def get_overview_elems(self, ar):
     elems = []
     buttons = self.get_mti_buttons(ar)
     # buttons = join_elems(buttons, ', ')
     elems.append(
         E.p(str(_("See as ")),
             *buttons,
             style="font-size:8px;text-align:right;padding:3pt;"))
     elems += self.get_name_elems(ar)
     elems.append(E.br())
     elems += join_elems(list(self.address_location_lines()), sep=E.br)
     elems = [
         E.div(*elems,
               style="font-size:18px;font-weigth:bold;"
               "vertical-align:bottom;text-align:middle")
     ]
     return elems
Exemplo n.º 55
0
Arquivo: ui.py Projeto: einarfelix/xl
    def get_table_summary(self, obj, ar):
        """The :meth:`summary view <lino.core.actors.Actor.get_table_summary>`
        for this table.

        """
        sar = self.request_from(ar, master_instance=obj)

        chunks = []
        items = [o.obj2href(ar) for o in sar]
        if len(items) > 0:
            chunks += join_elems(items, ", ")

        sar = self.insert_action.request_from(sar)
        if sar.get_permission():
            chunks.append(sar.ar2button())

        return E.p(*chunks)
Exemplo n.º 56
0
        def add(title, flt):
            links = []
            sar = self.request(master_instance=obj, filter=flt)
            # logger.info("20141009 %s", sar.data_iterator.query)
            n = sar.get_total_count()
            if n:
                for i, ex in enumerate(sar):
                    txt = self.format_excerpt(ex)
                    if ex.build_time is not None:
                        txt += " (%s)" % naturaltime(ex.build_time)
                    links.append(ar.obj2html(ex, txt))
                    if i >= self.MORE_LIMIT:
                        # links.append(ar.href_to_request(sar, _("more")))
                        links.append('...')
                        break

                items.append(E.li(title, " : ", *join_elems(links, sep=', ')))
Exemplo n.º 57
0
def welcome_messages(ar):
    """Yield a message "Your stars are X, Y, ..." for the welcome page.

    This message mentions all starred objects of the requesting user
    and whose :attr:`nickname <Star.nickname>` is not empty.

    """
    Star = rt.modules.stars.Star
    qs = Star.objects.filter(user=ar.get_user()).exclude(nickname='')
    if qs.count() > 0:
        chunks = [unicode(_("Your stars are "))]
        chunks += join_elems([
            ar.obj2html(obj.owner, obj.nickname or unicode(obj.owner))
            for obj in qs
        ])
        chunks.append('.')
        yield E.span(*chunks)
Exemplo n.º 58
0
 def description(cls, self, ar):
     # raise Exception("20191003")
     if ar is None:
         return ''
     elems = []
     elems.append(ar.obj2html(self.account))
     voucher = self.voucher.get_mti_leaf()
     if voucher is not None:
         elems.extend(voucher.get_movement_description(self, ar))
         # if voucher.narration:
         #     elems.append(voucher.narration)
         # p = voucher.get_partner()
         # if p is not None:
         #     elems.append(ar.obj2html(p))
         # if self.partner and self.partner != p:
         #     elems.append(ar.obj2html(self.partner))
     return E.p(*join_elems(elems, " / "))
Exemplo n.º 59
0
    def answer_buttons(self, obj, ar):
        # assert isinstance(obj, Answer)
        cs = obj.question.get_choiceset()
        if cs is None:
            return ''

        elems = []
        pv = dict(question=obj.question)

        # ia = obj.response.toggle_choice
        sar = obj.response.toggle_choice.request_from(
            ar, is_on_main_actor=False)
        # print(20170731, sar.is_on_main_actor)
        if False:  # since 20170129
            ba = Responses.actions.toggle_choice
            if ba is None:
                raise Exception("No toggle_choice on {0}?".format(ar.actor))
            sar = ba.request_from(ar)

            # print("20150203 answer_buttons({0})".format(sar))

            # if the response is registered, just display the choice, no
            # toggle buttons since answer cannot be toggled:
            # 20151211
            sar.selected_rows = [obj.response]
            
        if not sar.get_permission():
            return str(obj)

        AnswerChoice = rt.models.polls.AnswerChoice
        for c in cs.choices.all():
            pv.update(choice=c)
            text = str(c)
            qs = AnswerChoice.objects.filter(
                response=obj.response, **pv)
            if qs.count() == 1:
                text = [E.b('[', text, ']')]
            elif qs.count() == 0:
                pass
            else:
                raise Exception(
                    "Oops: %s returned %d rows." % (qs.query, qs.count()))
            sar.set_action_param_values(**pv)
            e = sar.ar2button(obj.response, text, style="text-decoration:none")
            elems.append(e)
        return ar.html_text(E.span(*join_elems(elems)))