Refreshing Widgets using query_arguments

You can build a Widget which gets refreshed without reloading the entire page.

The howtos.ajaxbootstrap example has Nav and a Div. The contents of the Div changes each time an item is selected on the Nav without reloading the entire page.

Only HTMLElements can refresh. To let an HTMLElement refresh, it needs arguments and needs to call enable_refresh() in its __init__ method.

In the example, RefreshedPanel is given arguments in an ExposedNames namespace called query_fields. Each argument is defined by assigning a callable for it to an attribute of the ExposedNames. The callable is called with an instance as argument and should return a Field describing that argument. The query_fields declared on RefreshedPanel is merged with that on query_fields at runtime:

    query_fields = ExposedNames()
    query_fields.selected = lambda i: IntegerField(required=False, default=1)

This makes the value of self.selected available in RefreshedPanel.__init__ to be used when generating the RefreshedPanel (self.selected is set from the URL or the default of the Field):

class RefreshedPanel(Div):
    def __init__(self, view, css_id):
        super().__init__(view, css_id=css_id)
        self.add_child(P(view, text='You selected link number %s' % self.selected))

A special “in-page” Bookmark refers to a Widget on the current UrlBoundView, but with different argument values.

Construct such a Bookmark for a given value of selected by calling for_widget() with suitable query_arguments. Before using the Bookmark, call on_view() to bind it to the current View.

    def get_bookmark(self, for_selected):
        return Bookmark.for_widget('Select %s' % for_selected, query_arguments={'selected': for_selected}).on_view(self.view)

Use such bound Bookmarks as usual:

class HomePanel(Div):
    def __init__(self, view):

        panel = RefreshedPanel(view, 'my_refreshedpanel')
        bookmarks = [panel.get_bookmark(1),

        self.add_child(H(view, 1, text='Refreshing widget'))


If a Widget declares query_fields, it must have a unique css_id.