In this article we will talk about what is JSX and why do we need JSX in react applications.We will also talk about basics of JSX and how to work with JSX .
What is JSX?
- JSX (JavaScript XML) is an XML-like syntax extension of JavaScript. Here “syntax extension” means that JSX is not valid Javascript. Web browsers can’t read it.
- It describes what the UI should look like.
- JSX may remind you of a template language, but it comes with the full power of JavaScript.
- JSX is not understood by the browser therefore react uses babel compiler to convert JSX into pure JavaScript which is understood by the browser.
Let us see a sample JSX code:
const element = <h1>Hello, world!</h1>;
The above code snippet somewhat looks like HTML and it also uses a JavaScript-like variable but is neither HTML nor JavaScript, it is JSX.
Why do we need JSX?
- It is faster than normal JavaScript as it performs optimizations while translating to regular JavaScript.
- JSX is not a necessity for react applications we can also use react without JSX but It makes react code simple and easy to understand.
- It makes easier for us to create templates.
- Instead of separating the markup and logic in separated files, React uses components for this purpose which contains both.
JSX Outer Elements
A JSX expression must have exactly one outermost element.
In other words, this code will work:
const paragraphs = ( <div id="i-am-the-outermost-element"> <p>I am a paragraph.</p> <p>I, too, am a paragraph.</p> </div>);
But this code will not work:
const paragraphs = ( <p>I am a paragraph.</p> <p>I, too, am a paragraph.</p>);
The first opening tag and the final closing tag of a JSX expression must belong to the same JSX element!
If you notice that a JSX expression has multiple outer elements, the solution is usually simple: wrap the JSX expression in a <div> </div>.
Using JavaScript expressions in JSX
In React we are allowed to use normal JavaScript expressions with JSX. To embed any javascript expression in a piece of code written in JSX we will have to wrap that expression in curly braces {}.
You can put any valid JavaScript expression inside the curly braces in JSX. For example, 2 + 2
, user.firstName
, or formatName(user)
are all valid JavaScript expressions. In the example below, we embed the result of calling a JavaScript function, formatName(user)
, into an element.
function formatName(user) {
return user.firstName + ' ' + user.lastName;
}
const user = {
firstName: 'Harper',
lastName: 'Perez'
};
const element = (
<h1>
Hello, {formatName(user)}!
</h1>
);
ReactDOM.render(
element,
document.getElementById('root')
);
If a JSX expression takes up more than one line, then you must wrap the multi-line JSX expression in parentheses.
This is to make sure we are avoiding JavaScript’s automatic semicolon insertion which will add semicolons (based on rules given by the JavaScript specifications) to terminate statements when we don’t necessarily want/expect that behavior in a JSX expression.
For example:
const theExample = ( <a href="https://www.example.com"> <h1> Click me! </h1> </a> );
JSX is an Expression Too
JSX is not understood by the browser therefore react uses Babel compiler (to convert JSX into pure javascript ) and after compilation, JSX expressions become regular JavaScript function calls and evaluate to JavaScript objects.
This means that you can use JSX inside of if
statements and for
loops, assign it to variables, accept it as arguments, and return it from functions:
function getGreeting(user) {
if (user) {
return <h1>Hello, {formatName(user)}!</h1>;
}
return <h1>Hello, Stranger.</h1>;
}
Here’s an example of a JSX element being saved in a variable:
const navBar = <nav>I am a nav bar</nav>;
Here’s an example of several JSX elements being stored in an object:
const myTeam = { center: <li>Benzo Walli</li>, powerForward: <li>Rasha Loa</li>, smallForward: <li>Tayshaun Dasmoto</li>, shootingGuard: <li>Colmar Cumberbatch</li>, pointGuard: <li>Femi Billon</li>};
Specifying Attributes with JSX
JSX elements can have attributes, just like HTML elements can. But instead of the normal naming convention of HTML, JSX uses camelCase convention for attributes.
For example,
const panda = <img src="images/panda.jpg" alt="panda" width="500px" height="500px" />;
We can also use custom attributes in JSX. For example ,
const element = <div>
<h1 className =
"hello"
>Hello World</h1>
<h2 data-sampleAttribute=
"sample"
> Custom attribute</h2>
< /div>;
Specifying attribute values : JSX allows us to specify attribute values in two ways:
- As string literals: We can specify the values of attributes as hard-coded strings using quotes:
const element = <div tabIndex="0"></div>;
- As javascript expressions: We can specify attributes as expressions using curly braces {}:
const varName="Honey"; var ele = <h1 className = {varName}>Hello!</h1>;
Note: We cannot use class and for attribute names used in Html, Instead we have to use className and htmlFor attribute in JSX. This is because JSX gets translated into JavaScript, and class
and for are the reserved words in JavaScript.
When JSX is rendered, JSX className
attributes are automatically rendered as class
attribute and htmlFor get rendered as for attribute .
Children in JSX
In JSX expressions that contain both an opening tag and a closing tag, the content between those tags is known as JSX children and is passed as a special prop: props.children
.
Specifying children : There are several different ways to pass children in JSX:
As String Literals :You can put a string between the opening and closing tags and props.children
will just be that string. For example:
<MyComponent> Hello world!</MyComponent>
props.children
in MyComponent
will simply be the string "Hello world!"
.
As JSX Children : You can provide more JSX elements as the children. This is useful for displaying nested components. For example:
<div>
Here is a list:
<ul>
<li>Item 1</li>
<li>Item 2</li>
</ul>
</div>
A React component can also return an array of elements:
render() {
// No need to wrap list items in an extra element!
return [
// Don't forget the keys :)
<li key="A">First item</li>,
<li key="B">Second item</li>,
<li key="C">Third item</li>,
];
}
As JavaScript Expressions : You can pass any JavaScript expression as children, by enclosing it within {}
. For example,
function Hello(props) {
return <div>Hello {props.addressee}!</div>;
}
As Functions : You can also pass function as JSX children .For example, if you have a custom component, you could have it take a callback as props.children
:
// Calls the children callback numTimes to produce a repeated component
function Repeat(props) {
let items = [];
for (let i = 0; i < props.numTimes; i++) {
items.push(props.children(i));
}
return <div>{items}</div>;
}
function ListOfTenThings() {
return (
<Repeat numTimes={10}>
{(index) => <div key={index}>This is item {index} in the list</div>}
</Repeat>
);
}
JSX Represents Objects
Babel compiles JSX down to React.createElement()
calls.For example,
Given below is the JSX expression assigning to a variable element.
const element = (
<h1 className="greeting">
Hello, world!
</h1>
);
const element = React.createElement(
'h1',
{className: 'greeting'},
'Hello, world!'
);
React.createElement()
create and return react element look like this :
// Note: this structure is simplified
const element = {
type: 'h1',
props: {
className: 'greeting',
children: 'Hello, world!'
}
};
These objects are called “React elements”. You can think of them as descriptions of what you want to see on the screen. React reads these objects and uses them to construct the DOM and keep it up to date.
Comments in JSX
JSX allows us to use comments as it allows us to use JavaScript expressions. Comments in JSX begins with / and ends with /. We can add comments in JSX by wrapping them in curly braces {} just like we did in the case of expressions. Below example shows how to add comments in JSX:
const element = <div>
<h1>Hello World !</h1>
{/ * This is a comment
in
JSX * /}
</div>;