ITvInputSessionWrapper.java revision 4c52697dbed682a19dacc78b0c08931ea8dbc6b5
1/* 2 * Copyright (C) 2014 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 android.media.tv; 18 19import android.content.Context; 20import android.graphics.Rect; 21import android.net.Uri; 22import android.os.Bundle; 23import android.os.IBinder; 24import android.os.Looper; 25import android.os.Message; 26import android.util.Log; 27import android.view.InputChannel; 28import android.view.InputEvent; 29import android.view.InputEventReceiver; 30import android.view.Surface; 31 32import com.android.internal.os.HandlerCaller; 33import com.android.internal.os.SomeArgs; 34 35/** 36 * Implements the internal ITvInputSession interface to convert incoming calls on to it back to 37 * calls on the public TvInputSession interface, scheduling them on the main thread of the process. 38 * 39 * @hide 40 */ 41public class ITvInputSessionWrapper extends ITvInputSession.Stub implements HandlerCaller.Callback { 42 private static final String TAG = "TvInputSessionWrapper"; 43 44 private static final int DO_RELEASE = 1; 45 private static final int DO_SET_MAIN_SESSION = 2; 46 private static final int DO_SET_SURFACE = 3; 47 private static final int DO_DISPATCH_SURFACE_CHANGED = 4; 48 private static final int DO_SET_STREAM_VOLUME = 5; 49 private static final int DO_TUNE = 6; 50 private static final int DO_SET_CAPTION_ENABLED = 7; 51 private static final int DO_SELECT_TRACK = 8; 52 private static final int DO_UNSELECT_TRACK = 9; 53 private static final int DO_APP_PRIVATE_COMMAND = 10; 54 private static final int DO_CREATE_OVERLAY_VIEW = 11; 55 private static final int DO_RELAYOUT_OVERLAY_VIEW = 12; 56 private static final int DO_REMOVE_OVERLAY_VIEW = 13; 57 private static final int DO_REQUEST_UNBLOCK_CONTENT = 14; 58 59 private final HandlerCaller mCaller; 60 61 private TvInputService.Session mTvInputSessionImpl; 62 private InputChannel mChannel; 63 private TvInputEventReceiver mReceiver; 64 65 public ITvInputSessionWrapper(Context context, TvInputService.Session sessionImpl, 66 InputChannel channel) { 67 mCaller = new HandlerCaller(context, null, this, true /* asyncHandler */); 68 mTvInputSessionImpl = sessionImpl; 69 mChannel = channel; 70 if (channel != null) { 71 mReceiver = new TvInputEventReceiver(channel, context.getMainLooper()); 72 } 73 } 74 75 @Override 76 public void executeMessage(Message msg) { 77 if (mTvInputSessionImpl == null) { 78 return; 79 } 80 81 switch (msg.what) { 82 case DO_RELEASE: { 83 mTvInputSessionImpl.release(); 84 mTvInputSessionImpl = null; 85 if (mReceiver != null) { 86 mReceiver.dispose(); 87 mReceiver = null; 88 } 89 if (mChannel != null) { 90 mChannel.dispose(); 91 mChannel = null; 92 } 93 return; 94 } 95 case DO_SET_MAIN_SESSION: { 96 mTvInputSessionImpl.setMainSession((Boolean) msg.obj); 97 return; 98 } 99 case DO_SET_SURFACE: { 100 mTvInputSessionImpl.setSurface((Surface) msg.obj); 101 return; 102 } 103 case DO_DISPATCH_SURFACE_CHANGED: { 104 SomeArgs args = (SomeArgs) msg.obj; 105 mTvInputSessionImpl.dispatchSurfaceChanged(args.argi1, args.argi2, args.argi3); 106 args.recycle(); 107 return; 108 } 109 case DO_SET_STREAM_VOLUME: { 110 mTvInputSessionImpl.setStreamVolume((Float) msg.obj); 111 return; 112 } 113 case DO_TUNE: { 114 mTvInputSessionImpl.tune((Uri) msg.obj); 115 return; 116 } 117 case DO_SET_CAPTION_ENABLED: { 118 mTvInputSessionImpl.setCaptionEnabled((Boolean) msg.obj); 119 return; 120 } 121 case DO_SELECT_TRACK: { 122 mTvInputSessionImpl.selectTrack((TvTrackInfo) msg.obj); 123 return; 124 } 125 case DO_UNSELECT_TRACK: { 126 mTvInputSessionImpl.unselectTrack((TvTrackInfo) msg.obj); 127 return; 128 } 129 case DO_APP_PRIVATE_COMMAND: { 130 SomeArgs args = (SomeArgs) msg.obj; 131 mTvInputSessionImpl.appPrivateCommand((String) args.arg1, (Bundle) args.arg2); 132 args.recycle(); 133 return; 134 } 135 case DO_CREATE_OVERLAY_VIEW: { 136 SomeArgs args = (SomeArgs) msg.obj; 137 mTvInputSessionImpl.createOverlayView((IBinder) args.arg1, (Rect) args.arg2); 138 args.recycle(); 139 return; 140 } 141 case DO_RELAYOUT_OVERLAY_VIEW: { 142 mTvInputSessionImpl.relayoutOverlayView((Rect) msg.obj); 143 return; 144 } 145 case DO_REMOVE_OVERLAY_VIEW: { 146 mTvInputSessionImpl.removeOverlayView(true); 147 return; 148 } 149 case DO_REQUEST_UNBLOCK_CONTENT: { 150 mTvInputSessionImpl.requestUnblockContent((String) msg.obj); 151 return; 152 } 153 default: { 154 Log.w(TAG, "Unhandled message code: " + msg.what); 155 return; 156 } 157 } 158 } 159 160 @Override 161 public void release() { 162 mCaller.executeOrSendMessage(mCaller.obtainMessage(DO_RELEASE)); 163 } 164 165 @Override 166 public void setMainSession(boolean isMain) { 167 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_SET_MAIN_SESSION, isMain)); 168 } 169 170 @Override 171 public void setSurface(Surface surface) { 172 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_SET_SURFACE, surface)); 173 } 174 175 @Override 176 public void dispatchSurfaceChanged(int format, int width, int height) { 177 mCaller.executeOrSendMessage(mCaller.obtainMessageIIII(DO_DISPATCH_SURFACE_CHANGED, 178 format, width, height, 0)); 179 } 180 181 @Override 182 public final void setVolume(float volume) { 183 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_SET_STREAM_VOLUME, volume)); 184 } 185 186 @Override 187 public void tune(Uri channelUri) { 188 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_TUNE, channelUri)); 189 } 190 191 @Override 192 public void setCaptionEnabled(boolean enabled) { 193 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_SET_CAPTION_ENABLED, enabled)); 194 } 195 196 @Override 197 public void selectTrack(TvTrackInfo track) { 198 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_SELECT_TRACK, track)); 199 } 200 201 @Override 202 public void unselectTrack(TvTrackInfo track) { 203 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_UNSELECT_TRACK, track)); 204 } 205 206 @Override 207 public void appPrivateCommand(String action, Bundle data) { 208 mCaller.executeOrSendMessage(mCaller.obtainMessageOO(DO_APP_PRIVATE_COMMAND, action, 209 data)); 210 } 211 212 @Override 213 public void createOverlayView(IBinder windowToken, Rect frame) { 214 mCaller.executeOrSendMessage(mCaller.obtainMessageOO(DO_CREATE_OVERLAY_VIEW, windowToken, 215 frame)); 216 } 217 218 @Override 219 public void relayoutOverlayView(Rect frame) { 220 mCaller.executeOrSendMessage(mCaller.obtainMessageO(DO_RELAYOUT_OVERLAY_VIEW, frame)); 221 } 222 223 @Override 224 public void removeOverlayView() { 225 mCaller.executeOrSendMessage(mCaller.obtainMessage(DO_REMOVE_OVERLAY_VIEW)); 226 } 227 228 @Override 229 public void requestUnblockContent(String unblockedRating) { 230 mCaller.executeOrSendMessage(mCaller.obtainMessageO( 231 DO_REQUEST_UNBLOCK_CONTENT, unblockedRating)); 232 } 233 234 private final class TvInputEventReceiver extends InputEventReceiver { 235 public TvInputEventReceiver(InputChannel inputChannel, Looper looper) { 236 super(inputChannel, looper); 237 } 238 239 @Override 240 public void onInputEvent(InputEvent event) { 241 if (mTvInputSessionImpl == null) { 242 // The session has been finished. 243 finishInputEvent(event, false); 244 return; 245 } 246 247 int handled = mTvInputSessionImpl.dispatchInputEvent(event, this); 248 if (handled != TvInputManager.Session.DISPATCH_IN_PROGRESS) { 249 finishInputEvent(event, handled == TvInputManager.Session.DISPATCH_HANDLED); 250 } 251 } 252 } 253} 254