66d1eb3e9f
- contracts: EmbedSlotSettings optional v2 fields (carousel default) + SlotSettingsPayload; gen + redocly green - api: DTO validation + normalization full-set (cn manage + ov public projection share normalizeStoredSettings) - embed-loader: params v2 parse/merge/url family, loader-v2.js fixed shell (border/radius/#10161E/safe-area, resize ignored, stack gap 12), dual-artifact build+sync; v1 source frozen - viewer: EmbedPage v=2 branch, EmbedStream (viewport/track/real anchors/collapse/empty), stream.ts pure fns, i18n zh/en - admin: types + utils (create default vertical-stream, clampScrollSpeed, v1/v2 snippet selection) - tests: loader 36 (+9 v2), viewer 222, admin 82, api unit 51, v1 embed e2e 20, v2 E01 gate 2 (195x280 desktop+mobile cross-origin, no footer) Co-Authored-By: Claude Code <noreply@anthropic.com>
2 lines
9.2 KiB
JavaScript
2 lines
9.2 KiB
JavaScript
(()=>{var k=["left","right"],H=["sm","md"],L=["auto","zh-CN","en"],R=["contain","cover"],s={position:"right",size:"md",intervalMs:5e3,lang:"auto",collapsedDefault:!1,imageFit:"contain",offsetX:16,offsetBottom:24,zIndex:1e3},X={sm:280,md:320},W=3e3,G=3e4,B=60,ce=640,Z=0,q=120,P=0,j=240,$=1,J=2147483e3,Q=["resize","collapse","expand","config","destroy"];function x(t,i,o){return t.indexOf(i)>=0?i:o}function g(t,i,o,f){let u=Number(t);return isNaN(u)||!isFinite(u)?f:Math.min(o,Math.max(i,Math.round(u)))}function c(t,i){let o=t[i];return o!=null&&o!==""}function ue(t){return g(t,W,G,s.intervalMs)}function Y(t,i){let o=t||{},f=typeof o.slot=="string"?o.slot.replace(/^\s+|\s+$/g,""):"",u=!!(i&&i.narrow);return{slot:f||null,lang:c(o,"lang")?x(L,o.lang,s.lang):s.lang,position:c(o,"position")?x(k,o.position,s.position):s.position,intervalMs:c(o,"interval")?ue(o.interval):s.intervalMs,size:u?"sm":c(o,"size")?x(H,o.size,s.size):s.size,collapsedDefault:s.collapsedDefault,imageFit:c(o,"imageFit")?x(R,o.imageFit,s.imageFit):s.imageFit,offsetX:c(o,"offsetX")?g(o.offsetX,Z,q,s.offsetX):s.offsetX,offsetBottom:c(o,"offsetBottom")?g(o.offsetBottom,P,j,s.offsetBottom):s.offsetBottom,zIndex:c(o,"zIndex")?g(o.zIndex,$,J,s.zIndex):s.zIndex,pollMs:c(o,"poll")?g(o.poll,250,6e4,null):null,narrow:u,explicit:{lang:c(o,"lang"),position:c(o,"position"),interval:c(o,"interval"),size:!u&&c(o,"size"),imageFit:c(o,"imageFit"),offsetX:c(o,"offsetX"),offsetBottom:c(o,"offsetBottom"),zIndex:c(o,"zIndex")}}}function K(t){return!t||typeof t!="object"?null:{position:x(k,t.position,s.position),size:x(H,t.size,s.size),intervalMs:g(t.intervalMs,W,G,s.intervalMs),lang:x(L,t.lang,s.lang),collapsedDefault:typeof t.collapsedDefault=="boolean"?t.collapsedDefault:s.collapsedDefault,imageFit:x(R,t.imageFit,s.imageFit),offsetX:g(t.offsetX,Z,q,s.offsetX),offsetBottom:g(t.offsetBottom,P,j,s.offsetBottom),zIndex:g(t.zIndex,$,J,s.zIndex)}}function ee(t,i){let o=K(i);if(o===null)return t;let f=t.explicit;return{slot:t.slot,lang:f.lang?t.lang:o.lang,position:f.position?t.position:o.position,intervalMs:f.interval?t.intervalMs:o.intervalMs,size:t.narrow?"sm":f.size?t.size:o.size,collapsedDefault:t.narrow?!0:o.collapsedDefault,imageFit:f.imageFit?t.imageFit:o.imageFit,offsetX:f.offsetX?t.offsetX:o.offsetX,offsetBottom:f.offsetBottom?t.offsetBottom:o.offsetBottom,zIndex:f.zIndex?t.zIndex:o.zIndex,pollMs:t.pollMs,narrow:t.narrow,explicit:f}}function te(t,i){if(!t||typeof t!="object")return null;let o=Number(t.configVersion);if(isNaN(o)||!isFinite(o))return null;let f=i==null?0:Number(i);if(o<=f)return null;let u=K(t.settings);return u===null?null:{configVersion:Math.round(o),settings:u}}function oe(t,i,o){let f=t+"/embed/"+encodeURIComponent(i)+"?lang="+encodeURIComponent(o.lang)+"&pos="+encodeURIComponent(o.position);return o.explicit.interval&&(f+="&interval="+String(o.intervalMs)),o.explicit.imageFit&&(f+="&fit="+encodeURIComponent(o.imageFit)),o.pollMs!==null&&o.pollMs!==void 0&&(f+="&poll="+String(o.pollMs)),f}function ne(t){if(t==null)return null;let i=Number(t);return isNaN(i)||!isFinite(i)?null:Math.min(ce,Math.max(B,Math.round(i)))}(function(){"use strict";try{let F=function(e){try{return t.sessionStorage.getItem(i+e)==="1"}catch(n){return!1}},N=function(e,n){try{n?t.sessionStorage.setItem(i+e,"1"):t.sessionStorage.removeItem(i+e)}catch(r){}},w=function(e){try{return t.sessionStorage.getItem(i+e)!==null}catch(n){return!1}},re=function(){if(document.currentScript&&document.currentScript.src)return document.currentScript;var e=document.querySelectorAll('script[src*="/embed/v1/loader.js"]');return e.length?e[e.length-1]:null},_=function(e){try{return new URL(e.src,t.location.href).origin}catch(n){return null}},le=function(e){var n=e==="zh-CN";if(!n&&e==="auto")try{n=/^zh/i.test(t.navigator.language||"")}catch(r){n=!1}return n?"\u5C55\u5F00\u7167\u7247\u8F6E\u64AD":"Show photo carousel"},ie=function(e){var n=e==="zh-CN";if(!n&&e==="auto")try{n=/^zh/i.test(t.navigator.language||"")}catch(r){n=!1}return n?"\u7167\u7247":"Photos"},ae=function(e){var n=document.createElement("div");n.setAttribute("role","button"),n.setAttribute("tabindex","0"),n.setAttribute("aria-label",le(e.config.lang));var r=n.style;r.position="fixed",r.height=u+"px",r.minWidth=u+"px",r.boxSizing="border-box",r.padding="0 14px",r.borderRadius=u/2+"px",r.background="rgba(15,23,42,0.88)",r.boxShadow="0 2px 10px rgba(0,0,0,0.3)",r.zIndex=String(e.config.zIndex),r.cursor="pointer",r.display="flex",r.alignItems="center",r.justifyContent="center",r.gap="6px",r.font='500 13px/1 system-ui, -apple-system, "Segoe UI", "PingFang SC", sans-serif',r.color="#ffffff",r.whiteSpace="nowrap",n.innerHTML='<svg viewBox="0 0 24 24" width="20" height="20" aria-hidden="true" focusable="false"><path fill="#ffffff" d="M9 2 7.17 4H4c-1.1 0-2 .9-2 2v12c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V6c0-1.1-.9-2-2-2h-3.17L15 2H9zm3 15c-2.76 0-5-2.24-5-5s2.24-5 5-5 5 2.24 5 5-2.24 5-5 5z"/></svg><span>'+ie(e.config.lang)+"</span>";function p(l){if(l.type==="keydown"){var a=l.key;if(a!=="Enter"&&a!==" "&&a!=="Spacebar")return;l.preventDefault()}e.userChoice=!0,E(e);try{e.frame.contentWindow&&e.frame.contentWindow.postMessage({photoliveEmbed:!0,type:"expand"},e.frameOrigin)}catch(d){}}return n.addEventListener("click",p),n.addEventListener("keydown",p),n},se=function(e){return e.collapsed?u:e.height},z=function(e){var n=e.config.position==="left"?"left":"right",r=n==="left"?"right":"left",p=e.narrow?"sm":e.config.size,l=X[p]||X.md,a=t.innerWidth-e.config.offsetX-8;a<C&&(a=C),l>a&&(l=a);var d=e.wrapper.style;if(d.width=l+"px",d.zIndex=String(e.config.zIndex),d[n]=e.config.offsetX+"px",d[r]="",e.handle){var m=e.handle.style;m.zIndex=String(e.config.zIndex),m[n]=e.config.offsetX+"px",m[r]=""}},T=function(){for(var e={left:[],right:[]},n=0;n<h.length;n++){var r=h[n];e[r.config.position==="left"?"left":"right"].push(r)}for(var p=["left","right"],l=0;l<p.length;l++)for(var a=e[p[l]],d=0,m=0;m<a.length;m++){var I=a[m],y=m===0?I.config.offsetBottom:d+se(a[m-1])+f;m>0&&y+B>t.innerHeight&&A(I,!1),I.wrapper.style.bottom=y+"px",I.handle&&(I.handle.style.bottom=y+"px"),d=y}},v=function(){if(S!==null||typeof t.requestAnimationFrame!="function"){T();return}S=t.requestAnimationFrame(function(){S=null,T()})},A=function(e,n){e.collapsed||(e.collapsed=!0,e.wrapper.style.height="0px",e.wrapper.style.boxShadow="none",e.handle||(e.handle=ae(e),document.body.appendChild(e.handle),z(e)),e.handle.style.display="flex",n!==!1&&N(e.config.slot,!0))},b=function(e,n){A(e,n),v()},E=function(e){e.collapsed&&(e.collapsed=!1,e.wrapper.style.height=e.height+"px",e.wrapper.style.boxShadow="0 4px 16px rgba(0,0,0,0.18)",e.handle&&(e.handle.style.display="none"),N(e.config.slot,!1),v())},fe=function(e){if(!e.destroyed){e.destroyed=!0,e.handle&&e.handle.parentNode&&e.handle.parentNode.removeChild(e.handle),e.wrapper.parentNode&&e.wrapper.parentNode.removeChild(e.wrapper);try{t.sessionStorage.removeItem(i+e.config.slot)}catch(r){}var n=h.indexOf(e);n>=0&&h.splice(n,1),delete M[e.config.slot],h.length===0&&t.removeEventListener("message",V),v()}},pe=function(e,n,r){e.backendVersion=n,e.config=ee(e.config,r),z(e),!e.userChoice&&!w(e.config.slot)&&(e.config.collapsedDefault?b(e,!1):e.narrow||E(e)),v()},de=function(e,n){var r=document.createElement("div"),p=r.style;p.position="fixed",p.bottom=n.offsetBottom+"px",p.height=o+"px",p.borderRadius="12px",p.boxShadow="0 4px 16px rgba(0,0,0,0.18)",p.overflow="hidden";var l=document.createElement("iframe");l.setAttribute("sandbox","allow-scripts allow-popups allow-popups-to-escape-sandbox allow-same-origin"),l.setAttribute("src",oe(e,n.slot,n)),l.setAttribute("referrerpolicy","no-referrer-when-downgrade"),l.setAttribute("title","PhotoLive photos");var a=l.style;a.width="100%",a.height="100%",a.border="0",a.display="block",r.appendChild(l),document.body.appendChild(r);var d={config:n,wrapper:r,frame:l,frameOrigin:_(l)||e,height:o,collapsed:!1,narrow:n.narrow,handle:null,userChoice:!1,backendVersion:0,destroyed:!1};return h.push(d),z(d),w(n.slot)?F(n.slot)&&b(d,!1):d.narrow&&b(d,!1),d},V=function(e){try{var n=e.data;if(!n||n.photoliveEmbed!==!0)return;var r=n.type;if(Q.indexOf(r)<0)return;for(var p=0;p<h.length;p++){var l=h[p];if(!(!l.frame.contentWindow||e.source!==l.frame.contentWindow)){if(e.origin!==l.frameOrigin)return;if(r==="resize"){var a=ne(n.height);a!==null&&(l.height=a,l.collapsed||(l.wrapper.style.height=a+"px"),v())}else if(r==="collapse")l.userChoice=!0,b(l,!0);else if(r==="expand")l.userChoice=!0,E(l);else if(r==="config"){var d=te(n,l.backendVersion);d!==null&&pe(l,d.configVersion,d.settings)}else fe(l);return}}}catch(m){}},D=function(){try{return!!t.matchMedia&&t.matchMedia("(max-width: 479px)").matches}catch(e){return!1}},O=function(){for(var e=D(),n=0;n<h.length;n++){var r=h[n];r.narrow!==e&&(r.narrow=e,e&&!r.userChoice&&!w(r.config.slot)&&b(r,!1)),z(r)}v()},U=function(){var e=re();if(e){var n=_(e);if(n){for(var r=D(),p=document.querySelectorAll('script[src*="/embed/v1/loader.js"]'),l=0;l<p.length;l++){var a=Y(p[l].dataset,{narrow:r});a.slot&&(M[a.slot]||(M[a.slot]=!0,de(n,a)))}t.addEventListener("message",V),t.addEventListener("resize",O),t.addEventListener("orientationchange",O)}}};var t=window;if(t.__photoliveEmbedV1)return;t.__photoliveEmbedV1="1";var i="pl-embed-collapsed:",o=96,f=8,u=44,C=180,h=[],M={},S=null;document.body?U():document.addEventListener("DOMContentLoaded",U)}catch(F){}})();})();
|