Android5.0开发范例大全 读书笔记(四)

(三)通信和联网

3.1显示Web信息

1.WebView通过loadUrl()方法直接访问网页时,点击跳转链接会打开系统默认的浏览器,若要拦截WebView事件,可为其添加WebViewClient

webView.setWebViewClient(new WebViewClient())

2.WebView默认不支持JavaScript,要通过setJavaScriptEnabled()进行设置

 webView.getSettings().setJavaScriptEnabled(true);

3.WebView可以直接显示Html内容

3.4下载图片文件

1.自定义一个ImageView控件,实现资源的下载与显示

值得一提的是,设置本地资源应该提供2个方法,一个通过资源id获取,一个通过drawable获取

网络下载可以通过asynctask实现,要注意不要在doInBackground()中更新UI线程

下面附上完整代码

public class WebImageView extends ImageView {
    private Drawable mPlaceholder, mImage;

    public WebImageView(Context context) {
        this(context, null);
    }

    public WebImageView(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public WebImageView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    public void setPlaceholderImage(Drawable drawable) {
        mPlaceholder = drawable;
        if (mImage == null) {
            setImageDrawable(mPlaceholder);
        }
    }

    public void setPlaceholderImage(int resid) {
        mPlaceholder = getResources().getDrawable(resid);
        System.out.println(1);
        if (mImage == null) {
            System.out.println(2);
            setImageDrawable(mPlaceholder);
        }
    }

    public void setImageUrl(String url) {
        DownloadTask task = new DownloadTask();
        task.execute(url);
    }

    private class DownloadTask extends AsyncTask<String, Void, Bitmap> {

        @Override
        protected Bitmap doInBackground(String... params) {
            String url = params[0];
            try {
                URLConnection connection = (new URL(url)).openConnection();
                InputStream is = connection.getInputStream();
                return BitmapFactory.decodeStream(is);
            } catch (IOException e) {
                e.printStackTrace();
                return null;
            }
        }

        @Override
        protected void onPostExecute(Bitmap bitmap) {
            mImage = new BitmapDrawable(getContext().getResources(), bitmap);
            setImageDrawable(mImage);
        }
    }
}

3.5完全在后台下载

1.DownloadManager适合处理和管理需要长时间运行的下载操作。其优点是即使在下载失败,链接改变甚至设备重启时,依然会继续尝试下载

2.首先实现一个广播接收者来监听下载状态

 private BroadcastReceiver receiver=new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            queryDownloadStatus();
        }
    };

    private void queryDownloadStatus(){
        DownloadManager.Query query=new DownloadManager.Query();
        query.setFilterById(prefs.getLong(DL_ID,0));
        Cursor c=dm.query(query);
        if(c.moveToFirst()){
            int status=c.getInt(c.getColumnIndex(DownloadManager.COLUMN_STATUS));
            switch (status){
                case DownloadManager.STATUS_PAUSED:
                case DownloadManager.STATUS_PENDING:
                case DownloadManager.STATUS_RUNNING:
                    break;
                case DownloadManager.STATUS_SUCCESSFUL:
                    try {
                        ParcelFileDescriptor file=dm.openDownloadedFile(prefs.getLong(DL_ID,0));
                        FileInputStream fis=new ParcelFileDescriptor.AutoCloseInputStream(file);
                        imageView.setImageBitmap(BitmapFactory.decodeStream(fis));
                        Toast.makeText(this,"download over!",Toast.LENGTH_SHORT).show();
                    } catch (FileNotFoundException e) {
                        e.printStackTrace();
                    }
                    break;
                case DownloadManager.STATUS_FAILED:
                    dm.remove(prefs.getLong(DL_ID, 0));
                    prefs.edit().clear().apply();
                    break;
            }
        }
    }

3.接着获取系统服务

dm= (DownloadManager) getSystemService(DOWNLOAD_SERVICE);

4.最后,在onResume中注册广播并开始下载

 @Override
    protected void onResume() {
        super.onResume();
        if(!prefs.contains(DL_ID)){
            Uri resource=Uri.parse("http://f2.market.xiaomi.com/download/AppChannel/0965d34f016634cb83347f609306d9a3fa045a9c5/com.netease.onmyoji.mi.apk");
            DownloadManager.Request request=new DownloadManager.Request(resource);
            request.setAllowedNetworkTypes(DownloadManager.Request.NETWORK_MOBILE| DownloadManager.Request.NETWORK_WIFI);
            request.setTitle("Download Sample");
            request.setDescription("Download SSR!");
            request.setAllowedOverRoaming(false);
            long id=dm.enqueue(request);
            prefs.edit().putLong(DL_ID,id).apply();
        }else{
            queryDownloadStatus();
        }
        registerReceiver(receiver,new IntentFilter(DownloadManager.ACTION_DOWNLOAD_COMPLETE));
    }

3.10发送短信

1.与之前的DownloadManager一样,发送短信的SmsManager也是系统级服务,二者的调用极为相似

2..首先实现广播接收者,发送短信一共有2个接受者,一个返回发送是否成功

private BroadcastReceiver sent = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            switch (getResultCode()) {
                case Activity.RESULT_OK:
                    Toast.makeText(SendSmsActivity.this, "发送成功", Toast.LENGTH_SHORT).show();
                    break;
                case SmsManager.RESULT_ERROR_GENERIC_FAILURE:
                case SmsManager.RESULT_ERROR_NO_SERVICE:
                case SmsManager.RESULT_ERROR_NULL_PDU:
                case SmsManager.RESULT_ERROR_RADIO_OFF:
                    Toast.makeText(SendSmsActivity.this, "发送失败", Toast.LENGTH_SHORT).show();
                    break;
            }
        }
    };

另一个返回接收是否成功

private BroadcastReceiver delivered = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            switch (getResultCode()) {
                case Activity.RESULT_OK:
                    Toast.makeText(SendSmsActivity.this, "传递成功", Toast.LENGTH_SHORT).show();
                    break;
                case Activity.RESULT_CANCELED:
                    Toast.makeText(SendSmsActivity.this, "传递失败", Toast.LENGTH_SHORT).show();
                    break;
            }
        }
    };

3.接着,分别在resume和pause中注册和注销广播

 @Override
    protected void onResume() {
        super.onResume();
        registerReceiver(sent, new IntentFilter(ACTION_SENT));
        registerReceiver(delivered,new IntentFilter(ACTION_DELIVERED));
    }
 @Override
    protected void onPause() {
        super.onPause();
        unregisterReceiver(sent);
        unregisterReceiver(delivered);
    }

4.最后调用SmsManager即可

private void sendSms(String msg) {
        PendingIntent sIntent = PendingIntent.getBroadcast(this, 0, new Intent(ACTION_SENT),0);
        PendingIntent dIntent = PendingIntent.getBroadcast(this, 0, new Intent(ACTION_DELIVERED),0);
        SmsManager manager=SmsManager.getDefault();
        manager.sendTextMessage(RECIPIENT_ADDRESS,null,msg,sIntent,dIntent);

    }

3.11蓝牙通信

1.蓝牙通信需要获取权限

 <uses-permission android:name="android.permission.BLUETOOTH" />
 <uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />

2.有时蓝牙并没有开启,所以要通过startActivityForResult启动

Intent enableIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
startActivityForResult(enableIntent, REQUEST_ENABLE);

3.此时应该设置一个onActivityResult方法来获取蓝牙的启动情况

@Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        switch (requestCode) {
            case REQUEST_ENABLE:
                if (resultCode != RESULT_OK) {
                    Toast.makeText(this, "蓝牙启动失败", Toast.LENGTH_SHORT).show();
                    finish();
                }
                break;
            case REQUEST_DISCOVERABLE:
                if (resultCode == RESULT_CANCELED) {
                    Toast.makeText(this, "蓝牙必须被设置为可见", Toast.LENGTH_SHORT).show();
                    finish();
                } else {
                    startListening();
                }
                break;
            default:
                break;
        }
    }

4.蓝牙功能分两方,一方让设备处于监听状态,监听其他设备的连入

listenButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                email = emailField.getText().toString();
                if (mBtAdapter.getScanMode() != BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) {
                    Intent discoverableIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE);
                    discoverableIntent.putExtra(BluetoothAdapter.EXTRA_DISCOVERABLE_DURATION, 3000);
                    startActivityForResult(discoverableIntent, REQUEST_DISCOVERABLE);
                }
                startListening();
            }

        });

监听时要用到唯一的UUID

private void startListening() {
        AcceptTask task = new AcceptTask();
        task.execute(MY_UUID);
        setProgressBarIndeterminateVisibility(true);
    }

5.另一方要让设备扫描可连入的设备,主要通过startDiscovery()方法

scanButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                email = emailField.getText().toString();
                mBtAdapter.startDiscovery();
                setProgressBarIndeterminateVisibility(true);
            }
        });

6.程序要使用2个AsyncTask来执行具体的功能,一个用来连接

private class AcceptTask extends AsyncTask<UUID, Void, BluetoothSocket> {

        @Override
        protected BluetoothSocket doInBackground(UUID... params) {
            String name = mBtAdapter.getName();
            mBtAdapter.setName(SEARCH_NAME);
            try {
                BluetoothServerSocket socket = mBtAdapter.listenUsingRfcommWithServiceRecord("BluetoothRecipe", params[0]);
                BluetoothSocket connected = socket.accept();
                mBtAdapter.setName(name);
                return connected;
            } catch (IOException e) {
                e.printStackTrace();
                mBtAdapter.setName(name);
                return null;
            }
        }

        @Override
        protected void onPostExecute(BluetoothSocket bluetoothSocket) {
            mBtSocket = bluetoothSocket;
            ConnectedTask task = new ConnectedTask();
            task.execute(mBtSocket);

        }
    }

7.另一个用来传输数据

 private class ConnectedTask extends AsyncTask<BluetoothSocket, Void, String> {

        @Override
        protected String doInBackground(BluetoothSocket... params) {
            InputStream in = null;
            OutputStream out = null;
            try {
                //发送数据
                out = params[0].getOutputStream();
                out.write(email.getBytes());
                //接受其他数据
                in = params[0].getInputStream();
                byte[] buffer = new byte[1024];
                in.read(buffer);
                String result = new String(buffer);
                mBtSocket.close();
                return result.trim();
            } catch (IOException e) {
                e.printStackTrace();
                return null;
            }
        }

        @Override
        protected void onPostExecute(String result) {
            Toast.makeText(ExchangeActivity.this, result, Toast.LENGTH_SHORT).show();
            setProgressBarIndeterminateVisibility(false);

        }
    }

8.两个AsyncTask之间使用BroadCast进行连接

private BroadcastReceiver mReceiver = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            String action = intent.getAction();
            if (BluetoothDevice.ACTION_FOUND.equals(action)) {
                BluetoothDevice device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
                if (device.getName().equals(SEARCH_NAME)) {
                    mBtAdapter.cancelDiscovery();
                    try {
                        mBtSocket = device.createRfcommSocketToServiceRecord(MY_UUID);
                        mBtSocket.connect();
                        ConnectedTask task = new ConnectedTask();
                        task.execute(mBtSocket);
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            } else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(action)) {
                setProgressBarIndeterminateVisibility(false);
            }
        }
    };

9.广播接收者分别在resume和pause中注册和注销

@Override
    protected void onResume() {
        super.onResume();
        IntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_FOUND);
        registerReceiver(mReceiver, filter);
        filter = new IntentFilter(BluetoothAdapter.ACTION_DISCOVERY_FINISHED);
        registerReceiver(mReceiver, filter);
    }

10.create中一些初始化信息

 requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
        setContentView(R.layout.activity_exchange);
        mBtAdapter = BluetoothAdapter.getDefaultAdapter();
        if (mBtAdapter == null) {
            Toast.makeText(this, "不支持蓝牙", Toast.LENGTH_SHORT).show();
            finish();
        }
        //开启蓝牙
        if (!mBtAdapter.isEnabled()) {
            Intent enableIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
            startActivityForResult(enableIntent, REQUEST_ENABLE);
        }
        emailField = (EditText) findViewById(R.id.emailField);

11.退出时将蓝牙的Socket清除

 @Override
    protected void onDestroy() {
        super.onDestroy();
        if (mBtSocket != null) {
            try {
                mBtSocket.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

 3.12查询网络状态

1.通过系统服务ConnectivityManager来获取网络状态

2.是否可以获取网络

public static boolean isNetworkReachable(Context context) {
        final ConnectivityManager mManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo current = mManager.getActiveNetworkInfo();
        return current != null && current.getState() == NetworkInfo.State.CONNECTED;
    }

3.是否可以获取wifi

public static boolean isWifiReachable(Context context) {
        final ConnectivityManager mManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo current = mManager.getActiveNetworkInfo();
        return current != null && current.getType() == ConnectivityManager.TYPE_WIFI;
    }
时间: 2024-11-05 13:44:49

Android5.0开发范例大全 读书笔记(四)的相关文章

Android5.0开发范例大全 读书笔记(六)

(六)与系统交互 6.1后台通知 1.关于后台通知,下面展示6种样式.值得一提的是,笔者的小米5只能显示基本样式,雷军真是良心厂商啊. 2.首先上布局xml <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="

Android5.0开发范例大全 读书笔记(五)

(四)实现设备硬件交互与媒体交互 4.6自定义摄像头覆盖层 1.将Camera中的内容实时的绘制到SurfaceView中 若要自定义拍摄界面,只要重新定义surface的界面即可 以下展示全部代码 public class PreviewActivity extends AppCompatActivity implements SurfaceHolder.Callback { Camera mCamera; SurfaceView mPreview; @Override protected v

Android5.0开发范例大全 读书笔记(二)

(二)用户交互  2.1ActionBar 1.首先,调用onCreateOptionsMenu(Menu menu)方法为actionbar设置样式 @Override public boolean onCreateOptionsMenu(Menu menu) { getMenuInflater().inflate(R.menu.support,menu); return true; } res/menu/support.xml如下 <?xml version="1.0" en

Android5.0开发范例大全 读书笔记(三)

(二)用户交互 2.14转发触摸事件 1.TouchDelegate很适合简单的触摸转发,它指定任意的矩形区域来向小视图转发触摸事件,其缺点是每个被转发的事件都会转发到代理视图的中间位置 public class TouchDelegateLayout extends FrameLayout { public TouchDelegateLayout(Context context) { this(context, null); } public TouchDelegateLayout(Conte

JavaScript、jQuery、HTML5、Node.js实例大全-读书笔记2

技术很多,例子很多,只好慢慢学,慢慢实践!!现在学的这本书是[JavaScript实战----JavaScript.jQuery.HTML5.Node.js实例大全] JavaScript.jQuery.HTML5.Node.js实例大全-读书笔记1 3.2 照片加载与定位 根据功能设计,可以先写好 HTML 结构基础,再配好 CSS 做出大致效果,最后用 JavaScript加上各种动作.首先请看 HTML 代码结构. 3.2.1 HTML 代码 CSS代码保存到 eg3.css 文件中,Ja

R实战读书笔记四

第三章 图形入门 本章概要 1 创建和保存图形 2 定义符号.线.颜色和坐标轴 3 文本标注 4 掌控图形维数 5 多幅图合在一起 本章所介绍内容概括如下. 一图胜千字,人们从视觉层更易获取和理解信息. 图形工作 R具有非常强大的绘图功能,看下面代码. > attach(mtcars) > plot(wt, mpg) > abline(lm(mpg~wt)) > title("Regression of MPG on Weight") > detach(m

android5.0开发必备版本和JDK环境配置

android5.0开发必备版本: JDK-1.8-x64; NDK-10-x64; ADT-5.0&4.0-x64; 谷歌代理: https://wen.lu/?gfe_rd=cr&ei=Ir7YU5XsOK3J8ge_24GgBQ&gws_rd=cr 也可用FQ软件:goagent,或FQ浏览器 goagent: https://github.com/goagent/goagent 配置地址:http://www.woshipm.com/it/13644.html JDK配置(

《JavaScript设计模式与开发实践》读书笔记之观察者模式

1.<JavaScript设计模式与开发实践>读书笔记之观察者模式 观察者模式定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都将得到通知. JavaScript中通常采用事件模型替代传统的观察者模式 1.1 逐步实现观察者模式 以客户看房为例 首先指定谁充当发布者,如售楼处 然后给发布者添加一个缓存列表,用于存放回调函数以便通知订阅者.这里为了让订阅者只接收自己感兴趣的消息,增加一个标识key 最后发布消息时候,发布者遍历缓存列表,依次触发里面存放的订阅者的回

《高效能程序员的修炼》读书笔记四

第一章第三节:如何培养写作习惯 -------------------------------- 我个人一直坚信要成为一名优秀的程序员,其实和写代码是没有多大关系的(刚好本书作者也是这样的想法).当然,作为一名程序员的话,具有一定水平的技术能力还是需要的.但,个人觉得更重要的是良好地沟通技巧. 本书作者的合伙人Joel Spolsky有过这样一段话: 杰出的程序员跟勉强过得去的程序员之间的差别,不在于他们掌握了多少种编程语言,也不在于他们谁更擅长Python或Java.真正的关键是,他们能不能把