Перейти к содержимому
Zone of Games Forum

Рекомендованные сообщения

5 часов назад, Chillstream сказал:

Надеюсь в ближайшее время сделаю, там прикол в движке, что надо строку делать где-то не больше 63 символа, либо текст не влезет в колонку в игре eysvDGD.png 

Накидал скрипт на html для валидации длины строк.
X9HyqOl.png

Пример работы:

qmVRpsx.png

 

Можно щёлкнуть по строке для редактирования, попытаться сократить и сохранить.

Wd3Qxlm.png

Там будет видно, улучшилась ситуация или нет. Если всё нормально — можно нажать кнопку копировать и скопировать себе в таблицу или туда, где вы там проводите редактуру. Будут скопированы все строки из блока (ячейки).

Также можно нажать кнопку “Сохранить всё”, чтобы сохранить все отредактированные строки на рабочий стол в txt файл.

Le6DHPC.png

Затем содержимое файла можно скопировать и вставить на таблицу.

 

Скрытый текст

<!DOCTYPE html>
<html lang="ru">
<head>
    <meta charset="UTF-8">
    <title>Валидатор длины текста</title>
    <style>
        body {
            font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
            margin: 0;
            padding: 20px;
            background-color: #f5f5f5;
            color: #333;
        }
        h1 {
            color: #2c3e50;
            text-align: center;
            margin-bottom: 30px;
        }
        .container {
            display: flex;
            gap: 30px;
            margin: 0 auto;
            max-width: 1200px;
            background: white;
            padding: 25px;
            border-radius: 10px;
            box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
        }
        textarea {
            width: 100%;
            height: 400px;
            font-family: 'Consolas', monospace;
            padding: 15px;
            border: 1px solid #ddd;
            border-radius: 5px;
            resize: vertical;
            font-size: 14px;
            line-height: 1.5;
        }
        .controls {
            display: flex;
            flex-direction: column;
            gap: 15px;
            min-width: 250px;
        }
        .control-group {
            display: flex;
            flex-direction: column;
            gap: 5px;
        }
        label {
            font-weight: 600;
            color: #2c3e50;
        }
        input[type="number"] {
            width: 100%;
            padding: 10px;
            border: 1px solid #ddd;
            border-radius: 5px;
            font-size: 16px;
        }
        button {
            padding: 12px 20px;
            background-color: #3498db;
            color: white;
            border: none;
            border-radius: 5px;
            cursor: pointer;
            font-size: 16px;
            font-weight: 600;
            transition: background-color 0.3s;
        }
        button:hover {
            background-color: #2980b9;
        }
        #output {
            margin-top: 30px;
            max-width: 1200px;
            margin-left: auto;
            margin-right: auto;
        }
        table {
            width: 100%;
            border-collapse: collapse;
            background: white;
            box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
            border-radius: 5px;
            overflow: hidden;
        }
        td, th {
            border: 1px solid #e0e0e0;
            padding: 12px 15px;
            vertical-align: top;
        }
        th {
            background-color: #3498db;
            color: white;
            text-align: left;
        }
        .exceeded {
            background-color: #ffebee;
        }
        .highlight {
            box-shadow: inset 0 0 0 2px #e74c3c;
        }
        .line-number {
            color: #7f8c8d;
            font-size: 0.85em;
            display: block;
            margin-bottom: 5px;
        }
        .block-separator {
            background-color: #3498db;
            height: 3px;
        }
        .block-separator td {
            padding: 0;
        }
        pre {
            margin: 0;
            white-space: pre-wrap;
            font-family: 'Consolas', monospace;
            font-size: 14px;
        }
        .nav-bar {
            position: fixed;
            bottom: 20px;
            left: 50%;
            transform: translateX(-50%);
            background: white;
            padding: 10px 20px;
            border-radius: 50px;
            box-shadow: 0 2px 15px rgba(0, 0, 0, 0.2);
            display: flex;
            gap: 15px;
            z-index: 1000;
            opacity: 0;
            transition: opacity 0.3s;
        }
        .nav-bar.visible {
            opacity: 1;
        }
        .nav-button {
            padding: 8px 15px;
            background-color: #3498db;
            color: white;
            border: none;
            border-radius: 20px;
            cursor: pointer;
            font-weight: 600;
            transition: all 0.3s;
        }
        .nav-button:hover {
            background-color: #2980b9;
            transform: translateY(-2px);
        }
        .nav-button:disabled {
            background-color: #bdc3c7;
            cursor: not-allowed;
            transform: none;
        }
        .counter {
            padding: 8px 15px;
            font-weight: 600;
            color: #2c3e50;
        }
        .valid-part {
            background-color: #e8f5e9;
        }
        .excess-part {
            background-color: #ffcdd2;
            text-decoration: underline wavy red;
        }
        .stats-panel {
            background: white;
            padding: 15px;
            border-radius: 8px;
            box-shadow: 0 2px 5px rgba(0,0,0,0.1);
            margin-bottom: 20px;
            display: flex;
            flex-wrap: wrap;
            gap: 20px;
        }
        .stat-item {
            min-width: 120px;
        }
        .stat-value {
            font-size: 24px;
            font-weight: bold;
            color: #2c3e50;
        }
        .stat-label {
            font-size: 14px;
            color: #7f8c8d;
        }
        .toggle-normal {
            margin: 10px 0;
            padding: 8px 12px;
            background: #ecf0f1;
            border: none;
            border-radius: 4px;
            cursor: pointer;
        }
        .collapsed .normal-row {
            display: none;
        }
        .summary-row {
            background-color: #f8f9fa;
            font-weight: bold;
        }
        .editable {
            cursor: pointer;
        }
        .editable:hover {
            background-color: #f0f7ff !important;
        }
        .edit-textarea {
            width: 100%;
            min-height: 100px;
            font-family: 'Consolas', monospace;
            padding: 10px;
            border: 2px solid #3498db;
            border-radius: 5px;
            resize: vertical;
            font-size: 14px;
            line-height: 1.5;
        }
        .edit-buttons {
            display: flex;
            gap: 10px;
            margin-top: 10px;
        }
        .edit-button {
            padding: 5px 10px;
            font-size: 14px;
            border-radius: 4px;
        }
        .save-button {
            background-color: #2ecc71;
            color: white;
        }
        .cancel-button {
            background-color: #e74c3c;
            color: white;
        }
        .copy-block-btn {
            background-color: #95a5a6;
            color: white;
            border: none;
            border-radius: 4px;
            padding: 4px 8px;
            font-size: 12px;
            cursor: pointer;
            margin-left: 10px;
            transition: background-color 0.3s;
        }
        .copy-block-btn:hover {
            background-color: #7f8c8d;
        }
        .copy-block-btn::before {
            content: "⏏";
            margin-right: 4px;
        }
        .block-actions {
            display: flex;
            justify-content: space-between;
            align-items: center;
        }
        .save-all-btn {
            background-color: #27ae60;
        }
        .save-all-btn:hover {
            background-color: #219653;
        }
    </style>
