Anydice.com is good for simple things, but I don't understand how to calculate probabilities for "If the lowest die is a 3 then roll an extra die unless.." rules that you sometime have in board games.

Here is a Javascript program that rolls dice with any number of sides, any number on each face of the dice, and any kind of rules you want to implement. Here I use a "If either die is Zero, re-roll one die that is zero" function, it isn't difficult to program different rules.

The program just makes lots of dice rolls and takes an average.

red = [1, 2, 3, 0, 0, 0], //Red Space Crusade die white = [1, 2, 0, 0, 0, 0], //White Space Crusade die |

2 white Space Crusade dice (see above picture), rerolling one zero value.

2 red Space Crusade dice, rerolling one zero value.

2 D6 dice, simple total.

For example, this function rolls 2 dice and returns the total. The dice can have any number of sides, and any number on each side. You can use if/then/else statements to handle things like doubles or snake eyes.

function rollTwo(colorDie) {//simple total var die1, die2; die1 = rollDie(colorDie); die2 = rollDie(colorDie); return die1 + die2; }The "trials" function takes the dice, number of rolls, and the function to apply:

function trials(diceArray, times, funct) { var i, roll, result = []; for (i = 0; i < times; i++) { roll = funct(diceArray); while (result.length < roll + 1) { result.push(0); } result[roll] = result[roll] + 1; } return result; }The "displayResult" function just creates a display string from the contents of the "result" array.

There is a paragraph in the .html to display the result string.

That's about it.

Sample output:

The rolls were

0: 29.34 %

1: 22.1 %

2: 29.05 %

3: 12.61 %

4: 6.9 %

0: 29.34 %

1: 22.1 %

2: 29.05 %

3: 12.61 %

4: 6.9 %

The rolls were

0: 12.72 %

1: 13.07 %

2: 17.71 %

3: 23.4 %

4: 16.35 %

5: 11.31 %

6: 5.44 %

0: 12.72 %

1: 13.07 %

2: 17.71 %

3: 23.4 %

4: 16.35 %

5: 11.31 %

6: 5.44 %

The rolls were

0: 0 %

1: 0 %

2: 2.75 %

3: 5.64 %

4: 8.24 %

5: 11.06 %

6: 13.89 %

7: 16.21 %

8: 13.78 %

9: 11.36 %

10: 8.79 %

11: 5.51 %

12: 2.77 %

0: 0 %

1: 0 %

2: 2.75 %

3: 5.64 %

4: 8.24 %

5: 11.06 %

6: 13.89 %

7: 16.21 %

8: 13.78 %

9: 11.36 %

10: 8.79 %

11: 5.51 %

12: 2.77 %

The chart gives the same numbers as the text output above it, 7 is 16.21 % (16.67 % is the correct answer) for example.

The program rolls the dice 10,000 times, so you never get exactly the same numbers.

If you copy and paste the text below into a text editor and save it as "whatever.html", you can click on the file and it runs in the browser. Or run the program from here.

<===================== below this line is the program ========================>

<!DOCTYPE html> <html> <body> <p id="white"></p> <p id="red"></p> <p id="d6"></p> <script> var white = [0, 0, 0, 0, 1, 2], //White Space Crusade die red = [0, 0, 0, 3, 1, 2], //Red Space Crusade die d6 = [1, 2, 3, 4, 5, 6], //Normal D6 d10 = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, ], //Normal D10

result; document.getElementById("red").innerHTML = "Calculating"; document.getElementById("white").innerHTML = "Calculating"; document.getElementById("d6").innerHTML = "Calculating"; result = trials(white, 10000, rerollOne); document.getElementById("white").innerHTML = "The rolls were <br>" + displayResult(result, 100) + " "; result = trials(red, 10000, rerollOne); document.getElementById("red").innerHTML = "The rolls were <br>" + displayResult(result, 100) + " "; result = trials(d6, 10000, rollTwo); document.getElementById("d6").innerHTML = "The rolls were <br>" + displayResult(result, 100) + " "; function displayResult(anArray, divide) {//result array, divisor for output to make it look like a percentage var i, limit, str = ""; limit = anArray.length; for (i = 0; i < limit; i++) { str += i; str += ": "; str += anArray[i] / divide; str += " %<br>"; } return str; } function trials(diceArray, times, funct) {//die array, number of iterations, function to use var i, roll, result = []; for (i = 0; i < times; i++) { roll = funct(diceArray); while (result.length < roll + 1) {//make result array bigger if needs be result.push(0); } result[roll] = result[roll] + 1; } return result; } function rollDie(colorDie) {//returns a random die roll result return colorDie[randIndex(colorDie.length)] } function randIndex(num) { return Math.floor((Math.random() * num)); } function rollTwo(colorDie) {//simple total var die1, die2; die1 = rollDie(colorDie); die2 = rollDie(colorDie); return die1 + die2; } function rerollOne(colorDie) {// if one result is zero, reroll it var die1, die2, reroll; die1 = rollDie(colorDie); die2 = rollDie(colorDie); reroll = rollDie(colorDie); if (die1 === 0) { die1 = reroll; //reroll first die if zero } else { if (die2 === 0) { die2 = reroll; //otherwise reroll second die if zero } } return die1 + die2; //total of 2 dice } </script> </body> </html>