android 傳送檔案

38
Android 傳傳傳傳 傳傳傳傳傳傳 傳傳傳 傳傳傳 2013/7 V1

Upload: howie

Post on 22-Jan-2016

108 views

Category:

Documents


3 download

DESCRIPTION

Android 傳送檔案. 建國科技大學 資管系 饒瑞佶 2013/7 V1. Android 傳送檔案. 透過 Intent 透過 BluetoothShare.java 部分 SDK 不能使用 透過標準 Bluetooth Service 與 socket Client vs. Server. 需要的權限. - PowerPoint PPT Presentation

TRANSCRIPT

Page 1: Android 傳送檔案

Android 傳送檔案

建國科技大學 資管系饒瑞佶

2013/7 V1

Page 2: Android 傳送檔案

Android 傳送檔案

• 透過 Intent• 透過 BluetoothShare.java–部分 SDK 不能使用

• 透過標準 Bluetooth Service 與socket–Client vs. Server

Page 3: Android 傳送檔案

需要的權限<uses-permission

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

android:name="android.permission.BLUETOOTH_ADMIN"/>

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

Page 4: Android 傳送檔案

提醒• 手機需要開啟藍芽• 需要設定成可以被偵測

Page 5: Android 傳送檔案

透過 Intent

Sdcard 卡內檔案

Page 6: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Page 7: Android 傳送檔案

Server

Page 8: Android 傳送檔案

透過標準 Bluetooth Service與 socketServer

Page 9: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Server - onCreate @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); image = (ImageView) findViewById(R.id.imageView1); mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); if (mBluetoothAdapter == null) { Toast.makeText(this,"Bluetooth is not available.",Toast.LENGTH_LONG).show(); finish(); return; }

Page 10: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Server - onCreateif (!mBluetoothAdapter.isEnabled()) { Toast.makeText(this,"Please enable your BT and re-run this program.",Toast.LENGTH_LONG).show(); finish(); return; } tv=(TextView) findViewById(R.id.textView1); tv.setText(" 請開啟接收! "); tv.setTextColor(Color.BLUE); // 按掃描按鈕,啟動掃描藍芽設備 Button scanButton = (Button) findViewById(R.id.button_scan); scanButton.setOnClickListener(new OnClickListener() { public void onClick(View v) { AcceptData acceptData = new AcceptData(); acceptData.start(); Bitmap bm1 = BitmapFactory.decodeByteArray(buffer, 0, buffer.length); image.setImageBitmap(bm1); } }); }

Page 11: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Server - class AcceptData // 接收圖片 class AcceptData extends Thread{ private final BluetoothServerSocket mmServerSocket; private BluetoothSocket socket = null; private InputStream mmInStream; private String device; public AcceptData() { BluetoothServerSocket tmp = null; try { tmp = mBluetoothAdapter.listenUsingRfcommWithServiceRecord("Bluetooth", MY_UUID); } catch (IOException e) { // }

