0基础从前端到Web3 —— Vite + React + TS moveCall a + b
一:初始化项目
V
i
t
e
\mathit {Vite}
Vite 作为近几年前端开发中常用的构建工具之一,具有启动速度快、更快的冷启动与热更新、按需加载等优势,极高提升了开发效率和体验,想要初始化一个项目也十分简单,本篇以
p
n
p
m
\mathit {pnpm}
pnpm 为例:
pnpm create vite
根据提示输入想要创建的项目名,再选择R
e
a
c
t
\mathit {React}
T
y
p
e
S
c
r
i
p
t
\mathit {TypeScript}
cd
进入你新建的项目,通过pnpm install
安装必要的依赖,等待一会儿后即可通过pnpm run dev
进行启动,这里可以选择打开浏览器预览初始化的页面(中央有一个点击计数的按钮)。- 本篇还需要使用到
S
u
i
M
o
v
e
\mathit {Sui\ Move}
pnpm add -D @mysten/sui.js @mysten/dapp-kit @tanstack/react-query
至此,基础的内容都已经初始化完毕,让我们将功能进行拆解进行实现。
二:功能实现
2.1 基础组件
在项目中进入src
文件夹,打开并修改main.tsx
文件。
import React from 'react'
import ReactDOM from 'react-dom/client'
import App from './App.tsx'
import '@mysten/dapp-kit/dist/index.css';
import { SuiClientProvider, WalletProvider } from '@mysten/dapp-kit';
import { getFullnodeUrl } from '@mysten/sui.js/client';
import { QueryClient, QueryClientProvider } from '@tanstack/react-query';
const queryClient = new QueryClient();
const networks = {
testnet: { url: getFullnodeUrl('testnet') },
mainnet: { url: getFullnodeUrl('mainnet') },
};
ReactDOM.createRoot(document.getElementById('root')!).render(
,
);
QueryClientProvider, SuiClientProvider, WalletProvider
是
S
u
i
C
l
i
e
n
t
,
S
u
i
N
e
t
w
o
r
k
s
,
W
a
l
l
e
t
\mathit {Sui\ Client},\ \mathit {Sui\ Networks},\ \mathit {Wallet}
Sui Client, Sui Networks, Wallet 的组件设置,格式相对固定,这里以连接
t
e
s
t
n
e
t
\mathit {testnet}
testnet 为例,具体的界面和相关的功能都在同目录下的App.tsx
当中编写。
2.2 界面布局
2.2.1 连接钱包
在@mysten/dapp-kit
当中可以导入ConnectButton
这一按钮,只需要通过调用,就可以返回一个点击连接浏览器钱包功能的按钮,为了设置其布局,我们在外面套一层
,通过
className
编写css
文件调整位置布局。
.ConnectButton {
text-align: center;
padding: 15%;
}
2.2.2 输入输出
这里使用
U
I
\mathit {UI}
UI 组件:
M
a
t
e
r
i
a
l
U
I
\mathit {Material\ UI}
Material UI 来进行后续界面布局,它是世上最流行的
R
e
a
c
t
U
I
\mathit {React\ UI}
React UI 框架,基础的格式和组件使用可以点击查看。
依赖安装很简单,也是通过
p
n
p
m
\mathit {pnpm}
pnpm 一行命令搞定:pnpm add -D @mui/material @emotion/react @emotion/styled
,如有特殊的需求可以通过上面的链接点击进入查看。
用Box
来框定范围、间距等,内部通过TextField
来设置文本框,两个用来输入的,一个用来输出的,输出答案的文本框不可编辑,内容将根据调用进程实时变更。
<Box
component="form"
sx={{
'& > :not(style)': { m: 1, width: '15ch', left: "33%"},
}}
noValidate
autoComplete="off"
>
+
=
具体的格式设置都可以通过
M
a
t
e
r
i
a
l
U
I
\mathit {Material\ UI}
Material UI 的详情页查看,这里也就不再赘述,关键是几个点击事件的监听。
const { mutate: signAndExecuteTransactionBlock } = useSignAndExecuteTransactionBlock();
const account = useCurrentAccount();
const [numberA, setNumberA] = React.useState("");
const readNumberA = (event: any) => {
setNumberA(event.target.value);
};
// console.log(numberA);
const [numberB, setNumberB] = React.useState("");
const readNumberB = (event: any) => {
setNumberB(event.target.value);
};
// console.log(numberB);
const [sum, setSum] = React.useState("");
const calculate = () => {
moveCall(Number(numberA), Number(numberB), account, signAndExecuteTransactionBlock, setSum);
};
readNumberA
和readNumberB
都是获取用户输入的内容,分别存储到numberA, numberB
当中。
Calculate
按钮实际功能是链上调用,将得到的两个数字作为参数传入(得到的是字符串,传入时转换成数字类型),后面的account
用来判断用户是否已经连接了钱包,signAndExecuteTransactionBlock
用来进行链上交易调用,setSum
不必多说,用来将计算所得(通过读取交易后的事件)来改变sum
,而我们的答案文本框的内容会根据sum
值改变而改变。
2.3 链上调用
首先,通过account
判断是否已经连接了钱包。
if (!account) {
setSum("Connect First!!!");
return;
}
然后,创建交易块并且填写交易信息,内容与直接通过
T
y
p
e
S
c
r
i
p
t
\mathit {TypeScript}
TypeScript 调用
S
u
i
M
o
v
e
S
D
K
\mathit {Sui\ Move\ SDK}
Sui Move SDK 时大差不差。
const txb = new TransactionBlock();
txb.moveCall({
target: "0xc20b020f8bf81400cc6c1d63ac37a4802ef873df35abd754ffd37992655b25e4::add::add",
arguments: [txb.pure(a), txb.pure(b)],
});
最后,通过传入的signAndExecuteTransactionBlock
进行签名并交易。
signAndExecuteTransactionBlock(
{
transactionBlock: txb,
chain: "sui:testnet",
options: {
showEvents: true,
},
},
{
onSuccess: (result: any) => {
setSum(result.events[0].parsedJson.res);
},
});
其中,chain
选择的是网络环境,本篇使用的是测试网(
t
e
s
t
n
e
t
\mathit {testnet}
testnet),options
当中的showEvents
则是令成功交易后返回的result
当中显示事件信息,onSuccess
则是处理成功交易后的逻辑,这里很简单,将event
当中存储的res
赋值给sum
。
2.4 简单演示
2.5 其它
额外提一点,如果已知链上的
o
b
j
e
c
t
I
d
\mathit {objectId}
objectId,该如何查询其内容:在@mysten/dapp-kit
当中有useSuiClientQuery, useSuiClientQueries
等一系列函数,这里以查询单一的对象为例:const { data } = useSuiClientQuery("getObject", { id: objectId, options: { showContent: true } });
可以通过console.log(data)
来查看结构,再通过.
来一层一层取用。
本篇完整的代码(包括
a
+
b
\mathit {a\ +\ b}
a + b 的
m
o
v
e
\mathit {move}
move 代码)可以点击查看。
l
e
t
s
m
o
v
e
\mathit {letsmove}
letsmove 学习激励计划的
t
a
s
k
6
\mathit {task6}
task6 新增要求必须使用
d
a
p
p
\mathit {dapp}
dapp–
k
i
t
\mathit {kit}
kit 在浏览器进行交易,可结合本篇以及前面的文章内容稍加修改后达成。
三:加入组织,共同进步!
- Sui 中文开发群(TG)
M
o
v
e
\mathit{Move}