Want your own launchpad?
I build these end to end: smart contracts, indexer, and front end.
Telegram: @cashblaze129
The first meme coin launchpad built for stock-paired markets, powered by Robinhood Chain.
Launch and trade meme coins paired directly against tokenised stocks:
TOKEN/NVDA · TOKEN/AAPL · TOKEN/META · TOKEN/SPCX
Fair launch. No presale. No insider allocation. Real liquidity from day one.
robinpair-launchpad.mp4
· launch creation, stock-paired trading, graduation
Fair-launch token platform where every launch is quoted in a Robinhood Chain stock token (TOKEN/NVDA, TOKEN/AAPL, TOKEN/META, TOKEN/SPCX …). Tokens trade on a constant-product bonding curve denominated in the stock asset and graduate into a locked Uniswap V3 position once the curve hits its quote threshold.
contracts/ Hardhat project (Solidity 0.8.24, OpenZeppelin 5)
contracts/config LaunchpadConfig - every business parameter lives here
contracts/core LaunchpadFactory, LaunchPool (bonding curve, fees, graduation)
contracts/token LaunchToken - fixed supply, minted once to the pool
contracts/graduation UniswapV3Migrator - locked full-range LP + LP fee split
contracts/libraries BondingCurveMath - virtual-reserve constant product
src/
config/ chain, contract addresses, quote assets, product constants
lib/abi ABIs generated from the compiled artifacts
lib/chain viem public client + wagmi config
lib/launchpad domain types, curve math mirror, formatting
lib/indexer server-side log/state readers (launches, trades, holders, portfolio)
app/api route handlers - the only place the UI fetches data from
components/ui design system primitives
components/… launch, trade and layout components
RobinPair — meme coins, real stocks, endless opportunities. Source artwork
lives in public/assets/; the derived marks in public/brand/ and
src/app/icon.png are generated from logo.png with the black background
flood-filled to transparency (an edge fill, not a brightness threshold, so the
white counter of the "R" survives).
Palette is sampled from the logo rather than guessed: acid lime #c0e010 with a
#d0f020 highlight, on a near-black ground carrying a faint green cast so the
whole surface belongs to the mark. Type is Saira for display — echoing the wide,
squared wordmark — Inter for dense UI text, and JetBrains Mono for every number.
Green means both brand and gains here, deliberately. The brand sheet marks gains in its own lime, and so does Robinhood's own product, so unifying them is faithful rather than sloppy. Red still owns the downside, which is what keeps the signal readable.
Configuration is centralised. LaunchpadConfig holds fee splits, the treasury,
the migrator address, the pause flag, and one QuoteAssetConfig per supported stock
token (curve seeds, curve/LP supply split, graduation threshold, creation fee, Uniswap
fee tier). The factory reads it at creation time and freezes the terms into the pool,
so changing configuration never alters the terms of a live launch.
The stock token is the quote and reserve asset. Reserves, fees, price, market cap and slippage are all denominated in it; the curve never touches ETH/WETH. Quote assets with any decimals are supported - the curve operates on raw units and never mixes the two scales.
Curve. k = virtualQuote₀ · virtualToken₀, live reserves
quote = virtualQuote₀ + realQuote, token = virtualToken₀ − tokensSold. Every rounding
decision favours the pool. Accounting invariant, checked in tests:
quote.balanceOf(pool) >= realQuoteReserve + accruedPlatformFees + accruedCreatorFees
Graduation. A buy that would cross the quote threshold is capped and the surplus
refunded. The pool then moves to Graduating; anyone may call graduate(), which takes
the graduation fee, burns unsold curve supply, and mints a full-range Uniswap V3 position
priced at the curve's final price. The position NFT stays in the migrator forever - there
is no code path that decreases liquidity - while swap fees remain collectable and are
split between creator and treasury.
Data. Everything shown in the UI is derived from chain state and Trade / Transfer
logs: price, market cap, volume, holders, candles, portfolio P&L. There are no mocked
figures anywhere in the app.
cd contracts
npm install
npx hardhat compile
npx hardhat testDeployment (never commit keys; everything comes from the environment):
cp .env.example .env # DEPLOYER_PRIVATE_KEY, TREASURY_ADDRESS, QUOTE_ASSETS, …
npx hardhat run scripts/deploy.ts --network robinhoodscripts/deploy.ts writes contracts/deployments/<chainId>.json with the addresses to
paste into the web .env. On a local node (npx hardhat node) it also deploys
MockStockToken stand-ins so the whole flow is exercisable offline - those are
development-only and are never deployed to a public network.
QUOTE_ASSETS format:
NVDA:0x…:18:23:67:0.05:10000
<symbol>:<address>:<decimals>:<virtualQuote>:<graduationThreshold>:<creationFee>:<uniswapFeeTier>
The curve can raise at most virtualQuote × curveSupply / (virtualTokenReserve − curveSupply)
- 2.93× the virtual quote reserve for the default shape - so thresholds are set just under that ceiling.
npm install
cp .env.example .env.local # addresses printed by the deploy script
npm run devnpm run build, npm run typecheck, npm run lint.
cd contracts && npx hardhat node # terminal 1
npm run deploy:local # terminal 2 (writes deployments/31337.json)
npm run seed:local # a few launches + real trades
npm run graduate:local # POOL_INDEX=0 fills a curve and migrates itCopy the printed addresses into .env.local (NEXT_PUBLIC_LAUNCHPAD_FACTORY,
NEXT_PUBLIC_LAUNCHPAD_CONFIG, NEXT_PUBLIC_MULTICALL3_ADDRESS,
NEXT_PUBLIC_QUOTE_ASSETS, NEXT_PUBLIC_DEPLOY_BLOCK) and run npm run dev.
The local node also gets a Multicall3 and a MockPositionManager so batched
reads and graduation work offline; neither is ever deployed to a public network.
Until NEXT_PUBLIC_LAUNCHPAD_FACTORY / NEXT_PUBLIC_LAUNCHPAD_CONFIG are set the app
renders a setup page listing exactly what is missing instead of an empty product.
| Testnet | Mainnet | |
|---|---|---|
| Chain id | 46630 | 4663 |
| Public RPC | https://rpc.testnet.chain.robinhood.com/rpc |
https://rpc.mainnet.chain.robinhood.com |
| Explorer | explorer.testnet.chain.robinhood.com | robinhoodchain.blockscout.com |
| Multicall3 | 0xcA11…76CA11 (verified live) |
0xcA11…76CA11 |
| Uniswap V3 | not deployed | NonfungiblePositionManager 0x73991a25C818Bf1f1128dEAaB1492D45638DE0D3 |
| Canonical stock tokens | none - testnet uses labelled test tokens | 194 assets via api.robinhood.com/rhj/assets |
Both profiles are built into src/config/chain.ts and contracts/config/networks.ts,
so only NEXT_PUBLIC_CHAIN_ID has to be set.
Stock tokens are never faked on mainnet. Quote assets are resolved from Robinhood's
canonical asset registry, and any configured address that is not in it renders with a
"Test token" badge plus a chain-wide banner. The Robinhood testnet has no canonical stock
tokens (anyone can deploy an ERC-20 called NVDA there), so a testnet deployment mints
its own openly-mintable test tokens instead of pointing at an impostor contract.
For the same reason Uniswap V3 is absent on testnet, so graduation there uses a clearly
labelled stub position manager; mainnet uses the real Uniswap V3 deployment.
cd contracts
cp .env.example .env
npm run new-deployer # writes a key to .env (never printed), prints its address
# fund that address at https://faucet.testnet.chain.robinhood.com
npm run estimate:testnet # what the deployment will cost at the current gas price
npm run preflight:testnet # RPC, chain id, balance, Multicall3, Uniswap, quote assets
npm run deploy:testnet # prints a ready-to-paste .env.local block
npm run seed:testnet # optional: a few launches with real tradesPaste the printed block into the web app's .env.local and run npm run dev.
| Value | Where | Why |
|---|---|---|
DEPLOYER_PRIVATE_KEY |
contracts/.env |
funded key for the target network (npm run new-deployer creates one) |
TREASURY_ADDRESS |
contracts/.env |
receives platform and graduation fees |
| Curve parameters per asset | QUOTE_ASSETS or config/launch-params.ts |
virtual reserve and graduation threshold should track each share price |
NEXT_PUBLIC_RPC_URL |
.env.local |
the public RPCs are rate-limited; use a provider key in production |