</head>
<body>
    <h1>Валидатор длины текста</h1>
    
    <div class="container">
        <textarea id="inputText" placeholder="Вставьте текст для проверки здесь..."></textarea>
        <div class="controls">
            <div class="control-group">
                <label for="maxLength">Максимальная длина строки:</label>
                <input type="number" id="maxLength" value="63" min="1">
            </div>
            <button id="processBtn" onclick="processText()">Проверить текст</button>
            <button id="saveAllBtn" class="save-all-btn" onclick="saveAllText()" style="display: none;">Сохранить всё (TXT)</button>
            <div class="control-group">
                <small>Примечание: программа учитывает текст без форматирования</small>
            </div>
        </div>
    </div>
    
    <div id="output"></div>
    <div id="statsPanel" class="stats-panel" style="display: none;"></div>
    
    <div class="nav-bar" id="navBar">
        <button class="nav-button" id="prevButton" onclick="navigateExceeded(-1)">← Назад</button>
        <span class="counter" id="counter">0/0</span>
        <button class="nav-button" id="nextButton" onclick="navigateExceeded(1)">Вперёд →</button>
    </div>

    <script>
        let exceededElements = [];
        let currentExceededIndex = -1;
        let allResults = [];
        let isCollapsed = false;
        
        function processText() {
            const inputText = document.getElementById('inputText').value;
            const maxLength = parseInt(document.getElementById('maxLength').value);
            const blocks = splitBlocks(inputText);
            allResults = analyzeBlocks(blocks, maxLength);
            displayStats(allResults, maxLength);
            displayResults(allResults);
            initNavigation();
            document.getElementById('saveAllBtn').style.display = 'block';
        }
        
        function splitBlocks(text) {
            const lines = text.split(/\r?\n/);
            let blocks = [];
            let currentBlock = [];
            let inQuotes = false;
            
            for (let line of lines) {
                // Убрали trim(), чтобы сохранять пустые строки внутри блоков
                const startsWithQuote = line.startsWith('"') && !inQuotes;
                const endsWithQuote = line.endsWith('"') && !line.endsWith('\\"');
                
                if (startsWithQuote) inQuotes = true;
                if (endsWithQuote) inQuotes = false;
                
                if (inQuotes || currentBlock.length > 0) {
                    currentBlock.push(line.replace(/\\"/g, '"'));
                    if (!inQuotes) {
                        const fullBlock = currentBlock.join('\n').replace(/^"(.*)"$/, '$1');
                        blocks.push(fullBlock);
                        currentBlock = [];
                    }
                } else {
                    // Добавляем строку в блок только если она не пустая ИЛИ если мы внутри блока
                    if (line.trim() !== '' || currentBlock.length > 0) {
                        blocks.push(line);
                    }
                }
            }
            
            return blocks;
        }
        
        function cleanText(text) {
            return text
                .replace(/\\[A-Za-z]\[\d+\]/g, '')
                .replace(/\\[A-Za-z]/g, '')
                .replace(/\\[}.]/g, '');
        }
        
        function analyzeBlocks(blocks, maxLength) {
            return blocks.map(block => {
                const lines = block.includes('\n') ? block.split('\n') : [block];
                return lines.map(line => {
                    const cleaned = cleanText(line);
                    const length = cleaned.length;
                    return {
                        original: line,
                        cleaned: cleaned,
                        length: length,
                        exceeded: length > maxLength,
                        diff: Math.max(0, length - maxLength)
                    };
                });
            });
        }
        
        function displayStats(results, maxLength) {
            const statsPanel = document.getElementById('statsPanel');
            statsPanel.style.display = 'block';
            
            let totalLines = 0;
            let exceededLines = 0;
            let maxExceed = 0;
            let totalExceed = 0;
            
            results.forEach(block => {
                block.forEach(line => {
                    totalLines++;
                    if (line.exceeded) {
                        exceededLines++;
                        totalExceed += line.diff;
                        if (line.diff > maxExceed) {
                            maxExceed = line.diff;
                        }
                    }
                });
            });
            
            const percentExceeded = totalLines > 0 ? (exceededLines / totalLines * 100).toFixed(1) : 0;
            const avgExceed = exceededLines > 0 ? (totalExceed / exceededLines).toFixed(1) : 0;
            
            statsPanel.innerHTML = `
                <div class="stat-item">
                    <div class="stat-value">${totalLines}</div>
                    <div class="stat-label">Всего строк</div>
                </div>
                <div class="stat-item">
                    <div class="stat-value">${exceededLines} <small>(${percentExceeded}%)</small></div>
                    <div class="stat-label">Превышений</div>
                </div>
                <div class="stat-item">
                    <div class="stat-value">${maxExceed}</div>
                    <div class="stat-label">Макс. превышение</div>
                </div>
                <div class="stat-item">
                    <div class="stat-value">${avgExceed}</div>
                    <div class="stat-label">Среднее превышение</div>
                </div>
                <div class="stat-item">
                    <div class="stat-value">${maxLength}</div>
                    <div class="stat-label">Лимит длины</div>
                </div>
                <button class="toggle-normal" onclick="toggleNormalRows()">
                    ${isCollapsed ? 'Показать все строки' : 'Скрыть нормальные строки'}
                </button>
            `;
        }
        
        function displayResults(results) {
            const output = document.getElementById('output');
            let html = `
                <table id="resultsTable" class="${isCollapsed ? 'collapsed' : ''}">
                    <thead>
                        <tr>
                            <th>Текст</th>
                            <th style="width: 80px;">Длина</th>
                            <th style="width: 80px;">Превышение</th>
                        </tr>
                    </thead>
                    <tbody>
            `;
            
            let blockCount = 0;
            results.forEach((block, blockIndex) => {
                let blockExceeded = false;
                let blockLines = 0;
                let blockExceededLines = 0;
                
                block.forEach(line => {
                    blockLines++;
                    if (line.exceeded) blockExceededLines++;
                });
                
                if (blockExceededLines > 0) blockCount++;
                
                // Собираем полный текст блока для копирования
                const fullBlockText = block.map(line => line.original).join('\n');
                
                html += `
                    <tr class="block-separator">
                        <td colspan="3"></td>
                    </tr>
                    <tr class="summary-row ${blockExceededLines === 0 ? 'normal-row' : ''}">
                        <td colspan="3">
                            <div class="block-actions">
                                <span>Блок ${blockIndex + 1}: ${blockLines} строк, ${blockExceededLines} превышений</span>
                                <button class="copy-block-btn" onclick="copyBlockText(${blockIndex})" title="Копировать весь блок">Копировать</button>
                            </div>
                        </td>
                    </tr>
                `;
                
                block.forEach((line, lineIndex) => {
                    const maxLen = parseInt(document.getElementById('maxLength').value);
                    const safeText = escapeHtml(line.original);
                    const safeCleaned = escapeHtml(line.cleaned);
                    
                    let highlighted = safeCleaned;
                    if (line.exceeded) {
                        highlighted = `<span class="valid-part">${safeCleaned.substring(0, maxLen)}</span>` +
                                       `<span class="excess-part">${safeCleaned.substring(maxLen)}</span>`;
                    }
                    
                    html += `
                        <tr class="${line.exceeded ? 'exceeded' : 'normal-row'} editable" 
                            id="row-${blockIndex}-${lineIndex}"
                            data-block="${blockIndex}"
                            data-line="${lineIndex}"
                            onclick="startEditLine(this, ${blockIndex}, ${lineIndex})">
                            <td>
                                <span class="line-number">Блок ${blockIndex + 1}, строка ${lineIndex + 1}</span>
                                <pre>${highlighted}</pre>
                            </td>
                            <td>${line.length}</td>
                            <td>${line.exceeded ? `+${line.diff}` : ''}</td>
                        </tr>
                    `;
                });
            });
            
            html += `
                    </tbody>
                </table>
            `;
            
            output.innerHTML = html;
        }
        
        function copyBlockText(blockIndex) {
            const blockText = allResults[blockIndex].map(line => line.original).join('\n');
            navigator.clipboard.writeText(blockText).then(() => {
                // Визуальная обратная связь
                const buttons = document.querySelectorAll('.copy-block-btn');
                const originalText = buttons[blockIndex].textContent;
                buttons[blockIndex].textContent = 'Скопировано!';
                buttons[blockIndex].style.backgroundColor = '#2ecc71';
                
                setTimeout(() => {
                    buttons[blockIndex].textContent = originalText;
                    buttons[blockIndex].style.backgroundColor = '#95a5a6';
                }, 2000);
            }).catch(err => {
                console.error('Ошибка копирования: ', err);
                alert('Не удалось скопировать текст');
            });
        }
        
        function startEditLine(rowElement, blockIndex, lineIndex) {
            // Если уже в режиме редактирования - игнорируем клик
            if (rowElement.querySelector('.edit-textarea')) return;
        
            const lineData = allResults[blockIndex][lineIndex];
            const originalContent = rowElement.innerHTML; // Получаем исходный HTML
        
            // Сохраняем исходный HTML в data-атрибут
            rowElement.setAttribute('data-original-content', originalContent);
        
            rowElement.classList.remove('editable');
            rowElement.innerHTML = `
                <td colspan="3">
                    <span class="line-number">Блок ${blockIndex + 1}, строка ${lineIndex + 1}</span>
                    <textarea class="edit-textarea" id="edit-${blockIndex}-${lineIndex}">${escapeHtml(lineData.original)}</textarea>
                    <div class="edit-buttons">
                        <button class="edit-button save-button" onclick="saveEditedLine(this, ${blockIndex}, ${lineIndex})">Сохранить</button>
                        <button class="edit-button cancel-button" onclick="cancelEditLine(this, ${blockIndex}, ${lineIndex})">Отмена</button> 
                    </div>
                </td>
            `;
        
            // Фокусируем textarea и устанавливаем курсор в конец
            const textarea = rowElement.querySelector('.edit-textarea');
            textarea.focus();
            textarea.selectionStart = textarea.selectionEnd = textarea.value.length;
        
            // Остановка всплытия события, чтобы не срабатывали другие обработчики
            event.stopPropagation();
        }
        
        function saveEditedLine(button, blockIndex, lineIndex) {
            const rowElement = button.closest('tr');
            const textarea = rowElement.querySelector('.edit-textarea');
            const newText = textarea.value;
            
            // Обновляем данные в allResults
            allResults[blockIndex][lineIndex].original = newText;
            allResults[blockIndex][lineIndex].cleaned = cleanText(newText);
            
            // Пересчитываем длину и превышение
            const maxLength = parseInt(document.getElementById('maxLength').value);
            const cleaned = allResults[blockIndex][lineIndex].cleaned;
            const length = cleaned.length;
            
            allResults[blockIndex][lineIndex].length = length;
            allResults[blockIndex][lineIndex].exceeded = length > maxLength;
            allResults[blockIndex][lineIndex].diff = Math.max(0, length - maxLength);
            
            // Перерисовываем только эту строку
            updateSingleRow(rowElement, blockIndex, lineIndex);
            
            // Обновляем статистику
            updateStats();
            
            // Остановка всплытия события
            event.stopPropagation();
        }
        
        function cancelEditLine(button, blockIndex, lineIndex) {
            const rowElement = button.closest('tr');

            // Получаем исходный HTML из data-атрибута
            const originalContent = rowElement.getAttribute('data-original-content');

            if (originalContent !== null) { 
                 rowElement.innerHTML = originalContent;
                 rowElement.classList.add('editable');
                 // Удаляем data-атрибут после использования
                 rowElement.removeAttribute('data-original-content');
            } else {
                 console.error("Не удалось восстановить оригинальное содержимое строки.");
                 // В качестве запасного варианта, можно попробовать перерисовать строку из данных
                 // updateSingleRow(rowElement, blockIndex, lineIndex); 
            }

            // Остановка всплытия события
            event.stopPropagation();
        }
        
        function updateSingleRow(rowElement, blockIndex, lineIndex) {
            const lineData = allResults[blockIndex][lineIndex];
            const maxLen = parseInt(document.getElementById('maxLength').value);
            const safeText = escapeHtml(lineData.original);
            const safeCleaned = escapeHtml(lineData.cleaned);
            
            let highlighted = safeCleaned;
            if (lineData.exceeded) {
                highlighted = `<span class="valid-part">${safeCleaned.substring(0, maxLen)}</span>` +
                               `<span class="excess-part">${safeCleaned.substring(maxLen)}</span>`;
            }
            
            rowElement.className = lineData.exceeded ? 'exceeded editable' : 'editable';
            rowElement.setAttribute('onclick', `startEditLine(this, ${blockIndex}, ${lineIndex})`);
            rowElement.innerHTML = `
                <td>
                    <span class="line-number">Блок ${blockIndex + 1}, строка ${lineIndex + 1}</span>
                    <pre>${highlighted}</pre>
                </td>
                <td>${lineData.length}</td>
                <td>${lineData.exceeded ? `+${lineData.diff}` : ''}</td>
            `;
            
            // Обновляем навигацию по превышениям без автоматического перехода
            initNavigation(false);
        }
        
        function updateStats() {
            const maxLength = parseInt(document.getElementById('maxLength').value);
            displayStats(allResults, maxLength);
        }
        
        function toggleNormalRows() {
            isCollapsed = !isCollapsed;
            const table = document.getElementById('resultsTable');
            if (table) {
                table.classList.toggle('collapsed', isCollapsed);
            }
            document.querySelector('.toggle-normal').textContent = 
                isCollapsed ? 'Показать все строки' : 'Скрыть нормальные строки';
        }
        
        function initNavigation(shouldNavigate = true) {
            exceededElements = Array.from(document.querySelectorAll('.exceeded'));
            updateCounter();
            
            if (exceededElements.length > 0) {
                document.getElementById('navBar').classList.add('visible');
                if (shouldNavigate && currentExceededIndex === -1) {
                    navigateExceeded(1); // Перейти к первому превышению
                }
            } else {
                document.getElementById('navBar').classList.remove('visible');
                currentExceededIndex = -1;
            }
        }
        
        function navigateExceeded(direction) {
            if (exceededElements.length === 0) return;
            
            // Снять выделение с текущего элемента
            if (currentExceededIndex >= 0 && currentExceededIndex < exceededElements.length) {
                exceededElements[currentExceededIndex].classList.remove('highlight');
            }
            
            // Вычислить новый индекс
            let newIndex = currentExceededIndex + direction;
            
            if (newIndex < 0) {
                newIndex = exceededElements.length - 1;
            } else if (newIndex >= exceededElements.length) {
                newIndex = 0;
            }
            
            currentExceededIndex = newIndex;
            
            // Применить выделение к новому элементу
            exceededElements[currentExceededIndex].classList.add('highlight');
            
            // Прокрутить к элементу
            exceededElements[currentExceededIndex].scrollIntoView({
                behavior: 'smooth',
                block: 'center'
            });
            
            updateCounter();
        }
        
        function updateCounter() {
            const counter = document.getElementById('counter');
            if (exceededElements.length > 0) {
                counter.textContent = `${currentExceededIndex + 1}/${exceededElements.length}`;
            } else {
                counter.textContent = '0/0';
            }
            
            // Обновить состояние кнопок
            document.getElementById('prevButton').disabled = exceededElements.length === 0;
            document.getElementById('nextButton').disabled = exceededElements.length === 0;
        }
        
        function escapeHtml(unsafe) {
            if (!unsafe) return '';
            return unsafe
                .replace(/&/g, "&amp;")
                .replace(/</g, "&lt;")
                .replace(/>/g, "&gt;")
                .replace(/"/g, "&quot;")
                .replace(/'/g, "&#039;");
        }
        
        function saveAllText() {
            // Собираем все строки из всех блоков
            let fullText = '';
            
            allResults.forEach((block, blockIndex) => {
                block.forEach((line, lineIndex) => {
                    fullText += line.original;
                    // Добавляем перенос только если это не последняя строка в блоке
                    if (lineIndex < block.length - 1) {
                        fullText += '\n';
                    }
                });
                // Добавляем перенос между блоками, но не после последнего блока
                if (blockIndex < allResults.length - 1) {
                    fullText += '\n';
                }
            });
            
            // Создаем Blob с текстом
            const blob = new Blob([fullText], { type: 'text/plain;charset=utf-8' });
            
            // Создаем временную ссылку для скачивания
            const url = URL.createObjectURL(blob);
            const a = document.createElement('a');
            a.href = url;
            a.download = 'edited_text.txt';
            
            // Добавляем ссылку в документ и эмулируем клик
            document.body.appendChild(a);
            a.click();
            
            // Удаляем ссылку и освобождаем память
            setTimeout(() => {
                document.body.removeChild(a);
                URL.revokeObjectURL(url);
            }, 100);
        }
    </script>
</body>
</html>

 

Сохраните код на рабочий стол в какой-нибудь index.html и открывайте в любом браузере.

  • +1 1

Поделиться сообщением


Ссылка на сообщение

@0wn3df1x мне говорили, что вроде есть плагин, но не факт, что он подойдёт для моей версии, что за плагин и где взять не сказали,  спасибо за выше скрипт, он работает, но есть одна проблема, что он сохраняет в txt и если я выделю, тот текст который там 6126 строк и вставлю, не прокатит, потому-что структура у проги аля excel, то есть колонки, а их всего 4358.
Мне тут чатгпт написал код для редактирования excel, вроде работает, посмотрел по твоему скрипту и говорит идеально 61 символ, щас попробую в этом коде поменять на 61

Поделиться сообщением


Ссылка на сообщение
3 минуты назад, Chillstream сказал:

@0wn3df1x мне говорили, что вроде есть плагин, но не факт, что он подойдёт для моей версии, что за плагин и где взять не сказали,  спасибо за выше скрипт, он работает, но есть одна проблема, что он сохраняет в txt и если я выделю, тот текст который там 6126 строк и вставлю, не прокатит, потому-что структура у проги аля excel, то есть колонки, а их всего 4358.
Мне тут чатгпт написал код для редактирования excel, вроде работает, посмотрел по твоему скрипту и говорит идеально 61 символ, щас попробую в этом коде поменять на 61

Мой скрипт заточен под форматирование из Google-таблиц (в экселе должна быть та же система).

То есть, допустим, в таблице могут быть две ячейки

Первая ячейка в одну строку
Вторая ячейка
в двух строках


Когда мы копируем текст из таблицы в буфер обмена, то мы получаем эти строки в таком виде:

Первая ячейка в одну строку
"Вторая ячейка
в двух строках"


Т.е. при копировании в буфер обмена у второй ячейки, внутри которой было две строки, в начале и в конце добавилась кавычка. Таким образом Google-таблицы и Excel понимает, что при вставке
”Первая ячейка в одну строку” — пойдёт в первую ячейку
А
”Вторая ячейка
в двух строках”
Пойдёт в следующую ячейку в цельном виде. Если бы не было кавычек, вместо двух ячеек получилось бы три ячейки с тремя строками.
 



А так всё от той программы для реимпорта зависит.
Если в неё нельзя вставить текст целиком, можно править и вставлять исправленное построчно. 

Поделиться сообщением


Ссылка на сообщение

оказывается реально работает такой перенос, буду знать.

если сегодня получится доделать текст, сюда заливать русификатор без тестирования, мне кажется плохая идея. так что либо я сам поиграю, либо дам кому-нибудь поиграть и знакомых и посмотрю.

  • +1 3

Поделиться сообщением


Ссылка на сообщение
10 часов назад, Chillstream сказал:

Короче тестеров особо не нашлось, я сам лично устал его делать), я так побегал, вроде играется) надо уже более глубоко, кто поиграет сказать, какие есть ошибки. В игре некоторые слова будут на английском, это звуки, но могут встретится и не переведенные реально слова, напишите когда наберется исправлю. и насчет ошибок мешающим прохождение, вдруг такое будет.
pRQIlWp.png

ipHtrmT.png

9w4j7d6.png
@SerGEAnt скачать русификатор: https://workupload.com/file/KkQa47UUD22 

установка: кинуть data и font в папку игры где .exe

Некоторые вещи при подъеме их откуда либо почему то не имеют русского перевода. К примеру подобрав из мусорки Cheeze stix(не переведено, но вроде бы озночает Сырные палочки) они пишутся на английском а в инвентаре написанны по русски.

 

Поделиться сообщением


Ссылка на сообщение

То что пока бросается в глаза и мой вариант для исправления

Подвеска для зубов - Подвеска из зубов
Батончик мюсли - Мюсли батончик
Опыт за бой отображается странно “30 получено ОПТ %”
Пистолетная пуля - Патрон для пистолета
Гильза от дробовика - Патрон для Дробовика
Старая игровая приставка - Консоль прошлого поколения
Старинная игровая приставка - Ретро консоль
"Спиртовая" доска - Спиритическая доска
Цвет игрового идентификатора - Портативная консоль
Покраска - Сумка для холста
Сморщенная голова - Сушеная голова
Ртутный диск - Диск "Меркурий"
Фигура Армейского парня - Солдатик
Коробка сока - Банка Апельсиновой колы
Банка Лимонного напитка - Банка Лимонада
Карамель - Конфетка
Батончик Гранулы - Батончик “Козинак”

Поделиться сообщением


Ссылка на сообщение

Старая газета. С тех пор как это началось. - Старая газета. До момента, как всё это началось.
Кажется, она застряла. Вы не можете её открыть. - Похоже её заклинило. Ты не можешь её открыть.
Он заклинило. Вы не можете её открыть. - Похоже её заклинило. Ты не можешь её открыть.
Винтовочная пуля - Патрон для винтовки
Пуля малого калибра для SMG - Патрон для ПП
Банка из-под колы - Банка Колы
Энергетический напиток - Энергетик
Тонизирующее средство - Тоник
Клейкая лента - Скотч
 

Поделиться сообщением


Ссылка на сообщение

нормально ты тут написал), насчет опыта я заметил, но не нашел где исправлять, насчет сырных палочек вроде я оставил английский вариант, например в начале есть подбор в комнате на английском, это красный тег, нельзя переводить, остальное гляну.

