Ejemplo n.º 1
0
 def process(self):
     kw = dict(self.getAttributeValues())
     canvas = attr.getManager(self, interfaces.ICanvasManager).canvas
     if 'width' in kw:
         canvas.setLineWidth(kw['width'])
     if 'join' in kw:
         canvas.setLineJoin(kw['join'])
     if 'cap' in kw:
         canvas.setLineCap(kw['cap'])
     if 'miterLimit' in kw:
         canvas.setMiterLimit(kw['miterLimit'])
     if 'dash' in kw:
         canvas.setDash(kw['dash'])
Ejemplo n.º 2
0
 def process(self):
     kw = dict(self.getAttributeValues())
     canvas = attr.getManager(self, interfaces.ICanvasManager).canvas
     if 'width' in kw:
         canvas.setLineWidth(kw['width'])
     if 'join' in kw:
         canvas.setLineJoin(kw['join'])
     if 'cap' in kw:
         canvas.setLineCap(kw['cap'])
     if 'miterLimit' in kw:
         canvas.setMiterLimit(kw['miterLimit'])
     if 'dash' in kw:
         canvas.setDash(kw['dash'])
Ejemplo n.º 3
0
def heatkey(canvas, hkX, hkY, idpt):
    """Draw color key for the heat map."""
    canvas.setLineWidth(1)
    canvas.setLineCap(0)
    canvas.setFillColor(black)
    canvas.setFont(bFont, LfSize)
    canvas.drawString(hkX, hkY, "Nt id. %")
    # draw heatmap color scale
    canvas.setFont(rFont, NfSize)
    hk_list = sorted(idpt.iterkeys(), reverse=True)
    hk_list.insert(0, 100)
    hk_i = 0
    hkY -= hk_boxX*1.5
    canvas.drawCentredString(hkX+hk_boxX+incrN*3, hkY, str(100))
    while hk_i < len(hk_list)-1:
        hk_boxY = (hk_list[hk_i]-hk_list[hk_i+1])*hk_u
        hkY -= hk_boxY
        canvas.setFillColor(HexColor(idpt[hk_list[hk_i+1]]))
        canvas.rect(hkX, hkY, hk_boxX, hk_boxY, fill=1)
        canvas.setFillColor(black)
        canvas.drawCentredString(hkX+hk_boxX+incrN*3, hkY,
                                 str(hk_list[hk_i+1]))
        hk_i += 1
Ejemplo n.º 4
0
def addPage(canvas, page, strokes):
    canvas.setLineCap(1)
    if page['height'] > page['width']:
        PAGE = (A4[0], A4[1])
    else:
        PAGE = (A4[1], A4[0])

    canvas.setPageSize(PAGE)
    S = PAGE[0] / page['width']

    for s in strokes:
        dots = s['dots']
        x0, y0, p0, dt0 = dots[0]

        for x, y, p, dt in dots[1:]:
            # the factor 1.5 visually matches the thickness in neonote app
            canvas.setLineWidth((s['thickness'] + 1.5) * p)
            col = s['color']
            canvas.setStrokeColorRGB(col[1] / 255, col[2] / 255, col[3] / 255)
            canvas.line(S * x0, S * y0, S * x, S * y)
            x0, y0, p0 = x, y, p

    canvas.showPage()
