This book teaches anyone with a basic understanding of Java how to develop Android apps at a professional level.
The official site for Android developers. Provides the Android SDK and documentation for app developers and designers.
Murach's Android Programming
This book teaches anyone with a basic understanding of Java how to develop Android apps at a professional level.
Windows firewall block Remote Desktop connection - solved
It's found that Windows firewall block the remote desktop connection. To fix it:
- Search setting of "firewall" in windows Search, select "Allow an app through Windows Firewall".
- It can be noticed that Public of Remote Desktop app is unchecked.
- To enable Remote Desktop for public, click on the "Change Settings" button, and click to check it. Then OK.
- Remote Desktop Client app on Android work now.
VelocityTracker and VelocityTrackerCompat
package com.example.androidvelocitytracker;
import android.os.Build;
import android.os.Bundle;
import android.os.Build.VERSION_CODES;
import android.support.v4.view.VelocityTrackerCompat;
import android.util.SparseArray;
import android.view.MotionEvent;
import android.view.VelocityTracker;
import android.widget.TextView;
import android.app.Activity;
public class MainActivity extends Activity {
TextView textAvtion, textVelocityX0, textVelocityY0,
textVelocityX1, textVelocityY1;
TextView textVersion;
VelocityTracker velocityTracker = null;
static SparseArray<String> arrayVC = new SparseArray<String>();
static {
arrayVC.append(VERSION_CODES.BASE, "The original, first, version of Android.");
arrayVC.append(VERSION_CODES.BASE_1_1, "First Android update, officially called 1.1");
arrayVC.append(VERSION_CODES.CUPCAKE, "Android 1.5");
arrayVC.append(VERSION_CODES.CUR_DEVELOPMENT, "Magic version number...");
arrayVC.append(VERSION_CODES.DONUT, "Android 1.6");
arrayVC.append(VERSION_CODES.ECLAIR, "Android 2.0");
arrayVC.append(VERSION_CODES.ECLAIR_0_1, "Android 2.0.1");
arrayVC.append(VERSION_CODES.ECLAIR_MR1, "Android 2.1");
arrayVC.append(VERSION_CODES.FROYO, "Android 2.2");
arrayVC.append(VERSION_CODES.GINGERBREAD,"Android 2.3");
arrayVC.append(VERSION_CODES.GINGERBREAD_MR1, "Android 2.3.3");
arrayVC.append(VERSION_CODES.HONEYCOMB, "Android 3.0");
arrayVC.append(VERSION_CODES.HONEYCOMB_MR1, "Android 3.1");
arrayVC.append(VERSION_CODES.HONEYCOMB_MR2, "Android 3.2");
arrayVC.append(VERSION_CODES.ICE_CREAM_SANDWICH,"Android 4.0");
arrayVC.append(VERSION_CODES.ICE_CREAM_SANDWICH_MR1,"Android 4.0.3");
arrayVC.append(VERSION_CODES.JELLY_BEAN, "Android 4.1");
arrayVC.append(VERSION_CODES.JELLY_BEAN_MR1, "Android 4.2");
arrayVC.append(VERSION_CODES.JELLY_BEAN_MR2, "Android 4.3");
arrayVC.append(VERSION_CODES.KITKAT, "Android 4.4");
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
textAvtion = (TextView) findViewById(R.id.action);
textVelocityX0 = (TextView) findViewById(R.id.velocityx0);
textVelocityY0 = (TextView) findViewById(R.id.velocityy0);
textVelocityX1 = (TextView) findViewById(R.id.velocityx1);
textVelocityY1 = (TextView) findViewById(R.id.velocityy1);
textVersion = (TextView)findViewById(R.id.version);
int version = Build.VERSION.SDK_INT;
String BuildVersion = arrayVC.get(version, "unknown");
textVersion.setText(BuildVersion);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
int action = event.getActionMasked();
int index = event.getActionIndex();
int pointerId = event.getPointerId(index);
switch (action) {
case MotionEvent.ACTION_DOWN:
if (velocityTracker == null) {
velocityTracker = VelocityTracker.obtain();
} else {
velocityTracker.clear();
}
velocityTracker.addMovement(event);
if(pointerId == 0){
textVelocityX0.setText("X-velocity (pixel/s): 0");
textVelocityY0.setText("Y-velocity (pixel/s): 0");
}else if(pointerId == 1){
textVelocityX1.setText("X-velocity (pixel/s): 0");
textVelocityY1.setText("Y-velocity (pixel/s): 0");
}
break;
case MotionEvent.ACTION_MOVE:
velocityTracker.addMovement(event);
velocityTracker.computeCurrentVelocity(1000);
//1000 provides pixels per second
float xVelocity = VelocityTrackerCompat.getXVelocity(
velocityTracker, pointerId);
float yVelocity = VelocityTrackerCompat.getYVelocity(
velocityTracker, pointerId);
if(pointerId == 0){
textVelocityX0.setText("X-velocity (pixel/s): " + xVelocity);
textVelocityY0.setText("Y-velocity (pixel/s): " + yVelocity);
}else if(pointerId == 1){
textVelocityX1.setText("X-velocity (pixel/s): " + xVelocity);
textVelocityY1.setText("Y-velocity (pixel/s): " + yVelocity);
}
break;
case MotionEvent.ACTION_UP:
case MotionEvent.ACTION_CANCEL:
velocityTracker.recycle();
break;
}
return true;
}
}
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context=".MainActivity" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:autoLink="web"
android:text="http://arteluzevida.blogspot.com/"
android:textStyle="bold" />
<TextView
android:id="@+id/version"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/action"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:text="pointer 0"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/velocityx0"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/velocityy0"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:text="pointer 1"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/velocityx1"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/velocityy1"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
Download the files.
Get the Android version of device
This exercise use Android's SparseArrays to store SDK_INT-Build.VERSION_CODES pairs. SparseArrays map integers to Objects. Unlike a normal array of Objects, there can be gaps in the indices. It is intended to be more memory efficient than using a HashMap to map Integers to Objects, both because it avoids auto-boxing keys and its data structure doesn't rely on an extra entry object for each mapping.
Get the Android version of device |
package com.example.androidversion;
import android.os.Build;
import android.os.Build.VERSION_CODES;
import android.os.Bundle;
import android.util.SparseArray;
import android.widget.TextView;
import android.app.Activity;
public class MainActivity extends Activity {
static SparseArray<String> arrayVC = new SparseArray<String>();
static {
arrayVC.append(VERSION_CODES.BASE, "The original, first, version of Android.");
arrayVC.append(VERSION_CODES.BASE_1_1, "First Android update, officially called 1.1");
arrayVC.append(VERSION_CODES.CUPCAKE, "Android 1.5");
arrayVC.append(VERSION_CODES.CUR_DEVELOPMENT, "Magic version number...");
arrayVC.append(VERSION_CODES.DONUT, "Android 1.6");
arrayVC.append(VERSION_CODES.ECLAIR, "Android 2.0");
arrayVC.append(VERSION_CODES.ECLAIR_0_1, "Android 2.0.1");
arrayVC.append(VERSION_CODES.ECLAIR_MR1, "Android 2.1");
arrayVC.append(VERSION_CODES.FROYO, "Android 2.2");
arrayVC.append(VERSION_CODES.GINGERBREAD,"Android 2.3");
arrayVC.append(VERSION_CODES.GINGERBREAD_MR1, "Android 2.3.3");
arrayVC.append(VERSION_CODES.HONEYCOMB, "Android 3.0");
arrayVC.append(VERSION_CODES.HONEYCOMB_MR1, "Android 3.1");
arrayVC.append(VERSION_CODES.HONEYCOMB_MR2, "Android 3.2");
arrayVC.append(VERSION_CODES.ICE_CREAM_SANDWICH,"Android 4.0");
arrayVC.append(VERSION_CODES.ICE_CREAM_SANDWICH_MR1,"Android 4.0.3");
arrayVC.append(VERSION_CODES.JELLY_BEAN, "Android 4.1");
arrayVC.append(VERSION_CODES.JELLY_BEAN_MR1, "Android 4.2");
arrayVC.append(VERSION_CODES.JELLY_BEAN_MR2, "Android 4.3");
arrayVC.append(VERSION_CODES.KITKAT, "Android 4.4");
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//setContentView(R.layout.activity_main);
TextView textView = new TextView(this);
setContentView(textView);
int version = Build.VERSION.SDK_INT;
String BuildVersion = arrayVC.get(version, "unknown");
textView.setText(BuildVersion);
}
}
VelocityTracker, track the velocity of touch events
Example of using Android's VelocityTracker |
package com.example.androidvelocitytracker;
import android.os.Bundle;
import android.view.MotionEvent;
import android.view.VelocityTracker;
import android.widget.TextView;
import android.app.Activity;
public class MainActivity extends Activity {
TextView textAvtion, textVelocityX, textVelocityY,
textMaxVelocityX, textMaxVelocityY;
VelocityTracker velocityTracker = null;
float maxXVelocity;
float maxYVelocity;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
textAvtion = (TextView) findViewById(R.id.action);
textVelocityX = (TextView) findViewById(R.id.velocityx);
textVelocityY = (TextView) findViewById(R.id.velocityy);
textMaxVelocityX = (TextView) findViewById(R.id.maxvelocityx);
textMaxVelocityY = (TextView) findViewById(R.id.maxvelocityy);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
int action = event.getActionMasked();
switch (action) {
case MotionEvent.ACTION_DOWN:
if (velocityTracker == null) {
velocityTracker = VelocityTracker.obtain();
} else {
velocityTracker.clear();
}
velocityTracker.addMovement(event);
maxXVelocity = 0;
maxYVelocity = 0;
textVelocityX.setText("X-velocity (pixel/s): 0");
textVelocityY.setText("Y-velocity (pixel/s): 0");
textMaxVelocityX.setText("max. X-velocity: 0");
textMaxVelocityY.setText("max. Y-velocity: 0");
break;
case MotionEvent.ACTION_MOVE:
velocityTracker.addMovement(event);
velocityTracker.computeCurrentVelocity(1000);
//1000 provides pixels per second
float xVelocity = velocityTracker.getXVelocity();
float yVelocity = velocityTracker.getYVelocity();
if(xVelocity > maxXVelocity){
//max in right side
maxXVelocity = xVelocity;
}
if(yVelocity > maxYVelocity){
//Max in down side
maxYVelocity = yVelocity;
}
textVelocityX.setText("X-velocity (pixel/s): " + xVelocity);
textVelocityY.setText("Y-velocity (pixel/s): " + yVelocity);
textMaxVelocityX.setText("max. X-velocity: " + maxXVelocity);
textMaxVelocityY.setText("max. Y-velocity: " + maxYVelocity);
break;
case MotionEvent.ACTION_UP:
case MotionEvent.ACTION_CANCEL:
velocityTracker.recycle();
break;
}
return true;
}
}
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context=".MainActivity" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:autoLink="web"
android:text="http://arteluzevida.blogspot.com/"
android:textStyle="bold" />
<TextView
android:id="@+id/action"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/velocityx"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/maxvelocityx"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/velocityy"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/maxvelocityy"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
Next: VelocityTracker and VelocityTrackerCompat to track velocity for multi-touch case.
Android Security Cookbook
- Analyze the security of Android applications and devices, and exploit common vulnerabilities in applications and Android operating systems
- Develop custom vulnerability assessment tools using the Drozer Android Security Assessment Framework
- Reverse-engineer Android applications for security vulnerabilities
- Protect your Android application with up to date hardening techniques
- Set up the Android development tools and frameworks
- Engage in Application security concepts
- Use the Drozer Android Security Assessment Framework
- Customize and develop your own plugins for the Drozer Framework
- Exploit, enumerate, and analyze common application level exploits
- Protect applications from common vulnerabilities and exploits
- Reverse-engineer applications for common code level vulnerabilities
- Secure application networking, SSL/TLS
- Encryption to protect application data
Creating Dynamic UI with Android Fragments
- Learn everything you need to know to provide dynamic multi-screen UIs within a single activity
- Integrate the rich UI features demanded by today’s mobile users
- Understand the basics of using fragments and how to use them to create more adaptive and dynamic user experiences
- Understand the role and capabilities of fragments
- Explore the fragment-oriented features of Android Studio
- Create an app UI that works effectively on smartphones and tablets
- Use fragments to create engaging navigation capabilities like swipe-based screen browsing
- Work with special purpose fragment classes like ListFragment and DialogFragment
- Dynamically manage fragments using the FragmentTransaction class
- Learn appropriate application design for communicating between fragments
- Efficiently handle fragment creation and lifecycle
- Simplify cross-thread UI handling with fragments
- Form multi-screen UIs that run within a single activity
The Beautiful Design Winter 2013 Collection on Google Play
While beauty’s in the eye of the beholder, designing apps for a platform also requires an attention to platform norms to ensure a great user experience. The Android Design site is an excellent resource for designers and developers alike to get familiar with Android’s visual, interaction, and written language. Many developers have taken advantage of the tools and techniques provided on the site, and every now and then we like to showcase a few notable apps that go above and beyond the guidelines.
This summer, we published the first Beautiful Design collection on Google Play. Today, we're refreshing the collection with a new set of apps just in time for the holiday season.
As a reminder, the goal of this collection is to highlight beautiful apps with masterfully crafted design details such as beautiful presentation of photos, crisp and meaningful layout and typography, and delightful yet intuitive gestures and transitions.
The newly updated Beautiful Design Winter 2013 collection includes:
Timely (by Bitspin), a clock app that takes animation to a whole new level. Screen transitions are liquid smooth and using the app feels more like playing with real objects than fussing around with knobs and buttons. If you’ve ever wondered if setting an alarm could be fun, Timely unequivocally answers “yes”.
Circa, a news reader that’s fast, elegant and full of beautiful design details throughout. Sophisticated typography and banner image effects, coupled with an innovative and "snappy" interaction, makes reading an article feel fast and very, very fun.
Etsy, an app that helps you explore a world of wonderful hand-crafted goods with thoughtfully designed screen transitions, beautifully arranged layouts, and subtle flourishes like a blur effect that lets you focus on the task at hand. This wonderfully detailed app is an absolute joy to use.
Airbnb, The Whole Pantry, Runtastic Heart Rate Pro, Tumblr, Umano, Yahoo! Weather… each with delightful design details.
If you’re an Android developer, make sure to play with some of these apps to get a sense for the types of design details that can separate good apps from great ones. And remember to review the Android Design guidelines and the Android Design in Action video series for more ideas on how to design your next beautiful Android app.
Learning Mobile App Development: A Hands-on Guide to Building Apps with iOS and Android
- Understanding the unique design challenges associated with mobile apps
- Setting up your Android and iOS development environments
- Mastering Eclipse development tools for Android and Xcode 5 tools for iOS
- Designing interfaces and navigation schemes that leverage each platform’s power
- Reliably integrating persistent data into your apps
- Using lists (Android) or tables (iOS) to effectively present data to users
- Capturing device location, displaying it, and using it in your apps
- Accessing hardware devices and sensors
- Publishing custom apps internally within an organization
- Monetizing your apps on Apple’s AppStore or the Google Play marketplace, as well as other ways of profiting from app development, such as consulting and developer jobs
Implement Socket on Android to communicate with Raspberry Pi
The client side in the post is ported to Android in this exercise, setup Socket in AsyncTask, to communicate with Raspberry Pi. The updated version of Host (run socket operation in background thread) run on Raspberry Pi or any other PC is here.
Implement Socket on Android |
package com.example.androidclient;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.Socket;
import java.net.UnknownHostException;
import android.os.AsyncTask;
import android.os.Bundle;
import android.app.Activity;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
public class MainActivity extends Activity {
TextView textResponse;
EditText editTextAddress, editTextPort;
Button buttonConnect, buttonClear;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
editTextAddress = (EditText)findViewById(R.id.address);
editTextPort = (EditText)findViewById(R.id.port);
buttonConnect = (Button)findViewById(R.id.connect);
buttonClear = (Button)findViewById(R.id.clear);
textResponse = (TextView)findViewById(R.id.response);
buttonConnect.setOnClickListener(buttonConnectOnClickListener);
buttonClear.setOnClickListener(new OnClickListener(){
@Override
public void onClick(View v) {
textResponse.setText("");
}});
}
OnClickListener buttonConnectOnClickListener =
new OnClickListener(){
@Override
public void onClick(View arg0) {
/*
* You have to verify editTextAddress and
* editTextPort are input as correct format.
*/
MyClientTask myClientTask = new MyClientTask(
editTextAddress.getText().toString(),
Integer.parseInt(editTextPort.getText().toString()));
myClientTask.execute();
}};
public class MyClientTask extends AsyncTask<Void, Void, Void> {
String dstAddress;
int dstPort;
String response;
MyClientTask(String addr, int port){
dstAddress = addr;
dstPort = port;
}
@Override
protected Void doInBackground(Void... arg0) {
try {
Socket socket = new Socket(dstAddress, dstPort);
InputStream inputStream = socket.getInputStream();
ByteArrayOutputStream byteArrayOutputStream =
new ByteArrayOutputStream(1024);
byte[] buffer = new byte[1024];
int bytesRead;
while ((bytesRead = inputStream.read(buffer)) != -1){
byteArrayOutputStream.write(buffer, 0, bytesRead);
}
socket.close();
response = byteArrayOutputStream.toString("UTF-8");
} catch (UnknownHostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(Void result) {
textResponse.setText(response);
super.onPostExecute(result);
}
}
}
Layout
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
android:orientation="vertical"
tools:context=".MainActivity" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:autoLink="web"
android:text="http://arteluzevida.blogspot.com/"
android:textStyle="bold" />
<EditText
android:id="@+id/address"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="dstAddress" />
<EditText
android:id="@+id/port"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="dstPort" />
<Button
android:id="@+id/connect"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Connect..."/>
<Button
android:id="@+id/clear"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Clear"/>
<TextView
android:id="@+id/response"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
</LinearLayout>
AndroidManifest.xml have to be modified to add <uses-permission android:name="android.permission.INTERNET"/>
Download the files.
or Download and install the APK file.
Cross-post with Hello Raspberry Pi
Install the new Google Mobile Ads SDK for Android
If you're an Android developer you'll be familiar with Google Play services, a unified platform which makes it easy to integrate Google features into your Android apps, delivered through the Play Store and updated at regular intervals. Now that AdMob is part of the package, a key benefit is that changes to the Google Mobile Ads SDK for Android get pushed seamlessly to users through Google Play services. For most SDK updates you don’t need to update your apps each time it changes, saving you development time. Follow these instructions to install the SDK.
ActionBarCompat with ShareActionProvider to update dynamic content
In my experiment, onOptionsItemSelected() will not be called when Share menu item clicked. So a TextWatcher is implemented when any EditText changed, to update ShareIntent.
ActionBarCompat with ShareActionProvider to update dynamic content |
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
android:orientation="vertical"
tools:context=".MainActivity" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:autoLink="web"
android:text="http://arteluzevida.blogspot.com/"
android:textStyle="bold" />
<EditText
android:id="@+id/fieldemailaddress"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:inputType="textEmailAddress"
android:hint="email address" />
<EditText
android:id="@+id/fieldemailtitle"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Hello from android-er.blogspot.com"
android:hint="email title"/>
<EditText
android:id="@+id/fieldemailcontent"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="email content"/>
</LinearLayout>
/res/menu/main.xml, same as before.
<menu
xmlns:myapp="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:id="@+id/action_share"
android:title="Share"
myapp:actionProviderClass="android.support.v7.widget.ShareActionProvider"
myapp:showAsAction="always|withText" />
<item
android:id="@+id/action_settings"
myapp:showAsAction="always|withText"
android:title="@string/action_settings"/>
</menu>
MainActivity.java
package com.example.testactionbarcompat;
import android.content.Intent;
import android.os.Bundle;
import android.support.v4.view.MenuItemCompat;
import android.support.v7.app.ActionBarActivity;
import android.support.v7.widget.ShareActionProvider;
import android.text.Editable;
import android.text.TextWatcher;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.EditText;
import android.widget.Toast;
public class MainActivity extends ActionBarActivity {
EditText fieldEmailAddress, fieldEmailTitle, fieldEmailContent;
private ShareActionProvider myShareActionProvider;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
fieldEmailAddress = (EditText)findViewById(R.id.fieldemailaddress);
fieldEmailTitle = (EditText)findViewById(R.id.fieldemailtitle);
fieldEmailContent = (EditText)findViewById(R.id.fieldemailcontent);
fieldEmailAddress.addTextChangedListener(myTextWatcher);
fieldEmailTitle.addTextChangedListener(myTextWatcher);
fieldEmailContent.addTextChangedListener(myTextWatcher);
}
/*
* update ActionProvider by calling setShareIntent()
* When any EditText changed
*/
TextWatcher myTextWatcher = new TextWatcher(){
@Override
public void afterTextChanged(Editable s) {
setShareIntent();
}
@Override
public void beforeTextChanged(CharSequence s, int start,
int count, int after) {}
@Override
public void onTextChanged(CharSequence s, int start,
int before, int count) {}
};
@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);
//add MenuItem(s) to ActionBar using Java code
MenuItem menuItem_Info = menu.add(0, R.id.menuid_info, 0, "Info");
menuItem_Info.setIcon(android.R.drawable.ic_menu_info_details);
MenuItemCompat.setShowAsAction(menuItem_Info,
MenuItem.SHOW_AS_ACTION_ALWAYS|MenuItem.SHOW_AS_ACTION_WITH_TEXT);
//Handle share menu item
MenuItem shareItem = menu.findItem(R.id.action_share);
myShareActionProvider = (ShareActionProvider)
MenuItemCompat.getActionProvider(shareItem);
setShareIntent();
//return true;
return super.onCreateOptionsMenu(menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// TODO Auto-generated method stub
//return super.onOptionsItemSelected(item);
switch (item.getItemId()) {
case R.id.action_share:
//It never called in my experiment
Toast.makeText(this, "Share", Toast.LENGTH_SHORT).show();
setShareIntent();
return false;
case R.id.action_settings:
//match with /res/menu/main.xml
Toast.makeText(this, "Setting", Toast.LENGTH_SHORT).show();
return true;
case R.id.menuid_info:
//match with defined in onCreateOptionsMenu()
Toast.makeText(this, "Info", Toast.LENGTH_SHORT).show();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
//Set the share intent
private void setShareIntent(){
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("plain/text");
intent.putExtra(Intent.EXTRA_EMAIL,
new String[]{fieldEmailAddress.getText().toString()});
intent.putExtra(Intent.EXTRA_SUBJECT,
fieldEmailTitle.getText().toString());
intent.putExtra(Intent.EXTRA_TEXT,
fieldEmailContent.getText().toString());
myShareActionProvider.setShareIntent(intent);
}
}
Download the files.
Visit: ActionBarCompat Step-by-step
ActionBarCompat with ShareActionProvider
ActionBarCompat with Share ShareActionProvider |
Modify /res/menu/main.xml to add new item of action_share.
<menu
xmlns:myapp="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:id="@+id/action_share"
android:title="Share"
myapp:actionProviderClass="android.support.v7.widget.ShareActionProvider"
myapp:showAsAction="always|withText" />
<item
android:id="@+id/action_settings"
myapp:showAsAction="always|withText"
android:title="@string/action_settings"/>
</menu>
MainActivity.java.
package com.example.testactionbarcompat;
import android.content.Intent;
import android.os.Bundle;
import android.support.v4.view.MenuItemCompat;
import android.support.v7.app.ActionBarActivity;
import android.support.v7.widget.ShareActionProvider;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.Toast;
public class MainActivity extends ActionBarActivity {
private ShareActionProvider myShareActionProvider;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
@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);
//add MenuItem(s) to ActionBar using Java code
MenuItem menuItem_Info = menu.add(0, R.id.menuid_info, 0, "Info");
menuItem_Info.setIcon(android.R.drawable.ic_menu_info_details);
MenuItemCompat.setShowAsAction(menuItem_Info,
MenuItem.SHOW_AS_ACTION_ALWAYS|MenuItem.SHOW_AS_ACTION_WITH_TEXT);
//Handle share menu item
MenuItem shareItem = menu.findItem(R.id.action_share);
myShareActionProvider = (ShareActionProvider)
MenuItemCompat.getActionProvider(shareItem);
setShareIntent();
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// TODO Auto-generated method stub
//return super.onOptionsItemSelected(item);
switch (item.getItemId()) {
case R.id.action_settings:
//match with /res/menu/main.xml
Toast.makeText(this, "Setting", Toast.LENGTH_SHORT).show();
return true;
case R.id.menuid_info:
//match with defined in onCreateOptionsMenu()
Toast.makeText(this, "Info", Toast.LENGTH_SHORT).show();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
//Set the share intent
private void setShareIntent(){
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("plain/text");
intent.putExtra(Intent.EXTRA_TEXT, "Hello from android-er.blogspot.com");
myShareActionProvider.setShareIntent(intent);
}
}
Download the files.
Next:
- ActionBarCompat with ShareActionProvider to update dynamic content
Visit: ActionBarCompat Step-by-step
Pro Android Graphics
You’ll learn about:
- The foundational graphics concepts behind the three core new media areas (digital imaging, digital video, and 2D animation) which relate to graphics design, and how to optimize these new media assets for your Android applications across iTVs, tablets, eReaders, game consoles, and smartphones.
- Digital imaging techniques for Android apps design, including graphics design layouts and graphical user interface elements, and how to use image compositing techniques to take your digital imaging to far higher levels.
- Advanced image compositing and blending techniques, using Android’s PorterDuff, NinePatch, and LayerDrawable classes.
- Advanced 2D animation techniques, using Android’s Animation and AnimationDrawable classes.
- Digital video optimization, playback, and streaming, using open source 3D (Terragen 3) and video (VirtualDub) applications, as well as professional video editing applications such as Squeeze Pro 9. You’ll use these software packages with Android’s VideoView and MediaPlayer classes, and add compositing to enhance your end-users’ digital video experience.
What you’ll learn
- How to build graphics rich Android apps and games
- What are the key Android Graphics support APIs: Images, Animation and Video Concepts
- What are the digital imaging techniques for Android apps
- What are the advanced animation techniques for Android apps
- How to do digital video optimization for Android apps
Who this book is for
Table of Contents
- Android Digital Imaging: Formats, Concepts, and Optimization
- Android Digital Video: Formats, Concepts, and Optimization
- Android Frame Animation: XML, Concepts, and Optimization
- Android Procedural Animation: XML, Concepts, and Optimization
- Android DIP: Device-Independent Pixel Graphics Design
- Android UI Layouts: Graphics Design Using the ViewGroup Class
- Android UI Widgets: Graphics Design using the View Class
- Advanced ImageView: More Graphics Design Using ImageView
- Advanced ImageButton: Creating a Custom Multi-State ImageButton
- Using 9-Patch Imaging Techniques to Create Scalable Imaging Elements
- Advanced Image Blending: Using Android PorterDuff Classes
- Advanced Image Compositing: Using the LayerDrawable Class
- Digital Image Transitions: Using the TransitionDrawable Class
- Frame-Based Animation: Using the AnimationDrawable Class
- Procedural Animation: Using the Animation Classes
- Advanced Graphics: Mastering the Drawable Class
- Interactive Drawing: Using Paint and Canvas Classes Interactively
- Playing Captive Video Using the VideoView and MediaPlayer Classes
- Streaming Digital Video from an External Media Server
Pro iOS and Android Apps for Business: with jQuery Mobile, node.js, and MongoDB
You never have to deal with learning Objective-C, Java or any other difficult-to-learn language. Instead, you can build on your existing HTML5, JavaScript and CSS experience to quickly and effectively build any app your business needs. You can apply this knowledge to iOS and Android apps as well as other mobile platforms since the technologies used support most modern mobile platforms as well.
You'll learn:
- How to design a full-featured app, including requirements like offline access
- How to build the client-side of the app using jQuery Mobile, including adding stub code for calling the node.js server
- How to create a simple server with node.js and interact with it using REST
- How to use MongoDB with node.js for data storage
- How to use PhoneGap to ready your app for mobile deployment
- How to test and debug your app on iOS and Android
What you’ll learn
- How to design a full-featured app, including requirements like offline access
- How to build the client-side of the app using jQuery Mobile, including adding stub code for calling the node.js server
- How to create a simple server with node.js and interact with it using REST
- How to use MongoDB with node.js for data storage
- How to use PhoneGap to ready your app for mobile deployment
- How to test and debug your app on iOS and Android
Who this book is for
Table of Contents
Part I: The ClientChapter 1 – Designing My Mobile Organizer
Chapter 2 - Introducing jQuery and jQuery Mobile
Chapter 3 - Writing the Application with jQuery Mobile, Part I
Chapter 4 - Writing the Application with jQuery Mobile, Part II
Part II: The Server
Chapter 5 - Introducing node.js
Chapter 6 - Introducing MongoDB
Chapter 7 - Writing the Server with node.js and MongoDB, Part I
Chapter 8 - Writing the Server with node.js and MongoDB, Part II
Part III: Putting It All Together
Chapter 9 - Introducing Phonegap
Chapter 10 - The Final Build: Going Mobile With Phonegap
Handle onOptionsItemSelected() for ActionBarCompat
user click on Options Menu in ActionBarCompat |
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// TODO Auto-generated method stub
//return super.onOptionsItemSelected(item);
switch (item.getItemId()) {
case R.id.action_settings:
//match with /res/menu/main.xml
Toast.makeText(this, "Setting", Toast.LENGTH_SHORT).show();
return true;
case R.id.menuid_info:
//match with defined in onCreateOptionsMenu()
Toast.makeText(this, "Info", Toast.LENGTH_SHORT).show();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
Download the files.
Next:
- ActionBarCompat with Share ShareActionProvider
Visit: ActionBarCompat Step-by-step
Add MenuItem to ActionBarCompat using Java
New MenuItem of menuItem_Info added using Java code |
To add new MenuItem dynamically, we have to assign new id to it. Create a new file, /res/values/ids.xml, to define our
<?xml version="1.0" encoding="utf-8"?>
<resources>
<item name="menuid_info" type="id"/>
</resources>
Modify onCreateOptionsMenu() method in MainActivity.java to add new MenuItem using Java code:
package com.example.testactionbarcompat;
import android.os.Bundle;
import android.support.v4.view.MenuItemCompat;
import android.support.v7.app.ActionBarActivity;
import android.view.Menu;
import android.view.MenuItem;
public class MainActivity extends ActionBarActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
@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);
//add MenuItem(s) to ActionBar using Java code
MenuItem menuItem_Info = menu.add(0, R.id.menuid_info, 0, "Info");
menuItem_Info.setIcon(android.R.drawable.ic_menu_info_details);
MenuItemCompat.setShowAsAction(menuItem_Info,
MenuItem.SHOW_AS_ACTION_IF_ROOM|MenuItem.SHOW_AS_ACTION_WITH_TEXT);
return true;
}
}
Download the files.
Visit: ActionBarCompat Step-by-step
Example of using ActionBarCompat with android-support-v7-appcompat
ActionBarCompat on Nexus One running Android 2.3.6 |
- New a Android Application Project as normal.
- Right click on the project, select Properties, select Android tab on the left box, scroll down on the right to make sure the check box of "is Library" is un-checked, and click the Add button to add library of "android-support-v7-appcompat". then click OK.
add library of android-support-v7-appcompat |
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.testactionbarcompat"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="18" />
<application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/Theme.AppCompat" >
<activity
android:name="com.example.testactionbarcompat.MainActivity"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
- Modify menu resources file, /res/menu/main.xml.
Add a new xmlns, xmlns:myapp="http://schemas.android.com/apk/res-auto". You can choice any name (myapp in my example) you want. But it has to be matched with the name space in
Modify
<menu
xmlns:myapp="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:id="@+id/action_settings"
android:orderInCategory="100"
myapp:showAsAction="always"
android:title="@string/action_settings"/>
</menu>
- Modify MainActivity to extend ActionBarActivity with android.support.v7.app.ActionBarActivity imported.
package com.example.testactionbarcompat;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.view.Menu;
public class MainActivity extends ActionBarActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
@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;
}
}
- Now it can be re-build to generate app with Action Bar running on devices of Android 2.1 or higher.
Next:
- Add MenuItem to ActionBarCompat using Java
Visit: ActionBarCompat Step-by-step