import argparse
import os.path
import random

import cv2
from PIL import Image, ImageDraw, ImageFont
from tqdm import tqdm


def add_space(str):
    temp_str = ''
    if len(str) <= 6:
        num_of_space = (3 * (6 - len(str))) / (len(str) - 1)
        for i in range(0, len(str) - 1):
            temp_str += str[i]
            for j in range(0, int(num_of_space)):
                temp_str += ' '
        temp_str += str[len(str) - 1]
        return temp_str


def generate_idcard(name_dir, bingyi_dir, addr_dir, id_dir, save_dir, generate_num, bg_dir, font_dir):
    if not os.path.exists(save_dir):
        os.makedirs(save_dir)

    fp_name = open(name_dir, 'r', encoding='utf-8')
    fp_bingyi = open(bingyi_dir, 'r', encoding='utf-8')
    fp_addr= open(addr_dir, 'r', encoding='utf-8')
    fp_id = open(id_dir, 'r', encoding='utf-8')

    # 姓名列表
    name_list = []
    for name in fp_name.readlines():
        name_list.append(name.rstrip('\n').replace(" ", ''))
    # print(name_list)
    # 兵役選項
    bingyi_list = []
    for bingyi in fp_bingyi.readlines():
        bingyi_list.append(bingyi[2:].rstrip('\n'))

    # 出生地及住址
    addr_list = []
    for addr in fp_addr.readlines():
        addr = addr.rstrip('\n')
        ll = addr.split(',')
        addr_temp = ll[1] + ll[0]
        addr_list.append(addr_temp)

    # 編號
    id_list = []
    for id in fp_id.readlines():
        id_list.append(id.rstrip('\n'))
    cnt = 2401
    for i in tqdm(range(0, generate_num)):
        name_father_id = random.randint(0, len(name_list) - 1)
        name_mother_id = random.randint(0, len(name_list) - 1)
        name_couple_id = random.randint(0, len(name_list) - 1)
        bingyi_id = random.randint(0, len(bingyi_list) - 1)
        addr_id = random.randint(0, len(addr_list) - 1)
        id_id = random.randint(0, len(id_list) - 1)

        # 父母親及配偶姓名
        name_father = name_list[name_father_id]
        name_mother = name_list[name_mother_id]
        name_couple = name_list[name_couple_id]

        # 兵役
        bingyi = bingyi_list[bingyi_id]

        # 住址
        addr = addr_list[addr_id]

        n = random.randint(0, 1)
        if n == 0:
            # 出生地
            birth_place = '臺灣省' + addr[0:3]
        # 县或市为出生地
        else:
            birth_place = addr[0:3]

        # 編號
        id = id_list[id_id]

        # 获取背景图列表
        bg_img_name_list = os.listdir(bg_dir)
        bg_path_list = []
        for bg_img_name in bg_img_name_list:
            bg_path_list.append(bg_dir + '/' + bg_img_name)
        # 每次随机取背景图
        bg_path = bg_path_list[random.randint(0, len(bg_path_list) - 1)]
        pil_image = Image.open(bg_path)
        # pil_image 接收住这个图片对象
        # width 为图片的宽, height为图片的高

        width, height = pil_image.size
        # 生成一张尺寸为 width * height  背景色为白色的图片
        bg = Image.new('RGB', (width, height), color=(0, 0, 0))

        bg.paste(pil_image, (0, 0))  # 写入底图
        name_font_size = 35
        # 姓名中加入间隔
        name_father = add_space(name_father)
        name_mother = add_space(name_mother)
        name_couple = add_space(name_couple)

        temp_str = ''
        for i in range(0, len(addr) - 1):
            temp_str += addr[i]
            temp_str += ' '
        temp_str += addr[len(addr) - 1]

        addr = temp_str

        font_name_list = os.listdir(font_dir)
        font_path_list = []
        for font_name in font_name_list:
            font_path_list.append(font_dir + '/' + font_name)
        # 每次随机字体
        font_path = font_path_list[random.randint(0, len(font_path_list) - 1)]

        name_font = ImageFont.truetype(font_path, name_font_size)  # 设置名字字体和大小
        addr_font = ImageFont.truetype(font_path, 23)
        id_font = ImageFont.truetype('OpticalBBold.otf', 28)
        # # 计算出要写入的文字占用的像素
        # # 创建一个可以在给定图像上绘图的对象
        draw = ImageDraw.Draw(bg)

        # 设置配偶及役别数据项为空
        rand_bingyi = random.randint(0, 1)
        rang_spouse = random.randint(0, 1)
        if rand_bingyi == 0:
            bingyi=''
        if rang_spouse == 0:
            name_couple = ''

        draw.text((110, 17), name_father, fill="#444444", font=name_font)
        draw.text((415, 17), name_mother, fill="#444444", font=name_font)
        draw.text((115, 82), name_couple, fill="#444444", font=name_font)
        draw.text((415, 82), bingyi, fill="#444444", font=name_font)
        draw.text((115, 147), birth_place, fill="#444444", font=name_font)
        draw.text((115, 210), addr[0:24], fill="#444444", font=addr_font)
        draw.text((115, 240), addr[24:], fill="#444444", font=addr_font)
        draw.text((455, 377), id, fill="#42A329", font=id_font)

        path_list = []
        # 保存画布
        img_path = save_dir + '/idcard_back' + str(cnt) + '.png'
        cnt += 1
        # img_path = save_dir + '/idcard_' + str(cnt) + '_mask.png'
        bg.save(img_path, "PNG")

        path_list.append(img_path)

        boxes = []

        box_name_father = [105, 17, 305, 62]
        box0 = []
        box0.append(box_name_father)
        box0.append(name_father.replace(' ', ''))
        box0.append('father_name')
        boxes.append(box0)

        box_name_mother = [410, 17, 610, 62]
        box1 = []
        box1.append(box_name_mother)
        box1.append(name_mother.replace(' ', ''))
        box1.append('mother_name')
        boxes.append(box1)

        box_name_spouse = [110, 82, 310, 127]
        box2 = []
        box2.append(box_name_spouse)
        box2.append(name_couple.replace(' ', ''))
        box2.append('spouse_name')
        boxes.append(box2)

        box_birth_place = [110, 147, 335, 190]
        box3 = []
        box3.append(box_birth_place)
        box3.append(birth_place.replace(' ', ''))
        box3.append('birth_place')
        boxes.append(box3)

        box_bingyi = [410, 82, 610, 125]
        box4 = []
        box4.append(box_bingyi)
        box4.append(bingyi.replace(' ', ''))
        box4.append('level')
        boxes.append(box4)

        box_id = [450, 377, 655, 410]
        box5 = []
        box5.append(box_id)
        box5.append(id.replace(' ', ''))
        box5.append('number')
        boxes.append(box5)

        num = 1
        # fp = open(save_dir + '/rec_gt.txt', 'a', encoding='utf-8')
        fp1 = open(save_dir + '/Label.txt', 'a', encoding='utf-8')
        for path in path_list:
            # print(path)
            jishu = 1
            anno = str(path).split('/')[-1] + '\t['
            for box in boxes:
                if jishu <= 6:
                    if jishu == 6:
                        s = '{"transcription": "' + box[1] + '", "points": [[' + str(box[0][0]) + ', ' + str(box[0][1]) + '], [' + str(box[0][2]) + ', ' + str(box[0][1]) + '], [' + str(box[0][2]) + ', ' + str(box[0][3]) + '], [' + str(box[0][0]) + ', ' + str(box[0][3]) + ']], "difficult": false, "key_cls": "' + box[2] + '"}'
                    else:
                       s = '{"transcription": "' + box[1] + '", "points": [[' + str(box[0][0]) + ', ' + str(
                            box[0][1]) + '], [' + str(box[0][2]) + ', ' + str(box[0][1]) + '], [' + str(
                            box[0][2]) + ', ' + str(box[0][3]) + '], [' + str(box[0][0]) + ', ' + str(
                            box[0][3]) + ']], "difficult": false, "key_cls": "' + box[2] + '"}, '
                    anno += s
                # image_cut_save(path, box[0][0], box[0][1], box[0][2], box[0][3], save_dir + '/crop_imgs/' + str(path).split('/')[-1].split('.')[0] + '_' + str(num) + '.png')
                # line = 'crop_imgs/' + str(path).split('/')[-1].split('.')[0] + '_' + str(num) + '.png' + '\t' + box[1] + '\n'
                # fp.write(line)
                num += 1
                jishu += 1
            anno += ']\n'
            fp1.write(anno)
            # print(anno)
        fp1.close()
        # fp.close()
    fp_name.close()
    fp_bingyi.close()
    fp_addr.close()
    fp_id.close()
    return


