Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(8)

Side by Side Diff: remoting/android/java/src/org/chromium/chromoting/jni/Client.java

Issue 2007123003: [Android Client] Break down multi-threaded classes by thread (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 package org.chromium.chromoting.jni; 5 package org.chromium.chromoting.jni;
6 6
7 import android.graphics.Bitmap;
8 import android.graphics.Point;
9 import android.os.Looper;
10
11 import org.chromium.base.Log;
12 import org.chromium.base.annotations.CalledByNative; 7 import org.chromium.base.annotations.CalledByNative;
13 import org.chromium.base.annotations.JNINamespace; 8 import org.chromium.base.annotations.JNINamespace;
14 import org.chromium.base.annotations.SuppressFBWarnings; 9 import org.chromium.base.annotations.SuppressFBWarnings;
15 import org.chromium.chromoting.CapabilityManager; 10 import org.chromium.chromoting.CapabilityManager;
16 import org.chromium.chromoting.SessionAuthenticator; 11 import org.chromium.chromoting.SessionAuthenticator;
17 12
18 import java.nio.ByteBuffer;
19 import java.nio.ByteOrder;
20
21 /** 13 /**
22 * Class to manage a client connection to the host. This class controls the life time of the 14 * Class to manage a client connection to the host. This class controls the life time of the
23 * corresponding C++ object which implements the connection. A new object should be created for 15 * corresponding C++ object which implements the connection. A new object should be created for
24 * each connection to the host, so that notifications from a connection are alwa ys sent to the 16 * each connection to the host, so that notifications from a connection are alwa ys sent to the
25 * right object. 17 * right object.
26 */ 18 */
27 @JNINamespace("remoting") 19 @JNINamespace("remoting")
28 public class Client { 20 public class Client {
29 private static final String TAG = "Chromoting";
30
31 // Pointer to the C++ object, cast to a |long|. 21 // Pointer to the C++ object, cast to a |long|.
32 private long mNativeJniClient; 22 private long mNativeJniClient;
33 23
24 // Reference has to be kept until the lifecycle of Client ends. Code may use getDisplay()
25 // without doing a null check.
26 private Display mDisplay;
27
34 // The global Client instance (may be null). This needs to be a global singl eton so that the 28 // The global Client instance (may be null). This needs to be a global singl eton so that the
35 // Client can be passed between Activities. 29 // Client can be passed between Activities.
36 private static Client sClient; 30 private static Client sClient;
37 31
38 // Called on the UI thread. 32 // Called on the UI thread.
Lambros 2016/05/28 00:43:05 If everything is called on the UI thread, you can
Yuwei 2016/06/01 21:30:10 Done.
39 public Client() { 33 public Client() {
40 if (sClient != null) { 34 if (sClient != null) {
41 throw new RuntimeException("Client instance already created."); 35 throw new RuntimeException("Client instance already created.");
42 } 36 }
43 37
44 sClient = this; 38 sClient = this;
45 mNativeJniClient = nativeInit(); 39 mNativeJniClient = nativeInit();
46 } 40 }
47 41
42 /**
43 *
Lambros 2016/05/28 00:43:05 Better to provide a JavaDoc one-sentence summary,
Yuwei 2016/06/01 21:30:10 Done.
44 * @return the display object. It will be null before calling connectToHost( ) but won't be null
45 * after calling disconnectFromHost().
46 */
47 public Display getDisplay() {
48 return mDisplay;
49 }
50
48 // Called on the UI thread. Suppress FindBugs warning, since |sClient| is on ly used on the 51 // Called on the UI thread. Suppress FindBugs warning, since |sClient| is on ly used on the
49 // UI thread. 52 // UI thread.
50 @SuppressFBWarnings("LI_LAZY_INIT_STATIC") 53 @SuppressFBWarnings("LI_LAZY_INIT_STATIC")
51 public void destroy() { 54 public void destroy() {
52 if (sClient != null) { 55 if (sClient != null) {
53 disconnectFromHost(); 56 disconnectFromHost();
54 nativeDestroy(mNativeJniClient); 57 nativeDestroy(mNativeJniClient);
55 sClient = null; 58 sClient = null;
56 } 59 }
57 } 60 }
58 61
59 /** Returns the current Client instance, or null. */ 62 /** Returns the current Client instance, or null. */
60 public static Client getInstance() { 63 public static Client getInstance() {
61 return sClient; 64 return sClient;
62 } 65 }
63 66
64 /** Used for authentication-related UX during connection. Accessed on the UI thread. */ 67 /** Used for authentication-related UX during connection. Accessed on the UI thread. */
65 private SessionAuthenticator mAuthenticator; 68 private SessionAuthenticator mAuthenticator;
66 69
67 /** Whether the native code is attempting a connection. Accessed on the UI t hread. */ 70 /** Whether the native code is attempting a connection. Accessed on the UI t hread. */
68 private boolean mConnected; 71 private boolean mConnected;
69 72
70 /** Notified upon successful connection or disconnection. Accessed on the UI thread. */ 73 /** Notified upon successful connection or disconnection. Accessed on the UI thread. */
71 private ConnectionListener mConnectionListener; 74 private ConnectionListener mConnectionListener;
72 75
73 /**
74 * Callback invoked on the graphics thread to repaint the desktop. Accessed on the UI and
75 * graphics threads.
76 */
77 private Runnable mRedrawCallback;
78
79 /** Bitmap holding a copy of the latest video frame. Accessed on the UI and graphics threads. */
80 private Bitmap mFrameBitmap;
81
82 /** Protects access to {@link mFrameBitmap}. */
83 private final Object mFrameLock = new Object();
84
85 /** Position of cursor hot-spot. Accessed on the graphics thread. */
86 private Point mCursorHotspot = new Point();
87
88 /** Bitmap holding the cursor shape. Accessed on the graphics thread. */
89 private Bitmap mCursorBitmap;
90
91 /** Capability Manager through which capabilities and extensions are handled . */ 76 /** Capability Manager through which capabilities and extensions are handled . */
92 private CapabilityManager mCapabilityManager = new CapabilityManager(); 77 private CapabilityManager mCapabilityManager = new CapabilityManager();
93 78
94 public CapabilityManager getCapabilityManager() { 79 public CapabilityManager getCapabilityManager() {
95 return mCapabilityManager; 80 return mCapabilityManager;
96 } 81 }
97 82
98 /** Returns whether the client is connected. */ 83 /** Returns whether the client is connected. */
99 public boolean isConnected() { 84 public boolean isConnected() {
100 return mConnected; 85 return mConnected;
101 } 86 }
102 87
103 /** Attempts to form a connection to the user-selected host. Called on the U I thread. */ 88 /** Attempts to form a connection to the user-selected host. Called on the U I thread. */
104 public void connectToHost(String username, String authToken, String hostJid, 89 public void connectToHost(String username, String authToken, String hostJid,
105 String hostId, String hostPubkey, SessionAuthenticator authenticator , String flags, 90 String hostId, String hostPubkey, SessionAuthenticator authenticator , String flags,
106 ConnectionListener listener) { 91 ConnectionListener listener) {
107 disconnectFromHost(); 92 disconnectFromHost();
108 93
109 mConnectionListener = listener; 94 mConnectionListener = listener;
110 mAuthenticator = authenticator; 95 mAuthenticator = authenticator;
111 nativeConnect(mNativeJniClient, username, authToken, hostJid, hostId, ho stPubkey, 96 mDisplay = new Display();
112 mAuthenticator.getPairingId(hostId), mAuthenticator.getPairingSe cret(hostId), 97 nativeConnect(mNativeJniClient, mDisplay.getNativePointer(), username, a uthToken, hostJid,
113 mCapabilityManager.getLocalCapabilities(), flags); 98 hostId, hostPubkey, mAuthenticator.getPairingId(hostId),
99 mAuthenticator.getPairingSecret(hostId), mCapabilityManager.getL ocalCapabilities(),
100 flags);
114 mConnected = true; 101 mConnected = true;
115 } 102 }
116 103
117 /** Severs the connection and cleans up. Called on the UI thread. */ 104 /** Severs the connection and cleans up. Called on the UI thread. */
118 public void disconnectFromHost() { 105 public void disconnectFromHost() {
119 if (!mConnected) { 106 if (!mConnected) {
120 return; 107 return;
121 } 108 }
122 109
123 mConnectionListener.onConnectionState( 110 mConnectionListener.onConnectionState(
124 ConnectionListener.State.CLOSED, ConnectionListener.Error.OK); 111 ConnectionListener.State.CLOSED, ConnectionListener.Error.OK);
125 112
126 disconnectFromHostWithoutNotification(); 113 disconnectFromHostWithoutNotification();
127 } 114 }
128 115
129 /** Same as disconnectFromHost() but without notifying the ConnectionListene r. */ 116 /** Same as disconnectFromHost() but without notifying the ConnectionListene r. */
130 private void disconnectFromHostWithoutNotification() { 117 private void disconnectFromHostWithoutNotification() {
131 if (!mConnected) { 118 if (!mConnected) {
132 return; 119 return;
133 } 120 }
134 121
135 nativeDisconnect(mNativeJniClient); 122 nativeDisconnect(mNativeJniClient);
136 mConnectionListener = null; 123 mConnectionListener = null;
137 mConnected = false; 124 mConnected = false;
138 mCapabilityManager.onHostDisconnect(); 125 mCapabilityManager.onHostDisconnect();
139 126
140 // Drop the reference to free the Bitmap for GC. 127 mDisplay.destroy();
141 synchronized (mFrameLock) {
142 mFrameBitmap = null;
143 }
144 } 128 }
145 129
146 /** Called on the UI thread whenever the connection status changes. */ 130 /** Called on the UI thread whenever the connection status changes. */
147 @CalledByNative 131 @CalledByNative
148 void onConnectionState(int stateCode, int errorCode) { 132 void onConnectionState(int stateCode, int errorCode) {
149 ConnectionListener.State state = ConnectionListener.State.fromValue(stat eCode); 133 ConnectionListener.State state = ConnectionListener.State.fromValue(stat eCode);
150 ConnectionListener.Error error = ConnectionListener.Error.fromValue(erro rCode); 134 ConnectionListener.Error error = ConnectionListener.Error.fromValue(erro rCode);
151 mConnectionListener.onConnectionState(state, error); 135 mConnectionListener.onConnectionState(state, error);
152 if (state == ConnectionListener.State.FAILED || state == ConnectionListe ner.State.CLOSED) { 136 if (state == ConnectionListener.State.FAILED || state == ConnectionListe ner.State.CLOSED) {
153 // Disconnect from the host here, otherwise the next time connectToH ost() is called, 137 // Disconnect from the host here, otherwise the next time connectToH ost() is called,
(...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after
245 * lifecycle events. 229 * lifecycle events.
246 */ 230 */
247 public void enableVideoChannel(boolean enable) { 231 public void enableVideoChannel(boolean enable) {
248 if (!mConnected) { 232 if (!mConnected) {
249 return; 233 return;
250 } 234 }
251 235
252 nativeEnableVideoChannel(mNativeJniClient, enable); 236 nativeEnableVideoChannel(mNativeJniClient, enable);
253 } 237 }
254 238
255 /**
256 * Sets the redraw callback to the provided functor. Provide a value of null whenever the
257 * window is no longer visible so that we don't continue to draw onto it. Ca lled on the UI
258 * thread.
259 */
260 public void provideRedrawCallback(Runnable redrawCallback) {
261 mRedrawCallback = redrawCallback;
262 }
263
264 /** Forces the native graphics thread to redraw to the canvas. Called on the UI thread. */
265 public boolean redrawGraphics() {
266 if (!mConnected || mRedrawCallback == null) return false;
267
268 nativeScheduleRedraw(mNativeJniClient);
269 return true;
270 }
271
272 /**
273 * Called on the graphics thread to perform the redrawing callback requested by
274 * {@link #redrawGraphics}. This is a no-op if the window isn't visible (the callback is null).
275 */
276 @CalledByNative
277 void redrawGraphicsInternal() {
278 Runnable callback = mRedrawCallback;
279 if (callback != null) {
280 callback.run();
281 }
282 }
283
284 /**
285 * Returns a bitmap of the latest video frame. Called on the native graphics thread when
286 * DesktopView is repainted.
287 */
288 public Bitmap getVideoFrame() {
289 if (Looper.myLooper() == Looper.getMainLooper()) {
290 Log.w(TAG, "Canvas being redrawn on UI thread");
291 }
292
293 synchronized (mFrameLock) {
294 return mFrameBitmap;
295 }
296 }
297
298 /**
299 * Set a new video frame. Called on the native graphics thread when a new fr ame is allocated.
300 */
301 @CalledByNative
302 void setVideoFrame(Bitmap bitmap) {
303 if (Looper.myLooper() == Looper.getMainLooper()) {
304 Log.w(TAG, "Video frame updated on UI thread");
305 }
306
307 synchronized (mFrameLock) {
308 mFrameBitmap = bitmap;
309 }
310 }
311
312 /**
313 * Creates a new Bitmap to hold video frame pixels. The returned Bitmap is r eferenced by native
314 * code which writes the decoded frame pixels to it.
315 */
316 @CalledByNative
317 static Bitmap newBitmap(int width, int height) {
318 return Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
319 }
320
321 /**
322 * Updates the cursor shape. This is called on the graphics thread when rece iving a new cursor
323 * shape from the host.
324 */
325 @CalledByNative
326 void updateCursorShape(int width, int height, int hotspotX, int hotspotY, By teBuffer buffer) {
327 mCursorHotspot = new Point(hotspotX, hotspotY);
328
329 int[] data = new int[width * height];
330 buffer.order(ByteOrder.LITTLE_ENDIAN);
331 buffer.asIntBuffer().get(data, 0, data.length);
332 mCursorBitmap = Bitmap.createBitmap(data, width, height, Bitmap.Config.A RGB_8888);
333 }
334
335 /** Position of cursor hotspot within cursor image. Called on the graphics t hread. */
336 public Point getCursorHotspot() {
337 return mCursorHotspot;
338 }
339
340 /** Returns the current cursor shape. Called on the graphics thread. */
341 public Bitmap getCursorBitmap() {
342 return mCursorBitmap;
343 }
344
345 // 239 //
346 // Third Party Authentication 240 // Third Party Authentication
347 // 241 //
348 242
349 /** 243 /**
350 * Pops up a third party login page to fetch the token required for authenti cation. 244 * Pops up a third party login page to fetch the token required for authenti cation.
351 */ 245 */
352 @CalledByNative 246 @CalledByNative
353 void fetchThirdPartyToken(String tokenUrl, String clientId, String scope) { 247 void fetchThirdPartyToken(String tokenUrl, String clientId, String scope) {
354 mAuthenticator.fetchThirdPartyToken(tokenUrl, clientId, scope); 248 mAuthenticator.fetchThirdPartyToken(tokenUrl, clientId, scope);
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
397 } 291 }
398 292
399 nativeSendExtensionMessage(mNativeJniClient, type, data); 293 nativeSendExtensionMessage(mNativeJniClient, type, data);
400 } 294 }
401 295
402 private native long nativeInit(); 296 private native long nativeInit();
403 297
404 private native void nativeDestroy(long nativeJniClient); 298 private native void nativeDestroy(long nativeJniClient);
405 299
406 /** Performs the native portion of the connection. */ 300 /** Performs the native portion of the connection. */
407 private native void nativeConnect(long nativeJniClient, String username, Str ing authToken, 301 private native void nativeConnect(long nativeJniClient, long nativeJniDispla yHandler,
408 String hostJid, String hostId, String hostPubkey, String pairId, Str ing pairSecret, 302 String username, String authToken, String hostJid, String hostId, St ring hostPubkey,
409 String capabilities, String flags); 303 String pairId, String pairSecret, String capabilities, String flags) ;
410 304
411 /** Native implementation of Client.handleAuthenticationResponse(). */ 305 /** Native implementation of Client.handleAuthenticationResponse(). */
412 private native void nativeAuthenticationResponse( 306 private native void nativeAuthenticationResponse(
413 long nativeJniClient, String pin, boolean createPair, String deviceN ame); 307 long nativeJniClient, String pin, boolean createPair, String deviceN ame);
414 308
415 /** Performs the native portion of the cleanup. */ 309 /** Performs the native portion of the cleanup. */
416 private native void nativeDisconnect(long nativeJniClient); 310 private native void nativeDisconnect(long nativeJniClient);
417 311
418 /** Schedules a redraw on the native graphics thread. */
419 private native void nativeScheduleRedraw(long nativeJniClient);
420
421 /** Passes authentication data to the native handling code. */ 312 /** Passes authentication data to the native handling code. */
422 private native void nativeOnThirdPartyTokenFetched( 313 private native void nativeOnThirdPartyTokenFetched(
423 long nativeJniClient, String token, String sharedSecret); 314 long nativeJniClient, String token, String sharedSecret);
424 315
425 /** Passes mouse information to the native handling code. */ 316 /** Passes mouse information to the native handling code. */
426 private native void nativeSendMouseEvent( 317 private native void nativeSendMouseEvent(
427 long nativeJniClient, int x, int y, int whichButton, boolean buttonD own); 318 long nativeJniClient, int x, int y, int whichButton, boolean buttonD own);
428 319
429 /** Passes mouse-wheel information to the native handling code. */ 320 /** Passes mouse-wheel information to the native handling code. */
430 private native void nativeSendMouseWheelEvent(long nativeJniClient, int delt aX, int deltaY); 321 private native void nativeSendMouseWheelEvent(long nativeJniClient, int delt aX, int deltaY);
431 322
432 /** Passes key press information to the native handling code. */ 323 /** Passes key press information to the native handling code. */
433 private native boolean nativeSendKeyEvent( 324 private native boolean nativeSendKeyEvent(
434 long nativeJniClient, int scanCode, int keyCode, boolean keyDown); 325 long nativeJniClient, int scanCode, int keyCode, boolean keyDown);
435 326
436 /** Passes text event information to the native handling code. */ 327 /** Passes text event information to the native handling code. */
437 private native void nativeSendTextEvent(long nativeJniClient, String text); 328 private native void nativeSendTextEvent(long nativeJniClient, String text);
438 329
439 /** Passes touch event information to the native handling code. */ 330 /** Passes touch event information to the native handling code. */
440 private native void nativeSendTouchEvent( 331 private native void nativeSendTouchEvent(
441 long nativeJniClient, int eventType, TouchEventData[] data); 332 long nativeJniClient, int eventType, TouchEventData[] data);
442 333
443 /** Native implementation of Client.enableVideoChannel() */ 334 /** Native implementation of Client.enableVideoChannel() */
444 private native void nativeEnableVideoChannel(long nativeJniClient, boolean e nable); 335 private native void nativeEnableVideoChannel(long nativeJniClient, boolean e nable);
445 336
446 /** Passes extension message to the native code. */ 337 /** Passes extension message to the native code. */
447 private native void nativeSendExtensionMessage(long nativeJniClient, String type, String data); 338 private native void nativeSendExtensionMessage(long nativeJniClient, String type, String data);
448 } 339 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698