MediaWiki

Equipment.js:修订间差异

来自卡厄思梦境WIKI

律Rhyme留言 | 贡献
无编辑摘要
律Rhyme留言 | 贡献
无编辑摘要
第211行: 第211行:
             $item.append($info).append($actions);
             $item.append($info).append($actions);
             return $item;
             return $item;
        }
        // 插入文本到输入框
        function insertTextIntoTextarea($textarea, beforeText, afterText) {
            var textarea = $textarea[0];
            var start = textarea.selectionStart;
            var end = textarea.selectionEnd;
            var text = textarea.value;
            var selectedText = text.substring(start, end);
           
            var insertText;
            if (selectedText) {
                insertText = beforeText + selectedText + afterText;
            } else {
                insertText = beforeText + afterText;
            }
           
            var newText = text.substring(0, start) + insertText + text.substring(end);
            $textarea.val(newText);
           
            // 设置光标位置
            var newCursorPos = start + beforeText.length + selectedText.length;
            textarea.setSelectionRange(newCursorPos, newCursorPos);
            textarea.focus();
        }
        // 创建格式化按钮工具栏
        function createFormatToolbar($targetTextarea) {
            var $toolbar = $('<div>').addClass('equipment-format-toolbar');
           
            // 橙色文本按钮
            var $orangeBtn = $('<div>')
                .addClass('equipment-button equipment-button-small equipment-format-btn')
                .css('color', '#ff8c00')
                .text('橙色文本')
                .on('click', function () {
                    insertTextIntoTextarea($targetTextarea, '{{文本|橙|', '}}');
                });
           
            // 词典按钮
            var $dictBtn = $('<div>')
                .addClass('equipment-button equipment-button-small equipment-format-btn')
                .text('词典')
                .on('click', function () {
                    insertTextIntoTextarea($targetTextarea, '{{词典|', '}}');
                });
           
            $toolbar.append($orangeBtn).append($dictBtn);
            return $toolbar;
         }
         }


第244行: 第293行:
             // 描述 (5个等级)
             // 描述 (5个等级)
             for (var i = 1; i <= 5; i++) {
             for (var i = 1; i <= 5; i++) {
                 $form.append(createFormField('描述等级 ' + i, 'desc' + i, 'text',  
                 var $field = createFormField('描述等级 ' + i, 'desc' + i, 'text',  
                     isEdit && item.desc ? item.desc[i - 1] : '', false, true));
                     isEdit && item.desc ? item.desc[i - 1] : '', false, true);
               
                // 在第一个描述输入框上方添加格式化工具栏
                if (i === 1) {
                    var $textarea = $field.find('textarea');
                    var $toolbar = createFormatToolbar($textarea);
                    $field.find('.equipment-form-label').after($toolbar);
                }
               
                $form.append($field);
             }
             }
              
              

2025年10月17日 (五) 20:39的版本

