Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 20 additions & 13 deletions web/src/app/[cat]/InteractionClient.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,16 @@ export default function InteractionClient() {
const formatNumber = (num: number, decimals: number = 4): string => {
if (num === 0) return "0";
if (num < 0.0001) return num.toExponential(2);
return num.toFixed(decimals);

// Format with specified decimals
const formatted = num.toFixed(decimals);

// Remove trailing zeros after decimal point
if (formatted.includes('.')) {
return formatted.replace(/\.?0+$/, '');
}

return formatted;
};

const [isLoading, setIsLoading] = useState(true);
Expand Down Expand Up @@ -539,11 +548,13 @@ export default function InteractionClient() {
try {
await fetchTokenDetailsFromBlockchain();
toast.success('Token details synced successfully');
// Force re-initialization to refresh all data
await initializeTokenDetails();
} catch (error) {
console.error('Manual sync failed:', error);
toast.error('Failed to sync token details. Please try again.');
}
}, [tokenAddress, chainId, address, isOnline, fetchTokenDetailsFromBlockchain]);
}, [tokenAddress, chainId, address, isOnline, fetchTokenDetailsFromBlockchain, initializeTokenDetails]);

useEffect(() => {
if (isInitialized && tokenAddress && chainId && address) {
Expand Down Expand Up @@ -1116,7 +1127,7 @@ export default function InteractionClient() {
<Coins className="h-5 w-5 text-green-500 dark:text-[#FFD600]" />
<h3 className="text-lg font-semibold text-blue-400 dark:text-yellow-200">Max Supply</h3>
</div>
<p className="text-lg font-bold text-blue-400 dark:text-yellow-200">{tokenDetails.maxSupply} {tokenDetails.tokenSymbol}</p>
<p className="text-lg font-bold text-blue-400 dark:text-yellow-200">{formatNumber(tokenDetails.maxSupply)} {tokenDetails.tokenSymbol}</p>
</div>
<Button
onClick={openMaxSupplyModal}
Expand All @@ -1133,7 +1144,7 @@ export default function InteractionClient() {
<Target className="h-5 w-5 text-blue-400 dark:text-[#FFD600]" />
<h3 className="text-lg font-semibold text-blue-400 dark:text-yellow-200">Threshold Supply</h3>
</div>
<p className="text-lg font-bold text-blue-400 dark:text-yellow-200">{tokenDetails.thresholdSupply} {tokenDetails.tokenSymbol}</p>
<p className="text-lg font-bold text-blue-400 dark:text-yellow-200">{formatNumber(tokenDetails.thresholdSupply)} {tokenDetails.tokenSymbol}</p>
</div>
<Button
onClick={openThresholdModal}
Expand All @@ -1150,7 +1161,7 @@ export default function InteractionClient() {
<ArrowUp className="h-5 w-5 text-purple-500 dark:text-[#FFD600]" />
<h3 className="text-lg font-semibold text-blue-400 dark:text-yellow-200">Expansion Rate</h3>
</div>
<p className="text-lg font-bold text-blue-400 dark:text-yellow-200">{tokenDetails.maxExpansionRate} %</p>
<p className="text-lg font-bold text-blue-400 dark:text-yellow-200">{formatNumber(tokenDetails.maxExpansionRate)}%</p>
</div>
<Button
onClick={openExpansionRateModal}
Expand Down Expand Up @@ -1220,8 +1231,7 @@ export default function InteractionClient() {
<div className="flex items-center justify-between mb-4">
<div className="space-y-1">
<p className="text-sm text-gray-600 dark:text-yellow-200">
Max Mintable Amount:
<span
Max Mintable Amount: <span
className="font-bold cursor-help"
title={`${tokenDetails.maxMintableAmount} ${tokenDetails.tokenSymbol}`}
>
Expand All @@ -1230,8 +1240,7 @@ export default function InteractionClient() {
</p>
</div>
<p className="text-sm text-gray-600 dark:text-yellow-200">
Current Supply:
<span
Current Supply: <span
className="font-bold cursor-help"
title={`${tokenDetails.currentSupply} ${tokenDetails.tokenSymbol}`}
>
Expand Down Expand Up @@ -1266,8 +1275,7 @@ export default function InteractionClient() {
{mintAmount && !isNaN(Number(mintAmount)) && Number(mintAmount) > 0 && (
<div className="mt-2 p-2 rounded-lg bg-blue-50 dark:bg-yellow-400/10 border border-blue-200 dark:border-yellow-400/20">
<p className="text-xs text-blue-600 dark:text-yellow-200">
You will receive:
<span
You will receive: <span
className="font-bold cursor-help"
title={`${userAmountAfterFees || 0} ${tokenDetails.tokenSymbol}`}
>
Expand All @@ -1280,8 +1288,7 @@ export default function InteractionClient() {
)} {tokenDetails.tokenSymbol}
</span>
<br />
Clowder fee:
<span
Clowder fee: <span
className="font-bold cursor-help"
title={`${!isNaN(userAmountAfterFees) && userAmountAfterFees !== null ? Number(mintAmount) - userAmountAfterFees : 0} ${tokenDetails.tokenSymbol}`}
>
Expand Down
36 changes: 20 additions & 16 deletions web/src/app/my-cats/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -300,22 +300,7 @@ export default function MyCATsPage() {
}
}, [address, isOnline, getCache, batchSaveCatDetails, saveCache, fetchAllCATsFromBlockchain]);

// Manual sync function for consistency with InteractionClient
const handleManualSync = useCallback(async () => {
if (!address || !isOnline) {
if (!isOnline) {
toast.error('Cannot sync while offline. Please check your internet connection.');
}
return;
}

try {
await syncWithBlockchain(true);
} catch (error) {
console.error('Manual sync failed:', error);
toast.error('Failed to sync CATs. Please try again.');
}
}, [address, isOnline, syncWithBlockchain]);


// Listen for CAT creation events and auto-sync
useEffect(() => {
Expand Down Expand Up @@ -405,6 +390,25 @@ export default function MyCATsPage() {
}
}, [address, isInitialized, loadCATsFromStorage, pagination.catsPerPage]);

// Manual sync function for consistency with InteractionClient
const handleManualSync = useCallback(async () => {
if (!address || !isOnline) {
if (!isOnline) {
toast.error('Cannot sync while offline. Please check your internet connection.');
}
return;
}

try {
await syncWithBlockchain(true);
// Refresh the page data after successful sync
await updateFilteredCATs();
} catch (error) {
console.error('Manual sync failed:', error);
toast.error('Failed to sync CATs. Please try again.');
}
}, [address, isOnline, syncWithBlockchain, updateFilteredCATs]);

// Update current page CATs when page changes (without refetching from storage)
const updateCurrentPageCATs = useCallback((page: number) => {
// Early return with empty slice when no pages
Expand Down
40 changes: 4 additions & 36 deletions web/src/app/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -245,38 +245,6 @@ export default function Home() {
viewport={{ once: true }}
>
<div className="grid grid-cols-1 lg:grid-cols-3 gap-8 relative">
{/* Enhanced Flow arrows for desktop */}
<motion.div
className="hidden lg:block absolute top-1/2 left-1/3 w-12 h-0.5 bg-gradient-to-r from-blue-400 via-purple-400 to-blue-500 dark:from-yellow-400 dark:via-yellow-500 dark:to-yellow-600 transform -translate-y-1/2 shadow-sm"
initial={{ scaleX: 0 }}
whileInView={{ scaleX: 1 }}
transition={{ duration: 0.6, delay: 1.2 }}
viewport={{ once: true }}
>
<motion.div
className="absolute -right-2 -top-1.5 w-4 h-4 border-r-2 border-t-2 border-blue-500 dark:border-yellow-500 transform rotate-45"
initial={{ opacity: 0, x: -10 }}
whileInView={{ opacity: 1, x: 0 }}
transition={{ duration: 0.4, delay: 1.8 }}
viewport={{ once: true }}
></motion.div>
</motion.div>
<motion.div
className="hidden lg:block absolute top-1/2 left-2/3 w-12 h-0.5 bg-gradient-to-r from-blue-400 via-purple-400 to-blue-500 dark:from-yellow-400 dark:via-yellow-500 dark:to-yellow-600 transform -translate-y-1/2 shadow-sm"
initial={{ scaleX: 0 }}
whileInView={{ scaleX: 1 }}
transition={{ duration: 0.6, delay: 1.4 }}
viewport={{ once: true }}
>
<motion.div
className="absolute -right-2 -top-1.5 w-4 h-4 border-r-2 border-t-2 border-blue-500 dark:border-yellow-500 transform rotate-45"
initial={{ opacity: 0, x: -10 }}
whileInView={{ opacity: 1, x: 0 }}
transition={{ duration: 0.4, delay: 2.0 }}
viewport={{ once: true }}
></motion.div>
</motion.div>

{[
{
step: "01",
Expand Down Expand Up @@ -386,22 +354,22 @@ export default function Home() {
{
title: "Open Source Projects",
explanation: "Reward developers for coding, bug fixing, documentation, and improving the projects impact.",
gradient: "from-green-400 to-blue-500"
gradient: "from-blue-500 to-blue-600 dark:from-yellow-400 dark:to-yellow-500"
},
{
title: "Creative Collaboratives",
explanation: "Artists, musicians, and content creators can fairly share ownership according to their creative input and effort.",
gradient: "from-pink-400 to-purple-500"
gradient: "from-blue-500 to-blue-600 dark:from-yellow-500 dark:to-yellow-600"
},
{
title: "Event Management",
explanation: "Recognize and reward event organizers, volunteers, and promoters for making events successful and engaging.",
gradient: "from-cyan-400 to-sky-500"
gradient: "from-blue-500 to-blue-600 dark:from-yellow-400 dark:to-yellow-500"
},
{
title: "Community DAOs",
explanation: "Give community members fair governance rights and influence based on their active participation and contributions.",
gradient: "from-teal-400 to-emerald-500"
gradient: "from-blue-500 to-blue-600 dark:from-yellow-500 dark:to-yellow-600"
}
].map((useCase, index) => (
<motion.div
Expand Down