Handling Back Button in a webView - android

I have an android project and I want to handle the back button in the fragment when I use the webview. When I use the webView and click on more than one link and then I click on back. It closes the application. How can I make it go to the back page. So far, I have done the followings :
public class NewsFragment extends Fragment {
private ProgressDialog progressDialog;
private WebView myWebView ;
public NewsFragment()
{
// Required empty public constructor
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View rootView = inflater.inflate(R.layout.fragment_news, container, false);
myWebView = (WebView) rootView.findViewById(R.id.mwl_Website);
myWebView.setWebViewClient(new WebViewClient());
myWebView.getSettings().setBuiltInZoomControls(true);
myWebView.requestFocusFromTouch();
myWebView.setVerticalScrollBarEnabled(true);
myWebView.setHorizontalScrollBarEnabled(true);
myWebView.setVerticalScrollBarEnabled(true);
myWebView.setHorizontalScrollBarEnabled(true);
myWebView.requestFocusFromTouch();
myWebView.getSettings().setJavaScriptEnabled(true);
myWebView.getSettings().setUseWideViewPort(true);
myWebView.getSettings().setLoadWithOverviewMode(true);
myWebView.addJavascriptInterface(new WebAppInterface(getActivity()), "Android");
myWebView.getSettings().setJavaScriptEnabled(true);
myWebView.loadUrl(getResources().getString(R.string.WEBSITE));
new LoadViewTask().execute();
rootView.setOnKeyListener(new View.OnKeyListener() {
#Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
if (event.getAction() == android.view.KeyEvent.ACTION_DOWN) {
if ((keyCode == android.view.KeyEvent.KEYCODE_BACK)) {
if(myWebView!=null)
{
if(myWebView.canGoBack())
{
myWebView.goBack();
}
}
}
}
return true;
}
});
return rootView;
}
private class LoadViewTask extends AsyncTask<Void, Integer, Void>
{
//Before running code in separate thread
#Override
protected void onPreExecute()
{
progressDialog = ProgressDialog.show(getActivity(),"Loading...",
"Loading please wait...", false, false);
}
//The code to be executed in a background thread.
#Override
protected Void doInBackground(Void... params)
{
/* This is just a code that delays the thread execution 4 times,
* during 850 milliseconds and updates the current progress. This
* is where the code that is going to be executed on a background
* thread must be placed.
*/
try
{
//Get the current thread's token
synchronized (this)
{
//Initialize an integer (that will act as a counter) to zero
int counter = 0;
//While the counter is smaller than four
while(counter <= 4)
{
//Wait 850 milliseconds
this.wait(1000);
//Increment the counter
counter++;
//Set the current progress.
//This value is going to be passed to the onProgressUpdate() method.
publishProgress(counter*25);
}
}
}
catch (InterruptedException e)
{
e.printStackTrace();
}
return null;
}
//Update the progress
#Override
protected void onProgressUpdate(Integer... values)
{
//set the current progress of the progress dialog
progressDialog.setProgress(values[0]);
}
//after executing the code in the thread
#Override
protected void onPostExecute(Void result)
{
//close the progress dialog
progressDialog.dismiss();
}
}

Problem you are facing is that your onBackPressed() is getting called, and you need to override that -
like this -
#Override
public void onBackPressed() {
if(myWebView!=null) {
if (webView.canGoBack()) {
webView.goBack();
}
}
super.onBackPressed();
}
Ref

Related

I want to be able to redirect the user to a specific link in a WebView

