CKUI

A modern, dependency-free UI library for Tampermonkey scripts

Dit script moet niet direct worden geïnstalleerd - het is een bibliotheek voor andere scripts om op te nemen met de meta-richtlijn // @require https://update.greasyfork.org/scripts/564901/1748183/CKUI.js

Voor het installeren van scripts heb je een extensie nodig, zoals Tampermonkey, Greasemonkey of Violentmonkey.

Voor het installeren van scripts heb je een extensie nodig, zoals {tampermonkey_link:Tampermonkey}.

Voor het installeren van scripts heb je een extensie nodig, zoals Tampermonkey of Violentmonkey.

Voor het installeren van scripts heb je een extensie nodig, zoals Tampermonkey of Userscripts.

Voor het installeren van scripts heb je een extensie nodig, zoals {tampermonkey_link:Tampermonkey}.

Voor het installeren van scripts heb je een gebruikersscriptbeheerder nodig.

(Ik heb al een user script manager, laat me het downloaden!)

Voor het installeren van gebruikersstijlen heb je een extensie nodig, zoals {stylus_link:Stylus}.

Voor het installeren van gebruikersstijlen heb je een extensie nodig, zoals {stylus_link:Stylus}.

Voor het installeren van gebruikersstijlen heb je een extensie nodig, zoals {stylus_link:Stylus}.

Voor het installeren van gebruikersstijlen heb je een gebruikersstijlbeheerder nodig.

Voor het installeren van gebruikersstijlen heb je een gebruikersstijlbeheerder nodig.

Voor het installeren van gebruikersstijlen heb je een gebruikersstijlbeheerder nodig.

(Ik heb al een beheerder - laat me doorgaan met de installatie!)

// ==UserScript==
// @name         CKUI
// @namespace    ckylin-script-lib-ckui
// @version      2.1.1
// @description  A modern, dependency-free UI library for Tampermonkey scripts
// @match        http://*
// @match        https://*
// @grant        unsafeWindow
// @author       CKylinMC
// @license      GPL-3.0-only
// ==/UserScript==

// 调试用
if (typeof unsafeWindow === 'undefined' || !unsafeWindow) {
    window.unsafeWindow = window;
}

