Creating a HTML Game in React Native - Part One
Introduction
This will be the first of many posts that I will make to log my journey in getting a game in HTML to an android or IOS architecture. To make this journey, I decided to plump on using React Native, seeing how my professional life dictates currently that I need to be proficient in it.
So how did I decide to get a game going? Well with React being my primary library that I use to create new websites or web applications, decide to use the library to create my HTML game, firstly on a website, and then eventually onto a mobile platform via React Native. As I also wanted to manage my code in a reusable way, I also decided to use Nx to manage my code, so I could publish both to web and Mobile and reuse as much code as possible.
OK, so onto the coding.
Oh, and by the way, you can see the full code repo for this lesson here:
https://github.com/jayjaybeeuk/react-native-game-1
Setting up the application base
In order to get the system ready, we are going to make some assumptions in that we are running Node LTS 18+. So, to get our base application up and running, we run the following command:
npx create-nx-workspace@latest
From here, you select the choices:
✔ Choose what to create - Integrated Mono Repo
✔ What to create in the new workspace · React
✔ Repository name · react-native-game-1
✔ Application name · react-app
✔ Default stylesheet format · styled-components
✔ Enable distributed caching to make your CI faster · Yes
This should create an application called `react-app` which will be a React application to hold and showcase our game modules. It should create files and directories roughly like below in the apps
folder:
react-app/
├── src/
├── .babelrc
├── .browserslintrc
├── .eslintrc.json
├── jest.config.ts
├── project.json
├── tsconfig.app.json
├── tsconfig.json
└── tsconfig.spec.json
This will give us a default page created automatically by NX that will run if we run the following command:
nx serve react-app
This will start the application on `localhost:4200` to give you the following:
Creating a Game Module
So now we have created an application base, let's set about creating a basic Canvas game that we can insert inside of it. To do this, run the following:
npx nx g @nrwl/react:library game-module
You should choose the following features:
✔ Which bundler would you like to use to build the library? - None
✔ What unit test runner should be used · Jest
This will give you the files in the libs
folder:
game-module/
├── src/
├── .babelrc
├── .browserslintrc
├── .eslintrc.json
├── jest.config.ts
├── project.json
├── tsconfig.app.json
├── tsconfig.json
└── tsconfig.spec.json
The contents of this will be very simple, with the file game-module/src/lib/game-module.tsx
looking like so:
import styled from 'styled-components';
/* eslint-disable-next-line */
export interface GameModuleProps {}
const StyledGameM = styled.div` color: pink;`;
export function GameModule(props: GameModuleProps) {
return (
<StyledGameModule>
<h1>Welcome to GameModule!</h1>
</StyledGameModule>
);
So we're going to quickly turn this into an HTML test be replacing the above with code like this:
}
export default GameModule;
import { useRef, useEffect } from 'react';
import styled from 'styled-components';
/* eslint-disable-next-line */
export interface GameModuleProps {}
const StyledGameModule = styled.div`
color: pink;
`;
export function GameModule(props: GameModuleProps) {
//1. useRef to get the Canvas from the render
const canvasRef = useRef<HTMLCanvasElement>(null);
//2. useEffect is used to affect the canvas once the ref has been got
useEffect(() => {
//3. We need to get the 'current' from the ref
const canvas = canvasRef.current;
if (canvas != null) {
//4. Get the context
const ctx = canvas.getContext('2d');
if (ctx != null) {
//5. Apply the canvas changes to give us our hello world
ctx.font = '34px serif';
ctx.textAlign = 'center';
ctx.textBaseline = 'middle';
ctx.fillStyle = '#000000';
ctx.fillText('Hello World', 150, 50);
}
}
}, [canvasRef]);
return (
<StyledGameModule>
<canvas ref={canvasRef} width="300" height="100"></canvas>
</StyledGameModule>
);
}
export default GameModule;
Now we have a Game Module, we need to inject this into our React Application.
Adding the Game Module to the React App
Now we have the module, we can change our React App to show the module into a page. To do this, we need to go to the directory apps/react-app/src/app/
and delete the file nx-welcome.tsx
. We can then go into the file App.tsx
in the same directory and change the file to insert our new module that we have created. This can be done by changing these lines:
✖ import NxWelcome from'./nx-welcome';
✔ import { GameModule } from'@react-app/game-module';
✖ <NxWelcome title="react-app"/>
✔ <GameModule/>
If you run the app again via nx serve react-app
and go to http://localhost:4200
you will get that following screen:
Impressive, huh? OK, Maybe not quite, but we will add more functionality in the next instalment. This is going to start as a simple proof of concept in React Native before we return to the game