diff --git a/lib/bcdice/game_system/DungeonsAndDragons5.rb b/lib/bcdice/game_system/DungeonsAndDragons5.rb index 9d55e8ada..0d387494b 100644 --- a/lib/bcdice/game_system/DungeonsAndDragons5.rb +++ b/lib/bcdice/game_system/DungeonsAndDragons5.rb @@ -14,17 +14,19 @@ class DungeonsAndDragons5 < Base # ダイスボットの使い方 HELP_MESSAGE = <<~INFO_MESSAGE_TEXT - ・攻撃ロール AT[x][@c][>=t][y] + ・攻撃ロール AT[x][@c][>=t][y][B]  x:+-修正。省略可。  c:クリティカル値。省略可。  t:敵のアーマークラス。>=を含めて省略可。  y:有利(A), 不利(D)。省略可。 +  B:(B)ブレスやガイダンスによる+1d4。省略可。  ファンブル/失敗/成功/クリティカル を自動判定。  例)AT AT>=10 AT+5>=18 AT-3>=16 ATA AT>=10A AT+3>=18A AT-3>=16 ATD AT>=10D AT+5>=18D AT-5>=16D -   AT@19 AT+5@18 AT-2@19>=15 - ・能力値判定 AR[x][>=t][y] +   AT@19 AT+5@18 AT-2@19>=15 AT+3>=18AB AT+3>=18DB + ・能力値判定 AR[x][>=t][y][b]  攻撃ロールと同様。失敗/成功を自動判定。  例)AR AR>=10 AR+5>=18 AR-3>=16 ARA AR>=10A AR+3>=18A AR-3>=16 ARD AR>=10D AR+5>=18D AR-5>=16D +   AR+3>=18AB AR+3>=18DB ・両手持ちのダメージ 2HnDx[m]  n:ダイスの個数  x:ダイスの面数 @@ -33,7 +35,7 @@ class DungeonsAndDragons5 < Base  例)2H3D6 2H1D10+3 2H2D8-1 INFO_MESSAGE_TEXT - register_prefix('AT([+-]\d+)?(@\d+)?(>=\d+)?[AD]?', 'AR([+-]\d+)?(>=\d+)?[AD]?', '2H(\d+)D(\d+)([+-]\d+)?') + register_prefix('AT', 'AR', '2H') def initialize(command) super(command) @@ -57,17 +59,27 @@ def number_with_sign_from_int(number) # 攻撃ロール def attack_roll(command) - m = /^AT([-+]\d+)?(@(\d+))?(>=(\d+))?([AD]?)/.match(command) + m = /^AT([-+\d]+)?(@(\d+))?(>=(\d+))?([AD]?)6?(B?)/.match(command) unless m return nil end - modify = m[1].to_i + if m[1] + if Arithmetic.eval(m[1], @round_type) + modify = Arithmetic.eval(m[1], @round_type) + else + return nil + end + else + modify = 0 + end critical_no = m[3].to_i difficulty = m[5].to_i advantage = m[6] + bonus = m[7] usedie = 0 + bonus_mod = 0 roll_die = "" dice_command = "AT#{number_with_sign_from_int(modify)}" @@ -82,6 +94,9 @@ def attack_roll(command) unless advantage.empty? dice_command += advantage.to_s end + if bonus == "B" + dice_command += bonus.to_s + end output = ["(#{dice_command})"] @@ -98,14 +113,28 @@ def attack_roll(command) end end + if bonus == "B" + bonus_mod = @randomizer.roll_once(4).to_i + end + if modify != 0 - output.push("#{roll_die}#{number_with_sign_from_int(modify)}") - output.push((usedie + modify).to_s) + if bonus_mod != 0 + output.push("#{roll_die}#{number_with_sign_from_int(modify)}#{number_with_sign_from_int(bonus_mod)}") + output.push((usedie + modify + bonus_mod).to_s) + else + output.push("#{roll_die}#{number_with_sign_from_int(modify)}") + output.push((usedie + modify).to_s) + end else - unless advantage.empty? - output.push(roll_die) + if bonus_mod != 0 + output.push("#{roll_die}#{number_with_sign_from_int(bonus_mod)}") + output.push((usedie + bonus_mod).to_s) + else + unless advantage.empty? + output.push(roll_die) + end + output.push(usedie.to_s) end - output.push(usedie.to_s) end result = Result.new @@ -117,7 +146,7 @@ def attack_roll(command) result.fumble = true output.push(translate('fumble')) elsif difficulty > 0 - if usedie + modify >= difficulty + if usedie + modify + bonus_mod >= difficulty result.success = true output.push(translate('success')) else @@ -139,16 +168,18 @@ def attack_roll(command) # 能力値ロール def ability_roll(command) - m = /^AR([-+]\d+)?(>=(\d+))?([AD]?)/.match(command) + m = /^AR([-+\d]+)?(>=(\d+))?([AD]?)(B?)/.match(command) unless m return nil end - modify = m[1].to_i + modify = m[1] ? Arithmetic.eval(m[1], @round_type) : 0 difficulty = m[3].to_i advantage = m[4] + bonus = m[5] usedie = 0 + bonus_mod = 0 roll_die = "" dice_command = "AR#{number_with_sign_from_int(modify)}" @@ -158,6 +189,9 @@ def ability_roll(command) unless advantage.empty? dice_command += advantage.to_s end + if bonus == "B" + dice_command += bonus.to_s + end output = ["(#{dice_command})"] @@ -174,19 +208,33 @@ def ability_roll(command) end end + if bonus == "B" + bonus_mod = @randomizer.roll_once(4).to_i + end + if modify != 0 - output.push("#{roll_die}#{number_with_sign_from_int(modify)}") - output.push((usedie + modify).to_s) + if bonus_mod != 0 + output.push("#{roll_die}#{number_with_sign_from_int(modify)}#{number_with_sign_from_int(bonus_mod)}") + output.push((usedie + modify + bonus_mod).to_s) + else + output.push("#{roll_die}#{number_with_sign_from_int(modify)}") + output.push((usedie + modify).to_s) + end else - unless advantage.empty? - output.push(roll_die) + if bonus_mod != 0 + output.push("#{roll_die}#{number_with_sign_from_int(bonus_mod)}") + output.push((usedie + bonus_mod).to_s) + else + unless advantage.empty? + output.push(roll_die) + end + output.push(usedie.to_s) end - output.push(usedie.to_s) end result = Result.new if difficulty > 0 - if usedie + modify >= difficulty + if usedie + modify + bonus_mod >= difficulty result.success = true output.push(translate('success')) else @@ -208,14 +256,14 @@ def ability_roll(command) # 武器の両手持ちダメージ def twohands_damage_roll(command) - m = /^2H(\d+)D(\d+)([+-]\d+)?/.match(command) + m = /^2H(\d+)D(\d+)([-+\d]+)?/.match(command) unless m return nil end dice_count = m[1].to_i dice_number = m[2].to_i - modify = m[3].to_i + modify = m[3] ? Arithmetic.eval(m[3], @round_type) : 0 mod_str = number_with_sign_from_int(modify) output = ["(2H#{dice_count}D#{dice_number}#{mod_str})"] diff --git a/test/data/DungeonsAndDragons5.toml b/test/data/DungeonsAndDragons5.toml index faf766bc3..52335483a 100644 --- a/test/data/DungeonsAndDragons5.toml +++ b/test/data/DungeonsAndDragons5.toml @@ -56,6 +56,13 @@ rands = [ { sides = 20, value = 1 }, ] +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AT+ 加減算記号のみで数字のない不正入力時の処理確認" +output = "" +rands = [ +] + [[ test ]] game_system = "DungeonsAndDragons5" @@ -175,6 +182,24 @@ rands = [ { sides = 20, value = 19 }, ] +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AT+2+3>=10 加減算修正の表示確認" +output = "(AT+5>=10) > 19+5 > 24 > 成功" +success = true +rands = [ + { sides = 20, value = 19 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AT+7-2>=10 加減算修正の表示確認" +output = "(AT+5>=10) > 19+5 > 24 > 成功" +success = true +rands = [ + { sides = 20, value = 19 }, +] + [[ test ]] game_system = "DungeonsAndDragons5" input = "AT+3>=10 クリティカルの表示確認" @@ -296,6 +321,47 @@ rands = [ ] +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "ATB ボーナスの表示確認" +output = "(ATB) > 2+3 > 5" +rands = [ + { sides = 20, value = 2 }, + { sides = 4, value = 3 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AT+3>=18B ボーナスの表示確認" +output = "(AT+3>=18B) > 2+3+3 > 8 > 失敗" +failure = true +rands = [ + { sides = 20, value = 2 }, + { sides = 4, value = 3 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AT-3>=14B" +output = "(AT-3>=14B) > 18-3+3 > 18 > 成功" +success = true +rands = [ + { sides = 20, value = 18 }, + { sides = 4, value = 3 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AT-3>=15DB" +output = "(AT-3>=15DB) > [18,3]-3+3 > 3 > 失敗" +failure = true +rands = [ + { sides = 20, value = 18 }, + { sides = 20, value = 3 }, + { sides = 4, value = 3 }, +] + + [[ test ]] game_system = "DungeonsAndDragons5" input = "AR コマンドのみの表示確認" @@ -407,6 +473,24 @@ rands = [ { sides = 20, value = 19 }, ] +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AR+2+3>=10 加減算修正の表示確認" +output = "(AR+5>=10) > 19+5 > 24 > 成功" +success = true +rands = [ + { sides = 20, value = 19 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AR+5-10>=10 加減算修正の表示確認" +output = "(AR-5>=10) > 19-5 > 14 > 成功" +success = true +rands = [ + { sides = 20, value = 19 }, +] + [[ test ]] game_system = "DungeonsAndDragons5" input = "ARA 有利の表示確認" @@ -467,6 +551,36 @@ rands = [ ] +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "ARB ボーナスの表示確認" +output = "(ARB) > 3+3 > 6" +rands = [ + { sides = 20, value = 3 }, + { sides = 4, value = 3 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AR>=10B 失敗の表示確認" +output = "(AR>=10B) > 3+3 > 6 > 失敗" +failure = true +rands = [ + { sides = 20, value = 3 }, + { sides = 4, value = 3 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "AR>=10B 成功の表示確認" +output = "(AR>=10B) > 19+3 > 22 > 成功" +success = true +rands = [ + { sides = 20, value = 19 }, + { sides = 4, value = 3 }, +] + + [[ test ]] game_system = "DungeonsAndDragons5" input = "2H3D6 両手持ちダメージ、振り直しなし、修正なし" @@ -497,6 +611,26 @@ rands = [ { sides = 6, value = 3 }, ] +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "2H3D6+1+2 振り直しなし、加減算修正" +output = "(2H3D6+3) > [3,4,5]+3 > 15" +rands = [ + { sides = 6, value = 3 }, + { sides = 6, value = 4 }, + { sides = 6, value = 5 }, +] + +[[ test ]] +game_system = "DungeonsAndDragons5" +input = "2H3D6-10+5 振り直しなし、加減算修正" +output = "(2H3D6-5) > [5,4,3]-5 > 7" +rands = [ + { sides = 6, value = 5 }, + { sides = 6, value = 4 }, + { sides = 6, value = 3 }, +] + [[ test ]] game_system = "DungeonsAndDragons5" input = "2H3D6 振り直しあり、修正なし"