Need some advice. I want to be able to redirect the user to a specific link in WebView. Example: we go to the first link and if it directs us to "google.com" then we will have to direct the user to "http://test.com". I made an implementation, put a redirect in shouldOverrideUrlLoading, however, after SplashScreen-loading image done its work, a white background appears and that's it. At the same time, if you remove the code for redirection, then after performing its work, the SplashScreen - loading image, the first link opens and the page from the Internet is displayed correctly. How do I redirect to other pages after opening the first one?
public class MainActivity extends AppCompatActivity {
private WebView webView;
private final String TAG = "MainActivity";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
webView = findViewById(R.id.webView);
WebSettings webSettings = webView.getSettings();
webSettings.setJavaScriptEnabled(true);
webView.loadUrl("http://test/start");
new TaskForRedirecting().execute();
}
public class TaskForRedirecting extends AsyncTask<Boolean, Void, Boolean> {
#Override
protected void onPreExecute() {
super.onPreExecute();
}
#Override
protected Boolean doInBackground(Boolean... booleans) {
new Handler(Looper.getMainLooper()).post(new Runnable() {
#Override
public void run() {
Log.d(TAG, "Start loading here");
WebViewClient webViewClient = new WebViewClient() {
#Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (url.contains("google.com")) {
view.loadUrl("http://test1.com");
return false;
} else if (url.contains("yahoo.com")) {
view.loadUrl("http://test2.com");
return false;
} else {
}
return true;
}
#RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
if (request.getUrl().toString() == "google.com") {
view.loadUrl("http://test1.com");
view.loadUrl(request.getUrl().toString());
return false;
} else if (request.getUrl().toString() == "yahoo.com") {
view.loadUrl("http://test2.com");
return false;
}
return true;
}
};
webView.setWebViewClient(webViewClient);
Log.d(TAG, "Do in background: APP is Working!!!");
}
});
return false;
}
#Override
protected void onPostExecute(Boolean success) {
success = false;
if (success) {
Toast toast = Toast.makeText(MainActivity.this, "App is under maintenance!", Toast.LENGTH_SHORT);
toast.show();
} else {
Toast toast = Toast.makeText(MainActivity.this, "Let's start to work!", Toast.LENGTH_SHORT);
toast.show();
}
Log.d(TAG, "upload - final! ");
}
}
}
public class SplashScreenActivity extends AppCompatActivity {
long Delay = 6000;
private final String TAG = "SplashScreenActivity";
private WebView webView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
setContentView(R.layout.activity_splash_screen);
new SplashScreen().execute();
}
public class SplashScreen extends AsyncTask<Void, Void, Void> {
#Override
protected Void doInBackground(Void...voids) {
Timer RunSplash = new Timer();
TimerTask ShowSplash = new TimerTask() {
#Override
public void run() {
finish();
Intent intent = new Intent(SplashScreenActivity.this, MainActivity.class);
startActivity(intent);
}
};
RunSplash.schedule(ShowSplash, Delay);
Log.d(TAG, "ShowSplash - final! ");
return null;
}
}
}
Your implementation needs to change a bit, we don't need to set the webview client inside an AsyncTask, instead, we can set it directly but it should be set before we call loadurl.
I have removed the asynctask, and set the client in onCreate method before calling loadUrl.
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
webView = findViewById(R.id.webView);
WebSettings webSettings = webView.getSettings();
webSettings.setJavaScriptEnabled(true);
WebViewClient webViewClient = new WebViewClient() {
#Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (url.contains("google.com")) {
view.loadUrl("http://test1.com");
return true;
} else if (url.contains("yahoo.com")) {
view.loadUrl("http://test2.com");
return true;
}
return false;
}
#RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
if (request.getUrl().toString() == "google.com") {
view.loadUrl("http://test1.com");
return true;
} else if (request.getUrl().toString() == "yahoo.com") {
view.loadUrl("http://test2.com");
return true;
}
return false;
}
};
webView.setWebViewClient(webViewClient);
webView.loadUrl("http://test/start");
}
UPDATE
Please check out the shouldOverrideUrlLoading Doc, You should return true when you want to cancel the current load, so when you want to load a different URL, then return true else return false to continue the current load. Returning false means the URL which is being loaded to the webview will continue, your custom URL will not be loaded.

How to show ProgressDialog In Android Fragments?

I have some tabpages and fragments. And these fragments contain a GridView element. My program is going to webservice and reading JSON data, after getting images caching and populating gridviews custom grid.
Now, how can show ProgressDialog only not completed fragments? And how can I dismiss progressDialog GridView populating will complete?
My Fragment OnCreate Method;
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View v = inflater.inflate(R.layout.fragment_b, container, false);
context = getActivity();
final ProgressDialog dialog = ProgressDialog.show(context, "", "Please wait, Loading Page...", true);
GridView gridView = (GridView) v.findViewById(R.id.gridview);
if (isConnected()) {
try {
new ProgressTask(context).execute();
gridView.setAdapter(new AdapterB(context, WallPaperList));
} catch (NullPointerException e) {
e.printStackTrace();
return v;
}
} else {
Toast.makeText(v.getContext(), "Please check your internet connection..!", Toast.LENGTH_LONG).show();
}
return v;
}
its the short example for showing progress may this help you
private class DownloadImageTask extends AsyncTask<String, Void, Bitmap> {
#Override
protected void onPreExecute() {
super.onPreExecute();
progressDialog = ProgressDialog.show(DownloadImageActivity.this, "Wait", "Downloading...");
}
#Override
protected Bitmap doInBackground(String... params) {
//your downloading code
}
/**
* After completing background task Dismiss the progress dialog
* **/
protected void onPostExecute(Bitmap bitmap) {
progressDialog.dismiss();
}
}
Check this...........
public interface AsyncTaskListener<Boolean> {
public void onCompletingTask(Boolean result);
}
public class AsyncTaskGetApiKey extends AsyncTask<Void, Void, Boolean>{
ArrayList<AsyncTaskListener<Boolean>> listeners;
public AsyncTaskLoadingInSplash() {
listeners = new ArrayList<AsyncTaskListener<Boolean>>();
}
public void addListener(AsyncTaskListener<Boolean> listener){
listeners.add(listener);
}
public void removeListener(AsyncTaskListener<Boolean> listener){
listeners.remove(listener);
}
#Override
protected Boolean doInBackground(Void... params) {
//do your activities here
return true; // If everything is fine
}
#Override
protected void onPostExecute(Boolean result) {
// TODO Auto-generated method stub
super.onPostExecute(result);
for (AsyncTaskListener<Boolean> listener:listeners) {
listener.onReceivingApiKey(result);
}
}
}
public class MyFagemnt extends Fragment
implements AsyncTaskListener<Boolean>{
AsyncTaskGetApiKey task;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
//......
task = new AsyncTaskGetApiKey();
task.addListener(this);
//........
}
#Override
public void onCompletingTask(Boolean result) {
// your asyntask finished
// now close the progress bar
}
}
In AsyncTask, create progress dialog in onPreExecute() and dismiss that progress dialog in onPostExecute().
updated:
add this code in your viewpager activity.
viewPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {
#Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
#Override
public void onPageSelected(int position) {
//You can get Call back to show the progress dialog when swipping.
boolean isLoading = true;//Check if the fragment is still loading or not at given position.
if (isLoading) {
//Show progress dialog.
}
}
#Override
public void onPageScrollStateChanged(int state) {
}
});

Force close when press back while fetching data from internet

