react中使用signal的項(xiàng)目實(shí)踐
我參考solid的語(yǔ)法 完成了一個(gè)能在react里使用signal的npm包
曾經(jīng)考慮過使用vue或preact的獨(dú)立reactivity包 但考察過后發(fā)現(xiàn)不太符合需求 所以內(nèi)部實(shí)現(xiàn)都是自己完成的
API
提供了與solid很相似的api
- createSignal 創(chuàng)建signal
const [count, setCount] = createSignal(0) // 正常訪問signal count() // 不具有響應(yīng)性的訪問 count.value
- createMemo 創(chuàng)建派生signal.同樣可以通過
.value方式訪問值 - defineComponent 定義組件.
type CompProps = {
// 組件參數(shù)可以是signal
num: () => number
}
const Comp = defineComponent<CompProps>((props) => {
// props對(duì)象是signal 返回一個(gè)render函數(shù)
// render中用到的signal被自動(dòng)收集 變化后更新組件
return () => <span>{props().num()}</span>
})- createEffect 創(chuàng)建一個(gè)副作用 它會(huì)在useEffect階段被執(zhí)行 與組件渲染強(qiáng)相關(guān)
- createRef 創(chuàng)建一個(gè)react ref 可以直接用在html屬性上
- onCleanup 可以為組件 createMemo createEffect提供清理函數(shù)
說明
暫時(shí)不適配熱重載
使用例
import ReactDOM from 'react-dom/client'
import {
defineComponent,
createEffect,
createMemo,
createSignal,
onCleanup,
createRef,
} from '@fane_the_divine/react-signal'
const Page = defineComponent(() => {
// 驗(yàn)證基本的響應(yīng)式能力
const [count, setCount] = createSignal(0)
const spanRef = createRef<HTMLSpanElement>()
const double = createMemo(() => {
console.log(spanRef.current)
onCleanup(() => console.log('memo cleanup', count.value))
return count() * 2
})
createEffect(
(_, isFirst) => {
console.log(`effect: isFirst:${isFirst} `, spanRef.current)
onCleanup(() => console.log('cleanup in effect'))
},
[double],
)
const [show, setShow] = createSignal(true)
return () => {
console.log('render')
return (
<>
<button
onClick={() => {
setCount(count() + 1)
setCount(count() + 1)
}}
>
{count()}
</button>
<span ref={spanRef}> {double()}</span>
<button onClick={() => setShow(!show())}>{show() ? 'hidden' : 'show'}</button>
{show() ? <SubComp1 value={count} /> : null}
</>
)
}
})
const SubComp1 = defineComponent<{ value: () => number }>((props) => {
// 驗(yàn)證組件銷毀后的cleanup被執(zhí)行
createEffect(() => {
onCleanup(() => console.log('SubComp1 unmount in effect'))
})
onCleanup(() => console.log('SubComp1 unmount'))
return () => {
console.log('%csub comp1 render', 'font-size: 28px; font-weight: bold; color: blue;')
return <SubComp2 value={props().value} />
}
})
const SubComp2 = defineComponent<{ value: () => number }>((props) => {
// 驗(yàn)證signal跨層不重新渲染的能力
return () => {
console.log('%csub comp2 render', 'font-size: 28px; font-weight: bold; color: red;')
return <button>sub comp2 {props().value()}</button>
}
})
ReactDOM.createRoot(document.getElementById('root')!).render(<Page />)到此這篇關(guān)于react中使用signal的項(xiàng)目實(shí)踐的文章就介紹到這了,更多相關(guān)react使用signal內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
React星星評(píng)分組件的實(shí)現(xiàn)
評(píng)分插件在購(gòu)物的應(yīng)用中經(jīng)??梢钥吹玫剑怯弥鴦e人的總是沒有自己寫的順手,本文就使用React實(shí)現(xiàn)星星評(píng)分組件,感興趣的可以了解一下2021-06-06
React實(shí)現(xiàn)歌詞滾動(dòng)效果(跟隨音樂播放時(shí)間滾動(dòng))
這篇文章主要為大家詳細(xì)介紹了React實(shí)現(xiàn)歌詞滾動(dòng)效果(跟隨音樂播放使勁按滾動(dòng)),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2024-02-02
如何使用Redux Toolkit簡(jiǎn)化Redux
redux-toolkit是目前redux官方推薦的編寫redux邏輯的方法,針對(duì)redux的創(chuàng)建store繁瑣、樣板代碼太多、依賴外部庫(kù)等問題進(jìn)行了優(yōu)化,官方總結(jié)了四個(gè)特點(diǎn)是簡(jiǎn)易的/有想法的/強(qiáng)勁的/高效的,總結(jié)來看,就是更加的方便簡(jiǎn)單了2022-12-12
基于React實(shí)現(xiàn)虛擬滾動(dòng)的方案詳解
這篇文章將以固定高度和非固定高度兩種場(chǎng)景展開React中虛擬滾動(dòng)的實(shí)現(xiàn),文中的示例代碼講解詳細(xì),感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下2025-03-03
React如何實(shí)現(xiàn)像Vue一樣將css和js寫在同一文件
這篇文章主要介紹了React如何實(shí)現(xiàn)像Vue一樣將css和js寫在同一文件問題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2024-01-01
詳解如何給React-Router添加路由頁(yè)面切換時(shí)的過渡動(dòng)畫
這篇文章主要介紹了詳解如何給React-Router添加路由頁(yè)面切換時(shí)的過渡動(dòng)畫,小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2019-04-04

