feat: Introduce multi-platform architecture for Electron and Web clients with shared UI components, Convex backend for messaging, and integrated search functionality.
Some checks failed
Build and Release / build-and-release (push) Has been cancelled

This commit is contained in:
Bryan1029384756
2026-02-16 13:08:39 -06:00
parent 8ff9213b34
commit ec12313996
49 changed files with 2449 additions and 3914 deletions

View File

@@ -1,12 +1,40 @@
import React, { useState } from 'react';
import React from 'react';
import Tooltip from './Tooltip';
const ChatHeader = ({ channelName, channelType, channelTopic, onToggleMembers, showMembers, onTogglePinned, serverName, isMobile, onMobileBack }) => {
const [searchFocused, setSearchFocused] = useState(false);
const ChatHeader = ({
channelName,
channelType,
channelTopic,
onToggleMembers,
showMembers,
onTogglePinned,
serverName,
isMobile,
onMobileBack,
// Search props
searchQuery,
onSearchQueryChange,
onSearchSubmit,
onSearchFocus,
onSearchBlur,
searchInputRef,
searchActive,
}) => {
const isDM = channelType === 'dm';
const searchPlaceholder = isDM ? 'Search' : `Search ${serverName || 'Server'}`;
const handleSearchKeyDown = (e) => {
if (e.key === 'Enter') {
e.preventDefault();
onSearchSubmit?.();
}
if (e.key === 'Escape') {
e.preventDefault();
onSearchBlur?.();
e.target.blur();
}
};
return (
<div className="chat-header">
<div className="chat-header-left">
@@ -65,14 +93,29 @@ const ChatHeader = ({ channelName, channelType, channelTopic, onToggleMembers, s
</Tooltip>
)}
{!isMobile && (
<div className="chat-header-search-wrapper">
<div className="chat-header-search-wrapper" ref={searchInputRef}>
<svg className="chat-header-search-icon" width="16" height="16" viewBox="0 0 24 24" fill="currentColor">
<path d="M21.71 20.29L18 16.61A9 9 0 1016.61 18l3.68 3.68a1 1 0 001.42 0 1 1 0 000-1.39zM11 18a7 7 0 110-14 7 7 0 010 14z"/>
</svg>
<input
type="text"
placeholder={searchPlaceholder}
className={`chat-header-search ${searchFocused ? 'focused' : ''}`}
onFocus={() => setSearchFocused(true)}
onBlur={() => setSearchFocused(false)}
className={`chat-header-search ${searchActive ? 'focused' : ''}`}
value={searchQuery || ''}
onChange={(e) => onSearchQueryChange?.(e.target.value)}
onFocus={onSearchFocus}
onKeyDown={handleSearchKeyDown}
/>
{searchQuery && (
<button
className="chat-header-search-clear"
onClick={() => onSearchQueryChange?.('')}
>
<svg width="16" height="16" viewBox="0 0 24 24" fill="currentColor">
<path d="M18.4 4L12 10.4L5.6 4L4 5.6L10.4 12L4 18.4L5.6 20L12 13.6L18.4 20L20 18.4L13.6 12L20 5.6L18.4 4Z"/>
</svg>
</button>
)}
</div>
)}
</div>