Ejemplo n.º 5
0
    def render_element(root, element, canvas, styles):
        canvas.saveState()

        current_style = {}
        if len(styles):
            current_style.update(styles[-1])
        for declaration in element.get("style", "").split(";"):
            if declaration == "":
                continue
            key, value = declaration.split(":")
            current_style[key] = value
        styles.append(current_style)

        if "stroke-width" in current_style:
            canvas.setLineWidth(float(current_style["stroke-width"]))

        if "stroke-dasharray" in current_style:
            canvas.setDash([
                float(length)
                for length in current_style["stroke-dasharray"].split(",")
            ])

        if current_style.get("visibility") != "hidden":

            if "transform" in element.attrib:
                for transformation in element.get("transform").split(")")[::1]:
                    if transformation:
                        transform, arguments = transformation.split("(")
                        arguments = arguments.split(",")
                        if transform.strip() == "translate":
                            if len(arguments) == 2:
                                canvas.translate(float(arguments[0]),
                                                 float(arguments[1]))
                        elif transform.strip() == "rotate":
                            if len(arguments) == 1:
                                canvas.rotate(float(arguments[0]))
                            if len(arguments) == 3:
                                canvas.translate(float(arguments[1]),
                                                 float(arguments[2]))
                                canvas.rotate(float(arguments[0]))
                                canvas.translate(-float(arguments[1]),
                                                 -float(arguments[2]))

            if element.tag == "svg":
                if "background-color" in current_style:
                    set_fill_color(
                        canvas,
                        toyplot.color.css(current_style["background-color"]))
                    canvas.rect(
                        0,
                        0,
                        float(element.get("width")[:-2]),
                        float(element.get("height")[:-2]),
                        stroke=0,
                        fill=1,
                    )
                for child in element:
                    render_element(root, child, canvas, styles)

            elif element.tag == "g":
                if element.get("clip-path", None) is not None:
                    clip_id = element.get("clip-path")[5:-1]
                    clip_path = root.find(".//*[@id='%s']" % clip_id)
                    for child in clip_path:
                        if child.tag == "rect":
                            x = float(child.get("x"))
                            y = float(child.get("y"))
                            width = float(child.get("width"))
                            height = float(child.get("height"))
                            path = canvas.beginPath()
                            path.moveTo(x, y)
                            path.lineTo(x + width, y)
                            path.lineTo(x + width, y + height)
                            path.lineTo(x, y + height)
                            path.close()
                            canvas.clipPath(path, stroke=0, fill=1)
                        else:
                            toyplot.log.error("Unhandled clip tag: %s",
                                              child.tag)  # pragma: no cover

                for child in element:
                    render_element(root, child, canvas, styles)

            elif element.tag == "clipPath":
                pass

            elif element.tag == "line":
                stroke = get_stroke(current_style)
                if stroke is not None:
                    set_stroke_color(canvas, stroke)
                    canvas.setLineCap(get_line_cap(current_style))
                    canvas.line(
                        float(element.get("x1", 0)),
                        float(element.get("y1", 0)),
                        float(element.get("x2", 0)),
                        float(element.get("y2", 0)),
                    )
            elif element.tag == "path":
                stroke = get_stroke(current_style)
                if stroke is not None:
                    set_stroke_color(canvas, stroke)
                    canvas.setLineCap(get_line_cap(current_style))
                    path = canvas.beginPath()
                    commands = element.get("d").split()
                    while len(commands):
                        command = commands.pop(0)
                        if command == "L":
                            path.lineTo(float(commands.pop(0)),
                                        float(commands.pop(0)))
                        elif command == "M":
                            path.moveTo(float(commands.pop(0)),
                                        float(commands.pop(0)))
                    canvas.drawPath(path)
            elif element.tag == "polygon":
                fill, fill_gradient = get_fill(root, current_style)
                if fill_gradient is not None:
                    raise NotImplementedError(
                        "Gradient <polygon> not implemented."
                    )  # pragma: no cover
                if fill is not None:
                    set_fill_color(canvas, fill)
                stroke = get_stroke(current_style)
                if stroke is not None:
                    set_stroke_color(canvas, stroke)

                points = [
                    point.split(",")
                    for point in element.get("points").split()
                ]
                path = canvas.beginPath()
                for point in points[:1]:
                    path.moveTo(float(point[0]), float(point[1]))
                for point in points[1:]:
                    path.lineTo(float(point[0]), float(point[1]))
                path.close()
                canvas.drawPath(path,
                                stroke=stroke is not None,
                                fill=fill is not None)
            elif element.tag == "rect":
                fill, fill_gradient = get_fill(root, current_style)
                if fill is not None:
                    set_fill_color(canvas, fill)
                stroke = get_stroke(current_style)
                if stroke is not None:
                    set_stroke_color(canvas, stroke)

                x = float(element.get("x", 0))
                y = float(element.get("y", 0))
                width = float(element.get("width"))
                height = float(element.get("height"))

                path = canvas.beginPath()
                path.moveTo(x, y)
                path.lineTo(x + width, y)
                path.lineTo(x + width, y + height)
                path.lineTo(x, y + height)
                path.close()

                if fill_gradient is not None:
                    pdf_colors = []
                    pdf_offsets = []
                    for stop in fill_gradient:
                        offset = float(stop.get("offset"))
                        color = toyplot.color.css(stop.get("stop-color"))
                        opacity = float(stop.get("stop-opacity"))
                        pdf_colors.append(
                            reportlab.lib.colors.Color(color["r"], color["g"],
                                                       color["b"],
                                                       color["a"] * opacity))
                        pdf_offsets.append(offset)
                    canvas.saveState()
                    canvas.clipPath(path, stroke=0, fill=1)
                    canvas.setFillAlpha(1)
                    canvas.linearGradient(
                        float(fill_gradient.get("x1")),
                        float(fill_gradient.get("y1")),
                        float(fill_gradient.get("x2")),
                        float(fill_gradient.get("y2")),
                        pdf_colors,
                        pdf_offsets,
                    )
                    canvas.restoreState()

                canvas.drawPath(path,
                                stroke=stroke is not None,
                                fill=fill is not None)
            elif element.tag == "circle":
                fill, fill_gradient = get_fill(root, current_style)
                if fill_gradient is not None:
                    raise NotImplementedError(
                        "Gradient <circle> not implemented."
                    )  # pragma: no cover
                if fill is not None:
                    set_fill_color(canvas, fill)
                stroke = get_stroke(current_style)
                if stroke is not None:
                    set_stroke_color(canvas, stroke)

                cx = float(element.get("cx", 0))
                cy = float(element.get("cy", 0))
                r = float(element.get("r"))
                canvas.circle(cx,
                              cy,
                              r,
                              stroke=stroke is not None,
                              fill=fill is not None)
            elif element.tag == "text":
                x = float(element.get("x", 0))
                y = float(element.get("y", 0))
                fill, fill_gradient = get_fill(element, current_style)
                stroke = get_stroke(current_style)
                font_family = get_font_family(current_style)
                font_size = toyplot.units.convert(current_style["font-size"],
                                                  target="px")
                text = element.text

                canvas.saveState()
                canvas.setFont(font_family, font_size)
                if fill is not None:
                    set_fill_color(canvas, fill)
                if stroke is not None:
                    set_stroke_color(canvas, stroke)
                canvas.translate(x, y)
                canvas.scale(1, -1)
                canvas.drawString(0, 0, text)
                canvas.restoreState()

            elif element.tag == "image":
                # pylint: disable=redefined-variable-type

                import PIL.Image
                image = element.get("xlink:href")
                if not image.startswith("data:image/png;base64,"):
                    raise ValueError(
                        "Unsupported image type.")  # pragma: no cover
                image = base64.standard_b64decode(image[22:])
                image = io.BytesIO(image)
                image = PIL.Image.open(image)
                image = reportlab.lib.utils.ImageReader(image)

                x = float(element.get("x", 0))
                y = float(element.get("y", 0))
                width = float(element.get("width"))
                height = float(element.get("height"))

                canvas.saveState()
                path = canvas.beginPath()
                set_fill_color(canvas, toyplot.color.rgb(1, 1, 1))
                canvas.rect(x, y, width, height, stroke=0, fill=1)
                canvas.translate(x, y + height)
                canvas.scale(1, -1)
                canvas.drawImage(image=image,
                                 x=0,
                                 y=0,
                                 width=width,
                                 height=height,
                                 mask=None)
                canvas.restoreState()

            elif element.tag in ["defs", "title"]:
                pass

            else:
                raise Exception("unhandled tag: %s" %
                                element.tag)  # pragma: no cover

        styles.pop()
        canvas.restoreState()
