Шаг 176.
Основы Kotlin.
Объекты. Объявления объектов

    На этом шаге мы рассмотрим особенности использования синглтонов.

    Объявления объектов (синглтоны) полезны для организации и управления состоянием, особенно когда надо поддерживать какое-то состояние на протяжении работы программы. Для этого мы объявим объект Game.

    Объявление класса Game как синглтона также послужит нам удобным местом для определения цикла игры и позволит убрать его из функции main() в Game.kt. Разделение кода на классы и объявление объектов еще больше способствует вашей цели, направленной на поддержание кода в организованном состоянии.

    Объявите объект Game в Game.kt, используя объявление объектов.

import Player
import Room
import TownSquare

fun main() {
    .   .   .   .
}

fun printPlayerStatus(player: Player) {
    println("(Aura: ${player.auraColor()}) " +
            "(Blessed:  ${if (player.isBlessed) "YES" else "NO"})")
    println("${player.name} ${player.healthStatus()}")

object Game {

}


Рис.1. Объявление объекта Game (Game.kt)

    Функция main() в Game.kt должна служить исключительно для запуска игрового процесса. Вся игровая логика будет сосредоточена внутри объекта Game, существующего в единственном экземпляре.

    Так как экземпляр синглтона создается автоматически, нет нужды добавлять свой конструктор с кодом инициализации. Вместо этого достаточно определить блок инициализации, выполняющий все необходимое для инициализации вашего объекта. Добавим один такой блок в объект Game, который выведет приветствие при его создании.

import Player
import Room
import TownSquare

fun main() {
    .   .   .   .
}

fun printPlayerStatus(player: Player) {
    println("(Aura: ${player.auraColor()}) " +
            "(Blessed:  ${if (player.isBlessed) "YES" else "NO"})")
    println("${player.name} ${player.healthStatus()}")

object Game {
    init {
        println("Welcome, adventurer.")
    }
}


Рис.2. Добавление блока init в Game (Game.kt)

    Запустите Game.kt. Приветствие не выводится, потому что Game не был инициализирован. А не инициализирован он из-за того, что мы к нему пока не обращались.

    Чтобы обратиться к объекту, нужно сослаться на одно из его свойств или функций. Чтобы запустить инициализацию Game, объявим и вызовем функцию с именем play(). Эта функция будет служить домом для цикла игры NyetHack.

    Добавьте play() в Game и вызовите ее из main(). Функция объекта вызывается с использованием имени объекта, в котором она объявлена, а не экземпляра класса, как в случае с функциями класса.

import Player
import Room
import TownSquare

fun main() {
    .   .   .   .
    // Состояние игрока
    printPlayerStatus(player)
    Game.play()
}

fun printPlayerStatus(player: Player) {
    println("(Aura: ${player.auraColor()}) " +
            "(Blessed:  ${if (player.isBlessed) "YES" else "NO"})")
    println("${player.name} ${player.healthStatus()}")

object Game {
    init {
        println("Welcome, adventurer.")
    }
    fun play() {
        while (true) {
            // Игровой процесс NyetHack
        }
    }
}
Файл с проектом можно взять здесь.


Рис.3. Вызов функции из объявления объекта (Game.kt)

    Объект Game будет не только хранить состояние игры, но и выполнять цикл игры, принимающий и выполняющий команды игрока. Ваш цикл игры примет форму цикла while, что сделает игру NyetHack более интерактивной. Он будет иметь простое условие true, поддерживающее работу цикла, пока приложение не будет закрыто.

    Пока что play() не делает ничего. Скоро она разобьет игровой процесс NyetHack на раунды: в каждом раунде в консоль будут выводиться состояние игрока и прочая информация о мире, и затем будет приниматься ввод пользователя с помощью функции readLine().

    На следующем шаге мы продолжим изучение этого вопроса.




Предыдущий шаг Содержание Следующий шаг