rc
This commit is contained in:
parent
533eb76c76
commit
8b47de1c57
55
app/callout.tsx
Normal file
55
app/callout.tsx
Normal file
|
|
@ -0,0 +1,55 @@
|
||||||
|
import React, { useState } from 'react';
|
||||||
|
import { motion } from 'framer-motion';
|
||||||
|
|
||||||
|
const CalloutModal = ({ isOpen, onClose, item, onSubmit }) => {
|
||||||
|
const [tokenId, setTokenId] = useState('');
|
||||||
|
|
||||||
|
const handleTokenChange = (e) => {
|
||||||
|
setTokenId(e.target.value);
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleSubmit = () => {
|
||||||
|
onSubmit(tokenId);
|
||||||
|
onClose();
|
||||||
|
};
|
||||||
|
|
||||||
|
return isOpen ? (
|
||||||
|
<motion.div
|
||||||
|
initial={{ opacity: 0 }}
|
||||||
|
animate={{ opacity: 1 }}
|
||||||
|
exit={{ opacity: 0 }}
|
||||||
|
className="fixed inset-0 bg-black bg-opacity-50 flex items-center justify-center z-50 modal-bg"
|
||||||
|
>
|
||||||
|
<div className="bg-white p-4 rounded shadow-lg w-11/12 max-w-md modal">
|
||||||
|
|
||||||
|
<div className="flex items-start">
|
||||||
|
<h2 className="text-xl font-bold mb-2">Make a new call!</h2>
|
||||||
|
<button
|
||||||
|
className="p-1 ml-auto bg-transparent border-0 text-black float-right text-3xl leading-none font-semibold outline-none focus:outline-none"
|
||||||
|
onClick={onClose}
|
||||||
|
>
|
||||||
|
<span className="bg-transparent text-white h-10 w-6 text-2xl block outline-none focus:outline-none">x</span>
|
||||||
|
</button>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<p className="text-lg mb-4">Type in a tokens short code, that you will think boom anytime soon</p>
|
||||||
|
<input
|
||||||
|
type="text"
|
||||||
|
value={tokenId}
|
||||||
|
onChange={handleTokenChange}
|
||||||
|
className="w-full p-2 mb-4 border rounded glassmorphism"
|
||||||
|
placeholder="Enter token short code"
|
||||||
|
/>
|
||||||
|
<button
|
||||||
|
onClick={handleSubmit}
|
||||||
|
className="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded w-full glassmorphism"
|
||||||
|
>
|
||||||
|
Submit
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</motion.div>
|
||||||
|
) : null;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default CalloutModal;
|
||||||
|
|
@ -14,7 +14,7 @@ body {
|
||||||
|
|
||||||
:root {
|
:root {
|
||||||
|
|
||||||
--glassmorphism-gradient: linear-gradient(135deg, rgba(255, 255, 255, 0.15) 0%, rgba(0, 0, 0, 0.1) 100%);
|
--glassmorphism-gradient: linear-gradient(135deg, rgba(255, 255, 255, 0.05) 0%, rgba(0, 0, 0, 0.2) 100%);
|
||||||
--glassmorphism-gradient-hover: linear-gradient(135deg, rgba(255, 255, 255, 0.3) 0%, rgba(0, 0, 0, 0.3) 100%);
|
--glassmorphism-gradient-hover: linear-gradient(135deg, rgba(255, 255, 255, 0.3) 0%, rgba(0, 0, 0, 0.3) 100%);
|
||||||
--glassmorphism-bg: rgba(255, 255, 255, 0.03);
|
--glassmorphism-bg: rgba(255, 255, 255, 0.03);
|
||||||
--glassmorphism-blur: 10px;
|
--glassmorphism-blur: 10px;
|
||||||
|
|
@ -60,12 +60,14 @@ body {
|
||||||
justify-content: center; /* Center vertically */
|
justify-content: center; /* Center vertically */
|
||||||
align-items: center; /* Center horizontally */
|
align-items: center; /* Center horizontally */
|
||||||
position: relative;
|
position: relative;
|
||||||
transition: background-image 0.3s ease, box-shadow 0.3s ease, border 0.3s ease, backdrop-filter 0.3s ease;
|
transition:{duration:1}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.leaderboard-card:hover{
|
.leaderboard-card:hover{
|
||||||
background: var(--glassmorphism-gradient-hover), var(--glassmorphism-bg);
|
background: var(--glassmorphism-gradient-hover), var(--glassmorphism-bg);
|
||||||
|
transition:{duration:1}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -84,4 +86,23 @@ body {
|
||||||
justify-content: center; /* Center vertically */
|
justify-content: center; /* Center vertically */
|
||||||
width: 100%;
|
width: 100%;
|
||||||
position:relative; /* Adjust padding as needed */
|
position:relative; /* Adjust padding as needed */
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
.modal {
|
||||||
|
background: linear-gradient(135deg, rgba(255, 255, 255, 0.1) 0%, rgba(0, 0, 0, 1) 100%), var(--glassmorphism-bg);
|
||||||
|
backdrop-filter: blur(var(--glassmorphism-blur));
|
||||||
|
border: 1px solid var(--glassmorphism-border);
|
||||||
|
box-shadow: 0 4px 6px rgba(0, 0, 0, 1);
|
||||||
|
overflow: hidden;
|
||||||
|
transition: background 0.3s ease, box-shadow 0.3s ease, border 0.3s ease;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-bg {
|
||||||
|
background: linear-gradient(135deg, rgba(100, 100, 100, 0.02) 0%, rgba(0, 0, 0, 0.1) 100%), var(--glassmorphism-bg);
|
||||||
|
backdrop-filter: blur(var(--glassmorphism-blur));
|
||||||
|
border: 1px solid var(--glassmorphism-border);
|
||||||
|
box-shadow: 0 4px 6px rgba(0, 0, 0, 1);
|
||||||
|
overflow: hidden;
|
||||||
|
transition: background 0.3s ease, box-shadow 0.3s ease, border 0.3s ease;
|
||||||
}
|
}
|
||||||
|
|
@ -1,32 +1,80 @@
|
||||||
// Modal.js
|
// Modal.js
|
||||||
|
|
||||||
import React from 'react';
|
import React, { useEffect,useState} from 'react';
|
||||||
|
import { motion } from 'framer-motion';
|
||||||
|
|
||||||
const Modal = ({ isOpen, onClose, item }) => {
|
const Modal = ({ isOpen, onClose, item }) => {
|
||||||
|
|
||||||
|
const [details, setDetails] = useState(null);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (isOpen && item) {
|
||||||
|
const fetchDetails = async () => {
|
||||||
|
try {
|
||||||
|
const response = await fetch(`https://api.callfi.io/get_user_callouts.php?tag=${item.username}`);
|
||||||
|
if (!response.ok) {
|
||||||
|
throw new Error('Network response was not ok');
|
||||||
|
}
|
||||||
|
const data = await response.json();
|
||||||
|
setDetails(data);
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Failed to fetch user details:', error);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
fetchDetails();
|
||||||
|
}
|
||||||
|
}, [isOpen, item]);
|
||||||
|
|
||||||
if (!isOpen) return null;
|
if (!isOpen) return null;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="fixed inset-0 z-50 flex items-center justify-center overflow-x-hidden overflow-y-auto outline-none focus:outline-none">
|
<motion.div
|
||||||
<div className="relative w-auto max-w-3xl mx-auto my-6">
|
initial={{ opacity: 0 }}
|
||||||
|
animate={{ opacity: 1 }}
|
||||||
|
exit={{ opacity: 0 }} className="fixed inset-0 z-50 flex items-center justify-center overflow-x-hidden overflow-y-auto outline-none focus:outline-none modal-bg" onClick={onClose}>
|
||||||
|
<div className="relative w-auto max-w-3xl mx-auto my-6 modal">
|
||||||
{/* Modal content */}
|
{/* Modal content */}
|
||||||
<div className="relative flex flex-col bg-white border-0 rounded-lg shadow-lg outline-none focus:outline-none">
|
<div className="relative flex flex-col border-0 rounded-lg shadow-lg outline-none focus:outline-none">
|
||||||
{/* Header */}
|
{/* Header */}
|
||||||
<div className="flex items-start justify-between p-5 border-b border-solid rounded-t border-blueGray-200">
|
<div className="flex items-start justify-between p-5 border-b border-solid rounded-t border-blueGray-200">
|
||||||
<h3 className="text-3xl font-semibold">{item.username}s Details</h3>
|
<h3 className="text-3xl font-semibold">{item.username}s Callouts</h3>
|
||||||
<button
|
{/* <button
|
||||||
className="p-1 ml-auto bg-transparent border-0 text-black float-right text-3xl leading-none font-semibold outline-none focus:outline-none"
|
className="p-1 ml-auto bg-transparent border-0 text-black float-right text-3xl leading-none font-semibold outline-none focus:outline-none"
|
||||||
onClick={onClose}
|
onClick={onClose}
|
||||||
>
|
>
|
||||||
<span className="bg-transparent text-black h-6 w-6 text-2xl block outline-none focus:outline-none">×</span>
|
<span className="bg-transparent text-black h-6 w-6 text-2xl block outline-none focus:outline-none">×</span>
|
||||||
</button>
|
</button>*/}
|
||||||
</div>
|
</div>
|
||||||
{/* Body */}
|
{/* Body */}
|
||||||
<div className="relative p-6 flex-auto">
|
<div className="relative p-6 flex-auto">
|
||||||
<p className="my-4 text-blueGray-500 text-lg leading-relaxed">{item.username} has {item.points} points.</p>
|
<p className={`my-4 text-blueGray-500 text-2xl font-bold leading-relaxed ${
|
||||||
|
parseFloat(item.points) > 0 ? 'text-green-500' : 'text-red-500'
|
||||||
|
}`}>Total Gains : {parseFloat(item.points).toFixed(2)} x</p>
|
||||||
</div>
|
</div>
|
||||||
|
<div className="relative p-6 flex-auto">
|
||||||
|
{details != null ? (
|
||||||
|
<div>
|
||||||
|
{details.map((detail) => (
|
||||||
|
<p
|
||||||
|
key={detail.token}
|
||||||
|
className={`my-4 text-lg leading-relaxed ${
|
||||||
|
parseFloat(detail.gains) > 0 ? 'text-green-500' : 'text-red-400'
|
||||||
|
}`}
|
||||||
|
>
|
||||||
|
{detail.token}: {parseFloat(detail.gains).toFixed(2)}x [
|
||||||
|
{parseFloat(detail.price_at_creation).toFixed(8) + ' => ' + parseFloat(detail.price_now).toFixed(8)}]
|
||||||
|
</p>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
) : (
|
||||||
|
<p>Loading...</p>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</motion.div>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
25
app/page.tsx
25
app/page.tsx
|
|
@ -6,6 +6,10 @@ import { PrivyProvider, usePrivy } from "@privy-io/react-auth";
|
||||||
import { FaTwitter, FaWallet } from "react-icons/fa";
|
import { FaTwitter, FaWallet } from "react-icons/fa";
|
||||||
import { CheckIcon } from "@heroicons/react/outline";
|
import { CheckIcon } from "@heroicons/react/outline";
|
||||||
import Modal from './modal';
|
import Modal from './modal';
|
||||||
|
import CalloutModal from './callout';
|
||||||
|
|
||||||
|
import { motion } from 'framer-motion';
|
||||||
|
|
||||||
|
|
||||||
// Helper functions to generate pseudo data
|
// Helper functions to generate pseudo data
|
||||||
const generateRandomName = () => {
|
const generateRandomName = () => {
|
||||||
|
|
@ -32,6 +36,7 @@ function Home() {
|
||||||
const [leaderboardData, setLeaderboardData] = useState([]);
|
const [leaderboardData, setLeaderboardData] = useState([]);
|
||||||
const [isJoined, setIsJoined] = useState(false);
|
const [isJoined, setIsJoined] = useState(false);
|
||||||
const [selectedItem, setSelectedItem] = useState(null); // State to store selected leaderboard item
|
const [selectedItem, setSelectedItem] = useState(null); // State to store selected leaderboard item
|
||||||
|
const [newCallModalOpen, setNewCallModalOpen] = useState(false);
|
||||||
|
|
||||||
// Function to handle opening modal and setting selected item
|
// Function to handle opening modal and setting selected item
|
||||||
const openModal = (item) => {
|
const openModal = (item) => {
|
||||||
|
|
@ -45,6 +50,19 @@ function Home() {
|
||||||
setModalOpen(false);
|
setModalOpen(false);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const openNewCallModal = () => {
|
||||||
|
setNewCallModalOpen(true);
|
||||||
|
};
|
||||||
|
|
||||||
|
const closeNewCallModal = () => {
|
||||||
|
setNewCallModalOpen(false);
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleNewCallSubmit = (tokenId) => {
|
||||||
|
const twitterIntentURL = `https://x.com/intent/tweet?text=%24${tokenId}%20is%20Booming%20rn%21%20See%20ya%20on%20the%20moon%21%0A%0A%23CallFi%20%23CallingIt`;
|
||||||
|
window.open(twitterIntentURL, '_blank');
|
||||||
|
};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (darkMode) {
|
if (darkMode) {
|
||||||
document.documentElement.classList.add("dark");
|
document.documentElement.classList.add("dark");
|
||||||
|
|
@ -182,8 +200,8 @@ function Home() {
|
||||||
<div className="note-card glassmorphism mb-4 p-4 text-center rounded-lg px-20 py-5">
|
<div className="note-card glassmorphism mb-4 p-4 text-center rounded-lg px-20 py-5">
|
||||||
<h2 className="text-2xl font-bold mb-2">Feeling Lucky?</h2>
|
<h2 className="text-2xl font-bold mb-2">Feeling Lucky?</h2>
|
||||||
<p className="text-lg mb-4">Make a callout to a token you believe in!!</p>
|
<p className="text-lg mb-4">Make a callout to a token you believe in!!</p>
|
||||||
<button className="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded glassmorphism">
|
<button className="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded glassmorphism" onClick={openNewCallModal}>
|
||||||
<a href="https://x.com/intent/tweet?text=%24COC%20is%20Booming%20rn%21%20See%20ya%20on%20the%20moon%21%0A%0A%23CallFi%20%23CallingIt" target="_blank" rel="noopener noreferrer">CALL OUT!</a>
|
CALL OUT!
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
@ -217,15 +235,18 @@ function Home() {
|
||||||
<div className="w-full p-4 flex flex-col items-center justify-center">
|
<div className="w-full p-4 flex flex-col items-center justify-center">
|
||||||
<div className="w-full max-w-4xl">
|
<div className="w-full max-w-4xl">
|
||||||
{leaderboardData.map((item) => (
|
{leaderboardData.map((item) => (
|
||||||
|
<motion.div key ="id" whileHover={{scale:1.1, transition:{duration:0.2}}}>
|
||||||
<div key={item["id"]} className={`leaderboard-card glassmorphism ${item["points"] >= 0 ? 'positive' : 'negative'} mx-auto mb-4`} onClick={() => openModal(item)}>
|
<div key={item["id"]} className={`leaderboard-card glassmorphism ${item["points"] >= 0 ? 'positive' : 'negative'} mx-auto mb-4`} onClick={() => openModal(item)}>
|
||||||
<p className="text-center font-bold">{item["username"]}</p>
|
<p className="text-center font-bold">{item["username"]}</p>
|
||||||
<p className="text-center">{parseFloat(item["points"]).toFixed(2)}x</p>
|
<p className="text-center">{parseFloat(item["points"]).toFixed(2)}x</p>
|
||||||
</div>
|
</div>
|
||||||
|
</motion.div>
|
||||||
))}
|
))}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{/* Modal */}
|
{/* Modal */}
|
||||||
<Modal isOpen={modalOpen} onClose={closeModal} item={selectedItem} />
|
<Modal isOpen={modalOpen} onClose={closeModal} item={selectedItem} />
|
||||||
|
<CalloutModal isOpen={newCallModalOpen} onClose={closeNewCallModal} onSubmit={handleNewCallSubmit} />
|
||||||
|
|
||||||
{/* Rest of your Home component */}
|
{/* Rest of your Home component */}
|
||||||
|
|
||||||
|
|
|
||||||
Binary file not shown.
|
Before Width: | Height: | Size: 780 KiB After Width: | Height: | Size: 1.9 MiB |
BIN
public/black_backe.jpg
Normal file
BIN
public/black_backe.jpg
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 4.3 MiB |
BIN
public/black_backg.jpg
Normal file
BIN
public/black_backg.jpg
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 780 KiB |
BIN
public/black_backs.jpg
Normal file
BIN
public/black_backs.jpg
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 558 KiB |
Loading…
Reference in New Issue
Block a user