diff --git a/app/api/trading/execute-perp/route.js b/app/api/trading/execute-perp/route.js
index c8369c7..ff7f074 100644
--- a/app/api/trading/execute-perp/route.js
+++ b/app/api/trading/execute-perp/route.js
@@ -66,7 +66,23 @@ export async function POST(request) {
)
}
- // For now, simulate perpetual trades until Jupiter Perpetuals integration is complete
+ // Check if we should use real DEX or simulation
+ if (useRealDEX) {
+ console.log('🚀 Executing REAL perpetual trade via Jupiter Perpetuals')
+
+ // TODO: Implement actual Jupiter Perpetuals integration here
+ // For now, return an error indicating real trading is not yet implemented
+ return NextResponse.json(
+ {
+ success: false,
+ error: 'Real Jupiter Perpetuals trading not yet implemented. Set useRealDEX: false for simulation mode.',
+ feature: 'JUPITER_PERPS_REAL_TRADING',
+ status: 'IN_DEVELOPMENT'
+ },
+ { status: 501 } // Not Implemented
+ )
+ }
+
console.log('🎮 Executing SIMULATED perpetual trade (Jupiter Perps integration in development)')
// Normalize side for perps
diff --git a/app/chart-test/page.tsx b/app/chart-test/page.tsx
new file mode 100644
index 0000000..d310e2e
--- /dev/null
+++ b/app/chart-test/page.tsx
@@ -0,0 +1,14 @@
+'use client'
+import React from 'react'
+import TradingChart from '../../components/TradingChart.tsx'
+
+export default function SimpleChartTest() {
+ return (
+
+ {/* Top Bar */}
+
+
+
+
Chart Trading Terminal
+
+ {/* Symbol Selector */}
+
+ {['SOL', 'BTC', 'ETH'].map(symbol => (
+
+ ))}
+
+
+
+ {/* Market Status */}
+
+
+
+ {new Date().toLocaleTimeString()}
+
+
+
+
+
+ {/* Main Trading Interface */}
+
+ {/* Chart Area (70% width) */}
+
+
+
+
+ {/* Trading Panel (30% width) */}
+
+
+
+
+
+ {/* Bottom Panel - Positions */}
+
+
+
+
+
+
+
+
+
+ {positions.length > 0 && (
+
+ Total P&L: sum + (pos.unrealizedPnl || 0), 0) >= 0
+ ? 'text-green-400' : 'text-red-400'
+ }`}>
+ {positions.reduce((sum, pos) => sum + (pos.unrealizedPnl || 0), 0) >= 0 ? '+' : ''}$
+ {positions.reduce((sum, pos) => sum + (pos.unrealizedPnl || 0), 0).toFixed(2)}
+
+
+ )}
+
+
+ {/* Positions Table */}
+
+ {positions.length === 0 ? (
+
+ No open positions
+
+ ) : (
+
+ {positions.map((position: any) => (
+
+
+
+
+
+ {position.symbol} • {position.side}
+
+
+ Size: {position.amount} • Entry: ${position.entryPrice?.toFixed(2)}
+
+ {position.stopLoss && (
+
+ SL: ${position.stopLoss.toFixed(2)}
+
+ )}
+ {position.takeProfit && (
+
+ TP: ${position.takeProfit.toFixed(2)}
+
+ )}
+
+
+
+
+
+ ${(position.amount * position.currentPrice).toFixed(2)}
+
+
= 0 ? 'text-green-400' : 'text-red-400'
+ }`}>
+ {(position.unrealizedPnl || 0) >= 0 ? '+' : ''}${(position.unrealizedPnl || 0).toFixed(2)}
+
+
+
+
+
+
+
+ ))}
+
+ )}
+
+
+
+
+ )
+}
diff --git a/app/chart-trading/page.tsx b/app/chart-trading/page.tsx
new file mode 100644
index 0000000..8c91d17
--- /dev/null
+++ b/app/chart-trading/page.tsx
@@ -0,0 +1,198 @@
+'use client'
+import React, { useState, useEffect } from 'react'
+import TradingChart from '../../components/TradingChart'
+import CompactTradingPanel from '../../components/CompactTradingPanel'
+import PositionsPanel from '../../components/PositionsPanel'
+
+export default function ChartTradingPage() {
+ const [currentPrice, setCurrentPrice] = useState(166.21)
+ const [positions, setPositions] = useState([])
+ const [selectedSymbol, setSelectedSymbol] = useState('SOL')
+
+ useEffect(() => {
+ fetchPositions()
+ const interval = setInterval(fetchPositions, 10000) // Update every 10 seconds
+ return () => clearInterval(interval)
+ }, [])
+
+ const fetchPositions = async () => {
+ try {
+ const response = await fetch('/api/trading/positions')
+ const data = await response.json()
+
+ if (data.success) {
+ setPositions(data.positions || [])
+ }
+ } catch (error) {
+ console.error('Failed to fetch positions:', error)
+ }
+ }
+
+ const handleTrade = async (tradeData: any) => {
+ try {
+ console.log('Executing trade:', tradeData)
+
+ // For perpetual trades, use the execute-perp endpoint
+ const response = await fetch('/api/trading/execute-perp', {
+ method: 'POST',
+ headers: { 'Content-Type': 'application/json' },
+ body: JSON.stringify(tradeData)
+ })
+
+ const result = await response.json()
+
+ if (result.success) {
+ alert(`Trade executed successfully! ${result.message}`)
+ fetchPositions() // Refresh positions
+ } else {
+ alert(`Trade failed: ${result.error || result.message}`)
+ }
+ } catch (error) {
+ console.error('Trade execution error:', error)
+ alert('Trade execution failed. Please try again.')
+ }
+ }
+
+ const handlePriceUpdate = (price: number) => {
+ setCurrentPrice(price)
+ }
+
+ return (
+
+ {/* Top Bar */}
+
+
+
+
Trading Terminal
+
+ {/* Symbol Selector */}
+
+ {['SOL', 'BTC', 'ETH'].map(symbol => (
+
+ ))}
+
+
+
+ {/* Market Status */}
+
+
+
+ Server Time: {new Date().toLocaleTimeString()}
+
+
+
+
+
+ {/* Main Trading Interface */}
+
+ {/* Chart Area (70% width) */}
+
+
+
+
+ {/* Trading Panel (30% width) */}
+
+
+
+
+
+ {/* Bottom Panel - Positions */}
+
+
+
+
+
+
+
+
+
+ {positions.length > 0 && (
+
+ Total P&L: +$0.00
+
+ )}
+
+
+ {/* Positions Table */}
+
+ {positions.length === 0 ? (
+
+ No open positions
+
+ ) : (
+
+ {positions.map((position: any) => (
+
+
+
+
+
+ {position.symbol} • {position.side}
+
+
+ Size: {position.amount} • Entry: ${position.entryPrice?.toFixed(2)}
+
+
+
+
+
+
+ ${position.totalValue?.toFixed(2) || '0.00'}
+
+
= 0 ? 'text-green-400' : 'text-red-400'
+ }`}>
+ {(position.unrealizedPnl || 0) >= 0 ? '+' : ''}${(position.unrealizedPnl || 0).toFixed(2)}
+
+
+
+
+
+
+
+
+ ))}
+
+ )}
+
+
+
+
+ )
+}
diff --git a/app/globals.css b/app/globals.css
index 6450dbb..a51cd7d 100644
--- a/app/globals.css
+++ b/app/globals.css
@@ -93,3 +93,99 @@ input[type="range"]:focus::-webkit-slider-thumb {
input[type="range"]:focus::-moz-range-thumb {
box-shadow: 0 0 0 3px rgba(59, 130, 246, 0.3);
}
+
+/* Trading Chart Slider Styles */
+.slider::-webkit-slider-thumb {
+ appearance: none;
+ width: 20px;
+ height: 20px;
+ border-radius: 50%;
+ background: #3b82f6;
+ cursor: pointer;
+ border: 2px solid #1f2937;
+ box-shadow: 0 0 0 1px #3b82f6;
+}
+
+.slider::-webkit-slider-thumb:hover {
+ background: #2563eb;
+ box-shadow: 0 0 0 2px #2563eb;
+}
+
+.slider::-moz-range-thumb {
+ width: 20px;
+ height: 20px;
+ border-radius: 50%;
+ background: #3b82f6;
+ cursor: pointer;
+ border: 2px solid #1f2937;
+ box-shadow: 0 0 0 1px #3b82f6;
+}
+
+/* Chart container styling */
+.trading-chart-container {
+ position: relative;
+ background: linear-gradient(135deg, #1a1a1a 0%, #2d2d2d 100%);
+}
+
+/* Position indicator styles */
+.position-indicator {
+ position: absolute;
+ top: 10px;
+ right: 10px;
+ background: rgba(0, 0, 0, 0.8);
+ border-radius: 8px;
+ padding: 8px 12px;
+ color: white;
+ font-size: 12px;
+ z-index: 10;
+}
+
+/* Trading panel animations */
+.trade-button {
+ transition: all 0.2s ease-in-out;
+}
+
+.trade-button:hover {
+ transform: translateY(-1px);
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.3);
+}
+
+.trade-button:active {
+ transform: translateY(0);
+}
+
+/* Chart loading animation */
+.chart-loading {
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ height: 600px;
+ background: #1a1a1a;
+ border-radius: 8px;
+}
+
+.loading-spinner {
+ border: 2px solid #374151;
+ border-top: 2px solid #3b82f6;
+ border-radius: 50%;
+ width: 32px;
+ height: 32px;
+ animation: spin 1s linear infinite;
+}
+
+@keyframes spin {
+ 0% { transform: rotate(0deg); }
+ 100% { transform: rotate(360deg); }
+}
+
+/* Responsive chart adjustments */
+@media (max-width: 1024px) {
+ .trading-interface {
+ flex-direction: column;
+ }
+
+ .trading-panel {
+ width: 100%;
+ max-width: none;
+ }
+}
diff --git a/components/CompactTradingPanel.tsx b/components/CompactTradingPanel.tsx
new file mode 100644
index 0000000..f28b1e1
--- /dev/null
+++ b/components/CompactTradingPanel.tsx
@@ -0,0 +1,270 @@
+'use client'
+import React, { useState } from 'react'
+
+interface CompactTradingPanelProps {
+ symbol: string
+ currentPrice: number
+ onTrade?: (tradeData: any) => void
+}
+
+export default function CompactTradingPanel({
+ symbol = 'SOL',
+ currentPrice = 166.21,
+ onTrade
+}: CompactTradingPanelProps) {
+ const [side, setSide] = useState<'LONG' | 'SHORT'>('LONG')
+ const [orderType, setOrderType] = useState<'MARKET' | 'LIMIT'>('MARKET')
+ const [amount, setAmount] = useState('')
+ const [price, setPrice] = useState(currentPrice.toString())
+ const [leverage, setLeverage] = useState(1)
+ const [stopLoss, setStopLoss] = useState('')
+ const [takeProfit, setTakeProfit] = useState('')
+ const [loading, setLoading] = useState(false)
+
+ // Update price when currentPrice changes
+ React.useEffect(() => {
+ if (orderType === 'MARKET') {
+ setPrice(currentPrice.toString())
+ }
+ }, [currentPrice, orderType])
+
+ const calculateLiquidationPrice = () => {
+ const entryPrice = parseFloat(price) || currentPrice
+ const leverage_ratio = leverage || 1
+ if (side === 'LONG') {
+ return entryPrice * (1 - 1 / leverage_ratio)
+ } else {
+ return entryPrice * (1 + 1 / leverage_ratio)
+ }
+ }
+
+ const calculatePositionSize = () => {
+ const amt = parseFloat(amount) || 0
+ const entryPrice = parseFloat(price) || currentPrice
+ return amt * entryPrice
+ }
+
+ const handleTrade = async () => {
+ if (!amount || parseFloat(amount) <= 0) {
+ alert('Please enter a valid amount')
+ return
+ }
+
+ setLoading(true)
+ try {
+ const tradeData = {
+ symbol,
+ side: side === 'LONG' ? 'BUY' : 'SELL',
+ amount: parseFloat(amount),
+ price: orderType === 'MARKET' ? currentPrice : parseFloat(price),
+ type: orderType.toLowerCase(),
+ leverage,
+ stopLoss: stopLoss ? parseFloat(stopLoss) : undefined,
+ takeProfit: takeProfit ? parseFloat(takeProfit) : undefined,
+ tradingMode: 'PERP'
+ }
+
+ onTrade?.(tradeData)
+ } catch (error) {
+ console.error('Trade execution failed:', error)
+ } finally {
+ setLoading(false)
+ }
+ }
+
+ const leverageOptions = [1, 2, 3, 5, 10, 20, 25, 50, 100]
+
+ return (
+
+ {/* Header */}
+
+
{symbol}/USDC
+
+ ${currentPrice.toFixed(2)}
+
+
+
+ {/* Long/Short Toggle */}
+
+
+
+
+
+ {/* Order Type */}
+
+
+
+
+
+ {/* Leverage Slider */}
+
+
+
+ {leverage}x
+
+
+
setLeverage(parseInt(e.target.value))}
+ className="w-full h-2 bg-gray-700 rounded-lg appearance-none cursor-pointer slider"
+ />
+
+ {leverageOptions.map(lev => (
+ {lev}x
+ ))}
+
+
+
+
+ {/* Amount Input */}
+
+
+
+
setAmount(e.target.value)}
+ placeholder="0.00"
+ className="w-full p-3 bg-gray-800 border border-gray-700 rounded-lg text-white placeholder-gray-400 focus:border-blue-500 focus:outline-none"
+ />
+
+
+
+
+
+
+
+
+ {/* Price Input (for limit orders) */}
+ {orderType === 'LIMIT' && (
+
+
+ setPrice(e.target.value)}
+ placeholder="0.00"
+ className="w-full p-3 bg-gray-800 border border-gray-700 rounded-lg text-white placeholder-gray-400 focus:border-blue-500 focus:outline-none"
+ />
+
+ )}
+
+ {/* Stop Loss & Take Profit */}
+
+
+ {/* Position Info */}
+
+
+ Position Size:
+ ${calculatePositionSize().toFixed(2)}
+
+
+ Liquidation Price:
+ ${calculateLiquidationPrice().toFixed(2)}
+
+
+ Available:
+ $5,000.00
+
+
+
+ {/* Trade Button */}
+
+
+ {/* Quick Actions */}
+
+
+
+
+
+ )
+}
diff --git a/components/Navigation.tsx b/components/Navigation.tsx
index a5057d5..9fe8404 100644
--- a/components/Navigation.tsx
+++ b/components/Navigation.tsx
@@ -22,6 +22,12 @@ const navItems = [
icon: '💰',
description: 'Execute trades'
},
+ {
+ name: 'Chart Trading',
+ href: '/chart-trading-demo',
+ icon: '📈',
+ description: 'Advanced chart trading'
+ },
{
name: 'Automation',
href: '/automation',
diff --git a/components/TradeModal_backup.tsx b/components/TradeModal_backup.tsx
new file mode 100644
index 0000000..fb765c7
--- /dev/null
+++ b/components/TradeModal_backup.tsx
@@ -0,0 +1,402 @@
+"use client"
+import React, { useState, useEffect, ChangeEvent } from 'react'
+
+interface TradeModalProps {
+ isOpen: boolean
+ onClose: () => void
+ tradeData: {
+ entry: string
+ tp: string
+ sl: string
+ risk: string
+ reward: string
+ action: 'BUY' | 'SELL'
+ } | null
+ onExecute: (data: any) => void
+}
+
+interface FormData {
+ entry: string
+ tp1: string
+ tp2: string
+ sl: string
+ positionValue: string
+ leverage: number
+ tradingCoin: string
+ tp1Percentage: number
+ tp2Percentage: number
+}
+
+const supportedCoins = [
+ { symbol: 'SOL', name: 'Solana', icon: 'â—Ž', price: 159.5 },
+ { symbol: 'USDC', name: 'USD Coin', icon: '$', price: 1.0 }
+]
+
+export default function TradeModal({ isOpen, onClose, tradeData, onExecute }: TradeModalProps) {
+ console.log('🚀 TradeModal loaded with enhanced features - Version 2.0')
+ const [loading, setLoading] = useState(false)
+ const [walletBalance, setWalletBalance] = useState