#!/usr/bin/python
#
# Command-line dice roller

import sys
sys.path.append('lib/')

from dice import Dice
import random
import argparse
        
        
# This takes command-line input as dice description strings
# and builds a list of Dice objects
def parse_input(args):
    dice_list = []
    for arg in args:
        dice_list.append(Dice.from_str(arg))

    return dice_list


def parse_args():
    parser = argparse.ArgumentParser(description='Roll dice based on descriptions passed in on the command line', formatter_class=argparse.RawTextHelpFormatter)
    parser.add_argument('--repeat', '-r', metavar='N', type=int, default=1, help='repeat the given rolls N times')
    parser.add_argument('--verbose', '-v', action='store_true', help='print detailed information about each roll')
    parser.add_argument('dice', nargs=argparse.REMAINDER, help="""
Dice are input in the following form:

XdY[modifiers]

This will roll X Y-sided dice and apply the specified modifiers.

Modifiers can be any of the following (where N and M are integers):

(+|-)N   Add or subtract N from the total
lN       Drop the lowest-rolling N dice from the total
hN       Drop the highest-rolling N dice from the total
rN[xM]   Any dice that roll <= N will be rerolled.
         If the optional 'xM' option is specified, dice will be rerolled a maximum of M times.
         Otherwise each die will be rerolled until the result is > N

Examples:

1d20+5      roll 1 twenty-sided die, and add 5 to the result
6d6l1h1     roll 6 six-sided dice, and drop both the highest and the lowest roll
4d6l1r2x1   roll 4 six-sided dice. Any dice rolling a 1 or 2 will be rerolled once.
            If the result is still 1 or 2 it is kept. The lowest die is dropped from the result
""")
    return parser.parse_args()
    


def main():
    settings = parse_args()
    dice_list = parse_input(settings.dice)

    for i in range(settings.repeat):
        for dice in dice_list:
            ret = dice.roll()

            if settings.verbose:
                drop_info = ''
                reroll_info = ''

                if ret['dropped']:
                    drop_info = ' [dropped {}]'.format(','.join(['{}'.format(x) for x in ret['dropped']]))
                if ret['rerolled']:
                    reroll_info = ' [rerolled {}]'.format(','.join(['{}'.format(x) for x in ret['rerolled']]))
                
                print('{dice}: {rolls}{drop}{reroll} {total}'.format(dice=dice, rolls=ret['rolls'], total=ret['total'], drop=drop_info, reroll=reroll_info))

            else:
                print('{dice}: {total}'.format(dice=dice, total=ret['total']))


if __name__ == '__main__':
    main()