Open url in another application or in browser [Titanium] - android

I am writing a functionality that needs to open a URL either in the another app [if installed in my phone] or else, in the browser.
To open the URL in browser, I can use Titanium.Platefor.openURL();
To open the app I am creating the intent.
var intent = Titanium.Android.createIntent({
packageName : appUrl,
action : Titanium.Android.ACTION_SEND,
data : url
});
intent.addCategory(Titanium.Android.CATEGORY_BROWSABLE);
Titanium.Android.currentActivity.startActivity(intent);
I have stuck in below things:
How to pass the url to other app to open - I tried passing url using url : 'http://someurl' and data: 'http://someurl' - but didn't help. I got the error: No Activity found to handle Intent
How to find out whether the app is install or not? If yes - ask for the application to open, if no - open the url in browser.
Can anyone help?
Thanks in advance!

You can identify app is install or not using URL schema with Titanium.Platefor.openURL(); method in android. (if app is not installed it will return false).
and for ios there is one method for identify Titanium.Platform.canOpenURL().
and also you can passed something value to application for example if you open google map application with source and destination lat long in ios then call like this
var strUrl = "http://maps.google.com/maps?saddr=" + Alloy.Globals.UserLocation.latitude + "," + Alloy.Globals.UserLocation.longitude + "&daddr=" + dLatitude + "," + dLongitude;
if (OS_IOS) {
strUrl = "comgooglemaps://?saddr=" + Alloy.Globals.UserLocation.latitude + "," + Alloy.Globals.UserLocation.longitude + "&daddr=" + dLatitude + "," + dLongitude + "&directionsmode=driving";
if (Titanium.Platform.canOpenURL(strUrl)) {
Ti.Platform.openURL(strUrl);
} else {
strUrl = "http://maps.google.com/maps?saddr=" + Alloy.Globals.UserLocation.latitude + "," + Alloy.Globals.UserLocation.longitude + "&daddr=" + dLatitude + "," + dLongitude;
Ti.Platform.openURL(strUrl);
}
} else {
var result = Ti.Platform.openURL(strUrl);
Ti.API.info('RESULT = ' + result);
}
one more example.. if you want opening whatsApp application with given message text.
var whatsappUrl = encodeURI('whatsapp://send?text=' + msgBody);
if (OS_IOS) {
if (Ti.Platform.canOpenURL(whatsappUrl)) {
Ti.Platform.openURL(whatsappUrl);
} else {
Ti.Platform.openURL("https://itunes.apple.com/ae/app/whatsapp-messenger/id310633997?mt=8");
}
} else {
var isSuccess = Ti.Platform.openURL(whatsappUrl);
if (!isSuccess) {
Ti.Platform.openURL("https://play.google.com/store/apps/details?id=com.whatsapp&hl=en");
}
}
Hop this is helps you.. :)
Thanks

Related

scheme call from JS (web browser) to android activity doesn't update the intent with the scheme data in the url string

I am launching my app from the browser and if the app is not already loaded/running then it launches the app through onCreate and collects the intent.data and does the right thing. If the app is already running then launching the app from the browser bypasses the onCreate and goes right to onResume which I "believe" is expected behavior. But the intent.data associated with the launch from the browser is null. I was hoping that the intent data would be overwritten with the new intent data from scheme url string so that I can relaunch the webview inside the app with the new parameters. Is there some way that I can push this new data into the app when it is launched (i.e., resumed) by the browser?
// JS Browser code with arguments to be passed to the app.
var r = Math.random();
window.open("myScheme://caca.com/?mode=driver" + "&ec=" + ec + "&uh=" + $("#userHandle").val() + "&at=0" + "&random=" + r);
// Xamarin
onResume(...) {
...
try
{
// currentActivity.Intent.Data != null if app is not already running
// is null if already running
Android.Net.Uri data = currentActivity.Intent.Data;
string scheme = data.Scheme;
DebugToast("scheme " + scheme, ToastLength.Long);
if (scheme == "myScheme")
{
// force the cookies so the web app will come up as we specify
SetStorageValue("browserLaunched", "true");
SetStorageValue("mode", data.GetQueryParameter("mode"));
SetStorageValue("ec", data.GetQueryParameter("ec"));
SetStorageValue("uh", data.GetQueryParameter("uh"));
SetStorageValue("authToken", data.GetQueryParameter("at"));
SetStorageValue("at", data.GetQueryParameter("at"));
DebugToast("parms " + data.GetQueryParameter("mode") + " " + data.GetQueryParameter("ec") + " " + data.GetQueryParameter("uh") + " " + data.GetQueryParameter("at"), ToastLength.Long);
// restart the web view with arguments above
...
}
}
catch
{
....
}
}
Homer Simpson D'oh!. Needed to add 'onNewIntent()' to activity which receives the "um er dah" new Intent with the appropriate data attached.

Is API Key Required for Direction Apis Android

