This post was the precursor to the Foundation-React Template.
React and Foundation are two different web UI frameworks addressing different needs. They evolve differently. Both of them are powerful on their own accord. Fusing them together may create superpower.
We will walk through the process of adding React into Foundation. We will start by installing both Foundation and React through command line interface (CLI). Then we will create a simple Todo web app. Along the way we will highlight the development process. But before all that, let us summarize React and Foundation. The details can be found at their respective websites. Both of them are well documented.
React is a run-time UI rendering engine. It renders dynamic UI elements in its own fast virtual DOM, and only update necessary changes to the slow browser DOM. This behaves like a double buffering DOM which makes any UI update feels fast. React wraps a UI rendering script in a component. A React component can be bound to a data set where any changes to the data will trigger UI re-rendering. The nature of the React script simplifies the process. We know that Javascript can be embedded into HTML. On the other hand, React's JSX notation allows HTML elements to be embedded in Javascript. This makes writing UI rendering script easier and more readable. We can treat a JSX script as a UI template wrapped as a component. The JSX script will then be preprocessed and fed into the run-time rendering engine.
Foundation is a UI tool-chain with style. Foundation is a responsive front-end framework. It enables modular design. It simplifies scripting with preprocessing such as for SASS which in the website says a "CSS with superpowers". It automates many development tasks using webpack, gulp, nodejs, etc. However, the Foundation's responsive front-end framework is not unique on the Internet. There are many other competing frameworks. The strength of Foundation is in its tool-chain which improves development process.
Adding React to Foundation will change the game. The days of plain scripting for HTML, CSS and Javascript to develop front-ends have long gone. The days of UI frameworks are also numbered. It is no more about scripting. Now, it is about productive development process which involves automation. We will never stop scripting but what we want is that all best practices to be automated.
Let's install Foundation CLI:
Then change to the newly created todo folder and run foundation watch:
The foundation watch is not merely a local server. It is a development server. It monitors all source files looking for changes. If there is a change in a source file then it will trigger preprocessors and other development automation tools against all source files. The distribution files will be updated. And the browser will be refreshed. These free developer from many repetitive tasks and save a lot of development time. Foundation makes used of gulp to do the job. So we will extend gulp for React.
Install React:
React uses babel preset to preprocess jsx files into standard Javascript. So we need to include babel into gulp together with the React's babel preset.
Install Gulp Babel for React:
Foundation uses gulp to automate sass preproccessor and monitor file changes during development. On any source file changed gulp will rebuild the project and refresh the browser. The configuration is done in the gulpfile.js.
Open the gulpfile.js and insert the following line after require('gulp'):
Insert the following line within function serve() and before gulp.watch("*.html"):
Now add react and react-dom references to the bottom of index.html before the line with "js/app.js" with the following lines:
That's all. Let's run foundation watch again to launch our todo app.
Todo is a simple app that uses a single jsx file. A bigger app will have many modules in many jsx files. Loading many javascript files into a web app is not a good practice. Each time we create a jsx file we will have to include the generated js file into the index.html file. The best approach is to pack all generated js files into a single js file. That will be another discussion.
Now we know how to use React in Foundation for Sites. The next logical step is to create a Foundation-React template so that we don't have to go through most or all of these steps again when we want to create another application. That also will be another discussion.
React and Foundation are two different web UI frameworks addressing different needs. They evolve differently. Both of them are powerful on their own accord. Fusing them together may create superpower.
We will walk through the process of adding React into Foundation. We will start by installing both Foundation and React through command line interface (CLI). Then we will create a simple Todo web app. Along the way we will highlight the development process. But before all that, let us summarize React and Foundation. The details can be found at their respective websites. Both of them are well documented.
React is a run-time UI rendering engine. It renders dynamic UI elements in its own fast virtual DOM, and only update necessary changes to the slow browser DOM. This behaves like a double buffering DOM which makes any UI update feels fast. React wraps a UI rendering script in a component. A React component can be bound to a data set where any changes to the data will trigger UI re-rendering. The nature of the React script simplifies the process. We know that Javascript can be embedded into HTML. On the other hand, React's JSX notation allows HTML elements to be embedded in Javascript. This makes writing UI rendering script easier and more readable. We can treat a JSX script as a UI template wrapped as a component. The JSX script will then be preprocessed and fed into the run-time rendering engine.
Foundation is a UI tool-chain with style. Foundation is a responsive front-end framework. It enables modular design. It simplifies scripting with preprocessing such as for SASS which in the website says a "CSS with superpowers". It automates many development tasks using webpack, gulp, nodejs, etc. However, the Foundation's responsive front-end framework is not unique on the Internet. There are many other competing frameworks. The strength of Foundation is in its tool-chain which improves development process.
Adding React to Foundation will change the game. The days of plain scripting for HTML, CSS and Javascript to develop front-ends have long gone. The days of UI frameworks are also numbered. It is no more about scripting. Now, it is about productive development process which involves automation. We will never stop scripting but what we want is that all best practices to be automated.
Installation
There are many ways to install Foundation. Let us do it with Foundation CLI. We are doing Javascript so it is ironic if we do not have node with npm on our development machine. Node has many uses other than serving application back-ends.Let's install Foundation CLI:
$ npm install --global foundation-cli
# or sudo npm install --global foundation-cli
And create a new Foundation project:$ foundation new
After you selected "Foundation for Sites" and called the project "todo", Foundation CLI will ask you which template you want to use. Choose "Basic template". And wait for it to setup the new project and download dependencies.Then change to the newly created todo folder and run foundation watch:
$ cd todo
$ foundation watch
It will run a local server hosting the new default app and launch it in your browser at http://localhost:3000/. We are going to replace the default app with our todo app. But before that, we need to install React. Stop foundation watch with ctrl-c. We will run it again later.The foundation watch is not merely a local server. It is a development server. It monitors all source files looking for changes. If there is a change in a source file then it will trigger preprocessors and other development automation tools against all source files. The distribution files will be updated. And the browser will be refreshed. These free developer from many repetitive tasks and save a lot of development time. Foundation makes used of gulp to do the job. So we will extend gulp for React.
Install React:
$ npm install react react-dom
React uses babel preset to preprocess jsx files into standard Javascript. So we need to include babel into gulp together with the React's babel preset.
Install Gulp Babel for React:
$ npm install --save-dev gulp-babel @babel/core @babel/preset-env @babel/preset-react
JSX
We are going to prepare jsx preprocessor which will be handled by babel-preset-react. And we want the jsx preprocessor to be automated by gulp.Foundation uses gulp to automate sass preproccessor and monitor file changes during development. On any source file changed gulp will rebuild the project and refresh the browser. The configuration is done in the gulpfile.js.
Open the gulpfile.js and insert the following line after require('gulp'):
var babel = require('gulp-babel');
And then insert the following code before function serve():function react() {
return gulp.src('jsx/*.jsx')
.pipe(babel({
presets: ['@babel/env', '@babel/react']
}))
.pipe(gulp.dest('js'))
.pipe(browserSync.stream());
};
The code above tells gulp to monitor all jsx files in the jsx folder. When there is a change in a file then pass the file to the babel React preset to preprocess it into a js file, and copy the js file into the js folder, and then notify the browser to refresh.Insert the following line within function serve() and before gulp.watch("*.html"):
gulp.watch("jsx/*.jsx", react);
And insert the following line after gulp.task('sass', sass) :gulp.task('react', react);
And insert 'react' to the last two lines so that they look like the following:gulp.task('serve', gulp.series('sass', 'react', serve));
gulp.task('default', gulp.series('sass', 'react', serve));
The final gulpfile.js will look like the following:var gulp = require('gulp');
var babel = require('gulp-babel');
var browserSync = require('browser-sync').create();
var $ = require('gulp-load-plugins')();
var autoprefixer = require('autoprefixer');
var sassPaths = [
'node_modules/foundation-sites/scss',
'node_modules/motion-ui/src'
];
function sass() {
return gulp.src('scss/app.scss')
.pipe($.sass({
includePaths: sassPaths,
outputStyle: 'compressed' // if css compressed **file size**
})
.on('error', $.sass.logError))
.pipe($.postcss([
autoprefixer({ browsers: ['last 2 versions', 'ie >= 9'] })
]))
.pipe(gulp.dest('css'))
.pipe(browserSync.stream());
};
function react() {
return gulp.src('jsx/*.jsx')
.pipe(babel({
presets: ['@babel/env', '@babel/react']
}))
.pipe(gulp.dest('js'))
.pipe(browserSync.stream());
};
function serve() {
browserSync.init({
server: "./"
});
gulp.watch("scss/*.scss", sass);
gulp.watch("jsx/*.jsx", react);
gulp.watch("*.html").on('change', browserSync.reload);
}
gulp.task('sass', sass);
gulp.task('react', react);
gulp.task('serve', gulp.series('sass', 'react', serve));
gulp.task('default', gulp.series('sass', 'react', serve));
Index.html
Let's clean up the index.html file to look like the following:<!doctype html>
<html class="no-js" lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="x-ua-compatible" content="ie=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Todo</title>
<link rel="stylesheet" href="css/app.css">
</head>
<body>
<div class="grid-x grid-padding-x">
<div class="cell">
<div id="todos-example"></div>
</div>
</div>
<script src="node_modules/jquery/dist/jquery.js"></script>
<script src="node_modules/what-input/dist/what-input.js"></script>
<script src="node_modules/foundation-sites/dist/js/foundation.js"></script>
<script src="js/app.js"></script>
</body>
</html>
In the code above we inserted the React todo app placeholder in a div with the id todos-example. And we wrapped the placeholder inside a Foundation grid cell.Now add react and react-dom references to the bottom of index.html before the line with "js/app.js" with the following lines:
<script src="node_modules/react/umd/react.development.js"></script>
<script src="node_modules/react-dom/umd/react-dom.development.js"></script>
App.jsx
Create jsx folder and create app.jsx file in the folder. Add the following React code to the app.jsx file:$(document).foundation();
class TodoApp extends React.Component {
constructor(props) {
super(props);
this.state = { items: [], text: '' };
this.handleChange = this.handleChange.bind(this);
this.handleSubmit = this.handleSubmit.bind(this);
}
render() {
return (
<div>
<h3>My TODO</h3>
<TodoList items={this.state.items} />
<form onSubmit={this.handleSubmit}>
<label htmlFor="new-todo">
What needs to be done?
</label>
<input
type="text"
id="new-todo"
onChange={this.handleChange}
value={this.state.text}
/>
<button type="submit" class="button">
Add #{this.state.items.length + 1}
</button>
</form>
</div>
);
}
handleChange(e) {
this.setState({ text: e.target.value });
}
handleSubmit(e) {
e.preventDefault();
if (!this.state.text.length) {
return;
}
const newItem = {
text: this.state.text,
id: Date.now()
};
this.setState(state => ({
items: state.items.concat(newItem),
text: ''
}));
}
}
class TodoList extends React.Component {
render() {
return (
<ul>
{this.props.items.map(item => (
<li key={item.id}>{item.text}</li>
))}
</ul>
);
}
}
ReactDOM.render(
<TodoApp />,
document.getElementById('todos-example')
);
Notice that Foundation is initialized on the first line.That's all. Let's run foundation watch again to launch our todo app.
$ foundation watch
Todo is a simple app that uses a single jsx file. A bigger app will have many modules in many jsx files. Loading many javascript files into a web app is not a good practice. Each time we create a jsx file we will have to include the generated js file into the index.html file. The best approach is to pack all generated js files into a single js file. That will be another discussion.
Now we know how to use React in Foundation for Sites. The next logical step is to create a Foundation-React template so that we don't have to go through most or all of these steps again when we want to create another application. That also will be another discussion.
Comments
Post a Comment