(function(unsafeWindow, document) {
    'use strict';
    
    if (unsafeWindow.ckui && unsafeWindow.ckui.__initialized) {
        console.log('[CKUI] Already initialized, skipping...');
        return;
    }

    const globalConfig = {
        zIndexBase: 999990,
        currentTheme: 'light'
    };

    // 全局鼠标追踪状态
    if (!unsafeWindow.__ckui_mouseTrackingEnabled) {
        unsafeWindow.__ckui_mouseTrackingEnabled = false;
        unsafeWindow.__ckui_lastMouseX = null;
        unsafeWindow.__ckui_lastMouseY = null;
    }

    class InstanceManager {
        constructor() {
            this.modals = new Map();
            this.floatWindows = new Map();
            this.forms = new Map();
        }

        register(type, id, instance) {
            const map = this[type];
            if (map) {
                map.set(id, instance);
            }
        }

        unregister(type, id) {
            const map = this[type];
            if (map) {
                map.delete(id);
            }
        }

        get(type, id) {
            const map = this[type];
            return map ? map.get(id) : null;
        }

        has(type, id) {
            const map = this[type];
            return map ? map.has(id) : false;
        }
    }

    const instanceManager = new InstanceManager();

    class Reactive {
        constructor(value) {
            this._value = value;
            this._subscribers = [];
        }

        get value() {
            return this._value;
        }

        set value(newValue) {
            if (this._value !== newValue) {
                this._value = newValue;
                this._notify();
            }
        }

        subscribe(callback) {
            this._subscribers.push(callback);
            return () => {
                this._subscribers = this._subscribers.filter(cb => cb !== callback);
            };
        }

        _notify() {
            this._subscribers.forEach(callback => {
                try {
                    callback(this._value);
                } catch (e) {
                    console.error('[CKUI] Reactive callback error:', e);
                }
            });
        }
    }

    const utils = {
        uuid() {
            return 'ckui-' + Date.now().toString(36) + '-' + Math.random().toString(36).substr(2, 9);
        },

        createElement(tag, props = {}, children = []) {
            const el = document.createElement(tag);
            
            Object.entries(props).forEach(([key, value]) => {

                if (value === undefined || value === null) {
                    return;
                }
                
                if (key === 'style' && typeof value === 'object') {
                    Object.assign(el.style, value);
                } else if (key === 'class' || key === 'className') {
                    el.className = value;
                } else if (key.startsWith('on') && typeof value === 'function') {
                    el.addEventListener(key.substring(2).toLowerCase(), value);
                } else if (key === 'dataset' && typeof value === 'object') {
                    Object.assign(el.dataset, value);
                } else if (key === 'disabled' && value === false) {

                    return;
                } else {
                    el.setAttribute(key, value);
                }
            });

            children.forEach(child => {
                if (typeof child === 'string') {
                    el.appendChild(document.createTextNode(child));
                } else if (child instanceof Node) {
                    el.appendChild(child);
                }
            });

            return el;
        },

        injectStyles(css, id = null) {
            const styleId = id || `ckui-style-${Date.now()}`;
            let style = document.getElementById(styleId);
            
            if (!style) {
                style = document.createElement('style');
                style.id = styleId;
                document.head.appendChild(style);
            }
            
            style.textContent = css;
            return style;
        },

        escapeHtml(text) {
            const div = document.createElement('div');
            div.textContent = text;
            return div.innerHTML;
        },

        createShadowHost(options = {}) {
            const host = document.createElement('div');
            host.className = 'ckui-shadow-host';
            const zIndex = globalConfig.zIndexBase + 20;
            host.style.cssText = `all: initial; position: fixed; top: 0; left: 0; width: 0; height: 0;`;
            host.style.zIndex = zIndex; 
            
            const shadowRoot = host.attachShadow({ mode: 'open' });
            
            const style = document.createElement('style');
            style.textContent = coreStyles;
            shadowRoot.appendChild(style);
            
            const container = document.createElement('div');
            container.style.cssText = `position: fixed; top: 0; left: 0; width: 100vw; height: 100vh; z-index: 1;`;
            shadowRoot.appendChild(container);
            
            document.body.appendChild(host);
            
            return {
                host,
                shadowRoot,
                container
            };
        }
    };

    const coreStyles = `
        /* CKUI Core Styles - Isolated with high specificity */
        .ckui-root {
            /* all: initial; */ 
            font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
            font-size: 14px;
            line-height: 1.5;
            color: #333;
            box-sizing: border-box;
            
            /* CSS Variables for customization */
            --ckui-primary: #0f172a;
            --ckui-primary-hover: #1e293b;
            --ckui-secondary: #f8fafc;
            --ckui-secondary-hover: #f1f5f9;
            --ckui-border: #e5e7eb;
            --ckui-border-dark: #cbd5e1;
            --ckui-text: #0f172a;
            --ckui-text-secondary: #64748b;
            --ckui-text-muted: #94a3b8;
            --ckui-bg: white;
            --ckui-bg-secondary: #f8fafc;
            --ckui-success: #10b981;
            --ckui-success-hover: #059669;
            --ckui-danger: #ef4444;
            --ckui-danger-hover: #dc2626;
            --ckui-warning: #f59e0b;
            --ckui-info: #3b82f6;
            --ckui-btn-primary-text: white;
            --ckui-btn-danger-text: white;
            --ckui-btn-success-text: white;
            --ckui-radius: 6px;
            --ckui-radius-sm: 4px;
            --ckui-shadow-sm: 0 1px 3px rgba(0, 0, 0, 0.05);
            --ckui-shadow: 0 4px 12px rgba(0, 0, 0, 0.1);
            --ckui-shadow-lg: 0 4px 16px rgba(0, 0, 0, 0.1);
            --ckui-spacing-xs: 4px;
            --ckui-spacing-sm: 8px;
            --ckui-spacing: 12px;
            --ckui-spacing-md: 16px;
            --ckui-spacing-lg: 20px;
            --ckui-spacing-xl: 24px;
            --ckui-animation-duration: 0.2s;
            --ckui-animation-easing: ease-out;
        }

        .ckui-root *, .ckui-root *::before, .ckui-root *::after {
            box-sizing: border-box;
            margin: 0;
            padding: 0;
        }

        /* Overlay */
        .ckui-overlay {
            position: fixed;
            top: 0;
            left: 0;
            right: 0;
            bottom: 0;
            background: rgba(0, 0, 0, 0.5);
            display: flex;
            align-items: center;
            justify-content: center;
            animation: ckui-fade-in var(--ckui-animation-duration) var(--ckui-animation-easing);
        }

        /* Modal */
        .ckui-modal {
            position: relative;
            background: var(--ckui-bg);
            border-radius: var(--ckui-radius);
            box-shadow: var(--ckui-shadow-lg);
            border: 1px solid var(--ckui-border);
            max-width: 90vw;
            max-height: 90vh;
            display: flex;
            flex-direction: column;
            animation: ckui-modal-in var(--ckui-animation-duration) var(--ckui-animation-easing);
        }

        .ckui-modal-header {
            padding: var(--ckui-spacing-lg) var(--ckui-spacing-xl);
            border-bottom: 1px solid var(--ckui-border);
            display: flex;
            align-items: center;
            justify-content: space-between;
        }

        .ckui-modal-title {
            font-size: 18px;
            font-weight: 600;
            color: var(--ckui-text);
            margin: 0;
        }

        .ckui-modal-close {
            background: none;
            border: none;
            font-size: 24px;
            color: var(--ckui-text-secondary);
            cursor: pointer;
            padding: 0;
            width: 32px;
            height: 32px;
            display: flex;
            align-items: center;
            justify-content: center;
            border-radius: var(--ckui-radius);
            transition: all var(--ckui-animation-duration);
        }

        .ckui-modal-close:hover {
            background: var(--ckui-secondary-hover);
            color: var(--ckui-text);
        }

        .ckui-modal-body {
            padding: var(--ckui-spacing-xl);
            overflow-y: auto;
            flex: 1;
        }

        .ckui-modal-footer {
            padding: var(--ckui-spacing-md) var(--ckui-spacing-xl);
            border-top: 1px solid var(--ckui-border);
            display: flex;
            justify-content: flex-end;
            gap: var(--ckui-spacing);
        }

        /* Float Window */
        .ckui-float-window {
            position: fixed;
            background: var(--ckui-bg);
            border-radius: var(--ckui-radius);
            box-shadow: var(--ckui-shadow-lg);
            border: 1px solid var(--ckui-border);
            display: flex;
            flex-direction: column;
            min-width: 200px;
            max-width: 90vw;
            max-height: 90vh;
        }

        .ckui-float-header {
            padding: var(--ckui-spacing) var(--ckui-spacing-md);
            background: var(--ckui-bg);
            border-bottom: 1px solid var(--ckui-border);
            color: var(--ckui-text);
            cursor: move;
            user-select: none;
            border-radius: var(--ckui-radius) var(--ckui-radius) 0 0;
            display: flex;
            align-items: center;
            justify-content: space-between;
        }

        .ckui-float-title {
            font-size: 14px;
            font-weight: 600;
            margin: 0;
        }

        .ckui-float-controls {
            display: flex;
            gap: 4px;
        }

        .ckui-float-btn {
            background: transparent;
            border: none;
            color: var(--ckui-text-secondary);
            width: 24px;
            height: 24px;
            border-radius: var(--ckui-radius-sm);
            cursor: pointer;
            display: flex;
            align-items: center;
            justify-content: center;
            font-size: 16px;
            transition: all var(--ckui-animation-duration);
        }

        .ckui-float-btn:hover {
            background: var(--ckui-secondary-hover);
            color: var(--ckui-text);
        }

        .ckui-float-body {
            padding: var(--ckui-spacing-md);
            overflow-y: auto;
            flex: 1;
        }

        /* Notification */
        .ckui-notification-container {
            position: fixed;
            top: var(--ckui-spacing-lg);
            right: var(--ckui-spacing-lg);
            display: flex;
            flex-direction: column;
            gap: var(--ckui-spacing);
            pointer-events: none;
        }

        .ckui-notification {
            background: var(--ckui-bg);
            border-radius: var(--ckui-radius);
            box-shadow: var(--ckui-shadow);
            border: 1px solid var(--ckui-border);
            padding: var(--ckui-spacing-md) var(--ckui-spacing-lg);
            min-width: 300px;
            max-width: 400px;
            display: flex;
            align-items: flex-start;
            gap: var(--ckui-spacing);
            pointer-events: auto;
            animation: ckui-slide-in-right var(--ckui-animation-duration) var(--ckui-animation-easing);
        }

        .ckui-notification.success { border-left: 3px solid var(--ckui-success); }
        .ckui-notification.error { border-left: 3px solid var(--ckui-danger); }
        .ckui-notification.warning { border-left: 3px solid var(--ckui-warning); }
        .ckui-notification.info { border-left: 3px solid var(--ckui-info); }

        .ckui-notification-icon {
            font-size: 20px;
            flex-shrink: 0;
        }

        .ckui-notification-content {
            flex: 1;
        }

        .ckui-notification-title {
            font-weight: 600;
            color: var(--ckui-text);
            margin-bottom: var(--ckui-spacing-xs);
        }

        .ckui-notification-message {
            color: var(--ckui-text-secondary);
            font-size: 13px;
        }

        .ckui-notification-close {
            background: none;
            border: none;
            color: #94a3b8;
            cursor: pointer;
            font-size: 16px;
            padding: 0;
            width: 20px;
            height: 20px;
            display: flex;
            align-items: center;
            justify-content: center;
            flex-shrink: 0;
        }

        /* Button */
        .ckui-btn {
            display: inline-flex;
            align-items: center;
            justify-content: center;
            padding: var(--ckui-spacing-sm) var(--ckui-spacing-md);
            height: 36px;
            border: 1px solid var(--ckui-border);
            border-radius: var(--ckui-radius);
            background: var(--ckui-bg);
            color: var(--ckui-text);
            font-size: 14px;
            font-weight: 500;
            cursor: pointer;
            transition: all var(--ckui-animation-duration);
            outline: none;
            user-select: none;
        }

        .ckui-btn:hover {
            background: var(--ckui-secondary);
            border-color: var(--ckui-border-dark);
        }

        .ckui-btn:active {
            transform: scale(0.98);
        }

        .ckui-btn-primary {
            background: var(--ckui-primary);
            color: var(--ckui-btn-primary-text);
            border-color: var(--ckui-primary);
        }

        .ckui-btn-primary:hover {
            background: var(--ckui-primary-hover);
            border-color: var(--ckui-primary-hover);
        }

        .ckui-btn-danger {
            background: var(--ckui-danger);
            color: var(--ckui-btn-danger-text);
            border-color: var(--ckui-danger);
        }

        .ckui-btn-danger:hover {
            background: var(--ckui-danger-hover);
            border-color: var(--ckui-danger-hover);
        }

        .ckui-btn-success {
            background: var(--ckui-success);
            color: var(--ckui-btn-success-text);
            border-color: var(--ckui-success);
        }

        .ckui-btn-success:hover {
            background: var(--ckui-success-hover);
            border-color: var(--ckui-success-hover);
        }

        /* Input */
        .ckui-input {
            display: inline-block;
            width: 100%;
            height: 36px;
            padding: var(--ckui-spacing-sm) var(--ckui-spacing);
            border: 1px solid var(--ckui-border);
            border-radius: var(--ckui-radius);
            font-size: 14px;
            color: var(--ckui-text);
            background: var(--ckui-bg);
            transition: all var(--ckui-animation-duration);
            outline: none;
        }

        .ckui-input:focus {
            border-color: var(--ckui-info);
            box-shadow: 0 0 0 3px rgba(59, 130, 246, 0.1);
        }

        .ckui-input:disabled {
            background: var(--ckui-secondary);
            color: var(--ckui-text-muted);
            cursor: not-allowed;
        }

        /* Textarea */
        .ckui-textarea {
            display: block;
            width: 100%;
            padding: var(--ckui-spacing-sm) var(--ckui-spacing);
            border: 1px solid var(--ckui-border);
            border-radius: var(--ckui-radius);
            font-size: 14px;
            color: var(--ckui-text);
            background: var(--ckui-bg);
            transition: all var(--ckui-animation-duration);
            outline: none;
            resize: vertical;
            min-height: 80px;
            font-family: inherit;
        }

        .ckui-textarea:focus {
            border-color: var(--ckui-info);
            box-shadow: 0 0 0 3px rgba(59, 130, 246, 0.1);
        }

        /* Select */
        .ckui-select {
            display: inline-block;
            width: 100%;
            height: 36px;
            padding: var(--ckui-spacing-sm) var(--ckui-spacing);
            border: 1px solid var(--ckui-border);
            border-radius: var(--ckui-radius);
            font-size: 14px;
            color: var(--ckui-text);
            background: var(--ckui-bg);
            transition: all var(--ckui-animation-duration);
            outline: none;
            cursor: pointer;
        }

        .ckui-select:focus {
            border-color: var(--ckui-info);
            box-shadow: 0 0 0 3px rgba(59, 130, 246, 0.1);
        }

        /* Checkbox & Radio */
        .ckui-checkbox, .ckui-radio {
            display: inline-flex;
            align-items: center;
            cursor: pointer;
            user-select: none;
        }

        .ckui-checkbox input, .ckui-radio input {
            margin-right: 8px;
            width: 16px;
            height: 16px;
            cursor: pointer;
        }

        /* Label */
        .ckui-label {
            display: block;
            margin-bottom: var(--ckui-spacing-sm);
            color: var(--ckui-text);
            font-weight: 500;
            font-size: 14px;
        }

        /* Form Group */
        .ckui-form-group {
            margin-bottom: var(--ckui-spacing);
        }

        /* Layout */
        .ckui-row {
            display: flex;
            flex-wrap: wrap;
            margin: 0 calc(-1 * var(--ckui-spacing-sm));
        }

        .ckui-col {
            flex: 1;
            padding: 0 var(--ckui-spacing-sm);
        }

        .ckui-space {
            display: flex;
            gap: var(--ckui-spacing);
            align-items: center;
        }

        .ckui-divider {
            height: 1px;
            background: var(--ckui-border);
            margin: var(--ckui-spacing-md) 0;
        }

        /* Card */
        .ckui-card {
            background: var(--ckui-bg);
            border-radius: var(--ckui-radius);
            border: 1px solid var(--ckui-border);
            box-shadow: var(--ckui-shadow-sm);
            padding: var(--ckui-spacing-md);
            display: flex;
            flex-direction: column;
        }

        .ckui-card-title {
            font-size: 16px;
            font-weight: 600;
            color: var(--ckui-text);
            margin-bottom: var(--ckui-spacing-sm);
            line-height: 1.5;
        }

        .ckui-card > *:last-child {
            margin-bottom: 0;
        }

        /* Loading */
        .ckui-loading {
            display: inline-block;
            width: 20px;
            height: 20px;
            border: 2px solid var(--ckui-border);
            border-top: 2px solid var(--ckui-primary);
            border-radius: 50%;
            animation: ckui-spin 0.8s linear infinite;
        }

        /* Animations */
        @keyframes ckui-fade-in {
            from { opacity: 0; }
            to { opacity: 1; }
        }

        @keyframes ckui-fade-out {
            from { opacity: 1; }
            to { opacity: 0; }
        }

        @keyframes ckui-modal-in {
            from {
                opacity: 0;
                transform: scale(0.95);
            }
            to {
                opacity: 1;
                transform: scale(1);
            }
        }

        @keyframes ckui-modal-out {
            from {
                opacity: 1;
                transform: scale(1);
            }
            to {
                opacity: 0;
                transform: scale(0.95);
            }
        }

        @keyframes ckui-slide-in-right {
            from {
                transform: translateX(100%);
                opacity: 0;
            }
            to {
                transform: translateX(0);
                opacity: 1;
            }
        }

        @keyframes ckui-spin {
            0% { transform: rotate(0deg); }
            100% { transform: rotate(360deg); }
        }

        /* Theme - Dark Mode */
        .ckui-root.ckui-dark {
            --ckui-primary: #3b82f6;
            --ckui-primary-hover: #2563eb;
            --ckui-secondary: #1e293b;
            --ckui-secondary-hover: #334155;
            --ckui-border: #1e293b;
            --ckui-border-dark: #334155;
            --ckui-text: #f1f5f9;
            --ckui-text-secondary: #94a3b8;
            --ckui-text-muted: #64748b;
            --ckui-bg: #0f172a;
            --ckui-bg-secondary: #1e293b;
            --ckui-btn-primary-text: white;
            --ckui-btn-danger-text: white;
            --ckui-btn-success-text: white;
        }

        .ckui-root.ckui-dark .ckui-modal,
        .ckui-root.ckui-dark .ckui-float-window,
        .ckui-root.ckui-dark .ckui-notification,
        .ckui-root.ckui-dark .ckui-card {
            background: var(--ckui-bg);
            border-color: var(--ckui-border);
            color: var(--ckui-text);
        }

        .ckui-root.ckui-dark .ckui-modal-header,
        .ckui-root.ckui-dark .ckui-modal-footer,
        .ckui-root.ckui-dark .ckui-float-header {
            background: var(--ckui-bg);
            border-color: var(--ckui-border);
        }

        .ckui-root.ckui-dark .ckui-modal-body,
        .ckui-root.ckui-dark .ckui-float-body {
            background: var(--ckui-bg);
            color: var(--ckui-text) !important;
        }

        .ckui-root.ckui-dark .ckui-modal-body *,
        .ckui-root.ckui-dark .ckui-float-body * {
            color: inherit;
        }

        .ckui-root.ckui-dark .ckui-modal-title,
        .ckui-root.ckui-dark .ckui-float-title,
        .ckui-root.ckui-dark .ckui-card-title,
        .ckui-root.ckui-dark .ckui-label {
            color: var(--ckui-text);
        }

        .ckui-root.ckui-dark .ckui-modal-close,
        .ckui-root.ckui-dark .ckui-float-btn,
        .ckui-root.ckui-dark .ckui-notification-close {
            color: var(--ckui-text-secondary);
        }

        .ckui-root.ckui-dark .ckui-modal-close:hover,
        .ckui-root.ckui-dark .ckui-float-btn:hover {
            background: var(--ckui-secondary-hover);
            color: var(--ckui-text);
        }

        .ckui-root.ckui-dark .ckui-input,
        .ckui-root.ckui-dark .ckui-textarea,
        .ckui-root.ckui-dark .ckui-select {
            background: var(--ckui-bg-secondary);
            border-color: var(--ckui-border-dark);
            color: var(--ckui-text);
        }

        .ckui-root.ckui-dark .ckui-btn {
            background: var(--ckui-secondary) !important;
            border-color: var(--ckui-border-dark) !important;
            color: var(--ckui-text) !important;
        }

        .ckui-root.ckui-dark .ckui-btn:hover {
            background: var(--ckui-secondary-hover) !important;
            border-color: var(--ckui-border-dark) !important;
        }

        .ckui-root.ckui-dark .ckui-divider {
            background: var(--ckui-border);
        }

        .ckui-root.ckui-dark .ckui-notification-title {
            color: var(--ckui-text);
        }

        .ckui-root.ckui-dark .ckui-notification-message {
            color: var(--ckui-text-secondary);
        }

        /* Dark mode notification color enhancements */
        .ckui-root.ckui-dark .ckui-notification.success {
            border-left-color: #22c55e;
            background-color: var(--ckui-bg);
            background-image: linear-gradient(to right, rgba(34, 197, 94, 0.2) 0%, transparent 30%);
        }

        .ckui-root.ckui-dark .ckui-notification.error {
            border-left-color: #f87171;
            background-color: var(--ckui-bg);
            background-image: linear-gradient(to right, rgba(248, 113, 113, 0.2) 0%, transparent 30%);
        }

        .ckui-root.ckui-dark .ckui-notification.warning {
            border-left-color: #fbbf24;
            background-color: var(--ckui-bg);
            background-image: linear-gradient(to right, rgba(251, 191, 36, 0.2) 0%, transparent 30%);
        }

        .ckui-root.ckui-dark .ckui-notification.info {
            border-left-color: #60a5fa;
            background-color: var(--ckui-bg);
            background-image: linear-gradient(to right, rgba(96, 165, 250, 0.2) 0%, transparent 30%);
        }

        /* 深色模式下primary按钮直接使用变量,无需重定义 */
        .ckui-root.ckui-dark .ckui-btn-primary {
            background: var(--ckui-primary) !important;
            color: var(--ckui-btn-primary-text) !important;
            border-color: var(--ckui-primary) !important;
        }

        .ckui-root.ckui-dark .ckui-btn-primary:hover {
            background: var(--ckui-primary-hover) !important;
            border-color: var(--ckui-primary-hover) !important;
        }

        .ckui-root.ckui-dark .ckui-btn-danger {
            --ckui-danger: #dc2626;
            --ckui-danger-hover: #b91c1c;
            background: var(--ckui-danger);
            color: var(--ckui-btn-danger-text);
            border-color: var(--ckui-danger);
        }

        .ckui-root.ckui-dark .ckui-btn-danger:hover {
            background: var(--ckui-danger-hover);
            border-color: var(--ckui-danger-hover);
        }

        .ckui-root.ckui-dark .ckui-btn-success {
            --ckui-success: #059669;
            --ckui-success-hover: #047857;
            background: var(--ckui-success);
            color: var(--ckui-btn-success-text);
            border-color: var(--ckui-success);
        }

        .ckui-root.ckui-dark .ckui-btn-success:hover {
            background: var(--ckui-success-hover);
            border-color: var(--ckui-success-hover);
        }

        .ckui-root.ckui-dark .ckui-overlay {
            background: rgba(0, 0, 0, 0.8);
        }

        .ckui-root.ckui-dark .ckui-input:focus,
        .ckui-root.ckui-dark .ckui-textarea:focus,
        .ckui-root.ckui-dark .ckui-select:focus {
            border-color: #60a5fa;
            box-shadow: 0 0 0 3px rgba(96, 165, 250, 0.2);
        }
    `;

    class NotificationManager {
        constructor() {
            this.container = null;
            this.shadowHost = null;
            this.useShadow = false;
            this.init();
        }

        init(useShadow = false) {
            if (!this.container) {
                this.useShadow = useShadow;
                const className = globalConfig.currentTheme === 'dark' 
                    ? 'ckui-root ckui-dark ckui-notification-container'
                    : 'ckui-root ckui-notification-container';
                
                if (useShadow) {
                    const shadow = utils.createShadowHost();
                    this.shadowHost = shadow.host;
                    shadow.container.style.pointerEvents = 'none';
                    this.container = utils.createElement('div', {
                        class: className,
                        style: { zIndex: globalConfig.zIndexBase + 10 }
                    });
                    shadow.container.appendChild(this.container);
                } else {
                    this.container = utils.createElement('div', {
                        class: className,
                        style: { zIndex: globalConfig.zIndexBase + 10 }
                    });
                    document.body.appendChild(this.container);
                }
            }
        }

        show(options = {}) {
            const {
                title = '',
                message = '',
                type = 'info',
                duration = 3000,
                closable = true,
                shadow = false
            } = options;
            
            if (shadow && !this.useShadow) {
                this.destroy();
                this.init(true);
            } else if (!shadow && this.useShadow) {
                this.destroy();
                this.init(false);
            } else if (!this.container) {
                this.init(shadow);
            }

            const icons = {
                success: '✓',
                error: '✕',
                warning: '⚠',
                info: 'ℹ'
            };

            const notification = utils.createElement('div', {
                class: `ckui-notification ${type}`
            }, [
                utils.createElement('div', {
                    class: 'ckui-notification-icon'
                }, [icons[type] || icons.info]),
                utils.createElement('div', {
                    class: 'ckui-notification-content'
                }, [
                    title ? utils.createElement('div', {
                        class: 'ckui-notification-title'
                    }, [title]) : null,
                    message ? utils.createElement('div', {
                        class: 'ckui-notification-message'
                    }, [message]) : null
                ].filter(Boolean)),
                closable ? utils.createElement('button', {
                    class: 'ckui-notification-close',
                    onclick: () => this.close(notification)
                }, ['×']) : null
            ].filter(Boolean));

            this.container.appendChild(notification);

            if (duration > 0) {
                setTimeout(() => this.close(notification), duration);
            }

            return notification;
        }

        close(notification) {
            if (notification && notification.parentNode) {
                notification.style.animation = 'ckui-fade-out 0.2s ease-out forwards';
                setTimeout(() => {
                    if (notification.parentNode) {
                        notification.parentNode.removeChild(notification);
                    }
                }, 200);
            }
        }

        success(message, title = '成功') {
            return this.show({ type: 'success', title, message });
        }

        error(message, title = '错误') {
            return this.show({ type: 'error', title, message });
        }

        warning(message, title = '警告') {
            return this.show({ type: 'warning', title, message });
        }

        info(message, title = '提示') {
            return this.show({ type: 'info', title, message });
        }

        destroy() {
            if (this.container && this.container.parentNode) {
                this.container.parentNode.removeChild(this.container);
            }
            if (this.shadowHost && this.shadowHost.parentNode) {
                this.shadowHost.parentNode.removeChild(this.shadowHost);
            }
            this.container = null;
            this.shadowHost = null;
            this.useShadow = false;
        }
    }

    class Modal {
        constructor(options = {}) {
            this.id = options.id || null;
            this.options = {
                title: options.title || '提示',
                content: options.content || '',
                width: options.width || '500px',
                showClose: options.showClose !== false,
                footer: options.footer,
                onOk: options.onOk,
                onCancel: options.onCancel,
                maskClosable: options.maskClosable !== false,
                shadow: options.shadow || false,
                ...options
            };

            this.overlay = null;
            this.modal = null;
            this.resolvePromise = null;
            this.rejectPromise = null;
            this.isShowing = false;
            this.shadowHost = null;

            if (this.id) {
                instanceManager.register('modals', this.id, this);
            }
        }

        show() {

            if (this.isShowing) {
                this.close(false);
            }
            
            this.isShowing = true;
            return new Promise((resolve, reject) => {
                this.resolvePromise = resolve;
                this.rejectPromise = reject;
                this.render();
            });
        }

        refresh(options = {}) {

            this.options = { ...this.options, ...options };

            if (this.isShowing) {
                this.close(false);
                this.show();
            }
            
            return this;
        }

        render() {
            if (this.options.shadow) {
                const shadow = utils.createShadowHost();
                this.shadowHost = shadow.host;
            }

            const className = globalConfig.currentTheme === 'dark'
                ? 'ckui-root ckui-dark ckui-overlay'
                : 'ckui-root ckui-overlay';
            this.overlay = utils.createElement('div', {
                class: className,
                style: { zIndex: globalConfig.zIndexBase + 8 },
                onclick: (e) => {
                    if (this.options.maskClosable && e.target === this.overlay) {
                        this.cancel();
                    }
                }
            });

            if (!this.options.shadow) {
                const existingOverlays = document.querySelectorAll('.ckui-overlay');
                if (existingOverlays.length > 0) {
                    const maxZ = Math.max(...Array.from(existingOverlays).map(el => parseInt(el.style.zIndex) || 0));
                    this.overlay.style.zIndex = maxZ + 1;
                }
            }

            this.modal = utils.createElement('div', {
                class: 'ckui-modal',
                style: { width: this.options.width }
            });

            const header = utils.createElement('div', {
                class: 'ckui-modal-header'
            }, [
                utils.createElement('h3', {
                    class: 'ckui-modal-title'
                }, [this.options.title]),
                this.options.showClose ? utils.createElement('button', {
                    class: 'ckui-modal-close',
                    onclick: () => this.cancel()
                }, ['×']) : null
            ].filter(Boolean));

            const body = utils.createElement('div', {
                class: 'ckui-modal-body'
            });

            if (typeof this.options.content === 'string') {
                body.innerHTML = this.options.content;
            } else if (this.options.content instanceof Node) {
                body.appendChild(this.options.content);
            }

            let footer;
            if (this.options.footer === null) {
                footer = null;
            } else if (this.options.footer === 'alert') {

                footer = utils.createElement('div', {
                    class: 'ckui-modal-footer'
                }, [
                    utils.createElement('button', {
                        class: 'ckui-btn ckui-btn-primary',
                        onclick: () => this.ok()
                    }, ['确定'])
                ]);
            } else if (this.options.footer) {
                footer = utils.createElement('div', {
                    class: 'ckui-modal-footer'
                });
                if (this.options.footer instanceof Node) {
                    footer.appendChild(this.options.footer);
                } else {
                    footer.innerHTML = this.options.footer;
                }
            } else {
                footer = utils.createElement('div', {
                    class: 'ckui-modal-footer'
                }, [
                    utils.createElement('button', {
                        class: 'ckui-btn',
                        onclick: () => this.cancel()
                    }, ['取消']),
                    utils.createElement('button', {
                        class: 'ckui-btn ckui-btn-primary',
                        onclick: () => this.ok()
                    }, ['确定'])
                ]);
            }

            [header, body, footer].filter(Boolean).forEach(el => {
                this.modal.appendChild(el);
            });

            this.overlay.appendChild(this.modal);
            
            if (this.options.shadow && this.shadowHost) {
                this.shadowHost.shadowRoot.querySelector('div').appendChild(this.overlay);
            } else {
                document.body.appendChild(this.overlay);
            }

            this.handleEscape = (e) => {
                if (e.key === 'Escape') {
                    this.cancel();
                }
            };
            document.addEventListener('keydown', this.handleEscape);
        }

        async ok() {
            let shouldClose = true;
            let returnValue = true;
            
            if (this.options.onOk) {
                const result = await this.options.onOk();
                if (result === false) {
                    shouldClose = false;
                } else {
                    returnValue = result;
                }
            }

            if (shouldClose) {
                this.close(returnValue);
            }
        }

        cancel() {
            if (this.options.onCancel) {
                this.options.onCancel();
            }
            this.close(false);
        }

        close(result) {
            if (this.overlay && this.overlay.parentNode) {
                this.isShowing = false;
                document.removeEventListener('keydown', this.handleEscape);
                this.overlay.style.animation = 'ckui-fade-out 0.2s ease-out forwards';
                this.modal.style.animation = 'ckui-modal-out 0.2s ease-out forwards';
                setTimeout(() => {
                    if (this.overlay && this.overlay.parentNode) {
                        this.overlay.parentNode.removeChild(this.overlay);
                    }
                    if (this.shadowHost && this.shadowHost.parentNode) {
                        this.shadowHost.parentNode.removeChild(this.shadowHost);
                        this.shadowHost = null;
                    }
                    if (result) {
                        this.resolvePromise && this.resolvePromise(result);
                    } else {
                        this.rejectPromise && this.rejectPromise();
                    }
                }, 200);
            }
        }

        destroy() {
            this.close(false);
            if (this.id) {
                instanceManager.unregister('modals', this.id);
            }
        }

        static confirm(options) {
            const modal = new Modal(options);
            return modal.show();
        }

        static alert(options) {
            if (typeof options === 'string') {
                options = { content: options };
            }
            const modal = new Modal({
                maskClosable: false,
                showClose: false,
                ...options,
                footer: 'alert'
            });
            return modal.show().then(() => undefined).catch(() => undefined);
        }

        static prompt(options) {
            if (typeof options === 'string') {
                options = { title: options };
            }
            
            const inputValue = options.defaultValue || '';
            const input = utils.createElement('input', {
                class: 'ckui-root ckui-input',
                type: 'text',
                placeholder: options.placeholder || '',
                value: inputValue
            });
            
            const modal = new Modal({
                title: options.title || '请输入',
                content: input,
                width: options.width || '400px',
                maskClosable: false,
                ...options,
                onOk: () => {
                    return true;
                }
            });
            
            return modal.show()
                .then(() => input.value)
                .catch(() => null);
        }

        static select(options) {
            if (!options.options || !Array.isArray(options.options)) {
                throw new Error('select() requires options array');
            }
            
            let selectedValue = options.defaultValue || null;
            
            const container = utils.createElement('div', {
                class: 'ckui-root',
                style: { padding: '8px 0' }
            });
            
            const select = utils.createElement('select', {
                class: 'ckui-select',
                style: { 
                    width: '100%', 
                    fontSize: '15px',
                    height: '40px',
                    lineHeight: '1.5',
                    padding: '8px 12px'
                }
            });
            
            options.options.forEach(opt => {
                const option = utils.createElement('option', {
                    value: opt.value !== undefined ? opt.value : opt
                });
                option.textContent = opt.label || opt.toString();
                option.style.padding = '8px 12px';
                option.style.lineHeight = '1.8';
                
                if (opt.value === options.defaultValue || opt === options.defaultValue) {
                    option.selected = true;
                    selectedValue = opt.value !== undefined ? opt.value : opt;
                }
                
                select.appendChild(option);
            });

            select.onchange = () => {
                selectedValue = select.value;
            };
            
            container.appendChild(select);
            
            const modal = new Modal({
                title: options.title || '请选择',
                content: container,
                width: options.width || '400px',
                maskClosable: false,
                onOk: () => {
                    return selectedValue;
                }
            });
            
            return modal.show();
        }

        static sortableList(options) {
            if (!options.items || !Array.isArray(options.items)) {
                throw new Error('sortableList() requires items array');
            }
            
            let items = [...options.items];
            let draggedIndex = null;
            let dragOverIndex = null;
            let highlightIndices = new Set();
            
            const container = utils.createElement('div', {
                class: 'ckui-root',
                style: { minHeight: '200px', maxHeight: '400px', overflowY: 'auto', padding: '8px' }
            });

            const updateHighlights = () => {
                const itemElements = container.querySelectorAll('.ckui-item');
                itemElements.forEach((el, index) => {
                    const isHighlighted = highlightIndices.has(index);
                    if (isHighlighted) {
                        el.style.borderColor = '#10b981';
                        el.style.background = 'rgba(16, 185, 129, 0.25)';
                        el.style.boxShadow = '0 0 0 3px rgba(16, 185, 129, 0.3)';
                    } else {
                        el.style.borderColor = 'var(--ckui-border, #ccc)';
                        el.style.background = 'var(--ckui-bg, #fff)';
                        el.style.boxShadow = '';
                    }
                });
            };

            const blinkHighlight = (...indices) => {

                highlightIndices.clear();
                indices.forEach(i => highlightIndices.add(i));
                requestAnimationFrame(() => {
                    updateHighlights();

                    setTimeout(() => {
                        highlightIndices.clear();
                        requestAnimationFrame(() => {
                            updateHighlights();

                            setTimeout(() => {
                                indices.forEach(i => highlightIndices.add(i));
                                requestAnimationFrame(() => {
                                    updateHighlights();

                                    setTimeout(() => {
                                        highlightIndices.clear();
                                        requestAnimationFrame(() => {
                                            updateHighlights();
                                        });
                                    }, 400);
                                });
                            }, 400);
                        });
                    }, 400);
                });
            };

            const renderList = () => {
                container.innerHTML = '';

                items.forEach((item, index) => {
                    const itemEl = document.createElement('div');
                    itemEl.className = 'ckui-item';
                    itemEl.draggable = true;
                    itemEl.dataset.index = index;

                    const isHighlighted = highlightIndices.has(index);
                    const isDragging = draggedIndex === index;
                    itemEl.className = isHighlighted ? 'ckui-item ckui-item-highlight' : 'ckui-item';
                    itemEl.style.cssText = `
                        padding: 12px 16px;
                        margin-bottom: 8px;
                        border: 2px ${isDragging ? 'dashed' : 'solid'} var(--ckui-border, #ccc);
                        border-radius: var(--ckui-radius, 4px);
                        background: var(--ckui-bg, #fff);
                        cursor: grab;
                        display: flex;
                        align-items: center;
                        justify-content: space-between;
                        user-select: none;
                        transition: all 0.3s ease-in-out;
                        opacity: ${isDragging ? '0.6' : '1'};
                    `;

                    if (isDragging) {
                        itemEl.style.borderColor = '#3b82f6';
                        itemEl.style.background = 'rgba(59, 130, 246, 0.1)';
                        itemEl.style.cursor = 'grabbing';
                    }

                    if (isHighlighted) {
                        itemEl.style.borderColor = '#10b981';
                        itemEl.style.borderStyle = 'solid';
                        itemEl.style.background = 'rgba(16, 185, 129, 0.25)';
                        itemEl.style.boxShadow = '0 0 0 3px rgba(16, 185, 129, 0.3)';
                        itemEl.style.opacity = '1';
                    }

                    const leftContent = document.createElement('div');
                    leftContent.style.cssText = 'display: flex; align-items: center; gap: 12px; pointer-events: none;';
                    leftContent.innerHTML = `
                        <span style="color: #999; font-size: 18px;">☰</span>
                        <span style="color: #333;">${item.label || item}</span>
                    `;

                    const controls = document.createElement('div');
                    controls.style.cssText = 'display: flex; gap: 4px; pointer-events: auto;';

                    const createBtn = (text, onClick) => {
                        const btn = document.createElement('button');
                        btn.textContent = text;
                        btn.style.cssText = `
                            padding: 4px 10px;
                            cursor: pointer;
                            background: var(--ckui-secondary, #f8fafc);
                            border: 1px solid var(--ckui-border, #e5e7eb);
                            border-radius: var(--ckui-radius-sm, 4px);
                            color: var(--ckui-text-secondary, #64748b);
                            font-size: 16px;
                            line-height: 1;
                            transition: all 0.2s ease;
                            display: inline-flex;
                            align-items: center;
                            justify-content: center;
                            min-width: 28px;
                            height: 28px;
                        `;
                        btn.onclick = (e) => {
                            e.stopPropagation();
                            onClick();
                        };

                        btn.onmouseenter = () => {
                            btn.style.background = 'var(--ckui-primary, #0f172a)';
                            btn.style.color = 'white';
                            btn.style.borderColor = 'var(--ckui-primary, #0f172a)';
                            btn.style.transform = 'scale(1.1)';
                        };
                        btn.onmouseleave = () => {
                            btn.style.background = 'var(--ckui-secondary, #f8fafc)';
                            btn.style.color = 'var(--ckui-text-secondary, #64748b)';
                            btn.style.borderColor = 'var(--ckui-border, #e5e7eb)';
                            btn.style.transform = 'scale(1)';
                        };

                        btn.onmousedown = (e) => e.stopPropagation();
                        return btn;
                    };

                    if (index > 0) {
                        controls.appendChild(createBtn('↑', () => {
                            [items[index], items[index - 1]] = [items[index - 1], items[index]];

                            blinkHighlight(index - 1, index);
                        }));
                    }
                    if (index < items.length - 1) {
                        controls.appendChild(createBtn('↓', () => {
                            [items[index], items[index + 1]] = [items[index + 1], items[index]];

                            blinkHighlight(index, index + 1);
                        }));
                    }

                    itemEl.appendChild(leftContent);
                    itemEl.appendChild(controls);

                    itemEl.addEventListener('dragstart', (e) => {
                        draggedIndex = index;
                        e.dataTransfer.effectAllowed = 'move';

                        e.dataTransfer.setData('text/plain', index);
                    });

                    itemEl.addEventListener('dragover', (e) => {
                        e.preventDefault();
                        e.dataTransfer.dropEffect = 'move';
                        
                        if (draggedIndex !== null && index !== draggedIndex) {

                            const movedItem = items[draggedIndex];
                            items.splice(draggedIndex, 1);
                            items.splice(index, 0, movedItem);

                            draggedIndex = index;

                            renderList();
                        }
                    });

                    itemEl.addEventListener('drop', (e) => {
                        e.preventDefault();
                        e.stopPropagation();

                        if (draggedIndex !== null) {

                            blinkHighlight(index);
                        }
                    });

                    itemEl.addEventListener('dragend', () => {
                        draggedIndex = null;
                        renderList();
                    });

                    container.appendChild(itemEl);
                });
            };

            renderList();
            
            const modal = new Modal({
                title: options.title || '排序列表',
                content: container,
                width: options.width || '500px',
                maskClosable: false,
                onOk: () => {
                    return items;
                }
            });
            
            return modal.show();
        }
    }

    class FloatWindow {
        constructor(options = {}) {
            this.id = options.id || null;
            this.options = {
                title: options.title || '浮动窗口',
                content: options.content || '',
                width: options.width || '400px',
                height: options.height || 'auto',
                x: options.x || 100,
                y: options.y || 100,
                padding: options.padding || '16px',
                draggable: options.draggable !== false,
                minimizable: options.minimizable !== false,
                closable: options.closable !== false,
                onClose: options.onClose || null,
                shadow: options.shadow || false,
                ...options
            };

            this.window = null;
            this.isDragging = false;
            this.isMinimized = false;
            this.isShowing = false;
            this.dragStartX = 0;
            this.dragStartY = 0;
            this.windowStartX = 0;
            this.windowStartY = 0;
            this.onCloseCallbacks = [];
            this.onCloseOnceCallbacks = [];
            this.shadowHost = null;

            if (this.id) {
                instanceManager.register('floatWindows', this.id, this);
            }
        }

        show() {
            if (this.isShowing && this.window && this.window.parentNode) {

                this.window.style.display = '';
                this.window.style.transition = 'opacity 0.2s ease-out, transform 0.2s cubic-bezier(0.34, 1.56, 0.64, 1)';
                this.window.style.opacity = '1';
                this.window.style.transform = 'scale(1)';
                
                setTimeout(() => {
                    if (this.window) {
                        this.window.style.transition = '';
                    }
                }, 200);
                return this;
            }
            
            this.isShowing = true;
            this.render();
            return this;
        }

        refresh(options = {}) {

            this.options = { ...this.options, ...options };

            if (this.isShowing) {
                const wasMinimized = this.isMinimized;
                this.close();
                this.show();
                if (wasMinimized) {
                    this.toggleMinimize();
                }
            }
            
            return this;
        }

        moveToMouse(offsetX = 0, offsetY = 0) {
            return new Promise((resolve) => {
                let mouseX, mouseY;
                
                // 如果已启用全局追踪且有数据,直接使用
                if (unsafeWindow.__ckui_mouseTrackingEnabled && unsafeWindow.__ckui_lastMouseX !== null) {
                    mouseX = unsafeWindow.__ckui_lastMouseX;
                    mouseY = unsafeWindow.__ckui_lastMouseY;
                } else if (!unsafeWindow.__ckui_mouseTrackingEnabled) {
                    // 未启用追踪,fallback 到旧行为:首次调用时初始化
                    if (unsafeWindow.__ckui_lastMouseX === null) {
                        unsafeWindow.__ckui_lastMouseX = unsafeWindow.innerWidth / 2;
                        unsafeWindow.__ckui_lastMouseY = unsafeWindow.innerHeight / 2;

                        document.addEventListener('mousemove', (e) => {
                            unsafeWindow.__ckui_lastMouseX = e.clientX;
                            unsafeWindow.__ckui_lastMouseY = e.clientY;
                        }, { passive: true });
                    }
                    mouseX = unsafeWindow.__ckui_lastMouseX;
                    mouseY = unsafeWindow.__ckui_lastMouseY;
                } else {
                    // 已启用追踪但还没有数据,使用页面中心
                    mouseX = unsafeWindow.innerWidth / 2;
                    mouseY = unsafeWindow.innerHeight / 2;
                }

                if (!this.window) {
                    this.render();
                }

                const rect = this.window.getBoundingClientRect();

                const centerX = mouseX - (rect.width / 2) + offsetX;
                const centerY = mouseY - (rect.height / 2) + offsetY;

                const viewportWidth = unsafeWindow.innerWidth;
                const viewportHeight = unsafeWindow.innerHeight;
                
                let finalX = centerX;
                let finalY = centerY;

                if (finalX < 20) finalX = 20;
                if (finalY < 20) finalY = 20;
                if (finalX + rect.width > viewportWidth - 20) {
                    finalX = viewportWidth - rect.width - 20;
                }
                if (finalY + rect.height > viewportHeight - 20) {
                    finalY = viewportHeight - rect.height - 20;
                }
                
                this.window.style.left = finalX + 'px';
                this.window.style.top = finalY + 'px';

                requestAnimationFrame(() => {
                    this.window.style.transition = 'opacity 0.2s ease-out, transform 0.2s cubic-bezier(0.34, 1.56, 0.64, 1)';
                    this.window.style.opacity = '1';
                    this.window.style.transform = 'scale(1)';
                    
                    setTimeout(() => {
                        if (this.window) {
                            this.window.style.transition = '';
                        }
                        resolve(this);
                    }, 200);
                });
            });
        }

        onClose(callback, once = false) {
            if (once) {
                this.onCloseOnceCallbacks.push(callback);
            } else {
                this.onCloseCallbacks.push(callback);
            }
            return this;
        }

        offClose(callback) {
            this.onCloseCallbacks = this.onCloseCallbacks.filter(cb => cb !== callback);
            this.onCloseOnceCallbacks = this.onCloseOnceCallbacks.filter(cb => cb !== callback);
            return this;
        }

        render() {
            const className = globalConfig.currentTheme === 'dark'
                ? 'ckui-root ckui-dark ckui-float-window'
                : 'ckui-root ckui-float-window';
            this.window = utils.createElement('div', {
                class: className,
                style: {
                    left: this.options.x + 'px',
                    top: this.options.y + 'px',
                    width: this.options.width,
                    height: this.options.height,
                    zIndex: globalConfig.zIndexBase + 7,
                    opacity: '0',
                    transform: 'scale(0.95)'
                }
            });

            let parent = document.body;
            if (this.options.shadow) {
                const shadow = utils.createShadowHost();
                this.shadowHost = shadow.host;
                parent = shadow.container;
            }

            const header = utils.createElement('div', {
                class: 'ckui-float-header'
            }, [
                utils.createElement('h3', {
                    class: 'ckui-float-title'
                }, [this.options.title]),
                utils.createElement('div', {
                    class: 'ckui-float-controls'
                }, [
                    this.options.minimizable ? utils.createElement('button', {
                        class: 'ckui-float-btn',
                        onclick: () => this.toggleMinimize()
                    }, ['−']) : null,
                    this.options.closable ? utils.createElement('button', {
                        class: 'ckui-float-btn',
                        onclick: () => this.close()
                    }, ['×']) : null
                ].filter(Boolean))
            ]);

            this.body = utils.createElement('div', {
                class: 'ckui-float-body',
                style: { padding: this.options.padding }
            });

            if (typeof this.options.content === 'string') {
                this.body.innerHTML = this.options.content;
            } else if (this.options.content instanceof Node) {
                this.body.appendChild(this.options.content);
            }

            this.window.appendChild(header);
            this.window.appendChild(this.body);

            if (this.options.draggable) {
                this.setupDragging(header);
            }

            parent.appendChild(this.window);

            this.adjustPosition();

            requestAnimationFrame(() => {
                this.window.style.transition = 'opacity 0.2s ease-out, transform 0.2s cubic-bezier(0.34, 1.56, 0.64, 1)';
                this.window.style.opacity = '1';
                this.window.style.transform = 'scale(1)';

                setTimeout(() => {
                    if (this.window) {
                        this.window.style.transition = '';
                    }
                }, 200);
            });
        }

        adjustPosition() {
            if (!this.window) return;
            
            const rect = this.window.getBoundingClientRect();
            const viewportWidth = unsafeWindow.innerWidth;
            const viewportHeight = unsafeWindow.innerHeight;
            
            let x = parseInt(this.window.style.left);
            let y = parseInt(this.window.style.top);

            if (rect.right > viewportWidth) {
                x = viewportWidth - rect.width - 20;
            }

            if (rect.bottom > viewportHeight) {
                y = viewportHeight - rect.height - 20;
            }

            if (x < 20) {
                x = 20;
            }

            if (y < 20) {
                y = 20;
            }
            
            this.window.style.left = x + 'px';
            this.window.style.top = y + 'px';
        }

        setupDragging(header) {
            header.style.cursor = 'move';

            const onMouseDown = (e) => {

                this.isDragging = true;
                this.dragStartX = e.clientX;
                this.dragStartY = e.clientY;
                
                const rect = this.window.getBoundingClientRect();
                this.windowStartX = rect.left;
                this.windowStartY = rect.top;

                document.addEventListener('mousemove', onMouseMove);
                document.addEventListener('mouseup', onMouseUp);
                
                e.preventDefault();
            };

            const onMouseMove = (e) => {
                if (!this.isDragging) return;

                const deltaX = e.clientX - this.dragStartX;
                const deltaY = e.clientY - this.dragStartY;

                this.window.style.left = (this.windowStartX + deltaX) + 'px';
                this.window.style.top = (this.windowStartY + deltaY) + 'px';
            };

            const onMouseUp = () => {
                this.isDragging = false;
                document.removeEventListener('mousemove', onMouseMove);
                document.removeEventListener('mouseup', onMouseUp);
            };

            header.addEventListener('mousedown', onMouseDown);
        }

        toggleMinimize() {
            this.isMinimized = !this.isMinimized;
            this.body.style.display = this.isMinimized ? 'none' : 'block';

        }

        setContent(content) {
            if (typeof content === 'string') {
                this.body.innerHTML = content;
            } else if (content instanceof Node) {
                this.body.innerHTML = '';
                this.body.appendChild(content);
            }
            return this;
        }

        close() {
            if (this.window && this.window.parentNode) {
                this.isShowing = false;
                this.window.style.transition = 'opacity 0.2s ease-out, transform 0.2s cubic-bezier(0.6, -0.28, 0.74, 0.05)';
                this.window.style.opacity = '0';
                this.window.style.transform = 'scale(0.95)';
                
                setTimeout(() => {
                    if (this.window && this.window.parentNode) {
                        this.window.parentNode.removeChild(this.window);
                    }
                    if (this.shadowHost && this.shadowHost.parentNode) {
                        this.shadowHost.parentNode.removeChild(this.shadowHost);
                        this.shadowHost = null;
                    }
                    if (this.options.onClose) {
                        try {
                            this.options.onClose();
                        } catch (e) {
                            console.error('[CKUI] onClose callback error:', e);
                        }
                    }
                    
                    this.onCloseCallbacks.forEach(callback => {
                        try {
                            callback();
                        } catch (e) {
                            console.error('[CKUI] onClose callback error:', e);
                        }
                    });
                    
                    this.onCloseOnceCallbacks.forEach(callback => {
                        try {
                            callback();
                        } catch (e) {
                            console.error('[CKUI] onClose callback error:', e);
                        }
                    });
                    this.onCloseOnceCallbacks = [];
                }, 200);
            }
            return this;
        }

        destroy() {
            this.close();
            if (this.id) {
                instanceManager.unregister('floatWindows', this.id);
            }
            this.onCloseCallbacks = [];
            this.onCloseOnceCallbacks = [];
        }
    }

    class FormBuilder {
        constructor(config = {}) {
            this.id = config.id || null;
            this.config = config;
            this.fields = [];
            this.values = new Reactive({});

            if (this.id) {
                instanceManager.register('forms', this.id, this);
            }
        }

        destroy() {
            if (this.id) {
                instanceManager.unregister('forms', this.id);
            }
        }

        addField(field) {
            this.fields.push(field);
            if (field.name && field.value !== undefined) {
                this.values.value[field.name] = field.value;
            }
            return this;
        }

        input(options) {
            return this.addField({
                type: 'input',
                inputType: 'text',
                ...options
            });
        }

        textarea(options) {
            return this.addField({
                type: 'textarea',
                ...options
            });
        }

        select(options) {
            return this.addField({
                type: 'select',
                ...options
            });
        }

        checkbox(options) {
            return this.addField({
                type: 'checkbox',
                ...options
            });
        }

        radio(options) {
            return this.addField({
                type: 'radio',
                ...options
            });
        }

        button(options) {
            return this.addField({
                type: 'button',
                ...options
            });
        }

        render() {
            const form = utils.createElement('form', {
                class: 'ckui-form'
            });

            this.fields.forEach(field => {
                const group = this.renderField(field);
                if (group) {
                    form.appendChild(group);
                }
            });

            return form;
        }

        renderField(field) {
            switch (field.type) {
                case 'input':
                    return this.renderInput(field);
                case 'textarea':
                    return this.renderTextarea(field);
                case 'select':
                    return this.renderSelect(field);
                case 'checkbox':
                    return this.renderCheckbox(field);
                case 'radio':
                    return this.renderRadio(field);
                case 'button':
                    return this.renderButton(field);
                default:
                    return null;
            }
        }

        renderInput(field) {
            const group = utils.createElement('div', { class: 'ckui-root ckui-form-group' });
            
            if (field.label) {
                group.appendChild(utils.createElement('label', {
                    class: 'ckui-root ckui-label'
                }, [field.label]));
            }

            const input = utils.createElement('input', {
                class: 'ckui-root ckui-input',
                type: field.inputType || 'text',
                placeholder: field.placeholder || '',
                value: field.value || '',
                name: field.name || ''
            });

            input.addEventListener('input', (e) => {
                const currentValues = { ...this.values.value };
                currentValues[field.name] = e.target.value;
                this.values.value = currentValues;
                
                if (field.onChange) {
                    field.onChange(e.target.value);
                }
            });

            group.appendChild(input);
            return group;
        }

        renderTextarea(field) {
            const group = utils.createElement('div', { class: 'ckui-root ckui-form-group' });
            
            if (field.label) {
                group.appendChild(utils.createElement('label', {
                    class: 'ckui-root ckui-label'
                }, [field.label]));
            }

            const textarea = utils.createElement('textarea', {
                class: 'ckui-root ckui-textarea',
                placeholder: field.placeholder || '',
                name: field.name || ''
            });
            textarea.value = field.value || '';

            textarea.addEventListener('input', (e) => {
                const currentValues = { ...this.values.value };
                currentValues[field.name] = e.target.value;
                this.values.value = currentValues;
                
                if (field.onChange) {
                    field.onChange(e.target.value);
                }
            });

            group.appendChild(textarea);
            return group;
        }

        renderSelect(field) {
            const group = utils.createElement('div', { class: 'ckui-root ckui-form-group' });
            
            if (field.label) {
                group.appendChild(utils.createElement('label', {
                    class: 'ckui-root ckui-label'
                }, [field.label]));
            }

            const select = utils.createElement('select', {
                class: 'ckui-root ckui-select',
                name: field.name || ''
            });

            (field.options || []).forEach(opt => {
                const option = utils.createElement('option', {
                    value: opt.value
                }, [opt.label || opt.value]);
                
                if (opt.value === field.value) {
                    option.selected = true;
                }
                
                select.appendChild(option);
            });

            select.addEventListener('change', (e) => {
                const currentValues = { ...this.values.value };
                currentValues[field.name] = e.target.value;
                this.values.value = currentValues;
                
                if (field.onChange) {
                    field.onChange(e.target.value);
                }
            });

            group.appendChild(select);
            return group;
        }

        renderCheckbox(field) {
            const group = utils.createElement('div', { class: 'ckui-root ckui-form-group' });
            
            const label = utils.createElement('label', {
                class: 'ckui-root ckui-checkbox'
            });

            const input = utils.createElement('input', {
                type: 'checkbox',
                name: field.name || ''
            });

            if (field.value) {
                input.checked = true;
            }

            input.addEventListener('change', (e) => {
                const currentValues = { ...this.values.value };
                currentValues[field.name] = e.target.checked;
                this.values.value = currentValues;
                
                if (field.onChange) {
                    field.onChange(e.target.checked);
                }
            });

            label.appendChild(input);
            if (field.label) {
                label.appendChild(document.createTextNode(field.label));
            }

            group.appendChild(label);
            return group;
        }

        renderRadio(field) {
            const group = utils.createElement('div', { class: 'ckui-root ckui-form-group' });
            
            if (field.label) {
                group.appendChild(utils.createElement('div', {
                    class: 'ckui-root ckui-label'
                }, [field.label]));
            }

            (field.options || []).forEach(opt => {
                const label = utils.createElement('label', {
                    class: 'ckui-root ckui-radio',
                    style: { display: 'block', marginBottom: '8px' }
                });

                const input = utils.createElement('input', {
                    type: 'radio',
                    name: field.name || '',
                    value: opt.value
                });

                if (opt.value === field.value) {
                    input.checked = true;
                }

                input.addEventListener('change', (e) => {
                    if (e.target.checked) {
                        const currentValues = { ...this.values.value };
                        currentValues[field.name] = opt.value;
                        this.values.value = currentValues;
                        
                        if (field.onChange) {
                            field.onChange(opt.value);
                        }
                    }
                });

                label.appendChild(input);
                label.appendChild(document.createTextNode(opt.label || opt.value));
                group.appendChild(label);
            });

            return group;
        }

        renderButton(field) {
            const button = utils.createElement('button', {
                class: `ckui-root ckui-btn ${field.primary ? 'ckui-btn-primary' : ''}`,
                type: 'button',
                onclick: () => {
                    if (field.onClick) {
                        field.onClick(this.getValues());
                    }
                }
            }, [field.label || 'Button']);

            return button;
        }

        getValues() {
            return { ...this.values.value };
        }

        setValues(values) {
            this.values.value = { ...this.values.value, ...values };
        }

        bindValue(name, reactive) {
            const unsubscribe = this.values.subscribe((newValues) => {
                if (newValues[name] !== undefined) {
                    reactive.value = newValues[name];
                }
            });

            const reverseUnsubscribe = reactive.subscribe((newValue) => {
                const currentValues = { ...this.values.value };
                if (currentValues[name] !== newValue) {
                    currentValues[name] = newValue;
                    this.values.value = currentValues;
                }
            });

            return () => {
                unsubscribe();
                reverseUnsubscribe();
            };
        }
    }

    const ckui = {
        __initialized: true,
        version: '2.0.0',

        getInstance(type, id) {
            return instanceManager.get(type, id);
        },

        getModal(id) {
            return instanceManager.get('modals', id);
        },

        getFloatWindow(id) {
            return instanceManager.get('floatWindows', id);
        },

        getForm(id) {
            return instanceManager.get('forms', id);
        },

        reactive(value) {
            return new Reactive(value);
        },

        utils,

        notification: new NotificationManager(),
        notify(options) {
            return this.notification.show(options);
        },
        success(message, title, options = {}) {
            if (typeof title === 'object') {
                options = title;
                title = options.title || '成功';
            }
            return this.notification.show({ type: 'success', title: title || '成功', message, ...options });
        },
        error(message, title, options = {}) {
            if (typeof title === 'object') {
                options = title;
                title = options.title || '错误';
            }
            return this.notification.show({ type: 'error', title: title || '错误', message, ...options });
        },
        warning(message, title, options = {}) {
            if (typeof title === 'object') {
                options = title;
                title = options.title || '警告';
            }
            return this.notification.show({ type: 'warning', title: title || '警告', message, ...options });
        },
        info(message, title, options = {}) {
            if (typeof title === 'object') {
                options = title;
                title = options.title || '提示';
            }
            return this.notification.show({ type: 'info', title: title || '提示', message, ...options });
        },

        Modal,
        modal(options) {

            if (options.id) {
                const existing = instanceManager.get('modals', options.id);
                if (existing) {
                    return existing.refresh(options);
                }
            }
            return new Modal(options);
        },
        async alert(message, title, id) {
            let options = {};
            if (typeof message === 'object') {
                options = message;
            } else {
                options = { content: message, title: title || '提示', id: id };
            }

            if (options.id) {
                const existing = instanceManager.get('modals', options.id);
                if (existing) {
                    existing.refresh(options);
                    return existing.show().then(() => undefined).catch(() => undefined);
                }
            }
            return Modal.alert(options);
        },
        async confirm(message, title, id) {
            let options = {};
            if (typeof message === 'object') {
                options = message;
            } else {
                options = { content: message, title: title || '确认', id: id };
            }

            if (options.id) {
                const existing = instanceManager.get('modals', options.id);
                if (existing) {
                    existing.refresh(options);
                    return existing.show().then(() => true).catch(() => false);
                }
            }
            return Modal.confirm(options).then(() => true).catch(() => false);
        },
        async prompt(message, defaultValue, title, id) {
            let options = {};
            if (typeof message === 'object') {
                options = message;
            } else {
                options = {
                    title: title || message,
                    placeholder: message,
                    defaultValue: defaultValue || '',
                    id: id
                };
            }

            if (options.id) {
                const existing = instanceManager.get('modals', options.id);
                if (existing) {
                    existing.refresh(options);
                    return existing.show().then(() => {

                        const input = existing.modal.querySelector('.ckui-input');
                        return input ? input.value : null;
                    }).catch(() => null);
                }
            }
            return Modal.prompt(options);
        },
        async select(options) {

            if (options.id) {
                const existing = instanceManager.get('modals', options.id);
                if (existing) {
                    existing.destroy();
                }
            }
            return Modal.select(options);
        },
        async sortableList(options) {

            if (options.id) {
                const existing = instanceManager.get('modals', options.id);
                if (existing) {
                    existing.destroy();
                }
            }
            return Modal.sortableList(options);
        },

        FloatWindow,
        floatWindow(options) {

            if (options.id) {
                const existing = instanceManager.get('floatWindows', options.id);
                if (existing) {
                    return existing.refresh(options);
                }
            }
            return new FloatWindow(options);
        },

        FormBuilder,
        form(options) {

            if (options && options.fields) {
                const builderId = options.formId || null;

                let builder = builderId ? instanceManager.get('forms', builderId) : null;
                if (!builder) {
                    builder = new FormBuilder({ id: builderId });
                }

                builder.fields = [];
                options.fields.forEach(field => {
                    switch (field.type) {
                        case 'input':
                            builder.input(field);
                            break;
                        case 'textarea':
                            builder.textarea(field);
                            break;
                        case 'select':
                            builder.select(field);
                            break;
                        case 'checkbox':
                            builder.checkbox(field);
                            break;
                        case 'radio':
                            builder.radio(field);
                            break;
                    }
                });
                
                const modalId = options.id || null;
                const modal = modalId ? instanceManager.get('modals', modalId) : null;
                
                if (modal) {
                    modal.refresh({
                        title: options.title || '表单',
                        content: builder.render(),
                        width: options.width || '500px',
                        onOk: () => true
                    });
                    return modal.show()
                        .then(() => builder.getValues())
                        .catch(() => null);
                } else {
                    const newModal = new Modal({
                        id: modalId,
                        title: options.title || '表单',
                        content: builder.render(),
                        width: options.width || '500px',
                        onOk: () => true
                    });
                    
                    return newModal.show()
                        .then(() => builder.getValues())
                        .catch(() => null);
                }
            }

            const builderId = options?.id || null;
            if (builderId) {
                const existing = instanceManager.get('forms', builderId);
                if (existing) {
                    return existing;
                }
            }
            return new FormBuilder(options || {});
        },

        createElement: utils.createElement,
        h: utils.createElement,

        row(options, ...children) {

            if (!options || options instanceof Node || typeof options === 'string') {
                children = [options, ...children].filter(Boolean);
                options = {};
            }
            const props = {
                class: 'ckui-root ckui-row',
                style: options.style || {}
            };
            return utils.createElement('div', props, children);
        },

        col(options, ...children) {
            if (!options || options instanceof Node || typeof options === 'string') {
                children = [options, ...children].filter(Boolean);
                options = {};
            }
            const props = {
                class: 'ckui-root ckui-col',
                style: options.style || {}
            };
            return utils.createElement('div', props, children);
        },

        space(options, ...children) {
            if (!options || options instanceof Node || typeof options === 'string') {
                children = [options, ...children].filter(Boolean);
                options = {};
            }
            const props = {
                class: 'ckui-root ckui-space',
                style: options.style || {}
            };
            return utils.createElement('div', props, children);
        },

        card(options = {}) {
            const props = {
                class: 'ckui-root ckui-card',
                style: options.style || {}
            };
            const card = utils.createElement('div', props);
            
            if (options.title) {
                card.appendChild(utils.createElement('div', {
                    class: 'ckui-card-title'
                }, [options.title]));
            }

            if (options.content) {
                if (typeof options.content === 'string') {
                    const content = document.createElement('div');
                    content.innerHTML = options.content;
                    card.appendChild(content);
                } else if (options.content instanceof Node) {
                    card.appendChild(options.content);
                }
            }

            return card;
        },

        divider() {
            return utils.createElement('div', { class: 'ckui-root ckui-divider' });
        },

        button(options = {}) {
            const className = ['ckui-root', 'ckui-btn'];
            if (options.primary) className.push('ckui-btn-primary');
            if (options.danger) className.push('ckui-btn-danger');
            if (options.success) className.push('ckui-btn-success');

            return utils.createElement('button', {
                class: className.join(' '),
                onclick: options.onClick,
                disabled: options.disabled
            }, [options.label || 'Button']);
        },

        input(options = {}) {
            const input = utils.createElement('input', {
                class: 'ckui-root ckui-input',
                type: options.type || 'text',
                placeholder: options.placeholder || '',
                value: options.value || '',
                disabled: options.disabled
            });

            if (options.onChange) {
                input.addEventListener('input', (e) => options.onChange(e.target.value));
            }

            if (options.reactive) {
                input.value = options.reactive.value;
                input.addEventListener('input', (e) => {
                    options.reactive.value = e.target.value;
                });
                options.reactive.subscribe((value) => {
                    if (input.value !== value) {
                        input.value = value;
                    }
                });

                setTimeout(() => {
                    if (options.reactive.value !== input.value) {
                        input.value = options.reactive.value;
                    }
                }, 0);
            }

            return input;
        },

        textarea(options = {}) {
            const textarea = utils.createElement('textarea', {
                class: 'ckui-root ckui-textarea',
                placeholder: options.placeholder || '',
                disabled: options.disabled
            });
            textarea.value = options.value || '';

            if (options.onChange) {
                textarea.addEventListener('input', (e) => options.onChange(e.target.value));
            }

            if (options.reactive) {
                textarea.value = options.reactive.value;
                textarea.addEventListener('input', (e) => {
                    options.reactive.value = e.target.value;
                });
                options.reactive.subscribe((value) => {
                    if (textarea.value !== value) {
                        textarea.value = value;
                    }
                });

                setTimeout(() => {
                    if (options.reactive.value !== textarea.value) {
                        textarea.value = options.reactive.value;
                    }
                }, 0);
            }

            return textarea;
        },

        label(text, options = {}) {
            return utils.createElement('label', {
                class: 'ckui-root ckui-label',
                ...options
            }, [text]);
        },

        loading() {
            return utils.createElement('div', { class: 'ckui-root ckui-loading' });
        },

        setTheme(theme) {
            globalConfig.currentTheme = theme;
            const containers = document.querySelectorAll('.ckui-root');
            containers.forEach(container => {
                if (theme === 'dark') {
                    container.classList.add('ckui-dark');
                } else {
                    container.classList.remove('ckui-dark');
                }
            });
        },

        html(htmlString) {
            const container = document.createElement('div');
            container.className = 'ckui-root';
            container.innerHTML = htmlString;
            return container;
        },

        setZIndexBase(base) {
            globalConfig.zIndexBase = base;
        },

        getZIndexBase() {
            return globalConfig.zIndexBase;
        },

        setCSSVars(vars, target = null) {
            const root = target || document.querySelector('.ckui-root') || document.documentElement;
            Object.entries(vars).forEach(([key, value]) => {
                const varName = key.startsWith('--') ? key : `--ckui-${key}`;
                root.style.setProperty(varName, value);
            });
        },

        trackMouseEvent() {
            if (!unsafeWindow.__ckui_mouseTrackingEnabled) {
                unsafeWindow.__ckui_mouseTrackingEnabled = true;
                unsafeWindow.__ckui_lastMouseX = null;
                unsafeWindow.__ckui_lastMouseY = null;
                
                document.addEventListener('mousemove', (e) => {
                    unsafeWindow.__ckui_lastMouseX = e.clientX;
                    unsafeWindow.__ckui_lastMouseY = e.clientY;
                }, { passive: true });
                
                console.log('[CKUI] 全局鼠标追踪已启用');
            }
            return ckui;
        }
    };

    utils.injectStyles(coreStyles, 'ckui-core-styles');

    unsafeWindow.ckui = ckui;
    
    console.log('[CKUI] Initialized successfully! Version:', ckui.version);
})(unsafeWindow, document);