( function () {
    'use strict';
    
    mw.loader.using( ['mediawiki.api', 'mediawiki.util'], function () {
        if ( mw.config.get( 'wgPageName' ) !== 'MediaWiki:Equipment' ) {
            return;
        }

        mw.loader.load( mw.util.getUrl( 'MediaWiki:Equipment.css', { action: 'raw', ctype: 'text/css' } ), 'text/css' );

        var api = new mw.Api();
        var equipmentData = {};

        // 固定选项
        var AREA_OPTIONS = ['蓝壶', '双星之影', '雾之都市'];
        var RARITY_OPTIONS = ['蓝', '金', '彩'];
        var TYPE_OPTIONS = ['武器', '装甲', '戒指'];

        // 初始化
        function init() {
            loadEquipmentData();
        }

        // 加载装备数据
        function loadEquipmentData() {
            api.get({
                action: 'query',
                prop: 'revisions',
                titles: 'Module:装备/data',
                rvprop: 'content',
                rvslots: 'main',
                formatversion: 2
            }).done(function (data) {
                if (data.query && data.query.pages && data.query.pages[0]) {
                    var page = data.query.pages[0];
                    if (page.revisions && page.revisions[0]) {
                        var content = page.revisions[0].slots.main.content;
                        parseEquipmentData(content);
                        renderUI();
                        return;
                    }
                }
                mw.notify('加载装备数据失败: 未找到数据', { type: 'error' });
            }).fail(function (code, result) {
                console.error('API Error:', code, result);
                mw.notify('加载装备数据失败: ' + code, { type: 'error' });
            });
        }

        // 解析 Lua 数据
        function parseEquipmentData(luaCode) {
            equipmentData = {};
            
            try {
                // 匹配每个装备条目 - 改进的正则表达式
                var lines = luaCode.split('\n');
                var currentName = null;
                var currentItem = null;
                var inDesc = false;
                var descArray = [];
                
                for (var i = 0; i < lines.length; i++) {
                    var line = lines[i].trim();
                    
                    // 匹配装备名称
                    var nameMatch = line.match(/equipment\["([^"]+)"\]\s*=\s*\{/);
                    if (nameMatch) {
                        if (currentName && currentItem) {
                            if (descArray.length > 0) {
                                currentItem.desc = descArray;
                            }
                            equipmentData[currentName] = currentItem;
                        }
                        currentName = nameMatch[1];
                        currentItem = { name: currentName, desc: [] };
                        inDesc = false;
                        descArray = [];
                        continue;
                    }
                    
                    if (!currentItem) continue;
                    
                    // 匹配 desc 开始
                    if (line.match(/desc\s*=\s*\{/)) {
                        inDesc = true;
                        descArray = [];
                        continue;
                    }
                    
                    // desc 结束
                    if (inDesc && line.match(/^\}/)) {
                        inDesc = false;
                        currentItem.desc = descArray;
                        continue;
                    }
                    
                    // 在 desc 内
                    if (inDesc) {
                        var descMatch = line.match(/"([^"]*)"/);
                        if (descMatch) {
                            descArray.push(descMatch[1]);
                        }
                        continue;
                    }
                    
                    // 匹配其他属性
                    var idMatch = line.match(/id\s*=\s*(\d+)/);
                    if (idMatch) {
                        currentItem.id = idMatch[1];
                        continue;
                    }
                    
                    var areaMatch = line.match(/area\s*=\s*"([^"]+)"/);
                    if (areaMatch) {
                        currentItem.area = areaMatch[1];
                        continue;
                    }
                    
                    var rarityMatch = line.match(/rarity\s*=\s*"([^"]+)"/);
                    if (rarityMatch) {
                        currentItem.rarity = rarityMatch[1];
                        continue;
                    }
                    
                    var typeMatch = line.match(/type\s*=\s*"([^"]+)"/);
                    if (typeMatch) {
                        currentItem.type = typeMatch[1];
                        continue;
                    }
                    
                    var tagMatch = line.match(/tag\s*=\s*"([^"]+)"/);
                    if (tagMatch) {
                        currentItem.tag = tagMatch[1];
                        continue;
                    }
                }
                
                // 保存最后一个装备
                if (currentName && currentItem) {
                    if (descArray.length > 0) {
                        currentItem.desc = descArray;
                    }
                    equipmentData[currentName] = currentItem;
                }
                
                console.log('解析到的装备数据:', equipmentData);
                
            } catch (e) {
                console.error('解析装备数据出错:', e);
                mw.notify('解析装备数据失败', { type: 'error' });
            }
        }

        // 渲染界面
        function renderUI() {
            var $container = $('<div>').addClass('equipment-manager');
            
            // 标题
            $container.append($('<div>').addClass('equipment-title').text('装备数据管理'));
            
            // 统计信息
            var count = Object.keys(equipmentData).length;
            $container.append($('<div>').addClass('equipment-stats').text('共 ' + count + ' 个装备'));
            
            // 添加新装备按钮
            var $addBtn = $('<div>').addClass('equipment-button equipment-button-primary')
                .text('添加新装备')
                .on('click', function () {
                    showEditForm(null);
                });
            $container.append($addBtn);
            
            // 装备列表
            var $list = $('<div>').addClass('equipment-list');
            
            var items = Object.keys(equipmentData).sort();
            for (var i = 0; i < items.length; i++) {
                $list.append(createEquipmentItem(equipmentData[items[i]]));
            }
            
            $container.append($list);
            
            // 插入到页面
            $('#mw-content-text').empty().append($container);
        }

        // 创建装备项
        function createEquipmentItem(item) {
            var $item = $('<div>').addClass('equipment-item');
            
            var $info = $('<div>').addClass('equipment-info');
            $info.append($('<div>').addClass('equipment-name').text(item.name));
            $info.append($('<div>').addClass('equipment-meta')
                .text('ID: ' + item.id + ' | ' + item.area + ' | ' + item.rarity + ' | ' + item.type));
            $info.append($('<div>').addClass('equipment-tags').text('标签: ' + item.tag));
            
            var $actions = $('<div>').addClass('equipment-actions');
            $actions.append(
                $('<div>').addClass('equipment-button equipment-button-small').text('编辑')
                    .on('click', function () {
                        showEditForm(item);
                    })
            );
            $actions.append(
                $('<div>').addClass('equipment-button equipment-button-small equipment-button-danger').text('删除')
                    .on('click', function () {
                        deleteEquipment(item.name);
                    })
            );
            
            $item.append($info).append($actions);
            return $item;
        }

        // 插入文本到输入框
        function insertTextIntoTextarea($textarea, beforeText, afterText) {
            var textarea = $textarea[0];
            var start = textarea.selectionStart;
            var end = textarea.selectionEnd;
            var text = textarea.value;
            var selectedText = text.substring(start, end);
            
            var insertText;
            if (selectedText) {
                insertText = beforeText + selectedText + afterText;
            } else {
                insertText = beforeText + afterText;
            }
            
            var newText = text.substring(0, start) + insertText + text.substring(end);
            $textarea.val(newText);
            
            // 设置光标位置
            var newCursorPos = start + beforeText.length + selectedText.length;
            textarea.setSelectionRange(newCursorPos, newCursorPos);
            textarea.focus();
        }

        // 创建格式化按钮工具栏
        function createFormatToolbar($targetTextarea) {
            var $toolbar = $('<div>').addClass('equipment-format-toolbar');
            
            // 橙色文本按钮
            var $orangeBtn = $('<div>')
                .addClass('equipment-button equipment-button-small equipment-format-btn')
                .css('color', '#ff8c00')
                .text('橙色文本')
                .on('click', function () {
                    insertTextIntoTextarea($targetTextarea, '{{文本|橙|', '}}');
                });
            
            // 词典按钮
            var $dictBtn = $('<div>')
                .addClass('equipment-button equipment-button-small equipment-format-btn')
                .text('词典')
                .on('click', function () {
                    insertTextIntoTextarea($targetTextarea, '{{词典|', '}}');
                });
            
            $toolbar.append($orangeBtn).append($dictBtn);
            return $toolbar;
        }

        // 显示编辑表单
        function showEditForm(item) {
            var isEdit = item !== null;
            var $overlay = $('<div>').addClass('equipment-overlay');
            var $modal = $('<div>').addClass('equipment-modal');
            
            $modal.append($('<div>').addClass('equipment-modal-title')
                .text(isEdit ? '编辑装备' : '添加新装备'));
            
            var $form = $('<div>').addClass('equipment-form');
            
            // 名称
            $form.append(createFormField('名称', 'name', 'text', isEdit ? item.name : '', isEdit));
            
            // ID
            $form.append(createFormField('ID', 'id', 'number', isEdit ? item.id : ''));
            
            // 地区
            $form.append(createFormSelect('地区', 'area', AREA_OPTIONS, isEdit ? item.area : ''));
            
            // 稀有度
            $form.append(createFormSelect('稀有度', 'rarity', RARITY_OPTIONS, isEdit ? item.rarity : ''));
            
            // 类型
            $form.append(createFormSelect('类型', 'type', TYPE_OPTIONS, isEdit ? item.type : ''));
            
            // 标签
            $form.append(createFormField('标签 (用逗号分隔)', 'tag', 'text', isEdit ? item.tag : ''));
            
            // 描述 (5个等级)
            for (var i = 1; i <= 5; i++) {
                var $field = createFormField('描述等级 ' + i, 'desc' + i, 'text', 
                    isEdit && item.desc ? item.desc[i - 1] : '', false, true);
                
                // 在第一个描述输入框上方添加格式化工具栏
                if (i === 1) {
                    var $textarea = $field.find('textarea');
                    var $toolbar = createFormatToolbar($textarea);
                    $field.find('.equipment-form-label').after($toolbar);
                }
                
                $form.append($field);
            }
            
            var $actions = $('<div>').addClass('equipment-modal-actions');
            $actions.append(
                $('<div>').addClass('equipment-button equipment-button-primary').text('保存')
                    .on('click', function () {
                        saveEquipment($form, isEdit, item ? item.name : null);
                        $overlay.remove();
                    })
            );
            $actions.append(
                $('<div>').addClass('equipment-button').text('取消')
                    .on('click', function () {
                        $overlay.remove();
                    })
            );
            
            $modal.append($form).append($actions);
            $overlay.append($modal);
            $('body').append($overlay);
        }

        // 创建表单字段
        function createFormField(label, name, type, value, readonly, isTextarea) {
            var $field = $('<div>').addClass('equipment-form-field');
            $field.append($('<div>').addClass('equipment-form-label').text(label));
            
            var $input;
            if (isTextarea) {
                $input = $('<textarea>').addClass('equipment-form-input equipment-form-textarea')
                    .attr('name', name)
                    .attr('rows', '3')
                    .val(value || '');
            } else {
                $input = $('<input>').addClass('equipment-form-input')
                    .attr('type', type)
                    .attr('name', name)
                    .val(value || '');
            }
            
            if (readonly) {
                $input.attr('readonly', 'readonly');
            }
            $field.append($input);
            return $field;
        }

        // 创建下拉选择框
        function createFormSelect(label, name, options, value) {
            var $field = $('<div>').addClass('equipment-form-field');
            $field.append($('<div>').addClass('equipment-form-label').text(label));
            var $select = $('<select>').addClass('equipment-form-input').attr('name', name);
            
            $select.append($('<option>').val('').text('请选择...'));
            options.forEach(function (opt) {
                $select.append($('<option>').val(opt).text(opt));
            });
            $select.val(value || '');
            
            $field.append($select);
            return $field;
        }

        // 保存装备
        function saveEquipment($form, isEdit, oldName) {
            var formData = {};
            $form.find('input, select, textarea').each(function () {
                var $el = $(this);
                formData[$el.attr('name')] = $el.val().trim();
            });
            
            // 验证必填项
            if (!formData.name || !formData.id || !formData.area || !formData.rarity || !formData.type) {
                mw.notify('请填写所有必填项', { type: 'error' });
                return;
            }
            
            var desc = [];
            for (var i = 1; i <= 5; i++) {
                desc.push(formData['desc' + i] || '');
            }
            
            var newItem = {
                name: formData.name,
                id: formData.id,
                area: formData.area,
                rarity: formData.rarity,
                type: formData.type,
                tag: formData.tag,
                desc: desc
            };
            
            // 如果是编辑且名称改变了,删除旧的
            if (isEdit && oldName && oldName !== formData.name) {
                delete equipmentData[oldName];
            }
            
            equipmentData[formData.name] = newItem;
            saveToModule();
        }

        // 删除装备
        function deleteEquipment(name) {
            if (!confirm('确定要删除装备 "' + name + '" 吗?')) {
                return;
            }
            
            delete equipmentData[name];
            saveToModule();
        }

        // 保存到模块
        function saveToModule() {
            var luaCode = 'local equipment = {}\n\n';
            
            var names = Object.keys(equipmentData).sort();
            
            for (var i = 0; i < names.length; i++) {
                var name = names[i];
                var item = equipmentData[name];
                
                luaCode += 'equipment["' + name + '"] = {\n';
                luaCode += '    id = ' + item.id + ',\n';
                luaCode += '\tarea = "' + item.area + '",\n';
                luaCode += '    rarity = "' + item.rarity + '",\n';
                luaCode += '    type = "' + item.type + '",\n';
                luaCode += '    tag = "' + item.tag + '",\n';
                luaCode += '    desc = {\n';
                
                for (var j = 0; j < 5; j++) {
                    var desc = item.desc[j] || '';
                    luaCode += '        "' + desc + '"';
                    if (j < 4) luaCode += ',';
                    luaCode += '\n';
                }
                
                luaCode += '    }\n';
                luaCode += '}\n\n';
            }
            
            luaCode += 'return equipment\n';
            
            api.postWithToken('csrf', {
                action: 'edit',
                title: 'Module:装备/data',
                text: luaCode,
                summary: '通过装备管理界面更新数据',
                contentmodel: 'Scribunto'
            }).done(function () {
                mw.notify('保存成功!', { type: 'success' });
                loadEquipmentData();
            }).fail(function (code, result) {
                console.error('保存失败:', code, result);
                mw.notify('保存失败: ' + code, { type: 'error' });
            });
        }

        init();
    });
})();