skip to Main Content

I’m working in SolidJs and using HopeUi for some components.

I use the grid component from HopeUi, and I want to fill one of the grids with a canvas component.

The code for my App currently looks like this:


import './App.css'
import { Grid, GridItem } from "@hope-ui/solid"

function App() {

  return (
    <>
      <Grid 
        h="90vh" 
        templateRows="repeat(2, 1fr)" 
        templateColumns="repeat(5, 1fr)" 
        gap="$4"
      >
        <GridItem rowSpan={1} colSpan={1} bg="black" />
        <GridItem colSpan={2} bg="papayawhip" />
        <GridItem colSpan={2} bg="papayawhip" />
        <GridItem id='c' colSpan={5} bg="tomato">
          <canvas id='c' width='100vw' height='100vh' style="border:1px solid #000000;"/>
        </GridItem>
      </Grid>
    </>
  )
}

export default App

The resulting page looks like this:
enter image description here

I’ve tried setting the height and width to both 100% and 100vw/vh, but to no luck.

How can I make the canvas fill the parent grid without hardcoding the size?

3

Answers


  1. The width and height attributes of a canvas represent the number of pixels for drawing and should be integers. To visually fill the canvas within its positioned parent, you can use a function like this:

    function fitToContainer(canvas) {
      canvas.style.width = '100%';
      canvas.style.height = '100%';
      canvas.width = Math.floor(canvas.offsetWidth);
      canvas.height = Math.floor(canvas.offsetHeight);
    }
    
    // Example usage
    var canvas = document.querySelector('canvas');
    fitToContainer(canvas);
    
    
    Login or Signup to reply.
  2. According to specification, width and height properties of canvas will take values in px only (not vm or %).

    You can change its width and height with css or inline styling:

    CSS

    canvas {
       inline-size: 100vw; /*width*/
       block-size: 100vh;  /*height*/
    }
    

    HTML

    <canvas style="width:100vm"></canvas>
    

    Note that this doesn’t help with canvas width and height which they are real sizes that canvas API uses to determine your canvas dimensions and accordingly all shapes that it draws inside this canvas.
    You must use javascript for solving this:

    // you must have set it's sizes in css or style
    const canvas = document.querySelector("canvas");
    canvas.width = canvas.clientWidth;
    canvas.height = canvas.clientHeight;
    

    If you’re interested why canvas width and height properties not behave the same as css width and height, that’s because they are not for styling and actually not same as css width and height properties except for their names.

    They are just properties of canvas object like name is a property of foo object in:

    const foo = {name: 'mahdi'}
    
    Login or Signup to reply.
  3. As it is stated in the other answers, you need to need to use pixel value with the canvas element.

    If you need to interact with the underlying element imperatively, it is best to use a ref:

    function App() {
      let canvas;
    
      onMount(() => {
        // Intreact with the element
        canvas.width = canvas.clientWidth;
        canvas.height = canvas.clientHeight;
      });
    
      return <canvas ref={canvas} />;
    }
    

    You can find a working demo: https://www.solidjs.com/tutorial/bindings_forward_refs

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search