Спасибо, что прочитали мой вопрос :) Я не смог решить эту проблему после проверки всего форума. Я работаю над своим первым веб-просмотром. Ничего особенного. Это веб-просмотр с индикатором прогресса. Мой код в методе shouldOverrideUrlLoading не работает. Я хочу, чтобы все внешние ссылки моего сайта открывались в браузере, а не в приложении, но это не работает. Может кто-нибудь проверить мой код?

public class MainActivity extends AppCompatActivity
    implements NavigationView.OnNavigationItemSelectedListener {

private WebView wv;
private ProgressBar progressBar;
private FrameLayout frameLayout;
SwipeRefreshLayout swipe;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    frameLayout = (FrameLayout) findViewById(R.id.frameLayout);
    progressBar = (ProgressBar) findViewById(R.id.progressBar);
    progressBar.setMax(100);

    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);

    DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
    ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
            this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
    drawer.setDrawerListener(toggle);
    toggle.syncState();

    NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
    navigationView.setNavigationItemSelectedListener(this);

    swipe = (SwipeRefreshLayout) findViewById(R.id.swipe);
    swipe.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
        @Override
        public void onRefresh() {
            String webUrl = wv.getUrl();
            wv.loadUrl(webUrl);
        }
    });
    LoadWeb();

}

public void LoadWeb(){

    wv = (WebView)findViewById(R.id.webView);
    WebSettings settings = wv.getSettings();
    settings.setJavaScriptEnabled(true);

    wv.loadUrl("example.com");
    swipe.setRefreshing(true);
    wv.setWebViewClient(new HelpClient());
    wv.setWebViewClient(new MyAppWebViewClient());

    wv.setWebChromeClient(new WebChromeClient(){
        public void onProgressChanged(WebView view, int progress){
            frameLayout.setVisibility(View.VISIBLE);
            progressBar.setProgress(progress);

            if (progress == 100){
                frameLayout.setVisibility(View.GONE);

            }
            super.onProgressChanged(view, progress);
        }
    });
    progressBar.setProgress(0);

    wv.setWebViewClient(new WebViewClient(){

        public void onPageFinished(WebView view, String url){
            swipe.setRefreshing(false);
        }
    });

}

private class HelpClient extends WebViewClient {

    @Override
    public boolean shouldOverrideUrlLoading(WebView view, String url){
        view.loadUrl(url);
        frameLayout.setVisibility(View.VISIBLE);
        return true;

    }
}

private class MyAppWebViewClient extends WebViewClient {

    @Override
    public boolean shouldOverrideUrlLoading(WebView view, String url) {

        if(Uri.parse(url).getHost().endsWith("example.com")) {
            return false;
        }
        Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
        view.getContext().startActivity(intent);
        return true;
    }

}

@Override
public void onBackPressed() {
    if(wv.canGoBack()) {
        wv.goBack();
    } else {
        super.onBackPressed();
    }
}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.main, menu);
    return true;
}

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    // Handle action bar item clicks here. The action bar will
    // automatically handle clicks on the Home/Up button, so long
    // as you specify a parent activity in AndroidManifest.xml.
    int id = item.getItemId();

    //noinspection SimplifiableIfStatement


    return super.onOptionsItemSelected(item);
}

@SuppressWarnings("StatementWithEmptyBody")
@Override
public boolean onNavigationItemSelected(MenuItem item) {
    // Handle navigation view item clicks here.
    int id = item.getItemId();

    if (id == R.id.nav_home) {
        wv.loadUrl("example.com");

    } else if (id == R.id.nav_facebook) {

        try {
            Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse("fb://page/idfbpage"));
            startActivity(intent);
        } catch (Exception e) {
            Intent intent =  new Intent(Intent.ACTION_VIEW, Uri.parse("https://www.facebook.com/idfbpage"));
            startActivity(intent);
        }

    } else if (id == R.id.nav_instagram) {

        Uri uri = Uri.parse("http://instagram.com/_u/idinstapage");
        Intent likeIng = new Intent(Intent.ACTION_VIEW, uri);
        likeIng.setPackage("com.instagram.android");

        try {
            startActivity(likeIng);
        } catch (Exception e) {
            startActivity(new Intent(Intent.ACTION_VIEW, Uri.parse("http://instagram.com/idinstapage")));
        }

    } else if (id == R.id.nav_star) {

        Intent intent = new Intent(Intent.ACTION_VIEW);
        intent.setData(Uri.parse("market://details?id=idpackage"));
        startActivity(intent);

    } else if (id == R.id.nav_informazioni) {
        wv.loadUrl("example.com/info-app");

    }

    DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
    drawer.closeDrawer(GravityCompat.START);
    return true;
 }

}
0
NelloAscioneWeb 22 Окт 2017 в 13:09

