我们如何在 canvas 上加载本地图像?
How could we load a local image on a canvas?
您好,感谢您花时间阅读这个问题:
我正在尝试做一个学习 React 的练习,因为我最近在 JS 中做了一个代码,从本地加载一个文件,一个图像,到 canvas,然后当用户点击绘制圆圈;我尝试在 React 中做同样的事情。
我在 Canvas' 组件的 render() 中创建了一个 canvas,然后调用 make_base 函数获取上下文并将图像加载到其中。
代码如下:
import React from 'react';
class Canvas extends React.Component {
//A canvas to display images with a title
constructor(props) {
super(props);
this.state = {x: 0, y: 0, inside: ''};
this.handleClick = this.handleClick.bind(this);
this.make_base = this.make_base.bind(this);
}
_onMouseMove(e) {
this.setState({x: e.nativeEvent.offsetX, y: e.nativeEvent.offsetY});
}
componentDidMount() {
document.addEventListener('click', this.handleClick);
}
componentWillUnmount() {
document.removeEventListener('click', this.handleClick);
}
handleClick(e) {
e.stopPropagation();
console.log('INSIDE');
this.setState({inside: 'inside'});
}
make_base(image) {
const context = this.refs.canvas.getContext('2d');
let base_image = new Image();
base_image.src = image;
base_image.onload = function () {
context.drawImage(base_image, 0, 0);
}
}
render() {
const {x, y, inside} = this.state;
return (
<div className="previewComponent">
<div className="imgPreview">
{this.props.title}
<canvas ref="canvas" width={300} height={300}></canvas>
{this.make_base(this.props.image)}
<img src={this.props.image} alt="" onMouseMove={this._onMouseMove.bind(this)}
onClick={this.handleClick.bind(this)}/>
<h1>Mouse coordinates: {x} {y}</h1>
<h2>Inside?: {inside}</h2>
</div>
</div>
)
}
}
export {Canvas};
控制台告诉我们:
TypeError: Cannot read property 'getContext' of undefined
Canvas.make_base
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:36
33 | }
34 |
35 | make_base(image) {
> 36 | const context = this.refs.canvas.getContext('2d');
37 | let base_image = new Image();
38 | base_image.src = image;
39 | base_image.onload = function () {
View compiled
Canvas.render
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:55
52 | {this.props.title}
53 |
54 | <canvas ref="canvas" width={300} height={300}></canvas>
> 55 | {this.make_base(this.props.image)}
56 |
57 | <img src={this.props.image} alt="" onMouseMove={this._onMouseMove.bind(this)}
58 | onClick={this.handleClick.bind(this)}/>
如果假设我们已经在 render() 方法中创建了 canvas,我不明白为什么 getContext() 会变得未定义。
另外我研究过:
https://blog.lavrton.com/using-react-with-html5-canvas-871d07d8d753
How to add image to canvas
编辑:
我已经尝试了建议的答案,控制台仍然告诉我们:
TypeError: Cannot read property 'getContext' of undefined
Canvas.make_base
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:36
33 | }
34 |
35 | make_base(image) {
> 36 | const context = this.canvas.getContext('2d');
37 | let base_image = new Image();
38 | base_image.src = image;
39 | base_image.onload = function () {
View compiled
Canvas.render
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:55
52 | {this.props.title}
53 |
54 | <canvas ref={(canvas) => this.canvas = canvas} width={300} height={300}></canvas>
> 55 | {this.make_base(this.props.image)}
56 |
57 | <img src={this.props.image} alt="" onMouseMove={this._onMouseMove.bind(this)}
58 | onClick={this.handleClick.bind(this)}/>
View compiled
如果我们注释正在写入上下文的行,我们会看到两个空 canvas:
也许 canvas 不应该在 render 方法中创建,因为它仍然不能被外部方法访问?
EDIT2:给定的答案很有效:
但是我们想在光标所在的地方而不是按钮上绘制鼠标点击,所以这就是问题,我们如何获取坐标并将它们关联起来以在 canvas?
感谢您的帮助。
您使用的引用有误。
您必须将 ref 设置为 class 变量,如 this.canvas
class App extends React.Component {
constructor(props) {
super(props);
this.makeBase = this.makeBase.bind(this);
this.recordMouse = this.recordMouse.bind(this);
}
recordMouse(event) {
const ctx = this.canvas.getContext('2d');
ctx.beginPath();
ctx.fillRect(event.nativeEvent.offsetX,event.nativeEvent.offsetY,3,3);
ctx.stroke();
}
makeBase() {
const ctx = this.canvas.getContext('2d');
ctx.beginPath();
ctx.arc(95,50,40,0,2*Math.PI);
ctx.stroke();
}
render() {
return (
<div>
<canvas ref={(canvas)=>this.canvas=canvas} width="200" height="100" onMouseMove={this.recordMouse} />
<button onClick={this.makeBase}>Make Base</button>
</div>
);
}
}
ReactDOM.render(<App />, document.getElementById("root"));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<div id="root"></div>
您好,感谢您花时间阅读这个问题:
我正在尝试做一个学习 React 的练习,因为我最近在 JS 中做了一个代码,从本地加载一个文件,一个图像,到 canvas,然后当用户点击绘制圆圈;我尝试在 React 中做同样的事情。
我在 Canvas' 组件的 render() 中创建了一个 canvas,然后调用 make_base 函数获取上下文并将图像加载到其中。
代码如下:
import React from 'react';
class Canvas extends React.Component {
//A canvas to display images with a title
constructor(props) {
super(props);
this.state = {x: 0, y: 0, inside: ''};
this.handleClick = this.handleClick.bind(this);
this.make_base = this.make_base.bind(this);
}
_onMouseMove(e) {
this.setState({x: e.nativeEvent.offsetX, y: e.nativeEvent.offsetY});
}
componentDidMount() {
document.addEventListener('click', this.handleClick);
}
componentWillUnmount() {
document.removeEventListener('click', this.handleClick);
}
handleClick(e) {
e.stopPropagation();
console.log('INSIDE');
this.setState({inside: 'inside'});
}
make_base(image) {
const context = this.refs.canvas.getContext('2d');
let base_image = new Image();
base_image.src = image;
base_image.onload = function () {
context.drawImage(base_image, 0, 0);
}
}
render() {
const {x, y, inside} = this.state;
return (
<div className="previewComponent">
<div className="imgPreview">
{this.props.title}
<canvas ref="canvas" width={300} height={300}></canvas>
{this.make_base(this.props.image)}
<img src={this.props.image} alt="" onMouseMove={this._onMouseMove.bind(this)}
onClick={this.handleClick.bind(this)}/>
<h1>Mouse coordinates: {x} {y}</h1>
<h2>Inside?: {inside}</h2>
</div>
</div>
)
}
}
export {Canvas};
控制台告诉我们:
TypeError: Cannot read property 'getContext' of undefined
Canvas.make_base
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:36
33 | }
34 |
35 | make_base(image) {
> 36 | const context = this.refs.canvas.getContext('2d');
37 | let base_image = new Image();
38 | base_image.src = image;
39 | base_image.onload = function () {
View compiled
Canvas.render
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:55
52 | {this.props.title}
53 |
54 | <canvas ref="canvas" width={300} height={300}></canvas>
> 55 | {this.make_base(this.props.image)}
56 |
57 | <img src={this.props.image} alt="" onMouseMove={this._onMouseMove.bind(this)}
58 | onClick={this.handleClick.bind(this)}/>
如果假设我们已经在 render() 方法中创建了 canvas,我不明白为什么 getContext() 会变得未定义。
另外我研究过:
https://blog.lavrton.com/using-react-with-html5-canvas-871d07d8d753
How to add image to canvas
编辑:
我已经尝试了建议的答案,控制台仍然告诉我们:
TypeError: Cannot read property 'getContext' of undefined
Canvas.make_base
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:36
33 | }
34 |
35 | make_base(image) {
> 36 | const context = this.canvas.getContext('2d');
37 | let base_image = new Image();
38 | base_image.src = image;
39 | base_image.onload = function () {
View compiled
Canvas.render
C:/Users/YonePC/WebstormProjects/prototipo/src/components/animals/Canvas.js:55
52 | {this.props.title}
53 |
54 | <canvas ref={(canvas) => this.canvas = canvas} width={300} height={300}></canvas>
> 55 | {this.make_base(this.props.image)}
56 |
57 | <img src={this.props.image} alt="" onMouseMove={this._onMouseMove.bind(this)}
58 | onClick={this.handleClick.bind(this)}/>
View compiled
如果我们注释正在写入上下文的行,我们会看到两个空 canvas:
也许 canvas 不应该在 render 方法中创建,因为它仍然不能被外部方法访问?
EDIT2:给定的答案很有效:
但是我们想在光标所在的地方而不是按钮上绘制鼠标点击,所以这就是问题,我们如何获取坐标并将它们关联起来以在 canvas?
感谢您的帮助。
您使用的引用有误。
您必须将 ref 设置为 class 变量,如 this.canvas
class App extends React.Component {
constructor(props) {
super(props);
this.makeBase = this.makeBase.bind(this);
this.recordMouse = this.recordMouse.bind(this);
}
recordMouse(event) {
const ctx = this.canvas.getContext('2d');
ctx.beginPath();
ctx.fillRect(event.nativeEvent.offsetX,event.nativeEvent.offsetY,3,3);
ctx.stroke();
}
makeBase() {
const ctx = this.canvas.getContext('2d');
ctx.beginPath();
ctx.arc(95,50,40,0,2*Math.PI);
ctx.stroke();
}
render() {
return (
<div>
<canvas ref={(canvas)=>this.canvas=canvas} width="200" height="100" onMouseMove={this.recordMouse} />
<button onClick={this.makeBase}>Make Base</button>
</div>
);
}
}
ReactDOM.render(<App />, document.getElementById("root"));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<div id="root"></div>