...
This commit is contained in:
@@ -171,6 +171,7 @@
|
|||||||
LastOpenChat?.Responses.Add(model);
|
LastOpenChat?.Responses.Add(model);
|
||||||
LastOpenChat.LastText = MsgInput;
|
LastOpenChat.LastText = MsgInput;
|
||||||
await Task.Yield();
|
await Task.Yield();
|
||||||
|
// Scroll to bottom for user's own messages
|
||||||
await JS.InvokeVoidAsync("scrollToBottom", "B1");
|
await JS.InvokeVoidAsync("scrollToBottom", "B1");
|
||||||
MsgInput = string.Empty;
|
MsgInput = string.Empty;
|
||||||
}
|
}
|
||||||
@@ -181,7 +182,6 @@
|
|||||||
{
|
{
|
||||||
_shouldObserveVisibility = false;
|
_shouldObserveVisibility = false;
|
||||||
await JS.InvokeVoidAsync("observeVisibility", DotNetObjectReference.Create(this));
|
await JS.InvokeVoidAsync("observeVisibility", DotNetObjectReference.Create(this));
|
||||||
await JS.InvokeVoidAsync("scrollToTarget");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
protected override async Task OnInitializedAsync()
|
protected override async Task OnInitializedAsync()
|
||||||
@@ -236,9 +236,27 @@
|
|||||||
LastOpenChat = await ChatService.GetLastOpenChatInCompany(CompanyID);
|
LastOpenChat = await ChatService.GetLastOpenChatInCompany(CompanyID);
|
||||||
if (LastOpenChat != null)
|
if (LastOpenChat != null)
|
||||||
{
|
{
|
||||||
|
// Check if there are unread messages
|
||||||
|
var hasUnreadMessages = LastOpenChat.Responses?.Any(m => !m.IsRead && m.Type != Common.Enums.ConversationType.UE) ?? false;
|
||||||
|
|
||||||
|
if (hasUnreadMessages)
|
||||||
|
{
|
||||||
|
_shouldObserveVisibility = true;
|
||||||
|
StateHasChanged();
|
||||||
|
// Scroll to target (new message separator) after render
|
||||||
|
await Task.Delay(100);
|
||||||
|
await JS.InvokeVoidAsync("scrollToTarget");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// If no unread messages, scroll to bottom
|
||||||
|
await Task.Delay(100);
|
||||||
|
await JS.InvokeVoidAsync("scrollToBottom", "B1");
|
||||||
|
}
|
||||||
|
|
||||||
|
// Always set up visibility observation for chat bubbles
|
||||||
_shouldObserveVisibility = true;
|
_shouldObserveVisibility = true;
|
||||||
StateHasChanged();
|
StateHasChanged();
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -250,10 +268,23 @@
|
|||||||
{
|
{
|
||||||
msg.IsRead = true;
|
msg.IsRead = true;
|
||||||
await chatService.MarkAsReadChatItemAsync(id);
|
await chatService.MarkAsReadChatItemAsync(id);
|
||||||
|
// StateHasChanged();
|
||||||
}
|
}
|
||||||
StateHasChanged();
|
|
||||||
await Task.CompletedTask;
|
await Task.CompletedTask;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Method to handle new messages from other users
|
||||||
|
public async Task HandleNewMessage()
|
||||||
|
{
|
||||||
|
if (LastOpenChat?.Responses != null)
|
||||||
|
{
|
||||||
|
var hasUnreadMessages = LastOpenChat.Responses.Any(m => !m.IsRead && m.Type != Common.Enums.ConversationType.UE);
|
||||||
|
if (hasUnreadMessages)
|
||||||
|
{
|
||||||
|
await JS.InvokeVoidAsync("autoScrollToNewMessage");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
async Task Logout()
|
async Task Logout()
|
||||||
{
|
{
|
||||||
await baseController.RemoveToken();
|
await baseController.RemoveToken();
|
||||||
@@ -748,4 +779,51 @@
|
|||||||
el.scrollTop = el.scrollHeight;
|
el.scrollTop = el.scrollHeight;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Scroll to target element (new message separator)
|
||||||
|
window.scrollToTarget = () => {
|
||||||
|
const targetElement = document.getElementById('target');
|
||||||
|
if (targetElement) {
|
||||||
|
const chatContainer = document.getElementById('B1');
|
||||||
|
if (chatContainer) {
|
||||||
|
// Calculate the position of target element relative to chat container
|
||||||
|
const targetRect = targetElement.getBoundingClientRect();
|
||||||
|
const containerRect = chatContainer.getBoundingClientRect();
|
||||||
|
const relativeTop = targetRect.top - containerRect.top;
|
||||||
|
|
||||||
|
// Scroll to show the target element with some padding
|
||||||
|
const scrollPosition = chatContainer.scrollTop + relativeTop - 100; // 100px padding
|
||||||
|
chatContainer.scrollTo({
|
||||||
|
top: scrollPosition,
|
||||||
|
behavior: 'smooth'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// Observe visibility of chat bubbles using existing scroll-visibility.js approach
|
||||||
|
window.observeVisibility = (dotNetHelper) => {
|
||||||
|
const elements = document.querySelectorAll(".chat-bubble[data-id]");
|
||||||
|
const observer = new IntersectionObserver(entries => {
|
||||||
|
entries.forEach(entry => {
|
||||||
|
if (entry.isIntersecting) {
|
||||||
|
const id = entry.target.getAttribute("data-id");
|
||||||
|
dotNetHelper.invokeMethodAsync("MarkAsRead", parseInt(id));
|
||||||
|
observer.unobserve(entry.target); // Don't observe again
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}, {
|
||||||
|
threshold: 0.6 // 60% of the message must be visible
|
||||||
|
});
|
||||||
|
|
||||||
|
elements.forEach(el => observer.observe(el));
|
||||||
|
};
|
||||||
|
|
||||||
|
// Auto scroll to target when new messages arrive
|
||||||
|
window.autoScrollToNewMessage = () => {
|
||||||
|
setTimeout(() => {
|
||||||
|
window.scrollToTarget();
|
||||||
|
}, 100); // Small delay to ensure DOM is updated
|
||||||
|
};
|
||||||
|
|
||||||
</script>
|
</script>
|
Reference in New Issue
Block a user