Skip to content

Instantly share code, notes, and snippets.

@jeromecoupe
Last active June 1, 2016 12:47
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jeromecoupe/8558974ab9178b11f9a176d90dbad9b3 to your computer and use it in GitHub Desktop.
Save jeromecoupe/8558974ab9178b11f9a176d90dbad9b3 to your computer and use it in GitHub Desktop.
Implement an event calendar with Matrix: all event occurrences are stored as matrix blocks / fields
{% extends "_layouts/default" %}
{% block content %}
{#
Events just have a Matrix fields with multiple dates.
The goal is to get all dates within a certain date range, ordered by date asc
All event details should be repeated when an event occurs at multiple dates
Events are presented in a calendar view and should only appear for a given day if they have
a corresponding occurence on that day.
- id of the Matrix fiel is 106 and its handle is 'timetable'
- The MatrixBlock handle is 'mxBlockDate'
- The Matrix date field handle is 'mxDate'
We should be able to eager load assets and relatd items for events if needed
The number of queries qhoul be kept as low as possible
#}
<h2>Lowblocks plugin</h2>
{% set startDate = date('2016-05-24') %}
{% set endDate = date('2016-05-29') %}
<p>FROM: {{ startDate|date('Y-m-d 00:00') }} TO {{ endDate|date('Y-m-d 23:59') }}</p>
{# get all Matrix blocks using LowBlocks plugin
https://github.com/low/lowblocks
------------------------------------------------------- #}
{% set mxblocks = craft.lowblocks.blocks.fieldId(106).find({
mxDate: [
'and',
'>=' ~ startDate|date('Y-m-d 00:00'),
'<=' ~ endDate|date('Y-m-d 23:59')
],
order: 'mxDate asc',
limit: null
}) %}
{# use the blocks to find their father entries
------------------------------------------------------- #}
{# get the IDs for all the father entries of the Matrix blocks #}
{% set entryIds = [] %}
{% for mxblock in mxblocks %}
{% set entryIds = entryIds|merge([mxblock.ownerId]) %}
{% endfor %}
{# make an array with all the entries using the list of IDS #}
{#
- events is now an array of the owners EntryModels, keyed by the IDs of the owner entries.
- This makes it easier to retrieve specific owner Entries later.
- we could eager load everything we need for events at this point
[
1: EntryModel,
2: EntryModel
]
#}
{% set events = craft.entries.id(entryIds).indexBy('id').find() %}
{# display events in a calendar view
------------------------------------------------------- #}
{% for mxblock in mxblocks %}
{# use the array keys (IDs) to retrieve each event #}
{% set event = events[mxblock.ownerId] %}
{# register the first event occurence as currentDate #}
{% if loop.first %}
{% set currentDate = mxblock.mxDate|date('d-m-Y') %}
<h2>{{ currentDate }}</h2>
{% endif %}
{#
if the eventDate (stored in Matrix Block) is different than the stored currentDate,
assign new currentDate and display title
#}
{% set eventDate = mxblock.mxDate|date('d-m-Y') %}
{% if currentDate != eventDate %}
{% set currentDate = eventDate %}
<h2>{{ currentDate }}</h2>
{% endif %}
{# display event detail #}
<p>{{ event.title }} - {{ mxblock.mxDate|date('d-m-Y G:i') }}</p>
{% endfor %}
{% endblock %}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment