android 的一些基础实现
1、 Notification后台运行,Notification构建随着api的更新一直在变,因此一般最新的设计方法都可以去参考谷歌的文档。
1、Notification的更新一般不是和activivity控件一样更新,而是重新构建一样的notification,然后用notify(ID,notification)来刷新通知,只要ID一样就会更新,如果没有就创建。
2、如播放器、FMRadio等需要长期后台运行的则外面可以用startForeground(ID,notification),通知栏一般就不会回收。
3、利用setStyle来设计notification的样式和一些action的显示:如下面谷歌文档里的一段代码:
setShowActionsInCompactView设计显示的action的数字,参数是int可变数组,显示相应的action事件
Notification notification = new Notification.Builder(context) // Show controls on lock screen even when user hides sensitive content. .setVisibility(Notification.VISIBILITY_PUBLIC) .setSmallIcon(R.drawable.ic_stat_player) // Add media control buttons that invoke intents in your media service .addAction(R.drawable.ic_prev, "Previous", prevPendingIntent) // #0 .addAction(R.drawable.ic_pause, "Pause", pausePendingIntent) // #1 .addAction(R.drawable.ic_next, "Next", nextPendingIntent) // #2 // Apply the media style template .setStyle(new Notification.MediaStyle() .setShowActionsInCompactView(1 /* #1: pause button */) .setMediaSession(mMediaSession.getSessionToken()) .setContentTitle("Wonderful music") .setContentText("My Awesome Band") .setLargeIcon(albumArtBitmap) .build();
2 、按返回键不退出应用而是后台运行(覆写back键)
关键性的一句是moveTaskToBack(false);
@Override public boolean onKeyDown(int keyCode, KeyEvent event) { if (keyCode == KeyEvent.KEYCODE_BACK) { moveTaskToBack(false); return true; } return super.onKeyDown(keyCode, event); }
3 listView的设置条目位置,setsetSelectionFromTop 无效
1、无效的原因应该是在点击的某个button时候出现了耗资源耗时操作,比如我遇到的是开启一个收音机的服务导致了listview界面自动刷新回到了listview的最上面,为了解决这个问题在item点击事件里面利用setSelectionFromTop强制指定位置时候无效果。listview的刷新是在启动服务后发生的,且启动服务是另外一个线程,因此就算setSelectionFromTop在启动服务代码后也是无效的,因为运行到setSelectionFromTop时候服务仍然没有开启起来,只有开启起来了listview才会进行刷新。因此必须采用一个异步的延时操作:
2、arg1.getTop()是获取当前条目离listview最上端的距离。arg1是listview的一个Item。
final int c = arg2; final int y = arg1.getTop(); mStationList.postDelayed(new Runnable() { @Override public void run() { mStationList.requestFocusFromTouch(); //int y =mStationList.getHeight()/2-mStationList.getHeight()/6; mStationList.setSelectionFromTop(c,y); } } , 150);
4 调用系统的时钟来倒计时
该函数是过duration毫秒后就发送广播SLEEP_EXPIRED_ACTION
private void setAlarmExpired (long duration) { Intent i = new Intent(SLEEP_EXPIRED_ACTION); //SLEEP_EXPIRED_ACTION是自定义的一个intent-fliter字段 AlarmManager am =(AlarmManager)getSystemService(Context.ALARM_SERVICE); PendingIntent pi = PendingIntent.getBroadcast(this, 0, i, 0); am.set(AlarmManager.ELAPSED_REALTIME_WAKEUP, SystemClock.elapsedRealtime() + duration, pi); }
5 获取系统当前时间时、分、秒
方法一:
public void gettime(){ Calendar c = Calendar.getInstance(); c.getTime();//Fri Nov 11 09:49:48 GMT+00:00 2016 System.out.println(c.getTime().toString()); int hour = c.get(Calendar.HOUR_OF_DAY); int minute = c.get(Calendar.MINUTE); int seconds = c.get(Calendar.SECOND); }
方法二:
public void gettime(){ Date date = new Date(); SimpleDateFormat format = new SimpleDateFormat("yyyyMMddHHmmss"); // 格式化时间 String filename = format.format(date); System.out.println("cacccccccccccc"+ filename);//20161111095330,2016,11.11 9:53:30 }
6 n次点击事件的实现
int n =4; long a[] = new long[n]; public void click(View view) { long currentTimeMillis = System.currentTimeMillis(); for(int i = 0 ; i < n - 1; i ++) { a[i] = a[i+1]; } a[n-1]=currentTimeMillis; if(a[n-1] - a[0] < 500) { Toast.makeText(this , n+"点击成功" , Toast.LENGTH_SHORT).show(); a = new long[n]; } }
7、android 获取手机所有应用,查询所以的action,将隐式intent转化为显示intent的方法。和查询手机里的应用服务广播等操作。
见博客:http://www.cnblogs.com/bokeofzp/p/6044595.html 的第三节中的隐式转显示intetnt的函数
8、android截取手机屏幕(截屏)
1、利用view来获取:会有像素的损失。原因在于view.buildDrawingCache();时候源码里实现时有个drawingCacheSize,当大于这个值时候会销毁掉,因此2、3行重新约束了下view的大小。
public Bitmap myShot2(Activity activity) { // 获取windows中最顶层的view View view = activity.getWindow().getDecorView(); view.measure(View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED), View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED)); view.layout(0, 0, view.getMeasuredWidth(), view.getMeasuredHeight()); view.buildDrawingCache(); return view.getDrawingCache(); }
2、利用画布来将屏幕图像画入图片,这种方式获得屏幕截图清晰度高
public Bitmap myShot3(View view) { View view2 = this.getWindow().getDecorView(); Bitmap bitmap = Bitmap.createBitmap(view2.getWidth(), view2.getHeight(), Bitmap.Config.ARGB_8888); //利用bitmap生成画布 Canvas canvas = new Canvas(bitmap); //把view中的内容绘制在画布上 view2.draw(canvas); return bitmap }
9、android从图库、拍照获取图片的实现
public void takePhoto(View view) { if(bitmap2!=null&&!bitmap2.isRecycled()) bitmap2.recycle(); Intent imageIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE); File dir = new File(imagepath); if (!dir.exists()) { dir.mkdirs(); } imagepath= Environment.getExternalStorageDirectory()+"/zp.jpg"; File file = new File(imagepath); imageIntent.putExtra(MediaStore.EXTRA_OUTPUT,Uri.fromFile(file)); //会将拍的的照片存在该文件imagepath imageIntent.putExtra(MediaStore.EXTRA_VIDEO_QUALITY, 1); startActivityForResult(imageIntent,CAPTURE_IMAGE_ACTIVITY_REQUEST_CODE); System.out.println(imagepath); } public void gallery(View view) { if(bitmap!=null&&!bitmap.isRecycled()) bitmap.recycle(); Intent intent = new Intent(Intent.ACTION_GET_CONTENT); intent.setType("image/*"); intent.putExtra("crop", true); intent.putExtra("return-data", true); startActivityForResult(intent, PICK_IMAGE); } @Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { // if(data == null) // return; //从图库获取的回调处理 if(requestCode == PICK_IMAGE) { Uri uri =data.getData();//com.android.providers.media.documents/document/image%3A56 ContentResolver contentResolver = getContentResolver(); try { InputStream inputStream = contentResolver.openInputStream(uri); bitmap2 = BitmapFactory.decodeStream(inputStream); imageView.setImageBitmap(bitmap2); } catch (FileNotFoundException e) { e.printStackTrace(); } } //从相机的回调处理 else if(requestCode == CAPTURE_IMAGE_ACTIVITY_REQUEST_CODE ) { bitmap2 = BitmapFactory.decodeFile(imagepath); imageView.setImageBitmap(bitmap2); } super.onActivityResult(requestCode, resultCode, data); }
10、屏幕分辨率
方法一:
DisplayMetrics dm = new DisplayMetrics(); getWindowManager().getDefaultDisplay().getMetrics(dm); screenWidth = dm.widthPixels; getScreenHeight = dm.heightPixels;
方法二:
Display display = getWindowManager().getDefaultDisplay(); //过时getWidth // System.out.println("kkkkkkkkkkkkkkk2"+ display.getWidth()); Point point = new Point(); display.getSize(point); screenWidth = point.x; getScreenHeight = point.y;
方法三:
DisplayMetrics dm2 = getResources().getDisplayMetrics(); System.out.println("heigth2 : " + dm2.heightPixels); System.out.println("width2 : " + dm2.widthPixels);
11、代码中动态全屏和关闭全屏
** * 动态设置全屏 */ private void setFullScreen(){ getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN); } /** * 动态取消全屏 */ private void quitFullScreen(){ final WindowManager.LayoutParams attrs = getWindow().getAttributes(); attrs.flags &= (~WindowManager.LayoutParams.FLAG_FULLSCREEN); getWindow().setAttributes(attrs); getWindow().clearFlags(WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS); }
12、一些屏幕触控获取坐标或者距离的函数的区别
13、获取当前应用的名字
public String getCurrentActivityName() { if (mActivityManager == null) { mActivityManager = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE); } List<RunningTaskInfo> rti = mActivityManager.getRunningTasks(1); String currentTaskName = rti.get(0).topActivity.getPackageName(); return currentTaskName; }
14、通过intent查询intent的服务或者activity的包名类名(如查询桌面应用包名,和类名)
/** * 获得属于桌面的应用的应用包名称 * * @return 返回桌面的应用的应用包名称 */ private String getHomePackageName() { PackageManager packageManager = this.getPackageManager(); // 属性 Intent intent = new Intent(Intent.ACTION_MAIN); intent.addCategory(Intent.CATEGORY_HOME); List<ResolveInfo> mResolveInfo = packageManager.queryIntentActivities( //若是服务可以用queryIntentServices查询 intent, PackageManager.MATCH_DEFAULT_ONLY); // Make sure only one match was found if (mResolveInfo == null || mResolveInfo.size() != 1) { return null; } ResolveInfo resolveInfo = mResolveInfo.get(0); String packageName = resolveInfo.serviceInfo.packageName; //获取包 String className = resolveInfo.serviceInfo.name; //获取类名(全路径) ComponentName component = new ComponentName(packageName, className); return packageName; }
15、修改菜单的那3个点图标
在主题中添加下面的那条属性,然后在引用的style中添加图片资源
<resources> <!-- Base application theme for API 14+. This theme completely replaces AppBaseTheme from BOTH res/values/styles.xml and res/values-v11/styles.xml on API 14+ devices. --> <style name="AppBaseTheme" parent="Theme.AppCompat.Light.DarkActionBar"> <!-- API 14 theme customizations can go here. --> <item name="android:actionOverflowButtonStyle">@style/OverflowStyle</item> </style> <style name="OverflowStyle"> <item name="android:src">@drawable/actionbar_add_icon</item> </style> </resources>
16 、让屏幕长亮
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
17 获取屏幕长宽:
WindowManager wm = (WindowManager) getContext() .getSystemService(Context.WINDOW_SERVICE); screenWidth = wm.getDefaultDisplay().getWidth(); screenHeight = wm.getDefaultDisplay().getHeight();
18 字体颜色渐变 参考:http://blog.csdn.net/le_go/article/details/39154289
1、自定义控件 在layout 中设置paint 的属性。
2、在代码中设置
TextView mText = (TextView) findViewById(R.id.text); LinearGradient mLinearGradient = new LinearGradient(0, 0, 0, mText.getPaint().getTextSize(), Color.WHITE, Color.BLACK, Shader.TileMode.CLAMP); mText.getPaint().setShader(mLinearGradient);
18 背景颜色渐变,drawable中绘制:
<shape xmlns:android="http://schemas.android.com/apk/res/android"> <gradient android:startColor="#ff0000" android:endColor="#FFFF00" android:angle="90" /> </shape>