Page 12: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Server - class AcceptData mmServerSocket = tmp; try { socket = mmServerSocket.accept(); } catch (IOException e) { // } device = socket.getRemoteDevice().getName(); Toast.makeText(getBaseContext(), " 接收來自 " + device + " 的資料 ", Toast.LENGTH_SHORT).show(); InputStream tmpIn = null; try { tmpIn = socket.getInputStream(); } catch (IOException e) { // }

Page 13: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Server - class AcceptData mmInStream = tmpIn; int byteNo; try { byteNo = mmInStream.read(buffer); if (byteNo != -1) { //ensure DATAMAXSIZE Byte is read. int byteNo2 = byteNo; int bufferSize = 500000; //7340; while(byteNo2 != bufferSize){ bufferSize = bufferSize - byteNo2; byteNo2 = mmInStream.read(buffer,byteNo,bufferSize); if(byteNo2 == -1){ break; } byteNo = byteNo+byteNo2; } }

Page 14: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Server - class AcceptData if (socket != null) { try { mmServerSocket.close(); tv.setText(" 請重新開啟接收! "); tv.setTextColor(Color.RED); } catch (IOException e) { // } } } catch (Exception e) { try {mmServerSocket.close();tv.setText(" 請重新開啟接收! ");tv.setTextColor(Color.RED);} catch (IOException e1) {e1.printStackTrace();} } }}

Page 15: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Server - menu

Page 16: Android 傳送檔案

layout<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_parent" android:orientation="vertical" > <ImageView android:id="@+id/imageView1" android:layout_width="wrap_content" android:layout_height="wrap_content" />

<TextView android:id="@+id/textView1" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="xxx" android:textSize="20sp" />

<Button android:id="@+id/button_scan" android:layout_width="match_parent" android:layout_height="wrap_content" android:text=" 開啟接收 " /> </LinearLayout>

Page 17: Android 傳送檔案

Client

Page 18: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Client

Page 19: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Client-onCreate @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS); setContentView(R.layout.client); // 判斷設備是否支援藍芽 mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); if (mBluetoothAdapter == null) { Toast.makeText(this,"您的設備不支援藍芽! ",Toast.LENGTH_LONG).show(); finish(); return; }

Page 20: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Client-onCreate // 如果藍芽沒有開啟,會要求開啟 if (!mBluetoothAdapter.isEnabled()) { Toast.makeText(this,"請開啟藍芽! ",Toast.LENGTH_LONG).show(); Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE); startActivityForResult(enableBtIntent,REQUEST_ENABLE_BT); } setResult(Activity.RESULT_CANCELED); // 按掃描按鈕,啟動掃描藍芽設備 Button scanButton = (Button) findViewById(R.id.button_scan); scanButton.setOnClickListener(new OnClickListener() { public void onClick(View v) { doDiscovery(); v.setVisibility(View.GONE); } });

Page 21: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Client-onCreate // 已配對設備列表 mArrayAdapter = new ArrayAdapter<String>(this, R.layout.device_name); ListView pairedListView = (ListView) findViewById(R.id.paired_devices); pairedListView.setAdapter(mArrayAdapter); // 設定按了後的事件 pairedListView.setOnItemClickListener(mDeviceClickListener);

// 其他設備列表 mNewDevicesArrayAdapter = new ArrayAdapter<String>(this, R.layout.device_name); ListView newDevicesListView = (ListView) findViewById(R.id.new_devices); newDevicesListView.setAdapter(mNewDevicesArrayAdapter);

Page 22: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Client-onCreate // 設定按了後的事件 pairedListView.setOnItemClickListener(mDeviceClickListener);

// 其他設備列表 mNewDevicesArrayAdapter = new ArrayAdapter<String>(this, R.layout.device_name); ListView newDevicesListView = (ListView) findViewById(R.id.new_devices); newDevicesListView.setAdapter(mNewDevicesArrayAdapter); // 設定按了後的事件 newDevicesListView.setOnItemClickListener(mDeviceClickListener);

Page 23: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Client-onCreate // 註冊廣播,回報設備掃描 IntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_FOUND); this.registerReceiver(mReceiver, filter); // 註冊廣播,回報設備掃描完成 filter = new IntentFilter(BluetoothAdapter.ACTION_DISCOVERY_FINISHED); this.registerReceiver(mReceiver, filter); Set<BluetoothDevice> pairedDevices = mBluetoothAdapter.getBondedDevices(); // 如果有配對的設備 if (pairedDevices.size() > 0) { // 將所有配對列表加入 for (BluetoothDevice device : pairedDevices) {

Page 24: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client-onCreate // 將設備名稱與 MAC 加入列表 mArrayAdapter.add(device.getName() + "\n" + device.getAddress()); } }else{ mArrayAdapter.add(" 沒發現設備 "); } // 傳送圖片 Button sendButton = (Button) findViewById(R.id.send); sendButton.setOnClickListener(new OnClickListener() { public void onClick(View view) { if("".equals(address)){ Toast.makeText(SendingdataActivity.this,"您尚未選擇傳送對象! ",Toast.LENGTH_LONG).show(); return; }else{ SendData sendData = new SendData(); sendData.sendMessage(); } } }); }

Page 25: Android 傳送檔案

透過標準 Bluetooth Service與 socket

Client - doDiscovery() // 掃描設備 private void doDiscovery() { // 設定是窗抬頭 setProgressBarIndeterminateVisibility(true); setTitle(" 掃描中,請稍待 "); // 開啟其他設備標題 findViewById(R.id.title_new_devices).setVisibility(View.VISIBLE); // 掃描完成,停止 if (mBluetoothAdapter.isDiscovering()) { mBluetoothAdapter.cancelDiscovery(); } // 開始掃描 mBluetoothAdapter.startDiscovery(); }

Page 26: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client - BroadcastReceiver // BroadcastReceiver private final BroadcastReceiver mReceiver = new BroadcastReceiver() { @Override public void onReceive(Context context, Intent intent) { String action = intent.getAction(); // 如果有發現任何藍芽設備 if (BluetoothDevice.ACTION_FOUND.equals(action)) { // 透過 INTENT 取得其他藍芽設備 BluetoothDevice device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE); // 略過已配對設備,加入新其他設備 if (device.getBondState() != BluetoothDevice.BOND_BONDED) { mNewDevicesArrayAdapter.add(device.getName() + "\n" + device.getAddress()); } // 搜尋結束後,更改抬頭 } else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(action)) { setProgressBarIndeterminateVisibility(false); setTitle(" 請選擇設備 "); if (mNewDevicesArrayAdapter.getCount() == 0) { mNewDevicesArrayAdapter.add(" 沒發現設備 "); } } } };

Page 27: Android 傳送檔案

透過標準 Bluetooth Service 與 socketClient - OnItemClickListener

// 按了列表上的某個設備後進行的動作 private OnItemClickListener mDeviceClickListener = new OnItemClickListener() { public void onItemClick(AdapterView<?> av, View v, int arg2, long arg3) { // 取得設備 MAC address String info = ((TextView) v).getText().toString(); address = info.substring(info.length() - 17); //藍芽設備 MAC Toast.makeText(SendingdataActivity.this,"選擇傳送到 " + info,Toast.LENGTH_LONG).show(); } };

Page 28: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client - SendData // 傳送檔案 class SendData extends Thread { private BluetoothDevice device = null; private BluetoothSocket btSocket = null; private OutputStream outStream = null;

public SendData(){ device = mBluetoothAdapter.getRemoteDevice(address); try { btSocket = device.createRfcommSocketToServiceRecord(MY_UUID); } catch (Exception e) { // TODO: handle exception } mBluetoothAdapter.cancelDiscovery();

Page 29: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client - SendData try { btSocket.connect(); } catch (IOException e) { try { btSocket.close(); } catch (IOException e2) { } } Toast.makeText(getBaseContext(), "Connected to " + device.getName(), Toast.LENGTH_SHORT).show(); try { outStream = btSocket.getOutputStream(); } catch (IOException e) { } }

Page 30: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client - SendData public void sendMessage() { try { //mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter(); //sdcard 內圖片 String imgFilePath = Environment.getExternalStorageDirectory().toString() + "/translate.png"; FileInputStream fis = new FileInputStream(new File(imgFilePath)); Bitmap bm = BitmapFactory.decodeStream(fis); //Bitmap bm = BitmapFactory.decodeResource(getResources(), R.drawable.ic_launcher); ByteArrayOutputStream baos = new ByteArrayOutputStream();

Page 31: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client - SendDatabm.compress(Bitmap.CompressFormat.JPEG, 100,baos); //bm is the bitmap object byte[] b = baos.toByteArray(); //Toast.makeText(getBaseContext(), "size:" + String.valueOf(b.length), Toast.LENGTH_SHORT).show(); outStream.write(b); outStream.flush(); outStream.close(); btSocket.close(); } catch (IOException e) { return; } } }

Page 32: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client - onDestroy // 取消 BluetoothAdapter 與廣播註冊 @Override protected void onDestroy() {if (mBluetoothAdapter != null) {mBluetoothAdapter.cancelDiscovery(); } // Unregister broadcast listeners this.unregisterReceiver(mReceiver);super.onDestroy(); }

Page 33: Android 傳送檔案

透過標準 Bluetooth Service 與socket

Client - menu // 設定 menu 選項 @Override public boolean onCreateOptionsMenu(Menu menu) {menu.add(0, 1, 1, " 接收圖片 ").setIcon(android.R.drawable.ic_menu_help);menu.add(0, 2, 2, " 結束 ").setIcon(android.R.drawable.ic_menu_close_clear_cancel);return super.onCreateOptionsMenu(menu); } @Override public boolean onOptionsItemSelected(MenuItem item) {switch(item.getItemId()){ case 1: Intent it=new Intent(SendingdataActivity.this,Sendingdata_serverActivity.class); startActivity(it); this.finish(); break; case 2: this.finish(); break; }return super.onOptionsItemSelected(item); }

Page 34: Android 傳送檔案

layout<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_parent" android:orientation="vertical" > <TextView android:id="@+id/title_paired_devices" android:layout_width="match_parent" android:layout_height="wrap_content" android:text=" 已配對設備 " android:visibility="gone" android:background="#666" android:textColor="#fff" android:paddingLeft="5dp" /> <ListView android:id="@+id/paired_devices" android:layout_width="match_parent" android:layout_height="wrap_content" android:stackFromBottom="true" android:layout_weight="1" />

Page 35: Android 傳送檔案

layout<TextView android:id="@+id/title_new_devices" android:layout_width="match_parent" android:layout_height="wrap_content" android:text=" 其他設備 " android:visibility="gone" android:background="#666" android:textColor="#fff" android:paddingLeft="5dp" /> <ListView android:id="@+id/new_devices" android:layout_width="match_parent" android:layout_height="wrap_content" android:stackFromBottom="true" android:layout_weight="2" /> <Button android:id="@+id/button_scan" android:layout_width="match_parent" android:layout_height="wrap_content" android:text=" 掃描設備 " /> <Button android:id="@+id/send" android:layout_width="fill_parent" android:layout_height="wrap_content" android:text=" 傳送圖片 " /></LinearLayout>

Page 36: Android 傳送檔案

device_name.xml

<?xml version="1.0" encoding="utf-8"?>

<TextView xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:textSize="18sp" android:padding="5dp"/>

Page 37: Android 傳送檔案

透過 BluetoothShare.java

Page 38: Android 傳送檔案

透過 BluetoothShare.javapublic class BT_bluetoothshare extends Activity { @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.btintent); // 按傳送按鈕 Button scanButton = (Button) findViewById(R.id.button_send); scanButton.setOnClickListener(new OnClickListener() { public void onClick(View v) { sendfile("38:E7:D8:2C:6D:BB"); Toast.makeText(BT_bluetoothshare.this,"ok",Toast.LENGTH_LONG).show();

} }); }

// 傳送檔案 public void sendfile(String deviceMAC){ ContentValues values = new ContentValues(); values.put(BluetoothShare.URI, "file:///sdcard/chc.db"); values.put(BluetoothShare.DESTINATION, deviceMAC); values.put(BluetoothShare.DIRECTION, BluetoothShare.DIRECTION_OUTBOUND); Long ts = System.currentTimeMillis(); values.put(BluetoothShare.TIMESTAMP, ts); getContentResolver().insert(BluetoothShare.CONTENT_URI, values); }}