前回記事はこちらです。↓
完成に向けて、ラストスパート!!
後は点数計算を加えるのみとなりました。完成へ向けてラストスパートです!!。
和了りの時のイメージ
和了った時に、次のような画面を表示するために、必要な要素をプログラムに追加していきます。
点数計算プログラム
まずは、点数計算プログラムです。このプログラムを、”point_check.rb”というファイル名で、メインプログラムと同じフォルダ(ディレクトリ)に保存してください。
def mentsu_type_check(m)
mentsu = m
if m.count==2 then
return "雀頭"
elsif m.all?{|x|x==m[0]} then
return "刻子"
else
return "順子"
end
end
def point_check(t,sw,rw,ah,th)
yaku_list=[]
tehai_list = t
point_list = Hash.new
if (sw==31) then
point_list[ 20]=[0, 0, 2000, 3900, 7700,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 25]=[0, 0, 2400, 4800, 9600,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 30]=[0,1500, 2900, 5800,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 40]=[0,2000, 3900, 7700,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 50]=[0,2400, 4800, 9600,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 60]=[0,2900, 5800,12000,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 70]=[0,3400, 6800,12000,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 80]=[0,3900, 7700,12000,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[ 90]=[0,4400, 8700,12000,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[100]=[0,4800, 9600,12000,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
point_list[110]=[0,5300,10600,12000,12000,12000,18000,18000,24000,24000,24000,36000,36000,48000]
yakumann = 48000
else
point_list[ 20]=[0, 0,1300,2600,5200,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 25]=[0, 0,1600,3200,6400,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 30]=[0,1000,2000,3900,7700,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 40]=[0,1300,2600,5200,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 50]=[0,1600,3200,6400,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 60]=[0,2000,3900,7700,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 70]=[0,2300,4500,8000,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 80]=[0,2600,5200,8000,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[ 90]=[0,2900,5800,8000,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[100]=[0,3200,6400,8000,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
point_list[110]=[0,3600,7100,8000,8000,8000,12000,12000,16000,16000,16000,24000,24000,32000]
yakumann = 32000
end
point = 0
round_wind = Array.new
round_wind[31]="東"
round_wind[33]="南"
round_wind[35]="西"
round_wind[37]="北"
#自風
self_wind = Array.new
self_wind[31]="東"
self_wind[33]="南"
self_wind[35]="西"
self_wind[37]="北"
# 役満判定
tehai_list.each do |tehai|
yaku=[]
##地和判定
yaku << ["地和"] if th == true
##国士無双判定
if tehai.count==2 then
yaku << ["国士無双"]
end
##緑一色判定
if ((tehai.flatten-[22,23,24,26,28,43]).empty? == true) then
yaku << ["緑一色"]
end
#清老頭判定
if ((tehai.flatten-[1,9,11,19,21,29]).empty? == true) then
yaku << ["清老頭"]
end
#大三元判定
if ((tehai.include?([41,41,41]) && tehai.include?([43,43,43]) && tehai.include?([45,45,45])) == true) then
yaku << ["大三元"]
end
#四喜和判定
if ((tehai.include?([31,31,31]) && tehai.include?([33,33,33]) && tehai.include?([35,35,35])&& tehai.include?([37,37,37])) == true) then
yaku << ["大四喜"]
elsif(tehai.flatten.count{|x|x > 30 && x < 40} == 11) then
yaku << ["小四喜"]
end
#九連宝燈判定
if((tehai.flatten.all?{|x| x > 0 && x < 10}) || (tehai.flatten.all?{|x| x > 10 && x < 20}) || (tehai.flatten.all?{|x| x > 20 && x < 30})) then
#処理
cp_tehai = []
tehai.each do |x|
t=x.map{|y| y %10 }
cp_tehai << t
end
break if cp_tehai.flatten.count(1) != 3 || cp_tehai.flatten.count(9) != 3
cp_tehai= cp_tehai.flatten - [1,9]
tmp = true
(2..8).each do |x|
tmp = cp_tehai.include?(x)
break if tmp == false
end
break if tmp == false
yaku << ["九連宝燈"]
end
##四暗刻判定(刻子4)
if (mentsu_type_check(tehai[0])=="雀頭")&&(tehai[1..4].all?{|x|mentsu_type_check(x)=="刻子"}) then
yaku << ["四暗刻"]
end
#字一色判定
if (tehai.flatten.all?{|x| x > 30} == true) then
yaku << ["字一色"]
end
yaku.count==1 ? yakumei= "役満" : yakumei="#{yaku.count}倍役満"
yaku_list << [yaku , [yakumann * yaku.count , yakumei]] if yaku.count!=0
end #tehai_list.each 役満判定
if yaku_list.count!=0 then
#点数が高い方を返す
y = yaku_list.max_by{ |t| t[1][0]}
return y
end
#通常役判定
tehai_list.each do |tehai|
fu =20 + 2 #面前自摸和了り限定
yaku=[]
yaku << ["門前清自摸和",1]
#役牌判定
yaku << ["自風 #{self_wind[sw]}",1] if (tehai.include?([sw,sw,sw]))
yaku << ["場風 #{round_wind[sw]}",1] if (tehai.include?([rw,rw,rw]))
yaku << ["役牌 白",1] if (tehai.include?([41,41,41]))
yaku << ["役牌 發",1] if (tehai.include?([43,43,43]))
yaku << ["役牌 中",1] if (tehai.include?([45,45,45]))
#七対子判定
yaku << ["七対子",2] if(tehai.count==7)
#三暗刻判定
yaku << ["三暗刻",2] if(tehai.count{|m| mentsu_type_check(m)=="刻子"} == 3)
#一気通貫判定
if ((([[1,2,3],[4,5,6],[7,8,9]]-tehai).empty?) || (([[11,12,13],[14,15,16],[17,18,19]]-tehai).empty?) || (([[21,22,23],[24,25,26],[27,28,29]]-tehai).empty?)) then
yaku << ["一気通貫",2]
end
#三色同順判定
(1..7).each do |h|
if(([[h,h+1,h+2,],[h+10,h+11,h+12],[h+20,h+21,h+22]]-tehai).empty?) then
yaku <<["三色同順",2]
break
end
end
#三色同刻判定
(1..9).each do |h|
if(([[h,h,h,],[h+10,h+10,h+10],[h+20,h+20,h+20]]-tehai).empty?) then
yaku <<["三色同刻",2]
break
end
end
#小三元判定
yaku << ["小三元",2] if(tehai.flatten.count{|x|x > 40 && x < 50} == 8)
#一色判定
##清一色判定
if((tehai.flatten.all?{|x| x > 0 && x < 10}) || (tehai.flatten.all?{|x| x > 10 && x < 20}) || (tehai.flatten.all?{|x| x > 20 && x < 30})) then
yaku << ["清一色",6]
##混一色判定
elsif((tehai.flatten.all?{|x| x > 0 && x < 10 || x > 30}) || (tehai.flatten.all?{|x| x > 10 && x < 20 || x > 30}) || (tehai.flatten.all?{|x| x > 20})) then
yaku << ["混一色",3]
end
#盃口系判定
##二盃口判定
if ((mentsu_type_check(tehai[0])=="雀頭")&&(tehai[1..4].all?{|x|mentsu_type_check(x)=="順子"}) && (tehai[1]==tehai[2]) && (tehai[3]==tehai[4])) then
yaku << ["二盃口",3]
##一盃口判定
elsif ((mentsu_type_check(tehai[1])=="順子" && (tehai.count(tehai[1]) == 2)) || (mentsu_type_check(tehai[2])=="順子" && (tehai.count(tehai[2]) == 2)) || (mentsu_type_check(tehai[3])=="順子" && (tehai.count(tehai[3]) == 2))) then
yaku << ["一盃口",1]
end
#帯么老頭系判定
##混老頭判定
if ((tehai.flatten - [1,9,11,19,21,29,31,33,35,37,41,43,45]).empty?) then
yaku << ["混老頭",2]
##純全帯么判定
elsif(((tehai-[[1,1,1],[9,9,9],[11,11,11],[19,19,19],[21,21,21],[29,29,29],[1,2,3],[7,8,9],[11,12,13],[17,18,19],[21,22,23],[27,28,29]]).flatten - [1,9,11,19,21,29]).empty?) then
yaku << ["純全帯么",3]
##全帯么判定
elsif(((tehai-[[1,1,1],[9,9,9],[11,11,11],[19,19,19],[21,21,21],[29,29,29],[1,2,3],[7,8,9],[11,12,13],[17,18,19],[21,22,23],[27,28,29],[31,31,31],[33,33,33],[35,35,35],[37,37,37],[41,41,41],[43,43,43],[45,45,45]]).flatten - [1,9,11,19,21,29,31,33,35,37,41,43,45]).empty?) then
yaku << ["全帯么",2]
end
#断么九判定
if ((tehai.flatten - [2,3,4,5,6,7,8,12,13,14,15,16,17,18,22,23,24,25,26,27,28]).empty?) then
yaku << ["断么九",1]
end
#平和判定
#1.全て順子
if (mentsu_type_check(tehai[0])=="雀頭")&&(tehai[1..4].all?{|x|mentsu_type_check(x)=="順子"}) then
#2.雀頭が役牌ではない
if(tehai[0]!=[sw,sw] && tehai[0]!=[rw,rw] && tehai[0][0] < 40) then
#3.両面待ち
if( ((tehai[1][0] == ah) && ah % 10 != 7) || ((tehai[1][2] == ah) && ah % 10 != 3) || ((tehai[2][0] == ah) && ah % 10 != 7) || ((tehai[2][2] == ah) && ah % 10 != 3) || ((tehai[3][0] == ah) && ah % 10 != 7) || ((tehai[3][2] == ah) && ah % 10 != 3) || ((tehai[4][0] == ah) && ah % 10 != 7) || ((tehai[4][2] == ah) && ah % 10 != 3) ) then
yaku << ["平和",1]
end
end
end
#符計算
if (yaku.include?( ["七対子",2])) then
fu = 25
elsif (yaku.include?( ["平和",1])) then
fu = 20
else
#雀頭
if (tehai[0]==[41,41])||(tehai[0]==[43,43])||(tehai[0]==[45,45]) then
fu += 2
elsif (tehai[0]==[rw,rw]) then
fu += 2
elsif (tehai[0]==[sw,sw]) then
fu += 2
end
#刻子
tehai.each do |t|
if (mentsu_type_check(t)=="刻子") then
if (t.include?(1 || 9 || 11 || 19 || 21 || 29 || 31 || 33 || 35 || 37 || 41 || 43 ||45)) then
fu += 8
else
fu += 4
end
end
end
#和了り形
##単騎
if tehai[0]==[ah,ah] then
fu +=2
else
tehai.each do |t|
if (mentsu_type_check(t)=="順子") then
#嵌張
if (t[1]== ah) then
fu += 2
else
#辺張
[0,10,20].each do |x|
if ((t == [x+1,x+2,x+3] && ah == (x+3)) || (t == [x+7,x+8,x+9] && ah == (x+7))) then
fu +=2
end
end
end
end
end
end
#符の繰り上げ
fu = fu / 10.0
fu = fu.ceil
fu =fu * 10
fu = fu.to_i
end
han =0
yaku.map{|x|han += x[1]}
han = 13 if han > 14
yaku_list << [yaku,[point_list[fu][han],[han,fu]]] if yaku.count!=0
end #tehai_list.each 通常役判定
if yaku_list.count!=0 then
#点数が高い方を返す
y = yaku_list.max_by{ |t| t[1][0]}
return y
end
end
if文の羅列による条件分岐がメインの、力技のプログラムになっています。(;^ω^)
“point_check”関数には5つの引数を使用していて、内容は以下のようになっています。
- t : 手牌(和了判定プログラム”agari_check”の返り値)
- sw : 自風
- rw : 場風
- ah : 和了り牌
- th : 地和判定
点数計算において、字牌は自風と場風は役牌になる場合とならない場合があるため判定が必要で、
平和においては和了り方が両面待ちであるかどうかと、雀頭が役牌でないことを確認することが必要なため、このような引数になっています。
また、配牌直後で、和了り形ができていた場合は「地和」とするため、地和判定用の変数を用意します。
次に、“point_check”関数の返り値は、次のようになっていて、役満と通常役で若干違いがあります。
#役満
[役リスト, [点数, 役表示用文字列("役満" or "〇倍役満")]]
#通常役
[役リスト, [点数,[飜数,符]]]
このプログラムを使用するため、ゲームプログラムのはじめを、以下のように変更します。
require 'dxruby'
require_relative './agari_check.rb'
require_relative './point_check.rb' #←追加
これで、和了りの時に表示する情報を用意することができました。
次回は、点数計算時のプログラムを追加します。
次回記事は、こちらです。↓
コメント