[REACT_DOC]-Quick Start

Quick Start

概覽:

  • 如何創建以及嵌套組件
  • 如何添加markup 和樣式
  • 如何展示數據
  • 如何條件渲染,如何渲染列表
  • 如何響應事件並更新渲染
  • 如何在組件之間共享數據

創建以及嵌套組件

function MyButton() {
  return (
    <button>I'm a button</button>
  );
}
export default function MyApp() {
  return (
    <div>
      <h1>Welcome to my app</h1>
      <MyButton />
    </div>
  );
}

注意: <MyButton />以大寫字母開始, React 組件始終必須以大寫字母開始, 而 HTML tags 必須是小寫的。

export default 關鍵字聲明瞭在這個文件中的 主組件

用 JSX 書寫 標記(markup)

上面你所見到的 標記語法 被稱作 JSX, JSX 相比較HTML而言,會更加的嚴格, 比必須關閉標籤,例如 <br/> , 你的組件也不能夠 return 多個 JSX tags, 你必須將返回的標籤包裹, 例如 <div>...</div> 或者 <>...</>:

function AboutPage() {
  return (
    <>
      <h1>About</h1>
      <p>Hello there.<br />How do you do?</p>
    </>
  );
}

添加樣式

在 React 中, 你需要通過 className 屬性來執行一個標籤的 class

<img className="avatar" />

接着, 你在一個獨立的 CSS 文件中去書寫CSS 樣式:

/* In your CSS */
.avatar{
    border-radius:50%
}

React 並沒有規定你如何去添加這個CSS 文件,在最簡單的情況下,你可以直接添加一個 <link> tag 到你的 HTML 文件中,然後引入它。 如果你使用框架或者工具來構建 React項目, 那麼你需要參看他們的對應文檔以學習如何添加CSS 文件。

展示數據

JSX 允許你在一個花括號中插入一個變量以展示這個變量值。 例如:

return (
  <h1>
    {user.name}
  </h1>
);

同樣的, 也可以爲一個標籤的屬性指定變量值:

return (
  <img
    className="avatar"
    src={user.imageUrl}
  />
);

實際上, JSX 支持在花括號中解析更加複雜的表達式, 例如:

//App.js
const user = {
  name: 'Hedy Lamarr',
  imageUrl: 'https://i.imgur.com/yXOvdOSs.jpg',
  imageSize: 90,
};

export default function Profile() {
  return (
    <>
      <h1>{user.name}</h1>
      <img
        className="avatar"
        src={user.imageUrl}
        alt={'Photo of ' + user.name}
        style={{
          width: user.imageSize,
          height: user.imageSize
        }}
      />
    </>
  );
}

在上面的示例中, style={{}} 並不是一個特殊的語法, 而是style={} 語法花括號中的一個常規的 {} 對象。

條件渲染

在 React 中, 沒有特定的語法去寫 條件 渲染, 替而代之, 你可以直接使用 if 條件語句去完成:

let content;
if (isLoggedIn) {
  content = <AdminPanel />;
} else {
  content = <LoginForm />;
}
return (
  <div>
    {content}
  </div>
);

如果你更加喜歡簡潔的代碼, 那麼你可以使用三元表達式:

<div>
  {isLoggedIn ? (
    <AdminPanel />
  ) : (
    <LoginForm />
  )}
</div>

甚至,如果你壓根都不需要 else 分支,比可以使用一個簡寫的邏輯語法: &&

<div>
  {isLoggedIn && <AdminPanel />}
</div>

列表渲染

我們通常依賴 的特性,像for 循環, map 去渲染一個列表元素。 例如:

const products = [
  { title: 'Cabbage', id: 1 },
  { title: 'Garlic', id: 2 },
  { title: 'Apple', id: 3 },
];

在你的組件中, 使用map()函數去將一個數組轉換爲一個li 元素列表:

const listItems = products.map(product =>
  <li key={product.id}>
    {product.title}
  </li>
);

return (
  <ul>{listItems}</ul>
);

注意: <li> 有一個 key 屬性 , 對於列表中的每一項, 你都應該傳入一個字符串或者數字,用以標識該 項的唯一性 。這樣,當隨後發生了插入,刪除,或者重排序,React 通過這個key 就能明白髮生了什麼。

const products = [
  { title: 'Cabbage', isFruit: false, id: 1 },
  { title: 'Garlic', isFruit: false, id: 2 },
  { title: 'Apple', isFruit: true, id: 3 },
];

