目录
jsx基本概念及例子
jsx的基本用法
JSX表达式(有执行结果)
{} 语法嵌入不同的值 所呈现出来的特点
标签内行内样式
自定义组件
驼峰命名
Jsx的全称是Javascript XML,react定义的一种类似XML的JS拓展语法:JS+XML,使我们可以用类似于xml方式描述视图。
本质是React.createElement(component, props, ...children) 的语法糖
原理:babel-loader会预编译JSx为React.createElement(type,props,...children)
虚拟DOM是React.createElement产生的
优点:执行快,类型安全,简单快速 执行需要使用预编译器
作用:用来简化创建虚拟DOM
- 写法: var ele = <h1>Hello Jsx!</h1>
- 注意1:它不是字符串,也不是HTML/XML标签,不要写引号
- 注意2:它最终产生的是一个JS对象,需要使用 {}运行js表达式
- 注意3:样式类名指定不要用class,要用className(因为class是ES6内定义的关键字,所以这里需要使用className进行区分)
- 注意4:内联样式,要用style={{key:value}} 的形式去写。
- 注意5:只能有一个根标签。
- 注意6:标签必须闭合。
- 注意7:标签首字母
- 若字母小写开头,则将标签转为html内同名元素,若html中无该标签对应的同名元素,则报错。
- 若字母大写开头,react就去渲染相应的组件,若组件没有定义,则报错。
标签名任意:HTML标签或者其他标签。
jsx基本概念及例子
JSX是一种js的语法拓展,表面上是HTML,本质上是通过babel转换为js执行,在所有JSX里,我们是可以在 {} 中使用js的语法。
JSX本质是转换为React.createElement在React内部构件虚拟DOM,最终渲染处页面。
举个例子:这个是jsx的写法
class App extends React.Component{
render(){
return {
<div>
Hello {this.props.name}, I am {3+4} years old.
</div>
}
}
}
ReactDOM.render(
<App name="React"/>,
mountNode
)
转换成js的写法:
class App extends React.Component{
render(){
return React.crehateElement(
"div",
null, // 这里为div的属性
"Hello",
this.props.name,
", I am",
3 + 4,
" year old"
)
}
}
ReactDOM.render(
React.createElement(App, {name: "React"}),
mountNode
)
jsx的基本用法
主要的
标签内的注释是 {/* 注释内容*/}
这里展示jsx实现变量操作等,具体目录结构
App.css内:
.img{
border: 1px solid #f00;
}
logo.js内随便找一张将图片即可。
App.js (全部代码)
import React, { Component } from 'react'
import logo from "./logo.jpg";
import "./App.css";
//函数型组件传递props,在这里必须带属性,这用于父子组件数据传递
function Welcome1(props) {
return (
<div>
Hello,{props.name}
</div>
)
}
export default class App extends Component {
//1.当需要状态时,需要构造函数
constructor(props){
super(props);
//2.初始化状态,现在为响应式数据
// 每次状态更新都会导致render函数重新执行
this.state = {
count: 0,
date: new Date()
}
}
componentDidMount(){
this.timer = setInterval(() =>{
//3.更新状态
this.setState({
date:new Date(), //最简单的更新状态的方式
count:this.state.count + 1
})
//注意1.不能直接改状态
//this.state.data = new Date(); //错误的
},1000);
//注意2.setState()是异步的,需要在后面加一个参数进行异步调用
//这个写法是函数写法 setState
this.setState((prevState,prevProps)=>{
return {
count :prevState.count + 1
}
},() => {
console.log(this.state.count);
})
}
componentWillUnmount(){
clearInterval(this.timer);
}
formatName(user){
return user.firstName+' '+user.lastName;
}
render() {
const name = "123";
//jsx本身也是变量
const jsx = <p>hello,everyone</p>
return (
<div>
App组件
{/* 表达式 */}
<h1>{name}</h1>
<p>{this.formatName({firstName:'tom',lastName:'jerry'})}</p>
{/* 属性 */}
<img src={logo} style={{width:'100px'}} className="img" alt="11"/>
{/* jsx本身也是表达式 */}
{jsx}
{/* 组件属性传值(父传子) :传入的属性是只读的,单向数据流 */}
<Welcome1 name="tom"></Welcome1>
{/* 使用状态 */}
<p>{this.state.date.toLocaleTimeString()}</p>
</div>
)
}
}
在js内class是关键字,在react内均使用className作为额它的类名,没有class。
这个里面包含了jsx的几种简单用法。
只是简单例子运行完成后基本展示如下图:
JSX表达式(有执行结果)
变量/值 {num}
数字运算 {x+y}
判断 三元运算符 {1===2? true : false}
循环: 数组迭代方法map遍历
注⚠️:forEach无返回值,内部不能使用
所有命令式编程的循环 for for/in for/of while 都不是jsx表达式
例子:三元表达式(下面的内部均为自定义组件)
<div>
{
this.state.type ===1 ?
<Nowplaying></Nowplaying> :
<Comingsoon></Comingsoon>
}
</div>
{} 语法嵌入不同的值 所呈现出来的特点
- number/ string:值是什么就渲染什么出来
- boolean/null/undefined/Symbol/Bigint:渲染的内容为空
- 除数组外其余对象不支持在 {} 中进行渲染,但是也有特殊情况:
- JSX虚拟DOM对象
- 给元素设置style行内样式,要求必须写成一个对象格式
- 数组对象:把数组的每一项分别拿出来渲染,并不是变为字符串渲染,组件没有逗号
- 函数对象:不支持在 {}中渲染,但是可以作为函数组件,用<Component/>方式渲染!
注意:不能直接嵌入除数组以外的对象,但是可以嵌入 JSX元素对象【虚拟DOM对象】 {React.createElement("button", null, '取消')}
代码内部的jsx最后都要变为 React.createElement()格式
标签内行内样式
注:标签内行内样式的写法:
<img src={logo} style={{width:'100px',fontSize:'30px'}} className="img" alt="11"/>
这里是两层 {{}},可能学过vue的人知道,这个 使用“Mustache”语法 (双大括号) 的文本插值,用于展示数据。
但是这里不一样,最外层的大括号代表需要在内部写js的表达式,里面大括号表示你需要写关于样式的对象。内部样式需基于驼峰命名法
具体的值内需要加上 '引号' style={{width:'100px',fontSize:'30px'}}
设置样式类名,需要把class替换为className
自定义组件
在jsx内的实现:
function Welcome1(props) {
return (
<div>
Hello,{props.name}
</div>
)
}
<Welcome1 name="tom"></Welcome1>
这里呢,引入自定义标签,都必须是首字母大写(这里的代码是App.js内的例子代码)。
JSX内只能有js表达式(返回的值有结果),不能有js语句(if,for等)
注意:
1.在ReactDOM.createRoot()不能直接把HTML/body作为根容器渲染,需要额外指定一个盒子【例如:#root】
const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
<div></div>
);
2.每一个构建的视图,只能有一个根节点
出现多个根节点则报错 Adjacent JSX elements must be wrapped in an enclosing tag.
React给外面提供了一个特殊的节点(标签):React.Fragment 空文档标记标签
<></>
即可以保证只有一个根节点,又不增加层级!
驼峰命名
小驼峰。camelCase 首字母小写,其余每个一个有意义单词首字母大写
大驼峰 PascalCase 首字母都要大写
kabab-case写法 :personal-box