import React, { useState, useEffect, useRef } from 'react';
function TemplateCloneButton({ templateId, configId, userId, onComplete, customizations = {} }) {
const [isLoading, setIsLoading] = useState(false);
const popupRef = useRef(null);
const handleClone = () => {
customizations: customizations,
returnUrl: window.location.href,
timestamp: new Date().toISOString()
const encodedMetadata = btoa(JSON.stringify(metadata));
const embedUrl = `https://app.templated.io/editor/${templateId}?embed=${configId}&metadata=${encodedMetadata}`;
// Use popup window for better UX
popupRef.current = window.open(
'width=1200,height=800,scrollbars=yes,resizable=yes'
// Listen for completion message
const messageHandler = (event) => {
if (event.origin === 'https://app.templated.io' && event.data.type === 'template_saved') {
popupRef.current.close();
onComplete?.(event.data.template);
window.removeEventListener('message', messageHandler);
window.addEventListener('message', messageHandler);
// Handle popup closed manually
const checkClosed = setInterval(() => {
if (popupRef.current?.closed) {
clearInterval(checkClosed);
window.removeEventListener('message', messageHandler);
className="clone-template-btn"
{isLoading ? 'Opening Editor...' : 'Customize This Design'}
// Advanced template clone component with modal support
function TemplateCloneModal({ templateId, configId, userId, isOpen, onClose, onComplete }) {
const [embedUrl, setEmbedUrl] = useState('');
if (isOpen && templateId) {
timestamp: new Date().toISOString()
const encodedMetadata = btoa(JSON.stringify(metadata));
setEmbedUrl(`https://app.templated.io/editor/${templateId}?embed=${configId}&metadata=${encodedMetadata}`);
}, [isOpen, templateId, configId, userId]);
if (!isOpen) return null;
<div className="template-clone-modal">
<div className="modal-overlay" onClick={onClose}>
<div className="modal-content" onClick={(e) => e.stopPropagation()}>
<div className="modal-header">
<button onClick={onClose} className="close-btn">×</button>
<div className="modal-body">
title="Template Clone Editor"
// Template gallery with clone functionality
function TemplateGallery({ templates, configId, userId }) {
const [cloneModal, setCloneModal] = useState({ isOpen: false, templateId: null });
const handleCloneTemplate = (templateId) => {
setCloneModal({ isOpen: true, templateId });
const handleCloneComplete = (newTemplate) => {
console.log('Template cloned:', newTemplate);
setCloneModal({ isOpen: false, templateId: null });
// Refresh template list or show success message
const handleCloseModal = () => {
setCloneModal({ isOpen: false, templateId: null });
<div className="template-gallery">
<div className="template-grid">
{templates.map((template) => (
<div key={template.id} className="template-card">
<img src={template.thumbnail} alt={template.name} />
<div className="template-info">
<p>{template.description}</p>
<div className="template-actions">
onComplete={handleCloneComplete}
onClick={() => handleCloneTemplate(template.id)}
className="btn-secondary"
templateId={cloneModal.templateId}
isOpen={cloneModal.isOpen}
onClose={handleCloseModal}
onComplete={handleCloneComplete}
// Custom hook for template cloning
function useTemplateClone(configId) {
const [isCloning, setIsCloning] = useState(false);
const [clonedTemplates, setClonedTemplates] = useState([]);
const cloneTemplate = (templateId, userId, customizations = {}) => {
return new Promise((resolve, reject) => {
timestamp: new Date().toISOString()
const encodedMetadata = btoa(JSON.stringify(metadata));
const embedUrl = `https://app.templated.io/editor/${templateId}?embed=${configId}&metadata=${encodedMetadata}`;
const popup = window.open(embedUrl, 'template-clone', 'width=1200,height=800');
const messageHandler = (event) => {
if (event.origin === 'https://app.templated.io' && event.data.type === 'template_saved') {
setClonedTemplates(prev => [...prev, event.data.template]);
resolve(event.data.template);
window.removeEventListener('message', messageHandler);
window.addEventListener('message', messageHandler);
const checkClosed = setInterval(() => {
clearInterval(checkClosed);
window.removeEventListener('message', messageHandler);
reject(new Error('Popup closed by user'));