// ==UserScript== // @name ChatGPT ChatTree 🌳 // @name:zh-CN ChatGPT ChatTree 🌳 // @namespace https://czz9.top // @version 2023.10.20.03 // @description ChatGPT ChatTree 🌳, 🚀permanent and unrestricted management of your interactions with ChatGPT🚀 🔄real-time updates and visualization of ChatGPT conversation tree🔄 💡ChatGPT conversation tips, custom annotations, bookmarks💡🔍Smart Search in ChatGPT: quickly locate specific conversations🔍 📋ChatGPT Interaction Management Panel, user-friendly interface, comprehensive ChatGPT interaction management options, categorization, tags, and more📋 // @description:ar ChatGPT ChatTree 🌳، 🚀إدارة دائمة وغير محدودة لتفاعلاتك مع ChatGPT🚀 🔄تحديث شجرة المحادثة ChatGPT بالوقت الفعلي + مرئيات🔄 💡نصائح للمحادثة مع ChatGPT، تعليقات مخصصة، إشارات مرجعية💡🔍 بحث ذكي في ChatGPT: تحديد المواضع الدقيقة للمحادثات بسرعة🔍 📋لوحة إدارة التفاعل مع ChatGPT، واجهة سهلة الاستخدام، خيارات إدارة التفاعل الكاملة مع ChatGPT، التصنيف، والعلامات وأكثر📋 // @description:bg ChatGPT ChatTree 🌳, 🚀постоянно и без ограничения управлявайте взаимодействията си с ChatGPT🚀 🔄реално време актуализации и визуализации на дървото на разговори с ChatGPT🔄 💡Съвети за разговори с ChatGPT, персонализирани коментари, отметки💡🔍 Интелигентно търсене в ChatGPT: бързо намиране на конкретни разговори🔍 📋Панел за управление на взаимодействията с ChatGPT, удобен интерфейс, пълни опции за управление на взаимодействията, категории, етикети и други📋 // @description:ckb ChatGPT ChatTree 🌳، 🚀بەردووم و بێ سنووریدانی کارپێکردنی تایبەتمەندیەکانت لەگەڵ ChatGPT🚀 🔄نوێکردنەوەی بەرزی ڕووداوی ChatGPT بە ڕاستی گشتی + ڕوانین🔄 💡پێشاندانی تایبەتمەندیەکانی ChatGPT، تێبینی تایبەت، نیشانکردن💡🔍 گەڕانی زانایی لە ChatGPT: چاودێری ئاسانی گفتوگۆی تایبەت🔍 📋پانێڵی باشکردنی تایبەتمەندی لەگەڵ ChatGPT، ڕووکاری ئاسان بەکارهێنان، هەڵبژاردنە پڕەکانی باشکردن، پۆلەکان، تاگ و زیاتر📋 // @description:cs ChatGPT ChatTree 🌳, 🚀trvalé a neomezené řízení interakcí s ChatGPT🚀 🔄aktualizace stromu konverzace ChatGPT v reálném čase + vizualizace🔄 💡tipy na konverzaci s ChatGPT, vlastní komentáře, záložky💡🔍 inteligentní vyhledávání v ChatGPT: rychlé nalezení konkrétních konverzací🔍 📋Panel pro správu interakcí s ChatGPT, uživatelsky přívětivé rozhraní, komplexní možnosti správy interakcí, kategorie, štítky a více📋 // @description:da ChatGPT ChatTree 🌳, 🚀permanent og ubegrænset styring af dine interaktioner med ChatGPT🚀 🔄real-tids opdatering og visualisering af ChatGPT samtaletræ🔄 💡tips til samtaler med ChatGPT, brugerdefinerede kommentarer, bogmærker💡🔍 Intelligent søgning i ChatGPT: hurtig lokalisering af specifikke samtaler🔍 📋Styringspanel for interaktion med ChatGPT, brugervenlig grænseflade, fuldstændige styringsmuligheder for interaktion, kategorier, tags og mere📋 // @description:de ChatGPT ChatTree 🌳, 🚀dauerhafte und uneingeschränkte Verwaltung Ihrer Interaktionen mit ChatGPT🚀 🔄Echtzeit-Aktualisierung und Visualisierung des ChatGPT-Gesprächsbaums🔄 💡Tipps für Gespräche mit ChatGPT, benutzerdefinierte Kommentare, Lesezeichen💡🔍Intelligente Suche in ChatGPT: schnelle Auffindung spezifischer Gespräche🔍 📋Verwaltungsoberfläche für Interaktionen mit ChatGPT, benutzerfreundlich, umfassende Verwaltungsoptionen, Kategorien, Tags und mehr📋 // @description:el ChatGPT ChatTree 🌳, 🚀μόνιμη και απεριόριστη διαχείριση των αλληλεπιδράσεών σας με το ChatGPT🚀 🔄πραγματικός χρόνος ενημέρωσης και οπτικοποίησης του δέντρου συνομιλίας ChatGPT🔄 💡συμβουλές για συνομιλίες με το ChatGPT, προσαρμοσμένα σχόλια, σελιδοδείκτες💡🔍Έξυπνη αναζήτηση στο ChatGPT: γρήγορος εντοπισμός συγκεκριμένων συνομιλιών🔍 📋Πίνακας διαχείρισης αλληλεπιδράσεων με το ChatGPT, φιλικό προς τον χρήστη περιβάλλον, πλήρεις επιλογές διαχείρισης, κατηγορίες, ετικέτες και περισσότερα📋 // @description:en ChatGPT ChatTree 🌳, 🚀permanent and unrestricted management of your interactions with ChatGPT🚀 🔄real-time updates and visualization of ChatGPT conversation tree🔄 💡ChatGPT conversation tips, custom annotations, bookmarks💡🔍Smart Search in ChatGPT: quickly locate specific conversations🔍 📋ChatGPT Interaction Management Panel, user-friendly interface, comprehensive ChatGPT interaction management options, categorization, tags, and more📋 // @description:eo ChatGPT ChatTree 🌳, 🚀eterna kaj senlima administrado de viaj interagoj kun ChatGPT🚀 🔄aktualigoj en reala tempo kaj vida prezento de la babilo-arbo de ChatGPT🔄 💡konsiletoj por babili kun ChatGPT, propraj notoj, legosignoj💡🔍Inteligenta serĉo en ChatGPT: rapide trovi specifajn konversaciojn🔍 📋Administra panelo por interagoj kun ChatGPT, uzantamika interfaco, ampleksaj opcioj por administri interagojn, kategorioj, etikedoj kaj pli📋 // @description:es ChatGPT ChatTree 🌳, 🚀gestión permanente e ilimitada de tus interacciones con ChatGPT🚀 🔄actualizaciones en tiempo real y visualización del árbol de conversación de ChatGPT🔄 💡consejos para conversaciones con ChatGPT, anotaciones personalizadas, marcadores💡🔍Búsqueda inteligente en ChatGPT: localiza rápidamente conversaciones específicas🔍 📋Panel de gestión de interacción con ChatGPT, interfaz fácil de usar, opciones completas de gestión de interacción, categorización, etiquetas y más📋 // @description:fi ChatGPT ChatTree 🌳, 🚀jatkuva ja rajoittamaton vuorovaikutuksesi hallinta ChatGPT:n kanssa🚀 🔄ChatGPT-keskustelupuun reaaliaikaiset päivitykset ja visualisointi🔄 💡vinkkejä keskusteluihin ChatGPT:n kanssa, mukautetut huomautukset, kirjanmerkit💡🔍Älykäs haku ChatGPT:ssa: löydä nopeasti tiettyjä keskusteluja🔍 📋ChatGPT-vuorovaikutuksen hallintapaneeli, käyttäjäystävällinen käyttöliittymä, kattavat vuorovaikutuksen hallintaoptiot, luokittelu, tagit ja lisää📋 // @description:fr ChatGPT ChatTree 🌳, 🚀surveillance continue et sans restriction de vos dialogues avec ChatGPT🚀 🔄rafraîchissement et affichage en direct de l'arborescence des échanges avec ChatGPT🔄 💡astuces pour discuter avec ChatGPT, notes sur mesure, favoris💡🔍Fouille astucieuse dans ChatGPT : repérage immédiat des discussions ciblées🔍 📋Tableau de bord pour la gestion des interactions avec ChatGPT, ergonomie intuitive, choix exhaustifs pour la supervision des dialogues, classement, balises et davantage📋 // @description:fr-CA ChatGPT ChatTree 🌳, 🚀contrôle ininterrompu de vos échanges avec ChatGPT🚀 🔄actualisation en temps réel de la structure de conversation de ChatGPT🔄 💡trucs pour converser avec ChatGPT, commentaires personnalisés, marque-pages💡🔍identification express des conversations spécifiques🔍 📋Tableau de contrôle des interactions avec ChatGPT, interface accessible, catégorisation, balises et plus📋 // @description:he ChatGPT ChatTree 🌳, 🚀ניהול תמידי וללא הגבלות של האינטראקציה שלך עם ChatGPT🚀 🔄עדכונים בזמן אמת וויזואליזציה של עץ השיחה של ChatGPT🔄 💡טיפים לשיחה עם ChatGPT, הערות מותאמות אישית, סימניות💡🔍חיפוש חכם ב-ChatGPT: מיקום מהיר של שיחות מסוימות🔍 📋פנל ניהול האינטראקציה עם ChatGPT, ממשק ידידותי למשתמש, אפשרויות ניהול האינטראקציה המלאות, קטגוריזציה, תגיות ועוד📋 // @description:hr ChatGPT ChatTree 🌳, 🚀stalno i neograničeno upravljanje vašim interakcijama s ChatGPT-om🚀 🔄ažuriranja u stvarnom vremenu i vizualizacija ChatGPT-ovog razgovornog stabla🔄 💡savjeti za razgovore s ChatGPT-om, prilagođene napomene, oznake💡🔍Pametno pretraživanje u ChatGPT: brzo lociranje određenih razgovora🔍 📋Ploča za upravljanje interakcijama s ChatGPT-om, sučelje pogodno za korisnika, sveobuhvatne opcije za upravljanje interakcijama, kategorizacija, oznake i još mnogo toga📋 // @description:hu ChatGPT ChatTree 🌳, 🚀állandó és korlátlan interakciók kezelése a ChatGPT-vel🚀 🔄ChatGPT beszélgetési fa valós idejű frissítései és vizualizációja🔄 💡beszélgetési tippek a ChatGPT-tel, egyéni megjegyzések, könyvjelzők💡🔍Intelligens keresés a ChatGPT-ben: gyorsan megtalálja a kijelölt beszélgetéseket🔍 📋ChatGPT Interakció Kezelési Panel, felhasználóbarát felület, átfogó interakciókezelési lehetőségek, kategorizálás, címkék és több📋 // @description:id ChatGPT ChatTree 🌳, 🚀pengelolaan interaksi Anda dengan ChatGPT secara permanen dan tanpa batas🚀 🔄pembaruan real-time dan visualisasi pohon percakapan ChatGPT🔄 💡tips percakapan ChatGPT, anotasi kustom, bookmark💡🔍Pencarian Cerdas di ChatGPT: cepat menemukan percakapan spesifik🔍 📋Panel Manajemen Interaksi ChatGPT, antarmuka yang ramah pengguna, pilihan manajemen interaksi ChatGPT yang komprehensif, kategorisasi, tag, dan lain-lain📋 // @description:it ChatGPT ChatTree 🌳, 🚀gestione permanente e illimitata delle tue interazioni con ChatGPT🚀 🔄aggiornamenti in tempo reale e visualizzazione dell'albero di conversazione di ChatGPT🔄 💡consigli per conversazioni con ChatGPT, annotazioni personalizzate, segnalibri💡🔍Ricerca intelligente in ChatGPT: individuazione rapida di conversazioni specifiche🔍 📋Pannello di gestione interazioni con ChatGPT, interfaccia user-friendly, opzioni complete di gestione interazioni, categorizzazione, tag e altro ancora📋 // @description:ja ChatGPT ChatTree 🌳, 🚀ChatGPTとの対話を永続的かつ無制限に管理🚀 🔄ChatGPT会話ツリーのリアルタイム更新と可視化🔄 💡ChatGPTとの会話のヒント、カスタム注釈、ブックマーク💡🔍ChatGPTでのスマート検索:特定の会話を迅速に見つける🔍 📋ChatGPTとの対話管理パネル、ユーザーフレンドリーなインターフェース、対話管理の包括的なオプション、カテゴリー、タグなど📋 // @description:ka ChatGPT ChatTree 🌳, 🚀თქვენი ინტერაქციების მუდმივი და ულიმიტო მართვა ChatGPT-თან🚀 🔄ChatGPT სტუმრობის ხეს რეალურ დროში განახლებები და ვიზუალიზაცია🔄 💡რჩევები სტუმრობაში ChatGPT-თან, პერსონალური კომენტარები, წიგნის ნიშნები💡🔍სწრაფი ძებნა ChatGPT-ში: კონკრეტულ სასტუმროში სწრაფი მოძებნა🔍 📋ChatGPT-თან ინტერაქციის მართვის პანელი, მომხმარებლისთვის მეგობრიანი ინტერფეისი, ინტერაქციის მართვის რეგულაცია, კატეგორიზაცია, თეგები და სხვა📋 // @description:ko ChatGPT ChatTree 🌳, 🚀ChatGPT와의 상호작용을 영구적이고 무제한으로 관리🚀 🔄ChatGPT 대화 트리의 실시간 업데이트 및 시각화🔄 💡ChatGPT 대화 팁, 사용자 정의 주석, 북마크💡🔍ChatGPT 스마트 검색: 특정 대화를 빠르게 찾기🔍 📋ChatGPT 상호작용 관리 패널, 사용자 친화적 인터페이스, 전체 상호 작용 관리 옵션, 카테고리, 태그 및 기타📋 // @description:nb ChatGPT ChatTree 🌳, 🚀permanent og ubegrenset styring av dine interaksjoner med ChatGPT🚀 🔄sanntidsoppdateringer og visualisering av ChatGPT samtaletre🔄 💡ChatGPT samtale tips, egendefinerte kommentarer, bokmerker💡🔍Smart søk i ChatGPT: raskt finne spesifikke samtaler🔍 📋ChatGPT interaksjonsstyringspanel, brukervennlig grensesnitt, omfattende interaksjonsstyringsalternativer, kategorisering, tagger og mer📋 // @description:nl ChatGPT ChatTree 🌳, 🚀permanente en onbeperkte beheer van uw interacties met ChatGPT🚀 🔄real-time updates en visualisatie van ChatGPT gespreksboom🔄 💡ChatGPT gesprekstips, aangepaste opmerkingen, bladwijzers💡🔍Slim zoeken in ChatGPT: snel specifieke gesprekken lokaliseren🔍 📋ChatGPT Interactiebeheerpaneel, gebruiksvriendelijke interface, uitgebreide beheeropties voor interactie, categorisatie, tags en meer📋 // @description:pl ChatGPT ChatTree 🌳, 🚀stałe i nieograniczone zarządzanie interakcjami z ChatGPT🚀 🔄aktualizacje w czasie rzeczywistym i wizualizacja drzewa rozmów z ChatGPT🔄 💡wskazówki do rozmów z ChatGPT, niestandardowe komentarze, zakładki💡🔍inteligentne wyszukiwanie w ChatGPT: szybkie lokalizowanie konkretnych rozmów🔍 📋Panel zarządzania interakcjami z ChatGPT, intuicyjny interfejs, kompleksowe opcje zarządzania interakcjami, kategorie, etykiety i więcej📋 // @description:pt-BR ChatGPT ChatTree 🌳, 🚀gerenciamento permanente e irrestrito de suas interações com o ChatGPT🚀 🔄atualizações em tempo real e visualização da árvore de conversas do ChatGPT🔄 💡dicas de conversa com ChatGPT, anotações personalizadas, favoritos💡🔍Busca inteligente no ChatGPT: localizar rapidamente conversas específicas🔍 📋Painel de gerenciamento de interação com ChatGPT, interface amigável, opções abrangentes de gerenciamento de interação, categorização, tags e mais📋 // @description:ro ChatGPT ChatTree 🌳, 🚀administrare permanentă și nelimitată a interacțiunilor tale cu ChatGPT🚀 🔄actualizări în timp real și vizualizarea arborelui de conversație ChatGPT🔄 💡sfaturi de conversație cu ChatGPT, comentarii personalizate, semne de carte💡🔍Căutare inteligentă în ChatGPT: localizare rapidă a conversațiilor specifice🔍 📋Panoul de administrare a interacțiunilor cu ChatGPT, interfață prietenoasă, opțiuni complete de administrare a interacțiunilor, categorii, etichete și mai mult📋 // @description:ru ChatGPT ChatTree 🌳, 🚀постоянное и неограниченное управление вашими взаимодействиями с ChatGPT🚀 🔄обновления в реальном времени и визуализация дерева диалогов ChatGPT🔄 💡советы для разговоров с ChatGPT, настраиваемые комментарии, закладки💡🔍Умный поиск в ChatGPT: быстрое нахождение конкретных диалогов🔍 📋Панель управления взаимодействием с ChatGPT, удобный интерфейс, полные настройки управления взаимодействием, категории, теги и многое другое📋 // @description:sk ChatGPT ChatTree 🌳, 🚀trvalé a neobmedzené riadenie vašich interakcií s ChatGPT🚀 🔄aktualizácie v reálnom čase a vizualizácia rozhovorového stromu ChatGPT🔄 💡tipy na rozhovory s ChatGPT, vlastné poznámky, záložky💡🔍inteligentné vyhľadávanie v ChatGPT: rýchle nájdenie konkrétnych rozhovorov🔍 📋Panel na správu interakcií s ChatGPT, používateľsky prívetivé rozhranie, komplexné možnosti riadenia interakcií, kategórie, štítky a viac📋 // @description:sr ChatGPT ChatTree 🌳, 🚀stalno i neograničeno upravljanje vašim interakcijama sa ChatGPT🚀 🔄ažuriranja u realnom vremenu i vizualizacija stabla razgovora ChatGPT🔄 💡saveti za razgovore sa ChatGPT, prilagođene napomene, obeleživači💡🔍Pametna pretraga u ChatGPT: brzo lociranje specifičnih razgovora🔍 📋Panel za upravljanje interakcijama sa ChatGPT, korisnički prijatan interfejs, sveobuhvatne opcije za upravljanje interakcijama, kategorizacija, oznake i više📋 // @description:sv ChatGPT ChatTree 🌳, 🚀permanent och obegränsad hantering av dina interaktioner med ChatGPT🚀 🔄real-tidsuppdateringar och visualisering av ChatGPTs konversationsträd🔄 💡ChatGPT konversationstips, anpassade anteckningar, bokmärken💡🔍Smart sökning i ChatGPT: snabbt lokalisera specifika konversationer🔍 📋ChatGPT Interaktionshanteringspanel, användarvänligt gränssnitt, omfattande interaktionshanteringsalternativ, kategorisering, taggar och mer📋 // @description:th ChatGPT ChatTree 🌳, 🚀การจัดการที่ถาวรและไม่จำกัดกับการโต้ตอบของคุณกับ ChatGPT🚀 🔄การอัปเดตและการแสดงภาพของต้นไม้บทสนทนาของ ChatGPT ในเวลาจริง🔄 💡เคล็ดลับการสนทนา ChatGPT, หมายเหตุที่กำหนดเอง, บุ๊กมาร์ก💡🔍การค้นหาอย่างฉลาดใน ChatGPT: ค้นหาบทสนทนาเฉพาะอย่างรวดเร็ว🔍 📋แผงควบคุมการโต้ตอบกับ ChatGPT, อินเตอร์เฟซที่เป็นมิตร, ตัวเลือกการจัดการโต้ตอบที่ครอบคลุม, การจัดประเภท, แท็ก และอื่น ๆ📋 // @description:tr ChatGPT ChatTree 🌳, 🚀ChatGPT ile etkileşimlerinizi kalıcı ve sınırsız bir şekilde yönetme🚀 🔄ChatGPT konuşma ağacının gerçek zamanlı güncellemeleri ve görselleştirmesi🔄 💡ChatGPT ile konuşma ipuçları, özel notlar, yer imleri💡🔍ChatGPT'te Akıllı Arama: belirli konuşmaları hızlı bir şekilde bulun🔍 📋ChatGPT Etkileşim Yönetim Paneli, kullanıcı dostu arayüz, kapsamlı etkileşim yönetim seçenekleri, kategorizasyon, etiketler ve daha fazlası📋 // @description:uk ChatGPT ChatTree 🌳, 🚀постійне та безобмежене управління вашими взаємодіями з ChatGPT🚀 🔄оновлення дерева розмови ChatGPT у реальному часі + візуалізація🔄 💡поради для розмови з ChatGPT, власні анотації, закладки💡🔍розумний пошук в ChatGPT: швидке знаходження конкретних розмов🔍 📋Панель управління взаємодіями з ChatGPT, зручний інтерфейс, повний набір опцій для управління взаємодіями, категорії, теги та більше📋 // @description:ug ChatGPT ChatTree 🌳, 🚀مەڭگۈلۈك ۋە چەكسىز بولغان ChatGPT بىلەن ئالاقىڭىزنى باشقۇرۇڭ🚀 🔄ChatGPT سۆھبەت ئاگىدىنى چۈشەندۈرۈش ۋە كۆرسىتىش🔄 💡ChatGPT بىلەن سۆھبەتكە كېلىشىش ئۈچۈن تەۋسىيەلەر، شەخسىي ئىزاھاتلار، خەتكۈچلەر💡🔍ChatGPT دا ئەقىللىق ئىزدەش: مەلۇم سۆھبەتلەرنى تېز تاپالايدۇ🔍 📋ChatGPT ئارىلىق باشقۇرۇش تاختىسى، ئىشلىتىشكە يېڭىراك يۈزى، تولۇق باشقۇرۇش تاللانمىلىرى، تۈرلەر، خەتكۈچلەر ۋە باشقا📋 // @description:vi ChatGPT ChatTree 🌳, 🚀quản lý vĩnh viễn và không giới hạn các tương tác của bạn với ChatGPT🚀 🔄cập nhật và trực quan hóa cây trò chuyện ChatGPT theo thời gian thực🔄 💡mẹo trò chuyện với ChatGPT, ghi chú tùy chỉnh, dấu trang💡🔍Tìm kiếm thông minh trong ChatGPT: xác định nhanh các cuộc trò chuyện cụ thể🔍 📋Bảng điều khiển quản lý tương tác với ChatGPT, giao diện thân thiện, các tùy chọn quản lý tương tác đầy đủ, phân loại, thẻ và nhiều hơn nữa📋 // @description:zh-CN ChatGPT ChatTree 🌳,🚀永久、不受限制地管理您与ChatGPT的每一次互动🚀 🔄实时ChatGPT对话树更新+可视化🔄 💡ChatGPT对话提示,自定义注释,书签💡🔍 ChatGPT智能搜索:快速定位特定对话🔍 📋ChatGPT互动管理面板,界面友好,全面ChatGPT互动管理选项,分类、标签和更多📋 // @description:zh-TW ChatGPT ChatTree 🌳,🚀永久、不受限制地管理您與ChatGPT的每一次互動🚀 🔄即時ChatGPT對話樹更新+視覺化🔄 💡ChatGPT對話提示,自訂註解,書籤💡🔍 ChatGPT智能搜尋:快速定位特定對話🔍 📋ChatGPT互動管理面板,介面友善,全面ChatGPT互動管理選項,分類、標籤和更多📋 // @description:zh-HK ChatGPT ChatTree 🌳,🚀永久、不受限制地管理您與ChatGPT的每一次互動🚀 🔄實時ChatGPT對話樹更新+可視化🔄 💡ChatGPT對話提示,自定義註釋,書籤💡🔍 ChatGPT智能搜索:快速定位特定對話🔍 📋ChatGPT互動管理面板,界面友好,全面ChatGPT互動管理選項,分類、標籤和更多📋 // @description:zh-SG ChatGPT ChatTree 🌳,🚀永久、不受限制地管理您与ChatGPT的每一次互动🚀 🔄实时ChatGPT对话树更新+可视化🔄 💡ChatGPT对话提示,自定义注释,书签💡🔍 ChatGPT智能搜索:快速定位特定对话🔍 📋ChatGPT互动管理面板,界面友好,全面ChatGPT互动管理选项,分类、标签和更多📋 // @author cuizhenzhi // @match *://chat.openai.com/* // @grant GM_addStyle // @grant GM_getResourceText // @require https://cdnjs.cloudflare.com/ajax/libs/d3/5.16.0/d3.min.js // @require https://cdn.jsdelivr.net/npm/animejs@3.2.1/lib/anime.min.js // @require https://cdnjs.cloudflare.com/ajax/libs/interact.js/1.10.11/interact.min.js // @require https://cdnjs.cloudflare.com/ajax/libs/clipboard.js/2.0.8/clipboard.min.js // @require https://code.jquery.com/jquery-3.5.1.min.js // @require https://cdn.jsdelivr.net/npm/@popperjs/core@2.10.2/dist/umd/popper.min.js // @run-at document-end // @homepageURL https://github.com/cuizhenzhi/ChatTree // @supportURL https://github.com/cuizhenzhi/ChatTree/issues // @license GPL-2.0-only // @icon data:image/svg+xml;utf8, // @downloadURL none // ==/UserScript== (function () { "use strict"; const isDevelopmentMode = false; function log(...messages) { if (isDevelopmentMode) { console.log(...messages); } } function error(...messages) { console.error(...messages); } GM_addStyle(` #searchTopicContainer { margin-bottom: 20px; } .conversation { border: 1px solid #ccc; margin-bottom: 10px; padding: 10px; margin-top: 20px; margin-left: 20px; margin-right: 20px; display: flex; justify-content: space-between; align-items: center; transition: border 0.1s ease-in-out; /* 添加过渡效果 */ border-radius: 4px; /* 添加边框圆角 */ } .conversation:hover { border: 2px solid black; /* 鼠标悬停时改变边框样式 */ box-shadow: 0px 0px 10px black; /* 添加外边框阴影效果 */ } .category { background-color: #f3f3f3; display: inline-block; padding: 2px 8px; margin-right: 2px; margin-bottom: 2px; } .chatTreeTag { background-color: #e0e0e0; display: inline-block; padding: 2px 8px; margin-right: 5px; margin-bottom: 2px; } .delete-icon, .add-icon { cursor: pointer; margin-left: 5px; } .delete-icon:hover, .add-icon:hover { background: #adb5bd; } .conversation h3 { display: inline-block; margin: 0; /* 移除默认边距 */ } .conversation-actions { margin-left: auto; /* 推到右侧 */ } .topicContainer{ width: 35%; overflow: hidden; } .optionsContainer{ width: 12%; display: flex; justify-content: center; } .tagContainers { width: 26%; display: flex; justify-content: center; align-items: center; flex-wrap: wrap; } .categoriesContainer { width: 26%; display: flex; justify-content: center; align-items: center; flex-wrap: wrap; } #managePanel { color: black; overflow: hidden; background: rgb(255,253,249); position: fixed; top: 0px; left: 0px; width: 100%; height: 100%; z-index: 999; /* 根据需要设置,以确保该元素位于其他元素之上 */ } #panelToggleButtonSVGShow { position: fixed; left: 0; top: 40%; z-index: 1000; padding: 10px 20px; border: none; background: rgb(171, 104, 255); color: white; cursor: pointer; } .card-header{ height: 40px; display: flex; border: 1px solid #adb5bd; align-items: center; justify-content: space-between; padding: 0.5rem 1.25rem; /* Optional: for adding some space inside the card-header */ } .card-body{ height: 40px; display: flex; border: 1px solid #adb5bd; align-items: center; justify-content: space-between; padding: 0.5rem 1.25rem; /* Optional: for adding some space inside the card-header */ overflow: hidden; /* Add this line to hide the overflow content */ } .card-header h5 { margin: 0; /* Optional: to remove the default margin of the h5 element */ } .btn.btn-link:hover { cursor: pointer !important; text-decoration: underline !important; border: 1px solid #80bdff !important; border-radius: 5px !important; color: #005cbf !important; margin-right: auto; /* It pushes the link to the extreme right */ } .btn.btn-sm.btn-primary{ background: #007bff; color: white; border-radius: 5px !important; border: 1px solid #80bdff !important; height: 30px; cursor: pointer; } .btn.btn-sm.btn-danger{ background: #dc3545; color: white; border-radius: 5px !important; border: 1px solid red !important; height: 30px; cursor: pointer; } .btn.btn-sm.btn-success{ background: #28a745; color: white; border-radius: 5px !important; border: 1px solid green !important; height: 30px; cursor: pointer; } .collapse { height: 0; transition: height 0.5s ease-in-out; overflow: hidden; } @keyframes textBlink { 0%, 100% { color: black; } 50% { color: white; } } .blinkText { animation: textBlink 1s ease-in-out infinite; } @keyframes highlight { 0% { background-color: initial; } 50% { background-color: #ffffff; } 100% { background-color: initial; } } .highlight { animation: highlight 2s ease-in-out infinite; } @keyframes highlightt { 0% { background-color: initial; } 50% { background-color: #000000; } 100% { background-color: initial; } } .highlightt { animation: highlightt 2s ease-in-out infinite; } .close-button { margin-left: 5px; color: red; cursor: pointer; } .suggestions-container { position: absolute; left: 40px; width: 270px; top: 100%; /* Place it below the search box */ max-height: 150px; /* Adjust as per your preference */ overflow-y: auto; /* Add scrollbar if content is too much */ border: 1px solid #ccc; background-color: white; z-index: 99; /* Make it appear on top of other elements */ } .suggestion-item { padding: 10px; cursor: pointer; } .suggestion-item:hover { background-color: #eee; } .node-menu { display: none; position: absolute; border: 1px solid black; background-color: white; } #contentDiv { box-sizing: border-box; } /* Cursor styles */ .node { cursor: pointer; } .node circle { fill: #e5e5e5; } .node circle.chatgpt { } .node circle.用户 { fill: #1E90FF; } .node.descendant-dragging circle { fill: #b0e0e6 !important; } .node.selectedNode circle { fill: red !important; } .link.highlighted { /*stroke: yellow;*/ stroke: #808080; stroke-width: 4px; } .link.descendant-highlighted { stroke: #d3d3d3; /* 选择你想要的颜色 */ stroke-width: 4px; } .content-text { white-space: pre-line; } /* Menu styles */ .menu { opacity: 0; transition: opacity 300ms, transform 300ms; transform: translateX(100%); /* Start from the right */ border: none; /* Remove border */ } .menu.show { opacity: 1; transform: translateX(0); /* Move to its original position */ } #commentForm { width: 300px; padding: 20px; border: 1px solid #ccc; border-radius: 5px; box-shadow: 0 2px 5px rgba(0, 0, 0, 0.2); } #commentForm label, #commentForm textarea, #commentForm button { display: block; width: 100%; margin-bottom: 10px; } #commentForm textarea { resize: none; /* 禁止调整大小 */ } .commentHoverEffect { transition: all 0.3s ease-in-out; } .commentHoverEffect:hover { font-weight: bold; text-shadow: 2px 2px 4px rgba(0,0,0,0.5); } /*这是显示对话内容的注释样式*/ .comment-text { color: #ff5555; font-style: italic; margin-right: 10px; display: block; font-weight: bold; border-bottom: 2px dashed #ff5555; } /* SVG background */ #thumbnailSvg { /*background-color: rgba(128, 128, 128, 0.4); !* Gray with 0.4 opacity *!*/ /*background-image: linear-gradient(to top, #fad0c4 0%, #ffd1ff 100%);*/ background: linear-gradient(to top, rgba(250, 208, 196, 1) 0%, rgba(255, 209, 255, 0.9) 100%); /*background-image: linear-gradient(to top, rgba(220,220,220, 1) 0%, rgba(220,220,220, 1) 100%);*/ } #mainSvg { /*background-color: rgba(128, 128, 128, 0.4); !* Gray with 0.4 opacity *!*/ /*background-image: linear-gradient(to top, #fad0c4 0%, #ffd1ff 100%);*/ /*background-image: linear-gradient(to top, rgba(220,220,220, 0.2) 0%, rgba(220,220,220, 0.2) 100%);*/ } #search-container { top: 20px; left: 20px; display: flex; align-items: center; position: fixed; width: 50px; height: 40px; color: black; /*overflow: hidden;*/ background: transparent; /*flex-wrap: wrap;*/ /*z-index: 10000;*/ } #search-icon { width: 40px; height: 40px; cursor: pointer; display: flex; align-items: center; justify-content: center; font-size: 24px; /* adjust as needed */ background: transparent; /*background-color: #f1f1f1;*/ } #search-box { margin-top: 10px; width: 300px; height: 40px; /*background-color: #f1f1f1;*/ border: none; padding: 0 10px; outline: none; background: transparent; opacity: 0; pointer-events: none; border-radius: 6px; } #search-btn { padding: 5px 15px; margin-left: 10px; display: none; } #search-history { position: absolute; top: 50px; left: 0; /*display: none;*/ opacity: 0; /* 设置为 0 使其默认隐藏 */ /*display: ;*/ display: flex; flex-direction: row; /* 横向排列 */ flex-wrap: wrap; /* 当空间不足时换行 */ width: 0px; min-height: 0px; /* instead of height: 0px; */ align-content: flex-start; height: 20px; max-height: 200px; /*align-items: center; !* 确保每行的内容垂直居中对齐 *!*/ overflow-y: scroll; overflow-x: hidden; padding: 10px; /* 为了避免内容紧贴边缘,给予一些内边距 */ /*z-index: 10001;*/ /*border-radius: 6px;*/ } #search-results-count { box-sizing: border-box; line-height: 26px; /* 重置行高 */ margin: 0; padding: 3px 6px; display: flex; justify-content: center; /* 水平居中 */ align-items: center; /* 垂直居中 */ } .history-item { display: flex; align-items: center; width: auto; /* 根据内容自动调整宽度 */ max-width: 150px; /* 设置最大宽度 */ max-height: 30px; overflow: hidden; background-color: #f5f5f5; border-radius: 15px; padding: 5px 10px; margin-top: 10px; margin-right: 10px; /* 每个 history-item 之间的间距 */ /*gap: 10px;*/ } .history-text { /*max-width: 100px; !* 设置最大宽度 *!*/ flex-shrink: 1; min-width: 0; white-space: nowrap; /* 防止文本换行 */ overflow: hidden; text-overflow: ellipsis; /* 使用省略号 (...) 表示被裁切的文本 */ /*padding: 5px 10px;*/ } .history-delete { cursor: pointer; padding: 5px; border-radius: 50%; transition: background-color 0.3s; margin-left: auto; /* 这会将按钮推到其父元素的右边 */ } .history-delete:hover { background-color: rgba(200, 0, 0, 0.1); } #settingsDiv, .actionDiv, .rightMiddleDiv { width: 40px; height: 40px; display: flex; align-items: center; justify-content: center; position: fixed; z-index: 1000; background-color: rgba(255, 255, 255, 0.8); border-radius: 50%; /* 让div成为圆形 */ /*box-shadow: 0px 0px 10px rgba(0, 0, 0, 0.5);*/ box-shadow: none; transition: background-color 0.3s; /* 平滑过渡效果 */ user-select: none; } #feedbackDiv { bottom: 40%; display: flex; right: 10px; cursor: pointer; color: deepskyblue; font-size: 1.5em; } #colorSelectDiv { bottom: 46%; right: 10px; cursor: pointer; color: deepskyblue; font-size: 1.5em; } .rightMiddleDiv:hover { background-color: rgba(200, 200, 255, 0.9); /* 悬停时的背景色 */ } #rightMiddleMenu { position: fixed; bottom: 52%; right: 10px; } .actionDiv { display: none; right: 10px; cursor: pointer; color: deepskyblue; font-size: 1.5em; } @keyframes spin { 0% { transform: rotate(0deg); } 100% { transform: rotate(360deg); } } #settingsDiv { animation: spin 4s linear infinite; } #settingsDiv { right: 10px; bottom: 10px; color: rebeccapurple; /* 或你想要的任何颜色 */ cursor: pointer; display: flex; justify-content: center; /* 水平居中 */ align-items: center; /* 垂直居中 */ } #plusDiv { bottom: 60px; right: 60px; } #minusDiv { bottom: 60px; } #thumbNailDiv { bottom: 10px; right: 60px; } #refreshTree { bottom: 10px; right: 110px; } #undoDiv { bottom: 60px; right: 160px; } #redoDiv { bottom: 60px; right: 110px; } #deleteDiv { bottom: 10px; right: 160px; } #settingsDiv:hover, .actionDiv:hover { background-color: rgba(200, 200, 255, 0.9); /* 悬停时的背景色 */ } `); const getLang = function () { let lang = `{ "ar": { "chatTreeRunning": "🥳🌳ChatTree🌳في التشغيل!🎉", "updateCurrentConversationTree": "🌈 تحديث شجرة المحادثة الحالية 🌈", "adjustBackgroundColorAndOpacity": "🎨 تعديل لون الخلفية والشفافية 🎨", "toggleConversationTree": "🌳 عرض/إخفاء شجرة المحادثة 🌳", "noDatabaseAndCreationFailed": "لا يوجد قاعدة بيانات، ولم يتم الإنشاء بنجاح! الخروج من البرنامج النصي!", "mismatchedLink": "الرابط غير متطابق، يرجى تحديث الصفحة!", "startUpdatingConversationTree": "بدء تحديث شجرة المحادثة", "selectedItem": "لقد اخترت {item}", "successSavingChanges": "تم حفظ التغييرات بنجاح!", "codeCopiedToClipboard": "تم نسخ الكود إلى الحافظة!", "contentCopied": "تم نسخ المحتوى!", "emptyCommentPrompt": "التعليق فارغ. هل تريد ضبط التعليق على \\"فارغ\\"؟", "confirmDeleteLinkData": "تم التحقق من الرابط كـ {item}! هل تريد حذف بيانات هذا الرابط؟ سيتم حذف جميع محتوى المحادثة والتعليقات!", "confirmCurrentURL": "تم التحقق من الرابط كـ {item}! هل أنت متأكد؟", "commentSetToEmpty": "تم تعيين التعليق على \\"فارغ\\"", "enterCommentFirst": "الرجاء إدخال التعليق أولا", "commentSaved": "تم حفظ التعليق", "conversationDataDeleted": "تم حذف بيانات المحادثة بنجاح", "executeSearchWithQuery": "تنفيذ البحث: {item}", "searchPlaceholder": "أدخل كلمات البحث...", "searchButton": "بحث", "searchInContent": "في محتوى المحادثة", "searchInComments": "في التعليقات", "searchInBoth": "في المحتوى والتعليقات", "goToPrevious": "الانتقال إلى السابق", "goToNext": "الانتقال إلى التالي", "numberOfMatches": "{matches} نتائج", "nodeDetails": "تفاصيل", "enterComment": "الرجاء إدخال تعليق", "userCommentSave": "حفظ", "userCommentCancel": "إلغاء", "userCommentClear": "مسح", "openAdminPanel": "لوحة الإدارة", "allCategoriesFilter": "جميع الفئات", "conversationTitle": "عنوان", "actionOptions": "الإجراءات", "conversationCategory": "الفئة", "conversationTags": "العلامات" }, "bg": { "chatTreeRunning": "🥳🌳ChatTree🌳работи!🎉", "updateCurrentConversationTree": "🌈 Актуализация на текущото дърво на разговори 🌈", "adjustBackgroundColorAndOpacity": "🎨 Регулиране на цвета на фона и прозрачността 🎨", "toggleConversationTree": "🌳 Показване/скриване на дървото на разговори 🌳", "noDatabaseAndCreationFailed": "Няма база данни и създаването не бе успешно! Скриптът излиза!", "mismatchedLink": "Линкът не съответства, моля, опреснете страницата!", "startUpdatingConversationTree": "Започнете актуализация на дървото на разговори", "selectedItem": "Избрахте {item}", "successSavingChanges": "Промените са запазени успешно!", "codeCopiedToClipboard": "Кодът е копиран в клипборда!", "contentCopied": "Съдържанието е копирано!", "emptyCommentPrompt": "Коментарът е празен. Искате ли да зададете коментар като \\"празен\\"?", "confirmDeleteLinkData": "Линкът е проверен като {item}! Сигурни ли сте, че искате да изтриете информацията за този линк? Всички съдържания на разговори и коментари ще бъдат изтрити!", "confirmCurrentURL": "Линкът е проверен като {item}! Сигурни ли сте?", "commentSetToEmpty": "Коментарът е зададен като \\"празен\\"", "enterCommentFirst": "Моля, първо въведете коментар", "commentSaved": "Коментарът е запазен", "conversationDataDeleted": "Данните за разговора са изтрити успешно", "executeSearchWithQuery": "Изпълнение на търсене: {item}", "searchPlaceholder": "Въведете ключови думи за търсене...", "searchButton": "Търсене", "searchInContent": "В съдържанието на разговора", "searchInComments": "В коментарите", "searchInBoth": "В съдържание и коментари", "goToPrevious": "Към предишния", "goToNext": "Към следващия", "numberOfMatches": "{matches} съвпадения", "nodeDetails": "Подробности", "enterComment": "Моля, въведете коментар", "userCommentSave": "Запази", "userCommentCancel": "Отказ", "userCommentClear": "Изчисти", "openAdminPanel": "Админ панел", "allCategoriesFilter": "Всички категории", "conversationTitle": "Заглавие", "actionOptions": "Действия", "conversationCategory": "Категория", "conversationTags": "Етикети" }, "cs": { "chatTreeRunning": "🥳🌳ChatTree🌳běží!🎉", "updateCurrentConversationTree": "🌈 Aktualizovat aktuální strom konverzace 🌈", "adjustBackgroundColorAndOpacity": "🎨 Upravit barvu pozadí a průhlednost 🎨", "toggleConversationTree": "🌳 Zobrazit/skrýt strom konverzace 🌳", "noDatabaseAndCreationFailed": "Není databáze a vytvoření se nezdařilo! Skript se ukončuje!", "mismatchedLink": "Odkaz nesouzní, obnovte stránku!", "startUpdatingConversationTree": "Začít aktualizovat strom konverzace", "selectedItem": "Vybrali jste {item}", "successSavingChanges": "Změny byly úspěšně uloženy!", "codeCopiedToClipboard": "Kód byl zkopírován do schránky!", "contentCopied": "Obsah byl zkopírován!", "emptyCommentPrompt": "Komentář je prázdný. Chcete nastavit komentář na \\"prázdný\\"?", "confirmDeleteLinkData": "Odkaz byl ověřen jako {item}! Opravdu chcete smazat informace tohoto odkazu? Veškerý obsah konverzace a komentáře budou smazány!", "confirmCurrentURL": "Odkaz byl ověřen jako {item}! Potvrzujete?", "commentSetToEmpty": "Komentář byl nastaven na \\"prázdný\\"", "enterCommentFirst": "Nejprve zadejte komentář", "commentSaved": "Komentář byl uložen", "conversationDataDeleted": "Data konverzace byla úspěšně smazána", "executeSearchWithQuery": "Spustit vyhledávání: {item}", "searchPlaceholder": "Zadejte klíčová slova pro vyhledávání...", "searchButton": "Hledat", "searchInContent": "Ve obsahu konverzace", "searchInComments": "V komentářích", "searchInBoth": "V obsahu i komentářích", "goToPrevious": "Jít na předchozí", "goToNext": "Jít na další", "numberOfMatches": "{matches} shod", "nodeDetails": "Detaily", "enterComment": "Zadejte komentář", "userCommentSave": "Uložit", "userCommentCancel": "Zrušit", "userCommentClear": "Vymazat", "openAdminPanel": "Administrační panel", "allCategoriesFilter": "Všechny kategorie", "conversationTitle": "Název", "actionOptions": "Akce", "conversationCategory": "Kategorie", "conversationTags": "Tagy" }, "da": { "chatTreeRunning": "🥳🌳ChatTree🌳 kører!🎉", "updateCurrentConversationTree": "🌈 Opdater nuværende samtaletræ 🌈", "adjustBackgroundColorAndOpacity": "🎨 Juster baggrundsfarve og gennemsigtighed 🎨", "toggleConversationTree": "🌳 Vis/skjul samtaletræ 🌳", "noDatabaseAndCreationFailed": "Ingen database, og oprettelsen mislykkedes! Scriptet afslutter!", "mismatchedLink": "Link matcher ikke, opdater siden!", "startUpdatingConversationTree": "Begynder at opdatere samtaletræ", "selectedItem": "Du valgte {item}", "successSavingChanges": "Ændringer gemt succesfuldt!", "codeCopiedToClipboard": "Kode kopieret til udklipsholder!", "contentCopied": "Indhold kopieret!", "emptyCommentPrompt": "Kommentaren er tom. Vil du sætte kommentaren til \\"tom\\"?", "confirmDeleteLinkData": "Linket er {item}! Er du sikker på, at du vil slette disse linkdata? Alle samtaler og kommentarer vil blive slettet!", "confirmCurrentURL": "Linket er {item}! Er du sikker?", "commentSetToEmpty": "Kommentar sat til \\"tom\\"", "enterCommentFirst": "Indtast kommentar først", "commentSaved": "Kommentar gemt", "conversationDataDeleted": "Samtaledata slettet succesfuldt", "executeSearchWithQuery": "Udfør søgning: {item}", "searchPlaceholder": "Indtast søgeord...", "searchButton": "Søg", "searchInContent": "I samtaleindholdet", "searchInComments": "I kommentarer", "searchInBoth": "Både i indhold og kommentarer", "goToPrevious": "Gå til den forrige", "goToNext": "Gå til den næste", "numberOfMatches": "{matches} match", "nodeDetails": "Detaljer", "enterComment": "Indtast kommentar", "userCommentSave": "Gem", "userCommentCancel": "Annuller", "userCommentClear": "Ryd", "openAdminPanel": "Admin panel", "allCategoriesFilter": "Alle kategorier", "conversationTitle": "Titel", "actionOptions": "Handlinger", "conversationCategory": "Kategori", "conversationTags": "Tags" }, "de": { "chatTreeRunning": "🥳🌳ChatTree🌳 läuft!🎉", "updateCurrentConversationTree": "🌈 Aktualisiere aktuellen Konversationsbaum 🌈", "adjustBackgroundColorAndOpacity": "🎨 Hintergrundfarbe und Transparenz anpassen 🎨", "toggleConversationTree": "🌳 Konversationsbaum anzeigen/verbergen 🌳", "noDatabaseAndCreationFailed": "Keine Datenbank und Erstellung fehlgeschlagen! Skript beendet!", "mismatchedLink": "Link stimmt nicht überein, bitte aktualisieren Sie die Seite!", "startUpdatingConversationTree": "Beginne mit der Aktualisierung des Konversationsbaums", "selectedItem": "Sie haben {item} ausgewählt", "successSavingChanges": "Änderungen erfolgreich gespeichert!", "codeCopiedToClipboard": "Code wurde in die Zwischenablage kopiert!", "contentCopied": "Inhalt kopiert!", "emptyCommentPrompt": "Der Kommentar ist leer. Möchten Sie den Kommentar auf \\"leer\\" setzen?", "confirmDeleteLinkData": "Der erkannte Link ist {item}! Möchten Sie wirklich die Informationen zu diesem Link löschen? Alle Gesprächsinhalte und Kommentare werden gelöscht!", "confirmCurrentURL": "Der erkannte Link ist {item}! Sicher?", "commentSetToEmpty": "Kommentar auf \\"leer\\" gesetzt", "enterCommentFirst": "Bitte geben Sie zuerst einen Kommentar ein", "commentSaved": "Kommentar gespeichert", "conversationDataDeleted": "Konversationsdaten erfolgreich gelöscht", "executeSearchWithQuery": "Suche ausführen: {item}", "searchPlaceholder": "Suchbegriffe eingeben...", "searchButton": "Suchen", "searchInContent": "Im Gesprächsinhalt", "searchInComments": "In den Kommentaren", "searchInBoth": "In Inhalt und Kommentaren", "goToPrevious": "Zum vorherigen gehen", "goToNext": "Zum nächsten gehen", "numberOfMatches": "{matches} Übereinstimmungen", "nodeDetails": "Details", "enterComment": "Bitte Kommentar eingeben", "userCommentSave": "Speichern", "userCommentCancel": "Abbrechen", "userCommentClear": "Löschen", "openAdminPanel": "Admin-Panel", "allCategoriesFilter": "Alle Kategorien", "conversationTitle": "Titel", "actionOptions": "Optionen", "conversationCategory": "Kategorie", "conversationTags": "Tags" }, "el": { "chatTreeRunning": "🥳🌳ChatTree🌳 Είναι σε λειτουργία!🎉", "updateCurrentConversationTree": "🌈 Ενημέρωση του τρέχοντος δέντρου συνομιλίας 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ρύθμιση του χρώματος φόντου και της διαφάνειας 🎨", "toggleConversationTree": "🌳 Εμφάνιση/Απόκρυψη δέντρου συνομιλίας 🌳", "noDatabaseAndCreationFailed": "Δεν υπάρχει βάση δεδομένων και η δημιουργία απέτυχε! Το σενάριο τερματίζεται!", "mismatchedLink": "Ο σύνδεσμος δεν ταιριάζει, παρακαλώ ανανεώστε τη σελίδα!", "startUpdatingConversationTree": "Ξεκινώντας την ενημέρωση του δέντρου συνομιλίας", "selectedItem": "Επιλέξατε {item}", "successSavingChanges": "Οι αλλαγές αποθηκεύτηκαν επιτυχώς!", "codeCopiedToClipboard": "Ο κώδικας αντιγράφηκε στο πρόχειρο!", "contentCopied": "Το περιεχόμενο αντιγράφηκε!", "emptyCommentPrompt": "Το σχόλιο είναι κενό. Θέλετε να ορίσετε το σχόλιο ως \\"κενό\\";", "confirmDeleteLinkData": "Ο σύνδεσμος που εντοπίστηκε είναι {item}! Είστε σίγουροι ότι θέλετε να διαγράψετε αυτά τα δεδομένα συνδέσμου; Όλο το περιεχόμενο της συζήτησης και τα σχόλια θα διαγραφούν!", "confirmCurrentURL": "Ο σύνδεσμος που εντοπίστηκε είναι {item}! Είστε σίγουροι;", "commentSetToEmpty": "Το σχόλιο ορίστηκε ως \\"κενό\\"", "enterCommentFirst": "Παρακαλώ εισάγετε πρώτα ένα σχόλιο", "commentSaved": "Το σχόλιο αποθηκεύτηκε", "conversationDataDeleted": "Τα δεδομένα συνομιλίας διαγράφηκαν επιτυχώς", "executeSearchWithQuery": "Εκτέλεση αναζήτησης: {item}", "searchPlaceholder": "Εισάγετε λέξεις κλειδιά αναζήτησης...", "searchButton": "Αναζήτηση", "searchInContent": "Στο περιεχόμενο της συνομιλίας", "searchInComments": "Στα σχόλια", "searchInBoth": "Τόσο στο περιεχόμενο όσο και στα σχόλια", "goToPrevious": "Πήγαινε στο προηγούμενο", "goToNext": "Πήγαινε στο επόμενο", "numberOfMatches": "{matches} αντιστοιχίες", "nodeDetails": "Λεπτομέρειες", "enterComment": "Πληκτρολογήστε σχόλιο", "userCommentSave": "Αποθήκευση", "userCommentCancel": "Ακύρωση", "userCommentClear": "Καθαρισμός", "openAdminPanel": "Πίνακας Διαχείρισης", "allCategoriesFilter": "Όλες οι Κατηγορίες", "conversationTitle": "Τίτλος", "actionOptions": "Ενέργειες", "conversationCategory": "Κατηγορία", "conversationTags": "Ετικέτες" }, "en": { "chatTreeRunning": "🥳🌳ChatTree🌳 is Running!🎉", "updateCurrentConversationTree": "🌈 Update Current Conversation Tree 🌈", "adjustBackgroundColorAndOpacity": "🎨 Adjust Background Color and Opacity 🎨", "toggleConversationTree": "🌳 Show/Hide Conversation Tree 🌳", "noDatabaseAndCreationFailed": "No database, and creation failed! The script is terminating.", "mismatchedLink": "Link does not match, please refresh the page!", "startUpdatingConversationTree": "Starting to update the conversation tree", "selectedItem": "You selected {item}", "successSavingChanges": "Changes Saved Successfully!", "codeCopiedToClipboard": "Code Copied to Clipboard!", "contentCopied": "Content Copied!", "emptyCommentPrompt": "The comment is empty. Do you want to set the comment to \\"empty\\"?", "confirmDeleteLinkData": "Detected link is {item}! Are you sure you want to delete this link's information? All conversation content and comments will be deleted!", "confirmCurrentURL": "Detected link is {item}! Are you sure?", "commentSetToEmpty": "Comment set to \\"empty\\"", "enterCommentFirst": "Please enter a comment first", "commentSaved": "Comment Saved", "conversationDataDeleted": "Conversation Data Successfully Deleted", "executeSearchWithQuery": "Executing Search: {item}", "searchPlaceholder": "Enter search keywords...", "searchButton": "Search", "searchInContent": "Conversation Content", "searchInComments": "User Comments", "searchInBoth": "Content & Comments", "goToPrevious": "Go to Previous", "goToNext": "Go to Next", "numberOfMatches": "{matches} matches found", "nodeDetails": "Details", "enterComment": "Please Enter Comment", "userCommentSave": "Save", "userCommentCancel": "Cancel", "userCommentClear": "Clear", "openAdminPanel": "Admin Panel", "allCategoriesFilter": "All Categories", "conversationTitle": "Title", "actionOptions": "Actions", "conversationCategory": "Category", "conversationTags": "Tags" }, "eo": { "chatTreeRunning": "🥳🌳ChatTree🌳 funkcias!🎉", "updateCurrentConversationTree": "🌈 Ĝisdatigi la aktivan konversacian arbon 🌈", "adjustBackgroundColorAndOpacity": "🎨 Agordi fondon koloron kaj opakecon 🎨", "toggleConversationTree": "🌳 Montri/Kaŝi konversacian arbon 🌳", "noDatabaseAndCreationFailed": "Neniu datumbazo, kaj ne sukcesis krei! Skripto eliras!", "mismatchedLink": "Ligilo ne kongruas, bonvolu refreŝigi la paĝon!", "startUpdatingConversationTree": "Komenci ĝisdatigi la konversacian arbon", "selectedItem": "Vi selektis {item}", "successSavingChanges": "Ŝanĝoj sukcese konservitaj!", "codeCopiedToClipboard": "Kodo estis kopii al tondejo!", "contentCopied": "Enhavo estis kopii!", "emptyCommentPrompt": "Komento estas malplena. Ĉu vi volas agordi komenton al \\"malplena\\"?", "confirmDeleteLinkData": "Detektis ligilon {item}! Ĉu vi certas, ke vi volas forigi ĉi tiun ligilon informon? Ĉiuj konversaciaj enhavoj kaj komentoj estos forigitaj!", "confirmCurrentURL": "Detektis ligilon {item}! Ĉu vi certas?", "commentSetToEmpty": "Komento estis agordita al \\"malplena\\"", "enterCommentFirst": "Bonvolu unue enigi komenton", "commentSaved": "Komento konservita", "conversationDataDeleted": "Konversaciaj datenoj sukcese forigitaj", "executeSearchWithQuery": "Efektivi serĉon: {item}", "searchPlaceholder": "Enmetu serĉajn ŝlosilvortojn...", "searchButton": "Serĉi", "searchInContent": "Konversacia enhavo", "searchInComments": "Komentoj de uzantoj", "searchInBoth": "Enhavo & Komentoj", "goToPrevious": "Iru al antaŭa", "goToNext": "Iru al sekvanta", "numberOfMatches": "{matches} kongruajn trovis", "nodeDetails": "Detaloj", "enterComment": "Bonvolu Enmeti Komenton", "userCommentSave": "Konservi", "userCommentCancel": "Nuligi", "userCommentClear": "Forigi", "openAdminPanel": "Malfermi Adminan Panelon", "allCategoriesFilter": "Ĉiuj Kategorioj", "conversationTitle": "Titolo", "actionOptions": "Agadoj", "conversationCategory": "Kategorio", "conversationTags": "Etikedoj" }, "es": { "chatTreeRunning": "🥳🌳¡ChatTree🌳 en funcionamiento!🎉", "updateCurrentConversationTree": "🌈 Actualizar el árbol de conversación actual 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ajustar color de fondo y opacidad 🎨", "toggleConversationTree": "🌳 Mostrar/Ocultar árbol de conversación 🌳", "noDatabaseAndCreationFailed": "¡No hay base de datos y no se pudo crear! ¡Saliendo del script!", "mismatchedLink": "¡El enlace no coincide, por favor actualiza la página!", "startUpdatingConversationTree": "Comenzar a actualizar el árbol de conversación", "selectedItem": "Seleccionaste {item}", "successSavingChanges": "¡Cambios guardados con éxito!", "codeCopiedToClipboard": "¡Código copiado al portapapeles!", "contentCopied": "¡Contenido copiado!", "emptyCommentPrompt": "El comentario está vacío. ¿Quieres establecer el comentario como \\"vacío\\"?", "confirmDeleteLinkData": "¡Se detectó el enlace {item}! ¿Estás seguro de que quieres eliminar la información de este enlace? ¡Toda la conversación y los comentarios se eliminarán!", "confirmCurrentURL": "¡Se detectó el enlace {item}! ¿Estás seguro?", "commentSetToEmpty": "Comentario establecido como \\"vacío\\"", "enterCommentFirst": "Por favor, ingresa un comentario primero", "commentSaved": "Comentario guardado", "conversationDataDeleted": "Datos de la conversación eliminados con éxito", "executeSearchWithQuery": "Ejecutar búsqueda: {item}", "searchPlaceholder": "Ingrese palabras clave para buscar...", "searchButton": "Buscar", "searchInContent": "Contenido de la conversación", "searchInComments": "Comentarios de usuarios", "searchInBoth": "Contenido y comentarios", "goToPrevious": "Ir al anterior", "goToNext": "Ir al siguiente", "numberOfMatches": "{matches} coincidencias encontradas", "nodeDetails": "Detalles", "enterComment": "Por Favor Introduce un Comentario", "userCommentSave": "Guardar", "userCommentCancel": "Cancelar", "userCommentClear": "Borrar", "openAdminPanel": "Abrir Panel de Administración", "allCategoriesFilter": "Todas las Categorías", "conversationTitle": "Título", "actionOptions": "Opciones", "conversationCategory": "Categoría", "conversationTags": "Etiquetas" }, "fi": { "chatTreeRunning": "🥳🌳ChatTree🌳 on käynnissä!🎉", "updateCurrentConversationTree": "🌈 Päivitä nykyinen keskustelupuu 🌈", "adjustBackgroundColorAndOpacity": "🎨 Säädä taustavärin ja läpinäkyvyyden 🎨", "toggleConversationTree": "🌳 Näytä/Piilota keskustelupuu 🌳", "noDatabaseAndCreationFailed": "Tietokantaa ei ole, eikä luonti onnistunut! Skripti päättyy!", "mismatchedLink": "Linkki ei täsmää, päivitä sivu!", "startUpdatingConversationTree": "Aloita keskustelupuun päivittäminen", "selectedItem": "Valitsit kohteen {item}", "successSavingChanges": "Muutosten tallennus onnistui!", "codeCopiedToClipboard": "Koodi kopioitu leikepöydälle!", "contentCopied": "Sisältö kopioitu!", "emptyCommentPrompt": "Kommentti on tyhjä. Haluatko asettaa kommentin \\"tyhjäksi\\"?", "confirmDeleteLinkData": "Linkki {item} havaittu! Haluatko varmasti poistaa tämän linkin tiedot? Kaikki keskustelut ja kommentit poistetaan!", "confirmCurrentURL": "Linkki {item} havaittu! Oletko varma?", "commentSetToEmpty": "Kommentti asetettu \\"tyhjäksi\\"", "enterCommentFirst": "Syötä kommentti ensin", "commentSaved": "Kommentti tallennettu", "conversationDataDeleted": "Keskustelutiedot poistettu onnistuneesti", "executeSearchWithQuery": "Suorita haku: {item}", "searchPlaceholder": "Anna hakusanat...", "searchButton": "Hae", "searchInContent": "Keskustelun sisältö", "searchInComments": "Käyttäjien kommentit", "searchInBoth": "Sisältö ja kommentit", "goToPrevious": "Mene edelliseen", "goToNext": "Mene seuraavaan", "numberOfMatches": "{matches} osumaa löydetty", "nodeDetails": "Tiedot", "enterComment": "Ole Hyvä ja Kirjoita Kommentti", "userCommentSave": "Tallenna", "userCommentCancel": "Peruuta", "userCommentClear": "Tyhjennä", "openAdminPanel": "Avaa Hallintapaneeli", "allCategoriesFilter": "Kaikki Kategoriat", "conversationTitle": "Otsikko", "actionOptions": "Toiminnot", "conversationCategory": "Kategoria", "conversationTags": "Tagit" }, "fr": { "chatTreeRunning": "🥳🌳ChatTree🌳 est en cours d'exécution !🎉", "updateCurrentConversationTree": "🌈 Mettre à jour l'arbre de conversation actuel 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ajuster la couleur de fond et l'opacité 🎨", "toggleConversationTree": "🌳 Afficher/Masquer l'arbre de conversation 🌳", "noDatabaseAndCreationFailed": "Pas de base de données et la création a échoué ! Sortie du script !", "mismatchedLink": "Le lien ne correspond pas, veuillez rafraîchir la page !", "startUpdatingConversationTree": "Commencer à mettre à jour l'arbre de conversation", "selectedItem": "Vous avez sélectionné {item}", "successSavingChanges": "Modifications enregistrées avec succès !", "codeCopiedToClipboard": "Le code a été copié dans le presse-papiers !", "contentCopied": "Contenu copié !", "emptyCommentPrompt": "Le commentaire est vide. Voulez-vous définir le commentaire comme \\"vide\\" ?", "confirmDeleteLinkData": "Le lien {item} a été détecté ! Êtes-vous sûr de vouloir supprimer les informations de ce lien ? Toutes les conversations et les commentaires seront supprimés !", "confirmCurrentURL": "Le lien {item} a été détecté ! Êtes-vous sûr ?", "commentSetToEmpty": "Commentaire défini comme \\"vide\\"", "enterCommentFirst": "Veuillez d'abord entrer un commentaire", "commentSaved": "Commentaire enregistré", "conversationDataDeleted": "Données de conversation supprimées avec succès", "executeSearchWithQuery": "Effectuer une recherche : {item}", "searchPlaceholder": "Entrez des mots-clés pour rechercher...", "searchButton": "Rechercher", "searchInContent": "Contenu de la conversation", "searchInComments": "Commentaires des utilisateurs", "searchInBoth": "Contenu et commentaires", "goToPrevious": "Aller au précédent", "goToNext": "Aller au suivant", "numberOfMatches": "{matches} correspondances trouvées", "nodeDetails": "Détails", "enterComment": "Veuillez Entrer un Commentaire", "userCommentSave": "Enregistrer", "userCommentCancel": "Annuler", "userCommentClear": "Effacer", "openAdminPanel": "Ouvrir le Panneau d'Administration", "allCategoriesFilter": "Toutes les Catégories", "conversationTitle": "Titre", "actionOptions": "Options", "conversationCategory": "Catégorie", "conversationTags": "Étiquettes" }, "fr-CA": { "chatTreeRunning": "🥳🌳ChatTree🌳 est en marche !🎉", "updateCurrentConversationTree": "🌈 Mettre à jour l'arbre de conversation actuel 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ajustez la couleur de fond et l'opacité 🎨", "toggleConversationTree": "🌳 Afficher/Masquer l'arbre de conversation 🌳", "noDatabaseAndCreationFailed": "Pas de base de données et la création a échoué ! Le script se termine !", "mismatchedLink": "Le lien ne correspond pas, veuillez rafraîchir la page !", "startUpdatingConversationTree": "Commencer la mise à jour de l'arbre de conversation", "selectedItem": "Vous avez sélectionné {item}", "successSavingChanges": "Modifications enregistrées avec succès !", "codeCopiedToClipboard": "Le code a été copié dans le presse-papiers !", "contentCopied": "Contenu copié !", "emptyCommentPrompt": "Le commentaire est vide. Souhaitez-vous définir le commentaire comme \\"vide\\" ?", "confirmDeleteLinkData": "Le lien {item} a été détecté ! Êtes-vous sûr de vouloir supprimer les données de ce lien ? Toutes les conversations et les commentaires seront supprimés !", "confirmCurrentURL": "Le lien {item} a été détecté ! Êtes-vous sûr ?", "commentSetToEmpty": "Commentaire défini comme \\"vide\\"", "enterCommentFirst": "Veuillez d'abord entrer un commentaire", "commentSaved": "Commentaire sauvegardé", "conversationDataDeleted": "Données de conversation supprimées avec succès", "executeSearchWithQuery": "Exécuter la recherche : {item}", "searchPlaceholder": "Entrez des mots-clés pour chercher...", "searchButton": "Rechercher", "searchInContent": "Contenu de la conversation", "searchInComments": "Commentaires des utilisateurs", "searchInBoth": "Contenu et commentaires", "goToPrevious": "Aller au précédent", "goToNext": "Aller au suivant", "numberOfMatches": "{matches} correspondances trouvées", "nodeDetails": "Détails", "enterComment": "Veuillez Entrer un Commentaire", "userCommentSave": "Enregistrer", "userCommentCancel": "Annuler", "userCommentClear": "Effacer", "openAdminPanel": "Ouvrir le Panneau Administratif", "allCategoriesFilter": "Toutes les Catégories", "conversationTitle": "Titre", "actionOptions": "Options", "conversationCategory": "Catégorie", "conversationTags": "Balises" }, "he": { "chatTreeRunning": "🥳🌳ChatTree🌳 פועל!🎉", "updateCurrentConversationTree": "🌈 עדכן את עץ השיחה הנוכחי 🌈", "adjustBackgroundColorAndOpacity": "🎨 כוונן את צבע הרקע והשקיפות 🎨", "toggleConversationTree": "🌳 הצג/הסתר עץ שיחה 🌳", "noDatabaseAndCreationFailed": "אין מסד נתונים ויצירתו נכשלה! סקריפט יוצא!", "mismatchedLink": "הקישור אינו תואם, אנא רענן את הדף!", "startUpdatingConversationTree": "התחל לעדכן את עץ השיחה", "selectedItem": "בחרת {item}", "successSavingChanges": "השינויים נשמרו בהצלחה!", "codeCopiedToClipboard": "הקוד הועתק ללוח!", "contentCopied": "התוכן הועתק!", "emptyCommentPrompt": "ההערה ריקה. האם תרצה להגדיר את ההערה כ\\"ריקה\\"?", "confirmDeleteLinkData": "הקישור {item} זוהה! האם אתה בטוח שאתה רוצה למחוק את נתוני הקישור הזה? כל השיחות וההערות יימחקו!", "confirmCurrentURL": "הקישור {item} זוהה! האם אתה בטוח?", "commentSetToEmpty": "ההערה הוגדרה כ\\"ריקה\\"", "enterCommentFirst": "אנא הזן הערה קודם", "commentSaved": "ההערה נשמרה", "conversationDataDeleted": "נתוני השיחה נמחקו בהצלחה", "executeSearchWithQuery": "בצע חיפוש: {item}", "searchPlaceholder": "הזן מילות חיפוש...", "searchButton": "חפש", "searchInContent": "תוכן השיחה", "searchInComments": "הערות משתמש", "searchInBoth": "תוכן והערות", "goToPrevious": "עבור לקודם", "goToNext": "עבור להבא", "numberOfMatches": "{matches} תוצאות", "nodeDetails": "פרטים", "enterComment": "אנא הקלד תגובה", "userCommentSave": "שמור", "userCommentCancel": "בטל", "userCommentClear": "נקה", "openAdminPanel": "פתח לוח בקרה", "allCategoriesFilter": "כל הקטגוריות", "conversationTitle": "כותרת", "actionOptions": "אפשרויות", "conversationCategory": "קטגוריה", "conversationTags": "תגיות" }, "hu": { "chatTreeRunning": "🥳🌳ChatTree🌳 fut!🎉", "updateCurrentConversationTree": "🌈 Frissítsd az aktuális beszélgetésfát 🌈", "adjustBackgroundColorAndOpacity": "🎨 Állítsd be a háttérszín és az átlátszóság értékeit 🎨", "toggleConversationTree": "🌳 Beszélgetésfa megjelenítése/elrejtése 🌳", "noDatabaseAndCreationFailed": "Nincs adatbázis és a létrehozás sikertelen! A szkript kilép!", "mismatchedLink": "A link nem egyezik, kérjük, frissítse az oldalt!", "startUpdatingConversationTree": "Beszélgetésfa frissítésének kezdése", "selectedItem": "Kiválasztott elem: {item}", "successSavingChanges": "A változások mentése sikerült!", "codeCopiedToClipboard": "A kód vágólapra másolva!", "contentCopied": "A tartalom másolva!", "emptyCommentPrompt": "A megjegyzés üres. Beállítja \\"üres\\"-ként?", "confirmDeleteLinkData": "A {item} link észlelve! Biztosan törli e link adatát? Minden beszélgetés és megjegyzés törlődik!", "confirmCurrentURL": "A {item} link észlelve! Biztos benne?", "commentSetToEmpty": "A megjegyzés \\"üres\\"-re van állítva", "enterCommentFirst": "Kérjük, először írja be a megjegyzést", "commentSaved": "Megjegyzés mentve", "conversationDataDeleted": "A beszélgetés adatai sikeresen törölve", "executeSearchWithQuery": "Keresés indítása: {item}", "searchPlaceholder": "Írja be a keresendő kifejezéseket...", "searchButton": "Keresés", "searchInContent": "Beszélgetés tartalma", "searchInComments": "Felhasználói megjegyzések", "searchInBoth": "Tartalom és megjegyzések", "goToPrevious": "Ugrás az előzőre", "goToNext": "Ugrás a következőre", "numberOfMatches": "{matches} találat", "nodeDetails": "Részletek", "enterComment": "Kérjük, írja be a megjegyzést", "userCommentSave": "Mentés", "userCommentCancel": "Mégse", "userCommentClear": "Törlés", "openAdminPanel": "Admin Panel Megnyitása", "allCategoriesFilter": "Minden Kategória", "conversationTitle": "Cím", "actionOptions": "Műveletek", "conversationCategory": "Kategória", "conversationTags": "Címkék" }, "id": { "chatTreeRunning": "🥳🌳ChatTree🌳 Sedang Berjalan!🎉", "updateCurrentConversationTree": "🌈 Perbarui Pohon Percakapan Saat Ini 🌈", "adjustBackgroundColorAndOpacity": "🎨 Sesuaikan Warna Latar Belakang dan Kecerahan 🎨", "toggleConversationTree": "🌳 Tampilkan/Sembunyikan Pohon Percakapan 🌳", "noDatabaseAndCreationFailed": "Tidak ada database, dan pembuatan gagal! Script keluar!", "mismatchedLink": "Tautan tidak cocok, silakan segarkan halaman!", "startUpdatingConversationTree": "Mulai memperbarui Pohon Percakapan", "selectedItem": "Anda memilih {item}", "successSavingChanges": "Berhasil Menyimpan Perubahan!", "codeCopiedToClipboard": "Kode disalin ke papan klip!", "contentCopied": "Konten disalin!", "emptyCommentPrompt": "Komentar kosong. Apakah Anda ingin mengatur komentar ke \\"kosong\\"?", "confirmDeleteLinkData": "Tautan {item} terdeteksi! Apakah Anda yakin ingin menghapus data tautan ini? Semua konten percakapan dan komentar akan dihapus!", "confirmCurrentURL": "Tautan {item} terdeteksi! Apakah Anda yakin?", "commentSetToEmpty": "Komentar diatur ke \\"kosong\\"", "enterCommentFirst": "Silakan masukkan komentar terlebih dahulu", "commentSaved": "Komentar disimpan", "conversationDataDeleted": "Data Percakapan Berhasil Dihapus", "executeSearchWithQuery": "Melakukan pencarian: {item}", "searchPlaceholder": "Masukkan kata kunci pencarian...", "searchButton": "Cari", "searchInContent": "Konten Percakapan", "searchInComments": "Komentar Pengguna", "searchInBoth": "Konten dan Komentar", "goToPrevious": "Pergi ke Sebelumnya", "goToNext": "Pergi ke Berikutnya", "numberOfMatches": "{matches} hasil pencarian", "nodeDetails": "Detail", "enterComment": "Silakan masukkan komentar", "userCommentSave": "Simpan", "userCommentCancel": "Batal", "userCommentClear": "Hapus", "openAdminPanel": "Buka Panel Admin", "allCategoriesFilter": "Semua Kategori", "conversationTitle": "Judul", "actionOptions": "Opsi", "conversationCategory": "Kategori", "conversationTags": "Tag" }, "it": { "chatTreeRunning": "🥳🌳ChatTree🌳 in esecuzione!🎉", "updateCurrentConversationTree": "🌈 Aggiorna l'albero di conversazione corrente 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ajusta il colore di sfondo e l'opacità 🎨", "toggleConversationTree": "🌳 Mostra/Nascondi l'albero di conversazione 🌳", "noDatabaseAndCreationFailed": "Nessun database e la creazione non è riuscita! Script interrotto!", "mismatchedLink": "Il link non corrisponde, si prega di aggiornare la pagina!", "startUpdatingConversationTree": "Inizia l'aggiornamento dell'albero di conversazione", "selectedItem": "Hai selezionato {item}", "successSavingChanges": "Modifiche salvate con successo!", "codeCopiedToClipboard": "Codice copiato negli appunti!", "contentCopied": "Contenuto copiato!", "emptyCommentPrompt": "Il commento è vuoto. Vuoi impostare il commento su 'vuoto'?", "confirmDeleteLinkData": "Link rilevato {item}! Sei sicuro di voler eliminare le informazioni di questo link? Tutti i contenuti della conversazione e i commenti verranno eliminati!", "confirmCurrentURL": "Link rilevato {item}! Confermi?", "commentSetToEmpty": "Il commento è stato impostato su 'vuoto'", "enterCommentFirst": "Per favore, inserisci prima un commento", "commentSaved": "Commento salvato", "conversationDataDeleted": "Dati della conversazione eliminati con successo", "executeSearchWithQuery": "Esegui ricerca: {item}", "searchPlaceholder": "Inserisci parole chiave per la ricerca...", "searchButton": "Cerca", "searchInContent": "Contenuto della conversazione", "searchInComments": "Commenti degli utenti", "searchInBoth": "Contenuti e commenti", "goToPrevious": "Vai al precedente", "goToNext": "Vai al successivo", "numberOfMatches": "{matches} corrispondenze trovate", "nodeDetails": "Dettagli", "enterComment": "Per favore, inserisci un commento", "userCommentSave": "Salva", "userCommentCancel": "Annulla", "userCommentClear": "Cancella", "openAdminPanel": "Apri Pannello di Amministrazione", "allCategoriesFilter": "Tutte le Categorie", "conversationTitle": "Titolo", "actionOptions": "Opzioni", "conversationCategory": "Categoria", "conversationTags": "Tag" }, "ja": { "chatTreeRunning": "🥳🌳ChatTree🌳実行中!🎉", "updateCurrentConversationTree": "🌈 現在の会話ツリーを更新 🌈", "adjustBackgroundColorAndOpacity": "🎨 背景色と透明度を調整 🎨", "toggleConversationTree": "🌳 会話ツリーを表示/非表示 🌳", "noDatabaseAndCreationFailed": "データベースがなく、作成に失敗しました!スクリプトを終了します!", "mismatchedLink": "リンクが一致しません、ページを更新してください!", "startUpdatingConversationTree": "会話ツリーの更新を開始", "selectedItem": "{item}を選択しました", "successSavingChanges": "変更の保存に成功しました!", "codeCopiedToClipboard": "コードがクリップボードにコピーされました!", "contentCopied": "内容がコピーされました!", "emptyCommentPrompt": "コメントが空です。コメントを'空'に設定しますか?", "confirmDeleteLinkData": "{item}のリンクが検出されました! このリンクの情報を削除してもよろしいですか? すべての会話内容とコメントが削除されます!", "confirmCurrentURL": "{item}のリンクが検出されました!よろしいですか?", "commentSetToEmpty": "コメントが'空'に設定されました", "enterCommentFirst": "先にコメントを入力してください", "commentSaved": "コメントが保存されました", "conversationDataDeleted": "会話データが正常に削除されました", "executeSearchWithQuery": "検索を実行:{item}", "searchPlaceholder": "検索キーワードを入力...", "searchButton": "検索", "searchInContent": "会話の内容", "searchInComments": "ユーザーコメント", "searchInBoth": "内容とコメント", "goToPrevious": "前へ", "goToNext": "次へ", "numberOfMatches": "一致する項目{matches}件", "nodeDetails": "詳細", "enterComment": "コメントを入力してください", "userCommentSave": "保存", "userCommentCancel": "キャンセル", "userCommentClear": "クリア", "openAdminPanel": "管理パネルを開く", "allCategoriesFilter": "すべてのカテゴリ", "conversationTitle": "タイトル", "actionOptions": "オプション", "conversationCategory": "カテゴリ", "conversationTags": "タグ" }, "ka": { "chatTreeRunning": "🥳🌳ChatTree🌳 გაშვებულია!🎉", "updateCurrentConversationTree": "🌈 განაახლეთ ამჟამინდელი სასაუბრო ხე 🌈", "adjustBackgroundColorAndOpacity": "🎨 გაასწორეთ ფონის ფერი და გამჭვირვალობა 🎨", "toggleConversationTree": "🌳 ჩვენება/დამალვა სასაუბრო ხე 🌳", "noDatabaseAndCreationFailed": "არ არის მონაცემთა ბაზა და შექმნა ვერ ხერხდება! სკრიპტი გამოირიყება!", "mismatchedLink": "ბმული არ ემთხვევა, გთხოვთ, განაახლოთ გვერდი!", "startUpdatingConversationTree": "სასაუბრო ხის განახლების დაწყება", "selectedItem": "თქვენ აირჩიეთ {item}", "successSavingChanges": "ცვლილებები წარმატებით შენახულია!", "codeCopiedToClipboard": "კოდი კოპირებულია ბუფერში!", "contentCopied": "კონტენტი კოპირებულია!", "emptyCommentPrompt": "კომენტარი ცარიელია. გსურთ კომენტარი 'ცარიელი' განსაზღვროთ?", "confirmDeleteLinkData": "{item} ბმული აღმოჩენილია! დარწმუნებული ხართ, რომ გსურთ ამ ბმულის ინფორმაციის წაშლა? ყველა სასაუბრო კონტენტი და კომენტარი წაიშლება!", "confirmCurrentURL": "{item} ბმული აღმოჩენილია! დარწმუნებული ხართ?", "commentSetToEmpty": "კომენტარი 'ცარიელია' განსაზღვრულია", "enterCommentFirst": "გთხოვთ, ჯერ შეიყვანეთ კომენტარი", "commentSaved": "კომენტარი შენახულია", "conversationDataDeleted": "სასაუბრო მონაცემები წარმატებით წაიშალა", "executeSearchWithQuery": "ძიება შესრულება: {item}", "searchPlaceholder": "შეიყვანეთ ძიების სიტყვები...", "searchButton": "ძებნა", "searchInContent": "კონვერსიის კონტენტი", "searchInComments": "მომხმარებლის კომენტარები", "searchInBoth": "კონტენტი და კომენტარები", "goToPrevious": "წინაში გადასვლა", "goToNext": "შემდეგში გადასვლა", "numberOfMatches": "{matches} შესატყვისი", "nodeDetails": "დეტალები", "enterComment": "გთხოვთ შეიყვანოთ კომენტარი", "userCommentSave": "შენახვა", "userCommentCancel": "გაუქმება", "userCommentClear": "გასუფთავება", "openAdminPanel": "ადმინის პანელის გახსნა", "allCategoriesFilter": "ყველა კატეგორია", "conversationTitle": "სათაური", "actionOptions": "ოფციები", "conversationCategory": "კატეგორია", "conversationTags": "თეგები" }, "ko": { "chatTreeRunning": "🥳🌳ChatTree🌳 실행 중!🎉", "updateCurrentConversationTree": "🌈 현재 대화 트리 업데이트 🌈", "adjustBackgroundColorAndOpacity": "🎨 배경색과 투명도 조정 🎨", "toggleConversationTree": "🌳 대화 트리 표시/숨기기 🌳", "noDatabaseAndCreationFailed": "데이터베이스가 없으며 생성에 실패했습니다! 스크립트 종료!", "mismatchedLink": "링크가 일치하지 않습니다. 페이지를 새로고침하세요!", "startUpdatingConversationTree": "대화 트리 업데이트 시작", "selectedItem": "{item}를 선택했습니다", "successSavingChanges": "변경 사항이 성공적으로 저장되었습니다!", "codeCopiedToClipboard": "코드가 클립보드에 복사되었습니다!", "contentCopied": "내용이 복사되었습니다!", "emptyCommentPrompt": "댓글이 비어 있습니다. 댓글을 '비움'으로 설정하시겠습니까?", "confirmDeleteLinkData": "{item} 링크를 감지했습니다! 이 링크의 정보를 삭제하시겠습니까? 모든 대화 내용과 댓글이 삭제됩니다!", "confirmCurrentURL": "{item} 링크를 감지했습니다! 확인하시겠습니까?", "commentSetToEmpty": "댓글이 '비움'으로 설정되었습니다", "enterCommentFirst": "먼저 댓글을 입력해주세요", "commentSaved": "댓글이 저장되었습니다", "conversationDataDeleted": "대화 데이터가 성공적으로 삭제되었습니다", "executeSearchWithQuery": "검색 실행: {item}", "searchPlaceholder": "검색어를 입력하세요...", "searchButton": "검색", "searchInContent": "대화 내용", "searchInComments": "사용자 코멘트", "searchInBoth": "내용과 코멘트", "goToPrevious": "이전으로", "goToNext": "다음으로", "numberOfMatches": "{matches}개의 일치 항목", "nodeDetails": "세부 정보", "enterComment": "댓글을 입력하세요", "userCommentSave": "저장", "userCommentCancel": "취소", "userCommentClear": "지우기", "openAdminPanel": "관리 패널", "allCategoriesFilter": "모든 카테고리", "conversationTitle": "제목", "actionOptions": "작업", "conversationCategory": "카테고리", "conversationTags": "태그" }, "nb": { "chatTreeRunning": "🥳🌳ChatTree🌳 er i gang! 🎉", "updateCurrentConversationTree": "🌈 Oppdater gjeldende samtale-tre 🌈", "adjustBackgroundColorAndOpacity": "🎨 Juster bakgrunnsfarge og opasitet 🎨", "toggleConversationTree": "🌳 Vis/Skjul samtale-tre 🌳", "noDatabaseAndCreationFailed": "Ingen database, og opprettelsen mislyktes! Skriptet avslutter!", "mismatchedLink": "Lenken stemmer ikke, vennligst oppfrisk siden!", "startUpdatingConversationTree": "Begynner å oppdatere samtale-treet", "selectedItem": "Du valgte {item}", "successSavingChanges": "Endringene ble lagret!", "codeCopiedToClipboard": "Koden er kopiert til utklippstavlen!", "contentCopied": "Innholdet er kopiert!", "emptyCommentPrompt": "Kommentaren er tom. Vil du sette kommentaren til \\"tom\\"?", "confirmDeleteLinkData": "Linken er {item}! Er du sikker på at du vil slette denne linkens informasjon? All samtale og kommentarinnhold vil bli slettet!", "confirmCurrentURL": "Linken er {item}! Er du sikker?", "commentSetToEmpty": "Kommentaren er satt til \\"tom\\"", "enterCommentFirst": "Vennligst skriv en kommentar først", "commentSaved": "Kommentaren er lagret", "conversationDataDeleted": "Samtaledata er slettet", "executeSearchWithQuery": "Utfør søk: {item}", "searchPlaceholder": "Skriv inn søkeord...", "searchButton": "Søk", "searchInContent": "Samtaleinnhold", "searchInComments": "Brukerkommentarer", "searchInBoth": "Innhold og kommentarer", "goToPrevious": "Gå til forrige", "goToNext": "Gå til neste", "numberOfMatches": "{matches} treff", "nodeDetails": "Detaljer", "enterComment": "Vennligst skriv en kommentar", "userCommentSave": "Lagre", "userCommentCancel": "Avbryt", "userCommentClear": "Tøm", "openAdminPanel": "Administrasjonspanel", "allCategoriesFilter": "Alle kategorier", "conversationTitle": "Tittel", "actionOptions": "Handlinger", "conversationCategory": "Kategori", "conversationTags": "Merkelapper" }, "nl": { "chatTreeRunning": "🥳🌳ChatTree🌳 is actief! 🎉", "updateCurrentConversationTree": "🌈 Huidige gespreksboom bijwerken 🌈", "adjustBackgroundColorAndOpacity": "🎨 Achtergrondkleur en opaciteit aanpassen 🎨", "toggleConversationTree": "🌳 Gespreksboom weergeven/verbergen 🌳", "noDatabaseAndCreationFailed": "Geen database en het aanmaken is mislukt! Script wordt afgesloten!", "mismatchedLink": "Link komt niet overeen, ververs de pagina!", "startUpdatingConversationTree": "Begint met het bijwerken van de gespreksboom", "selectedItem": "Je hebt {item} geselecteerd", "successSavingChanges": "Wijzigingen succesvol opgeslagen!", "codeCopiedToClipboard": "Code gekopieerd naar klembord!", "contentCopied": "Inhoud gekopieerd!", "emptyCommentPrompt": "De opmerking is leeg. Wil je de opmerking instellen op \\"leeg\\"?", "confirmDeleteLinkData": "Gedetecteerde link is {item}! Weet je zeker dat je de informatie van deze link wilt verwijderen? Alle gespreks- en opmerkingsinhoud zal worden verwijderd!", "confirmCurrentURL": "Gedetecteerde link is {item}! Zeker weten?", "commentSetToEmpty": "Opmerking is ingesteld op \\"leeg\\"", "enterCommentFirst": "Voer eerst een opmerking in", "commentSaved": "Opmerking opgeslagen", "conversationDataDeleted": "Gespreksgegevens succesvol verwijderd", "executeSearchWithQuery": "Zoekopdracht uitvoeren: {item}", "searchPlaceholder": "Voer zoekwoorden in...", "searchButton": "Zoeken", "searchInContent": "In gespreksinhoud", "searchInComments": "In gebruikersopmerkingen", "searchInBoth": "In inhoud en opmerkingen", "goToPrevious": "Ga naar vorige", "goToNext": "Ga naar volgende", "numberOfMatches": "{matches} overeenkomsten", "nodeDetails": "Details", "enterComment": "Voer alstublieft een opmerking in", "userCommentSave": "Opslaan", "userCommentCancel": "Annuleren", "userCommentClear": "Wissen", "openAdminPanel": "Beheerpaneel", "allCategoriesFilter": "Alle categorieën", "conversationTitle": "Titel", "actionOptions": "Acties", "conversationCategory": "Categorie", "conversationTags": "Labels" }, "pl": { "chatTreeRunning": "🥳🌳ChatTree🌳 jest uruchomiony! 🎉", "updateCurrentConversationTree": "🌈 Aktualizuj aktualne drzewo rozmów 🌈", "adjustBackgroundColorAndOpacity": "🎨 Dostosuj kolor tła i przezroczystość 🎨", "toggleConversationTree": "🌳 Pokaż/ukryj drzewo rozmów 🌳", "noDatabaseAndCreationFailed": "Brak bazy danych, a jej utworzenie nie powiodło się! Skrypt zakończy działanie!", "mismatchedLink": "Link nie pasuje, odśwież stronę!", "startUpdatingConversationTree": "Rozpoczyna aktualizację drzewa rozmów", "selectedItem": "Wybrałeś {item}", "successSavingChanges": "Zmiany zostały zapisane!", "codeCopiedToClipboard": "Kod skopiowany do schowka!", "contentCopied": "Treść skopiowana!", "emptyCommentPrompt": "Komentarz jest pusty. Czy chcesz ustawić komentarz na \\"pusty\\"?", "confirmDeleteLinkData": "Wykryto link {item}! Czy na pewno chcesz usunąć informacje z tego linku? Wszystkie treści rozmów i komentarze zostaną usunięte!", "confirmCurrentURL": "Wykryto link {item}! Czy jesteś pewien?", "commentSetToEmpty": "Komentarz został ustawiony na \\"pusty\\"", "enterCommentFirst": "Najpierw wprowadź komentarz", "commentSaved": "Komentarz został zapisany", "conversationDataDeleted": "Dane rozmowy zostały pomyślnie usunięte", "executeSearchWithQuery": "Wykonaj wyszukiwanie: {item}", "searchPlaceholder": "Wprowadź słowa kluczowe...", "searchButton": "Szukaj", "searchInContent": "W treści rozmowy", "searchInComments": "W komentarzach użytkowników", "searchInBoth": "W treści i komentarzach", "goToPrevious": "Przejdź do poprzedniego", "goToNext": "Przejdź do następnego", "numberOfMatches": "{matches} dopasowań", "nodeDetails": "Szczegóły", "enterComment": "Proszę wprowadzić komentarz", "userCommentSave": "Zapisz", "userCommentCancel": "Anuluj", "userCommentClear": "Wyczyść", "openAdminPanel": "Panel administracyjny", "allCategoriesFilter": "Wszystkie kategorie", "conversationTitle": "Tytuł", "actionOptions": "Operacje", "conversationCategory": "Kategoria", "conversationTags": "Tagi" }, "pt-PT": { "chatTreeRunning": "🥳🌳ChatTree🌳 em execução! 🎉", "updateCurrentConversationTree": "🌈 Atualizar a árvore de conversação atual 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ajustar a cor de fundo e a opacidade 🎨", "toggleConversationTree": "🌳 Mostrar/ocultar árvore de conversação 🌳", "noDatabaseAndCreationFailed": "Sem base de dados e a criação falhou! Script a encerrar!", "mismatchedLink": "Link não corresponde, por favor atualize a página!", "startUpdatingConversationTree": "A iniciar a atualização da árvore de conversação", "selectedItem": "Selecionou {item}", "successSavingChanges": "Alterações guardadas com sucesso!", "codeCopiedToClipboard": "Código copiado para a área de transferência!", "contentCopied": "Conteúdo copiado!", "emptyCommentPrompt": "O comentário está vazio. Deseja definir o comentário como \\"vazio\\"?", "confirmDeleteLinkData": "O link detetado é {item}! Tem a certeza que quer eliminar as informações deste link? Todo o conteúdo da conversa e comentários serão eliminados!", "confirmCurrentURL": "O link detetado é {item}! Confirma?", "commentSetToEmpty": "O comentário foi definido como \\"vazio\\"", "enterCommentFirst": "Por favor, insira um comentário primeiro", "commentSaved": "Comentário guardado", "conversationDataDeleted": "Dados de conversação eliminados com sucesso", "executeSearchWithQuery": "Executar pesquisa: {item}", "searchPlaceholder": "Insira palavras-chave...", "searchButton": "Pesquisar", "searchInContent": "No conteúdo da conversa", "searchInComments": "Nos comentários do usuário", "searchInBoth": "Em conteúdo e comentários", "goToPrevious": "Ir para o anterior", "goToNext": "Ir para o próximo", "numberOfMatches": "{matches} correspondências", "nodeDetails": "Detalhes", "enterComment": "Insira um comentário", "userCommentSave": "Guardar", "userCommentCancel": "Cancelar", "userCommentClear": "Limpar", "openAdminPanel": "Painel de administração", "allCategoriesFilter": "Todas as categorias", "conversationTitle": "Título", "actionOptions": "Opções", "conversationCategory": "Categoria", "conversationTags": "Etiquetas" }, "pt-BR": { "chatTreeRunning": "🥳🌳ChatTree🌳 em execução! 🎉", "updateCurrentConversationTree": "🌈 Atualizar a árvore de conversa atual 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ajustar a cor de fundo e a opacidade 🎨", "toggleConversationTree": "🌳 Mostrar/esconder árvore de conversa 🌳", "noDatabaseAndCreationFailed": "Sem banco de dados e a criação falhou! Script encerrando!", "mismatchedLink": "Link não corresponde, por favor, atualize a página!", "startUpdatingConversationTree": "Começando a atualizar a árvore de conversa", "selectedItem": "Você selecionou {item}", "successSavingChanges": "Alterações salvas com sucesso!", "codeCopiedToClipboard": "Código copiado para a área de transferência!", "contentCopied": "Conteúdo copiado!", "emptyCommentPrompt": "O comentário está vazio. Você quer definir o comentário como \\"vazio\\"?", "confirmDeleteLinkData": "O link detectado é {item}! Tem certeza de que deseja excluir as informações deste link? Todo o conteúdo da conversa e os comentários serão excluídos!", "confirmCurrentURL": "O link detectado é {item}! Confirma?", "commentSetToEmpty": "O comentário foi definido como \\"vazio\\"", "enterCommentFirst": "Por favor, insira um comentário primeiro", "commentSaved": "Comentário salvo", "conversationDataDeleted": "Dados da conversa excluídos com sucesso", "executeSearchWithQuery": "Executar pesquisa: {item}", "searchPlaceholder": "Digite palavras-chave...", "searchButton": "Pesquisar", "searchInContent": "No conteúdo da conversa", "searchInComments": "Nos comentários do usuário", "searchInBoth": "Em conteúdo e comentários", "goToPrevious": "Ir para o anterior", "goToNext": "Ir para o próximo", "numberOfMatches": "{matches} correspondências", "nodeDetails": "Detalhes", "enterComment": "Digite um comentário", "userCommentSave": "Salvar", "userCommentCancel": "Cancelar", "userCommentClear": "Limpar", "openAdminPanel": "Painel de administração", "allCategoriesFilter": "Todas as categorias", "conversationTitle": "Título", "actionOptions": "Opções", "conversationCategory": "Categoria", "conversationTags": "Tags" }, "ro": { "chatTreeRunning": "🥳🌳ChatTree🌳 este în funcțiune!🎉", "updateCurrentConversationTree": "🌈 Actualizați arborele conversației curente 🌈", "adjustBackgroundColorAndOpacity": "🎨 Ajustați culoarea de fundal și opacitatea 🎨", "toggleConversationTree": "🌳 Afișați/Ascundeți arborele conversației 🌳", "noDatabaseAndCreationFailed": "Nu există bază de date și crearea a eșuat! Scriptul se închide!", "mismatchedLink": "Link-ul nu se potrivește, vă rugăm să reîmprospătați pagina!", "startUpdatingConversationTree": "Începeți să actualizați arborele conversației", "selectedItem": "Ați selectat {item}", "successSavingChanges": "Modificările au fost salvate cu succes!", "codeCopiedToClipboard": "Codul a fost copiat în clipboard!", "contentCopied": "Conținutul a fost copiat!", "emptyCommentPrompt": "Comentariul este gol. Doriți să setați comentariul ca \\"gol\\"?", "confirmDeleteLinkData": "Link detectat ca fiind {item}! Confirmați ștergerea informațiilor acestui link? Tot conținutul conversației și comentariile vor fi șterse!", "confirmCurrentURL": "Link detectat ca fiind {item}! Confirmați?", "commentSetToEmpty": "Comentariu setat ca \\"gol\\"", "enterCommentFirst": "Vă rugăm să introduceți mai întâi un comentariu", "commentSaved": "Comentariu salvat", "conversationDataDeleted": "Datele conversației au fost șterse cu succes", "executeSearchWithQuery": "Executați căutarea: {item}", "searchPlaceholder": "Introduceți cuvinte cheie...", "searchButton": "Căutare", "searchInContent": "În conținutul conversației", "searchInComments": "În comentariile utilizatorului", "searchInBoth": "În conținut și comentarii", "goToPrevious": "Mergi la precedentul", "goToNext": "Mergi la următorul", "numberOfMatches": "{matches} potriviri", "nodeDetails": "Detalii", "enterComment": "Introduceți un comentariu", "userCommentSave": "Salvați", "userCommentCancel": "Anulați", "userCommentClear": "Șterge", "openAdminPanel": "Panou administrativ", "allCategoriesFilter": "Toate categoriile", "conversationTitle": "Titlu", "actionOptions": "Opțiuni", "conversationCategory": "Categorie", "conversationTags": "Etichete" }, "ru": { "chatTreeRunning": "🥳🌳ChatTree🌳 запущен!🎉", "updateCurrentConversationTree": "🌈 Обновить текущее дерево беседы 🌈", "adjustBackgroundColorAndOpacity": "🎨 Настроить цвет фона и прозрачность 🎨", "toggleConversationTree": "🌳 Показать/Скрыть дерево беседы 🌳", "noDatabaseAndCreationFailed": "База данных отсутствует, и создание не удалось! Скрипт выходит!", "mismatchedLink": "Ссылка не совпадает, пожалуйста, обновите страницу!", "startUpdatingConversationTree": "Начать обновление дерева беседы", "selectedItem": "Вы выбрали {item}", "successSavingChanges": "Изменения успешно сохранены!", "codeCopiedToClipboard": "Код скопирован в буфер обмена!", "contentCopied": "Содержимое скопировано!", "emptyCommentPrompt": "Комментарий пуст. Вы хотите установить комментарий как \\"пустой\\"?", "confirmDeleteLinkData": "Обнаружена ссылка {item}! Подтвердить удаление информации этой ссылки? Весь контент беседы и комментарии будут удалены!", "confirmCurrentURL": "Обнаружена ссылка {item}! Подтвердить?", "commentSetToEmpty": "Комментарий установлен как \\"пустой\\"", "enterCommentFirst": "Пожалуйста, сначала введите комментарий", "commentSaved": "Комментарий сохранен", "conversationDataDeleted": "Данные беседы успешно удалены", "executeSearchWithQuery": "Выполнить поиск: {item}", "searchPlaceholder": "Введите ключевые слова...", "searchButton": "Поиск", "searchInContent": "В контенте диалога", "searchInComments": "В комментариях пользователя", "searchInBoth": "В контенте и комментариях", "goToPrevious": "Перейти к предыдущему", "goToNext": "Перейти к следующему", "numberOfMatches": "{matches} совпадений", "nodeDetails": "Подробности", "enterComment": "Введите комментарий", "userCommentSave": "Сохранить", "userCommentCancel": "Отмена", "userCommentClear": "Очистить", "openAdminPanel": "Панель управления", "allCategoriesFilter": "Все категории", "conversationTitle": "Заголовок", "actionOptions": "Опции", "conversationCategory": "Категория", "conversationTags": "Теги" }, "sk": { "chatTreeRunning": "🥳🌳ChatTree🌳 beží!🎉", "updateCurrentConversationTree": "🌈 Aktualizovať aktuálny konverzačný strom 🌈", "adjustBackgroundColorAndOpacity": "🎨 Upraviť farbu pozadia a priehľadnosť 🎨", "toggleConversationTree": "🌳 Zobraziť/Skryť konverzačný strom 🌳", "noDatabaseAndCreationFailed": "Nie je databáza a vytvorenie zlyhalo! Skript končí!", "mismatchedLink": "Odkaz sa nezhoduje, prosím, obnovte stránku!", "startUpdatingConversationTree": "Začať aktualizovať konverzačný strom", "selectedItem": "Vybrali ste {item}", "successSavingChanges": "Zmeny boli úspešne uložené!", "codeCopiedToClipboard": "Kód bol skopírovaný do schránky!", "contentCopied": "Obsah bol skopírovaný!", "emptyCommentPrompt": "Komentár je prázdny. Chcete nastaviť komentár na \\"prázdny\\"?", "confirmDeleteLinkData": "Odkaz detekovaný ako {item}! Potvrdiť odstránenie informácií tohto odkazu? Všetok obsah konverzácie a komentáre budú odstránené!", "confirmCurrentURL": "Odkaz detekovaný ako {item}! Potvrdiť?", "commentSetToEmpty": "Komentár bol nastavený na \\"prázdny\\"", "enterCommentFirst": "Najprv prosím, zadajte komentár", "commentSaved": "Komentár bol uložený", "conversationDataDeleted": "Dáta konverzácie boli úspešne odstránené", "executeSearchWithQuery": "Vykonať vyhľadávanie: {item}", "searchPlaceholder": "Zadajte kľúčové slová pre vyhľadávanie...", "searchButton": "Hľadať", "searchInContent": "V obsahu konverzácie", "searchInComments": "V komentároch", "searchInBoth": "V obsahu a komentároch", "goToPrevious": "Prejsť na predchádzajúci", "goToNext": "Prejsť na ďalší", "numberOfMatches": "{matches} zhôd", "nodeDetails": "Detaily", "enterComment": "Zadajte komentár", "userCommentSave": "Uložiť", "userCommentCancel": "Zrušiť", "userCommentClear": "Vymazať", "openAdminPanel": "Administračný panel", "allCategoriesFilter": "Všetky kategórie", "conversationTitle": "Názov", "actionOptions": "Možnosti", "conversationCategory": "Kategória", "conversationTags": "Značky" }, "sr": { "chatTreeRunning": "🥳🌳ChatTree🌳 je pokrenut!🎉", "updateCurrentConversationTree": "🌈 Ažurirajte trenutno stablo razgovora 🌈", "adjustBackgroundColorAndOpacity": "🎨 Podesite boju pozadine i providnost 🎨", "toggleConversationTree": "🌳 Prikaži/Sakrij stablo razgovora 🌳", "noDatabaseAndCreationFailed": "Nema baze podataka, a kreiranje nije uspelo! Skript izlazi!", "mismatchedLink": "Link se ne podudara, molimo osvežite stranicu!", "startUpdatingConversationTree": "Počnite ažurirati stablo razgovora", "selectedItem": "Izabrali ste {item}", "successSavingChanges": "Promene su uspešno sačuvane!", "codeCopiedToClipboard": "Kod je kopiran u klipbord!", "contentCopied": "Sadržaj je kopiran!", "emptyCommentPrompt": "Komentar je prazan. Da li želite postaviti komentar kao \\"prazan\\"?", "confirmDeleteLinkData": "Link je detektovan kao {item}! Potvrditi brisanje informacija o ovom linku? Svi podaci razgovora i komentari će biti obrisani!", "confirmCurrentURL": "Link je detektovan kao {item}! Potvrditi?", "commentSetToEmpty": "Komentar je postavljen kao \\"prazan\\"", "enterCommentFirst": "Molimo prvo unesite komentar", "commentSaved": "Komentar je sačuvan", "conversationDataDeleted": "Podaci razgovora su uspešno obrisani", "executeSearchWithQuery": "Izvršiti pretragu: {item}", "searchPlaceholder": "Unesite ključne reči za pretragu...", "searchButton": "Pretraga", "searchInContent": "U sadržaju razgovora", "searchInComments": "U komentarima", "searchInBoth": "U sadržaju i komentarima", "goToPrevious": "Idi na prethodni", "goToNext": "Idi na sledeći", "numberOfMatches": "{matches} poklapanja", "nodeDetails": "Detalji", "enterComment": "Unesite komentar", "userCommentSave": "Sačuvaj", "userCommentCancel": "Otkaži", "userCommentClear": "Obriši", "openAdminPanel": "Administrativni panel", "allCategoriesFilter": "Sve kategorije", "conversationTitle": "Naslov", "actionOptions": "Opcije", "conversationCategory": "Kategorija", "conversationTags": "Tagovi" }, "sv": { "chatTreeRunning": "🥳🌳ChatTree🌳 är igång!🎉", "updateCurrentConversationTree": "🌈 Uppdatera aktuellt konversations träd 🌈", "adjustBackgroundColorAndOpacity": "🎨 Justera bakgrundsfärg och opacitet 🎨", "toggleConversationTree": "🌳 Visa/Dölj konversationsträd 🌳", "noDatabaseAndCreationFailed": "Ingen databas, och skapandet misslyckades! Skriptet avslutas!", "mismatchedLink": "Länken matchar inte, vänligen uppdatera sidan!", "startUpdatingConversationTree": "Börja uppdatera konversationsträdet", "selectedItem": "Du valde {item}", "successSavingChanges": "Ändringar sparade framgångsrikt!", "codeCopiedToClipboard": "Koden har kopierats till urklipp!", "contentCopied": "Innehållet har kopierats!", "emptyCommentPrompt": "Kommentaren är tom. Vill du ställa in kommentaren som \\"tom\\"?", "confirmDeleteLinkData": "Länk identifierad som {item}! Bekräfta radering av denna länks information? All konversationsinnehåll och kommentarer kommer att raderas!", "confirmCurrentURL": "Länk identifierad som {item}! Bekräfta?", "commentSetToEmpty": "Kommentaren är inställd på \\"tom\\"", "enterCommentFirst": "Vänligen skriv en kommentar först", "commentSaved": "Kommentar sparad", "conversationDataDeleted": "Konversationsdata har raderats framgångsrikt", "executeSearchWithQuery": "Utför sökning: {item}", "searchPlaceholder": "Ange sökord...", "searchButton": "Sök", "searchInContent": "I konversationsinnehållet", "searchInComments": "I kommentarer", "searchInBoth": "I både innehåll och kommentarer", "goToPrevious": "Gå till föregående", "goToNext": "Gå till nästa", "numberOfMatches": "{matches} träffar", "nodeDetails": "Detaljer", "enterComment": "Ange en kommentar", "userCommentSave": "Spara", "userCommentCancel": "Avbryt", "userCommentClear": "Rensa", "openAdminPanel": "Administrationspanel", "allCategoriesFilter": "Alla kategorier", "conversationTitle": "Titel", "actionOptions": "Åtgärder", "conversationCategory": "Kategori", "conversationTags": "Taggar" }, "th": { "chatTreeRunning": "🥳🌳ChatTree🌳กำลังทำงาน!🎉", "updateCurrentConversationTree": "🌈 อัปเดตต้นไม้การสนทนาปัจจุบัน 🌈", "adjustBackgroundColorAndOpacity": "🎨 ปรับสีพื้นหลังและความโปร่งใส 🎨", "toggleConversationTree": "🌳 แสดง/ซ่อนต้นไม้การสนทนา 🌳", "noDatabaseAndCreationFailed": "ไม่มีฐานข้อมูล และไม่สามารถสร้างสำเร็จ! สคริปต์ออก!", "mismatchedLink": "ลิงก์ไม่ตรงกัน โปรดรีเฟรชหน้า!", "startUpdatingConversationTree": "เริ่มต้นอัปเดตต้นไม้การสนทนา", "selectedItem": "คุณเลือก {item}", "successSavingChanges": "บันทึกการเปลี่ยนแปลงสำเร็จ!", "codeCopiedToClipboard": "คัดลอกโค้ดไปยังคลิปบอร์ดแล้ว!", "contentCopied": "คัดลอกเนื้อหาแล้ว!", "emptyCommentPrompt": "คอมเมนต์ว่างเปล่า คุณต้องการตั้งค่าคอมเมนต์เป็น \\"ว่างเปล่า\\" หรือไม่?", "confirmDeleteLinkData": "ตรวจพบลิงก์เป็น {item}! ยืนยันที่จะลบข้อมูลลิงก์นี้หรือไม่? ข้อมูลการสนทนาและคอมเมนต์ทั้งหมดจะถูกลบ!", "confirmCurrentURL": "ตรวจพบลิงก์เป็น {item}! ยืนยันหรือไม่?", "commentSetToEmpty": "ตั้งค่าคอมเมนต์เป็น \\"ว่างเปล่า\\"", "enterCommentFirst": "โปรดใส่คอมเมนต์ก่อน", "commentSaved": "บันทึกคอมเมนต์แล้ว", "conversationDataDeleted": "ลบข้อมูลการสนทนาสำเร็จ", "executeSearchWithQuery": "ดำเนินการค้นหา: {item}", "searchPlaceholder": "ป้อนคำค้นหา...", "searchButton": "ค้นหา", "searchInContent": "ในเนื้อหาการสนทนา", "searchInComments": "ในความคิดเห็น", "searchInBoth": "ทั้งเนื้อหาและความคิดเห็น", "goToPrevious": "ไปที่ก่อนหน้า", "goToNext": "ไปที่ถัดไป", "numberOfMatches": "{matches} รายการที่ตรงกัน", "nodeDetails": "รายละเอียด", "enterComment": "กรุณาใส่ความคิดเห็น", "userCommentSave": "บันทึก", "userCommentCancel": "ยกเลิก", "userCommentClear": "ล้าง", "openAdminPanel": "แผงการจัดการ", "allCategoriesFilter": "ทุกหมวดหมู่", "conversationTitle": "ชื่อเรื่อง", "actionOptions": "การดำเนินการ", "conversationCategory": "ประเภท", "conversationTags": "แท็ก" }, "tr": { "chatTreeRunning": "🥳🌳ChatTree🌳Çalışıyor!🎉", "updateCurrentConversationTree": "🌈 Güncel Konuşma Ağacını Güncelle 🌈", "adjustBackgroundColorAndOpacity": "🎨 Arka Plan Rengini ve Şeffaflığı Ayarla 🎨", "toggleConversationTree": "🌳 Konuşma Ağacını Göster/Gizle 🌳", "noDatabaseAndCreationFailed": "Veritabanı yok ve oluşturulamadı! Betik çıkıyor!", "mismatchedLink": "Bağlantı eşleşmiyor, lütfen sayfayı yenileyin!", "startUpdatingConversationTree": "Konuşma Ağacını Güncellemeye Başla", "selectedItem": "{item} seçildi", "successSavingChanges": "Değişiklikler Başarıyla Kaydedildi!", "codeCopiedToClipboard": "Kod panoya kopyalandı!", "contentCopied": "İçerik kopyalandı!", "emptyCommentPrompt": "Yorum boş. Yorumu \\"boş\\" olarak ayarlamak istiyor musunuz?", "confirmDeleteLinkData": "{item} bağlantısı tespit edildi! Bu bağlantının bilgilerini silmek istediğinizi onaylıyor musunuz? Tüm konuşma ve yorum içerikleri silinecek!", "confirmCurrentURL": "{item} bağlantısı tespit edildi! Onaylıyor musunuz?", "commentSetToEmpty": "Yorum \\"boş\\" olarak ayarlandı", "enterCommentFirst": "Lütfen önce bir yorum girin", "commentSaved": "Yorum kaydedildi", "conversationDataDeleted": "Konuşma Verileri Başarıyla Silindi", "executeSearchWithQuery": "Arama Yapılıyor: {item}", "searchPlaceholder": "Arama anahtar kelimelerini girin...", "searchButton": "Ara", "searchInContent": "Konuşma İçeriğinde", "searchInComments": "Yorumlarda", "searchInBoth": "İçerik ve Yorumlarda", "goToPrevious": "Öncekine Git", "goToNext": "Sonrakine Git", "numberOfMatches": "{matches} eşleşme", "nodeDetails": "Detaylar", "enterComment": "Bir yorum girin", "userCommentSave": "Kaydet", "userCommentCancel": "İptal", "userCommentClear": "Temizle", "openAdminPanel": "Yönetim Paneli", "allCategoriesFilter": "Tüm Kategoriler", "conversationTitle": "Başlık", "actionOptions": "İşlemler", "conversationCategory": "Kategori", "conversationTags": "Etiketler" }, "uk": { "chatTreeRunning": "🥳🌳ChatTree🌳в роботі!🎉", "updateCurrentConversationTree": "🌈 Оновити поточне дерево розмов 🌈", "adjustBackgroundColorAndOpacity": "🎨 Налаштувати колір фону та прозорість 🎨", "toggleConversationTree": "🌳 Показати/сховати дерево розмов 🌳", "noDatabaseAndCreationFailed": "Немає бази даних, і не вдалося створити! Скрипт виходить!", "mismatchedLink": "Посилання не збігається, будь ласка, оновіть сторінку!", "startUpdatingConversationTree": "Почати оновлення дерева розмов", "selectedItem": "Ви обрали {item}", "successSavingChanges": "Зміни успішно збережено!", "codeCopiedToClipboard": "Код скопійовано в буфер обміну!", "contentCopied": "Зміст скопійовано!", "emptyCommentPrompt": "Коментар порожній. Ви хочете встановити коментар як \\"порожній\\"?", "confirmDeleteLinkData": "Посилання виявлене як {item}! Підтверджуєте видалення цього посилання? Всі дані розмов і коментарі будуть видалені!", "confirmCurrentURL": "Посилання виявлене як {item}! Підтвердити?", "commentSetToEmpty": "Коментар встановлено як \\"порожній\\"", "enterCommentFirst": "Будь ласка, спочатку введіть коментар", "commentSaved": "Коментар збережено", "conversationDataDeleted": "Дані розмови успішно видалено", "executeSearchWithQuery": "Виконати пошук: {item}", "searchPlaceholder": "Введіть ключові слова для пошуку...", "searchButton": "Пошук", "searchInContent": "У вмісті розмови", "searchInComments": "У коментарях", "searchInBoth": "У вмісті та коментарях", "goToPrevious": "Перейти до попереднього", "goToNext": "Перейти до наступного", "numberOfMatches": "{matches} збігів", "nodeDetails": "Деталі", "enterComment": "Введіть коментар", "userCommentSave": "Зберегти", "userCommentCancel": "Скасувати", "userCommentClear": "Очистити", "openAdminPanel": "Панель адміністрування", "allCategoriesFilter": "Всі категорії", "conversationTitle": "Заголовок", "actionOptions": "Дії", "conversationCategory": "Категорія", "conversationTags": "Теги" }, "ug": { "chatTreeRunning": "🥳🌳ChatTree🌳ئىشلىتىلىۋاتىدۇ!🎉", "updateCurrentConversationTree": "🌈 نۆۋەتتىكي سۆھبەت تەرەككىنى يېڭىلاڭ 🌈", "adjustBackgroundColorAndOpacity": "🎨 فون رەڭگىنى ۋە شېفافلىقىنى تەڭشەڭ 🎨", "toggleConversationTree": "🌳 سۆھبەت تەرەككىنى كۆرسىتىش/يوشۇرۇش 🌳", "noDatabaseAndCreationFailed": "ماڭلىق يوق، ھەمدە قۇرۇلمىدى! سكرىپت چىقىدۇ!", "mismatchedLink": "ئۇلىنىش ماس كەلمىدى، تور بەتنى يېڭىلاڭ!", "startUpdatingConversationTree": "سۆھبەت تەرەككىنى يېڭىلاشنى باشلاڭ", "selectedItem": "سىز تاللىغان {item}", "successSavingChanges": "ئۆزگەرتىشنى ساقلاش مۇۋەپپەقىيەتلىك بولدى!", "codeCopiedToClipboard": "كود تەسۋىرلىتىش تاختىسىغا كۆچۈرۈلدى!", "contentCopied": "مەزمۇن كۆچۈرۈلدى!", "emptyCommentPrompt": "ئىزاھات قۇرۇق. \\"قۇرۇق\\" دەپ بەلگىلەمسىز؟", "confirmDeleteLinkData": "{item} ئۇلىنىش تەپلىگەن! بۇ ئۇلىنىشنىڭ ئۇچۇرىنى ئۆچۈرۈشنى جەزملەسىزمۇ؟ بارلىق سۆھبەت ۋە ئىزاھات ئۆچۈرۈلىدۇ!", "confirmCurrentURL": "{item} ئۇلىنىش تەپلىگەن! جەزملەسىزمۇ؟", "commentSetToEmpty": "ئىزاھات \\"قۇرۇق\\" دەپ بەلگىلەندى", "enterCommentFirst": "ئاۋۋال ئىزاھات كىرگۈزۈڭ", "commentSaved": "ئىزاھات ساقلاندى", "conversationDataDeleted": "سۆھبەت ئۇچۇرى مۇۋەپپەقىيەتلىك ئۆچۈرۈلدى", "executeSearchWithQuery": "ئىزدەشنى ئىجرا قىلىدۇ: {item}", "searchPlaceholder": "ئىزدەش سۆزىنى كىرگۈزۈڭ...", "searchButton": "ئىزدەش", "searchInContent": "سۆھبەت مەزمۇنىدا", "searchInComments": "ئىزاھاتتا", "searchInBoth": "مەزمۇن ۋە ئىزاھاتتا", "goToPrevious": "ئالدىنقىغا بېرىش", "goToNext": "كېيىنكىگە بېرىش", "numberOfMatches": "{matches} دەسلەپتىكى ئۇنۇم", "nodeDetails": "نود تەپسىلاتى", "enterComment": "ئىزاھات كىرگۈزۈڭ", "userCommentSave": "ساقلا", "userCommentCancel": "بىكار قىل", "userCommentClear": "تازىلا", "openAdminPanel": "باشقۇرۇش تاختىسى", "allCategoriesFilter": "بارلىق تۈرلەر", "conversationTitle": "تېما", "actionOptions": "مەشغۇلاتلار", "conversationCategory": "تۈر", "conversationTags": "بەلگىلەر" }, "vi": { "chatTreeRunning": "🥳🌳ChatTree🌳đang chạy!🎉", "updateCurrentConversationTree": "🌈 Cập nhật cây trò chuyện hiện tại 🌈", "adjustBackgroundColorAndOpacity": "🎨 Điều chỉnh màu nền và độ mờ 🎨", "toggleConversationTree": "🌳 Hiển thị/Ẩn cây trò chuyện 🌳", "noDatabaseAndCreationFailed": "Không có cơ sở dữ liệu và không thể tạo được! Script thoát!", "mismatchedLink": "Liên kết không khớp, vui lòng làm mới trang!", "startUpdatingConversationTree": "Bắt đầu cập nhật cây trò chuyện", "selectedItem": "Bạn đã chọn {item}", "successSavingChanges": "Lưu thay đổi thành công!", "codeCopiedToClipboard": "Mã đã được sao chép vào bảng tạm!", "contentCopied": "Nội dung đã được sao chép!", "emptyCommentPrompt": "Bình luận trống. Bạn có muốn đặt bình luận thành \\"trống\\" không?", "confirmDeleteLinkData": "Đã phát hiện liên kết là {item}! Bạn có chắc chắn muốn xóa thông tin của liên kết này không? Tất cả nội dung trò chuyện và bình luận sẽ bị xóa!", "confirmCurrentURL": "Đã phát hiện liên kết là {item}! Bạn có xác nhận không?", "commentSetToEmpty": "Bình luận đã được đặt thành \\"trống\\"", "enterCommentFirst": "Vui lòng nhập bình luận trước", "commentSaved": "Bình luận đã được lưu", "conversationDataDeleted": "Dữ liệu trò chuyện đã được xóa thành công", "executeSearchWithQuery": "Thực hiện tìm kiếm: {item}", "searchPlaceholder": "Nhập từ khóa tìm kiếm...", "searchButton": "Tìm kiếm", "searchInContent": "Trong nội dung cuộc trò chuyện", "searchInComments": "Trong bình luận", "searchInBoth": "Cả trong nội dung và bình luận", "goToPrevious": "Đi đến trước đó", "goToNext": "Đi đến tiếp theo", "numberOfMatches": "{matches} kết quả phù hợp", "nodeDetails": "Chi tiết nút", "enterComment": "Nhập bình luận", "userCommentSave": "Lưu", "userCommentCancel": "Hủy", "userCommentClear": "Xóa sạch", "openAdminPanel": "Bảng Quản trị", "allCategoriesFilter": "Tất cả danh mục", "conversationTitle": "Tiêu đề", "actionOptions": "Tùy chọn", "conversationCategory": "Danh mục", "conversationTags": "Thẻ" }, "zh": { "chatTreeRunning": "🥳🌳ChatTree🌳运行中!🎉", "updateCurrentConversationTree": "🌈 更新当前对话树 🌈", "adjustBackgroundColorAndOpacity": "🎨 调整背景颜色和透明度 🎨", "toggleConversationTree": "🌳 显示/隐藏对话树 🌳", "noDatabaseAndCreationFailed": "没有数据库,并且未能成功创建!脚本退出!", "mismatchedLink": "链接不匹配,请刷新页面!", "startUpdatingConversationTree": "开始更新对话树", "selectedItem": "您选择了{item}", "successSavingChanges": "更改保存成功!", "codeCopiedToClipboard": "代码已复制到剪贴板!", "contentCopied": "内容已复制!", "emptyCommentPrompt": "注释为空。是否将注释设置为\\"空\\"?", "confirmDeleteLinkData": "监测到链接为 {item}!确认要删除这个链接的信息吗?所有的对话内容和注释都将被删除!", "confirmCurrentURL": "监测到链接为 {item}!确认吗?", "commentSetToEmpty": "注释已设置为\\"空\\"", "enterCommentFirst": "请先输入注释内容", "commentSaved": "注释已保存", "conversationDataDeleted": "对话数据成功删除", "executeSearchWithQuery": "执行搜索:{item}", "searchPlaceholder": "输入搜索关键词...", "searchButton": "搜索", "searchInContent": "对话内容", "searchInComments": "用户注释", "searchInBoth": "内容与注释", "goToPrevious": "转到上一个", "goToNext": "转到下一个", "numberOfMatches": "{matches} 个匹配项", "nodeDetails": "详情", "enterComment": "请输入注释", "userCommentSave": "保存", "userCommentCancel": "取消", "userCommentClear": "清空", "openAdminPanel": "管理面板", "allCategoriesFilter": "所有分类", "conversationTitle": "标题", "actionOptions": "操作", "conversationCategory": "分类", "conversationTags": "标签" }, "zh-CN": { "chatTreeRunning": "🥳🌳ChatTree🌳运行中!🎉", "updateCurrentConversationTree": "🌈 更新当前对话树 🌈", "adjustBackgroundColorAndOpacity": "🎨 调整背景颜色和透明度 🎨", "toggleConversationTree": "🌳 显示/隐藏对话树 🌳", "noDatabaseAndCreationFailed": "没有数据库,并且未能成功创建!脚本退出!", "mismatchedLink": "链接不匹配,请刷新页面!", "startUpdatingConversationTree": "开始更新对话树", "selectedItem": "您选择了{item}", "successSavingChanges": "更改保存成功!", "codeCopiedToClipboard": "代码已复制到剪贴板!", "contentCopied": "内容已复制!", "emptyCommentPrompt": "注释为空。是否将注释设置为\\"空\\"?", "confirmDeleteLinkData": "监测到链接为 {item}!确认要删除这个链接的信息吗?所有的对话内容和注释都将被删除!", "confirmCurrentURL": "监测到链接为 {item}!确认吗?", "commentSetToEmpty": "注释已设置为\\"空\\"", "enterCommentFirst": "请先输入注释内容", "commentSaved": "注释已保存", "conversationDataDeleted": "对话数据成功删除", "executeSearchWithQuery": "执行搜索:{item}", "searchPlaceholder": "输入搜索关键词...", "searchButton": "搜索", "searchInContent": "对话内容", "searchInComments": "用户注释", "searchInBoth": "内容与注释", "goToPrevious": "转到上一个", "goToNext": "转到下一个", "numberOfMatches": "{matches} 个匹配项", "nodeDetails": "详情", "enterComment": "请输入注释", "userCommentSave": "保存", "userCommentCancel": "取消", "userCommentClear": "清空", "openAdminPanel": "管理面板", "allCategoriesFilter": "所有分类", "conversationTitle": "标题", "actionOptions": "操作", "conversationCategory": "分类", "conversationTags": "标签" }, "zh-TW": { "chatTreeRunning": "🥳🌳ChatTree🌳運行中!🎉", "updateCurrentConversationTree": "🌈 更新當前對話樹 🌈", "adjustBackgroundColorAndOpacity": "🎨 調整背景顏色和透明度 🎨", "toggleConversationTree": "🌳 顯示/隱藏對話樹 🌳", "noDatabaseAndCreationFailed": "沒有資料庫,且未能成功創建!腳本退出!", "mismatchedLink": "鏈接不匹配,請刷新頁面!", "startUpdatingConversationTree": "開始更新對話樹", "selectedItem": "您選擇了{item}", "successSavingChanges": "更改保存成功!", "codeCopiedToClipboard": "代碼已複製到剪貼板!", "contentCopied": "內容已複製!", "emptyCommentPrompt": "註釋為空。是否將註釋設置為\\"空\\"?", "confirmDeleteLinkData": "監測到鏈接為 {item}!確認要刪除這個鏈接的信息嗎?所有的對話內容和註釋都將被刪除!", "confirmCurrentURL": "監測到鏈接為 {item}!確認嗎?", "commentSetToEmpty": "註釋已設置為\\"空\\"", "enterCommentFirst": "請先輸入註釋內容", "commentSaved": "註釋已保存", "conversationDataDeleted": "對話數據成功刪除", "executeSearchWithQuery": "執行搜索:{item}", "searchPlaceholder": "輸入搜索關鍵詞...", "searchButton": "搜索", "searchInContent": "對話內容", "searchInComments": "使用者註釋", "searchInBoth": "內容與註釋", "goToPrevious": "轉到上一個", "goToNext": "轉到下一個", "numberOfMatches": "{matches} 個匹配項", "nodeDetails": "詳情", "enterComment": "請輸入注釋", "userCommentSave": "保存", "userCommentCancel": "取消", "userCommentClear": "清空", "openAdminPanel": "管理面板", "allCategoriesFilter": "所有類別", "conversationTitle": "標題", "actionOptions": "操作選項", "conversationCategory": "類別", "conversationTags": "標籤" }, "zh-HK": { "chatTreeRunning": "🥳🌳ChatTree🌳運行中!🎉", "updateCurrentConversationTree": "🌈 更新當前對話樹 🌈", "adjustBackgroundColorAndOpacity": "🎨 調整背景顏色和透明度 🎨", "toggleConversationTree": "🌳 顯示/隱藏對話樹 🌳", "noDatabaseAndCreationFailed": "沒有資料庫,且未能成功創建!腳本退出!", "mismatchedLink": "鏈接不匹配,請刷新頁面!", "startUpdatingConversationTree": "開始更新對話樹", "selectedItem": "您選擇了{item}", "successSavingChanges": "更改保存成功!", "codeCopiedToClipboard": "代碼已複製到剪貼板!", "contentCopied": "內容已複製!", "emptyCommentPrompt": "註釋為空。是否將註釋設置為\\"空\\"?", "confirmDeleteLinkData": "監測到鏈接為 {item}!確認要刪除這個鏈接的信息嗎?所有的對話內容和註釋都將被刪除!", "confirmCurrentURL": "監測到鏈接為 {item}!確認嗎?", "commentSetToEmpty": "註釋已設置為\\"空\\"", "enterCommentFirst": "請先輸入註釋內容", "commentSaved": "註釋已保存", "conversationDataDeleted": "對話數據成功刪除", "executeSearchWithQuery": "執行搜索:{item}", "searchPlaceholder": "輸入搜尋關鍵詞...", "searchButton": "搜尋", "searchInContent": "對話內容", "searchInComments": "用戶註釋", "searchInBoth": "內容與註釋", "goToPrevious": "轉到上一個", "goToNext": "轉到下一個", "numberOfMatches": "{matches} 個匹配項", "nodeDetails": "詳情", "enterComment": "請輸入註釋", "userCommentSave": "儲存", "userCommentCancel": "取消", "userCommentClear": "清除", "openAdminPanel": "管理面板", "allCategoriesFilter": "所有類別", "conversationTitle": "標題", "actionOptions": "操作選項", "conversationCategory": "類別", "conversationTags": "標籤" }, "zh-SG": { "chatTreeRunning": "🥳🌳ChatTree🌳运行中!🎉", "updateCurrentConversationTree": "🌈 更新当前对话树 🌈", "adjustBackgroundColorAndOpacity": "🎨 调整背景颜色和透明度 🎨", "toggleConversationTree": "🌳 显示/隐藏对话树 🌳", "noDatabaseAndCreationFailed": "没有数据库,并且未能成功创建!脚本退出!", "mismatchedLink": "链接不匹配,请刷新页面!", "startUpdatingConversationTree": "开始更新对话树", "selectedItem": "您选择了{item}", "successSavingChanges": "更改保存成功!", "codeCopiedToClipboard": "代码已复制到剪贴板!", "contentCopied": "内容已复制!", "emptyCommentPrompt": "注释为空。是否将注释设置为\\"空\\"?", "confirmDeleteLinkData": "监测到链接为 {item}!确认要删除这个链接的信息吗?所有的对话内容和注释都将被删除!", "confirmCurrentURL": "监测到链接为 {item}!确认吗?", "commentSetToEmpty": "注释已设置为\\"空\\"", "enterCommentFirst": "请先输入注释内容", "commentSaved": "注释已保存", "conversationDataDeleted": "对话数据成功删除", "executeSearchWithQuery": "执行搜索:{item}", "searchPlaceholder": "输入搜索关键词...", "searchButton": "搜索", "searchInContent": "对话内容", "searchInComments": "用户注释", "searchInBoth": "内容与注释", "goToPrevious": "转到上一个", "goToNext": "转到下一个", "numberOfMatches": "{matches} 个匹配项", "nodeDetails": "详情", "enterComment": "请输入注释", "userCommentSave": "保存", "userCommentCancel": "取消", "userCommentClear": "清空", "openAdminPanel": "管理面板", "allCategoriesFilter": "所有分类", "conversationTitle": "标题", "actionOptions": "操作", "conversationCategory": "分类", "conversationTags": "标签" } }`; lang = JSON.parse(lang); const userLang = navigator.languages.find(l => l in lang) || 'en'; //const userLang = 'en'; //log("currentLang:",userLang); globalUserLang = userLang; return lang[userLang]; }; let globalUserLang; const currentLangPack = getLang(); //log("currentLangPack", currentLangPack); function translate(key) { return currentLangPack[key] || key; } const states = { mainButton: { isDragging: false, isMouseOver: false, isThereNavbar: false, isMouseInNavbar: false, isMainTreeBtnInNavbar: false, }, url: { isForLiveValidURL: false, isForDeletedValidURL: false, url: '' }, treeUpdate: { isDOMOperating: false, }, visualization: { contentDiv: 0, thumbnailSvg: 0, panelToggleButton: 0, }, }; const Default_RootNode_Content = "Chat Starts Here"; const DB_NAME = 'ChatTreeDB'; const CONVERSATIONS_STORE_NAME = 'conversations'; const SEARCH_HISTORY_STORE_NAME = 'searchHistory'; const USER_SETTINGS_STORE_NAME = 'userSettings'; let db; class DialogueNode { constructor(content, type) { this.content = content; this.type = type; this.uuid = generateUUID(); this.children = []; this.comment = ''; } } let conversationData = { url: null, rootNode: new DialogueNode(Default_RootNode_Content, "chatGPT"), uuid2pathMap: new Map(), uuid2nodeMap: new Map(), path2nodeMap: new Map(), bookMarked: new Map(), timestamp: Date.now(), participants: { user: { name: "UserName", avatarURL: "UserAvatarURL", avatarHTML: "💕", }, gpt: { type: "GPT-3", } } }; let GPT_Avatar_Config = { gpt4_Inner_Html: "
", gpt3_Inner_Html: "", } let root, treeLayout, svg, svgThumbnail, defs, gLinks, gNodes, nodeDrag, canvasDrag, zoom, searchHistoryRecord, chatHistory = [], curMouseOnUUID = null; const waitForDomChange = (element) => { return new Promise(resolve => { const observer = new MutationObserver((mutationsList, observer) => { observer.disconnect(); resolve(); }); observer.observe(element, {childList: true, subtree: true}); }); }; function sleep(ms) { return new Promise(resolve => setTimeout(resolve, ms)); } const treeOperation = { initializeChatTree: async function () { if (!states.url.isForLiveValidURL) { ButtonOperations.showUserNotification(translate("mismatchedLink")); return; } states.treeUpdate.isDOMOperating = true; let operatingURL = states.url.url; const button = document.querySelector('button.flex.w-full.items-center.gap-3.rounded-md.px-3.py-3.text-sm[data-headlessui-state=""]'); if (button) { const relativeFlexElement = button.querySelector('.relative.flex'); if (relativeFlexElement) { conversationData.participants.user.avatarHTML = relativeFlexElement.innerHTML; const imgElement = relativeFlexElement.querySelector('img.rounded-sm'); if (imgElement) { const imgSrc = imgElement.getAttribute('src'); conversationData.participants.user.avatarURL = imgSrc; } else { log('Image Element Not Found'); } } else { log('Relative Flex Element Not Found'); } const fontSemiboldElement = button.querySelector('.font-semibold'); if (fontSemiboldElement) { conversationData.participants.user.name = fontSemiboldElement.innerHTML; } else { log('Font Semibold Element Not Found'); } } else { let allDivs = DOMOperations.getAllDivs(); if (allDivs) { let userDiv = allDivs[0]; const imageDiv = userDiv.querySelector('div.flex-shrink-0.flex.flex-col.relative.items-end'); if (imageDiv) { const relativeFlexElement = imageDiv.querySelector('.relative.flex'); if (relativeFlexElement) { conversationData.participants.user.avatarHTML = relativeFlexElement.innerHTML; const imgElement = relativeFlexElement.querySelector('img.rounded-sm'); if (imgElement) { const imgSrc = imgElement.getAttribute('src'); conversationData.participants.user.avatarURL = imgSrc; } else { log('Image Element Not Found'); } } else { log('Relative Flex Element Not Found'); } } } log('Button Element Not Found'); } if (conversationData.rootNode.content.toLowerCase() === "New Chat".toLowerCase() || conversationData.rootNode.content.toLowerCase() === Default_RootNode_Content.toLowerCase() || conversationData.rootNode.content.toLowerCase() === "Chat Start Here".toLowerCase()) { try { const targetElement = document.querySelector('.absolute.flex.right-1.z-10.dark\\:text-gray-300.text-gray-800.visible'); if (targetElement) { let siblingElement = targetElement.parentElement.firstElementChild; while (siblingElement) { if (siblingElement.classList.contains('flex-1') && siblingElement.classList.contains('text-ellipsis') && siblingElement.classList.contains('max-h-5') && siblingElement.classList.contains('overflow-hidden') && siblingElement.classList.contains('break-all') && siblingElement.classList.contains('relative')) { log(siblingElement.textContent || siblingElement.innerText); conversationData.rootNode.content = siblingElement.textContent } siblingElement = siblingElement.nextElementSibling; } } else { log('Target element not found.'); } // async function testGetChatDetails() { // const token = await chatgpt.getAccessToken(); // chatgpt.getChatDetails(token, ['id', 'title']) // .then(data => { // log("Successfully got chat details:", data); // }) // .catch(error => { // console.error("Error in getChatDetails:", error); // }); // } // // await testGetChatDetails(); // 使用 chatgpt.js 库的 getChatData 方法获取聊天数据 // const chatData = await chatgpt.getChatData('active', 'all', 'all', 'all'); // //log(chatData); // 在控制台打印聊天数据 // conversationData.rootNode.content = chatData.title; // 如果需要,你可以在这里添加其他操作,例如将聊天数据发送到你的服务器 } catch (error) { console.error('Error getting chat data:', error); // 如果出现错误,在控制台打印错误信息 } } let gptInfoDiv = document.querySelector('.flex.flex-1.flex-grow.items-center.gap-1.px-2.py-1.text-gray-600'); //log(gptInfoDiv); if (gptInfoDiv) { conversationData.participants.gpt.type = gptInfoDiv.innerText; } log("url:", operatingURL); let result = DOMOperations.getButtonInfo(); let hasLeftButton = result.hasLeftButtonUnClicked; while (hasLeftButton) { if (states.url.url !== operatingURL || !states.treeUpdate.isDOMOperating) { log("监测到链接变换! 退出initializeChatTree 函数!"); states.treeUpdate.isDOMOperating = false; return; } let allChatDivs = DOMOperations.getAllDivs(); if (allChatDivs.length === 0) { log("监测到没有divs:退出初始化!"); states.treeUpdate.isDOMOperating = false; return; } let j = 0; for (; j < allChatDivs.length; j++) { if (result.childIndicesPath[j] !== 1) { DOMOperations.clickButtonAtDivLevel(0, j); log("clicking the ", j, "th div!"); await waitForDomChange(document.body); break; } } if (j === allChatDivs.length) { break; } result = DOMOperations.getButtonInfo(); log("result:", result); hasLeftButton = result.hasLeftButtonUnClicked; } log("Initializing Over."); await this.updateTree(operatingURL); }, initializeSubChatTree: async function (fromWhichDivClickLeft) { log("initializeSubChatTree"); let result = DOMOperations.getButtonInfo(); let allChatDivs = DOMOperations.getAllDivs(); if (allChatDivs.length === 0) { log("监测到没有divs:退出初始化!"); states.treeUpdate.isDOMOperating = false; return; } let hasLeftButton = false; for (let i = fromWhichDivClickLeft; i < allChatDivs.length; i++) { if (result.childIndicesPath[i] !== 1) { hasLeftButton = true; log("hasLeftButton === true"); break; } } while (hasLeftButton) { let j = fromWhichDivClickLeft; for (; j < allChatDivs.length; j++) { if (result.childIndicesPath[j] !== 1) { DOMOperations.clickButtonAtDivLevel(0, j); log("clicking the ", j, "th div!"); await waitForDomChange(document.body); break; } } if (j === allChatDivs.length) { break; } result = DOMOperations.getButtonInfo(); allChatDivs = DOMOperations.getAllDivs(); log("result:", result); for (let i = fromWhichDivClickLeft; i < allChatDivs.length; i++) { if (result.childIndicesPath[i] !== 1) { log("hasLeftButton === true"); hasLeftButton = true; break; } } } }, //🤖chatGPT版本 updateTree: async function (url) { let rootNodeContent = conversationData.rootNode.content ? conversationData.rootNode.content : Default_RootNode_Content; let newConversationData = { url: conversationData.url, rootNode: new DialogueNode(rootNodeContent, "chatGPT"), uuid2pathMap: new Map(), uuid2nodeMap: new Map(), path2nodeMap: new Map(), timestamp: Date.now(), participants: { user: { name: conversationData.participants.user.name, avatarURL: conversationData.participants.user.avatarURL, avatarHTML: conversationData.participants.user.avatarHTML, }, gpt: { type: conversationData.participants.gpt.type, } }, isWholeConversationBookMarked: conversationData.isWholeConversationBookMarked || false, chatTreeTags: conversationData.chatTreeTags || [], categories: conversationData.categories || [], bookMarked: conversationData.bookMarked }; let allpaths = []; log("更新树"); let operatingURL = url; if (states.url.url !== operatingURL) { log("监测到链接变换! 退出initializeChatTree 函数!"); return; } let allChatDivs = DOMOperations.getAllDivs(); let hasRightButtonUnClicked = true; let curRootDivChoice = 0; while (hasRightButtonUnClicked) { if (states.url.url !== operatingURL || !states.treeUpdate.isDOMOperating) { log("监测到链接变换! 退出updateTree 函数!"); states.treeUpdate.isDOMOperating = false; return; } hasRightButtonUnClicked = false; allChatDivs = DOMOperations.getAllDivs(); if (allChatDivs.length === 0) { log("监测到没有divs:退出更新!"); states.treeUpdate.isDOMOperating = false; return; } let result = DOMOperations.getButtonInfo(); for (let i = curRootDivChoice; i < allChatDivs.length; i++) { if (states.url.url !== operatingURL || !states.treeUpdate.isDOMOperating) { log("监测到链接变换! 退出initializeChatTree 函数!"); states.treeUpdate.isDOMOperating = false; return; } let contentResult = DOMOperations.getTextContent(allChatDivs[i], i); let path = result.childIndicesPath.slice(0, i + 1); // log("path", path, "content:", contentResult); // let isExisting = conversationData.path2nodeMap.get(arrayToKey(path)); // if (isExisting) { // log("isExisting!", isExisting); // log("contentResult.contentText", contentResult.contentText); // if (isExisting.content === contentResult.contentText) { // allpaths.push(arrayToKey(path)); // continue; // } else { // isExisting.content = contentResult.contentText // allpaths.push(arrayToKey(path)); // continue; // } // } let father = i > 0 ? newConversationData.path2nodeMap.get(arrayToKey(result.childIndicesPath.slice(0, i))) : newConversationData.rootNode; let newDialogueNode = new DialogueNode(contentResult.contentText, contentResult.userType); log("father :", father); father.children.push(newDialogueNode); log("newDialogueNode:", newDialogueNode); log("dataRenewing:", newConversationData); newConversationData.uuid2pathMap.set(newDialogueNode.uuid, path); newConversationData.uuid2nodeMap.set(newDialogueNode.uuid, newDialogueNode); newConversationData.path2nodeMap.set(arrayToKey(path), newDialogueNode); log("father:", father); allpaths.push(arrayToKey(path)); } let curRootChoice = allChatDivs.length - 1; for (; curRootChoice >= 0; curRootChoice--) { // if (url !== states.url.url) { // log("发现url变化! 退出更新树"); // states.treeUpdate.isDOMOperating = false; // return; // } if (result.childIndicesPath[curRootChoice] !== result.childrenCountPath[curRootChoice]) { await DOMOperations.clickButtonAtDivLevel(1, curRootChoice); let ableToContinue = false; while (!ableToContinue) { await sleep(50); let result1 = DOMOperations.getButtonInfo(); let childIndecices = result1.childIndicesPath; if (childIndecices.length !== result.childIndicesPath.length) { ableToContinue = true; break; } for (let i = 0; i < childIndecices.length; i++) { if (childIndecices[i] !== result.childIndicesPath[i]) { ableToContinue = true; break; } } } curRootDivChoice = curRootChoice; hasRightButtonUnClicked = true; //if(allChatDivs.length -1 > curRootChoice){ await treeOperation.initializeSubChatTree(curRootChoice + 1); //} break; } } if (!hasRightButtonUnClicked) { log("所有的节点都加进来了!") log("准备保存的data:", newConversationData); if (states.url.url !== operatingURL || window.location.href !== operatingURL) { log("监测到链接变化, 停止更新!"); states.treeUpdate.isDOMOperating = false; return; } try { await dbOperations.saveConversationsData(newConversationData); await dbOperations.loadConversationsData(operatingURL); } catch (error) { console.error("Error:", error); } log("重新读取到的data:", newConversationData); break; } } states.treeUpdate.isDOMOperating = false; dbOperations.initConversationData() .then(information => { controlPanelKit.renderConversations(chatHistory); }) .catch(error => console.error(error)); }, jumpToDialogueItem: async function (uuid) { if (!states.url.isForLiveValidURL) { return; } if (!uuid || !conversationData.uuid2pathMap.get(uuid) || uuid === conversationData.rootNode.uuid) { return; } let path = conversationData.uuid2pathMap.get(uuid); if (!path) { log("没有从map中获取路径! 请检查!") return; } let result = DOMOperations.getButtonInfo(); log("path:", path); let i = 0; while (i < path.length) { result = DOMOperations.getButtonInfo(); if (path[i] === result.childIndicesPath[i]) { i++; continue; } if (path[i] < result.childIndicesPath[i]) { DOMOperations.clickButtonAtDivLevel(0, i); log("path:", path); result = DOMOperations.getButtonInfo(); await sleep(200); continue; } if (path[i] > result.childIndicesPath[i]) { DOMOperations.clickButtonAtDivLevel(1, i); log("path:", path); result = DOMOperations.getButtonInfo(); await sleep(200); continue; } } let j = 0; for (; j < path.length; j++) { if (path[j] !== result.childIndicesPath[j]) { log("在:", j, "没有成功转到!"); log(path, result.childIndicesPath); break; } } sleep(200); if (j === path.length) { let allDivs = DOMOperations.getAllDivs(); log("path", path, "result.childIndicesPath", result.childIndicesPath, "allDivs[path.length - 1]", allDivs[path.length - 1]); function highlightDiv1() { allDivs[path.length - 1].classList.add('highlight'); setTimeout(() => { allDivs[path.length - 1].classList.remove('highlight'); }, 4000); } function highlightDiv2() { allDivs[path.length - 1].classList.add('highlightt'); setTimeout(() => { allDivs[path.length - 1].classList.remove('highlightt'); }, 4000); } function blinkText() { allDivs[path.length - 1].classList.add('blinkText'); setTimeout(() => { allDivs[path.length - 1].classList.remove('blinkText'); }, 5000); } allDivs[path.length - 1].scrollIntoView({behavior: 'smooth', block: 'center', inline: 'start'}); const htmlClass = document.documentElement.getAttribute('class'); if (htmlClass && htmlClass.includes('dark')) { highlightDiv1(); } else { highlightDiv2(); } setTimeout(() => { allDivs[path.length - 1].scrollIntoView({behavior: 'smooth', block: 'center', inline: 'start'}); const htmlClass = document.documentElement.getAttribute('class'); if (htmlClass && htmlClass.includes('dark')) { highlightDiv1(); } else { highlightDiv2(); } }, 1000); log("成功转到!"); } }, }; const urlOperations = { getCurrentURL: function () { return window.location.href; }, isForLiveValidURL: function (url) { const pattern = /^https:\/\/chat\.openai\.com\/c\/[a-z0-9\-]+\/?$/; return pattern.test(url); }, isForDeletedValidURL: function (url) { const pattern = /^https:\/\/chat\.openai\.com\/chattree\/[a-z0-9\-]+\/?$/; return pattern.test(url); }, changeBetweenChattreeWithCAndOneMeansChattreeToC: function (chattreetoc, url) { function replaceFirstChattreeWithC(url) { return url.replace(/^https:\/\/chat\.openai\.com\/chattree/, "https://chat.openai.com/c"); } function replaceFirstCWithChattree(url) { return url.replace(/^https:\/\/chat\.openai\.com\/c/, "https://chat.openai.com/chattree"); } if (chattreetoc) { return replaceFirstChattreeWithC(url); } else { return replaceFirstCWithChattree(url); } }, isNonUniqueURL: function (url) { const nonUniquePatterns = [ /^https:\/\/chat\.openai\.com\/?$/, /^https:\/\/chat\.openai\.com\/\?model=.+$/ ]; return nonUniquePatterns.some(pattern => pattern.test(url)); }, getCurURLInfo: function () { let curURL = window.location.href; let validURL = this.isForLiveValidURL(curURL); let nonUniqueURL = !this.isNonUniqueURL(curURL); return { curURL: curURL, validURL: validURL, nonUniqueURL: nonUniqueURL, }; }, observeTargetChanges: function () { let lastURL = window.location.href; log("lastURL:", lastURL); if (urlOperations.isForLiveValidURL(lastURL) || urlOperations.isForDeletedValidURL(lastURL)) { log("is_anyKind_of_valid"); urlOperations.handleURLChange(lastURL); states.url.url = lastURL; } function callback(mutationsList, observer) { const currentURL = window.location.href; log("currentURL:", currentURL); if (urlOperations.isForLiveValidURL(currentURL)) { if (currentURL !== lastURL) { log("URL changed:", currentURL); lastURL = currentURL; urlOperations.handleURLChange(currentURL); states.treeUpdate.isDOMOperating = false; } else { log("Current URL:", currentURL); } } else if (urlOperations.isForDeletedValidURL(currentURL)) { log("URL changed:", currentURL, " detected. Please refresh the page."); urlOperations.handleURLChange(currentURL); } else if (urlOperations.isNonUniqueURL(currentURL)) { log("Non-unique URL:", currentURL, " detected. Please refresh the page."); urlOperations.handleURLChange(currentURL); } }; let outter_observer; let inner_observer; let curState = null; const startObserving = (target, config, callback, observer) => { if (observer) { observer.disconnect(); } observer = new MutationObserver(callback); observer.observe(target, config); log('Started observing:', target); return observer; }; window.addEventListener("resize", function () { checkCurrentState(); }); const checkCurrentState = () => { const flexDiv = document.querySelector('.flex-shrink-0.overflow-x-hidden.dark.bg-gray-900'); const htmlTag = document.querySelector('html'); if (flexDiv && curState !== 1) { log('Switched to State 1.'); curState = 1; const config = {attributes: true, attributeFilter: ['style']}; outter_observer = startObserving(htmlTag, config, (mutations) => { if (mutations.some(m => m.type === 'attributes' && m.attributeName === 'style')) { log('HTML style changed.'); checkCurrentState(); } }, outter_observer); const innerConfig = {childList: true, subtree: true}; inner_observer = startObserving(flexDiv, innerConfig, (mutations) => { if (mutations.some(m => m.type === 'childList')) { log('FlexDiv child list changed.'); callback(); checkCurrentState(); } }, inner_observer); } else if (!flexDiv && curState !== 2) { log('Switched to State 2.'); curState = 2; const config = {childList: true, subtree: true}; outter_observer = startObserving(document.body, config, (mutations) => { if (mutations.some(m => m.type === 'childList')) { log('Body child list changed.'); const conversationList = document.querySelector('#headlessui-portal-root'); if (conversationList) { log('Conversation List Detected.'); inner_observer = startObserving(conversationList, config, (mutations) => { if (mutations.some(m => m.type === 'childList')) { log('Conversation List child list changed.'); callback(); } }, inner_observer); } checkCurrentState(); } }, outter_observer); } }; checkCurrentState(); }, handleURLChange: function (url) { log("In handleURLChange, Data:", conversationData); if (urlOperations.isNonUniqueURL(url)) { states.url.isForLiveValidURL = false; states.url.isForDeletedValidURL = false; states.url.url = ''; states.treeUpdate.isDOMOperating = false; conversationData = { url: null, rootNode: new DialogueNode(Default_RootNode_Content, "chatGPT"), uuid2pathMap: new Map(), uuid2nodeMap: new Map(), path2nodeMap: new Map(), bookMarked: new Map(), timestamp: Date.now(), participants: { user: { name: "UserName", avatarURL: "UserAvatarURL", avatarHTML: "User", }, gpt: { type: "GPT-3", } } }; root = d3.hierarchy(conversationData.rootNode); const widthPerNode = 30; const heightPerNode = 30; treeLayout = d3.tree().nodeSize([widthPerNode, heightPerNode]); treeLayout(root); settingsKit.refreshTree(); log("请刷新页面或者转到具有对话信息的页面从而获取正确的链接"); } else if (urlOperations.isForDeletedValidURL(url)) { states.url.isForLiveValidURL = false; states.url.isForDeletedValidURL = true; states.treeUpdate.isDOMOperating = false; states.url.url = url; document.documentElement.setAttribute('class', 'light'); // const htmlClass = document.documentElement.getAttribute('class'); // let wholeScreenDiv = document.getElementById("__next"); // 修正单词拼写 // if (wholeScreenDiv && htmlClass && htmlClass === 'black') { // wholeScreenDiv.style.background = 'rgb(51,53,65)'; // } else { // document.documentElement.className = 'light'; // 使用 className // } //rgb(51,53,65) log("this_is_delete_url", url); url = urlOperations.changeBetweenChattreeWithCAndOneMeansChattreeToC(1, url); log("delete_url_to_new_url", url); dbOperations.loadConversationsData(url).then(loadeddata => { log("Loaded data for URL:", loadeddata); let interval; interval = setInterval(() => { if (document.title === "查看模式(ChatTree提供支持): " + loadeddata.rootNode.content) { clearInterval(interval); } document.title = "查看模式(ChatTree提供支持): " + loadeddata.rootNode.content; }, 1500); conversationData = loadeddata; root = d3.hierarchy(conversationData.rootNode); const widthPerNode = 30; const heightPerNode = 30; treeLayout = d3.tree().nodeSize([widthPerNode, heightPerNode]); treeLayout(root); settingsKit.refreshTree(); }).catch(error => { console.error("Error loading data:", error); }); } else { states.url.isForLiveValidURL = true; states.url.isForDeletedValidURL = true; states.treeUpdate.isDOMOperating = false; states.url.url = url; dbOperations.loadConversationsData(url).then(loadeddata => { log("Loaded data for URL:", loadeddata); conversationData = loadeddata; root = d3.hierarchy(conversationData.rootNode); const widthPerNode = 30; const heightPerNode = 30; treeLayout = d3.tree().nodeSize([widthPerNode, heightPerNode]); treeLayout(root); settingsKit.refreshTree(); }).catch(error => { console.error("Error loading data:", error); }); } } }; //const DEFAULT_MAINSVG_BACKGROUND = 'linear-gradient(to top, rgba(51, 230, 15, 0.74) 0%, rgba(250, 0, 187, 0.74) 100%)'; const DEFAULT_MAINSVG_BACKGROUND = 'linear-gradient(to top, rgba(117, 194, 102, 0.31) 0%, rgba(206, 44, 166, 0.31) 100%)'; //'linear-gradient(to top, rgba(210, 108, 196, 0.2) 0%, rgba(205, 209, 83, 0.2) 100%)' const GlobalUserSettings = { MainTreeBtnColorSettings: {}, MainTreeBtnPositionSettings: {}, MainSVGBackground: DEFAULT_MAINSVG_BACKGROUND, }; const dbOperations = { initDatabase: function () { return new Promise((resolve, reject) => { const request = indexedDB.open(DB_NAME, 1); request.onerror = event => { console.error("Detailed Error:", event); reject("Error opening database:", event); }; request.onupgradeneeded = event => { log("升级数据库!"); db = event.target.result; if (!db.objectStoreNames.contains(CONVERSATIONS_STORE_NAME)) { db.createObjectStore(CONVERSATIONS_STORE_NAME, {keyPath: "url"}); } if (!db.objectStoreNames.contains(SEARCH_HISTORY_STORE_NAME)) { db.createObjectStore(SEARCH_HISTORY_STORE_NAME, {keyPath: "id"}); const initSearchHistory = {id: 'searchHistory', records: []}; const transaction = event.target.transaction; const historyStore = transaction.objectStore(SEARCH_HISTORY_STORE_NAME); historyStore.add(initSearchHistory); } if (!db.objectStoreNames.contains(USER_SETTINGS_STORE_NAME)) { db.createObjectStore(USER_SETTINGS_STORE_NAME, {keyPath: "id"}); const transaction = event.target.transaction; const userSettingsStore = transaction.objectStore(USER_SETTINGS_STORE_NAME); const mainTreeBtnColorSettings = {id: 'mainTreeBtn', color: '#0FD126', opacity: 0.9}; userSettingsStore.add(mainTreeBtnColorSettings); const mainTreeBtnPosSettings = {id: 'mainTreeBtnPos', top: '20px', left: '20px'}; userSettingsStore.add(mainTreeBtnPosSettings); } }; request.onsuccess = event => { db = event.target.result; dbOperations.getSearchHistory() .then(records => { log('Got search history:', records); }) .catch(error => console.error(error)); dbOperations.getUserSettings('mainTreeBtn') .then(MainTreeBtnSettings => { log('Got MainTreeBtnSettings:', MainTreeBtnSettings); GlobalUserSettings.MainTreeBtnColorSettings = MainTreeBtnSettings; treeMainBtn.style.background = GlobalUserSettings.MainTreeBtnColorSettings.color; treeMainBtn.style.opacity = GlobalUserSettings.MainTreeBtnColorSettings.opacity; navMainButton.style.backgroundColor = GlobalUserSettings.MainTreeBtnColorSettings ? GlobalUserSettings.MainTreeBtnColorSettings.color : "rgb(16,209,38)"; navMainButton.style.opacity = '1'; }) .catch(error => console.error(error)); dbOperations.getUserSettings('mainTreeBtnPos') .then(mainTreeBtnPos => { log('Got mainTreeBtnPosSettings:', mainTreeBtnPos); GlobalUserSettings.MainTreeBtnPositionSettings = mainTreeBtnPos; treeMainBtn.style.top = GlobalUserSettings.MainTreeBtnPositionSettings.top; treeMainBtn.style.left = GlobalUserSettings.MainTreeBtnPositionSettings.left; if (mainTreeBtnPos.isInNavbar === true) { navMainButton.style.display = 'block'; treeMainBtn.style.display = 'none'; states.mainButton.isMainTreeBtnInNavbar = true; } }) .catch(error => console.error(error)); dbOperations.getUserSettings('mainSVG') .then(mainSVGBackground => { log('Got mainTreeBtnPosSettings:', mainSVGBackground); if (mainSVGBackground && mainSVGBackground.background) { GlobalUserSettings.MainSVGBackground = mainSVGBackground.background; let mainSvg = document.getElementById('mainSvg'); if (mainSvg) { log("get mainSvg:", mainSvg); mainSvg.style.background = mainSVGBackground.background.toString(); log("get mainSVGBackground:", mainSVGBackground); } } }) .catch(error => console.error(error)); dbOperations.initConversationData() .then(information => { log("information:", information); log('initConversationData:', chatHistory); controlPanelKit.init(); controlPanelKit.renderConversations(chatHistory); controlPanelKit.updateCategorySelect(); filteredConversations = chatHistory; }) .catch(error => console.error(error)); resolve(); }; }); }, initConversationData: function () { if (!db) { return; } return new Promise((resolve, reject) => { let information = { conversations: [] }; const transaction = db.transaction([CONVERSATIONS_STORE_NAME], "readwrite"); const objectStore = transaction.objectStore(CONVERSATIONS_STORE_NAME); // 获取现有的 "conversations_information" 对象(如果存在) const getRequest = objectStore.get("conversations_information"); getRequest.onsuccess = event => { if (getRequest.result) { objectStore.delete("conversations_information"); } // 现在,我们可以遍历对象存储中的每个对象 objectStore.openCursor().onsuccess = event => { const cursor = event.target.result; if (cursor) { const url = cursor.value.url; if (url && !url.includes("conversations_information")) { if (cursor.value.rootNode.children.length === 0) { dbOperations.deleteConversationData(url) .then(log("a conversation is deleted!")) .catch(error => { console.error(error); }); } else { const id = url.split('/').pop(); const safeId = id.replace(/-/g, ''); information.conversations.push({ id: safeId, topic: cursor.value.rootNode.content, link: url, categories: cursor.value.categories || [], // 新增字段 chatTreeTags: cursor.value.chatTreeTags || [], // 新增字段 isWholeConversationBookMarked: cursor.value.isWholeConversationBookMarked || false, timestamp: cursor.value.timestamp }); } } cursor.continue(); } else { const putRequest = objectStore.put({ url: "conversations_information", data: information }); putRequest.onsuccess = event => { log("Information updated successfully."); resolve(information); }; putRequest.onerror = event => { console.error("Failed to update information.", event.target.error); reject(event.target.error); }; } chatHistory = information.conversations; }; }; getRequest.onerror = event => { console.error("Failed to get information.", event.target.error); reject(event.target.error); }; }); }, changeWholeConversationBookMarked: function (url, shouldBeBookMarked) { if (!url || !urlOperations.isForLiveValidURL(url)) { return; } return new Promise((resolve, reject) => { if (!db) { console.error("加载数据:Database has not been initialized."); return; } if (!url) { reject("加载数据:No URL key specified."); return; } const transaction = db.transaction([CONVERSATIONS_STORE_NAME], "readwrite"); const objectStore = transaction.objectStore(CONVERSATIONS_STORE_NAME); const request = objectStore.get(url); request.onsuccess = event => { let result = event.target.result; result.isWholeConversationBookMarked = shouldBeBookMarked; dbOperations.saveConversationsData(result) .then(() => dbOperations.initConversationData()) .then(information => { //controlPanelKit.updateCategorySelect(); }) .catch(error => { console.error(error); }); }; request.onerror = event => reject("Error loading data:", event.target.errorCode); }); }, addOrDeleteTagOrClassToURL: async function (url, isTag, value, isAdd) { log("In DBOper:", "url:", url, "isTag:", isTag, "value:", value, "isAdd:", isAdd); if (!url || !urlOperations.isForLiveValidURL(url)) { return; } return new Promise((resolve, reject) => { if (!db) { console.error("加载数据:Database has not been initialized."); return; } if (!url) { reject("加载数据:No URL key specified."); return; } const transaction = db.transaction([CONVERSATIONS_STORE_NAME], "readwrite"); const objectStore = transaction.objectStore(CONVERSATIONS_STORE_NAME); const request = objectStore.get(url); request.onsuccess = event => { let result = event.target.result; log("result:", result); if (isAdd) { if (!result.chatTreeTags) { result.chatTreeTags = []; } if (!result.categories) { result.categories = []; } if (isTag && !result.chatTreeTags.includes(value)) { result.chatTreeTags.push(value); log("added!"); } else if (!isTag && !result.categories.includes(value)) { result.categories.push(value); log("added!"); } } else { if (isTag && result.chatTreeTags.includes(value)) { result.chatTreeTags = result.chatTreeTags.filter(tag => tag != value); log("deleted!"); } else if (!isTag && result.categories.includes(value)) { result.categories = result.categories.filter(tag => tag != value); log("deleted!"); } } dbOperations.saveConversationsData(result) .then(() => dbOperations.initConversationData()) .then(information => { controlPanelKit.updateCategorySelect(); }) .catch(error => { console.error(error); }); }; request.onerror = event => reject("Error loading data:", event.target.errorCode); }); }, saveConversationsData: function (data) { if (data.url === null) { log("保存数据:No URL key specified."); return; } return new Promise((resolve, reject) => { if (!db) { console.error("保存数据:Database has not been initialized."); return; } if (!data.url) { reject("保存数据:No URL key specified."); return; } data.timestamp = Date.now(); const transaction = db.transaction([CONVERSATIONS_STORE_NAME], "readwrite"); const objectStore = transaction.objectStore(CONVERSATIONS_STORE_NAME); const request = objectStore.put(data); request.onsuccess = () => resolve(); request.onerror = event => reject("Error saving data:", event.target.errorCode); }); }, getUserSettings: function (key) { return new Promise((resolve, reject) => { const transaction = db.transaction([USER_SETTINGS_STORE_NAME], 'readonly'); const store = transaction.objectStore(USER_SETTINGS_STORE_NAME); const request = store.get(key); request.onsuccess = function (event) { const settings = event.target.result; log(settings); resolve(settings); }; request.onerror = function (event) { console.error('读取设置失败', event.target.errorCode); reject(event.target.errorCode); }; }); }, updateUserSettings: function (newSettings) { return new Promise((resolve, reject) => { const transaction = db.transaction([USER_SETTINGS_STORE_NAME], 'readwrite'); const store = transaction.objectStore(USER_SETTINGS_STORE_NAME); const request = store.put(newSettings); request.onsuccess = function (event) { log('设置更新成功'); resolve(); }; request.onerror = function (event) { console.error('更新设置失败', event.target.errorCode); reject(event.target.errorCode); }; }); }, changeConversationDataTopic: async function (url, newTopic) { if (!url || !urlOperations.isForLiveValidURL(url)) { return; } return new Promise((resolve, reject) => { if (!db) { console.error("加载数据:Database has not been initialized."); return; } if (!url) { reject("加载数据:No URL key specified."); return; } const transaction = db.transaction([CONVERSATIONS_STORE_NAME], "readwrite"); const objectStore = transaction.objectStore(CONVERSATIONS_STORE_NAME); const request = objectStore.get(url); request.onsuccess = event => { let result = event.target.result; result.rootNode.content = newTopic; dbOperations.saveConversationsData(result) .then(() => dbOperations.initConversationData()) .then(information => { controlPanelKit.updateCategorySelect(); }) .catch(error => { console.error(error); }); }; request.onerror = event => reject("Error loading data:", event.target.errorCode); }); }, loadConversationsData: function (url) { if (!url || (!urlOperations.isForLiveValidURL(url)) && (!urlOperations.isForDeletedValidURL(url))) { return; } return new Promise((resolve, reject) => { if (!db) { console.error("加载数据:Database has not been initialized."); return; } if (!url) { reject("加载数据:No URL key specified."); return; } const transaction = db.transaction([CONVERSATIONS_STORE_NAME], "readwrite"); const objectStore = transaction.objectStore(CONVERSATIONS_STORE_NAME); const request = objectStore.get(url); request.onsuccess = event => { let result = event.target.result; log(" resultOfRequest:", result); if (!result) { let conversationData = { url: url, rootNode: new DialogueNode(Default_RootNode_Content, "chatGPT"), uuid2pathMap: new Map(), uuid2nodeMap: new Map(), path2nodeMap: new Map(), bookMarked: new Map(), timestamp: Date.now(), participants: { user: { name: "UserName", avatarURL: "UserAvatarURL", avatarHTML: "User", }, gpt: { type: "GPT-3", } } }; conversationData.uuid2nodeMap.set(conversationData.rootNode.uuid, conversationData.rootNode); conversationData.uuid2pathMap.set(conversationData.rootNode.uuid, []); conversationData.path2nodeMap.set('', conversationData.rootNode); log("在load中: data", conversationData); resolve(conversationData); // const addRequest = objectStore.add(conversationData); // addRequest.onsuccess = () => { // log("返回data:", conversationData); // resolve(conversationData); // } // addRequest.onerror = event => reject("Error creating new data:", event.target.errorCode); } else { log("dataExisting!"); conversationData = result; if (!conversationData.bookMarked) { conversationData.bookMarked = new Map(); } if (!conversationData.participants) { conversationData.participants = { user: { name: "UserName", avatarURL: "UserAvatarURL", avatarHTML: "User", }, gpt: { type: "GPT-3", } } } root = d3.hierarchy(conversationData.rootNode); const widthPerNode = 30; const heightPerNode = 30; treeLayout = d3.tree().nodeSize([widthPerNode, heightPerNode]); treeLayout(root); settingsKit.refreshTree(); resolve(result); } }; request.onerror = event => reject("Error loading data:", event.target.errorCode); }); }, deleteConversationData: function (url) { return new Promise((resolve, reject) => { if (!url || !urlOperations.isForLiveValidURL(url)) { reject('Invalid URL'); return; } if (!db) { console.error('删除数据: Database has not been initialized.'); reject('Database not initialized'); return; } const transaction = db.transaction([CONVERSATIONS_STORE_NAME], 'readwrite'); const objectStore = transaction.objectStore(CONVERSATIONS_STORE_NAME); const deleteRequest = objectStore.delete(url); deleteRequest.onsuccess = () => { log(`Data for URL ${url} has been deleted.`); resolve(); }; deleteRequest.onerror = event => { console.error('Error deleting data:', event.target.errorCode); reject(event.target.errorCode); }; }); }, addSearchRecord: function (records) { return new Promise((resolve, reject) => { const transaction = db.transaction([SEARCH_HISTORY_STORE_NAME], 'readwrite'); const store = transaction.objectStore(SEARCH_HISTORY_STORE_NAME); const request = store.put({id: 'searchRecords', records: records}); request.onsuccess = () => { log('搜索记录已成功更新'); resolve(); }; request.onerror = () => { console.error('更新搜索记录时出错'); reject(new Error('更新搜索记录时出错')); }; }); }, getSearchHistory: function () { return new Promise((resolve, reject) => { const transaction = db.transaction([SEARCH_HISTORY_STORE_NAME], 'readonly'); const store = transaction.objectStore(SEARCH_HISTORY_STORE_NAME); const request = store.get('searchRecords'); request.onsuccess = event => { const records = event.target.result?.records || []; log('搜索历史记录:', records); searchHistoryRecord = records; resolve(records); }; request.onerror = event => { console.error('获取搜索历史记录失败'); reject(new Error('获取搜索历史记录失败')); }; }); } }; window.addEventListener('DOMContentLoaded', (event) => { log('DOM fully loaded and parsed'); // 在这里调用你的函数 let timeout; timeout = setTimeout(() => DOMOperations.setNavBarDiv(), 1000); }); const titleDiv = document.createElement('div'); const title = document.createElement('h3'); const stickyDiv = document.createElement('div'); const navPanelButton = document.createElement('button'); const navMainButton = document.createElement('button'); const DOMOperations = { setNavBarDiv: function () { let HistoryDiv = document.querySelector('.flex-col.flex-1.transition-opacity.duration-500.-mr-2.pr-2.overflow-y-auto'); let NoHistoryDiv = document.querySelector('.absolute.left-0.top-14.z-20.overflow-hidden.transition-all.duration-500.invisible.max-h-0'); // let navbarHTML = ` //Click to take the survey(Google Forms)