I do not use ksoap2
The callings must be asynchronously because other way honeycomb does not accept and it throws this exception http://developer.android.com/reference/android/os/NetworkOnMainThreadException.html
I am deriving the codes from .NET and Android has a very different architecturing than .NET. because of this when you leave comment please take notice of this fact.
In code block I will call different webmethods at least 5 or 6 times.
the code structure goes like this
public void X(){
int a = webMethodA();
. doSomethingWith a
.
.
b = webMethodB(a);
.
. doSomethingWith b
.
.
c = webMethod(b);
.
.
.
}
I tried to make it using with asyncTask and Handler, I could take result value but the problem is I could not handle the result value on X method. I have to use return values in X method block
For .net datasets it is better to store your data in your self designed Object collections that can be same in Webservice and android.
for example define class Person in webservice and Android which are same and deliver it.
you can use json in .Net and Android to serialize and deserialize your objects to a json string instead of using .Net xml.
for threading is this code your answer?
protected void btnCallWebservice_onClick() {
final Runnable r = new Runnable()
{
public void run()
{
threadWebservice();
}
};
performOnBackgroundThread(r);
}
public Thread performOnBackgroundThread(final Runnable runnable) {
final Thread t = new Thread() {
#Override
public void run() {
try {
runnable.run();
} finally {
}
}
};
t.start();
return t;
}
private void threadWebservice() {
try {
// call your webservice here
} catch (final Exception e) {
}
}
Related
In android, there are many async APIs such as WebView's evaluateJavascript, which will Asynchronously evaluates JavaScript in the context of the currently displayed page. Usually an execution will just proceed to the successive statements after the call of an async API without any waiting.
But how can I wait until this call finishes its executing, before proceeding to the successive statements. For example,
webview.evaluateJavascript("JS code", new ValueCallback<String> {
public void onReceiveValue(String value) {
//get JS return here
}
});
//Remaining code
How can I make sure the remaining code is executed after webview.evaluateJavascript has finished its executing (i.e., its callback onReceiveValue has finished its executing).
Edit: To be more precise, what I want is that remaining code should be executed after onReceiveValue has finished executing.
I find out a workaround by using JavaScript interface. The idea is that we create a bridge class that contains a method that takes the javascript execution result as input. Then we can obtain the result at the Java end. This method works because bridge methods are invoked by JavaScript code, which is run on another thread. We only need to wait on the UI thread for a little milliseconds, then the result is here for you. The following code is an illustration:
class Bridge {
public String result = null;
#JavascriptInterface
public void putJsResult(String result) {
this.result = result;
}
public String getJsResult() {
return this.result;
}
}
Bridge bridge = new Bridge();
wv.addJavascriptInterface(bridge, "bridge");
webview.evaluateJavascript("bridge.putJsResult(func())", null);
Thread.sleep(100);
//Result is there
String result = bridge.getJsResult();
When you have to wait for code execution, a simple class to use is CountDownLatch.
An example for your problem can be:
public class AboutActivity extends Activity {
private volatile CountDownLatch jsLatch = new CountDownLatch(1);
private volatile String jsReceivedValue = null
initWebView() {
// webview init
...
webview.evaluateJavascript("JS code", new ValueCallback<String> {
public void onReceiveValue(String value) {
//get JS return here
jsReceivedValue = value
jsLatch.countDown();
}
});
try {
// wait 60 seconds or assume there was some problem during the loading
jsLatch.await(60, TimeUnit.SECONDS);
} catch (InterruptedException e) {
// thread interrupted or time elapsed
}
if (jsReceivedValue == null) {
// show "problem during loading"
} else {
//Remaining code
}
}
}
Note that waiting for code execution on main thread, can lead to unresponsive app.
You can show a loading spinner while using a simple thread to avoid this:
new Thread(new Runnable() {
#Override
public void run() {
initWebView();
}
}).start();
I have two or more network calls in separated threads on main activity start, I want to show all data after network threads done.
Thread firstNetworkCallThread=new Thread(new Runnable() {
#Override
public void run() {
// network calls and get data...
}
});
Thread secondNetworkCallThread =new Thread(new Runnable() {
#Override
public void run() {
// network calls and get data...
}
});
firstNetworkCallThread.start();
secondNetworkCallThread.start();
I want these threads work parallel, and when both of them are complete, call new event to show data.
How can I do this?
Guava has a good solution for this. If you convert your Threads to ListenableFutures (also a Guava object) you can create a list of ListenableFutures and add a callback to that list.
Futures.addCallback(
Futures.allAsList(/*future1*/, /*future2*/, /*future3*/),
new AbstractDisposableFutureCallback<List<Object>>() {
#Override
protected void onSuccessfulResult(List<Object> results) {
// whatever should happen on success
}
#Override
protected void onNonCancellationFailure(Throwable throwable) {
// whatever should happen on failure
}
});
Guava also has a bunch methods such as #successfulAsList which only contains successful results or #inCompletionOrder which orders them based on when they completed and a bunch of others.
I generally tend to use Guava as it provides a fairly clean solutions to problems like these.
An example of how to creates a ListenableFuture is as follows:
ListeningExecutorService service = MoreExecutors.listeningDecorator(Executors.newFixedThreadPool(10));
ListenableFuture<Object> explosion =
service.submit(
new Callable<Object>() {
public Object call() {
// get network data
return null; // return the data
}
});
I'm building a simple Android Application. I want to parse JSON. I have everything working using Button. But I want call it without using Button. It need to be get the JSON first from url and then Parse it. I have function getJson() and parseJSON(). First I want getJSON to be called and after 5 second parseJSON(). here is my code:
Runnable[] methods = new Runnable[]{
new Runnable() {
#Override
public void run() {
Toast.makeText(SheduleActivity.this, "This is gettin JSON", Toast.LENGTH_LONG).show();
getJSON();
}
},
new Runnable() {
#Override
public void run() {
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
},
new Runnable() {
#Override
public void run() {
Toast.makeText(SheduleActivity.this, "This is Parsing JSON", Toast.LENGTH_LONG).show();
parseJSON();
}
}
};
for(Runnable r : methods)
//r.run();
service.submit(r);
service.shutdown();
while (!service.isTerminated()) {}
Toast.makeText(SheduleActivity.this,"Finished all threads", Toast.LENGTH_LONG).show();
Everytime I run my app only getJSON() method calls and stops. Any suggetions?
I think you need to use AsyncTask. put getJson() in doInBackground block and parseJSON() on onPostExecute block. hope this help.
Android does not suggest to use sleep(5000) for delay. Use handler to do this. See the documentation of Handler.
For example in your code,
Handler handler = new Handler( /* --- */ );
handler.postDelayed(methods[i], 5000);
Also for getting json from web, it is suggested to use Asynctask to make the UI responsive. Best tutorial for Asynctask is here.
I'm currently developing a game for android. This game has heavy networking.
Is it better to have two separate threads, one for receiving messages and the other for sending messages. Or is it better to have a single thread for sending and receiving messages?
public static void init(String h){
host=h;
connected=false;
instance = new Client();
new Thread(new Runnable() {
#Override
public void run() {
group = new NioEventLoopGroup();
try{
bootstrap = new Bootstrap()
.group(group)
.channel(NioSocketChannel.class)
.handler(instance);
channel = bootstrap.connect(host,PORT).sync().channel();
connected=true;
} catch (Exception e) {
if (notifier!=null){
notifier.onServerNoLongerReachable();
}
e.printStackTrace();
}
}
}).start();
}
public static void setNotifier(ClientInterface notif){
notifier = notif;
}
I'm using Netty and I have a custom interface that my activities implement
public interface ClientInterface{
void onReceive(String msg);
void onServerNoLongerReachable();
}
Using Thread is NOT a good practice for Android Dev.
Use Asynctask is better : https://developer.android.com/guide/components/processes-and-threads.html
Or as Cricket_007 you should take a look at RxJava : https://github.com/ReactiveX/RxAndroid
For networkCall, you could use Retrofit w/ RxJava:
http://square.github.io/retrofit/
I have listed of products with different category. I have to sort them. Because of the queries, It is taking more time to load. Between two activities, the screen is coming black. I want to run the query in the background. How can I do that and how to use its result in main activity?
private class InsertTask extends AsyncTask {
String cat;
#Override
protected void onPreExecute() {
super.onPreExecute();
}
#Override
protected Boolean doInBackground(String... params) {
Boolean success = false;
try {
category(cat);
success = true;
} catch (Exception e) {
if(e.getMessage()!=null)
e.printStackTrace();
}
return success;
}
#Override
protected void onPostExecute(Boolean success) {
super.onPostExecute(success);
}
private void category(String category) {
try{
Cursor1 = mDbHelper.fetchcategory(category);
}catch(Exception e){
Log.v("Excep", ""+e);
}
}
And when called
InsertTask task = new InsertTask();
task.execute();
I have listed the category in buttons. How can I get the values then?
You should use AsyncTask for that. And some more info.
Its good you have thought of AsyncTask. Firstly, you can declare this class as inner in you class activity (if you haven't previously did) and so you are able to access you view class members.
You can do this also by creating thread and one handler that will be used to update your UI components. Remember that if you use threads you'll need to lock/unlock your database object because of the thread safety(if any other thread is accessing the database for any reason). Read more about thread safety of dbs.
I was doing some searching myself, and I came across this read, its rather long but looks extremely helpful, with lots of code examples. (I bookmarked it for myself).
Threads, Async, and Handlers O MY!
But some form of threading is the ticket.
From Android dev.
(My favorite code snippet)
public void onClick(View v) {
new Thread(new Runnable() {
public void run() {
//Do Work here
}
}).start();
}