React Avatar Editor .

I do as an example:

<Dropzone onDrop={this.handleDrop} disableClick style={{ width: '250px', height: '250px' }}> <AvatarEditor ref={this.refAvatar} image={this.state.image} borderRadius={125} width={250} height={250} border={0} scale={1} /> </Dropzone> 

Everything looks right in the editor:

enter image description here

Treatment:

 handleDrop = dropped => { this.setState({ image: dropped[0] }) }; onClickSave = () => { // This returns a HTMLCanvasElement, it can be made into a data URL or a blob, // drawn on another canvas, or added to the DOM. const canvas = this.refAvatar.current.getImage(); // If you want the image resized to the canvas size (also a HTMLCanvasElement) const canvasScaled = this.refAvatar.current.getImageScaledToCanvas(); const img = canvasScaled.toDataURL(); const rect = this.refAvatar.current.getCroppingRect(); }; 

As a result, there is a canvasScaled (here is a cropped square picture) and rect .

And how to get a round picture? In their demo in the preview, the roundness is obtained at the expense of css: border-radius: 52.5px; . It will not help me to get a round pikchu and send to the server.

  • And you can ask, why not round off on the server? Fear of stress or something else? - andreymal
  • @andreymal extra load, absolutely no good. - Suvitruf
  • And you can still ask what the client border-radius didn’t please, why exactly the round picture?) - andreymal
  • @andreymal is actually an interesting question) - Suvitruf

1 answer 1

  1. Created an invisible canvas .

     <canvas style={{display: "none"}} ref={this.refCanvas} width={250} height={250} /> 
  2. I draw a cropped square image into it.
  3. I prune everything outside the circle.
  4. I get the final image.
  5. I send to the server.

Processing is now such:

 onClickSave = () => { const canvasScaled = this.refAvatar.current.getImageScaledToCanvas(); const img = canvasScaled.toDataURL(); const rect = this.refAvatar.current.getCroppingRect(); this.drawPreview(img, rect); }; drawPreview = (img, rect) => { const image = new Image(); image.src = img; image.onload = _ => {this.handleImageLoad(image)}; }; handleImageLoad = (image) => { const ctx = this.refCanvas.current.getContext('2d'); const width = 250; const height = 250; ctx.clearRect(0, 0, width, height); ctx.arc(125,125, 125, 0, Math.PI*2,true); ctx.clip(); ctx.drawImage(image, 0, 0, width, height); axios.post('http://localhost:8081/upload', {img: this.refCanvas.current.toDataURL()}, { 'Accept': 'application/json' }).then((response) => { console.log(response); }) .catch(err => { console.log(err); }); }; 

On the server, processing is trivial, there are express:

 app.post('/upload', (req, res) => { const data = req.body.img.replace(/^data:image\/\w+;base64,/, ""); const buf = new Buffer(data, 'base64'); fs.writeFile(__dirname + '/../public/image.png', buf); }); 

The picture is round:

enter image description here