Skip to content

Commit

Permalink
communities carousel: rewrite React to jinja & jquery
Browse files Browse the repository at this point in the history
  • Loading branch information
jennur committed Jun 23, 2023
1 parent b9568cd commit e37557f
Show file tree
Hide file tree
Showing 4 changed files with 169 additions and 65 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -5,31 +5,68 @@
* Invenio is free software; you can redistribute it and/or modify it
* under the terms of the MIT License; see LICENSE file for more details.
*/
import React from "react";
import ReactDOM from "react-dom";
import CommunitiesCarousel from "./CommunitiesCarousel";
import { OverridableContext, overrideStore } from "react-overridable";
import $ from "jquery";

const communitiesCarouselContainer = document.getElementById("communities-carousel");
const title = communitiesCarouselContainer.dataset.title;
const fetchUrl = communitiesCarouselContainer.dataset.fetchUrl;
const intervalDelay = parseInt(communitiesCarouselContainer.dataset.intervalDelay);
const animationSpeed = parseInt(communitiesCarouselContainer.dataset.animationSpeed);
const defaultLogo = communitiesCarouselContainer.dataset.defaultLogo;
const itemsPerPage = communitiesCarouselContainer.dataset.itemsPerPage;

const overriddenComponents = overrideStore.getAll();

ReactDOM.render(
<OverridableContext.Provider value={overriddenComponents}>
<CommunitiesCarousel
title={title}
fetchUrl={fetchUrl}
intervalDelay={intervalDelay}
animationSpeed={animationSpeed}
defaultLogo={defaultLogo}
itemsPerPage={itemsPerPage}
/>
</OverridableContext.Provider>,
communitiesCarouselContainer
);

const carouselSlides = $(".carousel.transition");
const prevSlideBtn = $("#prev-slide-btn");
const nextSlideBtn = $("#next-slide-btn");

const minIndex = 0;
const maxIndex = carouselSlides.length - 1;

var activeIndex = 0;

/**
* Switches carousel slide
* @param {string} direction Direction to slide - left or right
*/
const slide = (direction) => {
const prevIndex = activeIndex;

if (direction === "left") {
activeIndex++;
if (activeIndex > maxIndex) activeIndex = 0;
} else {
activeIndex--;
if (activeIndex < minIndex) activeIndex = maxIndex;
}

$(carouselSlides[activeIndex]).transition({
animation: `carousel-slide ${direction} in`,
duration: animationSpeed,
});

$(carouselSlides[prevIndex]).transition({
animation: `carousel-slide ${direction} out`,
duration: animationSpeed,
});
};

// Run carousel automatically on page load
const setCarouselTimer = () => setInterval(() => slide("left"), intervalDelay);
var carouselTimer = setCarouselTimer();

// Pause carousel on focus
$(communitiesCarouselContainer)
.on("focusin", () => {
clearInterval(carouselTimer);
})
.on("focusout", () => {
carouselTimer = setCarouselTimer();
});