Изменено пользователем Chillstream
  • +1 1

Поделиться сообщением


Ссылка на сообщение

Здравствуйте! Наткнулся на такие баги: нельзя передать товарищу в маске что-то покушать. Меню с выбором еды пустое  2. После победы над копией художника (той, которая атакует при разговоре) выскакивает ошибка  (не может найти какой-то файл пнг)

Поделиться сообщением


Ссылка на сообщение

@Malkovichi вот я и боялся, что такое выскочит, скинь скрин на че жалуется, насчет нельзя дать покушать, вот тут я честно не знаю даже где исправлять скинь сейв и диалог посмотрю может там чёто нарушено.

@CoffeeD  насчёт переводов сверху, почему juice box это апельсиновый сок? или painting — сумка для холста?

Изменено пользователем Chillstream

Поделиться сообщением


Ссылка на сообщение

так выше исправил текст и у меня есть мысля изза чего все ломается.

Поделиться сообщением


Ссылка на сообщение

Сейчас восстановлю, гляну. Просто я помню, что я брал orange cola can

Всё я понял. Перевод каким-то макаром поменял иконку. Там действительно “Сок” (но он апельсиновый =))

Ещё один момент. Полосы хп, выносливости и патронов, имеют длинну в соотношении слов. 

image.png

Когда там было слово “Патроны”  (или что там было не помню). Полоски были в 1 мм.