export default function ShoppingList() {
  const listItems = products.map(product =>
    <li
      key={product.id}
      style={{
        color: product.isFruit ? 'magenta' : 'darkgreen'
      }}
    >
      {product.title}
    </li>
  );

  return (
    <ul>{listItems}</ul>
  );
}

事件響應

你可以通過在你的組件中定義一個 event handler 以響應發生對應的事件。

function MyButton() {
  function handleClick() {
    alert('You clicked me!');
  }

  return (
    <button onClick={handleClick}>
      Click me
    </button>
  );
}

注意: onClick={handleClick} 的末尾沒有圓括號, 你只需要將這個事件的定義傳入, React 將會在你隨後點擊這個按鈕的時候再去調用這個事件。

更新屏幕

通常, 你會希望你的組件能夠 “記住” 一些信息, 並展示它。 例如,或許你想要計數按鈕被點擊的次數。 要做到這點, 你需要添加 start 到你的組件。

首先,從 react 引入useState

import { useState } from "react";

現在你可以在你的組件內部聲明一個 “狀態” 變量:

function MyButton(){
    const [count,setCount]  = useState(0);
    //...
}

你將會從 useState 中得到兩個東西, 當前的狀態(count), 以及一個提供給你去更新它的 (setCount)。 你可以任意定義他們的名字,但是約定俗稱的,我們喜歡寫作 [something, setSomething].

按鈕第一次展示的時候, count將會是 0 ,因爲你給 useState() 傳入了0, 這是它的初始值, 當你想要改變它的時候, 你需要調用 setCount() 方法, 並傳入一個新的值。 :

function MyButton() {
  const [count, setCount] = useState(0);

  function handleClick() {
    setCount(count + 1);
  }

  return (
    <button onClick={handleClick}>
      Clicked {count} times
    </button>
  );
}

如果你多次渲染了相同的組件,每個組件都會維護一份自己獨有的狀態。

import { useState } from 'react';

export default function MyApp() {
  return (
    <div>
      <h1>Counters that update separately</h1>
      <MyButton />
      <MyButton />
    </div>
  );
}

function MyButton() {
  const [count, setCount] = useState(0);

  function handleClick() {
    setCount(count + 1);
  }

  return (
    <button onClick={handleClick}>
      Clicked {count} times
    </button>
  );
}

記住, 每一個按鈕都會 "記住" 它自己的狀態,並且不會影響其它的按鈕。

使用 Hooks

使用 use 開頭的函數,被稱作 Hooks, useState 是一個 React 內置的 Hook, 你可在這裏找到更多的 Hooks( API reference. ), 你也可以通過組合已有的hook從而創建你自己的 Hooks .

Hooks 相比較其他的函數而言, Hooks 更加具有限制性。 你只能在你的組件的頂部去調用 Hooks , 如果你想要在一個條件或者循環中使用 useState, 那麼你應該抽離一個新的組件,並把Hooks 放在組件中。

在組件之間共享數據

在之前的示例中, 每個 MyButton 都有着自己獨立的 count, 但是有的時候,你會希望多個組件共享同一份數據,一處發生變化,其他地方也隨之變化。

還是以這個按鈕的例子來說,如果你希望兩個MyButton 組件共用同一個 count, 那麼,你需要將 state 從獨立的按鈕組件中 提升 到同時包含這兩個按鈕組件的最近父級組件。

image

export default function MyApp() {
  const [count, setCount] = useState(0);

  function handleClick() {
    setCount(count + 1);
  }

  return (
    <div>
      <h1>Counters that update together</h1>
      <MyButton count={count} onClick={handleClick} />
      <MyButton count={count} onClick={handleClick} />
    </div>
  );
}

function MyButton({ count, onClick }) {
  return (
   <button onClick={onClick}>
      Clicked {count} times
    </button>
  );
}

注意,在<MyButton count="..." onClick="..."> 上定義的這些屬性,將會被包裹爲一個對象作爲參數傳入給function MyButton({ count, onClick }){}, 這個對象被稱作 props

當你點擊任意一個按鈕的時候, 被傳入的onClick event handler 都將被觸發, 也就是這個定義在 MyApp 中的handleClick 函數會被觸發, 然後將count 加一。 接着,這個count 又會被傳入到每個 按鈕, 頁面也會隨之發生更新。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章