Skip to content

Clusters: link lesson plans and slides from each sub-cluster - #905

Open
LukasWallrich wants to merge 8 commits into
mainfrom
clusters-lesson-plans
Open

LukasWallrich wants to merge 8 commits into
mainfrom
clusters-lesson-plans

Conversation

@LukasWallrich

@LukasWallrich LukasWallrich commented Oct 2, 2026 •

Copy link
Copy Markdown
Contributor

Adds the FORRT Open Science Curriculum lesson plans to the cluster pages.

What it shows

  • A "Teaching materials" strip in each sub-cluster that has a set, below the sub-cluster description and above the readings. It links the slides (PPTX, PDF), each lesson plan (DOCX, PDF) and extra materials, and names the creator, reviewers, licence (CC BY-NC-SA 4.0) and Zenodo DOI.
  • A green dot on the sub-cluster header, in the sidebar, and in the cluster header ("· ● N with lesson plans").
  • A "● Lesson plans" filter chip next to the existing filters. It shows only sub-clusters with sets, and it explains the dot.

Data

  • data/lesson_plans.json is keyed by cluster number and the sub-cluster anchor slug. The slug formula is now in one partial (clusters/sc_slug.html), shared by the section, the sidebar and the check.
  • The build fails if a key matches no sub-cluster, so renaming a sub-cluster cannot silently drop its plans.
  • The file lists 8 published Zenodo records (2.5, 2.6, 3.5, 5.2, 7.3, 7.4, 7.6, 9.1). Sets 2.1 and 9.19 stay as Zenodo drafts until placeholders on their slides are fixed.

Checks

  • hugo builds cleanly.
  • Every file link in the data file returns HTTP 200.
  • Checked visually on desktop and mobile widths.

🤖 Generated with Claude Code


Summary by cubic

Adds the FORRT Open Science Curriculum lesson plans and slides to cluster pages, linking each published Zenodo record from the sub-cluster it belongs to.

  • A "Teaching materials" strip below each sub-cluster description links slides (PPTX, PDF), lesson plans (DOCX, PDF), and extra materials, naming the creator, reviewers, the CC BY-NC-SA 4.0 licence, and the Zenodo DOI; it names the set when it sits under a differently named sub-cluster. Chips wrap on narrow screens.
  • Sub-clusters with sets show a green dot on their header, in the sidebar, and in the cluster stats ("· ● N with lesson plans").
  • An "Only sub-clusters with lesson plans" checkbox combines with the existing search and tag filters; sub-clusters and clusters without sets are hidden, with a message for clusters that have none. When on, sub-clusters with a set stay open even when no other filter matches their cards, and the empty-cluster message is announced to screen readers.
  • data/lesson_plans.json is keyed by cluster number and sub-cluster anchor slug; the build fails if a key matches no sub-cluster, so renaming a sub-cluster cannot silently drop its materials.
  • The slug formula lives in one shared partial (clusters/sc_slug.html) used by the section, sidebar, and data validation.
  • Covers 8 published Zenodo records (2.5, 2.6, 3.5, 5.2, 7.3, 7.4, 7.6, 9.1); sets 2.1 and 9.19 remain drafts until placeholders on their slides are fixed.

Written for commit 1fe8f73. Summary will update on new commits.

View guided diff Turn on auto-fix

LukasWallrich and others added 4 commits October 1, 2026 23:05
…luster

- data/lesson_plans.json (sample entries) holds sets keyed by cluster number
  and sub-cluster slug.
- Sub-clusters with a set get a teaching-materials strip at the top of the
  accordion body and a green dot on the header. Cluster stats show the
  count, and the sidebar shows the dot.
- A "Lesson plans" filter chip shows only sub-clusters and clusters that
  have sets. It combines with the existing search and tag filters.
- The build fails when a lesson_plans.json key matches no cluster or
  sub-cluster.
- The sub-cluster slug now comes from one shared partial (sc_slug.html).

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…, DOIs reserved)

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…tly named sub-cluster

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
…ished sets

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@LukasWallrich
LukasWallrich requested a review from a team as a code owner October 2, 2026 08:39
@github-actions

github-actions Bot commented Oct 2, 2026

Copy link
Copy Markdown
Contributor

👍 All image files/references (if any) are in webp format, in line with our policy.

@github-actions

github-actions Bot commented Oct 2, 2026

Copy link
Copy Markdown
Contributor

✅ Spell Check Passed

