Beginning
on React by ClassComponent + HOC mode integration Five development, Full source sample:JavaScript | TypeScript.
- Preparation for the development environment.
- How to introduce Five SDK.
- Render a three-dimensional space in the screen.
Preparatory work
Development environment
- You need to prepare a modern browser.
Five Browser supports the following, please choose one of your families:
Safari | Safari on iOS | Chrome | Chrome for Android | Edge | Firefox |
---|---|---|---|---|---|
>= 9 | >= 9 | >= 49 | >= 93 | >= 13 | >= 45 |
- You need to install Node.jsand
Node.js
version of subdue >= 12.x in order to avoid historical compatibility problems.
Use development build tool
This example is initialized by ViteYou can initialize yourself with the code below.
- JavaScript
- TypeScript
# npm 6.x
npm create vite@latest my-vue-app --template react
# npm 7+, extra double-dash is needed:
npm create vite@latest my-vue-app -- --template react
# npm 6.x
npm create vite@latest my-vue-app --template react-ts
# npm 7+, extra double-dash is needed:
npm create vite@latest my-vue-app -- --template react-ts
Create the directory src/0.getting-started
for this tutorial under src
.
Each tutorial creates a new directory as a record that can be summarized and traced.When the course ends you will get:
src
├── 0.getting-started
├── 1.displaying-work
├── 2.knowing-state
...
This directory structure.The full code sample is also such a directory structure that you can always consult at any time.
If you are familiar with other development building tools such as Webpack
Snowpack
parcel
you can also use them.
Create HTML File
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<link rel="icon" href="data:;base64,iVBORw0KGgo=">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>started| Getting started</title>
<style>
* { margin: 0; padding: 0; }
html, body, #app { width: 100%; height: 100%; overflow: hidden; }
</style>
</head>
<body>
<div id="app"></div>
<script type="module" src="./index"></script>
</body>
</html>
Using direct import <script type="module" src="./index"></script>
is a feature of Vite ,
If you use other development and construction tools, please handle code import and entry files by yourself. Like HtmlWebpackPlugin under webpack and more.
Write test logical code
We first create a simple
Hello World
to make sure that the whole code is running.
- JavaScript
- TypeScript
const app = document.querySelector("#app");
app.innerHTML = "Hello World.";
export {};
const app = document.querySelector("#app")!;
app.innerHTML = "Hello World.";
export {};
Last export {};
because Vite uses type="module"
to introduce, each file needs to be a module
, needs export
.
If you use other development build tools, please write them as required by your own development build.
Start service npm run dev
and jump to the current page "http://localhost:3000/src/0.getting-started/index.html".
Please see your console. The port number will change due to your configuration and current port occupancy, please check the console output. If you use another development build tool, please start the service as required by your own development build tool.
Then you will see it on the page
Hello World.
This output indicates that the development of build tools has been completed.
The next sections will not elaborate further on the above steps and please do so together.
Install dependencies from npm
Install dependency in your project directory
- JavaScript
- TypeScript
npm install @realsee/five three
.117 react react-dom-wordpress/compose
rely on needs
- @realsee/five Five
- three three.js is Five dependencies/mathematical library. Currently please use version of 0.117.x - react React Framework
- [react-dom](https://npmjs.com/ react-dom) Browser-side renderer for React
- HOC wrapper for @wordpress/compose React HOC
npm install @realsee/five three@0.117 react react-dom @types/react @types/react-dom @wordpress/compose
relies for
- @realsee/five Five
- three three.js is Five Dependent Graphs/Mathemes. Currently please use version 0.117.x of
- react React Framework
- react-dom browser renderer
- [@typees/react](https://npmjs. om/@types/react) Type Statement for React Framework
- @types/react-dom React Browser Typebook Type Statement for Reactor
- @wordpress/compose React HOC Packager
Render a three-dimensional space
It's time to render a VR scene.
Load 3D space
Delete your previous Hello World
.We shall rewrite.
You can first fail to understand what the code will mean, and you will learn from the next chapter.
- JavaScript
- TypeScript
import React, { Component, ComponentClass } from "react";
import ReactDOM from "react-dom";
import { Work, parseWork } from "@realsee/five";
import { createFiveProvider, FiveCanvas } from "@realsee/five/react";
import { compose } from "@wordpress/compose";
/** Data URL of work.json */
const workURL = "https://vrlab-public.ljcdn.com/release/static/image/release/five/work-sample/07bdc58f413bc5494f05c7cbb5cbdce4/work.json";
/**
* React HOC gets work
* @param url work.json address
*/
function withFetchWork(url) {
return function(Compnent) {
return class extends Component {
state = { work: null };
componentDidMount() {
fetch(url).then(res => res.json()).then(json => {
this.setState({ work: parseWork(json) });
});
}
render() {
if (this.state.work === null) return null;
return <Compnent work={this.state.work} {...this.props}/>;
}
}
}
}
const FiveProvider = createFiveProvider();
const App = compose(
withFetchWork(workURL)
)(class extends Component {
render() {
const { work } = this.props;
return <FiveProvider initialWork={work}>
<FiveCanvas width={512} height={512}/>
</FiveProvider>;
}
});
ReactDOM.render(<App/>, document.querySelector("#app"));
export {};
import React, { Component, ComponentClass } from "react";
import ReactDOM from "react-dom";
import { Work, parseWork } from "@realsee/five";
import { createFiveProvider, FiveCanvas } from "@realsee/five/react";
import { compose } from "@wordpress/compose";
/** work. The data URL */
const workURL = "https://vrlab-public.ljcdn.com/release/static/image/release/five/work-sample/07bdc58f413bc5494f05c7cbb5cbdce4/work.json";
/**
* React HOC get work
* @param url work.json address
*/
function withFetchWork<P extends Record<string, any>>(url: string) {
return function(Compnent: ComponentClass<P & { work: Work }>): ComponentClass<P> {
return class extends Component<P, {work: Work | null}> {
state = { work: null };
componentDidMount() {
fetch(url).then(res => res.json()).then(json => {
this.setState({ work: parseWork(json) });
});
}
render() {
if (this.state.work === null) return null;
return <Compnent work={this.state.work} {...this.props}/>;
}
}
}
}
const FiveProvider = createFiveProvider();
const App = compose(
withFetchWork(workURL)
)(class extends Component<{work: Work}> {
render() {
const { work } = this.props;
return <FiveProvider initialWork={work}>
<FiveCanvas width={512} height={512}/>
</FiveProvider>;
}
})
ReactDOM.render(<App/>, document.querySelector("#app"));
export {};
Go back to your browser, see if there is already a three-dimensional position displayed on the left. You can use the mouse or touch the gesture. Basic browsing features are attached.
Make the screen full
While the working principles of the above code may not be fully understood, we can see FiveCanvas
affected by width
and height
properties, very much like the size of the picture.This guess is also supported by the position of the picture in the upper left corner of the browser.For each time, they are used to set screen size.
That's how we try to use React Hooks with our familiarity and lay it over the screen.
- JavaScript
- TypeScript
import React, { Component } from "react";
import ReactDOM from "react-dom";
import { parseWork } from "@realsee/five";
import { createFiveProvider, FiveCanvas } from "@realsee/five/react";
import { compose } from "@wordpress/compose";
/** Data URL of work.json */
const workURL = "https://vrlab-public.ljcdn .com/release/static/image/release/five/work-sample/07bdc58f413bc5494f05c7cbb5cbdce4/work.json";
/**
* React HOC gets work
* @param url work.json address
*/
function withFetchWork(url) {
return function(Compnent) {
return class extends Component {
state = { work: null };
componentDidMount() {
fetch(url).then(res => res.json()).then(json => {
this.setState({ work: parseWork(json) });
});
}
render() {
if (this.state.work === null) return null;
return <Compnent work={this.state.work} {...this.props}/>;
}
}
}
}
/**
* React HOC: Get the dimensions of the current
*/
function withWindowDimensions() {
return function(Compnent) {
return class extends Component {
state = this.getWindowDimensions();
resizeListener = () => {
this.setState(this.getWindowDimensions());
};
getWindowDimensions() {
return { width: window.innerWidth, height: window.innerHeight };
}
componentDidMount() {
window.addEventListener("resize", this.resizeListener, false);
}
componentWillUnmount() {
window.removeEventListener("resize", this.resizeListener, false);
}
render() {
const dimensions = { width: this.state.width, height: this.state.height };
return <Compnent windowDimensions={dimensions} {...this.props}/>;
}
}
}
}
const FiveProvider = createFiveProvider();
const App = compose(
withFetchWork(workURL),
withWindowDimensions()
)(
class extends Component {
render() {
const { work, windowDimensions } = this.props;
return <FiveProvider initialWork={work}>
<FiveCanvas width={windowDimensions.width} height={windowDimensions.height}/>
</FiveProvider>;
}
})
ReactDOM.render(<App/>, document.querySelector("#app"));
export {};
import React, { Component, ComponentClass } from "react";
import ReactDOM from "react-dom";
import { Work, parseWork } from "@realsee/five";
import { createFiveProvider, FiveCanvas } from "@realsee/five/react";
import { compose } from "@wordpress/compose";
/** work. The data URL */
const workURL = "https://vrlab-public.ljcdn.com/release/static/image/release/five/work-sample/07bdc58f413bc5494f05c7cbb5cbdce4/work.json";
/**
* React HOC get work
* @param url work.json address
*/
function withFetchWork<P extends Record<string, any>>(url: string) {
return function(Compnent: ComponentClass<P & { work: Work }>): ComponentClass<P> {
return class extends Component<P, {work: Work | null}> {
state = { work: null };
componentDidMount() {
fetch(url).then(res => res.json()).then(json => {
this.setState({ work: parseWork(json) });
});
}
render() {
if (this.state.work === null) return null;
return <Compnent work={this.state.work} {...this.props}/>;
}
}
}
}
/**
* React HOC: Get the current window size
*/
function withWindowDimensions<P extends Record<string, any>>() {
return function(Compnent: ComponentClass<P & { windowDimensions: { width: number, height: number} }>): ComponentClass<P> {
return class extends Component<P, {width: number, height: number}> {
state = this.getWindowDimensions();
resizeListener = () => {
this.setState(this.getWindowDimensions());
};
getWindowDimensions() {
return { width: window.innerWidth, height: window.innerHeight };
}
componentDidMount() {
window.addEventListener("resize", this.resizeListener, false);
}
componentWillUnmount() {
window.removeEventListener("resize", this.resizeListener, false);
}
render() {
const dimensions = { width: this.state.width, height: this.state.height };
return <Compnent windowDimensions={dimensions} {...this.props}/>;
}
}
}
}
const FiveProvider = createFiveProvider();
const App = compose(
withFetchWork(workURL),
withWindowDimensions()
)(class extends Component<{work: Work, windowDimensions: { width: number, height: number }}> {
render() {
const { work, windowDimensions } = this.props;
return <FiveProvider initialWork={work}>
<FiveCanvas width={windowDimensions.width} height={windowDimensions.height}/>
</FiveProvider>;
}
})
ReactDOM.render(<App/>, document.querySelector("#app"));
export {};
Go back to your browser and see if it does not meet expectations.
Your stick🥳 !
Split Code
All our codes are currently written in a js / ts file.While all logic can be seen at first glance, it is more confusing.The splitting of content into more than one document will improve this.
- Split
App
to separate files. - Split
to separate files with FetchWork
. - Split
to separate files without Windows Dimensions
method.
- JavaScript
- TypeScript
src/0.getting-started/withFetchWork.jsx
import React, { Component } from "react";
import { parseWork } from "@realsee/five";
/**
* React HOC for work
* @param url work. Son's address
*/
function withFetchWork(url) {
return function(Compnent) {
return class extends Component {
state = { work: null };
componentDidMount() {
fetch(url).then(res => res.json()).then(json => {
this.setState({ work: parseWork(json) });
});
}
render() {
if (this.state.work === null) return null;
return <Compnent work={this.state.work} {...this.props}/>;
}
}
}
}
export { withFetchWork };
src/0.getting-started/withWindowDimensions.jsx
import React, { Component } from "react";
/**
* React HOC: Get the size of the current window
*/
function withWindowDimensions() {
return function(Compnent) {
return class extends Component {
state = this.getWindowDimensions();
resizeListener = () => {
this.setState(this.getWindowDimensions());
};
getWindowDimensions() {
return { width: window.innerWidth, height: window.innerHeight };
}
componentDidMount() {
window.addEventListener("resize", this.resizeListener, false);
}
componentWillUnmount() {
window.removeEventListener("resize", this.resizeListener, false);
}
render() {
const dimensions = { width: this.state.width, height: this.state.height };
return <Compnent windowDimensions={dimensions} {...this.props}/>;
}
}
}
}
export { withWindowDimensions };
src/0.getting-started/App.jsx
import React, { Component } from "react";
import { compose } from "@wordpress/compose";
import { createFiveProvider, FiveCanvas } from "@realsee/five/react";
import { withFetchWork } from "./withFetchWork";
import { withWindowDimensions } from "./withWindowDimensions";
/** of work.json Data URL */
const workURL = "https://vrlab-public.ljcdn.com/release/static/image/release/five/work-sample/07bdc58f413bc5494f05c7cbb5cbdce4/work.json";
const FiveProvider = createFiveProvider();
const App = compose(
withFetchWork(workURL),
withWindowDimensions()
)(class extends Component {
render() {
const { work, windowDimensions } = this.props;
return <FiveProvider initialWork={work}>
<FiveCanvas width={windowDimensions.width} height={windowDimensions.height}/>
</FiveProvider>;
}
});
export { App };
src/0.getting-started/index.jsx
import React from "react";
import ReactDOM from "react-dom";
import { App } from "./App";
ReactDOM.render(<App/>, document.querySelector("#app"));
export {};
src/0.getting-started/withFetchWork.tsx
import React, { Component, ComponentClass } from "react";
import { Work, parseWork } from "@realsee/five";
/**
* React HOC get work
* @param url work. Son address
*/
function withFetchWork<P extends Record<string, any>>(url: string) {
return function(Compnent: ComponentClass<P & { work: Work }>): ComponentClass<P> {
return class extends Component<P, {work: Work | null}> {
state = { work: null };
componentDidMount() {
fetch(url).then(res => res.json()).then(json => {
this.setState({ work: parseWork(json) });
});
}
render() {
if (this.state.work === null) return null;
return <Compnent work={this.state.work} {...this.props}/>;
}
}
}
}
export { withFetchWork };
src/0.getting-started/withWindowDimensions.tsx
import React, { Component, ComponentClass } from "react";
/**
* React HOC: Get the current window size
*/
function withWindowDimensions<P extends Record<string, any>>() {
return function(Compnent: ComponentClass<P & { windowDimensions: { width: number, height: number} }>): ComponentClass<P> {
return class extends Component<P, {width: number, height: number}> {
state = this.getWindowDimensions();
resizeListener = () => {
this.setState(this.getWindowDimensions());
};
getWindowDimensions() {
return { width: window.innerWidth, height: window.innerHeight };
}
componentDidMount() {
window.addEventListener("resize", this.resizeListener, false);
}
componentWillUnmount() {
window.removeEventListener("resize", this.resizeListener, false);
}
render() {
const dimensions = { width: this.state.width, height: this.state.height };
return <Compnent windowDimensions={dimensions} {...this.props}/>;
}
}
}
}
export { withWindowDimensions };
src/0.getting-started/App.tsx
import React, { Component } from "react";
import { Work } from "@realsee/five";
import { createFiveProvider, FiveCanvas } from "@realsee/five/react";
import { compose } from "@wordpress/compose";
import { withFetchWork } from "./withFetchWork";
import { withWindowDimensions } from "./withWindowDimensions";
/** Data URL of work.json */
const workURL = "https://vrlab-public.ljcdn.com/release/static/image/release/five/work-sample/07bdc58f413bc5494f05c7cbb5cbdce4/work.json";
const FiveProvider = createFiveProvider();
const App = compose(
withFetchWork(workURL),
withWindowDimensions()
)(class extends Component<{work: Work, windowDimensions: { width: number, height: number }}> {
render() {
const { work, windowDimensions } = this.props;
return <FiveProvider initialWork={work}>
<FiveCanvas width={windowDimensions.width} height={windowDimensions.height}/>
</FiveProvider>;
}
});
export { App };
src/0.getting-started/index.tsx
import React from "react";
import ReactDOM from "react-dom";
import { App } from "./App";
ReactDOM.render(<App/>, document.querySelector("#app"));
export {};
It is not more comfortable.Each document is succinct and easy to understand their respective roles.
The next section will be completed by you
- Learn what is working.
- Learn how to work with the code just now, such as
FiveProvider
/FveCanvas
.