gradio_icons_gallery / index.html
elismasilva's picture
Update index.html
d06a21e verified
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Gradio Icon Gallery</title>
<script src="https://cdn.tailwindcss.com"></script>
<style>
/* A nicer scrollbar for dark mode */
::-webkit-scrollbar { width: 8px; }
::-webkit-scrollbar-track { background: #1f2937; } /* gray-800 */
::-webkit-scrollbar-thumb { background: #4b5563; border-radius: 4px; } /* gray-600 */
::-webkit-scrollbar-thumb:hover { background: #6b7280; } /* gray-500 */
.icon-container > svg {
animation: none !important;
}
</style>
</head>
<body class="bg-gray-900 text-gray-200 font-sans">
<div id="app" class="container mx-auto p-4 md:p-8">
<header class="text-center mb-8">
<h1 class="text-4xl font-bold text-white">Gradio Icon Gallery</h1>
<p class="text-gray-400 mt-2">Browse and search all available icons from <code class="bg-gray-700 text-orange-400 px-2 py-1 rounded">@gradio/icons</code>.</p>
</header>
<div class="sticky top-4 z-10 mb-8">
<input
type="text"
id="search-input"
placeholder="Search for an icon (e.g., 'Check', 'Download')..."
class="w-full p-3 bg-gray-800 border border-gray-700 rounded-lg text-white focus:ring-2 focus:ring-orange-500 focus:outline-none transition"
>
</div>
<div id="icon-grid" class="grid grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-6 xl:grid-cols-8 gap-4">
<!-- Icon cards will be inserted here by JavaScript -->
<div id="loading-message" class="col-span-full text-center py-10">
<p class="text-lg">Fetching icons from CDN...</p>
<p class="text-sm text-gray-500">This may take a moment.</p>
</div>
</div>
</div>
<script type="module">
// The definitive, corrected list of icon names.
const ICON_NAMES = [
"ArrowDown", "ArrowUp", "Back", "Backward", "Brush", "BrushSize", "Calendar",
"Camera", "Chart", "Chat", "Check", "Circle", "Clear", "Code", "Color",
"ColorPickerSolid", "Community", "Copy", "Crop", "Download", "DropdownArrow",
"DropdownCircularArrow", "Edit", "Erase", "Error", "Eyedropper", "File",
"Forward", "Image", "ImagePaste", "ImageResize", "Info", "JSON", "Layers",
"LineChart", "Maximise", "Maximize", "Microphone", "Minimize", "Music",
"Palette", "Pan", "Paperclip", "Pause", "Play", "Plot", "Plus", "Redo",
"Remove", "Resize", "Retry", "Rotate", "ScrollDownArrow", "Send", "Settings",
"Sketch", "Spinner", "Square", "Success", "Table", "TextHighlight", "Trash",
"Tree", "Trim", "Undo", "Upload", "Video", "Visibility", "VisibilityOff",
"VolumeHigh", "VolumeLow", "VolumeMuted", "Warning", "Webcam", "ZoomIn", "ZoomOut"
].sort(); // Sort the list alphabetically for a clean display.
const iconGrid = document.getElementById('icon-grid');
const searchInput = document.getElementById('search-input');
const loadingMessage = document.getElementById('loading-message');
let allIconData = [];
function renderIcons(filter = '') {
iconGrid.innerHTML = ''; // Clear the current grid
const lowerCaseFilter = filter.toLowerCase();
const filteredIcons = allIconData.filter(icon =>
icon.name.toLowerCase().includes(lowerCaseFilter)
);
if (filteredIcons.length === 0) {
iconGrid.innerHTML = `<div class="col-span-full text-center py-10"><p class="text-lg">No icons found for "${filter}"</p></div>`;
}
filteredIcons.forEach(iconData => {
const card = document.createElement('div');
card.className = "flex flex-col items-center justify-center p-4 bg-gray-800 rounded-lg border border-gray-700 hover:bg-gray-700 hover:border-orange-500 transition cursor-pointer";
const iconContainer = document.createElement('div');
iconContainer.className = "w-10 h-10 mb-3 text-white icon-container"; // Added 'icon-container' class
iconContainer.innerHTML = iconData.svgString;
const nameLabel = document.createElement('p');
nameLabel.className = "text-sm text-center font-mono break-all";
nameLabel.textContent = iconData.name;
card.appendChild(iconContainer);
card.appendChild(nameLabel);
card.addEventListener('click', () => {
const textToCopy = `<${iconData.name} />`;
navigator.clipboard.writeText(textToCopy).then(() => {
const originalText = nameLabel.textContent;
nameLabel.textContent = "Copied!";
nameLabel.classList.add('text-green-400');
setTimeout(() => {
nameLabel.textContent = originalText;
nameLabel.classList.remove('text-green-400');
}, 1500);
});
});
iconGrid.appendChild(card);
});
}
async function init() {
try {
// Fetch the raw text content of each .svelte file.
const fetchPromises = ICON_NAMES.map(name =>
fetch(`https://cdn.jsdelivr.net/npm/@gradio/[email protected]/src/${name}.svelte`)
.then(response => {
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status} for ${name}`);
}
return response.text();
})
);
const loadedSvgStrings = await Promise.all(fetchPromises);
allIconData = ICON_NAMES.map((name, index) => ({
name: name,
svgString: loadedSvgStrings[index]
}));
} catch (error) {
loadingMessage.innerHTML = `<p class="text-red-400">Failed to load icons. Check the browser console for details.</p>`;
console.error("Error fetching Gradio icons:", error);
return;
}
loadingMessage.style.display = 'none';
renderIcons();
searchInput.addEventListener('input', (e) => {
renderIcons(e.target.value);
});
}
// Start the application
init();
</script>
</body>
</html>