No spelling issues found when checking 8 changed file(s)! 🎉

@cubic-dev-ai cubic-dev-ai Bot left a comment •

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

4 issues found across 9 files

Reply with feedback, questions, or to request a fix.

Re-trigger cubic

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. When an issue isn't valid or won't be fixed in this PR, reply in its thread with the reason and then resolve the thread. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="layouts/clusters/cluster.html">

<violation number="1" location="layouts/clusters/cluster.html:76">
P3: When the lesson-plan filter is toggled on for a cluster without lesson plans, the entire cluster section is hidden by CSS and only this small paragraph replaces it, with nothing announced to assistive tech. Give the message a `role="status"` (matching the `aria-live="polite"` already used on the search results panel in clusters_controls.html) so the disappearing content is at least announced.</violation>
</file>

<file name="layouts/partials/clusters/cluster_section.html">

<violation number="1" location="layouts/partials/clusters/cluster_section.html:87">
P2: Long material labels render as non-wrapping chips, causing horizontal overflow on narrow screens. Allow chip content to wrap; cluster 5’s 75-character label already exercises this path.</violation>
</file>

<file name="assets/scss/custom.scss">

<violation number="1" location="assets/scss/custom.scss:674">
P3: Replace the hand-written rgba() greens with the `$lp-green` variable so the palette stays in one place (`rgba($lp-green, 0.35)` etc.); dart-sass accepts a hex color as the first rgba() argument, matching how `background: $lp-green` is already used in this block.</violation>
</file>

<file name="static/js/featured-resources.js">

<violation number="1" location="static/js/featured-resources.js:742">
P2: Turning on the lesson-plan filter only reveals strips for sub-clusters whose cards matched; `data-lp` sections with no matching cards (no publications, or only narrow-specificity cards, or no `.fr-cards-list` at all) are still collapsed by the `matchCount === 0` branch, so their teaching-materials strips stay hidden. Make Pass 2 treat `lpOnly` sections with `data-lp` as already matching (expand them and clear `acc-disabled`) instead of relying on `isFiltered` to expand them.</violation>
</file>

Comment thread layouts/partials/clusters/cluster_section.html
Comment thread static/js/featured-resources.js
Comment thread layouts/clusters/cluster.html Outdated
Comment thread assets/scss/custom.scss Outdated
@LukasWallrich

LukasWallrich commented Oct 2, 2026 •

Copy link
Copy Markdown
Contributor Author

✅ Staging Deployment Status

This PR has been successfully deployed to staging as part of an aggregated deployment.

Deployed at: 2026-10-21 13:29:42 UTC
Staging URL: https://staging.forrt.org

The staging site shows the combined state of all compatible open PRs.

LukasWallrich and others added 2 commits October 2, 2026 10:50
…er bar

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
… on the button row

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>

@cubic-dev-ai cubic-dev-ai Bot left a comment •

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All reported issues were addressed across 3 files (changes from recent commits).

Tip: Review your code locally with the cubic CLI to iterate faster.

Re-trigger cubic

Comment thread assets/scss/custom.scss Outdated
Comment thread assets/scss/custom.scss Outdated
- Chips wrap on narrow screens instead of overflowing
- With the lesson-plan filter on, sub-clusters with a set stay open even when no card matches other filters
- Empty-cluster message announced to screen readers (role=status)
- Greens use $lp-green; drop the filter-label colour rule that never applied; describe the checkbox in its comment

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

2 issues found across 3 files (changes from recent commits).

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. When an issue isn't valid or won't be fixed in this PR, reply in its thread with the reason and then resolve the thread. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="static/js/featured-resources.js">

<violation number="1" location="static/js/featured-resources.js:774">
P3: Turning the lesson-plan filter off while another facet filter is still active can permanently flip previously-collapsed lesson-plan sections open. Trace: checking the filter opens each data-lp section and captures `wasOpen='0'`; the new override keeps it open (never `acc-disabled`) while a facet leaves its cards at 0 matches; unchecking the filter then hits the disable branch, which re-captures `wasOpen='1'` because the section is not `acc-disabled`; the later Clear-filter restore then expands it. The disable branch (line ~796) overwrites `wasOpen` unconditionally, unlike the else-if branch which guards with `if (!header.dataset.wasOpen)`. Guard the capture so the pre-filter state survives the open/disable transition.</violation>

