AeThex-Connect/src/frontend/components/Chat/MessageList.css
MrPiglr cad2e81fc4
Phase 2: Complete Messaging System Implementation
- Added real-time messaging with Socket.io
- Created comprehensive database schema (8 tables, functions, triggers)
- Implemented messaging service with full CRUD operations
- Built Socket.io service for real-time communication
- Created React messaging components (Chat, ConversationList, MessageList, MessageInput)
- Added end-to-end encryption utilities (RSA + AES-256-GCM)
- Implemented 16 RESTful API endpoints
- Added typing indicators, presence tracking, reactions
- Created modern, responsive UI with animations
- Updated server with Socket.io integration
- Fixed auth middleware imports
- Added comprehensive documentation

Features:
- Direct and group conversations
- Real-time message delivery
- Message editing and deletion
- Emoji reactions
- Typing indicators
- Online/offline presence
- Read receipts
- User search
- File attachment support (endpoint ready)
- Client-side encryption utilities

Dependencies:
- socket.io ^4.7.5
- socket.io-client ^4.7.5
2026-01-10 04:45:07 +00:00

306 lines
4.7 KiB
CSS

/* Message List Container */
.message-list {
flex: 1;
overflow-y: auto;
padding: 1.5rem;
display: flex;
flex-direction: column-reverse;
gap: 1rem;
background: #f9fafb;
}
.message-list.empty {
justify-content: center;
align-items: center;
}
.no-messages {
text-align: center;
color: #9ca3af;
}
.no-messages p {
margin: 0.5rem 0;
}
.no-messages .hint {
font-size: 0.875rem;
color: #d1d5db;
}
/* Message Timestamp Divider */
.message-timestamp-divider {
text-align: center;
margin: 1rem 0;
position: relative;
}
.message-timestamp-divider::before {
content: '';
position: absolute;
top: 50%;
left: 0;
right: 0;
height: 1px;
background: #e5e7eb;
z-index: 0;
}
.message-timestamp-divider span,
.message-timestamp-divider::after {
display: inline-block;
padding: 0.25rem 1rem;
background: #f9fafb;
color: #6b7280;
font-size: 0.75rem;
border-radius: 12px;
position: relative;
z-index: 1;
}
/* Message */
.message {
display: flex;
gap: 0.75rem;
align-items: flex-start;
}
.message.own {
flex-direction: row-reverse;
}
.message.other {
flex-direction: row;
}
/* Message Avatar */
.message-avatar {
width: 32px;
height: 32px;
border-radius: 50%;
flex-shrink: 0;
}
.message-avatar img {
width: 100%;
height: 100%;
border-radius: 50%;
object-fit: cover;
}
.avatar-placeholder {
width: 32px;
height: 32px;
border-radius: 50%;
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
display: flex;
align-items: center;
justify-content: center;
color: white;
font-weight: 600;
font-size: 0.875rem;
}
/* Message Content */
.message-content-wrapper {
max-width: 70%;
display: flex;
flex-direction: column;
gap: 0.25rem;
}
.message.own .message-content-wrapper {
align-items: flex-end;
}
.message.other .message-content-wrapper {
align-items: flex-start;
}
.message-sender {
font-size: 0.75rem;
font-weight: 500;
color: #6b7280;
padding: 0 0.75rem;
}
.verified-badge {
color: #3b82f6;
margin-left: 0.25rem;
}
/* Message Bubble */
.message-bubble {
padding: 0.75rem 1rem;
border-radius: 1rem;
position: relative;
word-wrap: break-word;
}
.message.own .message-bubble {
background: #3b82f6;
color: white;
border-bottom-right-radius: 0.25rem;
}
.message.other .message-bubble {
background: white;
color: #111827;
border: 1px solid #e5e7eb;
border-bottom-left-radius: 0.25rem;
}
.message-reply-reference {
font-size: 0.75rem;
opacity: 0.7;
margin-bottom: 0.5rem;
padding-left: 0.5rem;
border-left: 2px solid currentColor;
}
.message-text {
font-size: 0.9375rem;
line-height: 1.5;
white-space: pre-wrap;
}
.message-attachments {
margin-top: 0.5rem;
display: flex;
flex-direction: column;
gap: 0.5rem;
}
.attachment {
padding: 0.5rem;
background: rgba(0, 0, 0, 0.05);
border-radius: 0.5rem;
font-size: 0.875rem;
}
.message.own .attachment {
background: rgba(255, 255, 255, 0.2);
}
/* Message Footer */
.message-footer {
display: flex;
align-items: center;
gap: 0.5rem;
margin-top: 0.25rem;
font-size: 0.6875rem;
opacity: 0.7;
}
.message-time {
font-weight: 400;
}
.edited-indicator {
font-style: italic;
}
.sending-indicator {
font-style: italic;
animation: pulse 1.5s ease-in-out infinite;
}
@keyframes pulse {
0%, 100% {
opacity: 0.5;
}
50% {
opacity: 1;
}
}
/* Message Reactions */
.message-reactions {
display: flex;
gap: 0.25rem;
margin-top: 0.5rem;
flex-wrap: wrap;
}
.reaction {
padding: 0.25rem 0.5rem;
background: rgba(0, 0, 0, 0.05);
border-radius: 12px;
font-size: 0.875rem;
cursor: pointer;
transition: background 0.2s;
}
.message.own .reaction {
background: rgba(255, 255, 255, 0.2);
}
.reaction:hover {
background: rgba(0, 0, 0, 0.1);
}
.message.own .reaction:hover {
background: rgba(255, 255, 255, 0.3);
}
/* Typing Indicator */
.typing-indicator {
display: flex;
align-items: center;
gap: 0.75rem;
padding: 0.75rem 1rem;
}
.typing-dots {
display: flex;
gap: 0.25rem;
}
.typing-dots span {
width: 8px;
height: 8px;
background: #9ca3af;
border-radius: 50%;
animation: typing 1.4s ease-in-out infinite;
}
.typing-dots span:nth-child(2) {
animation-delay: 0.2s;
}
.typing-dots span:nth-child(3) {
animation-delay: 0.4s;
}
@keyframes typing {
0%, 60%, 100% {
transform: translateY(0);
}
30% {
transform: translateY(-10px);
}
}
.typing-text {
font-size: 0.875rem;
color: #6b7280;
font-style: italic;
}
/* Scrollbar */
.message-list::-webkit-scrollbar {
width: 6px;
}
.message-list::-webkit-scrollbar-track {
background: #f3f4f6;
}
.message-list::-webkit-scrollbar-thumb {
background: #d1d5db;
border-radius: 3px;
}
.message-list::-webkit-scrollbar-thumb:hover {
background: #9ca3af;
}