text-transformer / src /components /BinaryConverter.jsx
OnyxlMunkey's picture
Text Transformer: Docker app for HF Space
0f5ca68
import React, { useState, useEffect } from 'react';
const BinaryConverter = ({ addToMessage, sharedInput, setSharedInput }) => {
const [output, setOutput] = useState('');
const [copied, setCopied] = useState(false);
const [toBinary, setToBinary] = useState(true);
const [hasError, setHasError] = useState(false);
const convertToBinary = (text) => {
let binary = '';
for (let i = 0; i < text.length; i++) {
binary += text[i].charCodeAt(0).toString(2) + ' ';
}
setOutput(binary.trim());
setHasError(false);
};
const convertFromBinary = (binary) => {
try {
let text = '';
const binaryChars = binary.split(' ');
for (let binaryChar of binaryChars) {
if (binaryChar) {
const decimal = parseInt(binaryChar, 2);
if (isNaN(decimal)) {
throw new Error('Invalid binary string');
}
text += String.fromCharCode(decimal);
}
}
setOutput(text);
} catch (error) {
setOutput('Error: Invalid binary string');
}
};
const handleInputChange = (e) => {
const newText = e.target.value;
// Limit input to 50,000 characters to prevent performance issues
if (newText.length > 50000) {
return;
}
setSharedInput(newText);
if (toBinary) {
convertToBinary(newText);
} else {
convertFromBinary(newText);
}
};
// Recalculate output when component mounts or sharedInput changes from another converter
useEffect(() => {
if (sharedInput) {
if (toBinary) {
convertToBinary(sharedInput);
} else {
convertFromBinary(sharedInput);
}
} else {
setOutput('');
}
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [sharedInput, toBinary]);
const copyToClipboard = () => {
navigator.clipboard.writeText(output);
setCopied(true);
setTimeout(() => setCopied(false), 2000);
};
const swapConversion = () => {
const oldInput = sharedInput;
setSharedInput(output);
setOutput(oldInput);
setToBinary(!toBinary);
};
return (
<div className="p-6 bg-gradient-to-br from-gray-900 to-black rounded-lg border border-gray-800 hover-glow transition-all duration-300">
<h2 className="text-3xl font-bold mb-6 text-white flex items-center gap-2">
<span className="text-invader-green">💻</span>
Binary Converter
</h2>
<div className="grid grid-cols-1 md:grid-cols-[1fr_auto_1fr] gap-6 items-center">
<div className="space-y-2">
<label htmlFor="binary-input" className="block text-sm font-medium text-gray-300 mb-2">{toBinary ? 'Text Input' : 'Binary Input'}</label>
<textarea
id="binary-input"
className="w-full h-40 p-4 bg-black border-2 border-invader-green/30 rounded-lg text-white focus:ring-2 focus:ring-invader-green focus:border-invader-green transition-all duration-300 hover:border-invader-green/50 resize-none"
placeholder={toBinary ? "Enter text to convert to binary" : "Enter binary to convert to text"}
value={sharedInput}
onChange={handleInputChange}
/>
</div>
<div className="flex justify-center">
<button
onClick={swapConversion}
className="p-3 bg-gradient-to-br from-invader-green to-green-600 text-black rounded-full hover:from-green-400 hover:to-green-500 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-invader-green transition-all duration-300 hover:scale-110 active:scale-95 shadow-lg hover:shadow-invader-green/50 font-bold"
title="Swap conversion direction"
>
<svg xmlns="http://www.w3.org/2000/svg" className="h-6 w-6" fill="none" viewBox="0 0 24 24" stroke="currentColor">
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M8 7h12m0 0l-4-4m4 4l-4 4m2 5H4m0 0l4 4m-4-4l4-4" />
</svg>
</button>
</div>
<div className="space-y-2">
<label htmlFor="binary-output" className="block text-sm font-medium text-gray-300 mb-2">{toBinary ? 'Binary Output' : 'Text Output'}</label>
<div id="binary-output" className="w-full h-40 p-4 bg-black border-2 border-invader-green/30 rounded-lg text-white relative overflow-auto hover:border-invader-green/50 transition-all duration-300">
<div className={`break-words ${output.startsWith('Error:') ? 'text-red-400' : ''}`}>{output || <span className="text-gray-500">Output will appear here...</span>}</div>
{output && !output.startsWith('Error:') && (
<div className="absolute top-2 right-2 flex flex-col gap-2">
<button
onClick={copyToClipboard}
className="px-4 py-2 bg-gradient-to-r from-invader-pink to-pink-600 text-black font-semibold rounded-md hover:from-pink-500 hover:to-pink-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-invader-pink transition-all duration-300 shadow-md hover:shadow-lg hover:scale-105 active:scale-95"
>
{copied ? '✓ Copied!' : '📋 Copy'}
</button>
<button
onClick={() => addToMessage(output)}
className="px-4 py-2 bg-gradient-to-r from-invader-green to-green-600 text-black font-semibold rounded-md hover:from-green-500 hover:to-green-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-invader-green transition-all duration-300 shadow-md hover:shadow-lg hover:scale-105 active:scale-95"
>
➕ Add
</button>
</div>
)}
</div>
</div>
</div>
</div>
);
};
export default BinaryConverter;