add first page and pie chart to board report
This commit is contained in:
BIN
requirements.txt
BIN
requirements.txt
Binary file not shown.
@@ -13,17 +13,45 @@ from reportlab.platypus import (
|
|||||||
Paragraph,
|
Paragraph,
|
||||||
TableStyle,
|
TableStyle,
|
||||||
PageBreak,
|
PageBreak,
|
||||||
|
Spacer,
|
||||||
)
|
)
|
||||||
from reportlab.lib import colors
|
from reportlab.lib import colors
|
||||||
|
|
||||||
import ipaddress
|
import ipaddress
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
import matplotlib.dates
|
||||||
|
import matplotlib.pyplot as plt
|
||||||
|
from svglib.svglib import svg2rlg
|
||||||
|
from matplotlib import cm
|
||||||
|
from matplotlib.ticker import FormatStrFormatter
|
||||||
|
|
||||||
|
|
||||||
from miners.miner_factory import MinerFactory
|
from miners.miner_factory import MinerFactory
|
||||||
from tools.bad_board_util.func.decorators import disable_buttons
|
from tools.bad_board_util.func.decorators import disable_buttons
|
||||||
from tools.bad_board_util.img import IMAGE_SELECTION_MATRIX, LOGO
|
from tools.bad_board_util.img import IMAGE_SELECTION_MATRIX, LOGO
|
||||||
from tools.bad_board_util.layout import window
|
from tools.bad_board_util.layout import window
|
||||||
|
|
||||||
|
IP_STYLE = ParagraphStyle(
|
||||||
|
"IP Style",
|
||||||
|
alignment=TA_CENTER,
|
||||||
|
fontSize=7,
|
||||||
|
fontName="Helvetica-Bold",
|
||||||
|
)
|
||||||
|
TITLE_STYLE = ParagraphStyle(
|
||||||
|
"Title",
|
||||||
|
alignment=TA_CENTER,
|
||||||
|
fontSize=20,
|
||||||
|
spaceAfter=40,
|
||||||
|
fontName="Helvetica-Bold",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def add_first_page_number(canvas, doc):
|
||||||
|
canvas.saveState()
|
||||||
|
canvas.drawString(letter[0] - 60, 20, "Page " + str(doc.page))
|
||||||
|
canvas.restoreState()
|
||||||
|
|
||||||
|
|
||||||
def add_page_header(canvas, doc):
|
def add_page_header(canvas, doc):
|
||||||
canvas.saveState()
|
canvas.saveState()
|
||||||
@@ -49,6 +77,7 @@ def add_page_header(canvas, doc):
|
|||||||
|
|
||||||
@disable_buttons
|
@disable_buttons
|
||||||
async def save_report(file_location):
|
async def save_report(file_location):
|
||||||
|
p1_logo, p1_title = create_first_page()
|
||||||
data = {}
|
data = {}
|
||||||
for line in window["ip_table"].Values:
|
for line in window["ip_table"].Values:
|
||||||
data[line[0]] = {
|
data[line[0]] = {
|
||||||
@@ -95,7 +124,7 @@ async def save_report(file_location):
|
|||||||
title=f"Board Report {datetime.datetime.now().strftime('%Y/%b/%d')}",
|
title=f"Board Report {datetime.datetime.now().strftime('%Y/%b/%d')}",
|
||||||
)
|
)
|
||||||
|
|
||||||
elements = []
|
pie_chart, board_table = create_boards_pie_chart(image_selection_data)
|
||||||
|
|
||||||
table_data = get_table_data(image_selection_data)
|
table_data = get_table_data(image_selection_data)
|
||||||
|
|
||||||
@@ -119,19 +148,20 @@ async def save_report(file_location):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
elements = []
|
||||||
|
elements.append(p1_logo)
|
||||||
|
elements.append(p1_title)
|
||||||
|
elements.append(PageBreak())
|
||||||
|
elements.append(pie_chart)
|
||||||
|
elements.append(Spacer(0, 60))
|
||||||
|
elements.append(board_table)
|
||||||
|
elements.append(PageBreak())
|
||||||
elements.append(miner_img_table)
|
elements.append(miner_img_table)
|
||||||
elements.append(PageBreak())
|
elements.append(PageBreak())
|
||||||
elements.append(
|
elements.append(
|
||||||
Paragraph(
|
Paragraph(
|
||||||
"Board Data",
|
"Board Data",
|
||||||
style=ParagraphStyle(
|
style=TITLE_STYLE,
|
||||||
"Title",
|
|
||||||
alignment=TA_CENTER,
|
|
||||||
fontSize=20,
|
|
||||||
spaceAfter=40,
|
|
||||||
fontName="Helvetica-Bold",
|
|
||||||
),
|
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
elements.append(create_data_table(list_data))
|
elements.append(create_data_table(list_data))
|
||||||
@@ -139,11 +169,97 @@ async def save_report(file_location):
|
|||||||
|
|
||||||
doc.build(
|
doc.build(
|
||||||
elements,
|
elements,
|
||||||
onFirstPage=add_page_header,
|
onFirstPage=add_first_page_number,
|
||||||
onLaterPages=add_page_header,
|
onLaterPages=add_page_header,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def create_boards_pie_chart(data):
|
||||||
|
labels = ["All Working", "1 Bad Board", "2 Bad Boards", "3 Bad Boards"]
|
||||||
|
num_bad_boards = [0, 0, 0, 0]
|
||||||
|
for item in data.keys():
|
||||||
|
num_bad_boards[len(data[item])] += 1
|
||||||
|
cmap = plt.get_cmap("Blues")
|
||||||
|
cs = cmap(np.linspace(0.2, 0.8, num=len(num_bad_boards)))
|
||||||
|
|
||||||
|
fig1, ax = plt.subplots()
|
||||||
|
ax.pie(
|
||||||
|
num_bad_boards,
|
||||||
|
labels=labels,
|
||||||
|
autopct="%1.2f%%",
|
||||||
|
shadow=True,
|
||||||
|
startangle=180,
|
||||||
|
colors=cs,
|
||||||
|
pctdistance=0.8,
|
||||||
|
)
|
||||||
|
ax.axis("equal")
|
||||||
|
ax.set_title("Broken Boards", fontsize=24, pad=20)
|
||||||
|
|
||||||
|
imgdata = BytesIO()
|
||||||
|
fig1.savefig(imgdata, format="svg")
|
||||||
|
imgdata.seek(0) # rewind the data
|
||||||
|
drawing = svg2rlg(imgdata)
|
||||||
|
imgdata.close()
|
||||||
|
plt.close("all")
|
||||||
|
pie_chart = KeepInFrame(375, 375, [Image(drawing)], hAlign="CENTER")
|
||||||
|
|
||||||
|
table_data = [labels, num_bad_boards]
|
||||||
|
|
||||||
|
t = Table(table_data)
|
||||||
|
|
||||||
|
table_style = TableStyle(
|
||||||
|
[
|
||||||
|
# ("FONTSIZE", (0, 0), (-1, -1), 13),
|
||||||
|
# line for below titles
|
||||||
|
("LINEBELOW", (0, 0), (-1, 0), 2, colors.black),
|
||||||
|
("FONTNAME", (0, 0), (-1, 0), "Helvetica-Bold"),
|
||||||
|
# line for above totals
|
||||||
|
("LINEABOVE", (0, -1), (-1, -1), 2, colors.black),
|
||||||
|
# line for beside unit #
|
||||||
|
("LINEAFTER", (0, 0), (0, -1), 2, colors.black),
|
||||||
|
# gridlines and outline of table
|
||||||
|
("INNERGRID", (0, 0), (-1, -1), 0.25, colors.black),
|
||||||
|
("BOX", (0, 0), (-1, -1), 2, colors.black),
|
||||||
|
("LEFTPADDING", (0, 0), (-1, -1), 3),
|
||||||
|
("RIGHTPADDING", (0, 0), (-1, -1), 3),
|
||||||
|
("BOTTOMPADDING", (0, 0), (-1, -1), 3),
|
||||||
|
("TOPPADDING", (0, 0), (-1, -1), 3),
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
|
t.setStyle(table_style)
|
||||||
|
|
||||||
|
# zebra stripes on table
|
||||||
|
for each in range(len(table_data)):
|
||||||
|
if each % 2 == 0:
|
||||||
|
bg_color = colors.whitesmoke
|
||||||
|
else:
|
||||||
|
bg_color = colors.lightgrey
|
||||||
|
|
||||||
|
t.setStyle(TableStyle([("BACKGROUND", (0, each), (-1, each), bg_color)]))
|
||||||
|
|
||||||
|
return pie_chart, t
|
||||||
|
|
||||||
|
|
||||||
|
def create_first_page():
|
||||||
|
title_style = ParagraphStyle(
|
||||||
|
"Title",
|
||||||
|
alignment=TA_CENTER,
|
||||||
|
fontSize=50,
|
||||||
|
spaceAfter=40,
|
||||||
|
spaceBefore=150,
|
||||||
|
fontName="Helvetica-Bold",
|
||||||
|
)
|
||||||
|
|
||||||
|
img_dec = b64decode(LOGO)
|
||||||
|
img = BytesIO(img_dec)
|
||||||
|
img.seek(0)
|
||||||
|
|
||||||
|
logo = KeepInFrame(450, 105, [Image(img)])
|
||||||
|
title = Paragraph("Board Report", style=title_style)
|
||||||
|
return logo, title
|
||||||
|
|
||||||
|
|
||||||
def create_data_table(data):
|
def create_data_table(data):
|
||||||
left_bad_boards = 0
|
left_bad_boards = 0
|
||||||
right_bad_boards = 0
|
right_bad_boards = 0
|
||||||
@@ -199,6 +315,7 @@ def create_data_table(data):
|
|||||||
# generate a basic table style
|
# generate a basic table style
|
||||||
table_style = TableStyle(
|
table_style = TableStyle(
|
||||||
[
|
[
|
||||||
|
("FONTSIZE", (0, 0), (-1, -1), 8),
|
||||||
# line for below titles
|
# line for below titles
|
||||||
("LINEBELOW", (0, 0), (-1, 0), 2, colors.black),
|
("LINEBELOW", (0, 0), (-1, 0), 2, colors.black),
|
||||||
("FONTNAME", (0, 0), (-1, 0), "Helvetica-Bold"),
|
("FONTNAME", (0, 0), (-1, 0), "Helvetica-Bold"),
|
||||||
@@ -214,6 +331,15 @@ def create_data_table(data):
|
|||||||
]
|
]
|
||||||
)
|
)
|
||||||
|
|
||||||
|
for (
|
||||||
|
row,
|
||||||
|
values,
|
||||||
|
) in enumerate(table_data):
|
||||||
|
if not row == 0 and not row == (len(table_data) - 1):
|
||||||
|
failed_boards = values[5]
|
||||||
|
if not failed_boards == 0:
|
||||||
|
table_style.add("TEXTCOLOR", (5, row), (5, row), colors.red)
|
||||||
|
|
||||||
# set the styles to the table
|
# set the styles to the table
|
||||||
t.setStyle(table_style)
|
t.setStyle(table_style)
|
||||||
|
|
||||||
@@ -230,20 +356,7 @@ def create_data_table(data):
|
|||||||
|
|
||||||
|
|
||||||
def get_table_data(data):
|
def get_table_data(data):
|
||||||
IP_STYLE = ParagraphStyle(
|
table_elems = [[Paragraph("Hashboard Visual Representation", style=TITLE_STYLE)]]
|
||||||
"IP Style",
|
|
||||||
alignment=TA_CENTER,
|
|
||||||
fontSize=7,
|
|
||||||
fontName="Helvetica-Bold",
|
|
||||||
)
|
|
||||||
TITLE_STYLE = ParagraphStyle(
|
|
||||||
"Title",
|
|
||||||
alignment=TA_CENTER,
|
|
||||||
fontSize=20,
|
|
||||||
spaceAfter=10,
|
|
||||||
fontName="Helvetica-Bold",
|
|
||||||
)
|
|
||||||
table_elems = [[Paragraph("Board Report", style=TITLE_STYLE)]]
|
|
||||||
table_row = []
|
table_row = []
|
||||||
table_style = TableStyle(
|
table_style = TableStyle(
|
||||||
[
|
[
|
||||||
|
|||||||
Reference in New Issue
Block a user