Pterohost docs

GMod: кастомный loading screen сервера

Как сделать кастомный экран загрузки для сервера Garry's Mod: sv_loadingurl, хостинг HTML-страницы, правила, музыка, прогресс загрузки и решение частых ошибок.

Кратко: Кастомный loading screen в Garry’s Mod задаётся одной строкой sv_loadingurl "https://..." в server.cfg. Страница создаётся как обычный HTML-файл с доступом к JavaScript-хукам для прогресса загрузки, правил сервера и фоновой музыки.

GMod: кастомный loading screen сервера

Экран загрузки - первое, что видит игрок при подключении к серверу. Стандартный loading screen Garry’s Mod минималистичен: серый фон, название сервера и прогресс-бар. Для сервера с серьёзным DarkRP, MilitaryRP или TTT-сообществом это потерянная возможность. Кастомный экран загрузки позволяет показать правила сервера, брендинг, текущую карту, онлайн, социальные сети и даже фоновую музыку - всё это пока игрок ждёт завершения загрузки карты и аддонов. В 2026 году технология не изменилась кардинально, но выросли требования к HTTPS и совместимости с Chromium-движком, встроенным в GMod.

Pterohost - игровой хостинг для Garry’s Mod с DDoS-защитой, NVMe SSD и поддержкой 24/7. Промокод 4START даёт -20% на первый заказ. Заказать Garry’s Mod сервер

Как работает loading screen в Garry’s Mod

Когда игрок подключается к серверу, движок Source открывает встроенный браузер на базе Chromium и загружает URL из конвара sv_loadingurl. Браузер рендерит страницу поверх фона загрузки - игрок видит именно вашу HTML-страницу, а не стандартный экран.

Ключевые технические детали:

  • Браузер внутри GMod - это Chromium (CEF, Chromium Embedded Framework). Поддерживаются HTML5, CSS3, JavaScript ES6+, Web Audio API, Canvas.
  • С 2022 года GMod требует HTTPS для sv_loadingurl. HTTP-адрес либо не загрузится, либо покажет предупреждение в зависимости от версии клиента.
  • Страница открывается сразу при подключении и закрывается автоматически, когда загрузка карты и контента завершена.
  • Через JavaScript сервер передаёт странице информацию: название сервера, URL, карту, максимальное количество игроков, SteamID игрока, гейм-мод.

Настройка sv_loadingurl

Основная настройка делается в garrysmod/cfg/server.cfg:

// Кастомный экран загрузки
sv_loadingurl "https://loading.yourserver.com/"

Или в garrysmod/cfg/autoexec.cfg - эффект тот же. После изменения нужен рестарт сервера (не просто changelevel).

Проверить текущее значение в консоли сервера:

] sv_loadingurl
sv_loadingurl = "https://loading.yourserver.com/" ( def. "" )

Пустое значение ("") означает, что используется стандартный экран Valve.

Параметры рядом с sv_loadingurl

КонварОписаниеРекомендация
sv_loadingurlURL страницы загрузкиHTTPS, без пробелов
sv_allowdownload 1Разрешает загрузку файловОставить 1
sv_downloadurlURL для FastDLОтдельно от loading URL
net_maxfilesize 64Макс. размер файла через загрузку64 МБ максимум

Где хостить страницу загрузки

Страница должна быть доступна по стабильному HTTPS-адресу с низкой задержкой - игрок видит её во время загрузки, и если она грузится 5 секунд, это раздражает.

Вариант 1: GitHub Pages (бесплатно)

Самый простой способ для небольших серверов:

  1. Создайте репозиторий yourname/gmod-loading на GitHub.
  2. Загрузите index.html и все ресурсы (изображения, CSS, JS, музыку).
  3. В настройках репозитория включите GitHub Pages (Source: main branch, / root).
  4. Адрес будет https://yourname.github.io/gmod-loading/.

Ограничение: репозиторий публичный, размер файлов до 100 МБ, общий лимит хранилища 1 ГБ. Для загрузочного экрана этого более чем достаточно.

Вариант 2: Cloudflare Pages (бесплатно, CDN)

Лучше GitHub Pages по скорости за счёт глобального CDN Cloudflare:

  1. Зарегистрируйтесь на pages.cloudflare.com.
  2. Подключите GitHub-репозиторий или загрузите файлы напрямую.
  3. Получите адрес вида https://your-project.pages.dev/.

Cloudflare Pages поддерживает кастомные домены - можно настроить loading.yourserver.com за несколько кликов.