3 ответа

Лучший ответ

В вашем методе LoadWeb() есть ошибка, потому что у вашего WebView должен быть только один WebViewClient и только один WebChromeClient. Так что, если вы используете метод wv.setWebViewClient(new YourWebViewClient()); более одного раза, то все остальные методы, заданные ранее, игнорируются, потому что вы можете установить его только один раз.

Для ваш случай:
Вы устанавливаете WebViewClient три (3) раза:

wv.setWebViewClient(new HelpClient());   //First time
wv.setWebViewClient(new MyAppWebViewClient());  //Second time

И в последний раз, когда вы устанавливаете его тем же методом, вы устанавливаете другой как:

wv.setWebViewClient(new WebViewClient(){

    public void onPageFinished(WebView view, String url){
        swipe.setRefreshing(false);
    }
});

Так что получается, что два предыдущих метода были проигнорированы, и единственный работающий метод был только последним (третьим). Вот почему я попросил вас перевести второй метод на setWebClient((new MyAppWebViewClient());, чтобы игнорировать предыдущий!

РЕШЕНИЕ
Теперь вы знаете, что мы должны установить только один WebViewClient для вашего webView, мы должны создать только ONE класс, который будет использоваться и выполнять работу всех трех других {{ X3}}, переопределив все необходимые методы. Сделайте этот класс внутри своей деятельности, но вытесните ваш метод any ( так же, как вы делали это при создании класса HelpClient () ). Вот наш класс Пожалуйста, убедитесь, что вы читаете комментарии в нем!

private class NewWebViewClient extends WebViewClient {
       //Now we have only one class to do a job of all the other three!

    @Override
    public void onPageFinished(WebView view, String url) {
        /*I here do whatever you want to do when the page has finished loading! Do it here inside this method and it will work may be control the framelayout visibility For example lets setRefreshing false to our swipe()*/
        swipe.setRefreshing(false);
        //.....add more methods you want here when the page loading is finished
    }

    @Override
    public boolean shouldOverrideUrlLoading(WebView view, String url) {
        /*In this method we are going to tell the android system what kind of link we want and what kind of link we dont want for that what we want we will handle for the extra the browser should do so!*/
        if (Uri.parse(url).getHost().endsWith("example.com")) {
            //if the code gets here this is your link then right? Lets do whatever we want with our link and logic for example lets set framelayout visible or doing anything this link's host is example.com!
            frameLayout.setVisibility(View.VISIBLE);
            return false;
        } else {
            //Ooops This link is not yours lets just open browsers right 
            Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
            view.getContext().startActivity(intent);
            return true;
        }

    }

}

После того, как ваш класс прекрасен, давайте просто установим WebViewClient только ОДИН РАЗ .

wv.setWebViewClient(new NewWebViewClient());

Вы можете просто игнорировать WebChromeClient, потому что вы устанавливаете его только тогда, когда вы хороши. Комментарий ниже, если вы обнаружите какие-либо трудности!

2
Xenolion 22 Окт 2017 в 15:48

Я надеюсь удалить эту строку

wv.setWebViewClient(new MyAppWebViewClient());

Решит проблему для вас.

0
clemens 22 Окт 2017 в 10:49

Вы используете два экземпляра WebViewClient, удалите один,

private class MyAppWebViewClient extends WebViewClient {

@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
    Log.d("TAG",url);
    if(Uri.parse(url).getHost().equals("example.com")) {
        return false;
    }
    Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
    view.getContext().startActivity(intent);//add the brakpoint here
    Log.d("TAG","Starting activity");
    return true;
}

}

Просто используйте это

0
himel 22 Окт 2017 в 11:04