def image_cut_save(path, left, upper, right, lower, save_path):
    """
        所截区域图片保存
    :param path: 图片路径
    :param left: 区块左上角位置的像素点离图片左边界的距离
    :param upper：区块左上角位置的像素点离图片上边界的距离
    :param right：区块右下角位置的像素点离图片左边界的距离
    :param lower：区块右下角位置的像素点离图片上边界的距离
     故需满足：lower > upper、right > left
    :param save_path: 所截图片保存位置
    """
    img = cv2.imread(path)  # 打开图像
    cropped = img[upper:lower, left:right]
    cv2.imwrite(save_path, cropped)


if __name__ == '__main__':
    parser = argparse.ArgumentParser()
    parser.add_argument('--name_dir', type=str, default='./materials/name_cht.txt')
    parser.add_argument('--bingyi_dir', type=str, default='./materials/bingyi.txt')
    parser.add_argument('--addr_dir', type=str, default='./materials/addr.txt')
    parser.add_argument('--id_dir', type=str, default='./materials/id_back.txt')
    parser.add_argument('--save_dir', type=str, default=r'C:\Users\KDAN\Desktop\workspace\文字检测数据集（台湾身份证）\tw_idcard_back_det_0215\imgs')
    parser.add_argument('--bg_dir', type=str, default='./test_bgs')
    parser.add_argument('--generate_num', type=int, default=700)
    parser.add_argument('--font_dir', type=str, default='./fonts')

    args = parser.parse_args()
    generate_idcard(args.name_dir, args.bingyi_dir, args.addr_dir, args.id_dir, args.save_dir, args.generate_num, args.bg_dir, args.font_dir)
    # image_cut_save('./idcard_0_02.png', 445, 340, 540, 370, 'result.png')
