11import React , { useState , useRef , useEffect } from 'react' ;
2+ import { LineChart , Legend , Line , XAxis , YAxis , Tooltip , CartesianGrid , ResponsiveContainer } from "recharts" ;
23import { Button } from './ui/button' ;
34
4- function NQubitInput ( { numQubits , setQubits } ) {
5+ function NQubitInput ( { setQubits } ) {
56 const [ tempQ , setTempQ ] = useState ( '' ) ;
67 const [ error , setError ] = useState ( '' ) ;
8+ const [ lineData , setLineData ] = useState ( [ ] ) ;
79 const inputRef = useRef ( null ) ;
810
911 useEffect ( ( ) => {
1012 inputRef . current ?. focus ( ) ;
1113 } , [ ] ) ;
1214
15+ const validate_input = ( x ) => {
16+ if ( / ^ \d + $ / . test ( x . trim ( ) ) === false ) {
17+ setError ( 'Please enter a valid and positive number.' ) ;
18+ setQubits ( null ) ;
19+ inputRef . current . focus ( ) ;
20+ return null ;
21+ }
22+ const parsedValue = parseInt ( x . trim ( ) , 10 ) ;
23+
24+ if ( isNaN ( parsedValue ) || parsedValue < 1 || ! isFinite ( parsedValue ) ) {
25+ setError ( 'Please enter a number greater than or equal to 1.' ) ;
26+ setQubits ( null ) ;
27+ inputRef . current . focus ( ) ;
28+ } else {
29+ setError ( '' ) ;
30+ }
31+
32+ return parsedValue ;
33+ }
34+
1335 const handleChange = ( e ) => {
1436 setTempQ ( e . target . value ) ;
15- setError ( '' ) ;
37+ const parsed = validate_input ( e . target . value ) ;
38+
39+ if ( error == '' && parsed !== null ) {
40+ const newData = [ ] ;
41+ for ( let i = 1 ; i <= parsed ; i ++ ) {
42+ newData . push ( {
43+ name : `Qubit ${ i } ` ,
44+ qubits : i ,
45+ bytes : Math . pow ( 2 , i ) * 16
46+ } ) ;
47+ }
48+ setLineData ( newData ) ;
49+ }
50+ else
51+ setLineData ( [ ] ) ;
1652 } ;
1753
1854 const handleConfirm = ( ) => {
@@ -21,19 +57,10 @@ function NQubitInput({ numQubits, setQubits }) {
2157 return ;
2258 }
2359
24- const parsedValue = parseInt ( tempQ . trim ( ) , 10 ) ;
25-
26- if ( / ^ \d + $ / . test ( tempQ . trim ( ) ) === false ) {
27- setError ( 'Please enter a valid and positive number.' ) ;
28- setQubits ( null ) ;
29- inputRef . current . focus ( ) ;
30- } else if ( isNaN ( parsedValue ) || parsedValue < 1 || ! isFinite ( parsedValue ) ) {
31- setError ( 'Please enter a number greater than or equal to 1.' ) ;
32- setQubits ( null ) ;
33- inputRef . current . focus ( ) ;
34- } else {
35- setError ( '' ) ;
36- setQubits ( parsedValue ) ;
60+ const x = validate_input ( tempQ ) ;
61+ if ( error == '' && x !== null ) {
62+ setLineData ( [ ] ) ;
63+ setQubits ( x ) ;
3764 }
3865 } ;
3966
@@ -44,60 +71,131 @@ function NQubitInput({ numQubits, setQubits }) {
4471 } ;
4572
4673 return (
47- < div
48- style = { {
74+ < div style = { {
75+ display : "flex"
76+ } } >
77+ < div style = { { height : "600px" , width : "50%" } } >
78+ < textarea
79+ readOnly
80+ value = { `A qubit (quantum bit) is the fundamental unit of quantum information.
81+ Unlike classical bits which are either 0 or 1, a qubit can be in a superposition ds
82+ of both 0 and 1 states at the same time. This allows quantum computers to
83+ perform complex calculations much faster than classical computers in some cases.` }
84+ style = { {
85+ width : '100%' ,
86+ height : '50%' ,
87+ padding : '12px' ,
88+ fontSize : '14px' ,
89+ fontFamily : 'monospace, monospace' ,
90+ resize : 'none' ,
91+ backgroundColor : '#f0f0f0' ,
92+ color : '#333' ,
93+ borderRadius : '8px' ,
94+ border : '1px solid #ccc' ,
95+ marginBottom : '1rem' ,
96+ whiteSpace : 'pre-wrap'
97+ } }
98+ />
99+ < div style = { { height : "480px" , width : "100%" , marginLeft : "20px" } } >
100+ { lineData . length > 0 ? (
101+ < ResponsiveContainer width = "100%" height = "100%" >
102+ < LineChart data = { lineData } margin = { { top : 10 , right : 30 , left : 0 , bottom : 0 } } >
103+ < CartesianGrid strokeDasharray = "3 3" />
104+ < XAxis dataKey = "qubits" label = { { value : 'Qubits' , position : 'insideBottom' , offset : - 5 } } />
105+ < YAxis
106+ label = { { value : "" , angle : - 90 , position : 'insideLeft' , offset : 50 } }
107+ tickFormatter = { ( val ) => {
108+ if ( val >= 1e15 ) return `${ ( val / 1e15 ) . toFixed ( 1 ) } PB` ;
109+ if ( val >= 1e12 ) return `${ ( val / 1e12 ) . toFixed ( 1 ) } TB` ;
110+ if ( val >= 1e9 ) return `${ ( val / 1e9 ) . toFixed ( 1 ) } GB` ;
111+ if ( val >= 1e6 ) return `${ ( val / 1e6 ) . toFixed ( 1 ) } MB` ;
112+ if ( val >= 1e3 ) return `${ ( val / 1e3 ) . toFixed ( 1 ) } KB` ;
113+ return `${ val } B` ;
114+ } }
115+ />
116+ < Tooltip
117+ contentStyle = { { background : "#F8F1E7" , fontWeight : "bold" , borderRadius : "5px" , padding : "10px" , boxShadow : "0px 0px 10px rgba(0,0,0,0.2)" } }
118+ formatter = { ( val ) =>
119+ [ val >= 1e15 ? `Mem. Required: ${ ( val / 1e15 ) . toFixed ( 1 ) } PB` :
120+ val >= 1e12 ? `Mem. Required: ${ ( val / 1e12 ) . toFixed ( 1 ) } TB` :
121+ val >= 1e9 ? `Mem. Required: ${ ( val / 1e9 ) . toFixed ( 1 ) } GB` :
122+ val >= 1e6 ? `Mem. Required: ${ ( val / 1e6 ) . toFixed ( 1 ) } MB` :
123+ val >= 1e3 ? `Mem. Required: ${ ( val / 1e3 ) . toFixed ( 1 ) } KB` :
124+ `${ val } B` ]
125+ }
126+ labelFormatter = { ( name ) => [ `Qubits: ${ name } ` ] } />
127+ < Legend />
128+ < Line type = "monotone" dataKey = "bytes" stroke = "#82ca9d" dot />
129+ </ LineChart >
130+ </ ResponsiveContainer >
131+
132+ ) : (
133+ < div className = "h-full flex items-center justify-center text-gray-500" >
134+ Chart will appear here once you enter a number.
135+ </ div >
136+ ) }
137+ </ div >
138+ </ div >
139+ < div style = { {
140+ width : "50%" ,
141+ height : "600px" ,
49142 display : "flex" ,
50- flexDirection : "column" ,
51- gap : "10px" ,
52- userSelect : "none" ,
53- width : "100%" ,
54- maxWidth : "500px" ,
55143 alignItems : "center" ,
56- justifyContent : "center" ,
57- top : "50%" ,
58- left : "50%" ,
59- position : "absolute" ,
60- transform : "translate(-50%, -50%)" ,
61- border : "solid 3px" ,
62- borderRadius : "8px" ,
63- padding : "2rem" ,
64- boxShadow : "0px 4px 12px rgba(0, 0, 0, 0.15)" ,
65- backgroundColor : "#fff" ,
66- } }
67- >
68- < h1 className = "text-2xl font-bold mb-4 text-center" >
69- Enter Number of Qubits
70- </ h1 >
71- < input
72- ref = { inputRef }
73- //type="number"
74- value = { tempQ }
75- onChange = { handleChange }
76- onKeyDown = { handleKeyDown }
77- className = "w-full p-2 border border-gray-300 rounded focus:outline-none focus:ring-2 focus:ring-blue-500"
78- placeholder = "Number of Qubits"
79- min = "1"
80- />
81- < Button
82- variant = "outline"
83- className = "w-full py-2"
84- onClick = { handleConfirm }
85- >
86- Confirm
87- </ Button >
88- < Button
89- variant = "ghost"
90- className = "w-full text-sm text-gray-500"
91- onClick = { ( ) => {
92- setTempQ ( '' ) ;
93- setError ( '' ) ;
94- setQubits ( null ) ;
95- inputRef . current . focus ( ) ;
96- } }
97- >
98- Reset
99- </ Button >
100- { error && < p className = "text-red-500 text-sm mt-2" style = { { fontFamily : "monospace, monospace" , } } > { error } </ p > }
144+ justifyContent : "center"
145+ } } >
146+ < div
147+ style = { {
148+ display : "flex" ,
149+ flexDirection : "column" ,
150+ gap : "10px" ,
151+ userSelect : "none" ,
152+ width : "100%" ,
153+ maxWidth : "500px" ,
154+ alignItems : "center" ,
155+ justifyContent : "center" ,
156+ border : "solid 3px" ,
157+ borderRadius : "8px" ,
158+ padding : "2rem" ,
159+ boxShadow : "0px 4px 12px rgba(0, 0, 0, 0.15)" ,
160+ backgroundColor : "#fff" ,
161+ } }
162+
163+ >
164+ < h1 className = "text-2xl font-bold mb-4 text-center" >
165+ Enter Number of Qubits
166+ </ h1 >
167+ < input
168+ ref = { inputRef }
169+ type = "number"
170+ value = { tempQ }
171+ onChange = { handleChange }
172+ onKeyDown = { handleKeyDown }
173+ className = "w-full p-2 border border-gray-300 rounded focus:outline-none focus:ring-2 focus:ring-blue-500"
174+ placeholder = "Number of Qubits"
175+ min = "1"
176+ />
177+ < Button
178+ variant = "outline"
179+ className = "w-full py-2"
180+ onClick = { handleConfirm }
181+ >
182+ Confirm
183+ </ Button >
184+ < Button
185+ variant = "ghost"
186+ className = "w-full text-sm text-gray-500"
187+ onClick = { ( ) => {
188+ setTempQ ( '' ) ;
189+ setError ( '' ) ;
190+ setQubits ( null ) ;
191+ inputRef . current . focus ( ) ;
192+ } }
193+ >
194+ Reset
195+ </ Button >
196+ { error . length > 0 && < p className = "text-red-500 text-sm mt-2" style = { { fontFamily : "monospace, monospace" , } } > { error } </ p > }
197+ </ div >
198+ </ div >
101199 </ div >
102200 ) ;
103201}
0 commit comments