mirror of
https://github.com/Freika/dawarich.git
synced 2026-01-10 17:21:38 -05:00
Use notifications badge
This commit is contained in:
parent
14b7397840
commit
bec9db1198
5 changed files with 61 additions and 33 deletions
File diff suppressed because one or more lines are too long
|
|
@ -2,46 +2,73 @@ import { Controller } from "@hotwired/stimulus"
|
|||
import consumer from "../channels/consumer"
|
||||
|
||||
export default class extends Controller {
|
||||
static targets = ["container"]
|
||||
static targets = ["badge"]
|
||||
static values = { userId: Number }
|
||||
|
||||
initialize() {
|
||||
this.subscription = null
|
||||
}
|
||||
|
||||
connect() {
|
||||
console.log("Controller connecting...")
|
||||
// Ensure we clean up any existing subscription
|
||||
console.log("[Stimulus] Notifications controller connecting...")
|
||||
|
||||
// Clean up any existing subscription
|
||||
if (this.subscription) {
|
||||
console.log("Cleaning up existing subscription")
|
||||
console.log("[Stimulus] Cleaning up existing subscription")
|
||||
this.subscription.unsubscribe()
|
||||
this.subscription = null
|
||||
}
|
||||
|
||||
this.subscription = consumer.subscriptions.create("NotificationsChannel", {
|
||||
connected: () => {
|
||||
console.log("Connected to NotificationsChannel", this.subscription)
|
||||
},
|
||||
disconnected: () => {
|
||||
console.log("Disconnected from NotificationsChannel")
|
||||
},
|
||||
received: (data) => {
|
||||
console.log("Received notification:", data, "Subscription:", this.subscription)
|
||||
this.displayNotification(data)
|
||||
}
|
||||
})
|
||||
// Create new subscription
|
||||
this.createSubscription()
|
||||
}
|
||||
|
||||
disconnect() {
|
||||
console.log("Controller disconnecting...")
|
||||
console.log("[Stimulus] Notifications controller disconnecting...")
|
||||
if (this.subscription) {
|
||||
this.subscription.unsubscribe()
|
||||
this.subscription = null
|
||||
}
|
||||
}
|
||||
|
||||
displayNotification(data) {
|
||||
console.log("Notification received:", data) // For debugging
|
||||
const notification = document.createElement("div")
|
||||
notification.classList.add("notification", `notification-${data.kind}`)
|
||||
notification.innerHTML = `<strong>${data.title}</strong>: ${data.content}`
|
||||
createSubscription() {
|
||||
console.log("[Stimulus] Creating new notification subscription")
|
||||
this.subscription = consumer.subscriptions.create("NotificationsChannel", {
|
||||
connected: () => {
|
||||
console.log("[WebSocket] Connected to NotificationsChannel")
|
||||
},
|
||||
disconnected: () => {
|
||||
console.log("[WebSocket] Disconnected from NotificationsChannel")
|
||||
},
|
||||
received: (data) => {
|
||||
console.log("[WebSocket] Received notification:", data)
|
||||
this.animateBadge()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
this.containerTarget.appendChild(notification)
|
||||
setTimeout(() => notification.remove(), 5000) // Auto-hide after 5 seconds
|
||||
animateBadge() {
|
||||
let badge = this.hasBadgeTarget ? this.badgeTarget : null
|
||||
|
||||
if (!badge) {
|
||||
badge = document.createElement("span")
|
||||
badge.className = "badge badge-xs badge-primary absolute top-0 right-0"
|
||||
badge.setAttribute("data-notifications-target", "badge")
|
||||
this.element.querySelector('.btn').appendChild(badge)
|
||||
}
|
||||
|
||||
// Create ping effect div if it doesn't exist
|
||||
let pingEffect = badge.querySelector('.ping-effect')
|
||||
if (!pingEffect) {
|
||||
pingEffect = document.createElement("span")
|
||||
pingEffect.className = "ping-effect absolute inline-flex h-full w-full rounded-full animate-ping bg-primary opacity-75"
|
||||
badge.appendChild(pingEffect)
|
||||
} else {
|
||||
// Reset animation
|
||||
pingEffect.remove()
|
||||
requestAnimationFrame(() => {
|
||||
badge.appendChild(pingEffect)
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -18,13 +18,14 @@ class Notification < ApplicationRecord
|
|||
private
|
||||
|
||||
def broadcast_notification
|
||||
Rails.logger.debug "Broadcasting notification to #{user.id}"
|
||||
NotificationsChannel.broadcast_to(
|
||||
user,
|
||||
{
|
||||
id: id,
|
||||
title: title,
|
||||
content: content,
|
||||
kind: kind
|
||||
kind: kind,
|
||||
timestamp: Time.current.to_i
|
||||
}
|
||||
)
|
||||
end
|
||||
|
|
|
|||
|
|
@ -21,9 +21,6 @@
|
|||
<div class='container mx-auto'>
|
||||
<%= render 'shared/navbar' %>
|
||||
<%= render 'shared/flash' %>
|
||||
<div data-controller="notifications" data-notifications-user-id-value="<%= current_user.id %>">
|
||||
<div data-notifications-target="container" class="notifications-container"></div>
|
||||
</div>
|
||||
<div class="flex flex-row gap-5 w-full px-5">
|
||||
<%= yield %>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -53,7 +53,9 @@
|
|||
<div class="navbar-end">
|
||||
<ul class="menu menu-horizontal bg-base-100 rounded-box px-1">
|
||||
<% if user_signed_in? %>
|
||||
<div class="dropdown dropdown-end dropdown-bottom">
|
||||
<div class="dropdown dropdown-end dropdown-bottom"
|
||||
data-controller="notifications"
|
||||
data-notifications-user-id-value="<%= current_user.id %>">
|
||||
<div tabindex="0" role="button" class='btn btn-sm btn-ghost hover:btn-ghost'>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
|
|
@ -68,7 +70,8 @@
|
|||
d="M15 17h5l-1.405-1.405A2.032 2.032 0 0118 14.158V11a6.002 6.002 0 00-4-5.659V5a2 2 0 10-4 0v.341C7.67 6.165 6 8.388 6 11v3.159c0 .538-.214 1.055-.595 1.436L4 17h5m6 0v1a3 3 0 11-6 0v-1m6 0H9" />
|
||||
</svg>
|
||||
<% if @unread_notifications.present? %>
|
||||
<span class="badge badge-xs badge-primary"></span>
|
||||
<span class="badge badge-xs badge-primary absolute top-0 right-0"
|
||||
data-notifications-target="badge"></span>
|
||||
<% end %>
|
||||
</div>
|
||||
<ul tabindex="0" class="dropdown-content z-10 menu p-2 shadow-lg bg-base-100 rounded-box min-w-52">
|
||||
|
|
|
|||
Loading…
Reference in a new issue