I am using below code to get directions to a particular lat & lng using google api. But I have not used the api key. This app which I am making will soon be pushed to playstore. I just want to make sure what I am doing here is correct or will it cause any problem for me ?
Thanks in advance :)
if (pc.getLatitude() != null && pc.getLongitude() != null) {
double latitude = Double.parseDouble(pc.getLatitude());
double longitude = Double.parseDouble(pc.getLongitude());
String uri = String.format(Locale.ENGLISH, "http://maps.google.com/maps?daddr=%f,%f (%s)", latitude, longitude, "Location");
Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(uri));
intent.setClassName("com.google.android.apps.maps", "com.google.android.maps.MapsActivity");
if (intent.resolveActivity(mContext.getPackageManager()) != null) {
Toast.makeText(mContext, R.string.toast_opening_google_maps, Toast.LENGTH_SHORT).show();
mContext.startActivity(intent);
} else {
Toast.makeText(mContext, R.string.toast_no_google_maps_warning, Toast.LENGTH_SHORT).show();
}
} else {
Toast.makeText(mContext, R.string.toast_no_ll_warning, Toast.LENGTH_LONG).show();
}
This is one more example of my api usage
String distanceUrl = "http://maps.googleapis.com/maps/api/distancematrix/json?" +
"origins=" + mOriginLatLng.latitude + "," + mOriginLatLng.longitude +
"&destinations=" + destination.latitude + "," + destination.longitude +
"&mode=driving&language=en-EN&sensor=false";
According to the documentation, you don't need an API key to launch Google Maps using an Intent.
According to the documentation, you will need an API key to use the Distance Matrix API.

monitor web browser programmatically in Android?

I've got a tricky question here. I need users to make a payment to a bank (namely Barclaycard) in UK. To do so, I have a https URL , I add the parameters (such as amount to pay, order reference, etc) to the URL, start this http connection as an Intent.ActionView, which will redirect the user to the browser where he can enter his credit card details on the bank's webpage and make the payment to our account successfully. So far so good ?
The code I use is below (I changed values for privacy reasons) The problem is, I need to get back to the app when the user has completed/failed/cancelled the payment. Barclaycardautomatically redirects to a particular URL when the payment has succeeded, another one if it failed. Is there no way of knowing when Barclaycard payment has succeeded so that then I would go back to the android app somehow ?
Button cardbutton = (Button) findViewById(R.id.card_button);
cardbutton.setOnClickListener(new View.OnClickListener()
{
#Override
public void onClick(View arg0)
{
String preHashString = new String();
String proHashString = new String();
String SHAPassPhrase = new String();
SHAPassPhrase = "GSvTh£h70ZkHdAq9b"; // FOR TEST ENVIRONMENT
preHashString = preHashString + "AMOUNT=" + String.valueOf((int) (order.getPaymentAmount() * 100.00)) + SHAPassPhrase;
preHashString = preHashString + "BGCOLOR=cccccc" + SHAPassPhrase;
preHashString = preHashString + "CN=" + user.getString("name") + SHAPassPhrase;
preHashString = preHashString + "CURRENCY=GBP" + SHAPassPhrase;
preHashString = preHashString + "LANGUAGE=en_US" + SHAPassPhrase;
preHashString = preHashString + "ORDERID=" + order.getOrderId() + SHAPassPhrase;
try
{
proHashString = SHA1(preHashString);
}
catch (NoSuchAlgorithmException e)
{
e.printStackTrace();
}
catch (UnsupportedEncodingException e)
{
e.printStackTrace();
}
String redirecturl = "https://mdepayments.epdq.co.uk/ncol/test/orderstandard.asp";
redirecturl += "?AMOUNT=" + String.valueOf((int) (order.getPaymentAmount() * 100));
redirecturl += "&CN=" + user.getString("name");
redirecturl += "&CURRENCY=GBP";
redirecturl += "&LANGUAGE=en_US";
redirecturl += "&ORDERID=" + order.getOrderId();
redirecturl += "&SHASIGN=" + proHashString;
Intent i = new Intent(Intent.ACTION_VIEW, Uri.parse(redirecturl));
startActivity(i);
}
});
You can have your own Webview in place inside your app, with some done / close button somewhere.. Then you can track all urls getting open in your WebView and do your stuff accordingly..User will stay in your app always..that solves your purpose..
For tracking all urls inside your WebView you need to register one WebViewClient and ovveride below function
public boolean shouldOverrideUrlLoading (WebView view, String url)
Have a look at WebView here and WebViewClient here
You should never be doing such things on user device. Someone can decompile your code and change it, so your app will "think" they made the payment.
This may lead to small problems like they using app for free to severe problems like you being forced to make all the payments.
Either use server-side solution or in-app-purchase from Google.
If your user gets redirected to a new URL you could use a ContentObserver that observes the bookmark history for any changes:
public class UrlObserver extends ContentObserver {
#Override
public void onChange(boolean selfChange) {
super.onChange(selfChange);
// check last URL in history
}
}
Reading the history can be done by:
private static final Uri CONTENT_URI = Browser.BOOKMARKS_URI;
Cursor cursor = context.getContentResolver().query(
CONTENT_URI, Browser.HISTORY_PROJECTION, null, null, null);
Registration of the content observer works with:
UrlObserver observer = new UrlObserver();
context.getContentResolver().registerContentObserver(CONTENT_URI, true, observer);
Once a particular URL has been detected, you can invoke an intent to bring your activity back to front.
This is a sample app which might help you in this case.
I'm not 100% sure what happens if the same site is used for the form transmission. It might be that the content observer won't trigger. In that case you might find some useful log entries.
Note: Chrome and the Android standard browser use different URLs for the query. Search the internet to find the right one.
Hope this helps .... Cheers!