<violation number="2" location="static/js/featured-resources.js:774">
P3: A sub-cluster kept open only because of `hasLp` (no cards matching the other filters) still has its badge rewritten to `0 / N` — a section that is visibly open and showing its teaching-materials strip reads as "0 matched" in the header. With the lesson-plan filter on plus, say, Type = Preprint or a search query, every kept-open strip section shows "0 / 14" while its strip is on screen. Make the badge consistent with the visible state — e.g. count the strip as a match (or hide/omit the zero count) when the section is kept open for this reason.</violation>
</file>

Tip: Review your code locally with the cubic CLI to iterate faster.

Re-trigger cubic


/* With the lesson-plan filter on, a sub-cluster with a set stays open even if no card
matches the other filters: its teaching-materials strip is what the user asked for. */
if (lpOnly && sec.hasLp) ownTextMatches = true;

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P3: Turning the lesson-plan filter off while another facet filter is still active can permanently flip previously-collapsed lesson-plan sections open. Trace: checking the filter opens each data-lp section and captures wasOpen='0'; the new override keeps it open (never acc-disabled) while a facet leaves its cards at 0 matches; unchecking the filter then hits the disable branch, which re-captures wasOpen='1' because the section is not acc-disabled; the later Clear-filter restore then expands it. The disable branch (line ~796) overwrites wasOpen unconditionally, unlike the else-if branch which guards with if (!header.dataset.wasOpen). Guard the capture so the pre-filter state survives the open/disable transition.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. When an issue isn't valid or won't be fixed in this PR, reply in its thread with the reason and then resolve the thread. At static/js/featured-resources.js, line 774:

<comment>Turning the lesson-plan filter off while another facet filter is still active can permanently flip previously-collapsed lesson-plan sections open. Trace: checking the filter opens each data-lp section and captures `wasOpen='0'`; the new override keeps it open (never `acc-disabled`) while a facet leaves its cards at 0 matches; unchecking the filter then hits the disable branch, which re-captures `wasOpen='1'` because the section is not `acc-disabled`; the later Clear-filter restore then expands it. The disable branch (line ~796) overwrites `wasOpen` unconditionally, unlike the else-if branch which guards with `if (!header.dataset.wasOpen)`. Guard the capture so the pre-filter state survives the open/disable transition.</comment>

<file context>
@@ -768,6 +769,10 @@
 
+        /* With the lesson-plan filter on, a sub-cluster with a set stays open even if no card
+           matches the other filters: its teaching-materials strip is what the user asked for. */
+        if (lpOnly && sec.hasLp) ownTextMatches = true;
+
         sectionResults.push({ matchCount: matchCount, cardVis: cardVis, ownTextMatches: ownTextMatches });
</file context>


/* With the lesson-plan filter on, a sub-cluster with a set stays open even if no card
matches the other filters: its teaching-materials strip is what the user asked for. */
if (lpOnly && sec.hasLp) ownTextMatches = true;

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P3: A sub-cluster kept open only because of hasLp (no cards matching the other filters) still has its badge rewritten to 0 / N — a section that is visibly open and showing its teaching-materials strip reads as "0 matched" in the header. With the lesson-plan filter on plus, say, Type = Preprint or a search query, every kept-open strip section shows "0 / 14" while its strip is on screen. Make the badge consistent with the visible state — e.g. count the strip as a match (or hide/omit the zero count) when the section is kept open for this reason.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. When an issue isn't valid or won't be fixed in this PR, reply in its thread with the reason and then resolve the thread. At static/js/featured-resources.js, line 774:

<comment>A sub-cluster kept open only because of `hasLp` (no cards matching the other filters) still has its badge rewritten to `0 / N` — a section that is visibly open and showing its teaching-materials strip reads as "0 matched" in the header. With the lesson-plan filter on plus, say, Type = Preprint or a search query, every kept-open strip section shows "0 / 14" while its strip is on screen. Make the badge consistent with the visible state — e.g. count the strip as a match (or hide/omit the zero count) when the section is kept open for this reason.</comment>

<file context>
@@ -768,6 +769,10 @@
 
+        /* With the lesson-plan filter on, a sub-cluster with a set stays open even if no card
+           matches the other filters: its teaching-materials strip is what the user asked for. */
+        if (lpOnly && sec.hasLp) ownTextMatches = true;
+
         sectionResults.push({ matchCount: matchCount, cardVis: cardVis, ownTextMatches: ownTextMatches });
</file context>

@richarddushime richarddushime left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants