From a2dc4f1964c3b9789006e89af17cd1d089fdb2da Mon Sep 17 00:00:00 2001 From: Sli Date: Wed, 8 Jan 2025 10:17:04 +0100 Subject: [PATCH] Create a new better script for showing more/less --- .npmrc | 1 + core/static/bundled/core/read-more-index.ts | 73 +++++++++++++++++++ core/static/core/style.scss | 4 + election/static/election/css/election.scss | 8 +- .../templates/election/election_detail.jinja | 26 ++----- locale/fr/LC_MESSAGES/django.po | 24 +++--- locale/fr/LC_MESSAGES/djangojs.po | 10 ++- package-lock.json | 13 ++-- package.json | 2 +- vite.config.mts | 4 - 10 files changed, 121 insertions(+), 44 deletions(-) create mode 100644 .npmrc create mode 100644 core/static/bundled/core/read-more-index.ts diff --git a/.npmrc b/.npmrc new file mode 100644 index 00000000..41583e36 --- /dev/null +++ b/.npmrc @@ -0,0 +1 @@ +@jsr:registry=https://npm.jsr.io diff --git a/core/static/bundled/core/read-more-index.ts b/core/static/bundled/core/read-more-index.ts new file mode 100644 index 00000000..52e095a3 --- /dev/null +++ b/core/static/bundled/core/read-more-index.ts @@ -0,0 +1,73 @@ +import clip from "@arendjr/text-clipper"; + +/* + This script adds a way to have a 'show more / show less' button + on some text content. + + The usage is very simple, you just have to add the attribute `show-more` + with the desired max size to the element you want to add the button to. + This script does html matching and is able to properly cut rendered markdown. + + Example usage: +

+ My very long text will be cut by this script +

+*/ + +function showMore(element: HTMLElement) { + if (!element.hasAttribute("show-more")) { + return; + } + + // Mark element as loaded so we can hide unloaded + // tags with css and avoid blinking text + element.setAttribute("show-more-loaded", ""); + + const fullContent = element.innerHTML; + const clippedContent = clip( + element.innerHTML, + Number.parseInt(element.getAttribute("show-more") as string), + { + html: true, + }, + ); + + // If already at the desired size, we don't do anything + if (clippedContent === fullContent) { + return; + } + + const actionLink = document.createElement("a"); + actionLink.setAttribute("class", "show-more-link"); + + let opened = false; + + const setText = () => { + if (opened) { + element.innerHTML = fullContent; + actionLink.innerText = gettext("Show less"); + } else { + element.innerHTML = clippedContent; + actionLink.innerText = gettext("Show more"); + } + element.appendChild(document.createElement("br")); + element.appendChild(actionLink); + }; + + const toggle = () => { + opened = !opened; + setText(); + }; + + setText(); + actionLink.addEventListener("click", (event) => { + event.preventDefault(); + toggle(); + }); +} + +document.addEventListener("DOMContentLoaded", () => { + for (const elem of document.querySelectorAll("[show-more]")) { + showMore(elem as HTMLElement); + } +}); diff --git a/core/static/core/style.scss b/core/static/core/style.scss index 913733d6..6a4f0235 100644 --- a/core/static/core/style.scss +++ b/core/static/core/style.scss @@ -131,6 +131,10 @@ body { display: none !important; } +[show-more]:not([show-more-loaded]) { + display: none !important; +} + /*--------------------------------HEADER-------------------------------*/ #popupheader { diff --git a/election/static/election/css/election.scss b/election/static/election/css/election.scss index 32ba7a9c..95f87f17 100644 --- a/election/static/election/css/election.scss +++ b/election/static/election/css/election.scss @@ -106,11 +106,17 @@ $min_col_width: 100px; margin: 0; } - >p { + .role_description { flex-grow: 1; margin-top: .5em; text-wrap: auto; text-align: left; + + // Show more/less element + a { + text-align: center; + display: block; + } } } diff --git a/election/templates/election/election_detail.jinja b/election/templates/election/election_detail.jinja index e9dfdd9b..28b2a956 100644 --- a/election/templates/election/election_detail.jinja +++ b/election/templates/election/election_detail.jinja @@ -4,12 +4,12 @@ {{ object.title }} {% endblock %} -{% block additional_css %} - +{% block additional_js %} + {% endblock %} -{% block additional_js %} - +{% block additional_css %} + {% endblock %} {% block content %} @@ -68,7 +68,7 @@

{{ role.title }}

-

{{ role.description }}

+

{{ role.description }}

{%- if role.max_choice > 1 and not election.has_voted(user) and election.can_vote(user) %} {% trans %}You may choose up to{% endtrans %} {{ role.max_choice }} {% trans %}people.{% endtrans %} {%- endif %} @@ -139,7 +139,9 @@
{{ candidature.user.first_name }} {{candidature.user.nick_name or ''}} {{ candidature.user.last_name }}
{%- if not election.is_vote_finished %} - {{ candidature.program | markdown or '' }} + + {{ candidature.program|markdown or '' }} + {%- endif %}
{%- if user.can_edit(candidature) -%} @@ -198,18 +200,6 @@ {% block script %} {{ super() }} -