Skip to content

Instantly share code, notes, and snippets.

@ochaochaocha3
Created November 24, 2014 09:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ochaochaocha3/47df224a36330c555399 to your computer and use it in GitHub Desktop.
Save ochaochaocha3/47df224a36330c555399 to your computer and use it in GitHub Desktop.
スパロボ風会話画面試作版
require 'gosu'
require 'yaml'
Character = Struct.new(:nick_name, :image)
Page = Struct.new(:chara, :text)
class Script
attr_reader :chara
attr_reader :pages
def initialize(window, yaml_path)
@window = window
load_script_file(yaml_path)
end
def load_script_file(yaml_path)
data = YAML.load_file(yaml_path)
load_characters(data['Characters'])
load_pages(data['Script'])
end
def load_characters(chara_data)
@chara = Hash[
chara_data.map do |id, data|
[
id,
Character.new(
data['NickName'],
Gosu::Image.new(@window, data['Image'], false)
)
]
end
]
end
def load_pages(script_data)
@pages = []
script_data.each do |page_data|
chara = @chara[page_data['Character']]
page_data['Speeches'].each do |lines|
@pages << Page.new(chara, lines.join("\n"))
end
end
end
end
Characters:
Kyosuke:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 通常
Image: 'img/chara/SRWI_KyosukeNanbu.bmp'
KyosukeA:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 攻撃
Image: 'img/chara/SRWI_KyosukeNanbu(A).bmp'
KyosukeA2:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 攻撃2
Image: 'img/chara/SRWI_KyosukeNanbu(A2).bmp'
KyosukeA3:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 攻撃3
Image: 'img/chara/SRWI_KyosukeNanbu(A3).bmp'
KyosukeAngry:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 怒り
Image: 'img/chara/SRWI_KyosukeNanbu(Angry).bmp'
KyosukeD:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: ダメージ
Image: 'img/chara/SRWI_KyosukeNanbu(D).bmp'
KyosukeD2:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: ダメージ2
Image: 'img/chara/SRWI_KyosukeNanbu(D2).bmp'
KyosukeSad:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 悲しみ
Image: 'img/chara/SRWI_KyosukeNanbu(Sad).bmp'
KyosukeSmile:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 笑顔
Image: 'img/chara/SRWI_KyosukeNanbu(Smile).bmp'
KyosukeSmile2:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 微笑
Image: 'img/chara/SRWI_KyosukeNanbu(Smile2).bmp'
KyosukeSurprised:
Name: キョウスケ・ナンブ
NickName: キョウスケ
Aspect: 驚き
Image: 'img/chara/SRWI_KyosukeNanbu(Surprised).bmp'
Exellen:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 通常
Image: 'img/chara/SRWI_ExellenBrowning.bmp'
ExellenA:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 攻撃
Image: 'img/chara/SRWI_ExellenBrowning(A).bmp'
ExellenA2:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 攻撃2
Image: 'img/chara/SRWI_ExellenBrowning(A2).bmp'
ExellenAngry:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 怒り
Image: 'img/chara/SRWI_ExellenBrowning(Angry).bmp'
ExellenAngry2:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 怒り2
Image: 'img/chara/SRWI_ExellenBrowning(Angry2).bmp'
ExellenD:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: ダメージ
Image: 'img/chara/SRWI_ExellenBrowning(D).bmp'
ExellenE:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 回避
Image: 'img/chara/SRWI_ExellenBrowning(E).bmp'
ExellenGrin:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: にやけ
Image: 'img/chara/SRWI_ExellenBrowning(Grin).bmp'
ExellenSad:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 悲しみ
Image: 'img/chara/SRWI_ExellenBrowning(Sad).bmp'
ExellenSerious:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 真剣
Image: 'img/chara/SRWI_ExellenBrowning(Serious).bmp'
ExellenSmile:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 笑顔
Image: 'img/chara/SRWI_ExellenBrowning(Smile).bmp'
ExellenSmile2:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 笑顔2
Image: 'img/chara/SRWI_ExellenBrowning(Smile2).bmp'
ExellenSurprised:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 驚き
Image: 'img/chara/SRWI_ExellenBrowning(Surprised).bmp'
ExellenSweat:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 汗ジト
Image: 'img/chara/SRWI_ExellenBrowning(Sweat).bmp'
ExellenControl:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: 洗脳
Image: 'img/chara/SRWI_ExellenBrowning(Control).bmp'
ExellenEinst:
Name: エクセレン・ブロウニング
NickName: エクセレン
Aspect: アインスト
Image: 'img/chara/SRWI_ExellenBrowning(Einst).bmp'
Bullet:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: 通常
Image: 'img/chara/SRWA_BrooklinRackfield.bmp'
BulletA:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: 攻撃
Image: 'img/chara/SRWA_BrooklinRackfield(A).bmp'
BulletAngry:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: 怒り
Image: 'img/chara/SRWA_BrooklinRackfield(Angry).bmp'
BulletD:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: ダメージ
Image: 'img/chara/SRWA_BrooklinRackfield(D).bmp'
BulletDiscouraged:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: 落胆
Image: 'img/chara/SRWA_BrooklinRackfield(Discouraged).bmp'
BulletEyesClose:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: 瞑目
Image: 'img/chara/SRWA_BrooklinRackfield(EyesClose).bmp'
BulletSmile:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: 笑顔
Image: 'img/chara/SRWA_BrooklinRackfield(Smile).bmp'
BulletSurprise:
Name: ブルックリン・ラックフィールド
NickName: ブリット
Aspect: 驚き
Image: 'img/chara/SRWA_BrooklinRackfield(Surprise).bmp'
Script:
- Character: ExellenA
Speeches:
-
- 「たいちょー」
-
- 「何もあんな手際良く撤収する事無かったと思いまーす」
- Character: Kyosuke
Speeches:
-
- 「足場の悪い山肌で残骸集めのバイトがしたかったのか、お前は?」
- Character: ExellenSweat
Speeches:
-
- 「ぬう……今のシフトだとその待遇も悪くない気すらする……」
- Character: ExellenA2
Speeches:
-
- 「……キョウスケ、まじめな話、最近のヘビーローテな勤労状況、
-  作為的なものを感じない?」
- Character: ExellenSweat
Speeches:
-
- 「今週だけで西海岸と東海岸何度往復したよ?」
- Character: BulletSmile
Speeches:
-
- 「仕方ありませんよ。自分達はケネス司令から頼りにされてるみたいですから」
- Character: ExellenSmile
Speeches:
-
- 「わお! 相変わらずのポジティブマンね、ブリット君」
- Character: Exellen
Speeches:
-
- 「でもあのタコ坊主指令がそんな可愛げのある性格してるかしら?」
-
- 「とりあえずこの新型量産機の稼働データはモリモリ集まるわね……
-  どんな感じ? 実際動かして」
- Character: Bullet
Speeches:
-
- 「レスポンス良いですよ。ちょっと軽めに感じるのはテスラ・ドライブのせい
-  なんですかね?」
- Character: Exellen
Speeches:
-
- 「量産型ビルトシュバインて割には、左腕装備八つ裂き光輪じゃないのね。
-  あのヨーヨー、SRXチームのR-2が装備してたやつ?」
- Character: Bullet
Speeches:
-
- 「ええ。モーションパターンもライディース少尉製だと思います」
-
- 「左腕装備はサークル・ザンバーにも換装できるので、右腕装備や小隊編成に
-  合わせてセッティングするんでしょう」
- Character: Exellen
Speeches:
-
- 「うちのチームに回って来るて事は、評価試験中?」
- Character: Kyosuke
Speeches:
-
- 「いや、それはもう済んで、これは先行生産分だ」
-
- 「リオンシリーズに生産ラインを譲って結局30機そこそこしか生産されなかった
-  ゲシュペンストMk-IIの流れを汲む事になるのかもしれんな」
- Character: Exellen
Speeches:
-
- 「ははぁん、成る程……」
- Character: ExellenE
Speeches:
-
- 「でも量産型猪(ビルトシュバイン)てさ」
- Character: ExellenSmile
Speeches:
-
- 「このシックなカラーリングといいうり坊ってカンジよね。
-  ヒヨコちゃんがうり坊の背に乗って突撃とか、無闇にファンシーな景色だわね」
- Character: ExellenSmile2
Speeches:
-
- 「お姉さんがパーソナルマーク考えてあげようか?」
- Character: BulletSurprise
Speeches:
-
- (子ブタちゃんて言われなかっただけマシなんだろうな……)
require 'gosu'
require_relative 'talk_window'
require_relative 'script'
window = TalkWindow.new(ARGV.include?('-f'))
window.script = Script.new(window, 'script.yaml')
window.start
require 'gosu'
class TalkWindow < Gosu::Window
attr_accessor :script
WIDTH = 1080
HEIGHT = 720
BOX_HEIGHT = 160
BOX_TOP = HEIGHT - BOX_HEIGHT
BOX_MARGIN = 20
CHARA_WIDTH = CHARA_HEIGHT = 96
FONT_SIZE = 32
def initialize(fullscreen)
super(WIDTH, HEIGHT, fullscreen)
self.caption = '会話画面テスト'
@mig2p = Gosu::Font.new(self, './fonts/migmix-2p-regular.ttf', FONT_SIZE)
@bg = Gosu::Image.new(self, 'img/bg-sky-16x9.png', false)
@bgm = Gosu::Song.new(self, 'sound/bgm/4-03-loop.ogg')
@bgm.volume = 0.5
@script_color = Gosu::Color.new(0xff, 0xee, 0xee, 0xee)
@script_bg_color_0 = Gosu::Color.new(0x77, 0, 0x44, 0x22)
@script_bg_color_1 = Gosu::Color.new(0x99, 0, 0x44, 0x22)
@script_bg_border_color = Gosu::Color.new(0x11, 0xff, 0xff, 0xff)
@chara_name_bg_color_0 = Gosu::Color.new(0x33, 0xFF, 0xFF, 0xFF)
@chara_name_bg_color_1 = Gosu::Color.new(0x22, 0xFF, 0xFF, 0xFF)
@chara_name_border_color_0 = Gosu::Color.new(0x55, 0xFF, 0xFF, 0xFF)
@chara_name_border_color_1 = Gosu::Color.new(0x33, 0x00, 0x00, 0x00)
@starting = false
@curtain_color_table = (0..16).to_a.map do |level|
alpha = 16 * (16 - level)
alpha = 255 if alpha > 255
Gosu::Color.new(alpha, 0, 0, 0)
end
@curtain_color_index = 16
@closing = false
@ready_to_close = false
@page_index = nil
@page = nil
@current_lines = ['']
@printing_text = false
@ready_to_go_to_next_page = false
end
def update
if @closing
@curtain_color_index -= 1
if @curtain_color_index < 0
@ready_to_close = true
@curtain_color_index = 0
end
elsif @starting
@curtain_color_index += 1
if @curtain_color_index >= 16
@starting = false
next_page
end
elsif @page
@char_index += 1
if @printing_text && @char_index < @page.text.length
if (ch = @page.text[@char_index]) == "\n"
@current_lines << ''
else
@current_lines.last << ch
end
else
@printing_text = false
@ready_to_go_to_next_page = true
end
end
end
def draw
if @bg
@bg.draw(0, 0, 0)
end
draw_script_box
if @page
draw_chara_nick_name(@page.chara)
draw_chara_image(@page.chara)
draw_script(@current_lines)
end
draw_curtain
close if @ready_to_close
end
def draw_script_box
draw_quad(0, BOX_TOP, @script_bg_color_0,
WIDTH, BOX_TOP, @script_bg_color_0,
0, HEIGHT, @script_bg_color_1,
WIDTH, HEIGHT, @script_bg_color_1)
border_left = 2 * BOX_MARGIN + CHARA_WIDTH + 4
border_right = WIDTH - BOX_MARGIN
(BOX_TOP + BOX_MARGIN).step(by: 3, to: HEIGHT - BOX_MARGIN) do |line_y|
draw_quad(border_left, line_y, @script_bg_border_color,
border_right, line_y, @script_bg_border_color,
border_left, line_y + 1, @script_bg_border_color,
border_right, line_y + 1, @script_bg_border_color)
end
end
def draw_chara_nick_name(chara)
box_left = 2 * BOX_MARGIN + CHARA_WIDTH + 4
box_right = box_left + 8 * FONT_SIZE
box_top = BOX_TOP + BOX_MARGIN
box_bottom = box_top + FONT_SIZE
draw_quad(box_left, box_top, @chara_name_bg_color_0,
box_right, box_top, @chara_name_bg_color_0,
box_left, box_bottom, @chara_name_bg_color_1,
box_right, box_bottom, @chara_name_bg_color_1)
draw_quad(box_left, box_top, @chara_name_border_color_0,
box_right - 1, box_top, @chara_name_border_color_0,
box_left, box_top + 1, @chara_name_border_color_0,
box_right - 1, box_top + 1, @chara_name_border_color_0)
draw_quad(box_left, box_top + 1, @chara_name_border_color_0,
box_left + 1, box_top + 1, @chara_name_border_color_0,
box_left, box_bottom - 1, @chara_name_border_color_0,
box_left + 1, box_bottom - 1, @chara_name_border_color_0)
draw_quad(box_left + 1, box_bottom - 1, @chara_name_border_color_1,
box_right, box_bottom - 1, @chara_name_border_color_1,
box_left + 1, box_bottom, @chara_name_border_color_1,
box_right, box_bottom, @chara_name_border_color_1)
draw_quad(box_right - 1, box_top, @chara_name_border_color_1,
box_right, box_top, @chara_name_border_color_1,
box_right - 1, box_bottom - 1, @chara_name_border_color_1,
box_right, box_bottom - 1, @chara_name_border_color_1)
text_left = (2 * BOX_MARGIN + CHARA_WIDTH + 4) + 30
text_top = BOX_TOP + BOX_MARGIN
@mig2p.draw(chara.nick_name, text_left, text_top, 10, 1, 1,
@script_color)
end
def draw_chara_image(chara)
chara_bg_top = BOX_TOP + BOX_MARGIN
chara_bg_right = BOX_MARGIN + CHARA_WIDTH + 2
chara_bg_bottom = chara_bg_top + CHARA_HEIGHT + 2
chara_bg_left = BOX_MARGIN
draw_quad(chara_bg_left, chara_bg_top, @chara_name_border_color_0,
chara_bg_right, chara_bg_top, @chara_name_border_color_0,
chara_bg_left, chara_bg_bottom, @chara_name_border_color_0,
chara_bg_right, chara_bg_bottom, @chara_name_border_color_0)
draw_quad(chara_bg_left, chara_bg_bottom, @chara_name_border_color_1,
chara_bg_right, chara_bg_bottom, @chara_name_border_color_1,
chara_bg_left, chara_bg_bottom + 1, @chara_name_border_color_1,
chara_bg_right, chara_bg_bottom + 1, @chara_name_border_color_1)
draw_quad(chara_bg_right, chara_bg_top, @chara_name_border_color_1,
chara_bg_right + 1, chara_bg_top, @chara_name_border_color_1,
chara_bg_right, chara_bg_bottom + 1, @chara_name_border_color_1,
chara_bg_right + 1, chara_bg_bottom + 1, @chara_name_border_color_1)
chara_top = chara_bg_top + 1
chara_left = chara_bg_left + 1
chara.image.draw(chara_left, chara_top, 10,
CHARA_WIDTH.to_f / chara.image.width,
CHARA_HEIGHT.to_f / chara.image.height)
end
def draw_script(lines)
text_left = (2 * BOX_MARGIN + CHARA_WIDTH + 4) + 8
lines.each.with_index(1) do |line, i|
text_top = BOX_TOP + BOX_MARGIN + i * (FONT_SIZE - 4) + 4
@mig2p.draw(line, text_left, text_top, 10, 1, 1, @script_color)
end
end
def draw_curtain
if @curtain_color_index < 16
draw_quad(0, 0, @curtain_color_table[@curtain_color_index],
WIDTH, 0, @curtain_color_table[@curtain_color_index],
0, HEIGHT, @curtain_color_table[@curtain_color_index],
WIDTH, HEIGHT, @curtain_color_table[@curtain_color_index],
1000)
end
end
def button_down(id)
case id
when Gosu::KbEscape, Gosu::KbQ
close_with_fade_out
end
end
def button_up(id)
case id
when Gosu::KbReturn, Gosu::KbEnter, Gosu::KbRight, Gosu::MsLeft
if !@closing && @page
if @ready_to_go_to_next_page
next_page
else
script_flush
end
end
end
end
def start
raise 'script required' unless @script
@starting = true
@curtain_color_index = -1
@bgm.play(true)
show
end
def close_with_fade_out
@ready_to_go_to_next_page = false
@closing = true
end
def next_page
@page_index = @page_index ? @page_index + 1 : 0
if @page_index >= @script.pages.length
close_with_fade_out
else
@page = @script.pages[@page_index]
@current_lines = ['']
@char_index = -1
@printing_text = true
@ready_to_go_to_next_page = false
end
end
def script_flush
@current_lines = @page.text.split("\n")
@char_index = @page.text.length
@printing_text = false
@ready_to_go_to_next_page = true
end
def script=(new_script)
@script = new_script
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment