001/**
002 *
003 * Copyright (c) 2014, the Railo Company Ltd. All rights reserved.
004 *
005 * This library is free software; you can redistribute it and/or
006 * modify it under the terms of the GNU Lesser General Public
007 * License as published by the Free Software Foundation; either 
008 * version 2.1 of the License, or (at your option) any later version.
009 * 
010 * This library is distributed in the hope that it will be useful,
011 * but WITHOUT ANY WARRANTY; without even the implied warranty of
012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
013 * Lesser General Public License for more details.
014 * 
015 * You should have received a copy of the GNU Lesser General Public 
016 * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
017 * 
018 **/
019package lucee.runtime.type.dt;
020
021import lucee.runtime.PageContext;
022import lucee.runtime.dump.DumpData;
023import lucee.runtime.dump.DumpProperties;
024import lucee.runtime.dump.DumpTable;
025import lucee.runtime.dump.SimpleDumpData;
026import lucee.runtime.exp.ExpressionException;
027import lucee.runtime.exp.PageException;
028import lucee.runtime.op.Caster;
029import lucee.runtime.op.Operator;
030
031/**
032 * TimeSpan Object, represent a timespan
033 */
034public final class TimeSpanImpl implements TimeSpan {
035
036        private double value;
037        private long valueMillis;
038        
039        private int day;
040        private int hour;
041        private int minute;
042        private int second;
043        private int milli;
044        
045
046        public static TimeSpan fromDays(double value){
047                return new TimeSpanImpl(value);
048        }
049        public static TimeSpan fromMillis(long value){
050                return new TimeSpanImpl(value);
051        }
052
053    private TimeSpanImpl(double valueDays) {
054        this((long)(valueDays*86400000D));
055    }
056        
057    private TimeSpanImpl(long valueMillis) {
058        value=valueMillis/86400000D;
059        long tmp=valueMillis;
060        day=(int) (valueMillis/86400000L);
061                tmp-=day*86400000;
062                hour=(int) (tmp/3600000);
063                tmp-=hour*3600000;
064                minute=(int) (tmp/60000);
065                tmp-=minute*60000;
066                second=(int) (tmp/1000);
067                tmp-=second*1000;
068                milli=(int) tmp;
069                
070                this.valueMillis=valueMillis;
071                /*day=(int)value;
072                double diff=value-day;
073                diff*=24;
074                hour=(int)diff;
075                diff=diff-hour;
076                diff*=60;
077                minute=(int)diff;
078                diff=diff-minute;
079                diff*=60;
080                second=(int)diff;
081                this.value=value;
082                milli=(int)(valueMillis-((second+(minute*60L)+(hour*3600L)+(day*3600L*24L))*1000));
083                */
084                //print.out("a("+hashCode()+"):"+day+":"+hour+":"+minute+":"+second+"+"+milli);
085                
086                
087                //total=(second+(minute*60L)+(hour*3600L)+(day*3600L*24L))*1000;
088                //total=(second+(minute*60L)+(hour*3600L)+(day*3600L*24L))*1000;
089                
090    }
091                
092        /**
093         * constructor of the timespan class
094         * @param day
095         * @param hour
096         * @param minute
097         * @param second
098         */
099        public TimeSpanImpl(int day, int hour, int minute, int second) {
100                
101                this.day=day;
102                this.hour=hour;
103                this.minute=minute;
104                this.second=second;
105                value=day+(((double)hour)/24)+(((double)minute)/24/60)+(((double)second)/24/60/60);
106                valueMillis=(second+(minute*60L)+(hour*3600L)+(day*3600L*24L))*1000;
107        }
108        
109        /**
110         * constructor of the timespan class
111         * @param day
112         * @param hour
113         * @param minute
114         * @param second
115         */
116        public TimeSpanImpl(int day, int hour, int minute, int second, int millisecond) {
117                this.day=day;
118                this.hour=hour;
119                this.minute=minute;
120                this.second=second;
121                this.milli=millisecond;
122                value=day+(((double)hour)/24)+(((double)minute)/24/60)+(((double)second)/24/60/60)+(((double)millisecond)/24/60/60/1000);
123                valueMillis=((second+(minute*60L)+(hour*3600L)+(day*3600L*24L))*1000)+millisecond;
124        }
125        
126    @Override
127        public String castToString() {
128                return Caster.toString(value);
129        }
130
131        @Override
132        public String castToString(String defaultValue) {
133                return Caster.toString(value);
134        }
135
136        @Override
137        public boolean castToBooleanValue() throws ExpressionException {
138                throw new ExpressionException("can't cast Timespan to boolean");
139        }
140    
141    @Override
142    public Boolean castToBoolean(Boolean defaultValue) {
143        return defaultValue;
144    }
145
146        @Override
147        public double castToDoubleValue() {
148                return value;
149        }
150    
151    @Override
152    public double castToDoubleValue(double defaultValue) {
153        return value;
154    }
155
156        @Override
157        public DateTime castToDateTime() throws ExpressionException {
158                throw new ExpressionException("can't cast Timespan to date");
159        }
160    
161    @Override
162    public DateTime castToDateTime(DateTime defaultValue) {
163        return defaultValue;
164    }
165
166
167        @Override
168        public int compareTo(boolean b) {
169                return Operator.compare(value, b?1D:0D);
170        }
171
172        @Override
173        public int compareTo(DateTime dt) throws PageException {
174                return Operator.compare(value, dt.castToDoubleValue());
175        }
176
177        @Override
178        public int compareTo(double d) throws PageException {
179                return Operator.compare(value, d);
180        }
181
182        @Override
183        public int compareTo(String str) throws PageException {
184                return Operator.compare(value, str);
185        }
186
187        @Override
188        public DumpData toDumpData(PageContext pageContext, int maxlevel, DumpProperties dp) {
189                DumpTable table=new DumpTable("timespan","#ff9900","#ffcc00","#000000");
190                if(milli>0)table.appendRow(1, new SimpleDumpData("Timespan"), new SimpleDumpData("createTimeSpan("+day+","+hour+","+minute+","+second+","+milli+")"));
191                else table.appendRow(1, new SimpleDumpData("Timespan"), new SimpleDumpData("createTimeSpan("+day+","+hour+","+minute+","+second+")"));
192                
193                
194                
195                return table;
196        }
197        @Override
198        public long getMillis() {
199                return valueMillis;
200        }
201        public long getMilli() {
202                return milli;
203        }
204        
205        @Override
206        public long getSeconds() {
207                return valueMillis/1000;
208        }
209        
210        @Override
211        public String toString() {
212                if(milli>0)
213                        return "createTimeSpan("+day+","+hour+","+minute+","+second+","+milli+")";
214                return "createTimeSpan("+day+","+hour+","+minute+","+second+")";
215        }
216
217    @Override
218    public int getDay() {
219        return day;
220    }
221    @Override
222    public int getHour() {
223        return hour;
224    }
225    @Override
226    public int getMinute() {
227        return minute;
228    }
229    @Override
230    public int getSecond() {
231        return second;
232    }
233
234        @Override
235        public boolean equals(Object obj) {
236                if(this==obj) return true;
237                if(!(obj instanceof TimeSpan)) return false;
238                return getMillis()==((TimeSpan)obj).getMillis();
239        }
240}