Может быть записать как “ХП” “ВНС” “ПТРН”?

Да, это действительно “Картина”. т.е. после использования Сумки для холста. Ну и Покраска в — Картину исправить =)

Поделиться сообщением


Ссылка на сообщение

да я просто думаю, как так, вроде написано Juice Box и еще момент, насчет приставок, там написано

Old game Console если мы переводим — консоль прошлого поколения
A very old game console. The controllers resemble TV remotes.  — тогда тут “очень старая консоль прошлого поколения?”

/console

птрн исправил, мне нужен какой нить баг, понять суть, где ошибка происходит, насчет вын и оз нормально же, я везде исправил где видел, а так придётся опть весь текст менять обратно на хп) 

Изменено пользователем Chillstream

Поделиться сообщением


Ссылка на сообщение

Мб “Консоль прошлого поколения” и “Винтажная консоль”?

Поделиться сообщением


Ссылка на сообщение

Создайте аккаунт или войдите в него для комментирования

Вы должны быть пользователем, чтобы оставить комментарий

Создать аккаунт

Зарегистрируйтесь для получения аккаунта. Это просто!

Зарегистрировать аккаунт

Войти

Уже зарегистрированы? Войдите здесь.

Войти сейчас

  • Похожие публикации

    • Автор: SamhainGhost

      Steam
      Изометрическая игра в жанре survival horror, основанная на ремеслах, с запутанными монстрами и искаженной реальностью. Собирайте мусор и стройте, чтобы пережить ужасные дни и ночи, используя скрытность и шум для борьбы с врагами, которые крадутся по звуку. Все это оформлено в стиле смелых комиксов и в духе ужасов 80-х.
      Русификатор от SamhainGhost, v1a (от 29.01.2026) — гугл диск / boosty
      Требуемая версия игры: 1.0.13_15856 (Build 21685002)

      Переведено через Deepseek, протестированы первые минут 30 игры, полёт нормальный.
      Но! Игра стрессовая и напряжная, это не по мне.
    • Автор: MikhailFedosov
      Русификатор для игры Feastopia https://store.steampowered.com/app/3085910/Feastopia/
      Инструкция:
      1. Скачать файл из телеграм канал (config.unity3d)
      2. Заменить файл по пути: Feastopia_Data/StreamingAssets
      3. Выбрать японский язык! Предпоследний. 
      Отлично отображается шрифт, ничто никуда не уезжает.
       

  • Сейчас популярно

  • Продвигаемые темы

  • Последние сообщения

    • Вообще-то нет, не смотрел. А вот Клеймор и NHK cмотрел.  Понравились оба.
    • Нет, сначала тебе надо посмотреть гинтаму, потом можешь посмотреть Клеймор, после этого можешь попробовать посмотреть  N.H.K ni yôkoso. Но если будет тяжело выключай. Если справишься, то можешь посмотреть зетсубо сенсея
    • Это только для разогрева. А я бы посоветовал Звёздную Тюрягу, но ты вероятно её смотрел.
    • @SamhainGhost смастерил нейросетевой русификатор для изометрического хоррора I Hate This Place. @SamhainGhost смастерил нейросетевой русификатор для изометрического хоррора I Hate This Place.
    • @spider91 нормально ты высрался, как тебя это всё задело. Ну, проанализируем немного. Откровенно говоря я абсолютно не помню что когда-то тебе писал в дискорде. Тут шла речь за проект. Так за саус парк я просил помощи, или то что там по шрифтам? В случае про твою болтовню с парком — где я просил помощи? Ты отписался в теме — без всяких просьб я предложил с ними связаться. Я что-то тебя лично просил? Может это я пытался помочь, а не просил помощи? Конечно довольно занятно ты это всё перевернул. Далее оказалось, что такие вещи “так” не решаются, при этом без всяких проблем выкладываешь эти “тайные” для вас переписки. Для тебя же так важно такие серьёзные разговоры проводить конфиденциально?)) Или нет? При этом — это была не личка, а сообщение, которое могли читать все в команде. Личка между нами была как оказалось в дискорде, и то я даже подзабыл о чем там вообще был разговор в 23 году. Обращался очевидно по шрифтам, даже не помню какого проекта, и что в этом плохого? Или я, как ты утверждаешь, до 23 года срал всю вашу команду, а потом посмел к тебе лично обратиться за какой-то помощью? Из всего этого — ты конечно молодец, упустил важную вещь. Хронологию событий, о которой я твоему лайкающему “дружбану”, выше напоминал. Как же так. Вашу команду срут, а вы общаетесь, помогаете якобы и ещё благодарите? Что-то тут не вяжется. Может у кого-то проблемы, что было ДО и что было ПОТОМ? Но это ладно. После этого вас продолжают срать и делиться момента с ошибками в локализации? Ты наверное это тоже назовёшь двуличностью? Забавно. Я никогда не скрывал и до твоего ответа. И если рассматривать сеть это тоже встречалось и не скрывалось, или обсуждения между товарищами, и ту же Дарью, о которой они даже больше наслышаны, то это было даже в приватных обсуждениях до тебя.  Нерасторопность — это такое обидное слово? Проекты в жопе — констатация факта на момент застоя. Как только медийно активизировались — вопросов то и нет. Если не изменяет память там не в контексте сравнения с геймвойсами было, которые активнее работали? Могу ошибаться, но по-моему это было в тот период. Признаю — грубо было сказано. Засчитано Дмитрию Вячеславовичу... Может ты расскажешь заодно людям, как ты (и/или другие) вконтакте со всеми споришь и в перепалку вступаешь? Люди вам пишут — ты видно с задёрганным глазом считаешь своим долгом какого-то неудобного человека разнести. И речь далеко не обо мне…  Как обычно — слова подписчика — бред. Не говоря уже о клоунах, которые спрашивали про психонавтов. Хотя там и я бы опустил, т.к. сам с сарказмом отписал на эту тему. Но всё же клоунами называть людей, которые вам про игру напомнили, и тут так совпало что вы материал якобы подготовили — не стоило. Гнусно? И грубовато было с твоей стороны всё же. Я за собой признал грубость, а ты сможешь? “Кричащее меньшинство”, “разовые выкрики” и прочие высеры — постоянство. Какой бы человек не был, подписчик в вашей группе — не здраво для такой “студии” выплёскивать такие изречения. Ладно пользователи, необразованные и не “интеллигентные”, но унижение в ответ — доставляет удовольствие? Я вот читаю со стороны, и диву даюсь. Вроде должен, тот же Димка — уровень держать, а нет. Везде поспорит, везде надо утереть нос “хейтерам”… Именно это и имелось ввиду под “гнусным поведением” с твоей стороны. Но как я вижу, ты в этом очень активен. То одному подписчику намажешь, то другому… Как же тебя это всё задевает… А когда с тобой поступают похоже — для тебя это некая отдушина, но всё же неприятно? А это что? Мой коммент по сплит фикшну так влияет на людей? Или я запоносил, а остальное померещилось? Кстати, такие комментарии были и с Евой, ещё без моего участия, на тех же “разных” ресурсах, которые ты тщательно мониторишь. Тебе же очень важно что люди пишут. Не задавал себе вопрос, почему они пишут аналогичное? Ты наверное и тут придумаешь про раздвоение, а то и множество личностей? Или все такие “высиральщики”, хейтеры недовольные? Это же всё разовые, единичные мнения! Откуда их столько!? Наверное это всё один человек?? Димка. В ноябре того года я поддерживал и ждал эту же озвучку на стеллар, хвалил вас за работу. Но ты почему-то это забываешь, оперируя отдельными фактами, где вас якобы срут. И даже сейчас, несмотря на продолжающиеся от тебя выпады — не меняет моего отношения к труду, вложенному командой. Сплит фикшн из той же оперы. Мы проходили вдвоём с супругой, и даже ей резал слух тот самый писк и оры. Я кстати, включил английскую дорогу потом, и сравнил — там актриса дубляжа орала меньше и вроде вообще не пищала (из того что я услышал). Дело хозяйское — сделали, и сделали. Мнение оставлено? Оставлено. От тебя, как помнится были аргументы и наплывы, что мол “твоё мнение что единственное правильное?” Конечно нет. Не единственное (хотя бы скрин выше), и не является истиной для всех, но почему ты наезжаешь? Тебе лично по яйцам серпом прошерстили в грубой форме тогда? Абсолютно ведь нет… То что ты там со своей, не знаю насколько подругой, был во главе всего проекта — не должно настолько сильно восприниматься как личное. Вот действительно, сколько можно обижаться? Аргументированная критика озвучена не раз, но ты выставляешь только то, что тебе удобно выставить. Ребята писали не развёрнуто, но по той же теме — каждый раз утирать всем нос, измываться и насмехаться — это действительно гнусное поведение. Я не беру в расчёт тех, кто реально вёл себя в той же группе с тобой нагло, с наездами и прочим, но ты сам обмазывался со своими ответами.
    • трудовые будни Итосики-сэнсэя, регулярно вспоминающего любимую фразу: Я в отчаянии!. Несовершенство мира, неустроенность личной жизни, отборные кадры из атласа подростковой психопатологии, наводнившие его класс.Приключения, радости и горести «унылого учителя» и обожающего его сплоченного класса в итоге составили один из самых интересных учебников японской жизни, философии и культуры, написанный в духе постмодернистской комедии абсурда — фирменного жанра студии Shaft и режиссера Симбо Акиюки  
    •   То есть, чтобы оценить по достоинству, я должен пересмотреть Сэйлор и Гинтаму?  Ну на хрен.  А ведь почти скачался.   @Dusker у меня из-за тебя ресурс SSDшника потратился попусту.  Ты мне должен.
  • Изменения статусов

    • TerryBogard  »  Siberian GRemlin

      C&C: RA: Retaliation (ПК) не работает.
      · 0 ответов
    • Алекс Лев  »  SerGEAnt

      Привет, Сержант. Прошу разрулить ситуэйшн и урезонить некоторых людей, оскорбивших мою личность. Пожалуйста, для этого прочтите нашу переписку с Ленивым. Примите меры, будьте добры, мною составлена бумага, ждущая вашей электронной подписи, для подачи её в суд. Если не желаете судебных разборок (а я пойду дальше, если меры не будут приняты), оскорбившие меня люди должны понести необходимое по вашему же Договору наказание. Спасибо.
      · 1 ответ
    • Antony1203  »  SerGEAnt

      Добрый вечер! С Новым Годом. Нашел на просторах сети русскую озвучку Halo Infinite, которая отсутствует на моем любимом сайте  Протестил. Все работает. Подскажите, как можно передать? Спасибо.
      · 2 ответа
    • Albeoris

      Демка вышла. Работаем.
      · 0 ответов
    • maddante665  »  parabelum

      https://disk.yandex.ru/d/A7W9aHwW7wLTjg
      ссылка на торрент , в нем архив с игрой.
      единстенное в геймпасее папка TotalChaos_Data так, а в стиме Total Chaos_Data, но если пробел убрать в архиве с ркссификатором все равно не работает, ломаются надписи , просто прозрачные. я пробовал только текст .
      · 1 ответ
  • Лучшие авторы


Zone of Games © 2003–2026 | Реклама на сайте.

×