Skip to content

Commit

Permalink
Feat: starknet wallet interact (keep-starknet-strange#27)
Browse files Browse the repository at this point in the history
* Initialize wallet integration with starknetkit

* Info screen, responsive, and add starknet-react

* Cleanup icons

* Fix icons shadows
  • Loading branch information
b-j-roberts authored Dec 19, 2024
1 parent fb21d0d commit f74a317
Show file tree
Hide file tree
Showing 24 changed files with 2,780 additions and 80 deletions.
3 changes: 3 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Needed to run Indexer
APIBARA_AUTH_TOKEN=dna_xxx

# Only needed to deploy the contract
STARKNET_KEYSTORE=$HOME/.starkli-sepolia/starkli-keystore.json
STARKNET_ACCOUNT=$HOME/.starkli-sepolia/starkli-account.json
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<div align="center">
<img src="apps/web/public/images/logo.png" alt="broly-logo" height="220"/>
<img src="apps/web/public/images/logo-high.png" alt="broly-logo" height="220"/>

# B.R.O.L.Y.
***Bitcoin Registry Orchestrates Like Yesterday***
Expand Down Expand Up @@ -97,6 +97,7 @@ broly/
├── packages/
│ ├── inscribor/ # Bitcoin inscription service
│ ├── onchain/ # Starknet smart contracts
│ ├── scripts/ # Deployment & Testing scripts
│ └── indexer/ # Starknet contract indexing
├── package.json
└── turbo.json
Expand Down
6 changes: 5 additions & 1 deletion apps/web/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,13 @@
"preview": "vite preview"
},
"dependencies": {
"@starknet-react/chains": "^3.1.1",
"@starknet-react/core": "^3.6.3",
"react": "^18.3.1",
"react-dom": "^18.3.1",
"react-router": "^7.0.1"
"react-router": "^7.0.1",
"starknet": "^6.11.0",
"starknetkit": "^2.6.1"
},
"devDependencies": {
"@eslint/js": "^9.13.0",
Expand Down
Binary file added apps/web/public/images/logo-high.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified apps/web/public/images/logo.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
132 changes: 126 additions & 6 deletions apps/web/src/App.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
import { useState } from 'react'
import { useState, useEffect } from 'react'
import { Routes, Route } from 'react-router'
import { CallData, RpcProvider, constants, byteArray, uint256 } from 'starknet';
import { useConnect, useDisconnect, useAccount, useContract, useSendTransaction } from '@starknet-react/core'
import { useStarknetkitConnectModal, StarknetkitConnector } from "starknetkit";
import './App.css'
import Header from './components/Header'
import orderbook_abi from './abi/orderbook.abi.json';

import Home from './pages/Home'
import Inscriptions from './pages/Inscriptions'
Expand All @@ -10,25 +14,141 @@ import Info from './pages/Info'
import Inscription from './pages/Inscription'
import Request from './pages/Request'

export const NODE_URL = 'https://starknet-sepolia.public.blastapi.io/rpc/v0_7';
export const STARKNET_CHAIN_ID = constants.StarknetChainId.SN_SEPOLIA;

//export const provider = new RpcProvider([NODE_URL], STARKNET_CHAIN_ID);
export const provider = new RpcProvider({
nodeUrl: NODE_URL,
chainId: STARKNET_CHAIN_ID
});

function App() {
// TODO: Move to seperate module ( starknet stuff )
const { connect, connectors } = useConnect()
const { disconnect, error } = useDisconnect()
const { address, status } = useAccount()
const { starknetkitConnectModal } = useStarknetkitConnectModal({
connectors: connectors as StarknetkitConnector[]
})
const [isConnected, setIsConnected] = useState(false)
const [connector, setConnector] = useState(null as StarknetkitConnector | null)

const connectWallet = async () => {
// TODO: If no wallet/connectors?
// TODO: Auto-reconnect on page refresh?
const { connector } = await starknetkitConnectModal()
if (!connector) {
return
}
connect({ connector })
setConnector(connector)
}

useEffect(() => {
if (!connectors) return;
if (connectors.length === 0) return;
if (isConnected) return;

const connectIfReady = async () => {
for (let i = 0; i < connectors.length; i++) {
let ready = await connectors[i].ready();
if (ready) {
connect({ connector: connectors[i] })
//setConnector(connectors[i])
break;
}
}
};
connectIfReady();
}, [connectors]);

useEffect(() => {
if (status === 'connected') {
setIsConnected(true)
} else if (status === 'disconnected') {
setIsConnected(false)
}
}, [address, status])

const disconnectWallet = async () => {
if (!isConnected || !connector) {
return
}
disconnect()
setConnector(null)
setIsConnected(false)
}

const toHex = (str: string) => {
let hex = '0x';
for (let i = 0; i < str.length; i++) {
hex += '' + str.charCodeAt(i).toString(16);
}
return hex;
};

const { contract: orderbookContract } = useContract({
address: import.meta.env.VITE_BROLY_CONTRACT_ADDRESS,
abi: orderbook_abi as any
});

const [calls, setCalls] = useState([] as any[])
const requestInscriptionCall = async () => {
if (!address || !orderbookContract) {
return
}
const calldata = CallData.compile([
byteArray.byteArrayFromString("message:Hello, Starknet!"),
byteArray.byteArrayFromString("tb1234567890123456789012345678901234567890"),
Number(100),
toHex("STRK"),
uint256.bnToUint256(2000)
]);
setCalls(
[orderbookContract.populate('request_inscription', calldata)]
)
}
const { send, data, isPending } = useSendTransaction({
calls
});
useEffect(() => {
const requestCall = async () => {
if (calls.length === 0) return;
send();
console.log('Call successful:', data, isPending);
// TODO: Update the UI with the new vote count
};
requestCall();
}, [calls]);

const cancelInscriptionCall = async () => {
// TODO
}

const [tabs, _setTabs] = useState([
{ name: 'Home', path: '/', component: Home },
{ name: 'Home', path: '/', component: Home as any },
{ name: 'Inscriptions', path: '/inscriptions', component: Inscriptions },
{ name: 'Collection', path: '/collection', component: Collection },
{ name: 'Info', path: '/info', component: Info },
])
const tabProps = {
requestInscriptionCall,
cancelInscriptionCall,
orderbookContract
}

// TODO: <Route path="*" element={<NotFound />} />
return (
<div className="h-screen relative">
<Header tabs={tabs} />
<Header tabs={tabs} connectWallet={connectWallet} isConnected={isConnected} disconnectWallet={disconnectWallet} />
<div className="h-[4.5rem]" />
<Routes>
{tabs.map((tab) => (
<Route key={tab.path} path={tab.path} element={<tab.component />} />
<Route key={tab.path} path={tab.path} element={<tab.component {...tabProps} />} />
))}
<Route path="/inscription/:id" element={<Inscription />} />
<Route path="/request/:id" element={<Request />} />
<Route path="/inscription/:id" element={<Inscription {...tabProps} />} />
<Route path="/request/:id" element={<Request {...tabProps} />} />
</Routes>
</div>
)
Expand Down
Loading

0 comments on commit f74a317

Please sign in to comment.