fix: resolve 401 Unauthorized in Gemini editUVLayer by properly passing auth token, update loading UI with grayscale/blur, fix WebGLShadowMap deprecation warnings
Build and Deploy / build-and-push (push) Successful in 28s

This commit is contained in:
AI Bot
2026-09-30 17:15:53 +05:30
parent 86ba3a961c
commit 49a3882441
4 changed files with 28 additions and 23 deletions
+20 -15
View File
@@ -29,7 +29,7 @@ const ModelPreview = ({ url }: { url: string }) => {
if (!model) return <div className="absolute inset-0 flex items-center justify-center"><Loader2 className="w-8 h-8 animate-spin text-zinc-500" /></div>; if (!model) return <div className="absolute inset-0 flex items-center justify-center"><Loader2 className="w-8 h-8 animate-spin text-zinc-500" /></div>;
return ( return (
<Canvas shadows camera={{ position: [0, 1.5, 3], fov: 45 }}> <Canvas shadows={{ type: THREE.PCFShadowMap }} camera={{ position: [0, 1.5, 3], fov: 45 }}>
<Stage environment="studio" intensity={0.5}> <Stage environment="studio" intensity={0.5}>
<primitive object={model} /> <primitive object={model} />
</Stage> </Stage>
@@ -39,7 +39,7 @@ const ModelPreview = ({ url }: { url: string }) => {
}; };
export const ImageTo3DModal: React.FC<ImageTo3DModalProps> = ({ isOpen, onClose, onPushToApp }) => { export const ImageTo3DModal: React.FC<ImageTo3DModalProps> = ({ isOpen, onClose, onPushToApp }) => {
const { profile, setProfile, token } = useAuthStore(); const { profile, setProfile } = useAuthStore();
const [meshyApiKey, setMeshyApiKey] = useState(''); const [meshyApiKey, setMeshyApiKey] = useState('');
// Image states // Image states
@@ -97,6 +97,7 @@ export const ImageTo3DModal: React.FC<ImageTo3DModalProps> = ({ isOpen, onClose,
setCleanedImagePreview(null); setCleanedImagePreview(null);
try { try {
const base64 = await fileToDataUrl(fileToClean); const base64 = await fileToDataUrl(fileToClean);
const token = localStorage.getItem('auth_token') || '';
const newUrl = await editUVLayer("Remove the background and make it solid transparent or white. Also carefully remove all text, labels, logos, and stickers, keeping the product as a perfectly clean, plain, unbranded object.", base64, token); const newUrl = await editUVLayer("Remove the background and make it solid transparent or white. Also carefully remove all text, labels, logos, and stickers, keeping the product as a perfectly clean, plain, unbranded object.", base64, token);
const res = await fetch(newUrl); const res = await fetch(newUrl);
@@ -300,10 +301,13 @@ export const ImageTo3DModal: React.FC<ImageTo3DModalProps> = ({ isOpen, onClose,
{/* Cleaned Image */} {/* Cleaned Image */}
<div className="flex-1 relative border-2 border-solid border-zinc-700 rounded-xl overflow-hidden bg-zinc-900/50 flex items-center justify-center group"> <div className="flex-1 relative border-2 border-solid border-zinc-700 rounded-xl overflow-hidden bg-zinc-900/50 flex items-center justify-center group">
{isCleaningImage ? ( {isCleaningImage ? (
<div className="flex flex-col items-center text-zinc-400 gap-3"> <>
<img src={originalImagePreview} alt="Original Grayscale" className="absolute inset-0 w-full h-full object-contain p-2 opacity-30 grayscale blur-sm" />
<div className="absolute inset-0 flex flex-col items-center justify-center text-zinc-300 gap-3 bg-black/40 z-10">
<Loader2 size={28} className="animate-spin text-blue-500" /> <Loader2 size={28} className="animate-spin text-blue-500" />
<span className="text-sm font-medium">AI Cleaning...</span> <span className="text-sm font-medium">AI Cleaning Image...</span>
</div> </div>
</>
) : cleanedImagePreview ? ( ) : cleanedImagePreview ? (
<> <>
<img src={cleanedImagePreview} alt="Cleaned" className="w-full h-full object-contain p-2" /> <img src={cleanedImagePreview} alt="Cleaned" className="w-full h-full object-contain p-2" />
@@ -405,22 +409,23 @@ export const ImageTo3DModal: React.FC<ImageTo3DModalProps> = ({ isOpen, onClose,
<h3 className="text-sm font-bold text-zinc-200">3D Preview</h3> <h3 className="text-sm font-bold text-zinc-200">3D Preview</h3>
</div> </div>
<div className="flex-1 relative flex items-center justify-center"> <div className="flex-1 relative flex items-center justify-center overflow-hidden">
{generatedModelUrl ? ( {isGenerating ? (
<>
{cleanedImagePreview || originalImagePreview ? (
<img src={(cleanedImagePreview || originalImagePreview) as string} alt="Generating Base" className="absolute inset-0 w-full h-full object-contain p-8 opacity-20 grayscale blur-md scale-110" />
) : null}
<div className="absolute inset-0 flex flex-col items-center justify-center text-zinc-300 bg-black/60 z-20">
<Loader2 size={36} className="animate-spin text-blue-500 mb-4" />
<p className="text-sm font-medium text-zinc-200">{progressMessage}</p>
</div>
</>
) : generatedModelUrl ? (
<ModelPreview url={generatedModelUrl} /> <ModelPreview url={generatedModelUrl} />
) : ( ) : (
<div className="flex flex-col items-center justify-center text-zinc-600 p-6 text-center"> <div className="flex flex-col items-center justify-center text-zinc-600 p-6 text-center">
{isGenerating ? (
<>
<Loader2 size={32} className="animate-spin text-blue-500 mb-4" />
<p className="text-sm font-medium text-zinc-300">{progressMessage}</p>
</>
) : (
<>
<Box size={32} className="mb-3 opacity-50" /> <Box size={32} className="mb-3 opacity-50" />
<p className="text-sm">Your 3D model will appear here</p> <p className="text-sm">Your 3D model will appear here</p>
</>
)}
</div> </div>
)} )}
</div> </div>
+2 -2
View File
@@ -48,7 +48,7 @@ export function UVEditor({ onClose, onSave, targetObject, loadedModel, sceneObje
const fileInputRef = useRef<HTMLInputElement>(null); const fileInputRef = useRef<HTMLInputElement>(null);
const dragRef = useRef<{ handle: Handle; startX: number; startY: number; layer: Layer } | null>(null); const dragRef = useRef<{ handle: Handle; startX: number; startY: number; layer: Layer } | null>(null);
const token = useAuthStore(state => state.token); const token = localStorage.getItem('auth_token') || '';
const [aiPrompt, setAiPrompt] = useState(""); const [aiPrompt, setAiPrompt] = useState("");
const [isEditingLayer, setIsEditingLayer] = useState(false); const [isEditingLayer, setIsEditingLayer] = useState(false);
const [aiPreviewUrl, setAiPreviewUrl] = useState<string | null>(null); const [aiPreviewUrl, setAiPreviewUrl] = useState<string | null>(null);
@@ -596,7 +596,7 @@ export function UVEditor({ onClose, onSave, targetObject, loadedModel, sceneObje
<span className="text-[10px] font-bold text-zinc-500 uppercase tracking-widest">3D Preview</span> <span className="text-[10px] font-bold text-zinc-500 uppercase tracking-widest">3D Preview</span>
</div> </div>
<div className="w-full aspect-square bg-zinc-950 rounded-xl overflow-hidden border border-zinc-800"> <div className="w-full aspect-square bg-zinc-950 rounded-xl overflow-hidden border border-zinc-800">
<Canvas shadows camera={{ position: [2, 2, 2], fov: 45 }}> <Canvas shadows={{ type: THREE.PCFShadowMap }} camera={{ position: [2, 2, 2], fov: 45 }}>
<ambientLight intensity={0.5} /> <ambientLight intensity={0.5} />
<directionalLight position={[5, 5, 5]} intensity={1} castShadow /> <directionalLight position={[5, 5, 5]} intensity={1} castShadow />
<Environment preset="studio" /> <Environment preset="studio" />
+1 -1
View File
@@ -2451,7 +2451,7 @@ export default function Editor() {
<div className="flex-1 relative bg-zinc-950"> <div className="flex-1 relative bg-zinc-950">
<ErrorBoundary> <ErrorBoundary>
<Canvas <Canvas
shadows shadows={{ type: THREE.PCFShadowMap }}
dpr={[1, 2]} dpr={[1, 2]}
gl={{ preserveDrawingBuffer: true, alpha: true }} gl={{ preserveDrawingBuffer: true, alpha: true }}
performance={{ min: 0.5 }} performance={{ min: 0.5 }}
+1 -1
View File
@@ -406,7 +406,7 @@ export default function SparkPlug() {
) : ( ) : (
<div className="w-full h-[400px] bg-zinc-900 rounded-xl overflow-hidden relative border border-zinc-800 flex flex-col items-center justify-center"> <div className="w-full h-[400px] bg-zinc-900 rounded-xl overflow-hidden relative border border-zinc-800 flex flex-col items-center justify-center">
{generatedGlbUrl ? ( {generatedGlbUrl ? (
<Canvas shadows dpr={[1, 2]} camera={{ position: [0, 0, 4], fov: 45 }}> <Canvas shadows={{ type: THREE.PCFShadowMap }} dpr={[1, 2]} camera={{ position: [0, 0, 4], fov: 45 }}>
<Suspense fallback={null}> <Suspense fallback={null}>
<Stage environment="studio" intensity={0.5}> <Stage environment="studio" intensity={0.5}>
<ModelPreview url={generatedGlbUrl} /> <ModelPreview url={generatedGlbUrl} />