您的位置:首页 > 移动开发 > Android开发

小功能的实现记录

2015-04-12 16:24 501 查看

1.再按一次退出程序的实现:

private long exitTime = 0; //

@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_BACK
&& event.getAction() == KeyEvent.ACTION_DOWN) {
if ((System.currentTimeMillis() - exitTime) > 2000) {
Toast.makeText(getApplicationContext(), "再按一次退出程序",
Toast.LENGTH_SHORT).show();
exitTime = System.currentTimeMillis();
} else {
finish();
System.exit(0);
}
return true;
}
return super.onKeyDown(keyCode, event);
}

2.普通的返回:

@Override
public boolean onKeyDown(int keyCode, KeyEvent event)  {
if (keyCode == KeyEvent.KEYCODE_BACK && event.getRepeatCount() == 0) { //按下的如果是BACK,同时没有重复
//do something here
return true;
}

return super.onKeyDown(keyCode, event);
}


3.自定义dialog以及自定义图标关闭dialog:

final AlertDialog.Builder builder = new AlertDialog.Builder(this);
// 获得layout的填充器
// LayoutInflater inflater = this.getLayoutInflater();
// View view = inflater.inflate(R.layout.content_dialog, null);
// dialog.setView(view);
LayoutInflater inflater = LayoutInflater.from(this);
View view = inflater.inflate(R.layout.content_dialog, null);
builder.setView(view);

TextView dialog_tv = (TextView) view.findViewById(R.id.content_tv);
dialog_tv.setText("\t\t" + jieshao);
ImageView dialog_close = (ImageView) view
.findViewById(R.id.close_dialog);
builder.create();
// 先获得一个dialog对象
final AlertDialog dialog = builder.show();
dialog_close.setOnClickListener(new OnClickListener() {

@Override
public void onClick(View v) {
dialog.dismiss();
}
});

4.AssetManager的使用,导入文件:

private void importDB() {
File file = new File(getFilesDir(), Contance.IMPORT_DB_NAME);
// 判断是否存在
if (file.exists() && file.length() > 0) {
Log.i(Contance.TAG_INFO, "已存在");
} else {
// 使用AssetManager类来访问assets文件夹
AssetManager asset = getAssets();
InputStream is = null;
FileOutputStream fos = null;
try {
is = asset.open(Contance.IMPORT_DB_NAME);
fos = new FileOutputStream(file);
int len = 0;
byte[] buf = new byte[1024];
while ((len = is.read(buf)) != -1) {
fos.write(buf, 0, len);
}
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (is != null) {
is.close();
}
if (fos != null) {
fos.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
Log.i(Contance.TAG_INFO, "已完成");
}

5.SplashActivity界面,handler.postDelayed(Runnable r)的使用;

private Handler handler = new Handler() {};
handler.postDelayed(new Runnable() {

@Override
public void run() {
<span style="white-space:pre">	</span>enterHome();

}
}, 1000);

6.scrollview滚动不到最低端

      在用ScrollView包裹TextView时发现。滚动条有时候滚动不到最底端,原因是在TextView中设置了Android:layout_marginTop="20dp",导致marginTop之后,scrollView初始显示的位置向下移动了20dp,你如果想要让他正常显示,必须在代码里面设置一下scrollView的初始显示位置就可以了。mScrollView.smoothScrollTo(0,0).

7.获得系统时间转换成小时分钟制

long sysTime = System.currentTimeMillis();
CharSequence sysTimeStr = DateFormat.format("hh:mm:ss", sysTime);

8.获得LayoutInflater实例的三种方式:
1. LayoutInflater inflater = getLayoutInflater();//调用Activity的getLayoutInflater()
2. LayoutInflater inflater = LayoutInflater.from(context);
3. LayoutInflater inflater =  (LayoutInflater)context.getSystemService
(Context.LAYOUT_INFLATER_SERVICE);


8.LatLng的经纬度转换为RoutePlanNode的经纬度

sX = (int) (START.latitude * 1E5);
sY = (int) (START.longitude * 1E5);
eX = (int) (END.latitude * 1E5);
eY = (int) (END.longitude * 1E5);

9.Intent intent = getIntent() 写成成员变量,就会爆空指针


10.经纬度的37.346532等是double类型

11.selector没有效果:默认状态必须放在最后一行

12.应用程序apk之间的跳转

Intent intent = new Intent();
ComponentName componentName;
componentName = new ComponentName("com.minuzuos.romactivate",
"com.minuzuos.romactivate.MainActivity");
intent.setComponent(componentName);
startActivity(intent);

13.检查网络是否连接并设置wifi

首先需要添加权限

<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.CHANGE_NETWORK_STATE" />
然后检查网络
/**
* 检查网络是否可用
*/
private boolean checkNetStatu() {
ConnectivityManager manager = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE);
NetworkInfo info = manager.getActiveNetworkInfo();
if (info != null && info.isAvailable()) {
return true;
} else {
return false;
}
}
然后设置网络

private void showSetNetDialog() {
Toast.makeText(getApplicationContext(), "网络不可用", 0).show();
AlertDialog.Builder builder = new Builder(this);
builder.setTitle("网络设置");
builder.setMessage("当前无可用的网络,是否设置网络");
builder.setPositiveButton("设置",
new android.content.DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
Intent intent = new Intent(
Settings.ACTION_WIFI_SETTINGS);
startActivity(intent);
// finish();
}
});
builder.setNegativeButton("取消",
new android.content.DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
});
builder.show();
}


