從原生JavaScript到React深入理解
從頭開(kāi)始理解 React
作者:Stéphane Bégaudeau
翻譯原文 https://www.sbegaudeau.com/2018/10/01/from-vanilla-javascript-to-react.html
React 是一個(gè)用于構(gòu)建用戶(hù)界面的 JavaScript 框架。它可用于通過(guò)動(dòng)態(tài)操作頁(yè)面內(nèi)容來(lái)創(chuàng)建 JavaScript 應(yīng)用程序。瀏覽器已經(jīng)提供了在頁(yè)面中創(chuàng)建元素的 API,即 DOM,所以新手可能想知道 React 帶來(lái)了什么以及它與 DOM 的關(guān)系。
原生 JavaScript 和 DOM
在 JavaScript 中,就像在大多數(shù)編程語(yǔ)言中一樣,您將可以訪(fǎng)問(wèn)具有各種對(duì)象和函數(shù)的全局范圍,您可以操縱這些對(duì)象和函數(shù)來(lái)構(gòu)建您的應(yīng)用程序。在 Web 環(huán)境中運(yùn)行的 JavaScript 應(yīng)用程序中,您將有權(quán)訪(fǎng)問(wèn)文檔對(duì)象模型 (DOM) API。如果您在基于節(jié)點(diǎn)的應(yīng)用程序中使用 JavaScript,您將無(wú)法訪(fǎng)問(wèn) DOM,但您可以導(dǎo)入替代實(shí)現(xiàn),例如JSDOM。
DOM 是一個(gè)簡(jiǎn)單的 API,可讓您以幾乎任何您想要的方式操作頁(yè)面的 HTML 文檔。由于全局document 對(duì)象,您可以開(kāi)始使用它。
從 document 這里開(kāi)始,您可以輕松地創(chuàng)建新元素、修改它們的屬性,甚至將它們添加為其他元素的子元素。多虧了 DOM,您可以通過(guò)編程方式創(chuàng)建任何 HTML 文檔,即使這樣做會(huì)非常冗長(zhǎng)。
在下面的示例中,我們將以編程方式在 HTML 文檔中創(chuàng)建一個(gè)簡(jiǎn)單的標(biāo)題。
<!DOCTYPE html>
<html>
<head>
<script src="app.js"></script>
</head>
<body>
<div id="app" />
</body>
</html>為此,我們將創(chuàng)建一個(gè)h1元素,該元素將插入到 HTML 頁(yè)面的正文中。
// The document object is accessible since it is in the global scope
const h1Element = document.createElement('h1');
h1Element.setAttribute('class', 'title');
const textElement = document.createTextNode('I am Groot');
h1Element.appendChild(textElement);
// document.getElementById('app') will retrieve the div with the identifier app
document.getElementById('app').appendChild(element);上面的代碼首先創(chuàng)建一個(gè)新屬性,然后向該元素h1添加一個(gè)class帶有值為title的新屬性。 它還創(chuàng)建一個(gè)簡(jiǎn)單的文本節(jié)點(diǎn)并將文本 'I am Groot' 添加為元素h1的子元素。最后,它使用 HTML 文檔將 h1 的標(biāo)簽添加到 div 中。app 執(zhí)行此代碼后,生成的 HTML 文檔將如下所示:
<!DOCTYPE html>
<html>
<head>
<script src="app.js"></script>
</head>
<body>
<div id="app">
<h1 class="title">I am Groot</h1>
</div>
</body>
</html>借助 DOM,我們還可以通過(guò) className 屬性直接操作元素的類(lèi)屬性(因?yàn)槊Q(chēng) class 是 JavaScript 中的保留關(guān)鍵字)。因此,以下代碼將產(chǎn)生完全相同的結(jié)果。
const h1Element = document.createElement('h1');
// h1Element.setAttribute('class', 'title');
h1Element.className = 'title';
const textElement = document.createTextNode('I am Groot');
h1Element.appendChild(textElement);
document.getElementById('app').appendChild(element);React 的基礎(chǔ)
大多數(shù) React 教程會(huì)讓你從直接使用 React 的所有奇跡開(kāi)始。我們將采用另一種方法,因?yàn)槲覀儗木帉?xiě)一些你可能永遠(yuǎn)不會(huì)再編寫(xiě)的 React 代碼開(kāi)始,以便更好地理解 React 的工作方式。
React 的創(chuàng)建考慮了 Web 應(yīng)用場(chǎng)景,因此,在其核心,它的一些 API 感覺(jué)就像 DOM。為了說(shuō)明這一點(diǎn),我們將看一下最重要的 React API 之一,React.createElement.
要使用 React 操作 DOM,您將需要兩個(gè)依賴(lài)項(xiàng) React 和 ReactDOM. React.createElement將讓您創(chuàng)建一個(gè)廉價(jià)且快速的數(shù)據(jù)結(jié)構(gòu),稱(chēng)為虛擬 DOM,代表您的用戶(hù)界面的結(jié)構(gòu)。ReactDOM將在您的 Web 應(yīng)用程序的真實(shí) DOM 中呈現(xiàn)這個(gè)虛擬 DOM。
React.createElement將需要三個(gè)參數(shù)來(lái)創(chuàng)建虛擬 DOM 的元素:
- 要?jiǎng)?chuàng)建的元素的名稱(chēng)
- 它的屬性
- 它的孩子
import React from 'react';
const name = 'h1';
const props = { className: 'title' };
const children = 'I am Groot';
const element = React.createElement(name, props, children);React.createElement 也可以接受包含要?jiǎng)?chuàng)建的元素的所有子元素的數(shù)組。
import React from 'react';
const name = 'h1';
const props = { className: 'title' };
const children = ['I am Groot'];
const element = React.createElement(name, props, children);參數(shù) children 也是元素的常規(guī)屬性,因此它可以是 props 對(duì)象的一部分。
import React from 'react';
const props = {
className: 'title',
children: ['I am Groot']
};
const element = React.createElement('h1', props);為了在 DOM 中渲染這個(gè)元素,我們需要選擇它在 DOM 中的渲染位置,在我們的例子中是div帶有標(biāo)識(shí)符app并告訴 ReactDOM 渲染它。
import React from 'react';
import ReactDOM from 'react-dom';
const props = {
className: 'title',
children: ['I am Groot']
};
const element = React.createElement('h1', ...props);
ReactDOM.render(element, document.getElementById('app'));此處顯示的所有代碼示例都可以通過(guò)將它們與未打包版本的 React 和 Babel 一起使用來(lái)進(jìn)行測(cè)試。這樣的配置應(yīng)該只用于簡(jiǎn)單的測(cè)試,因?yàn)樗鼈儧](méi)有像生產(chǎn)構(gòu)建那樣優(yōu)化。在這種特定情況下,應(yīng)刪除 和 的導(dǎo)入(此處均作為全局變量公開(kāi)react)。react-dom
<!DOCTYPE html>
<html>
<head>
<title>React</title>
<script src="https://unpkg.com/react@16/umd/react.development.js"></script>
<script src="https://unpkg.com/react-dom@16/umd/react-dom.development.js"></script>
<script src="https://unpkg.com/babel-standalone@6/babel.min.js"></script>
<script type="text/babel">
const props = {
className: 'title',
children: ['I am Groot']
};
const element = React.createElement('h1', props);
ReactDOM.render(element, document.getElementById('app'));
</script>
</head>
<body>
<div id="app" />
</body>
</html>咱老百姓也能學(xué)會(huì)的 JSX
雖然我們可以使用這種方法創(chuàng)建 Web 應(yīng)用程序的所有頁(yè)面,但它仍然非常冗長(zhǎng)。為了使操作 DOM 變得容易,React 提供了一種名為JSX的簡(jiǎn)單而強(qiáng)大的語(yǔ)言。
預(yù)處理器使用 JSX 在構(gòu)建期間將其轉(zhuǎn)換為常規(guī) JavaScript。一個(gè)常規(guī)的 React 項(xiàng)目使用預(yù)處理器來(lái)將 JSX 代碼轉(zhuǎn)換為對(duì) React.createElement. 因此,JSX 永遠(yuǎn)不會(huì)被 React 直接解釋?zhuān)憧梢栽跊](méi)有一行 JSX 的情況下使用 React。因此,下面的兩段代碼完全相同。首先,以編程方式使用 React:
import React from 'react';
const props = { className: 'title' };
const children = ['I am Groot'];
const element = React.createElement('h1', props, children);或使用 JSX 聲明:
import React from 'react'; const element = <h1 className="title">I am Groot</h1>;
由于 JSX 代碼將使用 轉(zhuǎn)換為調(diào)用 React.createElement,因此您需要導(dǎo)入 React,即使它似乎沒(méi)有被使用。
使用 JSX,您可以非常快速地以聲明方式創(chuàng)建大部分 DOM,而 React 只會(huì)看到對(duì)React.createElement. 由于 JSX 元素只是對(duì) 的調(diào)用 React.createElement,因此 children 仍然是常規(guī)屬性。因此,您也可以像這樣編寫(xiě)前面的示例:
import React from 'react'; const element = <h1 className="title" children="I am Groot"/>;
借助 JSX,您可以通過(guò)花括號(hào)訪(fǎng)問(wèn)變量:
import React from 'react';
const title = 'title';
const text = 'I am Groot';
const element = <h1 className={title} children={text}/>;當(dāng)然,我們也可以將變量命名為我們想要操作的屬性
import React from 'react';
const className = 'title';
const children = 'I am Groot';
const element = <h1 className={className} children={children}/>;這將允許我們使用擴(kuò)展語(yǔ)法來(lái)獲得更簡(jiǎn)潔的代碼
import React from 'react';
const props = {
className: 'title',
children: ['I am Groot']
};
const element = <h1 {...props}/>;最后,我們可以像以前一樣在 DOM 中渲染這個(gè)元素 React.createElement。
import React from 'react';
import ReactDOM from 'react-dom';
const props = {
className: 'title',
children: ['I am Groot']
};
ReactDOM.render(<h1 {...props}/>, document.getElementById('app'));現(xiàn)在我們已經(jīng)使用 JSX 通過(guò) React 渲染了我們的第一塊虛擬 DOM,我們準(zhǔn)備好看看如何使用 React 構(gòu)建一個(gè)基本的應(yīng)用程序。
奔跑吧,去用 React 組件開(kāi)發(fā)更多動(dòng)態(tài)代碼。
以上就是從原生JavaScript到React深入理解的詳細(xì)內(nèi)容,更多關(guān)于原生JavaScript到React的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
詳解如何用js實(shí)現(xiàn)一個(gè)網(wǎng)頁(yè)版節(jié)拍器
這篇文章主要為大家介紹了詳解如何用js實(shí)現(xiàn)一個(gè)網(wǎng)頁(yè)版節(jié)拍器示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-01-01
微信小程序 開(kāi)發(fā)之快遞查詢(xún)功能的實(shí)現(xiàn)
這篇文章主要介紹了微信小程序 開(kāi)發(fā)之快遞查詢(xún)功能的實(shí)現(xiàn)的相關(guān)資料,這里實(shí)現(xiàn)微信小程序查詢(xún)快遞的功能,需要的朋友可以參考下2017-01-01
JavaScript中Reduce10個(gè)常用場(chǎng)景技巧
這篇文章主要為大家介紹了JavaScript中Reduce10個(gè)常用場(chǎng)景和技巧,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-06-06
C#微信小程序服務(wù)端獲取用戶(hù)解密信息實(shí)例代碼
這篇文章主要介紹了 C#微信小程序服務(wù)端獲取用戶(hù)解密信息實(shí)例代碼的相關(guān)資料,需要的朋友可以參考下2017-03-03
使用compose函數(shù)優(yōu)化代碼提高可讀性及擴(kuò)展性
這篇文章主要為大家介紹了使用compose函數(shù)提高代碼可讀性及擴(kuò)展性,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-06-06
javascript使用btoa和atob來(lái)進(jìn)行Base64轉(zhuǎn)碼和解碼
javascript原生的api本來(lái)就支持,Base64,但是由于之前的javascript局限性,導(dǎo)致Base64基本中看不中用。當(dāng)前html5標(biāo)準(zhǔn)正式化之際,Base64將有較大的轉(zhuǎn)型空間,對(duì)于Html5 Api中出現(xiàn)的如FileReader Api, 拖拽上傳,甚至是Canvas,Video截圖都可以實(shí)現(xiàn)2017-03-03

