diff --git a/app/javascript/controllers/countdown_controller.js b/app/javascript/controllers/countdown_controller.js new file mode 100644 index 0000000..17c542f --- /dev/null +++ b/app/javascript/controllers/countdown_controller.js @@ -0,0 +1,71 @@ +import { Controller } from "@hotwired/stimulus" + +// Countdown controller for displaying remaining time until order expiration +export default class extends Controller { + static values = { + expiresAt: String, // ISO timestamp when the order expires + orderId: Number // Order ID for identification + } + + connect() { + // Parse the expiration timestamp + this.expirationTime = new Date(this.expiresAtValue).getTime() + + // Find the countdown element + this.countdownElement = this.element.querySelector('.countdown-timer') + + if (this.countdownElement && !isNaN(this.expirationTime)) { + // Start the countdown + this.updateCountdown() + this.timer = setInterval(() => this.updateCountdown(), 1000) + } + } + + disconnect() { + // Clean up the interval when the controller disconnects + if (this.timer) { + clearInterval(this.timer) + } + } + + updateCountdown() { + const now = new Date().getTime() + const distance = this.expirationTime - now + + // If the countdown is finished + if (distance < 0) { + this.countdownElement.innerHTML = "EXPIRÉ" + this.countdownElement.classList.add("text-red-600", "font-bold") + this.countdownElement.classList.remove("text-orange-600") + + // Add a more urgent visual indicator + this.element.classList.add("bg-red-50", "border-red-200") + this.element.classList.remove("bg-orange-50", "border-orange-200") + + // Stop the timer + if (this.timer) { + clearInterval(this.timer) + } + return + } + + // Calculate time components + const seconds = Math.floor(distance / 1000) + + // Display the result + this.countdownElement.innerHTML = `${seconds} secondes` + + // Add urgency styling when time is running low + if (seconds < 60) { + this.countdownElement.classList.add("text-red-600", "font-bold") + this.countdownElement.classList.remove("text-orange-600") + + // Add background warning for extra urgency + this.element.classList.add("bg-red-50", "border-red-200") + this.element.classList.remove("bg-orange-50", "border-orange-200") + } else if (seconds < 300) { // Less than 5 minutes + this.countdownElement.classList.add("text-orange-600", "font-bold") + this.element.classList.add("bg-orange-50", "border-orange-200") + } + } +} \ No newline at end of file diff --git a/app/javascript/controllers/index.js b/app/javascript/controllers/index.js index 8eee735..c2e384d 100755 --- a/app/javascript/controllers/index.js +++ b/app/javascript/controllers/index.js @@ -24,3 +24,6 @@ application.register("qr-code", QrCodeController); import EventFormController from "./event_form_controller"; application.register("event-form", EventFormController); + +import CountdownController from "./countdown_controller"; +application.register("countdown", CountdownController); diff --git a/app/views/pages/dashboard.html.erb b/app/views/pages/dashboard.html.erb index e7d195d..39e0612 100755 --- a/app/views/pages/dashboard.html.erb +++ b/app/views/pages/dashboard.html.erb @@ -129,7 +129,10 @@ <% @promoter_events.each do |event| %>
-

<%= event.name %>

+ <%= link_to promoter_event_path(event) do %> +

<%= event.name %>

+ <% end %> + <%= event.state.humanize %> @@ -246,7 +249,12 @@ Tentatives: <%= order.payment_attempts %>/3
<% if order.expiring_soon? %> - ⚠️ Expire dans <%= time_ago_in_words(order.expires_at) %> + + ⚠️ Expire dans + <% else %> Expire dans <%= time_ago_in_words(order.expires_at) %> <% end %> @@ -385,6 +393,7 @@ <% @upcoming_preview_events.each do |event| %>

<%= event.name %>

+