如何提高画布中圆形图的分辨率

时间:2017-06-13 05:00:43

标签: canvas graph resolution

我在画布中使用循环图,遵循以下过程 的 codepen 如您所见,当我放大页面时,圆圈会模糊不清。我想让这条线高分辨率。如何以放大页面后不模糊的方式进行操作。 我正在使用的Js代码如下:

$(document).ready(function(e) {

var el = document.getElementById('graph-1'); // get canvas
var options = {
percent:  el.getAttribute('data-percent')  ,
size: el.getAttribute('data-size') , /*|| 177*/
lineWidth: el.getAttribute('data-line') /*|| 4*/,
rotate: el.getAttribute('data-rotate') || 0
}

var canvas = document.createElement('canvas');
var paragrph = document.createElement('p');
var span = document.createElement('span');
span.textContent = options.percent + '%';


if (typeof(G_vmlCanvasManager) !== 'undefined') {
 G_vmlCanvasManager.initElement(canvas);
}

  var ctx = canvas.getContext('2d');
  canvas.width = canvas.height = options.size;

    el.appendChild(span);

    el.appendChild(canvas);

    ctx.translate(options.size / 2, options.size / 2); // change center
    ctx.rotate((-1 / 2 + options.rotate / 180) * Math.PI); // rotate -90 deg

    //imd = ctx.getImageData(0, 0, 240, 240);
    var radius = (options.size - options.lineWidth) / 2;

var drawCircle = function(color, lineWidth, percent) {
        percent = Math.min(Math.max(0, percent || 1), 1);
        ctx.beginPath();
        ctx.arc(0, 0, radius, 0, Math.PI * 2 * percent, false);
        ctx.strokeStyle = color;
        ctx.lineCap = 'round'; // butt, round or square
        ctx.lineWidth = lineWidth
        ctx.stroke();
};

drawCircle('#aeb4bb', options.lineWidth, 100 / 100);
drawCircle('#006bcf', options.lineWidth, options.percent / 100);

    });

HTML code:

<div  id="graph-1" data-percent="85.25" data-size="177" data-line="7"> </div>

1 个答案:

答案 0 :(得分:1)

devicePixelRatio

您可以使用window.devicePixelRatio获取缩放量,并在有缩放时使用window.onresize事件进行重绘(缩放更改窗口大小)

有关浏览器支持,请参阅MDN devicePixelRatio

修改了一些代码,以演示如何通过window.onresize事件扩展到不同的像素比率。

  

注意ES6代码需要对旧版浏览器进行转换。

// helper functions unrelated to answer
const getElementDataSet = (el, data = {}) => {Object.keys(el.dataset).forEach(key => {data[key] = el.dataset[key]}); return data }
const assignProps = (obj, props) => { Object.keys(props).forEach(key => obj[key] = props[key]);}       
const _$ = (name,props) => { const el = document.createElement(name); if (props) { assignProps(el, props) } return el }
const _A$ = (container,el) => {container.appendChild(el); return el }
// end of helper functions unrelated to answer

// Get graph container
const el = graph1;  
// defaults and get options
const options = getElementDataSet(el, {
        percent: 0, size: 100, lineWidth : 5, rotate: 0
    } 
);
// create elements and add to graph container
const elements = {
  canvas : _A$(el, _$('canvas',{width : options.size, height : options.size})),
  display : _A$(el, _$('div',{textContent : options.percent + '%'})),
}
const ctx = elements.canvas.getContext('2d');
function resizeCanvas(){
    elements.canvas.style.height = elements.canvas.style.width = options.startSize + "px";
    elements.canvas.height = elements.canvas.width = options.size;
}
function drawGraph(){
    function drawCircle(color, percent = options.percent / 100) {
      ctx.setTransform(1,0,0,1,options.size / 2, options.size / 2);
      ctx.rotate((-1 / 2 + options.rotate / 180) * Math.PI); // rotate -90 deg
      var radius = (options.size - options.lineWidth) / 2;

      percent = Math.min(Math.max(0, percent || 1), 1);
      ctx.beginPath();
      ctx.arc(0, 0, radius, 0, Math.PI * 2 * percent);
      ctx.strokeStyle = color;
      ctx.lineCap = 'round'; // butt, round or square
      ctx.lineWidth = options.lineWidth
      ctx.stroke();
    };
    const scale = devicePixelRatio;
    options.size = Math.floor(options.startSize * scale);
    options.lineWidth = Math.floor(options.startLineWidth * scale);
    resizeCanvas();    
    drawCircle('#aeb4bb',100);
    drawCircle('#006bcf');
};

// remember the start scalable values
options.startSize = options.size;
options.startLineWidth = options.lineWidth;
drawGraph(); 
// listen to resize events and scale as needed
addEventListener("resize", drawGraph );
canvas {
  border: 2px solid black;
}
 <div  id="graph1" data-percent="85.25" data-size="177" data-line-width="7"> </div>