1/*
2 * Copyright (C) 2006 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package com.android.internal.telephony;
18
19import java.util.ArrayList;
20import java.util.List;
21
22import android.telephony.Rlog;
23
24/**
25 * {@hide}
26 */
27public abstract class Call {
28    protected final String LOG_TAG = "Call";
29
30    /* Enums */
31
32    public enum State {
33        IDLE, ACTIVE, HOLDING, DIALING, ALERTING, INCOMING, WAITING, DISCONNECTED, DISCONNECTING;
34
35        public boolean isAlive() {
36            return !(this == IDLE || this == DISCONNECTED || this == DISCONNECTING);
37        }
38
39        public boolean isRinging() {
40            return this == INCOMING || this == WAITING;
41        }
42
43        public boolean isDialing() {
44            return this == DIALING || this == ALERTING;
45        }
46    }
47
48    public enum SrvccState {
49        NONE, STARTED, COMPLETED, FAILED, CANCELED;
50    }
51
52    /* Instance Variables */
53
54    public State mState = State.IDLE;
55
56    public ArrayList<Connection> mConnections = new ArrayList<Connection>();
57
58    // Flag to indicate if the current calling/caller information
59    // is accurate. If false the information is known to be accurate.
60    //
61    // For CDMA, during call waiting/3 way, there is no network response
62    // if call waiting is answered, network timed out, dropped, 3 way
63    // merged, etc.
64    protected boolean mIsGeneric = false;
65
66    /* Instance Methods */
67
68    /** Do not modify the List result!!! This list is not yours to keep
69     *  It will change across event loop iterations            top
70     */
71
72    public abstract List<Connection> getConnections();
73    public abstract Phone getPhone();
74    public abstract boolean isMultiparty();
75    public abstract void hangup() throws CallStateException;
76
77
78    /**
79     * hasConnection
80     *
81     * @param c a Connection object
82     * @return true if the call contains the connection object passed in
83     */
84    public boolean hasConnection(Connection c) {
85        return c.getCall() == this;
86    }
87
88    /**
89     * hasConnections
90     * @return true if the call contains one or more connections
91     */
92    public boolean hasConnections() {
93        List<Connection> connections = getConnections();
94
95        if (connections == null) {
96            return false;
97        }
98
99        return connections.size() > 0;
100    }
101
102    /**
103     * getState
104     * @return state of class call
105     */
106    public State getState() {
107        return mState;
108    }
109
110    /**
111     * isIdle
112     *
113     * FIXME rename
114     * @return true if the call contains only disconnected connections (if any)
115     */
116    public boolean isIdle() {
117        return !getState().isAlive();
118    }
119
120    /**
121     * Returns the Connection associated with this Call that was created
122     * first, or null if there are no Connections in this Call
123     */
124    public Connection
125    getEarliestConnection() {
126        List<Connection> l;
127        long time = Long.MAX_VALUE;
128        Connection c;
129        Connection earliest = null;
130
131        l = getConnections();
132
133        if (l.size() == 0) {
134            return null;
135        }
136
137        for (int i = 0, s = l.size() ; i < s ; i++) {
138            c = l.get(i);
139            long t;
140
141            t = c.getCreateTime();
142
143            if (t < time) {
144                earliest = c;
145                time = t;
146            }
147        }
148
149        return earliest;
150    }
151
152    public long
153    getEarliestCreateTime() {
154        List<Connection> l;
155        long time = Long.MAX_VALUE;
156
157        l = getConnections();
158
159        if (l.size() == 0) {
160            return 0;
161        }
162
163        for (int i = 0, s = l.size() ; i < s ; i++) {
164            Connection c = l.get(i);
165            long t;
166
167            t = c.getCreateTime();
168
169            time = t < time ? t : time;
170        }
171
172        return time;
173    }
174
175    public long
176    getEarliestConnectTime() {
177        long time = Long.MAX_VALUE;
178        List<Connection> l = getConnections();
179
180        if (l.size() == 0) {
181            return 0;
182        }
183
184        for (int i = 0, s = l.size() ; i < s ; i++) {
185            Connection c = l.get(i);
186            long t;
187
188            t = c.getConnectTime();
189
190            time = t < time ? t : time;
191        }
192
193        return time;
194    }
195
196
197    public boolean
198    isDialingOrAlerting() {
199        return getState().isDialing();
200    }
201
202    public boolean
203    isRinging() {
204        return getState().isRinging();
205    }
206
207    /**
208     * Returns the Connection associated with this Call that was created
209     * last, or null if there are no Connections in this Call
210     */
211    public Connection
212    getLatestConnection() {
213        List<Connection> l = getConnections();
214        if (l.size() == 0) {
215            return null;
216        }
217
218        long time = 0;
219        Connection latest = null;
220        for (int i = 0, s = l.size() ; i < s ; i++) {
221            Connection c = l.get(i);
222            long t = c.getCreateTime();
223
224            if (t > time) {
225                latest = c;
226                time = t;
227            }
228        }
229
230        return latest;
231    }
232
233    /**
234     * To indicate if the connection information is accurate
235     * or not. false means accurate. Only used for CDMA.
236     */
237    public boolean isGeneric() {
238        return mIsGeneric;
239    }
240
241    /**
242     * Set the generic instance variable
243     */
244    public void setGeneric(boolean generic) {
245        mIsGeneric = generic;
246    }
247
248    /**
249     * Hangup call if it is alive
250     */
251    public void hangupIfAlive() {
252        if (getState().isAlive()) {
253            try {
254                hangup();
255            } catch (CallStateException ex) {
256                Rlog.w(LOG_TAG, " hangupIfActive: caught " + ex);
257            }
258        }
259    }
260}
261