2017-08-01 4 views
0

私は答えが明白であるように感じますが、私はそれを見つけることができません。メインアクティビティのWebViewをApplicationクラスから参照するにはどうすればよいですか?アクティビティクラスでpublic static varを使用して参照を保持すると、メモリリークが発生します。メモリリークを起こすことなく、ActivityからApplicationクラスのWebViewにアクセスするにはどうしたらいいですか?

現在のコード(動作しますが、メモリリークの原因となります)。

活動

public class Core extends AppCompatActivity { 

public static WebView coreView; 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 

    setContentView(R.layout.activity_core); 

    WebView myWebView = (WebView) findViewById(R.id.webview); 
    WebSettings webSettings = myWebView.getSettings(); 
    webSettings.setJavaScriptEnabled(true); 
    webSettings.setDomStorageEnabled(true); 
    webSettings.setJavaScriptCanOpenWindowsAutomatically(true); 
    myWebView.setWebViewClient(new WebViewClient()); 
    myWebView.setPadding(0,80,0,0); 

    coreView = myWebView; 
} 
} 

アプリケーション

public class App extends Application { 
@Override 
public void onCreate() { 
    super.onCreate(); 

    Core.coreView.loadUrl("http://www.google.com"); 

} 

EDIT: 全アプリケーションクラス。

public class App extends Application { 
@Override 
public void onCreate() { 
    super.onCreate(); 

    OneSignal.startInit(this) 
      .inFocusDisplaying(OneSignal.OSInFocusDisplayOption.Notification) 
      .setNotificationOpenedHandler(new MainNotificationOpenedHandler()) 
      .setNotificationReceivedHandler(new MainNotificationReceivedHandler()) 
      .unsubscribeWhenNotificationsAreDisabled(true) 
      .init(); 

    OSPermissionSubscriptionState status = OneSignal.getPermissionSubscriptionState(); 
} 

private class MainNotificationOpenedHandler implements OneSignal.NotificationOpenedHandler { 
    // This fires when a notification is opened by tapping on it. 
    @Override 
    public void notificationOpened(OSNotificationOpenResult result) { 
     OSNotificationAction.ActionType actionType = result.action.type; 
     JSONObject data = result.notification.payload.additionalData; 
     String customKey; 

     Core.coreView.loadUrl(result.notification.payload.launchURL); 
    } 
} 

private class MainNotificationReceivedHandler implements OneSignal.NotificationReceivedHandler { 
    @Override 
    public void notificationReceived(OSNotification notification) { 
     JSONObject data = notification.payload.additionalData; 
    } 

} 

}

答えて

1

どのように私はApplicationクラスからの私の主な活動でのWebViewを参照していますか?

あなたはありません。そのコードをアクティビティ、またはそのアクティビティにスコープされたもの(たとえば、フラグメント)に移動します。

たとえば、ApplicationonCreate()が呼び出されるまでにCore.coreViewが設定されないため、問題のコードがクラッシュすることがあります。 ApplicationonCreate()が、アクティビティなどのコンポーネントが作成される前に、プロセスの開始の一環として呼び出されます。

+0

実行時にクラッシュすることは絶対に正しいですが、私はCore.coreView.loadUrl( "http://www.google.com")の質問を簡略化しました。実際にはイベントハンドラにあり、Applicationコンストラクタではありませんでした。 私はあなたの意見を取ります。したがって、アプリケーションコードをアクティビティの変更に使用しないでください。私がしようとしているのは、OneSignal SDKを使用して、ユーザーが通知を受け取ったときにwebview URLを変更することです。 OneSignalは、通知用の初期化/ハンドラがextendsアプリケーションクラス内にある必要があることを示します。したがって、ハンドラがアプリケーションにある場合、webviewにURLを変更するよう指示する方法はありますか? – dakishimesan

+0

PS:オリジナルの投稿にフルAppクラスが追加されました。ご協力ありがとうございました! – dakishimesan

+0

@dakishimesan:イベントバスを使用します(緑色のロボットのEventBus、 'LocalBroadcastManager'、Rxベースのものなど)。あなたの 'MainNotificationOpenedHandler'はイベントをバスに掲示してください。あなたの活動をバス上のイベントに登録し、必要に応じて対応してください。これが適切に行われると、メモリリークがなくなり、アクティビティが破壊されたケース(ユーザのナビゲーションなど)も処理されます。 – CommonsWare

関連する問題