// Navigation arrow event handlers
prevSlideBtn
.on("click", () => slide("right"))
.on("keydown", (event) => {
event.key === "Enter" && slide("right");
});
nextSlideBtn
.on("click", () => slide("left"))
.on("keydown", (event) => {
event.key === "Enter" && slide("left");
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
{# -*- coding: utf-8 -*-

This file is part of Invenio.
Copyright (C) 2023 CERN.

Invenio is free software; you can redistribute it and/or modify it
under the terms of the MIT License; see LICENSE file for more details.
#}

{% macro carousel_item(community=None) %}
<div class="item carousel align-items-center">
<img class="ui small image has-placeholder" src="{{ community.links.logo }}" />
<div class="content">
<div class="ui middle aligned grid rel-pb-1">
<div class="ten wide computer sixteen wide tablet column">
<a class="ui medium header" href="{{ community.links.self_html }}">
{{ community.metadata.title }}
</a>
</div>

<div class="six wide computer sixteen wide tablet column buttons">
<a
class="ui mini button"
href={community.links.self_html}
>
{{ _("Browse") }}
</a>
<a
class="ui mini icon positive left labeled button"
href="/uploads/new?community={{community.slug}}"
>
<i class="upload icon" aria-hidden="true"></i>
{{ _("New upload") }}
</a>
</div>
</div>

<p class="description">
{{ community.metadata.description | truncate(length=300, end='...') }}
</p>
</div>
</div>
{% endmacro %}
Original file line number Diff line number Diff line change
@@ -1,16 +1,18 @@
{# -*- coding: utf-8 -*-

This file is part of Invenio.
Copyright (C) 2016-2020 CERN.
Copyright (C) 2023 CERN.

Invenio is free software; you can redistribute it and/or modify it
under the terms of the MIT License; see LICENSE file for more details.
#}

{% from "invenio_communities/macros/communities_carousel_slides.html" import communities_carousel_slides %}

{% macro communities_carousel(
communities,
title=_("Featured communities"),
fetch_url="/api/communities/featured",
interval_delay="10000",
interval_delay="5000",
animation_speed="300",
items_per_page=1,
default_logo="/static/images/square-placeholder.png"
Expand All @@ -23,52 +25,40 @@
data-interval-delay="{{ interval_delay }}"
data-animation-speed="{{ animation_speed }}"
data-default-logo="{{ default_logo }}"
data-items-per-page="{{ items_per_page }}"
>
<div class="ui fluid container rel-pt-2 rel-pb-2 ml-0-mobile mr-0-mobile">
<div class="ui container">
<h2 class="ui header rel-mb-1">{{ title }}</h2>
<div class="ui fluid container carousel rel-pt-2 rel-pb-2 ml-0-mobile mr-0-mobile">
<div class="ui container rel-mb-1">
<h2 class="ui header">{{ title }}</h2>
</div>
<div class="ui grid container">
<div class="two wide column"></div>

<div class="ui container grid">
<div class="left aligned middle aligned two wide column pr-0">
<i
id="prev-slide-btn"
role="button"
tabindex="0"
aria-label="{{ _('Previous slide') }}"
class="angle left huge inverted icon carousel-arrow"
>
</i>
</div>
<div class="twelve wide column">
<div class="ui items">
<div class="item">
<div class="image">
<div class="ui placeholder">
<div class="square image"></div>
</div>
</div>

<div class="content">
<div class="header mt-5 rel-mb-2">
<div class="ui placeholder">
<div class="header">
<div class="line"></div>
</div>
</div>
</div>

<div class="description">
<div class="ui placeholder">
<div class="paragraph">
<div class="line"></div>
<div class="line"></div>
<div class="line"></div>
</div>
</div>
</div>
</div>
</div>
</div>
{{ communities_carousel_slides(communities, items_per_page) }}
</div>
<div class="right aligned middle aligned two wide column pl-0">
<i
id="next-slide-btn"
role="button"
tabindex="0"
aria-label="{{ _('Next slide') }}"
class="angle right huge inverted icon carousel-arrow"
>
</i>
</div>

<div class="two wide column"></div>
</div>

</div>
</div>

{{ webpack['invenio-communities-carousel.js'] }}
{% endmacro %}

Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
{# -*- coding: utf-8 -*-

This file is part of Invenio.
Copyright (C) 2023 CERN.

Invenio is free software; you can redistribute it and/or modify it
under the terms of the MIT License; see LICENSE file for more details.
#}

{% from "invenio_communities/macros/carousel_item.html" import carousel_item %}

{% macro communities_carousel_slides(communities, items_per_page) %}
{% set pageListLength = (communities|length / items_per_page) | round(0, 'ceil') | int %}
{% set communitiesList = communities|list %}
{% set index = 0 %}

<div id="carousel-slides">
{% for page in range(pageListLength) %}
{% set visibility_class = "visible" if (loop.index == 1) else "hidden" %}
<div class="ui items carousel page transition {{ visibility_class }} flex align-items-center">
{% for item in range(items_per_page) %}
{% set communityIndex = page*items_per_page + item %}
{% set community = communitiesList[communityIndex] %}

{% if community is defined %}
{{ carousel_item(community=community) }}
{% endif %}

{% set index = index + 1 %}
{% endfor %}
</div>
{% endfor %}
</div>
{% endmacro %}

0 comments on commit e37557f

Please sign in to comment.