Ejemplo n.º 6
0
def make_a_table(canvas, ncol, nrow, entries, str_index):
    width, height = A4
    cell_size = 16 * mm

    table_data = []
    for i in range(nrow):
        row = []
        for j in range(ncol):
            if 1 < j < ncol - 1:
                row.append('')
            else:
                try:
                    row.append(entries[i])
                except:
                    row.append('')
        table_data.append(row)

    kanji_tbl_style = []
    kanji_tbl_style.append(('INNERGRID', (0, 0), (-1, -1), 0.25, colors.black))
    kanji_tbl_style.append(('BOX', (0, 0), (-1, -1), 0.25, colors.black))
    for i in range(ncol):
        kanji_tbl_style.append(('ALIGN', (i, 0), (i, -1), 'CENTER'))
        kanji_tbl_style.append(('VALIGN', (i, 0), (i, -1), 'BOTTOM'))
        kanji_tbl_style.append(('FONT', (i, 0), (i, -1), 'Stroke', 36))
        if i == ncol - 1:
            kanji_tbl_style.append(('TEXTCOLOR', (i, 0), (i, -1), NAVY))
        elif i < 2:
            kanji_tbl_style.append(('TEXTCOLOR', (i, 0), (i, -1), GRAY))

    kanji_tbl = Table(table_data, colWidths=cell_size, rowHeights=cell_size)
    kanji_tbl.setStyle(TableStyle(kanji_tbl_style))
    kanji_tbl.wrapOn(canvas, width, height)
    table_x, table_y = 12 * mm, 21 * mm
    kanji_tbl.drawOn(canvas, table_x, table_y)

    kanji_info = []
    info_tbl_style = []
    info_style = ParagraphStyle(
        name='Info',
        fontName='Hiragino',
        fontSize=7,
    )
    for i in range(nrow):
        try:
            text = Paragraph(kanji_lookup[entries[i]], info_style)
            kanji_info.append([text])
        except:
            kanji_info.append([''])
    info_tbl_style.append(('VALIGN', (0, 0), (-1, -1), 'TOP'))
    info_tbl = Table(kanji_info, colWidths=50 * mm, rowHeights=cell_size)
    info_tbl.setStyle(TableStyle(info_tbl_style))
    info_tbl.wrapOn(canvas, width, height)
    info_tbl.drawOn(canvas, table_x + cell_size * ncol, table_y)

    for i in range(nrow):
        coord_trans = (table_x + cell_size * ncol + 50 * mm,
                       table_y + cell_size * i)
        if i % 2 == 1:
            char_x = table_x + cell_size * ncol + 5 * mm
        else:
            char_x = table_x + cell_size * ncol + 22 * mm
        coord_char = (char_x, table_y + cell_size * i + 2 * mm)

        try:
            kanji = entries[nrow - i - 1]
            canvas.setFillColor(BLACK)
            canvas.setFont('Times-Italic', 8)
            canvas.drawRightString(*coord_trans, trans_lookup[kanji])

            if kanji in font_lookup['bone']:
                canvas.setFillColor(GREEN30)
                canvas.setFont('Bone', 55)
            elif kanji in font_lookup['tenbun']:
                canvas.setFillColor(RED30)
                canvas.setFont('Tenbun', 55)
            else:
                continue
            canvas.drawString(*coord_char, kanji)
        except:
            pass

    sep_x = table_x + cell_size * ncol + 0.5 * mm
    canvas.setLineWidth(0.1 * mm)
    canvas.line(sep_x, table_y, sep_x, table_y + cell_size * nrow)
    canvas.setFillColor(LIGHTGRAY)
    rect_x, rect_y = table_x, height - 16 * mm
    canvas.roundRect(rect_x,
                     rect_y,
                     70 * mm,
                     10 * mm,
                     1 * mm,
                     fill=1,
                     stroke=0)
    canvas.setFont('Hiragino', 12)
    canvas.setFillColor(BLACK)
    canvas.drawString(rect_x + 2 * mm, rect_y + 3 * mm,
                      "Joytan Kanji Practice | 漢字練習帳")

    # Name with underline
    canvas.setLineWidth(0.1 * mm)
    canvas.setFillColor(BLACK)
    canvas.setFont('Hiragino', 10)
    name_x, name_y = width - 90 * mm, height - 14 * mm
    canvas.drawString(name_x, name_y, "名前:")
    canvas.line(name_x, name_y - 2 * mm, name_x + 70 * mm, name_y - 2 * mm)

    # Left footer
    canvas.setFont('Helvetica-Bold', 10)
    coord_msg = (table_x, table_y - 5 * mm)
    canvas.drawString(
        *coord_msg, "Support our project: https://kokimame.github.io/joytan/")
    coord_index = (table_x, table_y - 12 * mm)
    canvas.drawString(*coord_index, "%s | © Joytan" % str_index)

    # Right footer
    coord_l1 = (width - 20 * mm, table_y - 5 * mm)
    coord_l2 = (width - 20 * mm, table_y - 10 * mm)
    coord_l3 = (width - 20 * mm, table_y - 13 * mm)
    canvas.setFont('Hiragino', 9)
    canvas.drawRightString(*coord_l1, "【部首】/画数/学年 オンヨミ くんよみ")
    canvas.setFont('Hiragino', 8)
    canvas.drawRightString(
        *coord_l2,
        "【radical】/#stroke/grade Onyomi(Katakana) Kunyomi (Hiragana)")
    canvas.setFont('Times-Italic', 7)
    canvas.drawRightString(*coord_l3, "* Rough kanji-wise translation")

    # Additional lines
    canvas.setDash([0.1 * mm, 1.2 * mm])
    canvas.setLineCap(1)

    # Dotted vertical lines
    for i in range(ncol):
        x = table_x + cell_size / 2 + cell_size * i
        canvas.line(x, table_y, x, table_y + nrow * cell_size)
    # Dotted horizontal  lines
    for i in range(nrow):
        trans_y = table_y + cell_size / 2 + cell_size * i
        canvas.line(table_x, trans_y, table_x + ncol * cell_size, trans_y)
    # Separation between the Info panel
    for i in range(nrow + 1):
        x = table_x + cell_size * ncol
        trans_y = table_y + cell_size * i
        canvas.line(x, trans_y, x + 50 * mm, trans_y)

    canvas.showPage()