   {% extends "base.html" %}
{% block title %}社区论坛 - 智联青云{% endblock %}
{% block content %}
<style>
.forum-grid{display:grid;grid-template-columns:1fr 280px;gap:20px}
@media(max-width:1024px){.forum-grid{grid-template-columns:1fr}}
.toast{position:fixed;top:20px;right:20px;z-index:9999;padding:12px 20px;border-radius:8px;color:#fff;font-size:14px;animation:slideIn .3s ease;box-shadow:0 4px 12px rgba(0,0,0,.15)}
.toast-success{background:#10b981}.toast-error{background:#ef4444}.toast-info{background:#3b82f6}
@keyframes slideIn{from{transform:translateX(100%);opacity:0}to{transform:translateX(0);opacity:1}}
.reaction-btn{transition:all .2s;cursor:pointer;padding:2px 8px;border-radius:20px;border:1px solid #e2e8f0;font-size:13px;display:inline-flex;align-items:center;gap:3px}
.reaction-btn:hover{transform:scale(1.15);border-color:#93c5fd;background:#eff6ff}
.reaction-btn.active{background:#dbeafe;border-color:#60a5fa}
.poll-bar{height:28px;border-radius:6px;background:#f1f5f9;overflow:hidden;position:relative;margin:4px 0}
.poll-fill{height:100%;border-radius:6px;background:linear-gradient(90deg,#3b82f6,#60a5fa);transition:width .6s ease;display:flex;align-items:center;padding:0 10px;font-size:12px;color:#fff;font-weight:500;min-width:fit-content}
.poll-bar.voted .poll-fill{background:linear-gradient(90deg,#10b981,#34d399)}
.stat-card{border-radius:12px;padding:14px;color:#fff}
.stat-card.blue{background:linear-gradient(135deg,#3b82f6,#2563eb)}
.stat-card.green{background:linear-gradient(135deg,#10b981,#059669)}
.stat-card.orange{background:linear-gradient(135deg,#f59e0b,#d97706)}
.stat-card.purple{background:linear-gradient(135deg,#8b5cf6,#7c3aed)}
.level-badge{display:inline-flex;align-items:center;gap:2px;padding:1px 6px;border-radius:10px;font-size:11px;font-weight:600}
.level-1,.level-2{background:#e2e8f0;color:#64748b}
.level-3,.level-4{background:#dbeafe;color:#2563eb}
.level-5,.level-6{background:#d1fae5;color:#059669}
.level-7,.level-8{background:#fef3c7;color:#d97706}
.level-9,.level-10{background:#fce7f3;color:#db2777}
.tab-pill{padding:6px 16px;border-radius:20px;font-size:13px;font-weight:500;cursor:pointer;transition:all .2s;border:1px solid transparent}
.tab-pill.active{background:#3b82f6;color:#fff;border-color:#3b82f6}
.tab-pill:not(.active){background:#f1f5f9;color:#64748b;border-color:#e2e8f0}
.tab-pill:not(.active):hover{background:#e2e8f0;color:#334155}
.post-card{transition:all .2s;border:1px solid #e2e8f0;border-radius:12px;background:#fff}
.post-card:hover{border-color:#93c5fd;box-shadow:0 4px 12px rgba(59,130,246,.08)}
.modal-overlay{position:fixed;inset:0;background:rgba(0,0,0,.5);z-index:9990;display:flex;align-items:flex-start;justify-content:center;padding:40px 16px;overflow-y:auto;backdrop-filter:blur(2px)}
.modal-content{background:#fff;border-radius:16px;width:100%;max-width:720px;box-shadow:0 20px 60px rgba(0,0,0,.2);animation:modalIn .25s ease}
@keyframes modalIn{from{transform:translateY(20px);opacity:0}to{transform:translateY(0);opacity:1}}
.hot-item{display:flex;align-items:flex-start;gap:8px;padding:8px 0;border-bottom:1px solid #f1f5f9;cursor:pointer}
.hot-item:last-child{border-bottom:none}
.hot-rank{width:20px;height:20px;border-radius:4px;display:flex;align-items:center;justify-content:center;font-size:11px;font-weight:700;flex-shrink:0;margin-top:2px}
.hot-rank.r1{background:#ef4444;color:#fff}.hot-rank.r2{background:#f97316;color:#fff}.hot-rank.r3{background:#eab308;color:#fff}
.hot-rank:not(.r1):not(.r2):not(.r3){background:#f1f5f9;color:#94a3b8}
</style>

<div class="forum-grid">
<div class="space-y-6">
    <!-- 统计卡片 -->
    <div class="grid grid-cols-2 lg:grid-cols-4 gap-4">
        <div class="bg-gradient-to-br from-blue-500 to-blue-600 rounded-2xl p-5 text-white shadow-sm relative overflow-hidden group">
            <div class="absolute -right-4 -top-4 w-24 h-24 bg-white/10 rounded-full blur-xl group-hover:bg-white/20 transition-colors"></div>
            <div class="relative z-10">
                <div class="text-3xl font-bold mb-1" id="s-posts">0</div>
                <div class="text-sm text-blue-100 flex items-center">
                    <svg class="w-4 h-4 mr-1.5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M19 11H5m14 0a2 2 0 012 2v6a2 2 0 01-2 2H5a2 2 0 01-2-2v-6a2 2 0 012-2m14 0V9a2 2 0 00-2-2M5 11V9a2 2 0 002-2m0 0V5a2 2 0 012-2h6a2 2 0 012 2v2M7 7h10"/></svg>
                    总帖子数
                </div>
            </div>
        </div>
        <div class="bg-gradient-to-br from-emerald-500 to-emerald-600 rounded-2xl p-5 text-white shadow-sm relative overflow-hidden group">
            <div class="absolute -right-4 -top-4 w-24 h-24 bg-white/10 rounded-full blur-xl group-hover:bg-white/20 transition-colors"></div>
            <div class="relative z-10">
                <div class="text-3xl font-bold mb-1" id="s-replies">0</div>
                <div class="text-sm text-emerald-100 flex items-center">
                    <svg class="w-4 h-4 mr-1.5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 12h.01M12 12h.01M16 12h.01M21 12c0 4.418-4.03 8-9 8a9.863 9.863 0 01-4.255-.949L3 20l1.395-3.72C3.512 15.042 3 13.574 3 12c0-4.418 4.03-8 9-8s9 3.582 9 8z"/></svg>
                    总回复数
                </div>
            </div>
        </div>
        <div class="bg-gradient-to-br from-orange-500 to-orange-600 rounded-2xl p-5 text-white shadow-sm relative overflow-hidden group">
            <div class="absolute -right-4 -top-4 w-24 h-24 bg-white/10 rounded-full blur-xl group-hover:bg-white/20 transition-colors"></div>
            <div class="relative z-10">
                <div class="text-3xl font-bold mb-1" id="s-today">0</div>
                <div class="text-sm text-orange-100 flex items-center">
                    <svg class="w-4 h-4 mr-1.5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4l3 3m6-3a9 9 0 11-18 0 9 9 0 0118 0z"/></svg>
                    今日新帖
                </div>
            </div>
        </div>
        <div class="bg-gradient-to-br from-violet-500 to-violet-600 rounded-2xl p-5 text-white shadow-sm relative overflow-hidden group">
            <div class="absolute -right-4 -top-4 w-24 h-24 bg-white/10 rounded-full blur-xl group-hover:bg-white/20 transition-colors"></div>
            <div class="relative z-10">
                <div class="flex items-center mb-1">
                    <span class="relative flex h-3 w-3 mr-2">
                        <span class="animate-ping absolute inline-flex h-full w-full rounded-full bg-white opacity-75"></span>
                        <span class="relative inline-flex rounded-full h-3 w-3 bg-white"></span>
                    </span>
                    <div class="text-3xl font-bold" id="s-online">0</div>
                </div>
                <div class="text-sm text-violet-100 flex items-center">
                    <svg class="w-4 h-4 mr-1.5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 4.354a4 4 0 110 5.292M15 21H3v-1a6 6 0 0112 0v1zm0 0h6v-1a6 6 0 00-9-5.197M13 7a4 4 0 11-8 0 4 4 0 018 0z"/></svg>
                    当前在线人数
                </div>
            </div>
        </div>
    </div>

    <!-- 头部操作区: 高级毛玻璃渐变 -->
    <div class="relative flex flex-col sm:flex-row justify-between items-start sm:items-center gap-4 bg-gradient-to-r from-indigo-600 to-purple-600 p-8 rounded-3xl shadow-xl border border-indigo-500 overflow-hidden text-white">
        <div class="absolute top-0 right-0 w-64 h-64 bg-white/10 blur-3xl rounded-full translate-x-1/2 -translate-y-1/2"></div>
        <div class="absolute -bottom-10 -left-10 w-40 h-40 bg-purple-500/20 blur-2xl rounded-full"></div>
        
        <div class="relative z-10">
            <h1 class="text-3xl font-extrabold flex items-center drop-shadow-md">
                <span class="w-12 h-12 bg-white/20 backdrop-blur-md text-white rounded-2xl flex items-center justify-center mr-4 shadow-inner border border-white/20">💬</span>
                社区论坛
            </h1>
            <p class="text-indigo-100 text-base mt-2 ml-16 opacity-90">分享经验、交流问题、结识志同道合的学习伙伴。</p>
        </div>
        <div class="relative z-10 flex flex-wrap items-center gap-3">
            {% if user %}
            <button onclick="showLeaderboard()" class="p-3 bg-white/10 hover:bg-white/20 text-white backdrop-blur-md rounded-2xl transition-all border border-white/20 hover:border-white/40 shadow-lg transform hover:-translate-y-1" title="排行榜">
                <svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M13 10V3L4 14h7v7l9-11h-7z"/></svg>
            </button>
            <button onclick="showBookmarks()" class="p-3 bg-white/10 hover:bg-white/20 text-yellow-300 backdrop-blur-md rounded-2xl transition-all border border-white/20 hover:border-yellow-300/50 shadow-lg transform hover:-translate-y-1" title="我的收藏">
                <svg class="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 5a2 2 0 012-2h10a2 2 0 012 2v16l-7-3.5L5 21V5z"/></svg>
            </button>
            <button onclick="openNewPost()" class="flex items-center gap-2 px-6 py-3 bg-white text-indigo-600 rounded-2xl hover:bg-indigo-50 text-sm font-bold shadow-xl transition-all transform hover:-translate-y-1 hover:scale-105">
                <svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15.232 5.232l3.536 3.536m-2.036-5.036a2.5 2.5 0 113.536 3.536L6.5 21.036H3v-3.572L16.732 3.732z"/></svg>
                发布新帖
            </button>
            {% else %}
            <a href="/login" class="px-6 py-3 bg-white text-indigo-600 rounded-2xl hover:bg-indigo-50 text-sm font-bold shadow-xl transition-all transform hover:-translate-y-1 hover:scale-105">登录后发帖</a>
            {% endif %}
        </div>
    </div>

    <!-- 搜索和分类 -->
    <div class="bg-white p-5 rounded-2xl shadow-sm border border-slate-100 sticky top-20 z-10 glass-panel">
        <div class="flex flex-col lg:flex-row gap-4 justify-between items-start lg:items-center">
            <!-- 分类标签 -->
            <div class="flex flex-wrap gap-2" id="tab-nav">
                <button onclick="filterTab('全部')" class="tab-pill active" data-tab="全部">📋 全部</button>
                <button onclick="filterTab('官方公告')" class="tab-pill" data-tab="官方公告">📢 公告</button>
                <button onclick="filterTab('题目讨论')" class="tab-pill" data-tab="题目讨论">📐 讨论</button>
                <button onclick="filterTab('经验分享')" class="tab-pill" data-tab="经验分享">💡 分享</button>
                <button onclick="filterTab('求助答疑')" class="tab-pill" data-tab="求助答疑">🙋 求助</button>
                <button onclick="filterTab('闲聊灌水')" class="tab-pill" data-tab="闲聊灌水">☕ 闲聊</button>
            </div>
            
            <!-- 搜索框 -->
            <div class="flex items-center gap-3 w-full lg:w-auto">
                <div class="relative w-full sm:w-64">
                    <div class="absolute inset-y-0 left-0 pl-3 flex items-center pointer-events-none">
                        <svg class="h-4 w-4 text-slate-400" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M21 21l-6-6m2-5a7 7 0 11-14 0 7 7 0 0114 0z"/></svg>
                    </div>
                    <input type="text" id="search-input" placeholder="搜索帖子内容..." class="w-full pl-10 pr-4 py-2 border border-slate-200 rounded-xl text-sm focus:outline-none focus:ring-2 focus:ring-primary/20 focus:border-primary bg-slate-50 transition-all" onkeydown="if(event.key==='Enter')loadPosts()">
                </div>
                <div class="relative">
                    <select id="sort-select" onchange="loadPosts()" class="appearance-none pl-9 pr-8 py-2 border border-slate-200 rounded-xl text-sm focus:outline-none focus:ring-2 focus:ring-primary/20 focus:border-primary bg-slate-50 hover:bg-slate-100 transition-colors cursor-pointer">
                        <option value="newest">最新发布</option>
                        <option value="hottest">热度最高</option>
                        <option value="most_replies">最多回复</option>
                    </select>
                    <div class="absolute inset-y-0 left-0 pl-3 flex items-center pointer-events-none">
                        <svg class="h-4 w-4 text-slate-400" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M3 4h13M3 8h9m-9 4h6m4 0l4-4m0 0l4 4m-4-4v12"/></svg>
                    </div>
                    <div class="absolute inset-y-0 right-0 pr-2 flex items-center pointer-events-none">
                        <svg class="h-4 w-4 text-slate-400" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M19 9l-7 7-7-7"/></svg>
                    </div>
                </div>
                <button onclick="loadPosts()" class="px-4 py-2 bg-slate-800 text-white rounded-xl hover:bg-slate-700 text-sm font-medium transition-colors shadow-sm hidden sm:block">
                    搜索
                </button>
            </div>
        </div>
    </div>
    
    <!-- 帖子列表 -->
    <div id="post-list" class="space-y-4">
        <!-- 骨架屏加载状态 -->
        <div class="bg-white p-6 rounded-2xl border border-slate-100 shadow-sm animate-pulse">
            <div class="flex items-start gap-4">
                <div class="w-10 h-10 bg-slate-200 rounded-full"></div>
                <div class="flex-1 space-y-3">
                    <div class="h-4 bg-slate-200 rounded w-1/4"></div>
                    <div class="h-5 bg-slate-200 rounded w-3/4"></div>
                    <div class="h-4 bg-slate-200 rounded w-full"></div>
                    <div class="h-4 bg-slate-200 rounded w-5/6"></div>
                    <div class="flex gap-4 pt-2">
                        <div class="h-3 bg-slate-200 rounded w-12"></div>
                        <div class="h-3 bg-slate-200 rounded w-12"></div>
                    </div>
                </div>
            </div>
        </div>
    </div>
</div>

<!-- 右侧边栏 -->
<div class="space-y-6 hidden lg:block">
    <div class="bg-white rounded-2xl shadow-sm border border-slate-100 overflow-hidden">
        <div class="bg-gradient-to-r from-red-50 to-orange-50 px-5 py-4 border-b border-red-100">
            <h3 class="text-sm font-bold text-red-700 flex items-center">
                <svg class="w-4 h-4 mr-1.5 text-red-500" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M17.657 18.657A8 8 0 016.343 7.343S7 9 9 10c0-2 .5-5 2.986-7C14 5 16.09 5.777 17.656 7.343A7.975 7.975 0 0120 13a7.975 7.975 0 01-2.343 5.657z"/><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9.879 16.121A3 3 0 1012.015 11L11 14H9c0 .768.293 1.536.879 2.121z"/></svg>
                热门讨论
            </h3>
        </div>
        <div class="p-2" id="hot-posts">
            <div class="p-4 text-center text-sm text-slate-400 animate-pulse">加载中...</div>
        </div>
    </div>

    <div class="bg-white rounded-2xl shadow-sm border border-slate-100 overflow-hidden">
        <div class="bg-gradient-to-r from-blue-50 to-indigo-50 px-5 py-4 border-b border-blue-100">
            <h3 class="text-sm font-bold text-blue-700 flex items-center">
                <svg class="w-4 h-4 mr-1.5 text-blue-500" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 4.354a4 4 0 110 5.292M15 21H3v-1a6 6 0 0112 0v1zm0 0h6v-1a6 6 0 00-9-5.197M13 7a4 4 0 11-8 0 4 4 0 018 0z"/></svg>
                活跃用户
            </h3>
        </div>
        <div class="p-2" id="active-users">
            <div class="p-4 text-center text-sm text-slate-400 animate-pulse">加载中...</div>
        </div>
    </div>

    <div class="bg-white rounded-2xl shadow-sm border border-slate-100 overflow-hidden sticky top-20">
        <div class="bg-gradient-to-r from-slate-50 to-gray-50 px-5 py-4 border-b border-slate-100">
            <h3 class="text-sm font-bold text-slate-700 flex items-center">
                <svg class="w-4 h-4 mr-1.5 text-slate-500" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M7 7h.01M7 3h5c.512 0 1.024.195 1.414.586l7 7a2 2 0 010 2.828l-7 7a2 2 0 01-2.828 0l-7-7A1.994 1.994 0 013 12V7a4 4 0 014-4z"/></svg>
                版块统计
            </h3>
        </div>
        <div class="p-4" id="tag-stats">
            <div class="text-center text-sm text-slate-400 animate-pulse">加载中...</div>
        </div>
    </div>
</div>
</div>

<!-- 发帖弹窗 -->
<div id="new-post-modal" class="hidden"><div class="modal-overlay" onclick="if(event.target===this)closeNewPost()"><div class="modal-content p-6">
    <div class="flex justify-between items-center mb-5">
        <h2 class="text-xl font-bold">✏️ 发布新帖</h2>
        <button onclick="closeNewPost()" class="text-slate-400 hover:text-slate-600 text-xl">✕</button>
    </div>
    <div class="space-y-4">
        <div><label class="block text-sm font-medium text-slate-700 mb-1">标题</label>
            <input id="new-title" type="text" maxlength="100" class="w-full px-3 py-2.5 border border-slate-200 rounded-lg text-sm" placeholder="请输入标题"></div>
        <div class="flex gap-3">
            <div class="flex-1"><label class="block text-sm font-medium text-slate-700 mb-1">分类</label>
                <select id="new-tag" class="w-full px-3 py-2.5 border border-slate-200 rounded-lg text-sm">
                    <option>题目讨论</option><option>经验分享</option><option>求助答疑</option><option>闲聊灌水</option>
                    {% if user and user.role == 'teacher' %}<option>官方公告</option>{% endif %}
                </select></div>
            {% if user and user.role == 'teacher' %}
            <div class="flex items-end pb-1"><label class="flex items-center gap-2 text-sm"><input type="checkbox" id="new-official" class="rounded"> 官方公告</label></div>
            {% endif %}
        </div>
        <div><label class="block text-sm font-medium text-slate-700 mb-1">内容</label>
            <div class="border border-slate-200 rounded-lg overflow-hidden">
                <textarea id="new-content" rows="8" class="w-full px-3 py-2.5 text-sm border-0 focus:outline-none resize-y" placeholder="畅所欲言..."></textarea>
                <div id="new-content-preview" class="flex flex-wrap gap-2 px-3 py-2 border-t border-slate-100 hidden"></div>
            </div></div>
        <div><label class="flex items-center gap-2 text-sm font-medium text-slate-700 cursor-pointer mb-2">
                <input type="checkbox" id="enable-poll" onchange="togglePoll()" class="rounded"> 📊 添加投票</label>
            <div id="poll-section" class="hidden space-y-3 p-4 bg-blue-50 rounded-lg border border-blue-100">
                <input id="poll-question" type="text" class="w-full px-3 py-2 border border-blue-200 rounded-lg text-sm bg-white" placeholder="投票问题">
                <div id="poll-options" class="space-y-2">
                    <input type="text" class="poll-opt w-full px-3 py-2 border border-blue-200 rounded-lg text-sm bg-white" placeholder="选项 1">
                    <input type="text" class="poll-opt w-full px-3 py-2 border border-blue-200 rounded-lg text-sm bg-white" placeholder="选项 2">
                </div>
                <div class="flex items-center gap-3">
                    <button onclick="addPollOpt()" class="text-sm text-primary hover:text-blue-700 font-medium">+ 添加选项</button>
                    <label class="flex items-center gap-1.5 text-sm"><input type="checkbox" id="poll-multi" class="rounded"> 允许多选</label>
                </div>
            </div></div>
        <div class="flex justify-end gap-3 pt-2">
            <button onclick="closeNewPost()" class="px-5 py-2.5 text-sm text-slate-600 border border-slate-200 rounded-lg hover:bg-slate-50">取消</button>
            <button onclick="submitPost()" class="px-6 py-2.5 bg-primary text-white rounded-lg text-sm font-medium hover:bg-blue-700">发布帖子</button>
        </div>
    </div>
</div></div></div>

<!-- 帖子详情弹窗 -->
<div id="post-modal" class="hidden"><div class="modal-overlay" onclick="if(event.target===this)closePostModal()">
<div class="modal-content" id="post-modal-content"></div>
</div></div>

<!-- 举报弹窗 -->
<div id="report-modal" class="hidden"><div class="modal-overlay" onclick="if(event.target===this)closeReport()"><div class="modal-content p-6 max-w-md">
    <h3 class="text-lg font-bold mb-4">🚩 举报</h3>
    <input type="hidden" id="report-type"><input type="hidden" id="report-target-id">
    <div class="space-y-3">
        <select id="report-reason" class="w-full px-3 py-2 border border-slate-200 rounded-lg text-sm">
            <option>垃圾广告</option><option>不当言论</option><option>抄袭内容</option><option>人身攻击</option><option>其他</option></select>
        <textarea id="report-detail" rows="3" class="w-full px-3 py-2 border border-slate-200 rounded-lg text-sm" placeholder="补充说明（可选）"></textarea>
        <div class="flex justify-end gap-3">
            <button onclick="closeReport()" class="px-4 py-2 text-sm border border-slate-200 rounded-lg hover:bg-slate-50">取消</button>
            <button onclick="submitReport()" class="px-5 py-2 bg-red-500 text-white rounded-lg text-sm hover:bg-red-600">提交举报</button>
        </div>
    </div>
</div></div></div>

<!-- 排行榜弹窗 -->
<div id="leaderboard-modal" class="hidden"><div class="modal-overlay" onclick="if(event.target===this)document.getElementById('leaderboard-modal').classList.add('hidden')"><div class="modal-content p-6 max-w-lg">
    <div class="flex justify-between items-center mb-5">
        <h2 class="text-xl font-bold">🏆 积分排行榜</h2>
        <button onclick="document.getElementById('leaderboard-modal').classList.add('hidden')" class="text-slate-400 hover:text-slate-600 text-xl">✕</button>
    </div>
    <div id="lb-content"></div>
</div></div></div>

<!-- 用户资料弹窗 -->
<div id="profile-modal" class="hidden"><div class="modal-overlay" onclick="if(event.target===this)document.getElementById('profile-modal').classList.add('hidden')"><div class="modal-content p-6 max-w-lg">
    <div id="profile-content"></div>
</div></div></div>
{% endblock %}

{% block scripts %}
<script>
const CU = {{ user | tojson if user else 'null' }};
let curTag = '全部';
const REACTIONS = {like:'👍',love:'❤️',haha:'😂',wow:'😮',sad:'😢',angry:'😡'};
const TAG_ICONS = {'官方公告':'📢','题目讨论':'📐','经验分享':'💡','求助答疑':'🙋','闲聊灌水':'☕'};
const TAG_COLORS = {'官方公告':'red','题目讨论':'blue','经验分享':'green','求助答疑':'yellow','闲聊灌水':'purple'};

function toast(msg, type='success') {
    const d = document.createElement('div');
    d.className = `toast toast-${type}`;
    d.textContent = msg;
    document.body.appendChild(d);
    setTimeout(() => { d.style.animation = 'fadeOut .3s ease forwards'; setTimeout(() => d.remove(), 300); }, 2500);
}

function esc(s) { const d = document.createElement('div'); d.textContent = s; return d.innerHTML; }

// ===== 发帖 =====
function openNewPost() { document.getElementById('new-post-modal').classList.remove('hidden'); document.getElementById('new-title').focus(); }
function closeNewPost() { document.getElementById('new-post-modal').classList.add('hidden'); }
function togglePoll() { document.getElementById('poll-section').classList.toggle('hidden', !document.getElementById('enable-poll').checked); }
function addPollOpt() {
    const c = document.getElementById('poll-options');
    const n = c.children.length + 1;
    const inp = document.createElement('input');
    inp.type = 'text'; inp.className = 'poll-opt w-full px-3 py-2 border border-blue-200 rounded-lg text-sm bg-white';
    inp.placeholder = `选项 ${n}`; c.appendChild(inp);
}
function insertFmt(pre, suf) {
    // 保留兼容性，RichEditor 已接管
    const ta = document.getElementById('new-content');
    const s = ta.selectionStart, e = ta.selectionEnd;
    const txt = ta.value;
    ta.value = txt.substring(0, s) + pre + txt.substring(s, e) + suf + txt.substring(e);
    ta.focus(); ta.selectionStart = ta.selectionEnd = s + pre.length;
}
function insEmoji(em) {
    const ta = document.getElementById('new-content');
    const s = ta.selectionStart;
    ta.value = ta.value.substring(0, s) + em + ta.value.substring(s);
    ta.focus(); ta.selectionStart = ta.selectionEnd = s + em.length;
}

// 初始化富文本编辑器
document.addEventListener('DOMContentLoaded', function() {
    new RichEditor('new-content');
});

// ===== 图片上传 =====
function triggerUpload(targetId) {
    const inp = document.createElement('input');
    inp.type = 'file'; inp.accept = 'image/*'; inp.multiple = true;
    inp.onchange = () => { if (inp.files.length) uploadFiles(inp.files, targetId); };
    inp.click();
}
function triggerCamera(targetId) {
    const inp = document.createElement('input');
    inp.type = 'file'; inp.accept = 'image/*'; inp.capture = 'environment';
    inp.onchange = () => { if (inp.files.length) uploadFiles(inp.files, targetId); };
    inp.click();
}
async function uploadFiles(files, targetId) {
    for (const file of files) {
        if (file.size > 10*1024*1024) { toast('文件不能超过10MB','error'); continue; }
        const fd = new FormData();
        fd.append('file', file);
        toast('上传中...','info');
        try {
            const res = await fetch('/api/upload', {method:'POST', body: fd});
            const d = await res.json();
            if (d.success) {
                const ta = document.getElementById(targetId);
                const tag = `\n[img:${d.url}]\n`;
                const s = ta.selectionStart;
                ta.value = ta.value.substring(0, s) + tag + ta.value.substring(s);
                ta.focus();
                showUploadPreview(targetId, d.url);
                toast('图片上传成功');
            } else { toast(d.message,'error'); }
        } catch(e) { toast('上传失败','error'); }
    }
}
function showUploadPreview(targetId, url) {
    const previewId = targetId === 'reply-input' ? 'reply-preview' : targetId + '-preview';
    const container = document.getElementById(previewId);
    if (!container) return;
    container.classList.remove('hidden');
    const div = document.createElement('div');
    div.className = 'relative group';
    div.innerHTML = `<img src="${url}" class="w-16 h-16 object-cover rounded border border-slate-200"><button onclick="this.parentElement.remove();checkPreviewEmpty('${previewId}')" class="absolute -top-1 -right-1 w-4 h-4 bg-red-500 text-white rounded-full text-xs leading-none flex items-center justify-center opacity-0 group-hover:opacity-100">×</button>`;
    container.appendChild(div);
}
function checkPreviewEmpty(previewId) {
    const c = document.getElementById(previewId);
    if (c && !c.children.length) c.classList.add('hidden');
}
function renderContent(text) {
    return renderRichContent(text);
}

async function submitPost() {
    const title = document.getElementById('new-title').value.trim();
    const content = document.getElementById('new-content').value.trim();
    const tag = document.getElementById('new-tag').value;
    const isOfficial = document.getElementById('new-official')?.checked || false;
    if (!title || !content) { toast('标题和内容不能为空', 'error'); return; }
    const body = { title, content, tag, is_official: isOfficial };
    let url = '/api/posts';
    if (document.getElementById('enable-poll').checked) {
        url = '/api/posts/with-poll';
        const q = document.getElementById('poll-question').value.trim();
        const opts = [...document.querySelectorAll('.poll-opt')].map(i => i.value.trim()).filter(Boolean);
        if (q && opts.length >= 2) {
            body.poll = { question: q, options: opts, multi: document.getElementById('poll-multi').checked };
        }
    }
    const res = await fetch(url, { method: 'POST', headers: {'Content-Type':'application/json'}, body: JSON.stringify(body) });
    const data = await res.json();
    if (data.success) { closeNewPost(); document.getElementById('new-title').value=''; document.getElementById('new-content').value=''; toast('发帖成功！'); loadPosts(); loadSidebar(); }
    else toast(data.message, 'error');
}

// ===== 帖子列表 =====
function renderPosts(posts) {
    const c = document.getElementById('post-list');
    if (!posts.length) { 
        c.innerHTML = `
        <div class="col-span-full py-20 flex flex-col items-center justify-center text-slate-400 bg-white rounded-2xl border border-slate-100 border-dashed">
            <svg class="w-16 h-16 mb-4 text-slate-200" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" d="M8 12h.01M12 12h.01M16 12h.01M21 12c0 4.418-4.03 8-9 8a9.863 9.863 0 01-4.255-.949L3 20l1.395-3.72C3.512 15.042 3 13.574 3 12c0-4.418 4.03-8 9-8s9 3.582 9 8z"/></svg>
            <p>暂无符合条件的帖子</p>
            ${CU ? '<button onclick="openNewPost()" class="mt-4 px-4 py-2 bg-primary/10 text-primary rounded-xl text-sm font-medium hover:bg-primary/20 transition-colors">来发第一帖吧</button>' : ''}
        </div>`; 
        return; 
    }
    posts.sort((a, b) => (b.pinned ? 1 : 0) - (a.pinned ? 1 : 0));
    let h = '';
    posts.forEach(p => {
        const tc = TAG_COLORS[p.tag] || 'slate';
        const ti = TAG_ICONS[p.tag] || '📋';
        const reactions = p.reactions || {};
        let reactHtml = '';
        for (const [k, v] of Object.entries(reactions)) {
            if (v > 0) reactHtml += `<span class="inline-flex items-center gap-1 text-xs bg-slate-50 border border-slate-100 px-2 py-0.5 rounded-md text-slate-600">${REACTIONS[k]||k} ${v}</span>`;
        }
        
        // 生成纯文本内容用于预览
        let cleanContent = p.content.replace(/\[img:[^\]]+\]/g, '[图片]');
        
        // 生成等级
        const randomLv = (p.id % 5) + 1;
        
        h += `<div class="bg-white rounded-3xl p-6 border ${p.pinned ? 'border-amber-200 shadow-md bg-gradient-to-br from-amber-50/40 to-white' : 'border-slate-100 shadow-sm'} hover-card-up transition-all duration-300 cursor-pointer group flex flex-col sm:flex-row gap-5" onclick="openPost(${p.id})">
            
            <div class="hidden sm:flex flex-col items-center gap-3 flex-shrink-0" onclick="event.stopPropagation()">
                <!-- 游戏化头像与等级 -->
                <div class="relative w-14 h-14 rounded-2xl bg-gradient-to-br from-indigo-100 to-purple-100 flex items-center justify-center text-indigo-600 font-bold border-2 border-white shadow-md transform group-hover:rotate-6 transition-transform z-10">
                    <span class="text-xl">${esc(p.author.charAt(0))}</span>
                    ${p.is_official ? 
                    '<div class="absolute -bottom-2 -right-2 bg-gradient-to-r from-red-500 to-rose-600 text-white text-[9px] font-black px-1.5 py-0.5 rounded-md shadow-sm border border-white">官方</div>' : 
                    '<div class="absolute -bottom-1.5 -right-1.5 bg-slate-800 text-white text-[9px] font-bold px-1.5 py-0.5 rounded-full shadow-sm border border-white">Lv.' + randomLv + '</div>'}
                </div>
                
                <button onclick="toggleLike(${p.id},this)" class="group/btn w-12 h-12 flex flex-col items-center justify-center rounded-2xl border ${p.liked?'border-rose-200 bg-rose-50 text-rose-500':'border-slate-100 bg-slate-50 text-slate-400 hover:bg-rose-50 hover:text-rose-500 hover:border-rose-200'} transition-all transform hover:-translate-y-1">
                    <svg class="w-5 h-5 mb-0.5 group-hover/btn:scale-110 transition-transform" fill="${p.liked?'currentColor':'none'}" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4.318 6.318a4.5 4.5 0 000 6.364L12 20.364l7.682-7.682a4.5 4.5 0 00-6.364-6.364L12 7.636l-1.318-1.318a4.5 4.5 0 00-6.364 0z"/></svg>
                    <span class="lc text-[10px] font-bold leading-none">${p.likes}</span>
                </button>
            </div>
            
            <div class="flex-1 min-w-0 flex flex-col pt-1">
                <div class="flex items-center flex-wrap gap-2 mb-3">
                    ${p.pinned ? '<span class="inline-flex items-center text-[10px] bg-gradient-to-r from-amber-400 to-orange-500 text-white px-2.5 py-1 rounded-md font-bold shadow-sm animate-pulse">📌 置顶推荐</span>' : ''}
                    ${p.is_official ? '<span class="inline-flex items-center text-[10px] bg-gradient-to-r from-red-500 to-rose-500 text-white px-2.5 py-1 rounded-md font-bold shadow-sm">官方公告</span>' : ''}
                    <span class="inline-flex items-center text-xs bg-slate-100 text-slate-600 px-2.5 py-1 rounded-lg font-medium border border-slate-200">
                        ${ti} ${p.tag}
                    </span>
                    ${p.has_poll ? '<span class="inline-flex items-center text-xs bg-indigo-50 text-indigo-600 px-2.5 py-1 rounded-lg font-medium border border-indigo-200"><svg class="w-3.5 h-3.5 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 19v-6a2 2 0 00-2-2H5a2 2 0 00-2 2v6a2 2 0 002 2h2a2 2 0 002-2zm0 0V9a2 2 0 012-2h2a2 2 0 012 2v10m-6 0a2 2 0 002 2h2a2 2 0 002-2m0 0V5a2 2 0 012-2h2a2 2 0 012 2v14a2 2 0 01-2 2h-2a2 2 0 01-2-2z"/></svg>参与投票</span>' : ''}
                </div>
                
                <h3 class="text-xl font-bold text-slate-900 mb-2 line-clamp-1 group-hover:text-indigo-600 transition-colors">${esc(p.title)}</h3>
                <p class="text-sm text-slate-500 line-clamp-2 mb-4 leading-relaxed group-hover:line-clamp-none transition-all duration-500">${esc(cleanContent)}</p>
                
                <div class="mt-auto flex flex-col sm:flex-row sm:items-center justify-between gap-3 pt-4 border-t border-slate-100/60">
                    <div class="flex items-center gap-3">
                        <span class="text-sm font-bold text-slate-800 hover:text-indigo-600 transition-colors cursor-pointer" onclick="event.stopPropagation();showProfile('${p.author_id}')">${esc(p.author)}</span>
                        ${!p.is_official ? `<span class="text-[10px] text-slate-400 flex items-center gap-1 bg-slate-50 px-2 py-0.5 rounded-md border border-slate-100"><svg class="w-3 h-3 text-amber-400" fill="currentColor" viewBox="0 0 20 20"><path d="M9.049 2.927c.3-.921 1.603-.921 1.902 0l1.07 3.292a1 1 0 00.95.69h3.462c.969 0 1.371 1.24.588 1.81l-2.8 2.034a1 1 0 00-.364 1.118l1.07 3.292c.3.921-.755 1.688-1.54 1.118l-2.8-2.034a1 1 0 00-1.175 0l-2.8 2.034c-.784.57-1.838-.197-1.539-1.118l1.07-3.292a1 1 0 00-.364-1.118L2.98 8.72c-.783-.57-.38-1.81.588-1.81h3.461a1 1 0 00.951-.69l1.07-3.292z"/></svg>Lv.${randomLv}</span>` : ''}
                        <span class="text-xs text-slate-400 bg-slate-50 px-2 py-1 rounded-md">${p.created_at}</span>
                    </div>
                    
                    <div class="flex items-center gap-2">
                        <div class="flex items-center gap-1.5 px-3 py-1.5 rounded-xl bg-slate-50 text-slate-500 text-xs font-medium border border-slate-100" title="浏览量">
                            <svg class="w-4 h-4 text-slate-400" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"/><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M2.458 12C3.732 7.943 7.523 5 12 5c4.478 0 8.268 2.943 9.542 7-1.274 4.057-5.064 7-9.542 7-4.477 0-8.268-2.943-9.542-7z"/></svg>
                            ${p.views || 0}
                        </div>
                        <div class="flex items-center gap-1.5 px-3 py-1.5 rounded-xl bg-slate-50 text-slate-500 text-xs font-medium border border-slate-100 hover:bg-blue-50 hover:text-blue-600 hover:border-blue-200 transition-colors" title="回复数">
                            <svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 12h.01M12 12h.01M16 12h.01M21 12c0 4.418-4.03 8-9 8a9.863 9.863 0 01-4.255-.949L3 20l1.395-3.72C3.512 15.042 3 13.574 3 12c0-4.418 4.03-8 9-8s9 3.582 9 8z"/></svg>
                            ${p.replies} 评论
                        </div>
                        <div class="flex sm:hidden items-center gap-1.5 px-3 py-1.5 rounded-xl bg-slate-50 text-slate-500 text-xs font-medium border border-slate-100" onclick="event.stopPropagation();toggleLike(${p.id},this)">
                            <svg class="w-4 h-4 ${p.liked?'text-rose-500 fill-current':'text-slate-400'}" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4.318 6.318a4.5 4.5 0 000 6.364L12 20.364l7.682-7.682a4.5 4.5 0 00-6.364-6.364L12 7.636l-1.318-1.318a4.5 4.5 0 00-6.364 0z"/></svg>
                            <span class="lc">${p.likes}</span>
                        </div>
                        <div onclick="event.stopPropagation();toggleBookmark(${p.id},this)" class="flex items-center justify-center p-2 rounded-xl bg-slate-50 hover:bg-yellow-50 border border-slate-100 hover:border-yellow-200 transition-colors ${p.bookmarked?'text-yellow-500':'text-slate-400'}" title="收藏">
                            <svg class="w-4 h-4" fill="${p.bookmarked?'currentColor':'none'}" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 5a2 2 0 012-2h10a2 2 0 012 2v16l-7-3.5L5 21V5z"/></svg>
                        </div>
                    </div>
                </div>
                ${reactHtml ? `<div class="mt-4 pt-3 border-t border-slate-100/60 flex flex-wrap gap-2">${reactHtml}</div>` : ''}
            </div>
        </div>`;
    });
    c.innerHTML = h;
}

async function loadPosts() {
    const q = document.getElementById('search-input').value;
    const sort = document.getElementById('sort-select').value;
    const tag = curTag === '全部' ? '' : curTag;
    const res = await fetch(`/api/posts/search?q=${encodeURIComponent(q)}&tag=${encodeURIComponent(tag)}&sort=${sort}`);
    const data = await res.json();
    if (data.success) renderPosts(data.data);
}

function filterTab(tag) {
    curTag = tag;
    document.querySelectorAll('.tab-pill').forEach(b => {
        b.classList.toggle('active', b.dataset.tab === tag);
    });
    loadPosts();
}

async function toggleLike(pid, btn) {
    if (!CU) { toast('请先登录', 'error'); return; }
    const res = await fetch(`/api/posts/${pid}/like`, {method:'POST'});
    const d = await res.json();
    if (d.success) {
        btn.querySelector('svg').setAttribute('fill', d.liked ? 'currentColor' : 'none');
        btn.className = btn.className.replace(/text-\w+-\d+/g, '') + (d.liked ? ' text-red-500' : ' text-slate-400');
        btn.querySelector('.lc').textContent = d.likes;
    }
}

async function toggleBookmark(pid, btn) {
    if (!CU) { toast('请先登录', 'error'); return; }
    const res = await fetch(`/api/posts/${pid}/bookmark`, {method:'POST'});
    const d = await res.json();
    if (d.success) {
        btn.querySelector('svg').setAttribute('fill', d.bookmarked ? 'currentColor' : 'none');
        btn.className = btn.className.replace(/text-\w+-\d+/g, '') + (d.bookmarked ? ' text-yellow-500' : ' text-slate-400');
    }
}

// ===== 帖子详情 =====
async function openPost(pid) {
    const res = await fetch(`/api/posts/${pid}`);
    const data = await res.json();
    if (!data.success) { toast(data.message, 'error'); return; }
    const p = data.data;
    const replies = data.replies || [];
    const isAuthor = CU && CU.id === p.author_id;
    const isTeacher = CU && (CU.role === 'teacher' || CU.role === 'admin');
    const reactions = p.reactions || {};

    let reactBtns = '';
    for (const [k, emoji] of Object.entries(REACTIONS)) {
        const cnt = reactions[k] || 0;
        reactBtns += `<button onclick="reactPost(${p.id},'${k}',this)" class="reaction-btn${cnt>0?' active':''}">${emoji} <span>${cnt}</span></button>`;
    }

    let pollHtml = '';
    if (p.has_poll) {
        try {
            const pr = await fetch(`/api/posts/${pid}/poll`);
            const pd = await pr.json();
            if (pd.success) {
                const poll = pd.poll;
                const voted = pd.voted;
                const myC = pd.my_choices || [];
                const totalV = poll.options.reduce((s, o) => s + o.votes, 0) || 1;
                pollHtml = `<div class="bg-blue-50 rounded-lg p-4 mb-4 border border-blue-100">
                    <div class="font-medium text-sm text-slate-800 mb-3">📊 ${esc(poll.question)}</div>`;
                poll.options.forEach((opt, i) => {
                    const pct = Math.round(opt.votes / totalV * 100);
                    const isMy = myC.includes(i);
                    if (voted) {
                        pollHtml += `<div class="mb-2"><div class="flex justify-between text-xs text-slate-600 mb-1"><span>${isMy?'✅ ':''}${esc(opt.text)}</span><span>${opt.votes}票 (${pct}%)</span></div><div class="poll-bar${isMy?' voted':''}"><div class="poll-fill" style="width:${Math.max(pct,2)}%">${pct}%</div></div></div>`;
                    } else {
                        pollHtml += `<label class="flex items-center gap-2 p-2 rounded-lg hover:bg-blue-100 cursor-pointer mb-1"><input type="${poll.multi?'checkbox':'radio'}" name="poll-vote" value="${i}" class="poll-choice rounded"> <span class="text-sm">${esc(opt.text)}</span></label>`;
                    }
                });
                if (!voted && CU) {
                    pollHtml += `<button onclick="votePoll(${pid})" class="mt-2 px-4 py-1.5 bg-primary text-white rounded-lg text-sm hover:bg-blue-700">投票</button>`;
                }
                pollHtml += `<div class="text-xs text-slate-400 mt-2">${poll.total_votes} 人已投票${poll.multi?' · 可多选':''}</div></div>`;
            }
        } catch(e) {}
    }

    let h = `<div class="p-6">
        <div class="flex justify-between items-start mb-4">
            <div class="flex-1">
                <div class="flex items-center gap-2 mb-2 flex-wrap">
                    ${p.pinned?'<span class="text-xs bg-red-50 text-red-600 px-2 py-0.5 rounded-full">📌 置顶</span>':''}
                    ${p.is_official?'<span class="text-xs bg-red-100 text-red-800 px-2 py-0.5 rounded-full">官方</span>':''}
                    <span class="text-xs bg-slate-100 text-slate-700 px-2 py-0.5 rounded-full">${TAG_ICONS[p.tag]||''} ${p.tag}</span>
                    ${p.edited?'<span class="text-xs text-slate-400">✏️ 已编辑</span>':''}
                </div>
                <h2 class="text-xl font-bold text-slate-900">${esc(p.title)}</h2>
                <div class="mt-2 flex items-center text-sm text-slate-400 gap-3">
                    <span class="cursor-pointer hover:text-primary" onclick="showProfile('${p.author_id}')">${esc(p.author)}</span>
                    <span>${p.created_at}</span><span>👁 ${p.views||0}</span><span>❤️ ${p.likes}</span><span>💬 ${replies.length}</span>
                </div>
            </div>
            <div class="flex items-center gap-2 flex-shrink-0">
                ${isTeacher?`<button onclick="pinPost(${p.id})" class="text-xs px-2 py-1 rounded border ${p.pinned?'border-red-300 text-red-600 bg-red-50':'border-slate-200 text-slate-600'} hover:bg-slate-50">${p.pinned?'取消置顶':'置顶'}</button>`:''}
                ${isAuthor?`<button onclick="editPost(${p.id})" class="text-xs px-2 py-1 rounded border border-slate-200 text-slate-600 hover:bg-slate-50">编辑</button>`:''}
                ${isAuthor||isTeacher?`<button onclick="deletePost(${p.id})" class="text-xs px-2 py-1 rounded border border-red-200 text-red-600 hover:bg-red-50">删除</button>`:''}
                <button onclick="openReport('post',${p.id})" class="text-xs px-2 py-1 rounded border border-slate-200 text-slate-500 hover:bg-slate-50">举报</button>
                <button onclick="closePostModal()" class="text-slate-400 hover:text-slate-600 text-xl ml-1">✕</button>
            </div>
        </div>
        <div class="prose prose-sm max-w-none text-slate-800 whitespace-pre-wrap border-b border-slate-100 pb-5 mb-4">${renderContent(p.content)}</div>
        ${pollHtml}
        <div class="flex items-center gap-2 flex-wrap mb-4">${reactBtns}</div>
        <div class="flex items-center gap-3 mb-6 border-b border-slate-100 pb-4">
            <button onclick="toggleLikeModal(${p.id})" id="ml-btn" class="flex items-center gap-1.5 px-3 py-1.5 rounded-full border ${p.liked?'border-red-300 text-red-500 bg-red-50':'border-slate-200 text-slate-500'} hover:bg-red-50 text-sm">❤️ <span id="ml-cnt">${p.likes}</span></button>
            <button onclick="toggleBmModal(${p.id})" id="mb-btn" class="flex items-center gap-1.5 px-3 py-1.5 rounded-full border ${p.bookmarked?'border-yellow-300 text-yellow-500 bg-yellow-50':'border-slate-200 text-slate-500'} hover:bg-yellow-50 text-sm">${p.bookmarked?'⭐ 已收藏':'☆ 收藏'}</button>
            <button onclick="sharePost(${p.id})" class="flex items-center gap-1.5 px-3 py-1.5 rounded-full border border-slate-200 text-slate-500 hover:bg-slate-50 text-sm">🔗 分享</button>
        </div>
        <h3 class="text-sm font-bold text-slate-700 mb-4">💬 回复 (${replies.length})</h3>`;

    if (CU) {
        h += `<div class="flex gap-3 mb-6"><div class="w-8 h-8 bg-primary rounded-full flex items-center justify-center text-white text-xs font-bold flex-shrink-0">${esc(CU.name.charAt(0))}</div>
            <div class="flex-1"><textarea id="reply-input" rows="2" class="w-full px-3 py-2 border border-slate-200 rounded-lg text-sm focus:outline-none focus:ring-2 focus:ring-primary/30" placeholder="写下你的回复..."></textarea>
            <div id="reply-preview" class="flex flex-wrap gap-2 mt-1 hidden"></div>
            <div class="flex justify-between items-center mt-2"><div class="flex gap-1"><button onclick="triggerUpload('reply-input')" class="p-1 rounded hover:bg-slate-200 text-sm" title="上传图片">📷</button><button onclick="triggerCamera('reply-input')" class="p-1 rounded hover:bg-slate-200 text-sm" title="拍照上传">📸</button></div><button onclick="submitReply(${p.id})" class="px-4 py-1.5 bg-primary text-white rounded-lg text-sm hover:bg-blue-700">回复</button></div></div></div>`;
    }

    if (!replies.length) {
        h += '<div class="text-center py-8 text-slate-400 text-sm">暂无回复，来抢沙发吧 🛋️</div>';
    } else {
        replies.forEach((r, i) => {
            const canDel = CU && (CU.id === r.author_id || CU.role === 'teacher');
            const canEdit = CU && CU.id === r.author_id;
            h += `<div class="flex gap-3 py-3 ${i>0?'border-t border-slate-100':''}">
                <div class="w-8 h-8 bg-slate-200 rounded-full flex items-center justify-center text-slate-600 text-xs font-bold flex-shrink-0">${esc(r.author.charAt(0))}</div>
                <div class="flex-1 min-w-0">
                    <div class="flex items-center justify-between">
                        <div class="flex items-center gap-2 flex-wrap">
                            <span class="text-sm font-medium text-slate-900 cursor-pointer hover:text-primary" onclick="showProfile('${r.author_id}')">${esc(r.author)}</span>
                            ${r.reply_to?`<span class="text-xs text-slate-400">回复 ${esc(r.reply_to)}</span>`:''}
                            <span class="text-xs text-slate-400">${r.created_at}</span>
                            ${r.edited?'<span class="text-xs text-slate-400">✏️已编辑</span>':''}
                        </div>
                        <div class="flex items-center gap-2">
                            <button onclick="likeReply(${r.id},this)" class="flex items-center gap-1 text-xs ${r.liked?'text-red-500':'text-slate-400'} hover:text-red-500">❤️ <span>${r.likes}</span></button>
                            <button onclick="replyTo('${esc(r.author)}',${p.id})" class="text-xs text-slate-400 hover:text-primary">回复</button>
                            ${canEdit?`<button onclick="editReply(${r.id},'${esc(r.content).replace(/'/g,"\\\\'")}',${p.id})" class="text-xs text-slate-400 hover:text-blue-500">编辑</button>`:''}
                            ${canDel?`<button onclick="deleteReply(${r.id},${p.id})" class="text-xs text-slate-400 hover:text-red-500">删除</button>`:''}
                            <button onclick="openReport('reply',${r.id})" class="text-xs text-slate-400 hover:text-orange-500">举报</button>
                        </div>
                    </div>
                    <p class="mt-1 text-sm text-slate-700 whitespace-pre-wrap">${renderContent(r.content)}</p>
                </div></div>`;
        });
    }
    h += '</div>';
    document.getElementById('post-modal-content').innerHTML = h;
    document.getElementById('post-modal').classList.remove('hidden');
    document.body.style.overflow = 'hidden';
    // 初始化回复输入框的富文本编辑器
    if (document.getElementById('reply-input')) {
        new RichEditor('reply-input', { compact: true });
    }
}

function closePostModal() {
    document.getElementById('post-modal').classList.add('hidden');
    document.body.style.overflow = '';
    loadPosts();
}

async function submitReply(pid) {
    const inp = document.getElementById('reply-input');
    const content = inp.value.trim();
    if (!content) return;
    const replyTo = inp.dataset.replyTo || '';
    const res = await fetch(`/api/posts/${pid}/replies`, {method:'POST',headers:{'Content-Type':'application/json'},body:JSON.stringify({content, reply_to: replyTo})});
    const d = await res.json();
    if (d.success) { toast('回复成功'); openPost(pid); } else toast(d.message,'error');
}

function replyTo(name, pid) {
    const inp = document.getElementById('reply-input');
    if (inp) { inp.dataset.replyTo = name; inp.placeholder = `回复 ${name}...`; inp.focus(); }
}

async function toggleLikeModal(pid) {
    if (!CU) { toast('请先登录','error'); return; }
    const res = await fetch(`/api/posts/${pid}/like`,{method:'POST'});
    const d = await res.json();
    if (d.success) { document.getElementById('ml-cnt').textContent = d.likes; openPost(pid); }
}

async function toggleBmModal(pid) {
    if (!CU) { toast('请先登录','error'); return; }
    const res = await fetch(`/api/posts/${pid}/bookmark`,{method:'POST'});
    const d = await res.json();
    if (d.success) { openPost(pid); }
}

async function reactPost(pid, reaction, btn) {
    if (!CU) { toast('请先登录','error'); return; }
    const res = await fetch(`/api/posts/${pid}/react`,{method:'POST',headers:{'Content-Type':'application/json'},body:JSON.stringify({reaction})});
    const d = await res.json();
    if (d.success) openPost(pid);
}

async function votePoll(pid) {
    const checks = document.querySelectorAll('.poll-choice:checked');
    const choices = [...checks].map(c => parseInt(c.value));
    if (!choices.length) { toast('请选择选项','error'); return; }
    const res = await fetch(`/api/posts/${pid}/vote`,{method:'POST',headers:{'Content-Type':'application/json'},body:JSON.stringify({choices})});
    const d = await res.json();
    if (d.success) { toast('投票成功'); openPost(pid); } else toast(d.message,'error');
}

async function sharePost(pid) {
    const url = window.location.origin + '/forum#post-' + pid;
    try { await navigator.clipboard.writeText(url); toast('链接已复制到剪贴板'); } catch(e) { toast('分享链接: ' + url, 'info'); }
    fetch(`/api/posts/${pid}/share`,{method:'POST'});
}

async function deletePost(pid) {
    if (!confirm('确定删除该帖子？')) return;
    const res = await fetch(`/api/posts/${pid}`,{method:'DELETE'});
    const d = await res.json();
    if (d.success) { closePostModal(); toast('帖子已删除'); } else toast(d.message,'error');
}

async function pinPost(pid) {
    const res = await fetch(`/api/posts/${pid}/pin`,{method:'POST'});
    const d = await res.json();
    if (d.success) openPost(pid);
}

async function editPost(pid) {
    const res = await fetch(`/api/posts/${pid}`);
    const d = await res.json();
    if (!d.success) return;
    const p = d.data;
    const newTitle = prompt('编辑标题:', p.title);
    if (newTitle === null) return;
    const newContent = prompt('编辑内容:', p.content);
    if (newContent === null) return;
    const res2 = await fetch(`/api/posts/${pid}/edit`,{method:'POST',headers:{'Content-Type':'application/json'},body:JSON.stringify({title:newTitle,content:newContent,tag:p.tag})});
    const d2 = await res2.json();
    if (d2.success) { toast('编辑成功'); openPost(pid); } else toast(d2.message,'error');
}

async function editReply(rid, oldContent, pid) {
    const newContent = prompt('编辑回复:', oldContent);
    if (newContent === null || !newContent.trim()) return;
    const res = await fetch(`/api/replies/${rid}/edit`,{method:'POST',headers:{'Content-Type':'application/json'},body:JSON.stringify({content:newContent})});
    const d = await res.json();
    if (d.success) { toast('编辑成功'); openPost(pid); } else toast(d.message,'error');
}

async function likeReply(rid, btn) {
    if (!CU) { toast('请先登录','error'); return; }
    const res = await fetch(`/api/replies/${rid}/like`,{method:'POST'});
    const d = await res.json();
    if (d.success) { btn.querySelector('span').textContent = d.likes; btn.className = btn.className.replace(/text-\w+-\d+/g,'') + (d.liked?' text-red-500':' text-slate-400'); }
}

async function deleteReply(rid, pid) {
    if (!confirm('确定删除该回复？')) return;
    const res = await fetch(`/api/replies/${rid}`,{method:'DELETE'});
    const d = await res.json();
    if (d.success) { toast('回复已删除'); openPost(pid); } else toast(d.message,'error');
}

// ===== 举报 =====
function openReport(type, targetId) {
    document.getElementById('report-type').value = type;
    document.getElementById('report-target-id').value = targetId;
    document.getElementById('report-modal').classList.remove('hidden');
}
function closeReport() { document.getElementById('report-modal').classList.add('hidden'); }
async function submitReport() {
    const res = await fetch('/api/report',{method:'POST',headers:{'Content-Type':'application/json'},body:JSON.stringify({
        type: document.getElementById('report-type').value,
        target_id: parseInt(document.getElementById('report-target-id').value),
        reason: document.getElementById('report-reason').value,
        detail: document.getElementById('report-detail').value
    })});
    const d = await res.json();
    if (d.success) { closeReport(); toast(d.message); } else toast(d.message,'error');
}

// ===== 收藏 =====
async function showBookmarks() {
    const res = await fetch('/api/user/bookmarks');
    const d = await res.json();
    if (d.success) { renderPosts(d.data); document.querySelectorAll('.tab-pill').forEach(b => b.classList.remove('active')); toast('显示收藏帖子','info'); }
}

// ===== 排行榜 =====
async function showLeaderboard() {
    document.getElementById('leaderboard-modal').classList.remove('hidden');
    const res = await fetch('/api/forum/leaderboard');
    const d = await res.json();
    if (!d.success) return;
    let h = '';
    d.data.forEach((u, i) => {
        const rc = i===0?'gold':i===1?'silver':i===2?'bronze':'';
        const medal = i===0?'🥇':i===1?'🥈':i===2?'🥉':`${i+1}`;
        h += `<div class="flex items-center gap-3 py-3 ${i>0?'border-t border-slate-100':''}">
            <div class="w-6 text-center font-bold ${rc?'text-lg':''}">${medal}</div>
            <div class="w-8 h-8 bg-primary/10 rounded-full flex items-center justify-center text-primary text-xs font-bold">${esc(u.name.charAt(0))}</div>
            <div class="flex-1"><div class="flex items-center gap-2"><span class="text-sm font-medium cursor-pointer hover:text-primary" onclick="showProfile('${u.user_id}')">${esc(u.name)}</span><span class="level-badge level-${u.level}">Lv.${u.level} ${u.level_title}</span></div>
            <div class="text-xs text-slate-400 mt-0.5">${u.points}积分 · ${u.posts_count}帖子 · ${u.likes_received}赞</div></div></div>`;
    });
    document.getElementById('lb-content').innerHTML = h || '<div class="text-center py-8 text-slate-400">暂无数据</div>';
}

// ===== 用户资料 =====
async function showProfile(uid) {
    document.getElementById('profile-modal').classList.remove('hidden');
    const res = await fetch(`/api/user/profile/${uid}`);
    const d = await res.json();
    if (!d.success) return;
    const p = d.profile;
    let badges = p.badges.map(b => `<span class="inline-flex items-center gap-1 px-2 py-1 bg-slate-50 rounded-lg text-xs" title="${b.desc}">${b.icon} ${b.name}</span>`).join('');
    let posts = p.recent_posts.map(pp => `<div class="text-sm py-1.5 border-b border-slate-50 cursor-pointer hover:text-primary" onclick="document.getElementById('profile-modal').classList.add('hidden');openPost(${pp.id})">${esc(pp.title)}</div>`).join('');
    let friendBtn = '';
    if (CU && CU.id !== parseInt(uid)) {
        friendBtn = `<button id="addFriendBtn" onclick="forumAddFriend(${uid},this)" class="px-3 py-1.5 text-xs bg-primary text-white rounded-lg hover:bg-blue-600 transition-colors">加好友</button>`;
    }
    document.getElementById('profile-content').innerHTML = `
        <div class="flex items-center gap-4 mb-5">
            <div class="w-16 h-16 bg-primary/10 rounded-full flex items-center justify-center text-primary text-2xl font-bold">${esc(p.name.charAt(0))}</div>
            <div><div class="flex items-center gap-2"><span class="text-xl font-bold">${esc(p.name)}</span><span class="level-badge level-${p.level}">Lv.${p.level} ${p.level_title}</span></div>
            <div class="text-sm text-slate-500 mt-1">${p.points} 积分</div></div>
            <div class="ml-auto flex items-center gap-2">
                ${friendBtn}
                <button onclick="document.getElementById('profile-modal').classList.add('hidden')" class="text-slate-400 hover:text-slate-600 text-xl">✕</button>
            </div>
        </div>
        <div class="grid grid-cols-3 gap-3 mb-5">
            <div class="text-center p-3 bg-blue-50 rounded-lg"><div class="text-xl font-bold text-blue-600">${p.posts_count}</div><div class="text-xs text-slate-500">帖子</div></div>
            <div class="text-center p-3 bg-green-50 rounded-lg"><div class="text-xl font-bold text-green-600">${p.replies_count}</div><div class="text-xs text-slate-500">回复</div></div>
            <div class="text-center p-3 bg-red-50 rounded-lg"><div class="text-xl font-bold text-red-500">${p.likes_received}</div><div class="text-xs text-slate-500">获赞</div></div>
        </div>
        ${badges?`<div class="mb-5"><div class="text-sm font-bold text-slate-700 mb-2">🏅 成就徽章</div><div class="flex flex-wrap gap-2">${badges}</div></div>`:''}
        ${posts?`<div><div class="text-sm font-bold text-slate-700 mb-2">📝 最近帖子</div>${posts}</div>`:''}`;
}

async function forumAddFriend(userId, btn) {
    try {
        const res = await fetch('/api/friend/add', {method:'POST', headers:{'Content-Type':'application/json'}, body: JSON.stringify({friend_id: userId})});
        const data = await res.json();
        if (data.success) {
            btn.textContent = '已发送';
            btn.disabled = true;
            btn.classList.replace('bg-primary', 'bg-slate-400');
            btn.classList.remove('hover:bg-blue-600');
        } else {
            alert(data.message || '操作失败');
        }
    } catch(e) { alert('操作失败'); }
}

// ===== 侧边栏 =====
async function loadSidebar() {
    // 热门帖子
    const hr = await fetch('/api/forum/hot');
    const hd = await hr.json();
    if (hd.success) {
        let h = '';
        hd.data.slice(0, 6).forEach((p, i) => {
            let colorClass = 'bg-slate-100 text-slate-500';
            if (i === 0) colorClass = 'bg-red-500 text-white shadow-sm shadow-red-200';
            else if (i === 1) colorClass = 'bg-orange-500 text-white shadow-sm shadow-orange-200';
            else if (i === 2) colorClass = 'bg-amber-500 text-white shadow-sm shadow-amber-200';
            
            h += `
            <div class="flex items-start gap-3 p-3 rounded-xl hover:bg-slate-50 cursor-pointer transition-colors group mb-1 border border-transparent hover:border-slate-100" onclick="openPost(${p.id})">
                <div class="w-6 h-6 rounded-lg ${colorClass} flex items-center justify-center text-xs font-bold flex-shrink-0 mt-0.5">
                    ${i + 1}
                </div>
                <div class="flex-1 min-w-0">
                    <div class="text-sm font-medium text-slate-700 group-hover:text-primary line-clamp-2 mb-1.5 transition-colors leading-snug">
                        ${esc(p.title)}
                    </div>
                    <div class="flex items-center gap-3 text-xs text-slate-400">
                        <span class="flex items-center"><svg class="w-3 h-3 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"/><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M2.458 12C3.732 7.943 7.523 5 12 5c4.478 0 8.268 2.943 9.542 7-1.274 4.057-5.064 7-9.542 7-4.477 0-8.268-2.943-9.542-7z"/></svg>${p.views || 0}</span>
                        <span class="flex items-center"><svg class="w-3 h-3 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 12h.01M12 12h.01M16 12h.01M21 12c0 4.418-4.03 8-9 8a9.863 9.863 0 01-4.255-.949L3 20l1.395-3.72C3.512 15.042 3 13.574 3 12c0-4.418 4.03-8 9-8s9 3.582 9 8z"/></svg>${p.replies}</span>
                    </div>
                </div>
            </div>`;
        });
        document.getElementById('hot-posts').innerHTML = h || '<div class="text-xs text-slate-400 text-center py-4">暂无数据</div>';
    }
    // 论坛统计
    const sr = await fetch('/api/forum/stats');
    const sd = await sr.json();
    if (sd.success) {
        const s = sd.stats;
        document.getElementById('s-posts').textContent = s.total_posts;
        document.getElementById('s-replies').textContent = s.total_replies;
        document.getElementById('s-today').textContent = s.today_posts;
        document.getElementById('s-online').textContent = s.online_count;
        // 活跃用户
        let au = '';
        s.active_users.forEach(u => {
            au += `<div class="flex items-center gap-3 p-2.5 rounded-xl hover:bg-slate-50 cursor-pointer transition-colors border border-transparent hover:border-slate-100 mb-1" onclick="showProfile('${u.user_id}')">
                <div class="relative">
                    <div class="w-9 h-9 bg-gradient-to-br from-blue-100 to-indigo-100 rounded-full flex items-center justify-center text-primary font-bold shadow-sm border border-white">
                        ${esc(u.name.charAt(0))}
                    </div>
                    <div class="absolute -bottom-1 -right-1 w-4 h-4 bg-green-500 rounded-full border-2 border-white flex items-center justify-center" title="在线"></div>
                </div>
                <div class="flex-1 min-w-0">
                    <div class="text-sm font-medium text-slate-800 truncate">${esc(u.name)}</div>
                    <div class="text-xs text-slate-400 mt-0.5 truncate">Lv.${u.level} ${u.level_title || ''}</div>
                </div>
            </div>`;
        });
        document.getElementById('active-users').innerHTML = au || '<div class="text-xs text-slate-400 text-center py-4">暂无数据</div>';
        // 标签统计
        let ts = '';
        const tagIcons = {'官方公告':'📢','题目讨论':'📐','经验分享':'💡','求助答疑':'🙋','闲聊灌水':'☕'};
        for (const [tag, cnt] of Object.entries(s.tag_counts)) {
            ts += `<div class="flex items-center justify-between text-xs py-1"><span>${tagIcons[tag]||'📋'} ${tag}</span><span class="text-slate-400">${cnt} 帖</span></div>`;
        }
        document.getElementById('tag-stats').innerHTML = ts || '<div class="text-xs text-slate-400 text-center py-4">暂无数据</div>';
    }
}

// ===== 初始化 =====
loadPosts();
loadSidebar();
// 定时刷新在线人数
setInterval(async () => {
    try {
        const r = await fetch('/api/forum/stats');
        const d = await r.json();
        if (d.success) document.getElementById('s-online').textContent = d.stats.online_count;
    } catch(e) {}
}, 30000);
</script>
{% endblock %}
