ソースを参照

Load icons on main thread (#2536)

Only reason to offload icon loading to background thread is to avoid
supposed network on main thread calls which happen only in debug since
icons are passed loaded from localhost.
Guy Carmeli 7 年 前
コミット
3dd96a94ef
No account linked to committer's email address

+ 3
- 1
lib/android/app/src/main/java/com/reactnativenavigation/NavigationApplication.java ファイルの表示

@@ -13,11 +13,13 @@ import java.util.List;
13 13
 public abstract class NavigationApplication extends Application implements ReactApplication {
14 14
 
15 15
 	private ReactGateway reactGateway;
16
+	public static NavigationApplication instance;
16 17
 
17 18
 	@Override
18 19
 	public void onCreate() {
19 20
 		super.onCreate();
20
-		reactGateway = new ReactGateway(this, isDebug(), createAdditionalReactPackages());
21
+        instance = this;
22
+        reactGateway = new ReactGateway(this, isDebug(), createAdditionalReactPackages());
21 23
 	}
22 24
 
23 25
 	public ReactGateway getReactGateway() {

+ 1
- 1
lib/android/app/src/main/java/com/reactnativenavigation/presentation/OptionsPresenter.java ファイルの表示

@@ -23,8 +23,8 @@ public class OptionsPresenter {
23 23
     }
24 24
 
25 25
     public void applyOptions(Options options) {
26
-        applyTopBarOptions(options.topBarOptions);
27 26
         applyButtons(options.topBarOptions.leftButtons, options.topBarOptions.rightButtons);
27
+        applyTopBarOptions(options.topBarOptions);
28 28
         applyTopTabsOptions(options.topTabsOptions);
29 29
         applyTopTabOptions(options.topTabOptions);
30 30
     }

+ 42
- 39
lib/android/app/src/main/java/com/reactnativenavigation/utils/ImageUtils.java ファイルの表示

@@ -8,7 +8,11 @@ import android.graphics.drawable.Drawable;
8 8
 import android.net.Uri;
9 9
 import android.os.StrictMode;
10 10
 import android.support.annotation.NonNull;
11
+import android.support.annotation.Nullable;
11 12
 
13
+import com.reactnativenavigation.NavigationApplication;
14
+
15
+import java.io.FileNotFoundException;
12 16
 import java.io.IOException;
13 17
 import java.io.InputStream;
14 18
 import java.net.URL;
@@ -21,46 +25,45 @@ public class ImageUtils {
21 25
 		void onError(Throwable error);
22 26
 	}
23 27
 
24
-	public static void tryLoadIcon(final Context context, final String uri, final ImageLoadingListener listener) {
25
-		if (uri == null) {
26
-			if (listener != null) {
27
-				listener.onError(new IllegalArgumentException("Uri is null"));
28
-			}
29
-			return;
30
-		}
31
-		runWorkerThread(new Runnable() {
32
-			@Override
33
-			public void run() {
34
-				loadIcon(context, uri, listener);
35
-			}
36
-		});
37
-	}
28
+	public static void loadIcon(final Context context, final String uri, final ImageLoadingListener listener) {
29
+        try {
30
+            StrictMode.ThreadPolicy threadPolicy = adjustThreadPolicyDebug();
31
+            
32
+            InputStream is = openStream(context, uri);
33
+            Bitmap bitmap = BitmapFactory.decodeStream(is);
34
+            Drawable drawable = new BitmapDrawable(context.getResources(), bitmap);
35
+            listener.onComplete(drawable);
38 36
 
39
-	private static void loadIcon(Context context, String uri, final ImageLoadingListener listener) {
40
-		try {
41
-			InputStream is = null;
42
-			if (uri.contains("http")) {
43
-				URL url = new URL(uri);
44
-				is = url.openStream();
45
-			} else {
46
-				is = context.getContentResolver().openInputStream(Uri.parse(uri));
47
-			}
37
+            restoreThreadPolicyDebug(threadPolicy);
38
+        } catch (IOException e) {
39
+            listener.onError(e);
40
+        }
41
+    }
48 42
 
49
-			Bitmap bitmap = BitmapFactory.decodeStream(is);
50
-			Drawable drawable = new BitmapDrawable(context.getResources(), bitmap);
51
-			if (listener != null) {
52
-				listener.onComplete(drawable);
53
-			}
54
-		} catch (IOException e) {
55
-			if (listener != null) {
56
-				listener.onError(e);
57
-			} else {
58
-				e.printStackTrace();
59
-			}
60
-		}
61
-	}
43
+    private static StrictMode.ThreadPolicy adjustThreadPolicyDebug() {
44
+        StrictMode.ThreadPolicy threadPolicy = null;
45
+        if (NavigationApplication.instance.isDebug()) {
46
+            threadPolicy = StrictMode.getThreadPolicy();
47
+            StrictMode.setThreadPolicy(new StrictMode.ThreadPolicy.Builder().permitNetwork().build());
48
+        }
49
+        return threadPolicy;
50
+    }
62 51
 
63
-	private static void runWorkerThread(Runnable runnable) {
64
-		new Thread(runnable).start();
65
-	}
52
+    private static void restoreThreadPolicyDebug(@Nullable StrictMode.ThreadPolicy threadPolicy) {
53
+        if (NavigationApplication.instance.isDebug() && threadPolicy != null) {
54
+            StrictMode.setThreadPolicy(threadPolicy);
55
+        }
56
+    }
57
+
58
+    private static InputStream openStream(Context context, String uri) throws IOException {
59
+        return uri.contains("http") ? remoteUrl(uri) : localFile(context, uri);
60
+    }
61
+
62
+    private static InputStream remoteUrl(String uri) throws IOException {
63
+        return new URL(uri).openStream();
64
+    }
65
+
66
+    private static InputStream localFile(Context context, String uri) throws FileNotFoundException {
67
+        return context.getContentResolver().openInputStream(Uri.parse(uri));
68
+    }
66 69
 }

+ 7
- 13
lib/android/app/src/main/java/com/reactnativenavigation/views/TitleBarButton.java ファイルの表示

@@ -57,39 +57,33 @@ public class TitleBarButton implements MenuItem.OnMenuItemClickListener {
57 57
 			return;
58 58
 		}
59 59
 
60
-		ImageUtils.tryLoadIcon(context, button.icon.get(), new ImageUtils.ImageLoadingListener() {
60
+		ImageUtils.loadIcon(context, button.icon.get(), new ImageUtils.ImageLoadingListener() {
61 61
 			@Override
62 62
 			public void onComplete(@NonNull Drawable drawable) {
63 63
 				icon = drawable;
64
-				UiUtils.runOnMainThread(() -> {
65
-                    setIconColor();
66
-                    setNavigationClickListener();
67
-                    toolbar.setNavigationIcon(icon);
68
-                });
64
+                setIconColor();
65
+                setNavigationClickListener();
66
+                toolbar.setNavigationIcon(icon);
69 67
 			}
70 68
 
71 69
 			@Override
72 70
 			public void onError(Throwable error) {
73
-				//TODO: handle
74 71
 				error.printStackTrace();
75 72
 			}
76 73
 		});
77 74
 	}
78 75
 
79 76
 	private void applyIcon(Context context, final MenuItem menuItem) {
80
-		ImageUtils.tryLoadIcon(context, button.icon.get(), new ImageUtils.ImageLoadingListener() {
77
+		ImageUtils.loadIcon(context, button.icon.get(), new ImageUtils.ImageLoadingListener() {
81 78
 			@Override
82 79
 			public void onComplete(@NonNull Drawable drawable) {
83 80
 				icon = drawable;
84
-				UiUtils.runOnMainThread(() -> {
85
-                    menuItem.setIcon(icon);
86
-                    setIconColor();
87
-                });
81
+                menuItem.setIcon(icon);
82
+                setIconColor();
88 83
 			}
89 84
 
90 85
 			@Override
91 86
 			public void onError(Throwable error) {
92
-				//TODO: handle
93 87
 				error.printStackTrace();
94 88
 			}
95 89
 		});