PageSourceSearch

https://www.jacksu.tw/_next/static/chunks/pages/tool/image/photo-enhance-82efc2882e540bf1.js

js jacksu.tw collected 2026-10-02 02:10:28 UTC 12,901 bytes, 1 lines download raw bytes

1(self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[5301],{51286:function(e,t,n){(window.__NEXT_P=window.__NEXT_P||[]).push(["/tool/image/photo-enhance",function(){return n(73323)}])},73323:function(e,t,n){"use strict";n.r(t),n.d(t,{__toc:function(){return C},default:function(){return P}});var r=n(85893),a=n(4882),l=n(82643),i=n(67294),s=n(23302),c=n(3420),o=n(89508),u=n(95059),d=n(50791),m=n(24355),h=n(7329),x=n(30618),f=n(27560),p=n(6139),g=n(88976),j=n(43766),v=n(44204),b=n(2466),w=n(59142);function y(e){let{originalSrc:t,enhancedSrc:n}=e,[a,l]=(0,i.useState)(50),s=(0,i.useRef)(null),c=(0,i.useRef)(!1),o=(0,i.useRef)(50),u=(0,i.useRef)(null);function d(e){var t;let n=null===(t=s.current)||void 0===t?void 0:t.getBoundingClientRect();if(!n)return;let r=Math.max(0,Math.min(e-n.left,n.width));o.current=r/n.width*100,null===u.current&&(u.current=window.requestAnimationFrame(()=>{u.current=null,l(o.current)}))}return(0,i.useEffect)(()=>()=>{null!==u.current&&window.cancelAnimationFrame(u.current)},[]),(0,r.jsx)("div",{className:"h-full",children:(0,r.jsxs)("div",{ref:s,className:"h-full select-none overflow-hidden bg-gray-100 dark:bg-gray-800 relative",children:[(0,r.jsx)("img",{src:n,alt:"Enhanced",className:"absolute inset-0 w-full h-full object-contain !m-0 !rounded-none",draggable:!1}),(0,r.jsx)("div",{className:"absolute inset-0",style:{clipPath:"inset(0 ".concat(100-a,"% 0 0)")},children:(0,r.jsx)("img",{src:t,alt:"Original",className:"w-full h-full object-contain !m-0 !rounded-none",draggable:!1})}),(0,r.jsx)("div",{className:"absolute top-3 left-3 pointer-events-none ".concat((0,w.AM)({tone:"neutral",size:"sm"})),children:"原始"}),(0,r.jsx)("div",{className:"absolute top-3 right-3 pointer-events-none ".concat((0,w.AM)({tone:"neutral",size:"sm"})),children:"增強後"}),(0,r.jsxs)("div",{className:"absolute top-0 bottom-0 w-8 -ml-4 cursor-col-resize touch-none z-10",style:{left:"".concat(a,"%")},onPointerDown:function(e){c.current=!0,e.currentTarget.setPointerCapture(e.pointerId),d(e.clientX)},onPointerMove:function(e){c.current&&d(e.clientX)},onPointerUp:function(){c.current=!1},children:[(0,r.jsx)("div",{className:"absolute top-0 bottom-0 left-1/2 -translate-x-1/2 w-0.5 bg-white dark:bg-white"}),(0,r.jsxs)("div",{className:"absolute bottom-4 left-1/2 -translate-x-1/2 flex items-center gap-0.5 px-1.5 py-1 rounded-full bg-white text-gray-700 dark:bg-white dark:text-gray-700",children:[(0,r.jsx)(v.Z,{size:12,strokeWidth:2.5}),(0,r.jsx)(b.Z,{size:12,strokeWidth:2.5})]})]})]})})}var N=n(16641),R=n(75035);let k=[2,4].map(e=>({value:e,label:"".concat(e,"x")})),L={photo:"一般照片",portrait:"人像",landscape:"風景",night:"夜景",document:"文件",icon:"圖示 / 插畫"},E={opacity:0},S={duration:.2},z={duration:.3},D={opacity:1,y:0},U={duration:.35},O={duration:.3,ease:"easeOut"};function Z(e){return e||0===e?e<1024?"".concat(e," B"):e<1048576?"".concat((e/1024).toFixed(1)," KB"):"".concat((e/1024/1024).toFixed(2)," MB"):""}let _=(0,i.memo)(function(){let[e,t]=(0,i.useState)(null),{prepareImage:n,cancelPreview:a}=(0,u.Z)(),l=(0,s.J)(),[v,b]=(0,i.useState)(2),[w,_]=(0,i.useState)(!1),[C,M]=(0,i.useState)(""),[P,A]=(0,i.useState)(null),[T,F]=(0,i.useState)(null),[B,W]=(0,i.useState)(null),[X,I]=(0,i.useState)(0),[q,G]=(0,i.useState)(!1),[H,V]=(0,i.useState)(null),J=(0,i.useRef)(0),K=(0,i.useRef)(null),$=(0,i.useRef)(null),Q=(0,i.useRef)(null),Y=(0,i.useRef)(null),ee=(0,i.useRef)(0),et=(0,i.useRef)(!0),en=(0,i.useRef)(null),er=(0,i.useRef)(null),ea=(0,i.useRef)(null),el=(0,i.useRef)({p:-1,m:""});function ei(){var e;a(),ee.current+=1,null===(e=Q.current)||void 0===e||e.call(Q),Q.current=null,null!==Y.current&&(clearTimeout(Y.current),Y.current=null);let t=K.current,n=$.current;K.current=null,$.current=null,null==t||t.abort(),n&&(0,R.Ce)(n)}async function es(e){if(ei(),!e)return;let r=await n(e);r&&(_(!1),P&&URL.revokeObjectURL(P),T&&URL.revokeObjectURL(T),t(e),F(null),V(null),W(null),er.current=r,A(r),en.current=null)}async function ec(){if(!e)return;ei();let t=ee.current+1;ee.current=t,_(!0),W(null),M("正在上傳圖片..."),I(0),el.current={p:0,m:"正在上傳圖片..."};let n=(0,R.WE)();$.current=n;let r=new AbortController;K.current=r;let a=!1,l=()=>et.current&&ee.current===t&&K.current===r,i=(0,R.qr)(n,e=>{let{p:t,m:n}=e;if(!l())return;let r=el.current;
1(r.p!==t||r.m!==n)&&(el.current={p:t,m:n},I(t),M(n))},500,{signal:r.signal});Q.current=i,Y.current=setTimeout(()=>{l()&&(a=!0,r.abort(),(0,R.Ce)(n))},3e5);try{let t,a;let i=new FormData;i.append("image",e),i.append("scale",String(v)),i.append("job_id",n);let s=await fetch("/api/photo-enhance",{method:"POST",body:i,signal:r.signal});if(!l())return;if(!s.ok){let e=await s.json().catch(()=>({}));throw Error(e.error||"增強失敗,請重試")}let c=s.headers.get("x-detected-profile")||"photo",o=await s.blob();if(!l())return;let u=URL.createObjectURL(o);try{[t,a]=await Promise.all([new Promise(e=>{if(!P){e(null);return}let t=new Image;t.onload=()=>e({w:t.naturalWidth,h:t.naturalHeight}),t.onerror=()=>e(null),t.src=P}),(0,h.Z)(u)])}catch(e){throw URL.revokeObjectURL(u),e}if(!l()){URL.revokeObjectURL(u);return}en.current=o,ea.current=u,I(100),F(u),M(""),V({origSize:e.size,origDim:t,outSize:o.size,outDim:a,profile:c,scale:v})}catch(e){if(!l())return;if("AbortError"===e.name){(0,R.Ce)(n),a&&(I(0),W("增強失敗,請重試"),M(""));return}I(0),W(e.message),M("")}finally{l()&&(i(),Q.current=null,null!==Y.current&&(clearTimeout(Y.current),Y.current=null),_(!1),K.current=null,$.current=null)}}function eo(){ei(),_(!1),P&&URL.revokeObjectURL(P),T&&URL.revokeObjectURL(T),t(null),A(null),F(null),V(null),W(null),M(""),b(2),en.current=null}return(0,i.useEffect)(()=>{er.current=P},[P]),(0,i.useEffect)(()=>{ea.current=T},[T]),(0,i.useEffect)(()=>(et.current=!0,()=>{et.current=!1,ei(),er.current&&URL.revokeObjectURL(er.current),ea.current&&URL.revokeObjectURL(ea.current)}),[]),(0,r.jsxs)(c.E.div,{className:"mt-10 flex flex-col h-[calc(100svh-260px)] sm:h-[calc(100svh-280px)] min-[1800px]:h-[calc(100svh-240px)]",initial:!1,animate:D,transition:U,onDragOver:e?void 0:function(e){e.preventDefault()},onDragEnter:e?void 0:function(e){e.preventDefault(),J.current+=1,G(!0)},onDragLeave:e?void 0:function(){J.current-=1,0===J.current&&G(!1)},onDrop:e?void 0:function(e){if(J.current=0,G(!1),e.defaultPrevented)return;e.preventDefault();let t=e.dataTransfer.files[0];if(t&&t.type.startsWith("image/")){if(t.size>52428800){W("檔案大小不能超過 ".concat(50,"MB(目前 ").concat((t.size/1024/1024).toFixed(1),"MB)"));return}W(null),es(t)}},children:[!e&&(0,r.jsx)("div",{className:"flex-1 flex items-center justify-center",children:(0,r.jsxs)("div",{className:"w-full max-w-md 
1space-y-5",children:[(0,r.jsx)(j.Z,{onImageSelect:es,disabled:w,isDraggingExternal:q,onError:W,maxSize:50}),B&&(0,r.jsx)("p",{className:"text-sm text-red-500 text-center",children:B}),(0,r.jsxs)("div",{className:"flex items-center justify-between",children:[(0,r.jsx)("span",{className:"text-[13px] text-gray-600 dark:text-gray-400",children:"放大倍數"}),(0,r.jsx)(N.ZP,{items:k,activeValue:v,onChange:b,size:"sm",className:"!mb-0"})]})]})}),e&&(0,r.jsx)(o.M,{mode:"wait",children:(0,r.jsxs)(c.E.div,{className:"flex-1 flex flex-col min-h-0",initial:!l&&{opacity:1,y:6},animate:{opacity:1,y:0},exit:E,transition:S,children:[(0,r.jsxs)("div",{className:"flex-1 min-h-0 relative w-screen left-1/2 -translate-x-1/2 sm:w-auto sm:left-auto sm:translate-x-0 overflow-hidden bg-gray-100 dark:bg-gray-800",children:[(0,r.jsx)("img",{src:P,alt:"Preview",className:"w-full h-full object-contain !m-0 !rounded-none"}),T&&(0,r.jsx)(c.E.div,{className:"absolute inset-0",initial:{opacity:0},animate:{opacity:1},transition:l?{duration:0}:z,children:(0,r.jsx)(y,{originalSrc:P,enhancedSrc:T})}),(0,r.jsxs)(d.Z,{active:w,children:[(0,r.jsx)(x.Z,{size:28,className:"animate-spin text-white"}),(0,r.jsxs)("div",{className:"flex flex-col items-center gap-2 w-48",children:[(0,r.jsx)("span",{className:"text-sm text-white/90 font-medium",children:C}),(0,r.jsx)("div",{className:"w-full h-1.5 bg-white/20 rounded-full overflow-hidden",children:(0,r.jsx)(c.E.div,{className:"h-full bg-white rounded-full",initial:{width:0},animate:{width:"".concat(X,"%")},transition:O})}),(0,r.jsxs)("span",{className:"text-xs text-white/60",children:[X,"%"]})]})]})]}),H&&(0,r.jsx)(c.E.div,{initial:{height:0},animate:{height:"auto"},transition:l?{duration:0}:z,className:"shrink-0 overflow-hidden",children:(0,r.jsxs)("div",{className:"flex flex-wrap items-center justify-center gap-x-4 gap-y-1 text-xs text-gray-500 pt-3",children:[H.origDim&&H.outDim&&(0,r.jsxs)("span",{children:[(0,r.jsx)("span",{className:"text-gray-400",children:"尺寸"})," ",H.origDim.w,"\xd7",H.origDim.h," → ",H.outDim.w,"\xd7",H.outDim.h]}),(0,r.jsxs)("span",{children:[(0,r.jsx)("span",{className:"text-gray-400",children:"檔案"})," ",Z(H.origSize)," → ",Z(H.outSize)]}),(0,r.jsxs)("span",{children:[(0,r.jsx)("span",{className:"text-gray-400",children:"自動判斷"})," ",L[H.profile]||H.profile," \xb7 ",H.scale,"x"]})]})}),T?(0,r.jsxs)("div",{className:"flex items-center justify-between pt-4",children:[(0,r.jsxs)("button",{onClick:eo,className:"inline-flex items-center gap-1.5 px-3 py-1.5 text-sm font-medium rounded-md bg-white text-gray-600 transition-colors hover:bg-gray-100 hover:text-gray-900",children:[(0,r.jsx)(f.Z,{size:14}),(0,r.jsx)("span",{className:"sm:hidden",children:"重選"}),(0,r.jsx)("span",{className:"hidden sm:inline",children:"重新上傳"})]}),(0,r.jsxs)("button",{onClick:function(){if(!T)return;let t=document.createElement("a");t.href=T;let n=((null==e?void 0:e.name)||"image").replace(/\.[^.]+$/,"");t.download="".concat(n,"_enhanced_").concat(v,"x.png"),t.click()},className:"inline-flex items-center gap-1.5 px-3 py-1.5 text-sm font-medium rounded-md bg-gray-600 text-white transition-colors hover:bg-gray-700",children:[(0,r.jsx)(p.Z,{size:14}),(0,r.jsx)("span",{className:"sm:hidden",children:"下載"}),(0,r.jsx)("span",{className:"hidden sm:inline",children:"下載圖片"})]})]}):(0,r.jsxs)("div",{className:"grid grid-cols-3 items-center pt-4",children:[(0,r.jsx)("div",{className:"flex justify-start",children:(0,r.jsxs)("button",{onClick:eo,disabled:w,className:"inline-flex items-center gap-1.5 px-3 py-1.5 text-sm font-medium rounded-md bg-white text-gray-600 transition-[color,background-color,opacity] duration-150 hover:bg-gray-100 hover:text-gray-900 disabled:opacity-40",children:[(0,r.jsx)(f.Z,{size:14}),"重選"]})}),(0,r.jsx)("div",{className:"flex justify-center",children:(0,r.jsx)(N.ZP,{items:k,activeValue:v,onChange:b,disabled:w,loading:w,size:"sm",className:"!mb-0"})}),(0,r.jsx)("div",{className:"flex justify-end",children:(0,r.jsx)("button",{onClick:ec,disabled:w,className:"inline-flex items-center gap-1.5 px-3 py-1.5 text-sm font-medium rounded-md bg-gray-600 text-white transition-[color,background-color,opacity] duration-150 hover:bg-gray-700 disabled:opacity-60",children:(0,r.jsx)(m.Z,{active:w,icon:(0,r.jsx)(g.Z,{size:14}),idleLabel:"開始增強",mobileIdleLabel:"增強",processingLabel:"處理中...",mobileProcessingLabel:"處理"})})})]}),B&&(0,r.jsx)("p",{className:"text-sm text-red-500 mt-2",children:B})]},"preview")})]})}),C=[];function M(e){let t=Object.assign({h1:"h1"},(0,l.a)(),e.components);return(0,r.jsxs)(r.Fragment,{children:[(0,r.jsx)(t.h1,{children:"圖片畫質增強"}),"\n",(0,r.jsx)(_,{})]})}var P=(0,a.j)({MDXContent:function(){let e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{},{wrapper:t}=Object.assign({},(0,l.a)(),e.components);return t?(0,r.jsx)(t,{...e,children:(0,r.jsx)(M,{...e})}):M(e)},pageOpts:{filePath:"pages/tool/image/photo-enhance.mdx",route:"/tool/image/photo-enhance",frontMatter:{title:"圖片畫質增強 | Real-ESRGAN 超解析度放大",description:"使用 Real-ESRGAN 超解析度技術放大照片並增強畫質,讓低解析
1度圖片重現清晰細節。"},timestamp:1790614476e3,title:"圖片畫質增強 | Real-ESRGAN 超解析度放大",headings:C},pageNextRoute:"/tool/image/photo-enhance"})},44204:function(e,t,n){"use strict";n.d(t,{Z:function(){return r}});let r=(0,n(51692).Z)("ChevronLeft",[["path",{d:"m15 18-6-6 6-6",key:"1wnfg3"}]])},88976:function(e,t,n){"use strict";n.d(t,{Z:function(){return r}});let r=(0,n(51692).Z)("Sparkles",[["path",{d:"M9.937 15.5A2 2 0 0 0 8.5 14.063l-6.135-1.582a.5.5 0 0 1 0-.962L8.5 9.936A2 2 0 0 0 9.937 8.5l1.582-6.135a.5.5 0 0 1 .963 0L14.063 8.5A2 2 0 0 0 15.5 9.937l6.135 1.581a.5.5 0 0 1 0 .964L15.5 14.063a2 2 0 0 0-1.437 1.437l-1.582 6.135a.5.5 0 0 1-.963 0z",key:"4pj2yx"}],["path",{d:"M20 3v4",key:"1olli1"}],["path",{d:"M22 5h-4",key:"1gvqau"}],["path",{d:"M4 17v2",key:"vumght"}],["path",{d:"M5 18H3",key:"zchphs"}]])}},function(e){e.O(0,[4882,2940,2888,9774,179],function(){return e(e.s=51286)}),_N_E=e.O()}]);

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.