フロントエンドプレイアブル
This commit is contained in:
124
app/models/turn.rb
Normal file
124
app/models/turn.rb
Normal file
@@ -0,0 +1,124 @@
|
||||
class Turn < ApplicationRecord
|
||||
belongs_to :game
|
||||
|
||||
# 特定の国の実行可能な命令を取得
|
||||
# 例: turn.possible_orders_for("FRANCE")
|
||||
def possible_orders_for(power_name)
|
||||
possible_orders&.dig("possible_orders", power_name.to_s.upcase)
|
||||
end
|
||||
|
||||
# 特定の国の決定済み命令を取得
|
||||
# 例: turn.orders_for("FRANCE")
|
||||
def orders_for(power_name)
|
||||
# orders は直接ハッシュを保存する場合を想定(必要に応じてネストを調整)
|
||||
orders&.dig(power_name.to_s.upcase)
|
||||
end
|
||||
|
||||
# 命令が存在するすべての国名リストを取得
|
||||
def powers
|
||||
possible_orders&.dig("possible_orders")&.keys || []
|
||||
end
|
||||
|
||||
# 特定の国の命令が提出済みかチェック
|
||||
def orders_submitted_for?(power_name)
|
||||
orders&.key?(power_name.to_s.upcase)
|
||||
end
|
||||
|
||||
# 未提出の国のリストを取得
|
||||
def pending_powers
|
||||
game.participants.where.not(power: nil).map(&:power).reject do |power|
|
||||
orders_submitted_for?(power)
|
||||
end
|
||||
end
|
||||
|
||||
# 自動命令を生成(参加者がいない国用)
|
||||
def generate_auto_orders_for_unassigned_powers
|
||||
unassigned = game.unassigned_powers
|
||||
return if unassigned.empty?
|
||||
|
||||
client = GameApiClient.new
|
||||
current_orders = orders || {}
|
||||
|
||||
unassigned.each do |power|
|
||||
if game.auto_order_mode == "hold"
|
||||
# HOLD命令を生成
|
||||
current_orders[power] = generate_hold_orders(power)
|
||||
else
|
||||
# ランダム命令を生成
|
||||
auto_orders_response = client.api_calculate_auto_orders(game_state, power)
|
||||
if auto_orders_response
|
||||
# APIレスポンスから命令を抽出
|
||||
# レスポンスが {"orders": [...]} の形式の場合
|
||||
if auto_orders_response.is_a?(Hash) && auto_orders_response["orders"]
|
||||
current_orders[power] = auto_orders_response["orders"]
|
||||
elsif auto_orders_response.is_a?(Array)
|
||||
current_orders[power] = auto_orders_response
|
||||
else
|
||||
# フォールバック: HOLD命令を使用
|
||||
current_orders[power] = generate_hold_orders(power)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
update(orders: current_orders)
|
||||
update(orders: current_orders)
|
||||
end
|
||||
|
||||
# 引き分け投票
|
||||
def vote_draw(power_name)
|
||||
current_votes = draw_votes || []
|
||||
power = power_name.to_s.upcase
|
||||
unless current_votes.include?(power)
|
||||
current_votes << power
|
||||
update(draw_votes: current_votes)
|
||||
end
|
||||
end
|
||||
|
||||
# 引き分け投票取り消し
|
||||
def revoke_draw_vote(power_name)
|
||||
current_votes = draw_votes || []
|
||||
power = power_name.to_s.upcase
|
||||
if current_votes.include?(power)
|
||||
current_votes.delete(power)
|
||||
update(draw_votes: current_votes)
|
||||
end
|
||||
end
|
||||
|
||||
# 投票済みかチェック
|
||||
def draw_voted?(power_name)
|
||||
(draw_votes || []).include?(power_name.to_s.upcase)
|
||||
end
|
||||
|
||||
# 全会一致で引き分けかチェック
|
||||
def unanimous_draw?
|
||||
# 生存している国
|
||||
active_powers = powers
|
||||
return false if active_powers.empty?
|
||||
|
||||
# プレイヤーが割り当てられている国のみを対象とする
|
||||
# (未割り当ての国は投票できないため、除外する)
|
||||
assigned_powers = game.participants.where.not(power: nil).pluck(:power).map(&:upcase)
|
||||
|
||||
# 投票権を持つ国 = 生存している かつ プレイヤーがいる
|
||||
eligible_powers = active_powers.map(&:upcase) & assigned_powers
|
||||
|
||||
return false if eligible_powers.empty?
|
||||
|
||||
current_votes = draw_votes || []
|
||||
eligible_powers.all? { |power| current_votes.include?(power) }
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def generate_hold_orders(power)
|
||||
possible = possible_orders_for(power)
|
||||
return {} unless possible
|
||||
|
||||
hold_orders = {}
|
||||
possible.each do |unit, moves|
|
||||
hold_orders[unit] = [ "H" ] if moves.is_a?(Array)
|
||||
end
|
||||
hold_orders
|
||||
end
|
||||
end
|
||||
Reference in New Issue
Block a user