首页 文章

调整HTML5画布大小以适合窗口

提问于
浏览
354

如何自动缩放HTML5 <canvas> 元素以适合页面?

例如,我可以通过将 heightwidth 属性设置为100%来缩放 <div> ,但 <canvas> 不会缩放,是吗?

14 回答

  • 8

    以下解决方案最适合我 . 由于我对编码比较陌生,我喜欢用视觉确认某些东西按照我期望的方式工作 . 我在以下网站找到了它:http://htmlcheats.com/html/resize-the-html5-canvas-dyamically/

    这是代码:

    <!DOCTYPE html>
    
    <head>
        <meta charset="utf-8">
        <title>Resize HTML5 canvas dynamically | www.htmlcheats.com</title>
        <style>
        html, body {
          width: 100%;
          height: 100%;
          margin: 0px;
          border: 0;
          overflow: hidden; /*  Disable scrollbars */
          display: block;  /* No floating content on sides */
        }
        </style>
    </head>
    
    <body>
        <canvas id='c' style='position:absolute; left:0px; top:0px;'>
        </canvas>
    
        <script>
        (function() {
            var
            // Obtain a reference to the canvas element using its id.
            htmlCanvas = document.getElementById('c'),
            // Obtain a graphics context on the canvas element for drawing.
            context = htmlCanvas.getContext('2d');
    
           // Start listening to resize events and draw canvas.
           initialize();
    
           function initialize() {
               // Register an event listener to call the resizeCanvas() function 
               // each time the window is resized.
               window.addEventListener('resize', resizeCanvas, false);
               // Draw canvas border for the first time.
               resizeCanvas();
            }
    
            // Display custom canvas. In this case it's a blue, 5 pixel 
            // border that resizes along with the browser window.
            function redraw() {
               context.strokeStyle = 'blue';
               context.lineWidth = '5';
               context.strokeRect(0, 0, window.innerWidth, window.innerHeight);
            }
    
            // Runs each time the DOM window resize event fires.
            // Resets the canvas dimensions to match window,
            // then draws the new borders accordingly.
            function resizeCanvas() {
                htmlCanvas.width = window.innerWidth;
                htmlCanvas.height = window.innerHeight;
                redraw();
            }
        })();
    
        </script>
    </body> 
    </html>
    

    蓝色边框显示调整大小画布的边缘,并且始终沿着窗口的边缘,在所有4个边上都可见,而上述其他一些答案则不然 . 希望能帮助到你 .

  • 1

    一个 pure CSS 方法添加到@jerseyboy的解决方案上面 .
    适用于Firefox(在v29中测试),Chrome(在v34中测试)和Internet Explorer(在v11中测试) .

    <!DOCTYPE html>
    <html>
        <head>
        <style>
            html,
            body {
                width: 100%;
                height: 100%;
                margin: 0;
            }
            canvas {
                background-color: #ccc;
                display: block;
                position: absolute;
                top: 0;
                left: 0;
                right: 0;
                bottom: 0;
                width: 100%;
                height: 100%;
            }
        </style>
    </head>
    <body>
        <canvas id="canvas" width="500" height="500"></canvas>
        <script>
            var canvas = document.getElementById('canvas');
            if (canvas.getContext) {
                var ctx = canvas.getContext('2d');
                ctx.fillRect(25,25,100,100);
                ctx.clearRect(45,45,60,60);
                ctx.strokeRect(50,50,50,50);
            }
        </script>
    </body>
    </html>
    

    链接到示例:http://temporaer.net/open/so/140502_canvas-fit-to-window.html

    但请小心,正如@jerseyboy在评论中所述:

    用CSS重新调整画布很麻烦 . 至少在Chrome和Safari上,鼠标/触摸事件位置不会与画布像素位置1:1对应,您必须转换坐标系 .

  • 8

    我认为这应该是我们应该做的:http://www.html5rocks.com/en/tutorials/casestudies/gopherwoord-studios-resizing-html5-games/

    function resizeGame() {
        var gameArea = document.getElementById('gameArea');
        var widthToHeight = 4 / 3;
        var newWidth = window.innerWidth;
        var newHeight = window.innerHeight;
        var newWidthToHeight = newWidth / newHeight;
    
        if (newWidthToHeight > widthToHeight) {
            newWidth = newHeight * widthToHeight;
            gameArea.style.height = newHeight + 'px';
            gameArea.style.width = newWidth + 'px';
        } else {
            newHeight = newWidth / widthToHeight;
            gameArea.style.width = newWidth + 'px';
            gameArea.style.height = newHeight + 'px';
        }
    
        gameArea.style.marginTop = (-newHeight / 2) + 'px';
        gameArea.style.marginLeft = (-newWidth / 2) + 'px';
    
        var gameCanvas = document.getElementById('gameCanvas');
        gameCanvas.width = newWidth;
        gameCanvas.height = newHeight;
    }
    
    window.addEventListener('resize', resizeGame, false);
    window.addEventListener('orientationchange', resizeGame, false);
    
  • 10

    基本上你要做的是将onresize事件绑定到你的身体,一旦你捕获事件你只需要使用window.innerWidth和window.innerHeight来调整画布的大小 .

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
    
    <html xmlns="http://www.w3.org/1999/xhtml">
    <head>
        <title>Canvas Resize</title>
    
        <script type="text/javascript">
            function resize_canvas(){
                canvas = document.getElementById("canvas");
                if (canvas.width  < window.innerWidth)
                {
                    canvas.width  = window.innerWidth;
                }
    
                if (canvas.height < window.innerHeight)
                {
                    canvas.height = window.innerHeight;
                }
            }
        </script>
    </head>
    
    <body onresize="resize_canvas()">
            <canvas id="canvas">Your browser doesn't support canvas</canvas>
    </body>
    </html>
    
  • -2

    我相信我找到了一个优雅的解决方案:

    JavaScript

    /* important! for alignment, you should make things
     * relative to the canvas' current width/height.
     */
    function draw() {
      var ctx = (a canvas context);
      ctx.canvas.width  = window.innerWidth;
      ctx.canvas.height = window.innerHeight;
      //...drawing code...
    }
    

    CSS

    html, body {
      width:  100%;
      height: 100%;
      margin: 0px;
    }
    

    到目前为止,对我没有任何大的负面影响 .

  • 2

    如果您的div完全填满了网页,那么您可以填满该div,因此有一个填充div的画布 .

    您可能会觉得这很有趣,因为您可能需要使用css来使用百分比,但是,这取决于您使用的浏览器,以及与规范一致的程度:http://www.whatwg.org/specs/web-apps/current-work/multipage/the-canvas-element.html#the-canvas-element

    canvas元素的固有尺寸等于坐标空间的大小,数字以CSS像素解释 . 但是,元素可以通过样式表任意调整大小 . 在渲染过程中,缩放图像以适合此布局大小 .

    您可能需要获取div的offsetWidth和height,或获取窗口高度/宽度并将其设置为像素值 .

  • 47
    (function() {
    
        // get viewport size
        getViewportSize = function() {
            return {
                height: window.innerHeight,
                width:  window.innerWidth
            };
        };
    
        // update canvas size
        updateSizes = function() {
            var viewportSize = getViewportSize();
            $('#myCanvas').width(viewportSize.width).height(viewportSize.height);
            $('#myCanvas').attr('width', viewportSize.width).attr('height', viewportSize.height);
        };
    
        // run on load
        updateSizes();
    
        // handle window resizing
        $(window).on('resize', function() {
            updateSizes();
        });
    
    }());
    
  • 3

    使用jQuery,您可以跟踪窗口调整大小并使用jQuery更改画布的宽度 .

    这样的事情

    $( window ).resize(function() {
     		$("#myCanvas").width($( window ).width())
    });
    
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
    <canvas id="myCanvas" width="200" height="100" style="border:1px solid #000000;">
    
  • 335

    根据浏览器客户端的尺寸设置画布坐标空间的宽度和高度,需要在调整浏览器大小时调整大小和重绘 .

    一个不太复杂的解决方案是在Javascript变量中维护可绘制的维度,但是根据screen.width,screen.height维度设置画布尺寸 . 使用CSS来适应:

    #containingDiv { 
      overflow: hidden;
    }
    #myCanvas {
      position: absolute; 
      top: 0px;
      left: 0px;
    }
    

    浏览器窗口通常不会大于屏幕本身(除非屏幕分辨率被误报,因为它可能与非匹配的双显示器一样),因此背景将不会显示,像素比例也不会变化 . 除非您使用CSS来缩放画布,否则画布像素将与屏幕分辨率成正比 .

  • 18

    除非您希望画布自动升级您的图像数据('s what James Black'的答案谈到,但它看起来不太漂亮),您必须自己调整大小并重新绘制图像 . Centering a canvas

  • 1

    CSS

    body { margin: 0; } 
    canvas { display: block; }
    

    JavaScript

    window.addEventListener("load", function()
    {
        var canvas = document.createElement('canvas'); document.body.appendChild(canvas);
        var context = canvas.getContext('2d');
    
        function draw()
        {
            context.clearRect(0, 0, canvas.width, canvas.height);
            context.beginPath();
            context.moveTo(0, 0); context.lineTo(canvas.width, canvas.height); 
            context.moveTo(canvas.width, 0); context.lineTo(0, canvas.height); 
            context.stroke();
        }
        function resize()
        {
            canvas.width = window.innerWidth;
            canvas.height = window.innerHeight;
            draw();
        }
        window.addEventListener("resize", resize);
        resize();
    });
    
  • 4
    function resize() {
    
        var canvas = document.getElementById('game');
        var canvasRatio = canvas.height / canvas.width;
        var windowRatio = window.innerHeight / window.innerWidth;
        var width;
        var height;
    
        if (windowRatio < canvasRatio) {
            height = window.innerHeight;
            width = height / canvasRatio;
        } else {
            width = window.innerWidth;
            height = width * canvasRatio;
        }
    
        canvas.style.width = width + 'px';
        canvas.style.height = height + 'px';
    };
    
    window.addEventListener('resize', resize, false);
    
  • 20

    如果您对保留纵横比感兴趣并且在纯CSS中这样做(给定纵横比),您可以执行以下操作 . 关键是 ::content 元素上的 padding-bottom ,它调整了 container 元素的大小 . 它的大小相对于其父级的宽度,默认为 100% . 此处指定的比率必须与 canvas 元素上的大小比例相匹配 .

    // Javascript
    
    var canvas = document.querySelector('canvas'),
        context = canvas.getContext('2d');
    
    context.fillStyle = '#ff0000';
    context.fillRect(500, 200, 200, 200);
    
    context.fillStyle = '#000000';
    context.font = '30px serif';
    context.fillText('This is some text that should not be distorted, just scaled', 10, 40);
    
    /*CSS*/
    
    .container {
      position: relative; 
      background-color: green;
    }
    
    .container::after {
      content: ' ';
      display: block;
      padding: 0 0 50%;
    }
    
    .wrapper {
      position: absolute;
      top: 0;
      right: 0;
      left: 0;
      bottom: 0;
    }
    
    canvas {
      width: 100%;
      height: 100%;
    }
    
    <!-- HTML -->
    
    <div class=container>
      <div class=wrapper>
        <canvas width=1200 height=600></canvas>  
      </div>
    </div>
    
  • 0

    我正在使用sketch.js所以在我为画布运行init命令后,我用jquery更改了宽度和高度 . 它基于父元素的维度 .

    $('#DrawCanvas') . sketch() . attr('height',$('#DrawCanvas') . parent() . height()) . attr('width',$('#DrawCanvas') . . 父()宽度());

相关问题