Spaces:
Running
Running
Download static/index.html from smodusermc/InfinityChat: direct link, hf CLI and curl.
- Browser
- Download file 53.1 kB
-
https://huggingface.co/spaces/smodusermc/InfinityChat/resolve/main/static/index.html
- Command line
-
hf download hf://spaces/smodusermc/InfinityChat/static/index.html
-
curl -L -o index.html https://huggingface.co/spaces/smodusermc/InfinityChat/resolve/main/static/index.html
53.1 kB
| <html lang="en"> | |
| <head> | |
| <meta charset="UTF-8"> | |
| <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no"> | |
| <title>InfinityChat</title> | |
| <meta name="theme-color" content="#2563EB"> | |
| <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.5.1/css/all.min.css"> | |
| <link rel="preconnect" href="https://fonts.googleapis.com"> | |
| <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin> | |
| <link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap" rel="stylesheet"> | |
| <link rel="stylesheet" href="/static/style.css?v=11"> | |
| </head> | |
| <body> | |
| <div id="auth-screen" class="screen active"> | |
| <div class="auth-bg"> | |
| <div class="auth-bg-circle auth-bg-circle-1"></div> | |
| <div class="auth-bg-circle auth-bg-circle-2"></div> | |
| <div class="auth-bg-circle auth-bg-circle-3"></div> | |
| </div> | |
| <div class="auth-container"> | |
| <div class="auth-header"> | |
| <div class="auth-logo"><i class="fas fa-infinity"></i></div> | |
| <h1 class="auth-title">InfinityChat</h1> | |
| <p class="auth-subtitle">Secure, private, real-time messaging</p> | |
| </div> | |
| <div class="auth-tabs"> | |
| <button class="auth-tab active" data-tab="login"> | |
| <i class="fas fa-sign-in-alt"></i> Sign In | |
| </button> | |
| <button class="auth-tab" data-tab="signup"> | |
| <i class="fas fa-user-plus"></i> Create Account | |
| </button> | |
| </div> | |
| <form id="login-form" class="auth-form active"> | |
| <div class="form-group"> | |
| <label for="login-username"><i class="fas fa-user"></i> Username</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="login-username" class="form-input" | |
| placeholder="Enter your username" required | |
| autocomplete="username" spellcheck="false"> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="login-password"><i class="fas fa-lock"></i> Password</label> | |
| <div class="input-wrapper"> | |
| <input type="password" id="login-password" class="form-input" | |
| placeholder="Enter your password" required | |
| autocomplete="current-password"> | |
| <button type="button" class="input-toggle" data-toggle="login-password"> | |
| <i class="fas fa-eye"></i> | |
| </button> | |
| </div> | |
| </div> | |
| <button type="submit" class="btn btn-primary btn-block"> | |
| <i class="fas fa-arrow-right"></i> Sign In | |
| </button> | |
| </form> | |
| <form id="signup-form" class="auth-form"> | |
| <div class="form-group"> | |
| <label for="signup-username"><i class="fas fa-user"></i> Username</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="signup-username" class="form-input" | |
| placeholder="Choose a username" required | |
| minlength="3" maxlength="30" | |
| pattern="[a-zA-Z0-9_]+" autocomplete="off" spellcheck="false"> | |
| </div> | |
| <small class="form-hint">3-30 characters, letters, numbers, underscores</small> | |
| </div> | |
| <div class="form-group"> | |
| <label for="signup-display"><i class="fas fa-id-card"></i> Display Name</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="signup-display" class="form-input" | |
| placeholder="Your display name (optional)" | |
| maxlength="50" autocomplete="off"> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="signup-password"><i class="fas fa-lock"></i> Password</label> | |
| <div class="input-wrapper"> | |
| <input type="password" id="signup-password" class="form-input" | |
| placeholder="Create a password" required | |
| minlength="6" autocomplete="new-password"> | |
| <button type="button" class="input-toggle" data-toggle="signup-password"> | |
| <i class="fas fa-eye"></i> | |
| </button> | |
| </div> | |
| <small class="form-hint">At least 6 characters</small> | |
| </div> | |
| <div class="password-strength"> | |
| <div class="strength-bar"> | |
| <div id="strength-fill" class="strength-fill"></div> | |
| </div> | |
| <span id="strength-text" class="strength-text"></span> | |
| </div> | |
| <button type="submit" class="btn btn-primary btn-block"> | |
| <i class="fas fa-user-plus"></i> Create Account | |
| </button> | |
| </form> | |
| <div id="auth-error" class="alert alert-error"> | |
| <i class="fas fa-exclamation-circle"></i> | |
| <span id="auth-error-text"></span> | |
| </div> | |
| <div id="auth-loading" class="auth-loading hidden"> | |
| <div class="spinner"></div> | |
| <span>Please wait...</span> | |
| </div> | |
| </div> | |
| </div> | |
| <div id="chat-screen" class="screen"> | |
| <div class="app-layout"> | |
| <!-- ================= SIDEBAR / CONVERSATION LIST ================= --> | |
| <div id="sidebar-backdrop" class="sidebar-backdrop hidden"></div> | |
| <aside id="sidebar" class="sidebar"> | |
| <div class="sidebar-header"> | |
| <div class="sidebar-brand"> | |
| <div class="auth-logo sidebar-logo"><i class="fas fa-infinity"></i></div> | |
| <span class="sidebar-brand-name">InfinityChat</span> | |
| </div> | |
| <button id="sidebar-close-btn" class="btn-icon sidebar-close" aria-label="Close menu"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div class="sidebar-me"> | |
| <div class="me-avatar-wrap"> | |
| <img id="sb-me-avatar" class="me-avatar hidden" alt="My avatar"> | |
| <div id="sb-me-avatar-ph" class="me-avatar-ph"><i class="fas fa-user"></i></div> | |
| </div> | |
| <div class="me-info"> | |
| <div id="sb-me-name" class="me-name">…</div> | |
| <div class="me-status"><span class="status-dot online"></span><span>Online</span></div> | |
| </div> | |
| <button id="me-settings-btn" class="btn-icon btn-icon-sm" aria-label="Settings" title="Settings"> | |
| <i class="fas fa-cog"></i> | |
| </button> | |
| </div> | |
| <nav id="conv-list" class="conv-list" aria-label="Conversations"></nav> | |
| <div class="sidebar-footer"> | |
| <button id="sidebar-logout-btn" class="btn btn-ghost btn-block"> | |
| <i class="fas fa-sign-out-alt"></i> Log out | |
| </button> | |
| </div> | |
| </aside> | |
| <!-- ================= MAIN CHAT COLUMN ================= --> | |
| <main class="chat-main"> | |
| <header class="chat-header"> | |
| <div class="header-section header-left"> | |
| <button id="sidebar-open-btn" class="btn-icon sidebar-open" aria-label="Open conversations"> | |
| <i class="fas fa-bars"></i> | |
| </button> | |
| <div class="conv-avatar-wrap"> | |
| <img id="conv-avatar" class="conv-avatar-img hidden" alt="Conversation avatar"> | |
| <div id="conv-avatar-ph" class="conv-avatar-ph"><i class="fas fa-globe"></i></div> | |
| <span id="conv-presence-dot" class="presence-dot hidden"></span> | |
| </div> | |
| <div class="header-info"> | |
| <h2 class="header-name" id="conv-title">Global Chat</h2> | |
| <span class="header-status" id="conv-subtitle"><span class="status-dot online"></span> Online</span> | |
| </div> | |
| </div> | |
| <div class="header-section header-right"> | |
| <button id="private-chat-btn" class="btn-icon" aria-label="New private chat" title="New private chat"> | |
| <i class="fas fa-user-plus"></i> | |
| </button> | |
| <button id="group-btn" class="btn-icon" aria-label="New group chat" title="New group chat"> | |
| <i class="fas fa-people-group"></i> | |
| </button> | |
| <button id="online-btn" class="btn-icon" aria-label="Online users" title="Online users"> | |
| <i class="fas fa-users"></i> | |
| <span id="online-badge" class="badge hidden">0</span> | |
| </button> | |
| <button id="conv-options-btn" class="btn-icon" aria-label="Chat options" title="Chat options"> | |
| <i class="fas fa-ellipsis-h"></i> | |
| </button> | |
| <button id="social-btn" class="btn-icon" aria-label="Social feed" title="Social feed"> | |
| <i class="fas fa-hashtag"></i> | |
| </button> | |
| <button id="settings-btn" class="btn-icon" aria-label="Settings" title="Settings"> | |
| <i class="fas fa-cog"></i> | |
| </button> | |
| <button id="logout-btn" class="btn-icon" aria-label="Logout" title="Log out"> | |
| <i class="fas fa-sign-out-alt"></i> | |
| </button> | |
| </div> | |
| </header> | |
| <div id="connection-status" class="connection-status"> | |
| <i class="fas fa-wifi"></i> | |
| <span id="connection-text">Connecting...</span> | |
| </div> | |
| <div id="messages-container" class="messages-container"> | |
| <div id="messages-scroll" class="messages-scroll"> | |
| <div id="load-more" class="load-more"> | |
| <button id="load-older-btn" class="btn btn-ghost hidden"> | |
| <i class="fas fa-chevron-up"></i> Load older messages | |
| </button> | |
| </div> | |
| <div id="messages-list" class="messages-list"> | |
| <div id="empty-state" class="empty-state"> | |
| <div id="empty-icon" class="empty-icon"><i class="fas fa-comments"></i></div> | |
| <h3 id="empty-title">No messages yet</h3> | |
| <p id="empty-sub">Start the conversation below</p> | |
| </div> | |
| </div> | |
| </div> | |
| <button id="scroll-bottom-btn" class="scroll-bottom-btn hidden"> | |
| <i class="fas fa-chevron-down"></i> | |
| </button> | |
| <div id="latest-message-bar" class="latest-message-bar hidden"> | |
| <div class="lmb-avatar" id="lmb-avatar"></div> | |
| <span class="lmb-name" id="lmb-name"></span> | |
| <span class="lmb-text" id="lmb-text"></span> | |
| </div> | |
| </div> | |
| <div id="typing-indicator" class="typing-indicator hidden"> | |
| <div class="typing-dots"> | |
| <span class="typing-dot"></span> | |
| <span class="typing-dot"></span> | |
| <span class="typing-dot"></span> | |
| </div> | |
| <span id="typing-text" class="typing-text"></span> | |
| </div> | |
| <div id="reply-preview" class="reply-preview hidden"> | |
| <div class="reply-bar"> | |
| <i class="fas fa-reply reply-icon"></i> | |
| <div class="reply-content"> | |
| <span class="reply-label">Replying to <strong id="reply-user"></strong></span> | |
| <span id="reply-text" class="reply-text"></span> | |
| </div> | |
| <button id="cancel-reply" class="btn-icon btn-icon-sm"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| </div> | |
| <div class="compose-area"> | |
| <div id="upload-preview" class="upload-preview hidden"> | |
| <div class="upload-info"> | |
| <i id="upload-icon" class="fas fa-file-alt"></i> | |
| <div class="upload-text"> | |
| <span id="upload-filename"></span> | |
| <span id="upload-size" class="upload-size"></span> | |
| </div> | |
| </div> | |
| <button id="cancel-upload" class="btn-icon btn-icon-sm"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <form id="compose-form" class="compose-form"> | |
| <div class="compose-tools"> | |
| <button type="button" id="attach-btn" class="btn-icon" aria-label="Attach file" title="Attach file"> | |
| <i class="fas fa-paperclip"></i> | |
| </button> | |
| <button type="button" id="emoji-btn" class="btn-icon" aria-label="Emoji" title="Emoji"> | |
| <i class="fas fa-smile"></i> | |
| </button> | |
| </div> | |
| <input type="file" id="file-input" | |
| accept="image/*,video/*,audio/*,.pdf,.doc,.docx,.txt,.zip" | |
| style="display:none"> | |
| <div class="input-area"> | |
| <textarea id="message-input" class="message-input" | |
| placeholder="Type a message... (Paste or drop images too)" rows="1" | |
| maxlength="10000"></textarea> | |
| </div> | |
| <button type="submit" id="send-btn" class="btn btn-send" disabled> | |
| <i class="fas fa-paper-plane"></i> | |
| </button> | |
| </form> | |
| <div id="upload-progress" class="upload-progress hidden"> | |
| <div class="progress-track"> | |
| <div id="progress-fill" class="progress-fill" style="width:0%"></div> | |
| </div> | |
| <span id="progress-text" class="progress-text">0%</span> | |
| </div> | |
| </div> | |
| </main> | |
| </div> | |
| <div id="drop-overlay" class="drop-overlay hidden"> | |
| <i class="fas fa-cloud-upload-alt"></i> | |
| <span>Drop files to attach</span> | |
| </div> | |
| </div> | |
| <!-- ================= SOCIAL / TWITTER-LIKE PAGE ================= --> | |
| <div id="social-screen" class="screen"> | |
| <div class="social-app"> | |
| <header class="social-topbar"> | |
| <button id="social-back-btn" class="btn-icon" aria-label="Back to chat" title="Back to chat"> | |
| <i class="fas fa-arrow-left"></i> | |
| </button> | |
| <div class="social-topbar-title"> | |
| <strong id="social-page-title">Home</strong> | |
| <span id="social-page-sub">Posts from people you follow</span> | |
| </div> | |
| <div class="social-topbar-search"> | |
| <i class="fas fa-search"></i> | |
| <input id="social-search-input" type="search" placeholder="Search posts or people" autocomplete="off"> | |
| <button id="social-search-clear" class="btn-icon btn-icon-sm hidden" aria-label="Clear search"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <button id="social-settings-btn" class="btn-icon" aria-label="Social settings" title="Social settings"> | |
| <i class="fas fa-sliders"></i> | |
| </button> | |
| </header> | |
| <div class="social-body"> | |
| <aside class="social-nav"> | |
| <div class="social-nav-user"> | |
| <div class="user-avatar social-nav-avatar"> | |
| <img id="social-me-avatar" class="hidden" alt="me"> | |
| <span id="social-me-avatar-ph" class="social-nav-initial"></span> | |
| </div> | |
| <div class="social-nav-userinfo"> | |
| <strong id="social-me-name">…</strong> | |
| <span id="social-me-username" class="text-secondary">@…</span> | |
| </div> | |
| </div> | |
| <nav class="social-nav-links"> | |
| <button class="social-nav-link active" data-social-view="home"> | |
| <i class="fas fa-home"></i><span>Home</span> | |
| </button> | |
| <button class="social-nav-link" data-social-view="explore"> | |
| <i class="fas fa-compass"></i><span>Explore</span> | |
| </button> | |
| <button class="social-nav-link" data-social-view="notifications"> | |
| <i class="fas fa-bell"></i><span>Notifications</span> | |
| <span id="social-unread-badge" class="badge hidden">0</span> | |
| </button> | |
| <button class="social-nav-link" data-social-view="bookmarks"> | |
| <i class="fas fa-bookmark"></i><span>Bookmarks</span> | |
| </button> | |
| <button class="social-nav-link" data-social-view="profile"> | |
| <i class="fas fa-user-circle"></i><span>My Profile</span> | |
| </button> | |
| </nav> | |
| <button id="social-compose-nav-btn" class="btn btn-primary btn-block social-compose-btn"> | |
| <i class="fas fa-feather"></i> Post | |
| </button> | |
| <div class="social-nav-footer"> | |
| <button id="social-logout-btn" class="btn btn-ghost btn-block"> | |
| <i class="fas fa-sign-out-alt"></i> Log out | |
| </button> | |
| </div> | |
| </aside> | |
| <main class="social-main"> | |
| <div id="social-compose" class="social-compose"> | |
| <div class="user-avatar"> | |
| <img id="social-compose-avatar" class="hidden" alt="me"> | |
| <span id="social-compose-avatar-ph"></span> | |
| </div> | |
| <div class="social-compose-main"> | |
| <textarea id="social-post-input" class="social-post-input" | |
| placeholder="What is happening?!" | |
| maxlength="28000" rows="2"></textarea> | |
| <div class="social-compose-tools"> | |
| <label class="btn-icon" title="Upload media" for="social-media-input"> | |
| <i class="fas fa-image"></i> | |
| </label> | |
| <label class="btn-icon" title="Emoji" for="social-post-emoji"> | |
| <i class="fas fa-smile"></i> | |
| </label> | |
| <span id="social-post-count" class="social-post-count"></span> | |
| <button id="social-post-btn" class="btn btn-primary btn-sm" disabled> | |
| <i class="fas fa-feather"></i> Post | |
| </button> | |
| </div> | |
| <div id="social-media-preview" class="social-media-preview hidden"></div> | |
| <div id="social-upload-progress" class="social-upload-progress hidden"> | |
| <div class="social-progress-track"><div class="social-progress-fill" style="width:0%"></div></div> | |
| <span>Uploading…</span> | |
| </div> | |
| </div> | |
| </div> | |
| <div id="social-feed" class="social-feed"> | |
| <div class="social-feed-empty hidden"> | |
| <i class="fas fa-feather"></i> | |
| <h3>Nothing here yet</h3> | |
| <p>Follow people or make the first post.</p> | |
| </div> | |
| </div> | |
| <div id="social-loading" class="social-loading hidden"><div class="spinner"></div></div> | |
| </main> | |
| <aside class="social-rail"> | |
| <section class="social-card social-trending"> | |
| <h3><i class="fas fa-fire"></i> Trending</h3> | |
| <div id="social-trending-list" class="social-trending-list"></div> | |
| </section> | |
| <section class="social-card social-suggest"> | |
| <h3><i class="fas fa-user-plus"></i> Who to follow</h3> | |
| <div id="social-suggest-list" class="social-suggest-list"></div> | |
| </section> | |
| </aside> | |
| </div> | |
| <!-- Hidden inputs for composer media and emoji --> | |
| <input type="file" id="social-media-input" class="hidden" multiple accept="image/*,video/*" style="display:none"> | |
| <input type="text" id="social-post-emoji" class="hidden" style="display:none"> | |
| </div> | |
| </div> | |
| <!-- Compose / reply / quote modal --> | |
| <div id="social-compose-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="social-compose-modal"></div> | |
| <div class="modal-container modal-md"> | |
| <div class="modal-header"> | |
| <h2 id="social-compose-modal-title"><i class="fas fa-feather"></i> Compose</h2> | |
| <button class="btn-icon" data-close="social-compose-modal"><i class="fas fa-times"></i></button> | |
| </div> | |
| <div class="modal-body"> | |
| <div id="social-compose-modal-context" class="social-reply-context hidden"></div> | |
| <textarea id="social-compose-modal-input" class="social-post-input" | |
| placeholder="What is happening?!" maxlength="28000" rows="5"></textarea> | |
| <div id="social-compose-modal-media-preview" class="social-media-preview hidden"></div> | |
| <div id="social-compose-modal-progress" class="social-upload-progress hidden"> | |
| <div class="social-progress-track"><div class="social-progress-fill" style="width:0%"></div></div> | |
| <span>Uploading…</span> | |
| </div> | |
| <div class="social-compose-tools"> | |
| <label class="btn-icon" title="Upload media" for="social-compose-modal-media"> | |
| <i class="fas fa-image"></i> | |
| </label> | |
| <span id="social-compose-modal-count" class="social-post-count"></span> | |
| <button id="social-compose-modal-submit" class="btn btn-primary btn-sm"> | |
| <i class="fas fa-feather"></i> Post | |
| </button> | |
| </div> | |
| <input type="file" id="social-compose-modal-media" class="hidden" multiple | |
| accept="image/*,video/*" style="display:none"> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Social settings modal --> | |
| <div id="social-settings-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="social-settings-modal"></div> | |
| <div class="modal-container modal-sm"> | |
| <div class="modal-header"> | |
| <h2><i class="fas fa-sliders"></i> Social Settings</h2> | |
| <button class="btn-icon" data-close="social-settings-modal"><i class="fas fa-times"></i></button> | |
| </div> | |
| <div class="modal-body"> | |
| <div class="settings-toggle-row"> | |
| <div><label for="social-setting-autoplay">Autoplay media</label><div class="toggle-hint">Play videos automatically in your feed</div></div> | |
| <label class="toggle-switch"><input type="checkbox" id="social-setting-autoplay"><span class="toggle-slider"></span></label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div><label for="social-setting-muted">Mute videos by default</label><div class="toggle-hint">Start videos muted when autoplaying</div></div> | |
| <label class="toggle-switch"><input type="checkbox" id="social-setting-muted" checked><span class="toggle-slider"></span></label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div><label for="social-setting-hide-reposts">Hide reposts</label><div class="toggle-hint">Remove reposts from Home</div></div> | |
| <label class="toggle-switch"><input type="checkbox" id="social-setting-hide-reposts"><span class="toggle-slider"></span></label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div><label for="social-setting-compact">Compact posts</label><div class="toggle-hint">Show more posts with smaller cards</div></div> | |
| <label class="toggle-switch"><input type="checkbox" id="social-setting-compact"><span class="toggle-slider"></span></label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div><label for="social-setting-live">Live refresh</label><div class="toggle-hint">Automatically refresh the feed</div></div> | |
| <label class="toggle-switch"><input type="checkbox" id="social-setting-live" checked><span class="toggle-slider"></span></label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div><label for="social-setting-badges">Notification badge</label><div class="toggle-hint">Show unread notification count</div></div> | |
| <label class="toggle-switch"><input type="checkbox" id="social-setting-badges" checked><span class="toggle-slider"></span></label> | |
| </div> | |
| <div class="form-group" style="margin-top:1rem"> | |
| <label for="social-setting-default">Default feed</label> | |
| <div class="input-wrapper"> | |
| <select id="social-setting-default" class="form-input"> | |
| <option value="home">Home</option> | |
| <option value="explore">Explore</option> | |
| </select> | |
| </div> | |
| </div> | |
| </div> | |
| <div class="modal-footer"> | |
| <button class="btn btn-ghost" data-close="social-settings-modal">Cancel</button> | |
| <button id="social-settings-save" class="btn btn-primary"><i class="fas fa-check"></i> Save</button> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Backups are managed from the separate /admin console. --> | |
| <!-- Settings Modal --> | |
| <div id="settings-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="settings-modal"></div> | |
| <div class="modal-container"> | |
| <div class="modal-header"> | |
| <h2><i class="fas fa-cog"></i> Settings</h2> | |
| <button class="btn-icon" data-close="settings-modal"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div class="modal-body"> | |
| <section class="settings-section"> | |
| <h3>Profile</h3> | |
| <div class="avatar-section"> | |
| <div id="settings-avatar-preview" class="settings-avatar"> | |
| <i class="fas fa-user-circle"></i> | |
| </div> | |
| <img id="settings-avatar-img" class="settings-avatar-img hidden" alt="Avatar"> | |
| <button id="avatar-upload-btn" class="btn btn-secondary btn-sm"> | |
| <i class="fas fa-camera"></i> Change Photo | |
| </button> | |
| <input type="file" id="avatar-input" accept="image/png,image/jpeg,image/gif,image/webp" style="display:none"> | |
| </div> | |
| <div class="form-group"> | |
| <label for="settings-display-name">Display Name</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="settings-display-name" class="form-input" maxlength="50"> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="settings-username"> | |
| Username <span class="label-hint">(cannot be changed)</span> | |
| </label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="settings-username" class="form-input" disabled> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="settings-bio">Bio <span class="label-hint">(shown on your social profile)</span></label> | |
| <div class="input-wrapper"> | |
| <textarea id="settings-bio" class="form-input" maxlength="200" rows="2" placeholder="Tell people about yourself"></textarea> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="settings-location">Location</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="settings-location" class="form-input" maxlength="80" placeholder="City, region"> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="settings-website">Website</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="settings-website" class="form-input" maxlength="160" placeholder="https://example.com"> | |
| </div> | |
| </div> | |
| </section> | |
| <section class="settings-section"> | |
| <h3>Account</h3> | |
| <div class="form-group"> | |
| <label for="pw-current">Current password</label> | |
| <div class="input-wrapper"> | |
| <input type="password" id="pw-current" class="form-input" | |
| autocomplete="current-password" placeholder="••••••••"> | |
| <button type="button" class="input-toggle" data-toggle="pw-current"> | |
| <i class="fas fa-eye"></i> | |
| </button> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="pw-new">New password</label> | |
| <div class="input-wrapper"> | |
| <input type="password" id="pw-new" class="form-input" minlength="6" | |
| autocomplete="new-password" placeholder="At least 6 characters"> | |
| <button type="button" class="input-toggle" data-toggle="pw-new"> | |
| <i class="fas fa-eye"></i> | |
| </button> | |
| </div> | |
| </div> | |
| <button id="pw-change-btn" class="btn btn-secondary btn-sm"> | |
| <i class="fas fa-key"></i> Change Password | |
| </button> | |
| <span id="pw-msg" class="form-hint"></span> | |
| </section> | |
| <section class="settings-section"> | |
| <h3>Privacy</h3> | |
| <button id="refresh-blocks-btn" class="btn btn-secondary btn-sm"> | |
| <i class="fas fa-ban"></i> Refresh Blocked Users | |
| </button> | |
| <div id="blocked-users-list" class="blocked-users-list"></div> | |
| </section> | |
| <section class="settings-section"> | |
| <h3>Appearance</h3> | |
| <div class="form-group"> | |
| <label>Theme</label> | |
| <div class="theme-selector"> | |
| <button class="theme-option active" data-theme="light"> | |
| <div class="theme-preview theme-preview-light"> | |
| <div class="theme-preview-header"></div> | |
| <div class="theme-preview-body"> | |
| <div class="theme-preview-message self"></div> | |
| <div class="theme-preview-message other"></div> | |
| </div> | |
| </div> | |
| <span>Light</span> | |
| </button> | |
| <button class="theme-option" data-theme="dark"> | |
| <div class="theme-preview theme-preview-dark"> | |
| <div class="theme-preview-header"></div> | |
| <div class="theme-preview-body"> | |
| <div class="theme-preview-message self"></div> | |
| <div class="theme-preview-message other"></div> | |
| </div> | |
| </div> | |
| <span>Dark</span> | |
| </button> | |
| <button class="theme-option" data-theme="custom"> | |
| <div class="theme-preview theme-preview-custom"> | |
| <div class="theme-preview-header"></div> | |
| <div class="theme-preview-body"> | |
| <div class="theme-preview-message self"></div> | |
| <div class="theme-preview-message other"></div> | |
| </div> | |
| </div> | |
| <span>Custom</span> | |
| </button> | |
| <button class="theme-option" data-theme="midnight"> | |
| <div class="theme-preview theme-preview-midnight"> | |
| <div class="theme-preview-header"></div> | |
| <div class="theme-preview-body"> | |
| <div class="theme-preview-message self"></div> | |
| <div class="theme-preview-message other"></div> | |
| </div> | |
| </div> | |
| <span>Midnight</span> | |
| </button> | |
| <button class="theme-option" data-theme="ocean"> | |
| <div class="theme-preview theme-preview-ocean"> | |
| <div class="theme-preview-header"></div> | |
| <div class="theme-preview-body"> | |
| <div class="theme-preview-message self"></div> | |
| <div class="theme-preview-message other"></div> | |
| </div> | |
| </div> | |
| <span>Ocean</span> | |
| </button> | |
| <button class="theme-option" data-theme="sunset"> | |
| <div class="theme-preview theme-preview-sunset"> | |
| <div class="theme-preview-header"></div> | |
| <div class="theme-preview-body"> | |
| <div class="theme-preview-message self"></div> | |
| <div class="theme-preview-message other"></div> | |
| </div> | |
| </div> | |
| <span>Sunset</span> | |
| </button> | |
| </div> | |
| </div> | |
| <div id="custom-theme-settings" class="custom-theme-section hidden"> | |
| <div class="color-picker-row"> | |
| <div class="color-picker-group"> | |
| <label>Your Messages</label> | |
| <div class="color-input-wrapper"> | |
| <input type="color" id="custom-self-color" value="#2563EB"> | |
| <span class="color-hex" id="self-color-hex">#2563EB</span> | |
| </div> | |
| </div> | |
| <div class="color-picker-group"> | |
| <label>Their Messages</label> | |
| <div class="color-input-wrapper"> | |
| <input type="color" id="custom-other-color" value="#F3F4F6"> | |
| <span class="color-hex" id="other-color-hex">#F3F4F6</span> | |
| </div> | |
| </div> | |
| <div class="color-picker-group"> | |
| <label>Text Color</label> | |
| <div class="color-input-wrapper"> | |
| <input type="color" id="custom-text-color" value="#111827"> | |
| <span class="color-hex" id="text-color-hex">#111827</span> | |
| </div> | |
| </div> | |
| </div> | |
| </div> | |
| </section> | |
| <section class="settings-section"> | |
| <h3>Behaviour</h3> | |
| <div class="settings-toggle-row"> | |
| <div> | |
| <label for="toggle-autoscroll">Auto-scroll to bottom</label> | |
| <div class="toggle-hint">Automatically scroll down when new messages arrive</div> | |
| </div> | |
| <label class="toggle-switch"> | |
| <input type="checkbox" id="toggle-autoscroll"> | |
| <span class="toggle-slider"></span> | |
| </label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div> | |
| <label for="toggle-scroll-btn">Show scroll-to-bottom button</label> | |
| <div class="toggle-hint">Show arrow button when not at bottom</div> | |
| </div> | |
| <label class="toggle-switch"> | |
| <input type="checkbox" id="toggle-scroll-btn" checked> | |
| <span class="toggle-slider"></span> | |
| </label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div> | |
| <label for="toggle-latest-bar">Show latest message bar</label> | |
| <div class="toggle-hint">Show new message preview when scrolled up</div> | |
| </div> | |
| <label class="toggle-switch"> | |
| <input type="checkbox" id="toggle-latest-bar" checked> | |
| <span class="toggle-slider"></span> | |
| </label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div> | |
| <label for="toggle-sound">Notification sound</label> | |
| <div class="toggle-hint">Play a soft sound for new messages</div> | |
| </div> | |
| <label class="toggle-switch"> | |
| <input type="checkbox" id="toggle-sound" checked> | |
| <span class="toggle-slider"></span> | |
| </label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div> | |
| <label for="toggle-enter-send">Enter to send</label> | |
| <div class="toggle-hint">Press Enter to send, Shift+Enter for a new line</div> | |
| </div> | |
| <label class="toggle-switch"> | |
| <input type="checkbox" id="toggle-enter-send" checked> | |
| <span class="toggle-slider"></span> | |
| </label> | |
| </div> | |
| <div class="settings-toggle-row"> | |
| <div> | |
| <label>Desktop notifications</label> | |
| <div class="toggle-hint">Browser pop-ups for new messages</div> | |
| </div> | |
| <button id="notify-perm-btn" class="btn btn-secondary btn-sm"> | |
| <i class="fas fa-bell"></i> Enable | |
| </button> | |
| </div> | |
| </section> | |
| <section class="settings-section"> | |
| <h3>About</h3> | |
| <div class="about-info"> | |
| <div class="about-row"> | |
| <span>Version</span> | |
| <span class="text-secondary" id="about-version">3.0.0</span> | |
| </div> | |
| <div class="about-row"> | |
| <span>Encryption</span> | |
| <span class="text-success"> | |
| <i class="fas fa-shield-alt"></i> AES-256-GCM | |
| </span> | |
| </div> | |
| <div class="about-row"> | |
| <span>Private chats</span> | |
| <span class="text-secondary">Up to 3 per person</span> | |
| </div> | |
| <div class="about-row"> | |
| <span>Storage</span> | |
| <span class="text-secondary">HF Xet Buckets</span> | |
| </div> | |
| </div> | |
| </section> | |
| </div> | |
| <div class="modal-footer"> | |
| <button class="btn btn-ghost" data-close="settings-modal">Cancel</button> | |
| <button id="save-settings" class="btn btn-primary"> | |
| <i class="fas fa-check"></i> Save Changes | |
| </button> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Online Modal --> | |
| <div id="online-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="online-modal"></div> | |
| <div class="modal-container modal-sm"> | |
| <div class="modal-header"> | |
| <h2><i class="fas fa-users"></i> Online Users</h2> | |
| <button class="btn-icon" data-close="online-modal"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div id="online-users-list" class="online-users-list"></div> | |
| <div class="modal-footer"> | |
| <span id="online-total" class="text-secondary">0 users online</span> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Start private chat modal --> | |
| <div id="conv-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="conv-modal"></div> | |
| <div class="modal-container modal-sm"> | |
| <div class="modal-header"> | |
| <h2><i class="fas fa-user-lock"></i> Private Chats</h2> | |
| <button class="btn-icon" data-close="conv-modal"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div class="modal-body"> | |
| <p class="conv-modal-desc" id="conv-modal-desc">Chat privately with <strong>…</strong></p> | |
| <input type="search" id="conv-user-search" class="form-input hidden" placeholder="Search by name or username…" autocomplete="off"> | |
| <div id="conv-modal-list" class="conv-modal-list"></div> | |
| </div> | |
| <div class="modal-footer"> | |
| <button class="btn btn-ghost" data-close="conv-modal">Cancel</button> | |
| <button id="new-chat-btn" class="btn btn-primary"> | |
| <i class="fas fa-plus"></i> Start New Chat | |
| </button> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Group creation modal --> | |
| <div id="group-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="group-modal"></div> | |
| <div class="modal-container modal-md"> | |
| <div class="modal-header"> | |
| <h2><i class="fas fa-people-group"></i> New Group Chat</h2> | |
| <button class="btn-icon" data-close="group-modal"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div class="modal-body"> | |
| <div class="form-group"> | |
| <label for="group-name-input">Group name</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="group-name-input" class="form-input" maxlength="60" | |
| placeholder="e.g. Weekend Plans"> | |
| </div> | |
| </div> | |
| <div class="form-group"> | |
| <label for="group-user-search">Add people</label> | |
| <div class="input-wrapper"> | |
| <input type="text" id="group-user-search" class="form-input" | |
| placeholder="Search by name…"> | |
| </div> | |
| </div> | |
| <div id="group-user-results" class="conv-modal-list"></div> | |
| <div id="group-selected-list" class="group-selected-list"></div> | |
| </div> | |
| <div class="modal-footer"> | |
| <button class="btn btn-ghost" data-close="group-modal">Cancel</button> | |
| <button id="create-group-btn" class="btn btn-primary"> | |
| <i class="fas fa-plus"></i> Create Group | |
| </button> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Conversation options modal --> | |
| <div id="conv-options-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="conv-options-modal"></div> | |
| <div class="modal-container modal-sm"> | |
| <div class="modal-header"> | |
| <h2 id="conv-options-title"><i class="fas fa-ellipsis-h"></i> Chat Options</h2> | |
| <button class="btn-icon" data-close="conv-options-modal"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div class="modal-body conv-options-body"> | |
| <button id="rename-conv-btn" class="btn btn-secondary btn-block"> | |
| <i class="fas fa-pen"></i> Rename Chat | |
| </button> | |
| <button id="add-group-members-btn" class="btn btn-secondary btn-block"> | |
| <i class="fas fa-user-plus"></i> Add Members | |
| </button> | |
| <button id="delete-conv-btn" class="btn btn-danger btn-block"> | |
| <i class="fas fa-eye-slash"></i> Delete Private Chat | |
| </button> | |
| <button id="block-conv-user-btn" class="btn btn-danger btn-block"> | |
| <i class="fas fa-ban"></i> Block Person | |
| </button> | |
| <button id="leave-conv-btn" class="btn btn-danger btn-block"> | |
| <i class="fas fa-sign-out-alt"></i> Leave/Delete Group | |
| </button> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Read receipts modal --> | |
| <div id="receipts-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="receipts-modal"></div> | |
| <div class="modal-container modal-sm"> | |
| <div class="modal-header"> | |
| <h2><i class="fas fa-check-double"></i> Read Receipts</h2> | |
| <button class="btn-icon" data-close="receipts-modal"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div class="modal-body"> | |
| <p id="receipts-summary" class="receipts-summary"></p> | |
| <div id="receipts-list" class="receipts-list"></div> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Confirmation dialog (replaces blocking confirm()) --> | |
| <div id="confirm-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="confirm-modal"></div> | |
| <div class="modal-container modal-sm"> | |
| <div class="modal-header"> | |
| <h2 id="confirm-title"><i class="fas fa-question-circle"></i> Confirm</h2> | |
| <button class="btn-icon" data-close="confirm-modal"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| <div class="modal-body"> | |
| <p id="confirm-message" class="confirm-message"></p> | |
| </div> | |
| <div class="modal-footer"> | |
| <button class="btn btn-ghost" id="confirm-cancel-btn">Cancel</button> | |
| <button class="btn btn-primary" id="confirm-ok-btn">OK</button> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Image lightbox --> | |
| <div id="lightbox-modal" class="modal hidden"> | |
| <div class="modal-backdrop" data-close="lightbox-modal"></div> | |
| <div class="lightbox-container"> | |
| <div class="lightbox-header"> | |
| <span id="lightbox-name" class="lightbox-name"></span> | |
| <div> | |
| <a id="lightbox-download" class="btn-icon lightbox-btn" target="_blank" rel="noopener" title="Open original"> | |
| <i class="fas fa-external-link-alt"></i> | |
| </a> | |
| <button class="btn-icon lightbox-btn" data-close="lightbox-modal" aria-label="Close"> | |
| <i class="fas fa-times"></i> | |
| </button> | |
| </div> | |
| </div> | |
| <img id="lightbox-img" class="lightbox-img" alt="Preview"> | |
| </div> | |
| </div> | |
| <!-- Emoji Picker --> | |
| <div id="emoji-picker" class="emoji-picker hidden"> | |
| <div class="emoji-header"> | |
| <div class="emoji-categories"> | |
| <button class="emoji-cat active" data-cat="smileys"><i class="fas fa-smile"></i></button> | |
| <button class="emoji-cat" data-cat="people"><i class="fas fa-user"></i></button> | |
| <button class="emoji-cat" data-cat="animals"><i class="fas fa-dog"></i></button> | |
| <button class="emoji-cat" data-cat="food"><i class="fas fa-utensils"></i></button> | |
| <button class="emoji-cat" data-cat="activities"><i class="fas fa-futbol"></i></button> | |
| <button class="emoji-cat" data-cat="objects"><i class="fas fa-lightbulb"></i></button> | |
| <button class="emoji-cat" data-cat="symbols"><i class="fas fa-heart"></i></button> | |
| <button class="emoji-cat" data-cat="flags"><i class="fas fa-flag"></i></button> | |
| </div> | |
| </div> | |
| <div id="emoji-grid" class="emoji-grid"></div> | |
| </div> | |
| <div id="toast-container" class="toast-container"></div> | |
| <script src="/static/script.js?v=11"></script> | |
| </body> | |
| </html> |