14.获取map集合中数据的办法

//Map集合取数据的四种方法
public class MapFetch {
// 第一种方法(传统方法)
@Test
public void funOne() {
Map map = new HashMap();
map.put("1", "第一个数");
map.put("2", "第二个数");
map.put("3", "第三个数");
Set set = map.keySet();
Iterator it = set.iterator();
while (it.hasNext()) {
String key = (String) it.next();
String value = (String) map.get(key);
System.out.println(key + "=" + value);
}
}

// 第二种方法(传统方法)
@Test
public void funTwo() {
Map map = new HashMap();
map.put("1", "第一个数");
map.put("2", "第二个数");
map.put("3", "第三个数");
Set set = map.entrySet();
Iterator it = set.iterator();
while (it.hasNext()) {
Entry entry = (Entry) it.next();
String key = (String) entry.getKey();
String value = (String) entry.getValue();
System.out.println(key + "=" + value);
}
}

// 第三种方法(增强for循环方法)
@Test
public void funThree() {
Map map = new LinkedHashMap();
map.put("1", "第一个数");
map.put("2", "第二个数");
map.put("3", "第三个数");
for (Object obj : map.keySet()) {
String key = (String) obj;
String value = (String) map.get(key);
System.out.println(key + "=" + value);
}
}

// 第四种方法(增强for循环方法)
@Test
public void funFour() {
Map map = new LinkedHashMap();
map.put("1", "第一个数");
map.put("2", "第二个数");
map.put("3", "第三个数");
for (Object obj : map.entrySet()) {
Entry entry = (Entry) obj;
String key = (String) entry.getKey();
String value = (String) entry.getValue();
System.out.println(key + "=" + value);
}
}

}


15.textview首行缩进

方式一:(推荐)

setText("\u3000\u3000"+xxxxx);

方式二:这种方式不同分辨率会有问题

setText(""+xxxxx);

半角:\u0020

全角:\u3000

16.桌面隐藏图标

<category android:name="android.intent.category.DEFAULT" />
只需要将入口activity的category中的launcher改成default即可。

17.获得手机参数