Whenever user press back button While fetching xml data from web using AsyncTask my app goes to force close state. How can i solve this. Thanks in advance.
public class InboxActivity extends Activity {
public static ExpandableListView mailList;
List<HashMap<String,String>> list;
MailList asyncTaskMailList;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.inbox_layout);
ConstantValues.footerCurrentActivity=InboxActivity.this;
mailList=(ExpandableListView)findViewById(R.id.expandableListView1);
HomePageActivity.homePageTabHost.getTabWidget().getChildTabViewAt(ConstantValues.CURRENT_POSITION)
.setBackgroundDrawable(getResources().getDrawable(R.drawable.tab_widget_normal));
asyncTaskMailList=new MailList();
asyncTaskMailList.execute();
}
private OnChildClickListener childClickListener=new ExpandableListView.OnChildClickListener() {
public boolean onChildClick(ExpandableListView parent, View v,int groupPosition, int childPosition, long id) {
ConstantValues.STATION_NAME=ConstantValues.inboxStations.get(groupPosition);
ConstantValues.CURRENT_POSITION=1;
startActivity(new Intent(InboxActivity.this, HomePageActivity.class));
return false;
}
};
#Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if(keyCode == KeyEvent.KEYCODE_BACK){
this.getParent().onBackPressed();
asyncTaskMailList.cancel(true);
return true;
}
return super.onKeyDown(keyCode, event);
}
#Override
protected void onStop() {
super.onStop();
asyncTaskMailList.cancel(true);
}
#Override
protected void onDestroy() {
asyncTaskMailList.cancel(true);
super.onDestroy();
}
class MailList extends AsyncTask<String, String, String>
{
#Override
protected void onPreExecute() {
super.onPreExecute();
NetworkExceptionPopUp.showProgressBar();
}
#Override
protected String doInBackground(String... params) {
list=new ArrayList<HashMap<String,String>>();
WebServerCall.getInboxMail(InboxActivity.this);
return null;
}
#Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
mailList.setAdapter(new InboxAdapter(InboxActivity.this));
NetworkExceptionPopUp.dismissProgressBar();
mailList.setOnGroupClickListener(null);
mailList.setOnChildClickListener(childClickListener);
mailList.setClickable(true);
}
}
}
Above code is my updated code. This also sometime shows exception. Here, I had used onStop() and OnDestroy() to cancel AsyncTask while other activity comes top.
#Override
protected void onPreExecute() {
super.onPreExecute();
NetworkExceptionPopUp.showProgressBar();
/** add this line to your progressDialog so that diaolg as well your background operation wont stop in intermediate state. */
// pd.setCancelable(false);
}
So now when you will click back button Dialog will not dismiss.
Hope this help for you.
private MailList task;
#Override
public void onCreate(Bundle savedInstanceState) {
...
task = new MailList().execute();
...
}
#Override
public void onBackPressed() {
if (task != null && task.getStatus() == AsyncTask.Status.RUNNING) {
task.cancel(true);
}
...
}
...

In Android Webview comment box is not displaying fully

Here is my Code:
public class SampleFB1Activity extends Activity {
WebView web2,childView =null;
private LinearLayout parentLayout;
private Activity MyActivity;
private String requestUrl="http://example.com/test.html";
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
this.getWindow().requestFeature(Window.FEATURE_PROGRESS);
setContentView(R.layout.main);
getWindow().setFeatureInt(Window.FEATURE_PROGRESS,Window.PROGRESS_VISIBILITY_ON);
parentLayout =(LinearLayout)findViewById(R.id.parentlayout);
MyActivity = this;
web2 = new WebView(this);
web2.setLayoutParams(getLayoutParams());
web2.setWebViewClient(new FaceBookClient());
web2.setWebChromeClient(new MyChromeClient());
web2.getSettings().setJavaScriptEnabled(true);
web2.getSettings().setAppCacheEnabled(true);
web2.getSettings().setJavaScriptCanOpenWindowsAutomatically(true);
web2.getSettings().setSupportMultipleWindows(true);
web2.getSettings().setSupportZoom(true);
web2.getSettings().setBuiltInZoomControls(true);
parentLayout.addView(web2);
web2.loadUrl(requestUrl);
}
private LayoutParams getLayoutParams() {
// TODO Auto-generated method stub
return new LinearLayout.LayoutParams(LayoutParams.FILL_PARENT,LayoutParams.FILL_PARENT);
}
final class MyChromeClient extends WebChromeClient{
#Override
public boolean onCreateWindow(WebView view, boolean dialog,
boolean userGesture, Message resultMsg) {
childView = new WebView(SampleFB1Activity.this);
childView.getSettings().setJavaScriptEnabled(true);
childView.getSettings().setSupportZoom(true);
childView.getSettings().setBuiltInZoomControls(true);
childView.setWebViewClient(new FaceBookClient());
childView.setWebChromeClient(this);
childView.setLayoutParams(new LinearLayout.LayoutParams(LayoutParams.FILL_PARENT,LayoutParams.FILL_PARENT));
parentLayout.addView(childView);
childView.requestFocus();
web2.setVisibility(View.GONE);
WebView.WebViewTransport transport =(WebView.WebViewTransport)resultMsg.obj;
transport.setWebView(childView);
resultMsg.sendToTarget();
return true;
}
#Override
public void onProgressChanged(WebView view, int newProgress) {
MyActivity.setProgress(newProgress*100);
}
#Override
public void onCloseWindow(WebView window) {
parentLayout.removeViewAt(parentLayout.getChildCount()-1);
childView =null;
web2.setVisibility(View.VISIBLE);
web2.requestFocus();
}
}
private class FaceBookClient extends WebViewClient{
#Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
Log.i("REQUEST URL",url);
return false;
}
}
#Override
public void onBackPressed() {
if(childView != null && parentLayout.getChildCount()==2){
childView.stopLoading();
parentLayout.removeViewAt(parentLayout.getChildCount()-1);
if(web2.getVisibility() == View.GONE)
web2.setVisibility(View.VISIBLE);
}else{
super.onBackPressed();
}
}
In version 3 I am able to see only half comment box and in 4 instead of comment box
it is showing button (Login to facebook to post comment) but will not display comment box.
Please help...

