4👍
I’d suggest looking at adding the djangocms-link plugin as a child plugin. It’s a very good plugin to link to internal CMS pages or external addresses. That way you could drop the button
field from your model, and instead render the child plugins in your template.
The docs on nested plugins would be a good read.
Your plugin definition would become something like this;
class ParentCMSPlugin(CMSPluginBase):
render_template = 'parent.html'
name = 'Parent'
model = ParentPlugin
allow_children = True
child_classes = ['LinkPlugin']
To render child plugins you’d then do this with your template;
{% load cms_tags %}
<section class="card card--primary-light">
<div class="card__inner">
<div class="card__content">
<div class="card__text">
<h2 class="card__title">
{{ instance.title }}
</h2>
<p class="card__description">
{{ instance.description }}
</p>
</div>
{% for plugin in instance.child_plugin_instances %}
{% render_plugin plugin %}
{% endfor %}
</div>
</div>
</section>
And that would use the default render template for the child plugin. If the default didn’t match the styling etc, you could handle the rendering in the template instead of using render_plugin
or subclass the LinkPlugin
to work how you want, or extend it’s attributes etc.
Some further consideration should do to dropping your description field in favour of also using the TextPlugin
as a child, because the CMS text plugin can nest plugins within itself and is something I’d always use over an HTMLField
.
Further still, if you’re developing applications hooked in to CMS, take a look at PlaceholderFields
which allow you to create placeholders in your own models to hold & use the CMS plugins that you can use in CMS pages. That gets really good for things like news apps or blog style content etc.