private void getServicesInfo() {

// 每次都清空集合
serviceInfoMap.clear();

// romversion:获取系统ROM版本号
String strSystem = android.os.Build.DISPLAY;
serviceInfoMap.put("romversion", strSystem);

// brand:获取手机厂商
String strPhoneBrand = android.os.Build.MANUFACTURER;
serviceInfoMap.put("brand", strPhoneBrand);

// model:获取手机型号
String strPhoneModle = android.os.Build.MODEL;
serviceInfoMap.put("model", strPhoneModle);

// device:获取手机具体型号
String strPhoneDevices = android.os.Build.DEVICE;
serviceInfoMap.put("device", strPhoneDevices);

// imei:获取手机imei手机序列号
TelephonyManager telephonyManager = (TelephonyManager) this
.getSystemService(Context.TELEPHONY_SERVICE);
String strImei = telephonyManager.getDeviceId();
serviceInfoMap.put("imei", strImei);


<span style="font-size:14px;">	// osversion:"1.0.0-20150507-bacon" 手机操作系统版本号,或者是ROM版本
String strSystem = android.os.Build.DISPLAY;
mDevicesInfoMap.put(Contance.REQ_OSVERSION, strSystem);</span>


<span style="font-size:14px;">// 想要获得系统的rom版本号,这是某个特定手机专有的一个字段。
// 此时就需要查看手机原码,找到那个字段的value,从而获得它的key值,就是ro.cm.display.version
// 然后通过调用android.os.SystemProperties类,它类似于android.Provider.Settings.System
// 但是android.os.SystemPriperties是内部隐藏类,在应用程序编写过程中是无法调用的。(安全性,如果每个人都可以调用,轻易查询系统的方法,就不好了)
// 此刻利用JNI来编写,但是这个不会,有点麻烦。
// 还有就是把手机的SDK导入本地,然后关联这个SDK,再编写
// 其实最方便的方法就是利用反射
String strSystem = getRomVersion("ro.cm.display.version");
Log.i(TEST_TAG, strSystem);
serviceInfoMap.put("romversion", strSystem);

public String getRomVersion(String key) {
Class<?> clazz;
try {
clazz = Class.forName("android.os.SystemProperties");
Method method = clazz.getDeclaredMethod("get", String.class);
Log.i(TEST_TAG,
"jieguo" + (String) method.invoke(clazz.newInstance(), key));
return (String) method.invoke(clazz.newInstance(), key);
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
} catch (InstantiationException e) {
e.printStackTrace();
}
return "";
}</span>
<span style="white-space:pre">	</span>PackageInfo info;
try {
info = this.getPackageManager().getPackageInfo(this.getPackageName(), 0);
// 当前应用的版本名称
String versionName = info.versionName;
// 当前版本的版本号
int versionCode = info.versionCode;
// 当前版本的包名
String packageNames = info.packageName;
} catch (NameNotFoundException e) {
e.printStackTrace();
}


18.ListView布局中使用android:descendantFocusability属性获取焦点

开发中很常见的一个问题,项目中的listview不仅仅是简单的文字,常常需要自己定义listview,自己的Adapter去继承BaseAdapter,在adapter中按照需求进行编写,问题就出现了,可能会发生点击每一个item的时候没有反应,无法获取的焦点。原因多半是由于在你自己定义的Item中存在诸如ImageButton,Button,CheckBox等子控件(也可以说是Button或者Checkable的子类控件),此时这些子控件会将焦点获取到,所以常常当点击item时变化的是子控件,item本身的点击没有响应。

该属性是当一个为view获取焦点时,定义viewGroup和其子控件两者之间的关系。
属性的值有三种:
        beforeDescendants:viewgroup会优先其子类控件而获取到焦点
        afterDescendants:viewgroup只有当其子类控件不需要获取焦点时才获取焦点
        blocksDescendants:viewgroup会覆盖子类控件而直接获得焦点

19.ListView之间的分割线:

只需在listview中设置android:divider就可以了

设置分割线的高度,就是android:dividerHeight

20.需求:自定义的progress图片大小和textview的大小一致。

首先获得textview的大小 ,调用getTextSize()方法。

随后设置ProgressBar是图片旋转。

在drawable创建一个xml,内容如下:

<animated-rotate xmlns:android="http://schemas.android.com/apk/res/android"
android:drawable="@drawable/refresh_doing"
android:fromDegrees="0.0"
android:pivotX="50.0%"
android:pivotY="50.0%"
android:toDegrees="360.0" >

</animated-rotate>


然后设置progressbar的属性:

android:indeterminateDrawable="@drawable/progressbarstyle"


随后设置progressbar的宽高和控件居中属性:

float textSize = description.getTextSize();
RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(
(int) textSize, (int) textSize);
params.addRule(RelativeLayout.CENTER_IN_PARENT);
progressBar.setLayoutParams(params);
上面就是全部内容,解决了。

期间遇到了问题,刚开始设置是如下:

LayoutParams params2;
params2 = (LayoutParams) progressBar.getLayoutParams();
params2.width = (int) textSize;
params.height =(int) textSize;
progressBar.setLayoutParams(params2);
此时,就会报错。log为

java.lang.ClassCastException: android.widget.LinearLayout$LayoutParams cannot be cast to android.widget.RelativeLayout$LayoutParams
最后添加了父布局RelativeLayout之后,就可以了

参考内容如下:
http://zhidao.baidu.com/link?url=mnoZENLKVPR2AGJbGQOvRszBEEn8Pkq_vo1gdE_PsFctBLd6VQCkNyHol1Sb81Kr8fngx8ZSoQKnAuyjjNT_Gq http://www.2cto.com/kf/201307/227311.html http://www.cnblogs.com/wanqieddy/p/4040601.html http://blog.csdn.net/wwj_748/article/details/7902527

21.SharedPreferences的简单使用,键值对保存。

首先创建一个SharedPreferences对象
private SharedPreferences preferences;
然后通过调用PreferenceManager的getDefaultSharedPreferences(context)来获取一个SharedPreferences对象
preferences = PreferenceManager.getDefaultSharedPreferences(context);
加入我要记录当前的系统时间,并且保存,如下:
preferences.edit().putLong(UPDATED_AT + mId, System.currentTimeMillis()).commit();
通过调用SharedPreference的edit()方法来获得一个SharedPreferences.Editor对象,
接着调用这个Editor对象的putLong()方法添加值,第一个是键,第二个是值
然后使用Edition对象的commit()方法提交修改,否则无法写入数据。
想要获得这个值的时候,调用get方法,传入键,也可给定一个默认值。
lastUpdateTime = preferences.getLong(UPDATED_AT + mId, -1);


22.library导出成jar包。

由于我想把框架的library打包成jar包,直接放到项目中使用。

首先,library得是is library选中状态,这个在右键首选项中有,然后右键export,选择java->JAR file 然后给定路径就OK了。
但是导出成jar包后,直接复制使用,不管怎么样,都是报错的。都无法运行项目。
最后采用了一个笨方法,就是新建一个空项目,把所有的代码都复制到新的项目中,library是没有布局文件和清单文件的,记得删除。然后扎起同样的步骤,导出成jar包。最后ok了。

23.如何让应用不出现在recent中

只要在清单文件中加上android:excludeFromRecents="true" 这句话,就可以把应用从recent中取消掉。

24.非acitivity界面弹出dialog

需求:想要对listview中的按钮设置点击事件,这样就需要在adapter中对按钮进行初始化,以及点击事件的处理。点击按钮的时候,需要弹出Dialog。,但是报错



会出现如上的错误信息,android.view.WindowManager$BadTokenException:
Unable to add window — token null

导致这个方法的原因是在new 的时候,传入的上下文的参数,不能使用getApplicationContext()获得的Context。应该使用MainActivity.this才可以。

这样就能在一个非Activity中创建一个dialog了,

在adpter中设置,只需要在初始化adapter的时候,把上下文传入MainActivity就好了。

25.输出数组、split方法、char转换String、获取字符串的数字部分。

<span style="white-space:pre">	</span>public String str = "6.2.4.53_r843fb8e";

<span style="white-space:pre">	</span>button.setOnClickListener(new OnClickListener() {

@Override
public void onClick(View v) {
String[] sss = str.split("\\.");
System.out.println(Arrays.toString(sss));
String str1 = sss[sss.length - 1];
StringBuilder builder = new StringBuilder();
for (int i = 0; i < str1.length(); i++) {
String str2 = String.valueOf(str1.charAt(i));
if (isInteger(str2)) {
builder.append(str2);
} else {
break;
}
}
System.out.println(builder.toString());
// for (int i = 0; i < sss.length; i++) {
// System.out.println(sss[i].toString());
// }
}
});

<span style="white-space:pre">	</span>public static boolean isInteger(String value) {
try {
Integer.parseInt(value);
return true;
} catch (NumberFormatException e) {
return false;
}
}


26.bitmap和drawabe的一些操作

26.1 将aasets文件下的图片设置成bitmap

<span style="white-space:pre">	</span>InputStream is;
try {
<span style="white-space:pre">	</span>is = this.getAssets().open(路径名称,如:a/b/c.jpg);
Bitmap bmp = BitmapFactory.decodeStream(is);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

26.2 将本地路径下的图片设置成bitmap

// 获取路径的图片
FileInputStream fis = new FileInputStream(路径名称,如:/data/data/packagename/files/c.png<span style="font-family: Arial, Helvetica, sans-serif;">);</span>
Bitmap bmp = BitmapFactory.decodeStream(fis);

26.3 将drawable下的图片设置成bitmap

Resources res = getResources();
Bitmap bmp = BitmapFactory.decodeResource(res,R.drawable.ic_launcher);

imageView.setImageBitmap(bmp)


27.检测某apk是否已经安装

方法一;
/**
* 检测某程序是否安装
*/
public static boolean isInstalledApp(Context context, String packageName)
{
Boolean flag = false;

try
{
PackageManager pm = context.getPackageManager();
List<PackageInfo> pkgs = pm.getInstalledPackages(PackageManager.GET_UNINSTALLED_PACKAGES);
for (PackageInfo pkg : pkgs)
{
// 当找到了名字和该包名相同的时候,返回
if ((pkg.packageName).equals(packageName))
{
return flag = true;
}
}
}
catch (Exception e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}

return flag;
}


方法二:
<span style="white-space:pre">	</span>/**
* 检测某程序是否安装
*/
public static boolean isInstalledApp(Context context, String packageName) {
Boolean flag = false;
try {
PackageManager pm = context.getPackageManager();
Intent newIntent = new Intent(Intent.ACTION_MAIN, null);
newIntent.addCategory(Intent.CATEGORY_LAUNCHER);
List<ResolveInfo> pkgs = pm.queryIntentActivities(newIntent, 0);
// List<PackageInfo> pkgs = pm.getInstalledPackages(0);
for (ResolveInfo pkg : pkgs) {
// 当找到了名字和该包名相同的时候,返回
if ((pkg.activityInfo.packageName).equals(packageName)) {

return flag = true;
}
}
} catch (Exception e) {
e.printStackTrace();
}
return flag;
}


方法一和方法二是有区别的,使用过后会发现,方法一有时候返回存在的应用,实际是不存在的,这是由于之前安装过应用,但是已经卸载了,在本地有残留。说明方法一的范围比较广泛。
方法二增加了category,设置了属性Intent.CATEGORY_LAUNCHER,这样就可以过滤只在桌面显示的应用了。基本方法二可以满足需求。(参考android原码写的方法)

28.根据包名打开一个应用

/**
* 打开apk的操作,根据包名打开
*/
public void openApkOprator() {

Intent intent = new Intent();
PackageManager packageManager = this.getPackageManager();
intent = packageManager.getLaunchIntentForPackage(prePkgName);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
| Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED
| Intent.FLAG_ACTIVITY_CLEAR_TOP);
this.startActivity(intent);

}


29.替换string'中的字符

String a = ”abc“;
String b = a.replace("a","b");

30.反射的基本使用

30.1 反射调用无返回值的方法

[java] view plaincopy
public void setFilePathPermissions(String name, int mode,
int extraPermissions) {
Class<?> clazz;
try {
// 包名加类名
clazz = Class.forName("android.app.ContextImpl");
// 方法名
Method method = clazz.getDeclaredMethod(
"setFilePermissionsFromMode", new Class[] { String.class,
int.class, int.class });
method.invoke(null, name, mode, extraPermissions);
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
首先Class.forName中的参数,是类的全名加上包名。
getDeclaredMethod方法中的第一个参数是方法名,第二个参数,是个参数数组,就比如setFilePermissionsFromMode方法有三个参数, 后面就追加三个参数,可以像上面那样写个数组,中间有三个元素,

[java] view plaincopy
clazz.getDeclaredMethod("setFilePermissionsFromMode", new Class[] { String.class,int.class, int.class });
也可以把数组显示去掉,如下

[java] view plaincopy
clazz.getDeclaredMethod("setFilePermissionsFromMode", String.class,int.class, int.class );
所需要反射的方法的参数有几个,就写几个,是什么类型,就调用类型.class的方法。记住,int和integer是不一样的。
method.invoke(null, name, mode, extraPermissions);其实也是两个参数模式,如果方法是static的话,第一个参数,就设置为null,否则写成clazz.newInstance(),

后面三个参数,本身和上面类型.class是一个意思,也是一个数组,这是就是直接写的方式,把三个参数传进来就ok了。

如果该方法没有返回值,你自己创建的方法名的返回值类型就写void就行了。

参考博客:

http://blog.csdn.net/stevenhu_223/article/details/9286121

http://m.blog.csdn.net/blog/liuyanggofurther/38351469

30.2 反射调用有返回类型的方法

public String getRomVersion(String key) {
Class<?> clazz;
try {
clazz = Class.forName("android.os.SystemProperties");
Method method = clazz.getDeclaredMethod("get", String.class);
Log.i(TEST_TAG,
"jieguo" + (String) method.invoke(clazz.newInstance(), key));
return (String) method.invoke(clazz.newInstance(), key);
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
} catch (InstantiationException e) {
e.printStackTrace();
}
return "";
}


30.3 反射调用常量

在android原码的android.os.SystemProperties中,有这样一个常量public static final int PROP_VALUE_MAX = 91;

现在想办法得到这个值:

public void getValue() {
try {
Class<?> clazz = Class.forName("android.os.SystemProperties");
Field field = clazz.getField("PROP_VALUE_MAX");
field.setAccessible(true);
int value = field.getInt(field);
System.out.println("------>" + value);
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (NoSuchFieldException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
参考博客   :http://blog.csdn.net/barryhappy/article/details/24442953

30.4 利用反射,并且是内部类。调用变量

public void getValue() {
try {
Class<?> clazz = Class.forName("android.net.NetworkStats$Entry");
// 获取变量
Field field2 = clazz.getDeclaredField("rxBytes");
field2.setAccessible(true);
System.out.println("------>" + field2.toString());
System.out.println("----->" + field2.get(clazz.newInstance()));
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (NoSuchFieldException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InstantiationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}


参考博客:

java反射之内部类: http://www.cnblogs.com/frydsh/archive/2012/12/24/2831690.html

java反射机制中的getDeclaredField() : http://my.oschina.net/swords/blog/117357

利用java反射获取类的私有变量 :http://m.blog.csdn.net/blog/huxiweng/8859399

反射机制及应用场景:  http://www.cnblogs.com/whoislcj/p/6038511.html

31.判断listvew是否到达顶部或底部

// 获得ListView的第一个item的视图
View firstChild = listView.getChildAt(0);
// 获得ListView当前显示的第一个item的id
int firstVisiblePos = listView.getFirstVisiblePosition();
if (firstVisiblePos == 0) {
System.out.println("当前显示的第一个条目是整个listview的第0条");
}
if (firstChild.getTop() == 0) {
System.out.println("已经到达顶部了");
}
// 获得ListView当前显示的最后一个item的id
int lastVisibalePos = listView.getLastVisiblePosition();
if (true) {

}

基本就是这么个情况,关于是否到达顶部,有方法,是否到达底部,你只需要把getChildAt()的参数传入listview的长度即可,调用getBottom方法,进行判断就可以了。


32.生成ViewHolder时,为什么建议使用static

https://github.com/android-cn/android-discuss/issues/65

非静态内部类隐式持有外部类的强引用。

其实这个是考静态内部类和非静态内部类的主要区别之一。非静态内部类会隐式持有外部类的引用,就像大家经常将自定义的adapter在Activity类里,然后在adapter类里面是可以随意调用外部activity的方法的。当你将内部类定义为static时,你就调用不了外部类的实例方法了,因为这时候静态内部类是不持有外部类的引用的。声明ViewHolder静态内部类,可以将ViewHolder和外部类解引用。大家会说一般ViewHolder都很简单,不定义为static也没事吧。确实如此,但是如果你将它定义为static的,说明你懂这些含义。万一有一天你在这个ViewHolder加入一些复杂逻辑,做了一些耗时工作,那么如果ViewHolder是非静态内部类的话,就很容易出现内存泄露。如果是静态的话,你就不能直接引用外部类,迫使你关注如何避免相互引用。
所以将 ViewHolder内部类 定义为静态的,是一种好习惯。

我认为正确使用ViewHolder的话,是否加static都不会造成内存泄露.
因为ViewHolder的生命周期一般比Adaper要短.

33.隐藏输入键盘和显示键盘

//关闭键盘输入法
public static void collapseSoftInputMethod(Context context, View v) {
if (v != null) {
InputMethodManager imm = (InputMethodManager) context.getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(v.getWindowToken(), 0);
}
}

//显示输入法
public static void showSoftInputMethod(Context context, View v) {
if (v != null) {
InputMethodManager imm = (InputMethodManager) context.getSystemService(Context.INPUT_METHOD_SERVICE);
imm.showSoftInput(v, 0);
}
}


34.网络检测

34.1检测网络是否可用

/**
* @Name: checkNetwork
* @Description: 检查当前网络
* @param: 无
* @return: true--有网络 false---无网络
*/
public boolean checkNetwork() {
ConnectivityManager conn = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo net = conn.getActiveNetworkInfo();
if (net != null && net.isConnected()) {
return true;
}
return false;
}

34.2 检测wifi是否可用

public boolean isWifiConnected(Context context) {
if (context != null) {
ConnectivityManager mConnectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo mWiFiNetworkInfo = mConnectivityManager.getNetworkInfo(ConnectivityManager.TYPE_WIFI);
if (mWiFiNetworkInfo != null) {
return mWiFiNetworkInfo.isAvailable();
}
}
return false;
}

34.3检测移动网络是否可用

public boolean isMobileConnected(Context context) {
if (context != null) {
ConnectivityManager mConnectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo mMobileNetworkInfo = mConnectivityManager.getNetworkInfo(ConnectivityManager.TYPE_MOBILE);
if (mMobileNetworkInfo != null) {
return mMobileNetworkInfo.isAvailable();
}
}
return false;
}

34.4 检测网络类型

public static int getConnectedType(Context context) {
if (context != null) {
ConnectivityManager mConnectivityManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo mNetworkInfo = mConnectivityManager.getActiveNetworkInfo();
if (mNetworkInfo != null && mNetworkInfo.isAvailable()) {
return mNetworkInfo.getType();
}
}
return -1;
}


35.receiver中开启service

receiver中只能使用startService(),不能使用bindService。开发文档规定的

36.Setting.System.getInt()/putInt()

receiver中只能使用getint,不能put,put能在activity中使用。今天发现在service中都不能使用getInt(),具体为什么,我tm也不知道。

37.listview判断是否到达顶部

// 获得ListView的第一个item的视图
View firstChild = listView.getChildAt(0);
// 获得ListView当前显示的第一个item的id
int firstVisiblePos = listView.getFirstVisiblePosition();
if (firstVisiblePos == 0) {
System.out.println("当前显示的第一个条目是整个listview的第0条");
}
if (firstChild.getTop() == 0) {
System.out.println("已经到达顶部了");
}
// 获得ListView当前显示的最后一个item的id
int lastVisibalePos = listView.getLastVisiblePosition();
if (true) {

}

基本就是这么个情况,关于是否到达顶部,有方法,是否到达底部,你只需要把getChildAt()的参数传入listview的长度即可,调用getBottom方法,进行判断就可以了。
listiew保存当前position'以及位置:http://www.cnblogs.com/xitang/p/3560652.html

38.在代码中修改TextView的drawableTop的图片

Drawable drawable= getResources().getDrawable(R.drawable.drawable); /// 这一步必须要做,否则不会显示.
drawable.setBounds(0, 0, drawable.getMinimumWidth(), drawable.getMinimumHeight());
myTextview.setCompoundDrawables(drawable,null,null,null);


39.JNI的cpp文件中打印可以在android的logcat查看的log

首先,关于cpp文件log的输出,打log,需要引入头文件,无非是两种

#include <utils/Log.h>和#include <cutils/Log.h>

两个文件不同的是,前者是android\system\core\include\utils下的Log.h文件

后者是android\system\core\include\cutils下的Log.h文件。

但是这两者又有什么区别呢。

打开首先打开cutils/Log.h看一下:只有一句话:  #include <log/log.h>

说明,即使是在cutils/Log.h,也只是引用了log/log.h

然后打开utils/Log.h,发现头文件出引用了



说明,最终使用的还是log\log.h文件的内容,这里面的内容就有很多了,就不一一赘述了。

按照常规方法,我在cpp文件中加入了log,内容为:LOGI("niejianjian_jni_log!!!");

但是,编译的时候,却报错,内容为:“LOGI” was not delcared in this scope,提示没有定义,这个时候,就要添加一些内容,才可以打印出log信息。

1.导入log头文件

例如:#include <utils/Log.h>

   #include <android/Log.h>

2.修改Android.mk文件

加上LOCAL_LDLIBS :=-llog

注意,这一句必须放在include $(CLEAR_VARS)后面,否则不生效

3.定义LOG函数

#define TAG "myDemo-jni" // 这个是自定义的LOG的标识  
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG,TAG ,__VA_ARGS__) // 定义LOGD类型  
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO,TAG ,__VA_ARGS__) // 定义LOGI类型  
#define LOGW(...) __android_log_print(ANDROID_LOG_WARN,TAG ,__VA_ARGS__) // 定义LOGW类型  
#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR,TAG ,__VA_ARGS__) // 定义LOGE类型  
#define LOGF(...) __android_log_print(ANDROID_LOG_FATAL,TAG ,__VA_ARGS__) // 定义LOGF类型 

定义完了之后,他们分别相当于android的java代码中的 Log.d(),Log.i()等方法。

下面举个例子。

我在cpp文件中先加入了log头文件,然后声明了一下内容:



然后我在代码中使用LOGI。内容如下:

LOGI("niejianjian_jni_log!!!");

最后,在DDMS的Logcat中查看打印的log结果如下:



到此,打印cpp打印log的方法就结束了。

参考博客:http://www.2cto.com/kf/201307/227148.html

40.16进制的byte数组打印成字符串

public static void main(String[] args) {

byte[] b = new byte[] { 0x02, 0x30, 0x40, 0x01 };

for (int i = 0; i < b.length; i++) {
// 打印出十进制
System.out.println(Byte.toString(b[i]));
}
System.out.println(bytesToHexString(b));

}

/**
* byte数组转换成16进制字符串
* @param src
* @return
*/
public static String bytesToHexString(byte[] src) {
StringBuilder stringBuilder = new StringBuilder();
if (src == null || src.length <= 0) {
return null;
}
for (int i = 0; i < src.length; i++) {
int v = src[i] & 0xFF;
String hv = Integer.toHexString(v);
if (hv.length() < 2) {
stringBuilder.append(0);
}
stringBuilder.append(hv);
}
return stringBuilder.toString();
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  android开发 onkeydown