Вариант 3: Свой VPS/nginx

Если у вас уже есть VPS с nginx (например, для FastDL), добавьте отдельный server block:

server {
    listen 443 ssl;
    server_name loading.yourserver.com;

    ssl_certificate /etc/letsencrypt/live/loading.yourserver.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/loading.yourserver.com/privkey.pem;

    root /var/www/loading;
    index index.html;

    # CORS для ресурсов (опционально)
    add_header Access-Control-Allow-Origin "*";

    # Кэширование статики
    location ~* \.(css|js|png|jpg|mp3|woff2)$ {
        expires 30d;
        add_header Cache-Control "public, immutable";
    }
}

SSL-сертификат от Let’s Encrypt - бесплатно через certbot:

certbot --nginx -d loading.yourserver.com

Структура HTML-страницы

Минимальная рабочая страница загрузки:

<!DOCTYPE html>
<html lang="ru">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Загрузка сервера...</title>
    <style>
        * { margin: 0; padding: 0; box-sizing: border-box; }
        body {
            background: #1a1a2e;
            color: #eee;
            font-family: 'Segoe UI', sans-serif;
            display: flex;
            flex-direction: column;
            align-items: center;
            justify-content: center;
            min-height: 100vh;
        }
        h1 { font-size: 2rem; margin-bottom: 1rem; }
        .progress-bar {
            width: 400px;
            height: 8px;
            background: #333;
            border-radius: 4px;
            overflow: hidden;
        }
        .progress-fill {
            height: 100%;
            background: linear-gradient(90deg, #4facfe, #00f2fe);
            width: 0%;
            transition: width 0.3s ease;
        }
        #status { margin-top: 0.5rem; font-size: 0.85rem; color: #aaa; }
    </style>
</head>
<body>
    <h1>YourServer DarkRP</h1>
    <p id="map-info">Подключение...</p>
    <div class="progress-bar">
        <div class="progress-fill" id="progress"></div>
    </div>
    <p id="status">Инициализация...</p>

    <script>
        // Хук GameDetails вызывается GMod при передаче данных сервера
        function GameDetails(servername, serverurl, mapname, maxplayers, steamid, gamemode) {
            document.querySelector('h1').textContent = servername;
            document.getElementById('map-info').textContent =
                'Карта: ' + mapname + ' | Режим: ' + gamemode + ' | Макс: ' + maxplayers;
        }

        // SetStatusChanged - вызывается при смене статуса загрузки
        function SetStatusChanged(status) {
            document.getElementById('status').textContent = status;
        }

        // DownloadingFile - вызывается при загрузке каждого файла
        function DownloadingFile(filename) {
            document.getElementById('status').textContent = 'Загрузка: ' + filename;
        }

        // LoadingProgressChanged - прогресс от 0 до 100
        function LoadingProgressChanged(progress) {
            document.getElementById('progress').style.width = progress + '%';
        }
    </script>
</body>
</html>

JavaScript-хуки от Garry’s Mod

GMod вызывает следующие JavaScript-функции на вашей странице:

ФункцияАргументыОписание
GameDetails(servername, serverurl, mapname, maxplayers, steamid, gamemode)строкиВызывается один раз при старте. Содержит основную инфу о сервере и игроке
SetStatusChanged(status)строкаСтатус текущей операции: “Connecting…”, “Downloading…” и т.д.
DownloadingFile(filename)строкаИмя файла, который сейчас качается через FastDL или игровой канал
LoadingProgressChanged(progress)число 0-100Прогресс загрузки в процентах

Все четыре функции нужно объявить в глобальном scope (window.GameDetails = function(){...}). Если функция не объявлена, GMod просто не вызывает её - ошибки не будет.

Добавление правил сервера

Показ правил на экране загрузки - один из ключевых кейсов. Игрок вынужден их прочитать, пока ждёт:

<div class="rules-block">
    <h2>Правила сервера</h2>
    <ol>
        <li>Запрещён RDM (Random Deathmatch) без повода</li>
        <li>Запрещён NLR (New Life Rule) - не возвращаться на место смерти 3 минуты</li>
        <li>Уважайте других игроков - оскорбления ведут к бану</li>
        <li>Чит-программы и эксплойты - перманентный бан</li>
        <li>Вопросы администрации решать через @ в чате или Discord</li>
    </ol>
    <p class="rules-note">Незнание правил не освобождает от ответственности.</p>
</div>

Добавьте стилизацию: тёмный блок с рамкой, пронумерованный список, выделение важных пунктов красным. Типичная практика - требовать, чтобы игрок прокрутил до конца правил (CSS-трюк через IntersectionObserver или кнопку “Я прочитал”, которая появляется после таймера).

Важно: кнопка “Я принимаю правила” на загрузочном экране - только визуальная. Она не блокирует вход на сервер на уровне движка. Если нужна реальная система согласия с правилами, используйте Lua-аддон (например, ULX MOTD или отдельный согласие-скрипт), который блокирует игрока до нажатия кнопки в игровом меню.

Фоновая музыка

Добавить музыку можно через стандартный HTML5 Audio:

<audio id="bg-music" autoplay loop preload="auto">
    <source src="https://loading.yourserver.com/music/theme.mp3" type="audio/mpeg">
</audio>

<!-- Кнопка отключения звука -->
<button id="mute-btn" onclick="toggleMute()">Выключить музыку</button>

<script>
    var audio = document.getElementById('bg-music');
    var muted = false;

    // Автовоспроизведение может быть заблокировано - запускаем по взаимодействию
    document.addEventListener('click', function() {
        if (audio.paused) {
            audio.play().catch(function(e) {
                console.log('Autoplay blocked: ' + e);
            });
        }
    }, { once: true });

    function toggleMute() {
        muted = !muted;
        audio.muted = muted;
        document.getElementById('mute-btn').textContent =
            muted ? 'Включить музыку' : 'Выключить музыку';
    }
</script>

Рекомендации по музыке:

  • Формат MP3, 128-192 kbps. WAV слишком тяжёлый, OGG работает не везде в CEF.
  • Файл должен лежать на HTTPS-сервере. HTTP-ресурс на HTTPS-странице блокируется политикой Mixed Content.
  • Размер трека - до 5 МБ. Больше - долго грузится и раздражает при медленном интернете.
  • Добавьте кнопку выключения - не все хотят слушать музыку во время загрузки.
  • Не забывайте про авторские права: используйте royalty-free треки (Pixabay, Free Music Archive, ccMixter) или собственные записи.

Отображение онлайна и динамических данных

Если хотите показывать текущий онлайн сервера прямо на loading screen, нужна серверная часть. GMod loading screen - это обычная веб-страница, она не имеет прямого доступа к данным сервера.

Вариант: Steam Web API

Steam предоставляет бесплатный API для получения информации о сервере:

async function updateServerInfo() {
    // Steam Web API - GetServersAtAddress
    // addr - IP:порт вашего игрового сервера
    var addr = '1.2.3.4:27015';
    var apiKey = 'YOUR_STEAM_API_KEY'; // получить на steamcommunity.com/dev/apikey

    try {
        var res = await fetch(
            'https://api.steampowered.com/IGameServersService/GetServerList/v1/' +
            '?key=' + apiKey +
            '&filter=addr\\' + addr +
            '&limit=1'
        );
        var data = await res.json();
        if (data.response && data.response.servers && data.response.servers.length > 0) {
            var srv = data.response.servers[0];
            document.getElementById('online').textContent =
                srv.players + '/' + srv.max_players + ' игроков';
        }
    } catch (e) {
        console.log('Steam API error: ' + e);
    }
}

// Обновлять каждые 30 секунд
updateServerInfo();
setInterval(updateServerInfo, 30000);

Обратите внимание: Steam API не предназначен для частых запросов. Разумный интервал - раз в 30 секунд. Для высокой нагрузки сделайте прокси-эндпоинт на своём сервере с кэшированием.

Готовые шаблоны и ресурсы

Вместо написания с нуля можно взять готовое решение:

РешениеОписаниеГде взять
EasyHTML Loading ScreenПопулярный шаблон с прогресс-баром, музыкой, правилами. Настройка через config.jsGitHub: gmodloading/easyhtml
Hypnos Loading ScreenБолее современный дизайн, поддержка тем, виджет DiscordGitHub, gmodstore
Lordz Loading ScreenШаблон для MilitaryRP с картой сервера и статистикойgmodstore.com
Proprio Custom LoadingКоммерческий, гибкая настройка без HTML-знанийgmodstore.com

При выборе готового шаблона проверяйте:

  • Дату последнего обновления (поддержка HTTPS, совместимость с CEF 2022+).
  • Наличие хука LoadingProgressChanged - без него прогресс-бар не работает.
  • Лицензию на использование музыки, если она идёт в комплекте.

Частые проблемы и их решения

Пустая страница или ошибка соединения

Причина 1: HTTP вместо HTTPS.

Решение: обязательно используйте https:// в sv_loadingurl. С 2022 года CEF в GMod блокирует HTTP по умолчанию.

// Неправильно:
sv_loadingurl "http://loading.yourserver.com/"

// Правильно:
sv_loadingurl "https://loading.yourserver.com/"

Причина 2: Лишние пробелы в значении конвара.

Проверить в консоли сервера: sv_loadingurl без аргументов выведет текущее значение. Пробел после кавычки или URL - частая причина.

Причина 3: SSL-сертификат просрочен или самоподписанный.

CEF не принимает невалидные сертификаты. Используйте Let’s Encrypt (бесплатно) или сертификаты от Cloudflare/GitHub Pages.

Музыка не воспроизводится

Современные браузеры (включая CEF) блокируют автовоспроизведение без пользовательского взаимодействия. Решение: запускать воспроизведение по первому click-событию (пример кода выше) или использовать обходной путь через Promise:

window.addEventListener('load', function() {
    var audio = document.getElementById('bg-music');
    var playPromise = audio.play();

    if (playPromise !== undefined) {
        playPromise.catch(function() {
            // Автовоспроизведение заблокировано - ждём клика
            document.body.addEventListener('click', function() {
                audio.play();
            }, { once: true });
        });
    }
});

Функции GameDetails не вызываются

Убедитесь, что функции объявлены в глобальном scope, а не внутри другой функции или модуля:

// Правильно - глобальные функции:
function GameDetails(servername, serverurl, mapname, maxplayers, steamid, gamemode) {
    // ...
}

// Неправильно - внутри DOMContentLoaded или другой функции:
document.addEventListener('DOMContentLoaded', function() {
    function GameDetails(...) { /* GMod сюда не доберётся */ }
});

Экран зависает и не закрывается

Это не баг loading screen - обычно это симптом долгой загрузки карты или аддонов. Сам loading screen закрывается автоматически движком. Но если на странице есть JavaScript-ошибки, вызывающие бесконечный цикл, CEF может “заморозить” рендеринг. Проверяйте консоль браузера: откройте URL страницы в обычном Chrome/Firefox и смотрите DevTools.

Mixed Content - ресурсы заблокированы

Если ваша страница HTTPS грузит изображения, шрифты или музыку по HTTP, CEF заблокирует их молча. Признак: элементы не отображаются, музыка не играет, консоль браузера показывает “Mixed Content: The page at HTTPS was loaded over HTTPS, but requested an insecure resource”.

Решение: убедитесь, что все внешние ресурсы (<img src>, <audio src>, @import url(), fetch()) используют HTTPS.

Пример финального server.cfg

Минимальная конфигурация сервера с loading screen:

hostname "YourServer DarkRP | discord.gg/yourserver"
sv_loadingurl "https://loading.yourserver.com/"
sv_downloadurl "https://fastdl.yourserver.com/garrysmod/"

sv_allowdownload 1
net_maxfilesize 64

// Таймаут подключения - дать игроку время прочитать правила
sv_timeout 65

Параметр sv_timeout стоит увеличить до 60-65 секунд, если у вас много контента и игроки с медленным интернетом могут не успеть загрузиться за стандартные 30 секунд.

Связанные материалы

Перед настройкой loading screen убедитесь, что ваш сервер полностью настроен: в статье Сборка сервера Garry’s Mod описан весь путь от SteamCMD до рабочего гейм-мода. Для управления сервером и выдачи прав изучите ULX - система администрирования GMod. Если запускаете DarkRP - смотрите Настройка DarkRP сервера с примерами jobs.lua и darkrp_config.

Заключение

Кастомный loading screen - быстрая и эффективная доработка, которая значительно улучшает первое впечатление от сервера. Настройка занимает 30-60 минут: создать HTML-страницу, разместить на HTTPS-хостинге, прописать sv_loadingurl в server.cfg. Через JavaScript-хуки GameDetails и LoadingProgressChanged страница становится живой - показывает карту, прогресс загрузки и информацию о сервере. Добавление правил на loading screen снижает количество нарушений - игроки действительно их читают. Музыка создаёт атмосферу, хотя важно дать возможность её отключить.

Pterohost - надёжный хостинг Garry’s Mod серверов с защитой от DDoS-атак, быстрыми NVMe-дисками и технической поддержкой 24/7. Промокод 4START даёт -20% на первый заказ. Заказать Garry’s Mod сервер