import ClockRange from"../../Core/ClockRange.js";import defined from"../../Core/defined.js";import destroyObject from"../../Core/destroyObject.js";import DeveloperError from"../../Core/DeveloperError.js";import JulianDate from"../../Core/JulianDate.js";import getElement from"../getElement.js";import TimelineHighlightRange from"./TimelineHighlightRange.js";import TimelineTrack from"./TimelineTrack.js";let timelineWheelDelta=1e12;const timelineMouseMode={none:0,scrub:1,slide:2,zoom:3,touchOnly:4},timelineTouchMode={none:0,scrub:1,slideZoom:2,singleTap:3,ignore:4},timelineTicScales=[.001,.002,.005,.01,.02,.05,.1,.25,.5,1,2,5,10,15,30,60,120,300,600,900,1800,3600,7200,14400,21600,43200,86400,172800,345600,604800,1296e3,2592e3,5184e3,7776e3,15552e3,31536e3,63072e3,126144e3,15768e4,31536e4,63072e4,126144e4,15768e5,31536e5,63072e5,126144e5,15768e6,31536e6],timelineMonthNames=["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"];function Timeline(e,t){if(!defined(e))throw new DeveloperError("container is required.");if(!defined(t))throw new DeveloperError("clock is required.");e=getElement(e);const i=e.ownerDocument;this.container=e;const n=i.createElement("div");n.className="cesium-timeline-main",e.appendChild(n),this._topDiv=n,this._endJulian=void 0,this._epochJulian=void 0,this._lastXPos=void 0,this._scrubElement=void 0,this._startJulian=void 0,this._timeBarSecondsSpan=void 0,this._clock=t,this._scrubJulian=t.currentTime,this._mainTicSpan=-1,this._mouseMode=timelineMouseMode.none,this._touchMode=timelineTouchMode.none,this._touchState={centerX:0,spanX:0},this._mouseX=0,this._timelineDrag=0,this._timelineDragLocation=void 0,this._lastHeight=void 0,this._lastWidth=void 0,this._topDiv.innerHTML='
',this._timeBarEle=this._topDiv.childNodes[0],this._trackContainer=this._topDiv.childNodes[1],this._trackListEle=this._topDiv.childNodes[1].childNodes[0],this._needleEle=this._topDiv.childNodes[2],this._rulerEle=this._topDiv.childNodes[3],this._context=this._trackListEle.getContext("2d"),this._trackList=[],this._highlightRanges=[],this.zoomTo(t.startTime,t.stopTime),this._onMouseDown=createMouseDownCallback(this),this._onMouseUp=createMouseUpCallback(this),this._onMouseMove=createMouseMoveCallback(this),this._onMouseWheel=createMouseWheelCallback(this),this._onTouchStart=createTouchStartCallback(this),this._onTouchMove=createTouchMoveCallback(this),this._onTouchEnd=createTouchEndCallback(this);const o=this._timeBarEle;i.addEventListener("mouseup",this._onMouseUp,!1),i.addEventListener("mousemove",this._onMouseMove,!1),o.addEventListener("mousedown",this._onMouseDown,!1),o.addEventListener("DOMMouseScroll",this._onMouseWheel,!1),o.addEventListener("mousewheel",this._onMouseWheel,!1),o.addEventListener("touchstart",this._onTouchStart,!1),o.addEventListener("touchmove",this._onTouchMove,!1),o.addEventListener("touchend",this._onTouchEnd,!1),o.addEventListener("touchcancel",this._onTouchEnd,!1),this._topDiv.oncontextmenu=function(){return!1},t.onTick.addEventListener(this.updateFromClock,this),this.updateFromClock()}function twoDigits(e){return e<10?`0${e.toString()}`:e.toString()}function createMouseDownCallback(e){return function(t){e._mouseMode!==timelineMouseMode.touchOnly&&(0===t.button?(e._mouseMode=timelineMouseMode.scrub,e._scrubElement&&(e._scrubElement.style.backgroundPosition="-16px 0"),e._onMouseMove(t)):(e._mouseX=t.clientX,2===t.button?e._mouseMode=timelineMouseMode.zoom:e._mouseMode=timelineMouseMode.slide)),t.preventDefault()}}function createMouseUpCallback(e){return function(t){e._mouseMode=timelineMouseMode.none,e._scrubElement&&(e._scrubElement.style.backgroundPosition="0 0"),e._timelineDrag=0,e._timelineDragLocation=void 0}}function createMouseMoveCallback(e){return function(t){let i;if(e._mouseMode===timelineMouseMode.scrub){t.preventDefault();const i=t.clientX-e._topDiv.getBoundingClientRect().left;i<0?(e._timelineDragLocation=0,e._timelineDrag=-.01*e._timeBarSecondsSpan):i>e._topDiv.clientWidth?(e._timelineDragLocation=e._topDiv.clientWidth,e._timelineDrag=.01*e._timeBarSecondsSpan):(e._timelineDragLocation=void 0,e._setTimeBarTime(i,i*e._timeBarSecondsSpan/e._topDiv.clientWidth))}else if(e._mouseMode===timelineMouseMode.slide){if(i=e._mouseX-t.clientX,e._mouseX=t.clientX,0!==i){const t=i*e._timeBarSecondsSpan/e._topDiv.clientWidth;e.zoomTo(JulianDate.addSeconds(e._startJulian,t,new JulianDate),JulianDate.addSeconds(e._endJulian,t,new JulianDate))}}else e._mouseMode===timelineMouseMode.zoom&&(i=e._mouseX-t.clientX,e._mouseX=t.clientX,0!==i&&e.zoomFrom(Math.pow(1.01,i)))}}function createMouseWheelCallback(e){return function(t){let i=t.wheelDeltaY||t.wheelDelta||-t.detail;timelineWheelDelta=Math.max(Math.min(Math.abs(i),timelineWheelDelta),1),i/=timelineWheelDelta,e.zoomFrom(Math.pow(1.05,-i))}}function createTouchStartCallback(e){return function(t){const i=t.touches.length;let n,o;const s=e._topDiv.getBoundingClientRect().left;t.preventDefault(),e._mouseMode=timelineMouseMode.touchOnly,1===i?(n=JulianDate.secondsDifference(e._scrubJulian,e._startJulian),o=Math.round(n*e._topDiv.clientWidth/e._timeBarSecondsSpan+s),Math.abs(t.touches[0].clientX-o)<50?(e._touchMode=timelineTouchMode.scrub,e._scrubElement&&(e._scrubElement.style.backgroundPosition=1===i?"-16px 0":"0 0")):(e._touchMode=timelineTouchMode.singleTap,e._touchState.centerX=t.touches[0].clientX-s)):2===i?(e._touchMode=timelineTouchMode.slideZoom,e._touchState.centerX=.5*(t.touches[0].clientX+t.touches[1].clientX)-s,e._touchState.spanX=Math.abs(t.touches[0].clientX-t.touches[1].clientX)):e._touchMode=timelineTouchMode.ignore}}function createTouchEndCallback(e){return function(t){const i=t.touches.length,n=e._topDiv.getBoundingClientRect().left;e._touchMode===timelineTouchMode.singleTap?(e._touchMode=timelineTouchMode.scrub,e._onTouchMove(t)):e._touchMode===timelineTouchMode.scrub&&e._onTouchMove(t),e._mouseMode=timelineMouseMode.touchOnly,1!==i?e._touchMode=i>0?timelineTouchMode.ignore:timelineTouchMode.none:e._touchMode===timelineTouchMode.slideZoom&&(e._touchState.centerX=t.touches[0].clientX-n),e._scrubElement&&(e._scrubElement.style.backgroundPosition="0 0")}}function createTouchMoveCallback(e){return function(t){let i,n,o,s,a,l,c=1;const h=e._topDiv.getBoundingClientRect().left;e._touchMode===timelineTouchMode.singleTap&&(e._touchMode=timelineTouchMode.slideZoom),e._mouseMode=timelineMouseMode.touchOnly,e._touchMode===timelineTouchMode.scrub?(t.preventDefault(),1===t.changedTouches.length&&(n=t.changedTouches[0].clientX-h,n>=0&&n<=e._topDiv.clientWidth&&e._setTimeBarTime(n,n*e._timeBarSecondsSpan/e._topDiv.clientWidth))):e._touchMode===timelineTouchMode.slideZoom&&(o=t.touches.length,2===o?(s=.5*(t.touches[0].clientX+t.touches[1].clientX)-h,a=Math.abs(t.touches[0].clientX-t.touches[1].clientX)):1===o&&(s=t.touches[0].clientX-h,a=0),defined(s)&&(a>0&&e._touchState.spanX>0?(c=e._touchState.spanX/a,l=JulianDate.addSeconds(e._startJulian,(e._touchState.centerX*e._timeBarSecondsSpan-s*e._timeBarSecondsSpan*c)/e._topDiv.clientWidth,new JulianDate)):(i=e._touchState.centerX-s,l=JulianDate.addSeconds(e._startJulian,i*e._timeBarSecondsSpan/e._topDiv.clientWidth,new JulianDate)),e.zoomTo(l,JulianDate.addSeconds(l,e._timeBarSecondsSpan*c,new JulianDate)),e._touchState.centerX=s,e._touchState.spanX=a))}}Timeline.prototype.addEventListener=function(e,t,i){this._topDiv.addEventListener(e,t,i)},Timeline.prototype.removeEventListener=function(e,t,i){this._topDiv.removeEventListener(e,t,i)},Timeline.prototype.isDestroyed=function(){return!1},Timeline.prototype.destroy=function(){this._clock.onTick.removeEventListener(this.updateFromClock,this);const e=this.container.ownerDocument;e.removeEventListener("mouseup",this._onMouseUp,!1),e.removeEventListener("mousemove",this._onMouseMove,!1);const t=this._timeBarEle;t.removeEventListener("mousedown",this._onMouseDown,!1),t.removeEventListener("DOMMouseScroll",this._onMouseWheel,!1),t.removeEventListener("mousewheel",this._onMouseWheel,!1),t.removeEventListener("touchstart",this._onTouchStart,!1),t.removeEventListener("touchmove",this._onTouchMove,!1),t.removeEventListener("touchend",this._onTouchEnd,!1),t.removeEventListener("touchcancel",this._onTouchEnd,!1),this.container.removeChild(this._topDiv),destroyObject(this)},Timeline.prototype.addHighlightRange=function(e,t,i){const n=new TimelineHighlightRange(e,t,i);return this._highlightRanges.push(n),this.resize(),n},Timeline.prototype.addTrack=function(e,t,i,n){const o=new TimelineTrack(e,t,i,n);return this._trackList.push(o),this._lastHeight=void 0,this.resize(),o},Timeline.prototype.zoomTo=function(e,t){if(!defined(e))throw new DeveloperError("startTime is required.");if(!defined(t))throw new DeveloperError("stopTime is required");if(JulianDate.lessThanOrEquals(t,e))throw new DeveloperError("Start time must come before end time.");if(this._startJulian=e,this._endJulian=t,this._timeBarSecondsSpan=JulianDate.secondsDifference(t,e),this._clock&&this._clock.clockRange!==ClockRange.UNBOUNDED){const e=this._clock.startTime,t=this._clock.stopTime,i=JulianDate.secondsDifference(t,e),n=JulianDate.secondsDifference(e,this._startJulian),o=JulianDate.secondsDifference(t,this._endJulian);this._timeBarSecondsSpan>=i?(this._timeBarSecondsSpan=i,this._startJulian=this._clock.startTime,this._endJulian=this._clock.stopTime):n>0?(this._endJulian=JulianDate.addSeconds(this._endJulian,n,new JulianDate),this._startJulian=e,this._timeBarSecondsSpan=JulianDate.secondsDifference(this._endJulian,this._startJulian)):o<0&&(this._startJulian=JulianDate.addSeconds(this._startJulian,o,new JulianDate),this._endJulian=t,this._timeBarSecondsSpan=JulianDate.secondsDifference(this._endJulian,this._startJulian))}this._makeTics();const i=document.createEvent("Event");i.initEvent("setzoom",!0,!0),i.startJulian=this._startJulian,i.endJulian=this._endJulian,i.epochJulian=this._epochJulian,i.totalSpan=this._timeBarSecondsSpan,i.mainTicSpan=this._mainTicSpan,this._topDiv.dispatchEvent(i)},Timeline.prototype.zoomFrom=function(e){let t=JulianDate.secondsDifference(this._scrubJulian,this._startJulian);e>1||t<0||t>this._timeBarSecondsSpan?t=.5*this._timeBarSecondsSpan:t+=t-.5*this._timeBarSecondsSpan;const i=this._timeBarSecondsSpan-t;this.zoomTo(JulianDate.addSeconds(this._startJulian,t-t*e,new JulianDate),JulianDate.addSeconds(this._endJulian,i*e-i,new JulianDate))},Timeline.prototype.makeLabel=function(e){const t=JulianDate.toGregorianDate(e),i=t.millisecond;let n=" UTC";if(i>0&&this._timeBarSecondsSpan<3600){n=Math.floor(i).toString();while(n.length<3)n=`0${n}`;n=`.${n}`}return`${timelineMonthNames[t.month-1]} ${t.day} ${t.year} ${twoDigits(t.hour)}:${twoDigits(t.minute)}:${twoDigits(t.second)}${n}`},Timeline.prototype.smallestTicInPixels=7,Timeline.prototype._makeTics=function(){const e=this._timeBarEle,t=JulianDate.secondsDifference(this._scrubJulian,this._startJulian),i=Math.round(t*this._topDiv.clientWidth/this._timeBarSecondsSpan),n=i-8;let o;const s=this;this._needleEle.style.left=`${i.toString()}px`;let a="";const l=.01,c=31536e6,h=1e-10;let r=0,u=this._timeBarSecondsSpan;uc&&(u=c,this._timeBarSecondsSpan=c,this._endJulian=JulianDate.addSeconds(this._startJulian,c,new JulianDate));let d=this._timeBarEle.clientWidth;d<10&&(d=10);const m=this._startJulian,_=Math.min(u/d*1e-5,.4);let p;const D=JulianDate.toGregorianDate(m);p=u>31536e4?JulianDate.fromDate(new Date(Date.UTC(100*Math.floor(D.year/100),0))):u>31536e3?JulianDate.fromDate(new Date(Date.UTC(10*Math.floor(D.year/10),0))):u>86400?JulianDate.fromDate(new Date(Date.UTC(D.year,0))):JulianDate.fromDate(new Date(Date.UTC(D.year,D.month,D.day)));const M=JulianDate.secondsDifference(this._startJulian,JulianDate.addSeconds(p,_,new JulianDate));let f=M+u;function S(e){return Math.floor(M/e)*e}function T(e,t){return Math.ceil(e/t+.5)*t}function v(e){return(e-M)/u}function J(e,t){return e-t*Math.round(e/t)}this._epochJulian=p,this._rulerEle.innerHTML=this.makeLabel(JulianDate.addSeconds(this._endJulian,-l,new JulianDate));let g=this._rulerEle.offsetWidth+20;g<30&&(g=180);const E=r;r-=h;const b={startTime:M,startJulian:m,epochJulian:p,duration:u,timeBarWidth:d,getAlpha:v};this._highlightRanges.forEach((function(e){a+=e.render(b)}));let k=0,w=0,y=0,L=g/d;L>1&&(L=1),L*=this._timeBarSecondsSpan;let B=-1,C=-1;const X=timelineTicScales.length;let W;for(W=0;WL&&e>r)break;C<0&&d*(e/this._timeBarSecondsSpan)>=this.smallestTicInPixels&&(C=B)}if(B>0){while(B>0)if(--B,Math.abs(J(k,timelineTicScales[B]))<1e-5){timelineTicScales[B]>=r&&(w=timelineTicScales[B]);break}if(C>=0)while(C=r){y=timelineTicScales[C];break}++C}}r=E,r>h&&y<1e-5&&Math.abs(r-k)>h&&(y=r,r<=k+h&&(w=0));let x,$=-999999;if(d*(y/this._timeBarSecondsSpan)>=3)for(o=S(y);o<=f;o=T(o,y))a+=``;if(d*(w/this._timeBarSecondsSpan)>=3)for(o=S(w);o<=f;o=T(o,w))a+=``;if(d*(k/this._timeBarSecondsSpan)>=2){this._mainTicSpan=k,f+=k,o=S(k);const e=JulianDate.computeTaiMinusUtc(p);while(o<=f){let t=JulianDate.addSeconds(m,o-M,new JulianDate);if(k>2.1){const i=JulianDate.computeTaiMinusUtc(t);Math.abs(i-e)>.1&&(o+=i-e,t=JulianDate.addSeconds(m,o-M,new JulianDate))}const i=Math.round(d*v(o)),n=this.makeLabel(t);this._rulerEle.innerHTML=n,x=this._rulerEle.offsetWidth,x<10&&(x=g);const s=i-(x/2-1);s>$?($=s+x+5,a+=`${n}`):a+=``,o=T(o,k)}}else this._mainTicSpan=-1;a+=``,e.innerHTML=a,this._scrubElement=e.lastChild,this._context.clearRect(0,0,this._trackListEle.width,this._trackListEle.height),b.y=0,this._trackList.forEach((function(e){e.render(s._context,b),b.y+=e.height}))},Timeline.prototype.updateFromClock=function(){this._scrubJulian=this._clock.currentTime;const e=this._scrubElement;if(defined(this._scrubElement)){const t=JulianDate.secondsDifference(this._scrubJulian,this._startJulian),i=Math.round(t*this._topDiv.clientWidth/this._timeBarSecondsSpan);this._lastXPos!==i&&(this._lastXPos=i,e.style.left=i-8+"px",this._needleEle.style.left=`${i}px`)}defined(this._timelineDragLocation)&&(this._setTimeBarTime(this._timelineDragLocation,this._timelineDragLocation*this._timeBarSecondsSpan/this._topDiv.clientWidth),this.zoomTo(JulianDate.addSeconds(this._startJulian,this._timelineDrag,new JulianDate),JulianDate.addSeconds(this._endJulian,this._timelineDrag,new JulianDate)))},Timeline.prototype._setTimeBarTime=function(e,t){if(e=Math.round(e),this._scrubJulian=JulianDate.addSeconds(this._startJulian,t,new JulianDate),this._scrubElement){const t=e-8;this._scrubElement.style.left=`${t.toString()}px`,this._needleEle.style.left=`${e.toString()}px`}const i=document.createEvent("Event");i.initEvent("settime",!0,!0),i.clientX=e,i.timeSeconds=t,i.timeJulian=this._scrubJulian,i.clock=this._clock,this._topDiv.dispatchEvent(i)},Timeline.prototype.resize=function(){const e=this.container.clientWidth,t=this.container.clientHeight;if(e===this._lastWidth&&t===this._lastHeight)return;this._trackContainer.style.height=`${t}px`;let i=1;this._trackList.forEach((function(e){i+=e.height})),this._trackListEle.style.height=`${i.toString()}px`,this._trackListEle.width=this._trackListEle.clientWidth,this._trackListEle.height=i,this._makeTics(),this._lastXPos=void 0,this._lastWidth=e,this._lastHeight=t};export default Timeline;