FB.api('/me') always giving error code:2500 in phonegap android

I am using facebook plugin to login and logout a user, which are working fine. The problem is when I request for the logged in user details using the function FB.api('/me'), it always gives the following error:
{"message":"An active access token must be used to query information about the current user.","type":"OAuthException","code":2500}
I used the debug mode to check PluginResult(pr) and JSONObject of the response. JSONObject contains the user information, which I required, I dont get where I am doing wrong.
Plz help......
MY CODE:
function login() {
FB.login(function(response) {
if (response.session) {
console.log('Welcome! Fetching your information.... ');
FB.api('/me', function(response) {
console.log('Good to see you, ' + JSON.stringify(response) + '.');
});
} else {
console.log('User cancelled login or did not fully authorize.');
}
},{scope: 'email,user_likes'});
}
function logout() {
FB.logout(function(response) {
console.log(localStorage.getItem("user_fb_log_status"));
localStorage.setItem("user_fb_log_status","LOGGED_OUT");
alert('logged out');
});
}
The above code is working fine to login and logout the user. Below is the code i used to get the user details,
function me() {
FB.api('/me', { fields: 'id, name, picture' }, function(response) {
if (response.error) {
alert(JSON.stringify(response.error));
} else {
var data = document.getElementById('data');
fdata=response.data;
console.log("fdata: "+fdata);
response.data.forEach(function(item) {
var d = document.createElement('div');
d.innerHTML = "<img src="+item.picture+"/>"+item.name;
data.appendChild(d);
});
}
});
}
You need access token to retrieve more details than basic user information. Check that whether you have correct access token in Debug Tool to and ensure that you have all require permissions set permission.
Problem solved after changing the "session" in 'getResponse' method in ConnectPlugin to "authResponse"
FB.api method is working fine for me to get the user details and post a feed to the facebook after I change the following method in ConnectPlugin.java as following.
public JSONObject getResponse() {
String response = "{" + "\"status\": \""
+ (facebook.isSessionValid() ? "connected" : "unknown") + "\","
+
// "\"session\": {" + "\"access_token\": \""
// + facebook.getAccessToken() + "\"," + "\"expires\": \""
// + facebook.getAccessExpires() + "\","
// + "\"session_key\": true," + "\"sig\": \"...\","
// + "\"uid\": \"" + this.userId + "\"" +
"\"authResponse\": {" +
"\"accessToken\": \"" + facebook.getAccessToken() + "\"," +
"\"expiresIn\": \"" + facebook.getAccessExpires() + "\"," +
"\"session_key\": true," +
"\"sig\": \"...\"," +
"\"userId\": \"" + this.userId + "\"" +
"}" + "}";
try {
return new JSONObject(response);
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return new JSONObject();
}

Facebook chat - X-FACEBOOK-PLATFORM authentication

I want to build an XMPP client on android, I've got it running perfect with authentication using Digest-MD-5, however when I try to convert it to X-FACEBOOK-PLATFORM it keeps failing.
So basically the X-FACEBOOK-PLATFORM authentication uses only a part of a access token. That is called the session key.
The access token is seperated by "|" characters, so you split the access token and only take the characters that are in the center. Refer below.
******|a681464febcefb8*-**|******
long callId = new GregorianCalendar().getTimeInMillis() / 1000L;
String sig = "api_key=" + apiKey
+ "call_id=" + callId
+ "method=" + method
+ "nonce=" + nonce
+ "session_key=" + sessionKey
+ "v=" + version
+ appSecret;
try {
sig = MD5(sig);
}
catch (NoSuchAlgorithmException e) {
throw new IllegalStateException(e);
}
String composedResponse = "api_key=" + URLEncoder.encode(apiKey, "utf-8")
+ "&call_id=" + callId
+ "&method=" + URLEncoder.encode(method, "utf-8")
+ "&nonce=" + URLEncoder.encode(nonce, "utf-8")
+ "&session_key=" + URLEncoder.encode(sessionKey, "utf-8")
+ "&v=" + URLEncoder.encode(version, "utf-8")
+ "&sig=" + URLEncoder.encode(sig, "utf-8");
I never got FB chat to work with my appSecret but used sessionSecret instead. You can get it using oldish REST API.
http://developers.facebook.com/docs/reference/rest/auth.promoteSession/
This way you can keep your appSecret as a secret. Also it's worth noticing X-FACEBOOK-PLATFORM authentication rarely succeeds on first try but requires 3-6 retries usually. Beats me why though as I'm using same session key and secret..

Categories

Resources