crbreadcrumb — Generalized breadcrumb rendering¶
Renderables¶
The cradmin.crbreadcrumb
module provides generalized renderables for breadcrumbs. There
renderables can be used to render breadcrumbs anywhere on a page using
the cradmin_render_renderable()
template tag.
Cascading breadcrumbs in cradmin instances, apps and views¶
Having renderables for breadcrumbs is good, but it does not help with the challenge of having to create the full breadcrumb path in each view, and having to refactor that everywhere if we move views around. To solve this problem, we have added support for breadcrumbs in:
django_cradmin.crinstance.BaseCrAdminInstance
django_cradmin.crapp.App
django_cradmin.viewhelpers.mixins.CommonCradminViewMixin
(mixin used by all our base views)
All of these classes have a get_breadcrumb_item_list_renderable()
-method. The
method on crinstance.BaseCrAdminInstance creates a breadcrumb item list renderable object
(a subclass of django_cradmin.crbreadcrumb.BreadcrumbItemList
). The method
on crapp.App just call request.cradmin_instance.get_breadcrumb_item_list_renderable()
to get the breadcrumb item list from the cradmin instance. And, in the same spirit, the
method on viewhelpers.mixins.CommonCradminViewMixin just call
request.cradmin_app.get_breadcrumb_item_list_renderable()
to get the breadcrumb item
list from the cradmin app. Docs for each of these methods here:
django_cradmin.crinstance.BaseCrAdminInstance.get_breadcrumb_item_list_renderable()
django_cradmin.crapp.App.get_breadcrumb_item_list_renderable()
django_cradmin.viewhelpers.mixins.CommonCradminViewMixin.get_breadcrumb_item_list_renderable()
As a convenience, crinstance.BaseCrAdminInstance, crapp.App and viewhelpers.mixins.CommonCradminViewMixin also define
a add_breadcrumb_list_items()
-method which can be used to just add breadcrumb items as long
as the cradmin instance/app actually provide a breadcrumb item list rendereable. You normally
want to override these methods, and they are documented here:
django_cradmin.crinstance.BaseCrAdminInstance.add_breadcrumb_list_items()
django_cradmin.crapp.App.add_breadcrumb_list_items()
django_cradmin.viewhelpers.mixins.CommonCradminViewMixin.add_breadcrumb_list_items()
Note
These methods are named add_breadcrumb_list_items(). This does not mean that you can only add items (it is just the use case in 95% of use cases). Since you have a BreadcrumbItemList, you can add, remove, insert, extend, etc, not just add.
Example¶
A typical and simple example:
class SiteEditView(viewhelpers.formview.UpdateRoleView):
def add_breadcrumb_list_items(self, breadcrumb_item_list):
breadcrumb_item_list.append(label='Edit', active=True)
class SiteOverviewView(viewhelpers.generic.WithinRoleTemplateView):
# No add_breadcrumb_list_items() method because this is the index view for
# the app, so the breadcrumb the app adds takes you to this view.
pass
class SiteDetailsApp(crapp.App):
appurls = [
crapp.Url(r'^$', SiteOverviewView.as_view(), name=crapp.INDEXVIEW_NAME),
crapp.Url(r'^edit$', SiteEditView.as_view(), name='edit'),
]
def add_breadcrumb_list_items(self, breadcrumb_item_list):
breadcrumb_item_list.append(
url=self.reverse_appindexurl(),
label='{} details'.format(
self.request.cradmin_instance.get_titletext_for_role(self.request.cradmin_role))
)
class SiteCradminInstance(crinstance.BaseCrAdminInstance):
rolefrontpage_appname = 'details'
apps = [
('details', SiteDetailsApp)
]
def add_breadcrumb_list_items(self, breadcrumb_item_list):
if self.get_rolequeryset().count() > 1:
# Add breadcrumb back to the roleselect view if we have more than one site
breadcrumb_item_list.append(
url=self.get_instance_frontpage_url(),
label='Sites')
Custom breadcrumb item list renderable:
class MyCustomBreadcrumbItemList(crbreadcrumb.WrappedBreadcrumbItemList):
# We just override the css class in this example, but you can do much more!
def get_bem_block(self):
return 'my-custom-breadcrumb-item-list'
class SiteCradminInstance(crinstance.BaseCrAdminInstance):
# Everything else is just like in SiteCradminInstance above, but
# we add this property
breadcrumb_item_list_renderable_class = MyCustomBreadcrumbItemList
Custom breadcrumb item list in just a single view:
# This works for crapp.App too if you want a custom breadcrumb style for all views in an app!
class SiteEditView(viewhelpers.formview.UpdateRoleView):
def add_breadcrumb_list_items(self, breadcrumb_item_list):
breadcrumb_item_list.append(label='Edit', active=True)
def get_breadcrumb_item_list_renderable(self):
# We get the breadcrumb item list from super() this will include everything from
# the cradmin instance and app, and the item we added in add_breadcrumb_list_items()
# above.
breadcrumb_item_list = super().get_breadcrumb_item_list_renderable()
if breadcrumb_item_list is None:
# Handle that breadcrumbs may have been disabled in the cradmin instance or app.
return None
# Then we create an instance of MyCustomBreadcrumbItemList with a copy
# of the items of the items from super().
return MyCustomBreadcrumbItemList.from_breadcrumb_item_list(breadcrumb_item_list)
Rendering breadcrumbs at a custom location¶
Lets say your design requires you to render the breadcrumb centered above the title in the page-cover on a certain page. You can achieve this fairly easily.
This can be solved in many different ways, but we will go with a fairly easy solution where we:
- Use
BreadcrumbItemList
instead ofWrappedBreadcrumbItemList
to get a plain<nav class="breadcrumb-item-list">
without any wrapper. - Set a custom location for the breadcrumb so it is not rendered at the default location.
- Render the breadcrumb in the
page-cover-content
block.
First, we override get_breadcrumb_item_list_renderable
on the view:
class SiteEditView(viewhelpers.formview.UpdateRoleView):
def add_breadcrumb_list_items(self, breadcrumb_item_list):
breadcrumb_item_list.append(label='Edit', active=True)
def get_breadcrumb_item_list_renderable(self):
# We have an example above that explains how just copying items works in detail.
breadcrumb_item_list = super().get_breadcrumb_item_list_renderable()
if breadcrumb_item_list is None:
return None
breadcrumb_item_list = crbreadcrumb.BreadcrumbItemList.from_breadcrumb_item_list(breadcrumb_item_list)
# We set a custom location to avoid rendering the breadcrumbs
# at the default location
breadcrumb_item_list.set_location('custom')
return breadcrumb_item_list
Next, we override the template:
{% extends "django_cradmin/viewhelpers/formview/within_role_update_view.django.html" %}
{% load cradmin_tags %}
{% block page-cover-content %}
{# Render breadcrumbs here instead #}
<div class="text-center paragraph">
{% cradmin_render_breadcrumb_item_list %}
</div>
{{ block.super }}
{% endblock page-cover-content %}
Note
You can change how the breadcrumbs are rendered for all views in your
site by overring the breadcrumb item list renderable
on your cradmin instances (typically with a common base class or mixin class),
and override the django_cradmin/standalone-base.django.html
template.
Disabling breadcrumbs¶
Disabling breadcrumbs can be done on cradmin instance, app or views. It is
the same for all of them, you just override the get_breadcrumb_item_list_renderable()
method and return None
:
# View
class SiteEditView(viewhelpers.formview.UpdateRoleView):
def get_breadcrumb_item_list_renderable(self):
return None
# App
class SiteDetailsApp(crapp.App):
def get_breadcrumb_item_list_renderable(self):
return None
# Cradmin instance
class SiteCradminInstance(crinstance.BaseCrAdminInstance):
def get_breadcrumb_item_list_renderable(self):
return None
crbreadcrumb module¶
Bases:
django_cradmin.renderable.AbstractBemRenderable
Breadcrumb item renderable.
Parameters: - label (str) – The text/label.
- url (str) – The link URL. If this is None or any other boolean false value, we render the item as a <span> instead of as a <a> element.
- active (bool) – If this is
True
, we add the--active
BEM variant to the element. - label_maxlength (int) – The max length of the label before it is shortened using the
truncatechars
django template filter. You typically do not set this directly, but instead overrideBreadcrumbItemList.get_default_item_label_maxlength()
to get uniformed max lengths for all your breadcrumbs. - active_label_maxlength (int) – The max length of the label if active=True before the label
is shortened using the
truncatechars
django template filter. You typically do not set this directly, but instead overrideBreadcrumbItemList.get_default_active_item_label_maxlength()
to get uniformed max lengths for all your breadcrumbs. - render_link_for_active (bool) – If this is
True
, we render as a link (<a>
) even ifactive
isTrue
. We do, of course, not render as a link if we do not have anurl
. - parent_bem_block – Provided automatically by
BreadcrumbItemList
.
Get the bem element string.
Get a list of BEM variants.
You do not include the block/element, just the part after
--
.
Should we render the element as a link (
<a>
)?
Get HTML element attributes as a dict.
Bases:
django_cradmin.renderable.AbstractBemRenderable
Breadcrumb separator renderable.
Get the bem element string.
Bases:
django_cradmin.renderable.AbstractBemRenderable
List of breadcrumb items.
We provide a lot of helper methods, but if you need more powerful features, such as removal of breadcrumb items, you can just manipulate the
breadcrumb_item_list
attribute directly. All the append*, insert*, etc. methods just add items to this list.list – A plain python list of
django_cradmin.renderable.AbstractRenderable
objects, normallyBreadcrumbItem
objects.
django_cradmin.crinstance.BaseCrAdminInstance – The cradmin instance sent in as an argument to
__init__()
.
Parameters: cradmin_instance (django_cradmin.crinstance.BaseCrAdminInstance) – A cradmin instance. Render location – Above page cover.
Render location – Below page cover.
Get a list of extra css classes.
The location to render the breadcrumb at by default.
Can be overridden on a per view, per app or per cradmin instance basis using
set_location()
.Only relevant if using the
django_cradmin.templatetags.cradmin_tags.cradmin_render_breadcrumb_item_list()
template tag with thelocation
argument. Defaults toLOCATION_BELOW_PAGE_COVER
.
Get the location to render the breadcrumb item list at.
Do not override this - override
get_default_location()
instead.
Set the location to render the breadcrumb item list at.
Can be used in the
get_breadcrumb_item_list_renderable()
method of cradmin instances, apps or views to override the location to render breadcrumbs at.Parameters: location (str) – Location.
Override this to use a custom BEM block for the breadcrumb.
Get a list of BEM variants.
You do not include the block/element, just the part after
--
.
Get the renderable class for breadcrumb item separators.
Defaults to
BreadcrumbSeparator
.
Make a breadcrumb item separator renderable.
Get the renderable class for breadcrumb items.
Defaults to
BreadcrumbItem
.
The default max length of the label of items.
If the label is longer than this, the label is truncated using the
truncatechars
django template filter.If you return None or another boolean false falue from this method, labels are not truncated.
Returns: The max length of item labels, or None
. Defaults to15
.Return type: int
The default max length of the label of active items.
If the label is longer than this, the label is truncated using the
truncatechars
django template filter.If you return None or another boolean false falue from this method, labels are not truncated.
Returns: The max length of item labels, or None
. Defaults to25
.Return type: int
Get kwargs for the
get_item_renderable_class()
.Make sure you call super to get the required kwargs if you override this method.
Parameters: **extra_kwargs – Extra kwargs. Returns: kwargs. Return type: dict
Make an item renderable.
Parameters: **kwargs – Kwargs for the item renderable class. This is forwarded to get_item_renderable_kwargs()
to enable default kwargs for all items in the breadcrumb item list.
Uses
make_item_renderable()
to create a renderable, and appends the created item to the breadcrumb list.
Uses
make_item_renderable()
to create a renderable, and prepends the created item to the breadcrumb list.
Uses
make_item_renderable()
to create a renderable, and inserts the created item in the breadcrumb list.
Insert a renderable object at a specific index in the breadcrumb list.
Parameters: - index (int) – The index to insert at.
- renderable_object – The renderable object (a subclass
of
django_cradmin.renderable.AbstractRenderable
)
Prepend a renderable object to the breadcrumb list.
Parameters: renderable_object – The renderable object (a subclass of django_cradmin.renderable.AbstractRenderable
)
Append a renderable object to the breadcrumb list.
Parameters: renderable_object – The renderable object (a subclass of django_cradmin.renderable.AbstractRenderable
)
Just like
append()
except that it takes an iterable of renderables instead of a single renderable.
Iterate through all the breadcrumb items and separators.
Separators is yielded automatically after each item except the last one. Separator renderables can be overridden with
make_separator_renderable()
.
Bases:
django_cradmin.renderable.AbstractBemRenderable
Wraps a
BreadcrumbItemList
in a box.Get the bem block string.
Get a list of BEM variants.
You do not include the block/element, just the part after
--
.
Bases:
django_cradmin.crbreadcrumb.BreadcrumbItemList
Renders and works just like
BreadcrumbItemList
except that it is wrapped within aBreadcrumbItemListWrapper
.You can subclass
BreadcrumbItemListWrapper
and replace the wrapper class by overridingget_wrapper_renderable_class()
.Parameters: cradmin_instance (django_cradmin.crinstance.BaseCrAdminInstance) – A cradmin instance. Get the renderable for the wrapper element(s).
Returns: BreadcrumbItemListWrapper
or a subclass.Return type: django_cradmin.crbreadcrumb.BreadcrumbItemListWrapper
Get kwargs for the class returned by
get_wrapper_renderable_class()
.Returns: Kwargs. Return type: dict
Render
get_template_names
with the context returned byget_context_data()
.- Paramteters:
- request (HttpRequest): If this is provided, we forward it to
get_context_data()
, and torender_to_string()
(which is used to render the template).