Example of implementing dashed border with html2canvas

Example of implementing dashed border with html2canvas

html2canvas is a library that generates canvas from html elements. Most of the styles of the drawn canvas are consistent with CSS. For example, as of 1.0.0-alpha.12, dashed borders are still drawn as solid lines, and border-collapse still has problems.

Here, based on an idea in github issues, the dashed border effect is simulated and implemented.

Applicable situations: There are many separate borders, that is, not a complete border, and border-radius is not considered

1. First, before drawing in html2canvas, find out the direction and position of all dotted borders in the element where the canvas needs to be drawn

findDashedBorders = (page) => {
        const tds = page.querySelectorAll("td");
        const borders = [];
        tds.forEach(td => {
            const computedStyle = window.getComputedStyle(td);
            const borderStyle = computedStyle.borderStyle ? computedStyle.borderStyle.split(' ') : [];
            const dashedIndex = findAll(borderStyle, 'dashed');
            if (dashedIndex.length) {
                const rect = td.getBoundingClientRect();
                dashedIndex.map(index => {
                    const border = {
                        rect,
                        border: dashedBorder[index]
                    }
                    borders.push(border);
                    td.style[`border${dashedBorder[index]}Color`] = 'transparent';
                });
            }
        });
        return borders;
    }

Page is the element that needs to draw the canvas. All the elements with dashed borders are td elements, so find all td elements and use the getComputedStyle() method to find its borderStyle. If it has a dashed border, the value of this attribute is in the form of "dashed dashed none none", so find all dashed directions according to the custom findAll() method (for example, "dashed dashed none none" will return [0, 1]), where the dashedBorder array is as follows:

const dashedBorder = ["Top", "Right", "Bottom", "Left"];

After finding the direction, get its position at the same time, store the direction and position information in the borders array, and set this border to transparent so that html2canvas does not draw this frame. We will deal with it separately later. (Note: The dotted borders on this page will become transparent. This does not consider changing the transparent border back to its original color after drawing is completed.)

2. Use html2canvas to get the drawn canvas

pages.forEach((page, idx) => {
    const borders = this.findDashedBorders(page);
    const parentRect = page.getBoundingClientRect();
    html2canvas(page, {scale: 2, logging: false, useCORS: true}).then((canvas) => {
       this.drawDashedBorder(canvas, borders, parentRect);
       ......
    })
})

Pages are all the elements that need to be drawn on the canvas. When we get the dashed border of each page, we also get the position of the page so that when we draw the dashed border, we can get the position of the border relative to the page. After html2canvas draws the canvas, we further draw the dashed border through the drawDashedBorder() method. Let's implement this method.

3. drawDashedBorder() further draws the dotted line after getting the canvas.

drawDashedBorder = (canvas, borders, parentRect) => {
        var ctx = canvas.getContext("2d");
        ctx.setLineDash([6, 3]);
        ctx.strokeStyle = '#3089c7';
        ctx.lineWidth = 1;
        ctx.globalAlpha = 1;

        borders.forEach(border => {
            var left = (border.rect.left + 0.5 - parentRect.left)*2;
            var right = (border.rect.right - 0.5 - parentRect.left)*2;
            var top = (border.rect.top + 0.5 - parentRect.top)*2;
            var bottom = (border.rect.bottom - 0.5 - parentRect.top)*2;

            switch (border.border) {
                case 'Top':
                    ctx.beginPath();
                    ctx.moveTo(left, top);
                    ctx.lineTo(right, top);
                    ctx.stroke();
                    break;
                case 'Right':
                    ctx.beginPath();
                    ctx.moveTo(right, top);
                    ctx.lineTo(right, bottom);
                    ctx.stroke();
                    break;
                case 'Bottom':
                    ctx.beginPath();
                    ctx.moveTo(left, bottom);
                    ctx.lineTo(right, bottom);
                    ctx.stroke();
                    break;
                case 'Left':
                    ctx.beginPath();
                    ctx.moveTo(left, top);
                    ctx.lineTo(left, bottom);
                    ctx.stroke();
                    break;
                default:
                    break;
            }
        })
    }

This means that according to the direction and position information of the dashed border in borders, the dashed line is drawn using the setLineDash method after obtaining the 2D context in the canvas. The positions are all *2 because we used twice the size of the canvas before.

4. This method is currently only available for testing in Chrome, and is invalid in Firefox because the information returned by getComputedStyle in Firefox is different from that in Chrome.

Since I don't have a deep understanding of canvas and cannot pr, I can only look forward to the official implementation of html2canvas.

The above is the full content of this article. I hope it will be helpful for everyone’s study. I also hope that everyone will support 123WORDPRESS.COM.

<<:  A Brief Analysis of MySQL - MVCC

>>:  Velocity.js implements page scrolling switching effect

Recommend

MySQL query sorting and paging related

Overview It is usually not what we want to presen...

UTF-8 and GB2312 web encoding

Recently, many students have asked me about web p...

HTML code example: detailed explanation of hyperlinks

Hyperlinks are the most frequently used HTML elem...

How to use positioning to center elements (web page layout tips)

How to center an element in the browser window He...

Mount the disk in a directory under Ubuntu 18.04

Introduction This article records how to mount a ...

Disable input text box input implementation properties

Today I want to summarize several very useful HTML...

A brief analysis of CSS3 using text-overflow to solve text layout problems

Basic syntax The use of text-overflow requires th...

MySQL reports an error: Can't find file: './mysql/plugin.frm' solution

Find the problem Recently, I found a problem at w...

Chinese and English font name comparison table (including Founder and Arphic)

In CSS files, we often see some font names become...

One minute to experience the smoothness of html+vue+element-ui

Technology Fan html web page, you must know vue f...

CSS to achieve the image hovering mouse folding effect

CSS to achieve the image hovering mouse folding e...

Uniapp's experience in developing small programs

1. Create a new UI project First of all, our UI i...

Introduction to CSS3 color value RGBA and gradient color usage

Before CSS3, gradient images could only be used a...

Perfect solution for vertical centering of form elements

Copy code The code is as follows: <!DOCTYPE ht...