progressBar and refresh webview combination android

EDIT:
I am using a ProgressBar for a Webview that works fine. Now I want to refresh my Webview, which also works. When I am trying to combine them, the Spinner doesn't end at all. This is my code:
private final Runnable m_Runnable = new Runnable()
{
public void run()
{
//Toast.makeText(WebcamsScreen.this,"in runnable",Toast.LENGTH_SHORT).show();
doRefreshingStuff(id);
WebcamsScreen.this.mHandler.postDelayed(m_Runnable, 20000);
}
};
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//initialitions
doRefreshingStuff(id);
this.mHandler = new Handler();
this.mHandler.postDelayed(m_Runnable,20000);
doRefreshingStuff(id);
}
public void doRefreshingStuff(String id){
setContentView(R.layout.web4);
webView7 = (WebView) findViewById(R.id.web_4_1);
webView7.getSettings().setJavaScriptEnabled(true);
webView7.getSettings().setJavaScriptEnabled(true);
progressBar = ProgressDialog.show(WebcamsScreen.this, "example", "...");
url="my url";
webView7.setWebViewClient(new WebViewClient() {
public boolean shouldOverrideUrlLoading(WebView view, String url1) {
view.loadUrl(url1);
return true;
}
public void onPageFinished(WebView view, String url1) {
if (progressBar.isShowing()) {
progressBar.dismiss();
}
}
});
webView7.loadUrl(url);
what must I change?
It looks like you are refreshing your WebView every 20 seconds and popping up a new progress dialog when you do. Your code assumes that the old progress dialog has already been dismissed. If it hasn't, then the progress dialog just became orphaned and will remain on display forever. You can probably fix this by inserting this code:
if (progressBar != null && progressBar.isShowing()) {
progressBar.dismiss();
}
just before the line progressBar = ....
But I wouldn't fix your code that way. You are doing a huge amount of work that you don't need to do. (For instance, you don't need to reload the same content view.) Here's my revised version:
private final Runnable m_Runnable = new Runnable() {
public void run() {
doRefreshingStuff(id);
mHandler.postDelayed(m_Runnable, 20000);
}
};
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//initialitions
setContentView(R.layout.web4);
webView7 = (WebView) findViewById(R.id.web_4_1);
webView7.getSettings().setJavaScriptEnabled(true);
webView7.getSettings().setJavaScriptEnabled(true);
webView7.setWebViewClient(new WebViewClient() {
public void onPageStarted(WebView view, String url, Bitmap favicon) {
if (!mProgressBar.isShowing()) {
mProgressBar.show();
}
}
public void onPageFinished(WebView view, String url1) {
if (mProgressBar.isShowing()) {
mProgressBar.dismiss();
}
}
});
mProgressBar = new ProgressDialog(this);
mProgressBar.setTitle("example");
mProgressBar.setMessage("...");
mHandler = new Handler();
}
protected void onResume() {
super.onResume();
mHandler.post(m_Runnable);
}
protected void onPause() {
super.onPause();
mHandler.removeCallbacks(m_Runnable);
}
public void doRefreshingStuff(String id) {
url="my url";
webView7.loadUrl(url);
}
Note that I moved the starting of the page loading loop to onResume() and kill the looping in onPause(). You may want slightly different logic, but you should definitely stop looping somehow when your activity pauses or finishes.

Categories

Resources