Выделение говорящего цветом (версия 3, универсальная)


init python:
    # автоматическое объявление спрайтов
    config.automatic_images_minimum_components = 1
    config.automatic_images = [" ", "_", "/"]
    config.automatic_images_strip = ["images"]

init:
    # яркость и масштаб выделенного персонажа
    default char_brightness = .15
    default char_zoom = 1.025

    # время на выделение персонажа
    default char_t = .25

    # позиция спрайта на экране
    transform xpos(x=.5):
        anchor(.5, 1.)
        pos(x, 1.)

    # плавно отключаем выделение персонажа
    transform mark_off(t=char_t):
        ease_quad t matrixcolor BrightnessMatrix(0) zoom 1

    # плавно включаем выделение персонажа
    transform mark(t=char_t, z=char_zoom):
        parallel:
            matrixcolor BrightnessMatrix(0)
            # для вспышки
            ease_quad t*.25 matrixcolor BrightnessMatrix(char_brightness * 2)
            # для постоянного выделения
            ease_quad t*.75 matrixcolor BrightnessMatrix(char_brightness)
        parallel:
            # увеличение - выдвигаемся на передний план
            ease_quad t zoom z

init python:
    from functools import partial

    # найти на экране картинку, которая начинается с заданного тега
    # (чтобы выделение не учитывало эмоции и прочие дополнительные теги)
    def img_by_tag(tag):
        if tag:
            imgs = renpy.get_showing_tags()
            for i in imgs:
                if str(i).startswith(tag):
                    return str(i)
        # если на экране нет говорящего персонажа, то и не показываем его
        return None

    # последний говоривший
    speaking_char = None

    # показать того же персонажа, если он уже есть на экране
    def char_show(char, at_list=[]):
        i = img_by_tag(char)
        if i:
            renpy.show(i, at_list=at_list)

    # снять выделение
    def char_off(t=None):
        # если нужно ждать, то берем установленную в настройках паузу
        if t == True:
            t = char_t
        # снимаем выделение
        char_show(img_by_tag(store.speaking_char), at_list=[mark_off()])
        store.speaking_char = None
        # пауза, если нужна, чтобы персонаж успел снять выделение
        if t:
            renpy.pause(t)

    # выделяем говорящего
    def char_blink(char, event_name, *args, **kwarg):
        # если начинает говорить новый персонаж
        if event_name == "begin" and char != store.speaking_char:
            # то со старого снимаем выделение
            char_off()
            # запоминаем нового оратора
            store.speaking_char = char
            # ставим на него выделение
            char_show(char, at_list=[mark()])

    # сокращаем писанину при объявлении персонажей

    # функция с параметрами в качестве одного параметра
    def c_b(*args, **kwarg):
        return partial(char_blink, *args, **kwarg)

    # замена обычного Character на новый, где вторым параметром идёт спрайт
    def CH(name=None, sprite=None, *args, **kwarg):
        return Character(name, callback=c_b(sprite), *args, **kwarg)

    # рассказчик снимает выделение с последнего персонажа из-за sprite=None
    narrator = CH()

    # вторым параметром указан первый тег спрайта, связанного с персонажем
    g = CH(_("Девочка"), "girl", color="#f88")

    # остальные параметры могут быть такие же, как в обычном Character
    b = CH(_("Мальчик"), "boy")

    # если не указывать спрайт, то персонаж будет просто снимать выделение с последнего говорящего
    v = CH(_("Внутренний голос"), color="#f88")

label start:
    scene bg street
    with dissolve
    # показываем персонажей
    show boy ok at xpos(.33)
    show girl ok at xpos(.66)
    with dissolve
    pause .5

    # начинаем тупой диалог
    g "Привет."

    b "Дароф!"

    "*свечение исчезает*"

    show boy wat
    b "Ты видела? Меня только что йоком тобнуло, аж искры из глаз посыпались. Я светился, как лампочка в холодильнике."

    show boy ok
    b "А сейчас отпустило, вроде."

    g "Не, я ничего не видела. Гонишь, наверное. Признавайся, чем закинулся."

    show girl wat

    # молча убрать выделение и подождать, пока оно снимется
    $ char_off(True)
    g "Ой, а меня тоже пропёрло, кажется. Это что, заразно? Отойди от меня, наркоман чёртов!"

    v "Что я несу! Вот он урод, из-за него я... Хотя нет, всё нормально: все мужики уроды, а девушки всегда правы."

    b "Похоже, нас колбасит каждый раз, когда заговорим. Кто-то с Ренпаем балуется."

    show girl ok
    g "Долбаные разработчики..."

    $ char_off()

    scene black
    with dissolve
    return

Комментарии