Get unlimited public & private packages + team-based management with npm Teams.Learn more »

v6-game-server

0.11.172 • Public • Published

V6-Game-Server

Сервер на node.js для пошаговых игр.

Установка

npm install v6-game-server

Запуск

        var Server = require('v6-game-server',
            // настройки
            conf = {},
            // игровой движок
            engine = {},
            // сервер
            server = new Server(conf, engine);
        
        server.start();

Настройки

Настройки сервера с параметрами по умолчанию
    {
        game: 'default',         // обязательный парамерт, алиас игры и бд
        port: 8080,              // порт подключения веб сокета
        pingTimeout:100000,      // таймаут клиента в мс
        pingInterval:10000,      // интервал пинга клиента в мс
        closeOldConnection: true,  // закрывать старое соединение клиента, при открытии нового  
        loseOnLeave: false,      // засчитывать поражение при разрыве соединения с клиентом
        reconnectOldGame: true,  // загружать игру клинета, в которой произошел разрыв
        spectateEnable: true,    // разрешить просмотр игр
        logLevel:3,              // уровень подробности лога, 0 - без лога, 1 - только ошибки
        turnTime: 100,              // время на ход игрока в секундах
        timeMode: 'reset_every_switch', // режимы таймера:
                                        // 'reset_every_turn' сбрасывать после каждого хода
                                        // 'reset_every_switch' сбрасывать после перехода хода
                                        // 'dont_reset' не сбрасывать таймер, время на всю партию
                                        // 'common' у игроков общее время на ход
        timeStartMode: 'after_switch',  // когда запускать таймер
                                        // 'after_turn' после первого хода
                                        // 'after_switch' после первого перехода хода
                                        // 'after_round_start' сразу после начала раунда
        addTime: 0,                 // сколько милисекунд добавлять к времени на ход игрока после каждого его хода
        maxTimeouts: 1,          // разрешенное число пропусков хода игрока подряд до поражения
        clearTimeouts: true, // обнулять число пропусков игрока после его хода
        maxOfflineTimeouts: 1,   // число пропусков отключенного игрока подряд до поражения
        minTurns: 0,             // минимальное число число ходов (переходов хода) для сохранения игры
        takeBacks: 0,            // число разрешенных игроку ходов назад
        loadRanksInRating: false,   // загружать актуальные ранги при открытии таблицы рейтинга
        ratingUpdateInterval: 1000, // интервал обновления рангов в списке игроков
        penalties: false,        // загружать штарфы игроков
        mode: 'debug',           // значение 'develop' уставновит режим без использования бд
        gameModes: ['default'],  // игровые режимы, со своим рейтингом и историей, имена без пробелов
        modesAlias:{default:'default'}, // отображаемые клиенту алиасы режимов
        enableIpGames: false,       // разрешает игры с одного ip
        minUnfocusedTurns: 0,       // минимальное число ходов с потерей фокуса для засчитывания победы как читерской
         // 0 - не считать
        minPerUnfocusedTurns: 0.9,  // соотношение числа ходов с потерей фокуса для засчитывания победы как читерской
        adminList: [], // список userId админов
        adminPass: '', // пароль для функций администратора
        mongo:{                  // настройки подключения mongodb
            host: '127.0.0.1',
            port: '27017'
        },
        redis:{                  // настройки подключения redis
         host: '127.0.0.1',
         port: '6379'
        },
        https: true, // настройки https
        httpsKey: '/path../serv.key',
        httpsCert: '/path../serv.crt',
        httpsCa: ['/path../sub.class1.server.ca.pem', '/path../ca.pem'],
    }
Примеры настроек:
- 	обычная игра, время на ход 30 секунд, разрешен один пропуск хода,
	время игрока обнуляется после каждого хода, таймер стартует после первого хода
    {
        turnTime: 30,
        maxTimeouts: 2,
        timeMode: 'reset_every_turn',
        timeStartMode: 'after_turn',
    }
-	блиц, время на партию 60 секунд, время игрока не обнуляется,
	после каждого его хода к его времени на ход добавляется 1 секунда,
	таймер стартует после перехода хода к другому игроку,
	после первого пропуска хода ему засчитывается поражение
    {
        turnTime: 60,
        maxTimeouts: 1,
        timeMode: 'dont_reset',
        timeStartMode: 'after_switch',
        addTime: 1000
    }
-	игра с общим временем на ход, по типу "кто быстрее",
	таймер страртует сразу после начала раунда,
	по истечении часа срабатывает таймаут и необходимо решить результат игры
    {
        turnTime: 3600,
        maxTimeouts: 2,
        timeMode: 'common',
        timeStartMode: 'after_round_start',
    }

Игровой движок

Методы игрового движка
    {
        /**
         * вызывается после соединения нового пользователя в первый раз
         * устанавливает значения нового пользователя по умолчанию
         * рейтинги, очки, и т.д.
         */
        initUserData: function(mode, modeData){
            return modeData;
        },
        
        /**
         * вызывается перед началом игрового раунда
         * возвращаемый объект будет передан всем игрокам в начале раунда
         * по умолчанию возвращает объект переданный игроком в приглашении
         */
        initGame: function (room) {
            return {
                inviteData: room.inviteData
            }
        },
 
        /**
         * вызывается в начале раунда
         * возвращает игрока, который будет ходить первым
         * по умолчанию первым ходит создатель комнаты, 
         * в следующем раунде ход переходит к другому игроку
         */
        setFirst: function (room) {
            if (!room.game.first) return room.owner;
            return room.getOpponent(room.game.first)
        },
 
        /**
         * вызывается каждый ход или пропуск хода игрока
         * возвращаемый объект будет передан всем игрокам и записан в историю
         * если вернуть false || null || undefined ход будет признан некорректным
         * в случае пропуска хода, turn = {action: 'timeout'}
         * если вернуть объект с полем action = 'timeout'
         * он будет принят как событие пропуск хода, иначе как обычный ход
         * type {'turn'|'timeout'} - ход игрока или таймаут
   */
        doTurn: function(room, user, turn, type){
            if (type == 'timeout'){
                // this is user timeout
            }
            return turn;
        },
 
        /**
         * вызывается каждый ход игрока или после события пропуска хода
         * возвращаемый игрок будет ходить следующим
         * если вернуть того же игрока, чей был ход, ход останется за ним
         * type {'turn'|'timeout'} - ход игрока или таймаут
         */
        switchPlayer: function(room, user, turn, type){
            if (type == 'timeout'){
                // this is user timeout
            }
            return room.getOpponent(user);
        },
 
        /**
         * вызывается после отправке игроком события
         * возвращаемый объект будет передан заданным игрокам, и должен быть следующего вида:
         * { event, target, user } || [Array], где
         * event - объект с обязательным полем type
         * target - цель для отправки события null || Room || User
         * может быть массивом с разными объектами событий и целями
         */
        userEvent: function(room, user, event){
            return {
                event: event,
                target: room,
                user: user.userId
            }
        },
 
        /**
         * вызывается в начале раунда и после каждого хода игрока
         * возвращаемый объект будет передан заданным игрокам, и должен быть следующего вида:
         * { event, target, user } || [Array], где
         * event - объект с обязательным полем type
         * target - цель для отправки события null || Room || User
         * может быть массивом с разными объектами событий и целями
         */
        gameEvent: function(room, user, turn, roundStart){
           return null;
        },
 
        /**
         * вызывается каждый ход и событие, определяет окончание раунда
         * возвращаемый объект будет передан всем игрокам 
         * и должен быть вида {winner : user}, где
         * user - User (игрок победитель ) || null (ничья)
         * если вернуть false - раунд еще не окончен
         * дополнительное поле 'action' указывает на действие,
         * по которому завершилась игра, по умолчанию 'game_over'
         * если пользователь не подключен, то игра завешится по
         * максимальному числу офлайн таймаутов
         * если не подключены оба, завершится поражением пропустившего
         * если не обрабатывать пропускать ход можно бесконечно
         * type {'turn'|'event','timeout'} - ход, событие или таймаут
         */
     getGameResult: function(room, user, turn, type){
         switch (type){
             case 'timeout':
                 if (type == 'timeout'){
                     // if user have max timeouts, other win
                     if (room.data[user.userId].timeouts == room.maxTimeouts){
                         return {
                             winner: room.getOpponent(user),
                             action: 'timeout'
                         };
                     } else return false;
                 }
                 break;
             case 'event':
                 if (turn.type){
                     return false;
                 }
                 break;
             case 'turn':
                 switch (turn.result){
                     case 0: // win other player
                         return {
                             winner: room.getOpponent(user)
                         };
                         break;
                     case 1: // win current player
                         return {
                             winner: user
                         };
                         break;
                     case 2: // draw
                         return {
                             winner: null
                         };
                         break;
                     default: // game isn't end
                         return false;
                 }
                 break;
         }
     },
 
        /**
         * вызывается по окончанию раунда
         * возвращаемый объект утсанавливает значение очков игроков 
         * room.players[0][room.mode].['score'] = new_score
         */
        getUsersScores: function(room, result){
            // например
            for (var i = 0; i < room.players.length; i++){
            if (room.players[i] == result.winner)
                room.players[i][room.mode].score += 10;
            else room.players[i][room.mode].score -= 10;
        }
        return result;
        },
        
        /**
         * вызывается после отмены хода, для изменения игрового 
         * состояния в комнате
         */
        doTakeBack: function(room, user){
            return null;
        },
 
        /**
         * вызывается после авторизации пользователя
         * проверяет подлинноть подписи
         */
        checkSign: function(user){
            return (user.userId && user.userName && user.sign);
        }
 
        /**
         * действие по вызову администратора
         * @param admin
         * @param type
         * @param data
         */
        adminAction: function(admin, type, data){
 
        }
    };

Игровые сущности

Room
    {
        owner: User,  // создатель
        players: Array, // массив с игроками
        spectators: Array, // массив зрителей
        inviteData: Object // объект приглашения
        mode: String // режим
        games: Int; // сыграно раундов
        turnTime: Int; // время на ход
        game: {
            state: String  // состояние игры:  waiting,  playing, end
            current: User, // текущий игрок
            first: User, // игрок, чей ход первый, установленный функцией engine.setFirst
            history: Array, // массив с иторией ходов и событий
            shistory: String// массив с историей, преобразованный в строку
            turnStartTime: UTC  // дата начала хода игрока
        },
        data: Object, // массив ключ значение, где ключи - userId
                            // для хранения временной информации для каждого игрока
        getOpponent: Function(user: User)   // возвращает соперника игрока
        setUserTurnTime: Function(time: ms) // устанавливает время на следующий ход
    }
User
    {
        userId: String,  // идетификатор игрока
        userName: String // имя
        sign: String // подпись
        currentRoom: Room // текущая комната (играет или зритель)
    }

Keywords

none

Install

npm i v6-game-server

DownloadsWeekly Downloads

238

Version

0.11.172

License

none

Unpacked Size

340 kB

Total Files

44

Last publish

Collaborators

  • avatar