深入了解React.js的JSX1 JSX 与HTML2 JSX 和HTML 的不同之处

JSX 是React 为JavaScript 语法带来的可选扩展,用于在JavaScript 代码中编写声明式XML 风格语法。

对于Web 项目而言,React 的JSX 提供了一组类似于HTML 的XML 标签,但在其他使用场景中,会使用其他组XML 标签来描述用户界面(如React with SVG、React Canvas和React Native)。转译后,XML 会被转换为针对React 库的函数调用。这行代码:

<h1>Hello World</h1> 

会被转译为:

React.createElement("h1", null, "Hello World"); 

JSX 是可选的。但拥抱它会带来如下好处

  • XML 包含特性的元素树非常适合表示UI。
  • 能够更精确和更方便地呈现应用程序的结构。
  • 是普通JavaScript,并不会改变这门语言的语义。

1 JSX 与HTML

对于Web 场景而言,JSX 看上去就像HTML,但它并不是HTML 规范的具体实现。React 的创造者只是让JSX 足够像HTML,这样就可以用来正确地描述Web 界面,并没有忽略这样一个事实,即它仍然应该遵循JavaScript 的风格和语法

2 JSX 和HTML 的不同之处

2.1 标签特性采取驼峰式大小写风格

例如,在HTML 中,输入标签可以包含一个可选的maxlengh 特性: <input type="text" maxlength="30"/> 在JSX 中,该特性应该写作maxLength(请注意大写字母“L”): return <input type="text" maxLength="30" />

2.2 所有元素都必须闭合

由于JSX 是XML,因此元素都必须闭合。诸如 和<img>这样的标签并不包含结束标签,需要自闭合。所以要使用<br/>而不是<br>,要使用<imgsrc="..."/>而不是<imgsrc="...">

2.3 特性名称基于DOM API

这一点可能难以理解,但实际上却非常简单。在与DOM API 进行交互时,标签特性的名称可能会和在HTML 中使用时有所不同。其中一个例子是class 和className。例如,对于这段普通的HTML: <div id="box" class="some-class"></div> 如果你想要使用普通JavaScript 来操作DOM 并更改它的类名,你可能会编写这样的代码: document.getElementById("box").className="some-other-class" 在JavaScript 中,这个特性称为className 而不是class。由于JSX 只是JavaScript的一种语法扩展,它遵循了DOM 所定义的特性命名规范。同样的div 用JSX 来表示就应该是: return <div id="box" className="some-class"></div>

2.3 JSX 的怪异之处

JSX 偶尔也比较奇怪。针对在使用JSX 构建组件时可能会遇到的常见问题,本节汇总了一些小技巧、提示和策略来供你应对。

  • 单一根节点 React 组件只能渲染一个根节点。想要了解这个限制的原因,我们先来看看render函数的一个返回示例:
return(  
    <h1>Hello World</h1> 
) 

它会被转换成一条语句:

return React.createElement("h1",null,"Hello World");

但是,下面的代码却不是合法的:

return (  
<h1>Hello World</h1> 
<h2>Have a nice day</h2> 
) 

需要明确的是,这并非JSX 的限制,而是JavaScript 的一个特性:一条返回语句只能返回单个值,而在前面的代码中我们尝试返回两条语句(两次React.createElement 调用)。解决的方法非常简单:就像你在普通JavaScript 中会做的那样,将所有返回值包含到一个根对象中。

return (  
<div> 
<h1>Hello World</h1> 
<h2>Have a nice day</h2> 
</div> 
) 

它完全有效,因为它会被转换成:

return React.createElement("div",null,  
React.createElement("h1",null,"Hello World"),  
React.createElement("h2",null," Have a nice day"),  
) 

它返回单个值,并且是通过合法的JavaScript 完成的。

  • 条件语句 如果语句不兼容于JSX,看上去像是JSX 的限制所致,实际上却是因为JSX 只是普通的JavaScript 回顾一下JSX 是如何被转换为普通JavaScript 如下JSX
return (  
      <div className="salutation">Hello JSX</div> 
) 

会被转换成这样的JavaScript

return (  
    React.createElement("div",{className:"salutation"},"Hello JSX");  
) 

然而,如果尝试在JSX 的中间编写if 语句,例如: <div className={if (condition) { "salutation" }}>Hello JSX</div>

它就会被转换成一个非法的JavaScript 表达式,如图2-1 所示:

image

  • 有什么解决方法? 尽管并无可能在JSX 中使用“if”语句,但仍有根据条件渲染内容的方法,包括使用三元表达式和将条件赋值给一个变量(空值和未定义的值都会被React 进行处理,JSX在转义时什么都不会输出)。

使用三元表达式

如果你有一个非常简单的表达式,可以使用三元形式:

render() {  
  return (  
    <div className={condition ? "salutation" : ""}> 
      Hello JSX  
    </div> 
  )  
} 

这段代码会被转换成一段合法的JavaScript:

React.createElement("div",{className: condition ?"salutation" : ""},  
"Hello JSX"); 

三元形式还可用来有条件地渲染整个节点:

<div> 
{condition ?  
<span>Hello JSX</span> 
: null}  
</div> 

将条件外置

如果三元表达式还不能应付你的要求,解决方法是不要在JSX 的中间使用条件。简单地将条件语句移动到外部(就像你在第2 章中隐藏和显示ContactItem 细节时所采取的方法)。

下面是原先的代码:

1.  render() {  
2.  return (  
3.  <div className={if (condition) { "salutation" }}> 
4.  Hello JSX  
5.  </div> 
6.  )  
7.  } 

将条件移动到JSX 的外部,就像:

render() {  
let className;  
if(condition){  
className = "salutation";  
}  
return (  
<div className={className}>Hello JSX</div> 
)  
} 

React 知道如何处理未定义的值,如果条件为假,它甚至不会在div 标签中创建class特性。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏运维

JavaScript 学习总结

Java和Javascript的区别就像印度和印度尼西亚的区别,名字中有点相同的东西。

40640
来自专栏前端知识分享

第61天:json遍历和封装运动框架(多个属性)

 var json = {width:200,height:300,left:50} console.log(json.width); for(var k in...

10420
来自专栏黑泽君的专栏

day03_js学习笔记_03_js的事件、js的BOM、js的DOM

19910
来自专栏知道一点点

sass学习入门篇(三)

这章我们讲“嵌套”,嵌套包括两种:一,选择器嵌套。二是属性的嵌套。一般用选择器嵌套居多

11360
来自专栏前端杂货铺

html标签属性(attribute)和dom元素的属性(property)

简介 attribute和property都有属性之意,但对于attribute和property的区分其实并不难。从对象来说,attribute是html文档...

31450
来自专栏JavaEdge

全面入门jQuery最佳实践(二)-jQuery的属性与样式1 .attr()与.removeAttr()2 html()及.text()

每个元素都有一个或者多个特性,这些特性的用途就是给出相应元素或者其内容的附加信息。如:在img元素中,src就是元素的特性,用来标记图片的地址。

12030
来自专栏梦魇小栈

JQuery分析及实现part5之事件模块功能及实现

11850
来自专栏小壮和前端

js写2048游戏代码

41820
来自专栏WindCoder

从li看html标签属性(attribute)和dom元素的属性(property)

从对象来说,attribute是html文档上标签属性,而property则是对应dom元素的自身属性。

44310
来自专栏栗霖积跬步之旅

1.react的基础知识

React 的基础之:JSX 语法 react 使用 JSX 语法,js 代码中可以写 HTML 代码。 let myTitle = <h1>Hello, Wo...

29060

扫码关注云+社区

领取腾讯云代金券