Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> Android開發實例 >> 使用 Android 實現聯網

使用 Android 實現聯網

編輯:Android開發實例

  簡介

  本文建立在 “使用 Eclipse 開發 Android 應用程序” 一文的基礎之上,探究了 Android 的網絡功能。了解如何利用 Android 的網絡選項來實現有趣、有用的東西。Android 平台非常適合 Java™ 開發人員:他們可以使用已有的技能將網絡連接帶到一個移動或 “嵌入式” 平台中。

  在本文中,了解用於 Android 應用程序的網絡選項以及基本的 Android 聯網技巧。本文研究一個真實的應用程序,它在結合使用環境監視系統時需要具備聯網功能。這類系統為什麼如此重要?原因之一是:如果您的朋友需要外出幾個星期,在他離開後,他打電話給我,讓我從他家裡找到某樣東西並郵寄給他。我來到他的家裡,發現供暖設備已經被切斷並且水管已經凍裂 — 場面非常混亂。如果備有一個溫度監控系統,那麼就可以避免出現這類事故。本文將探查 Android 在這類監控系統中扮演的角色。

  Android 聯網功能

  Android 基於 Linux® 內核,包含一組優秀的聯網功能。如果尚未安裝 Android SDK,那麼需要 下載 它才能實踐本文的示例。

  表 1 展示了 Android SDK 中一些與網絡有關的包。

  表 1. Android SDK 網絡包

包描述java.net提供與聯網有關的類,包括流和數據包(datagram)sockets、Internet 協議和常見 HTTP 處理。該包是一個多功能網絡資源。有經驗的 Java 開發人員可以立即使用這個熟悉的包創建應用程序。java.io雖然沒有提供顯式的聯網功能,但是仍然非常重要。該包中的類由其他 Java 包中提供的 socket 和連接使用。它們還用於與本地文件(在與網絡進行交互時會經常出現)的交互。java.nio包含表示特定數據類型的緩沖區的類。適合用於兩個基於 Java 語言的端點之間的通信。org.apache.*表示許多為 HTTP 通信提供精確控制和功能的包。可以將 Apache 視為流行的開源 Web 服務器。android.net除核心 java.net.* 類以外,包含額外的網絡訪問 socket。該包包括 URI 類,後者頻繁用於 Android 應用程序開發,而不僅僅是傳統的聯網方面。android.net.http包含處理 SSL 證書的類。android.net.wifi包含在 Android 平台上管理有關 WiFi(802.11 無線 Ethernet)所有方面的類。並不是所有設備都配備了 WiFi 功能,特別是 Android 在 Motorola 和 LG 等手機制造商的 “翻蓋手機” 領域獲得了成功。android.telephony.gsm包含用於管理和發送 SMS(文本)消息的類。一段時間後,可能會引入額外的包來來為非 GSM 網絡提供類似的功能,比如 CDMA 或 android.telephony.cdma 等網絡。

  上表並沒有列出所有包,但是可以讓您清楚地意識到該平台的強大功能。下一小節將介紹一些簡單的網絡示例。

  簡單的網絡示例

  為了演示將 Android 連接到一個網絡有多麼簡單,這個示例將展示如何從 Web 頁面發送文本。可以 下載 本例的源代碼。圖 1 展示了應用程序的實際使用。

  圖 1. 從 Web 頁面獲取文本

  本節提供了構建示例應用程序所需的代碼。我們將首先查看 UI 部分,然後介紹與網絡有關的代碼。

  共有三個 UI 元素:

  EditText 讓用戶能夠進入一個 Web 頁面(圖 1 和 清單 2 所示的 http://developer.android.com)。

  使用一個按鈕告訴程序取回 Web 頁面文本。

  檢索回數據後,它將顯示在 TextView 中。

  清單 1 展示了 main.xml 文件,這是該應用程序的完整 UI 布局。

  清單 1. main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:orientation="vertical"
  android:layout_width="fill_parent"
  android:layout_height="fill_parent"
  >
<EditText 
android:layout_height="wrap_content"
android:id="@+id/address"
android:layout_width="fill_parent"
android:text="http://google.com"
>
</EditText>
<Button
 android:id="@+id/ButtonGo" 
 android:layout_width="wrap_content" 
 android:layout_height="wrap_content"
 android:text="go!"
 >
</Button>
<TextView 
  android:layout_width="fill_parent" 
  android:layout_height="fill_parent" 
  android:background="#ffffff"
  android:textColor="#000000"

android:id="@+id/pagetext"
  />
</LinearLayout>

  清單 2 展示了本示例使用的 Java 代碼。

  清單 2. GetWebPage.java

package com.msi.getwebpage;

import android.app.Activity;
import android.os.Bundle;
// used for interacting with user interface
import android.widget.Button;
import android.widget.TextView;
import android.widget.EditText;
import android.view.View;
// used for passing data 
import android.os.Handler;
import android.os.Message;
// used for connectivity
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;


public class GetWebPage extends Activity {
  /** Called when the activity is first created. */

  Handler h;


@Override
  public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);
    
    final EditText eText = (EditText) findViewById(R.id.address);
    final TextView tView = (TextView) findViewById(R.id.pagetext);
    
    this.h = new Handler() {

      @Override
      public void handleMessage(Message msg) {
        // process incoming messages here
        switch (msg.what) {
          case 0:
          
tView.append((String) msg.obj);
          
break;
        }
        super.handleMessage(msg);
      }
    };
    final Button button = (Button) findViewById(R.id.ButtonGo);
    button.setOnClickListener(new Button.OnClickListener() {
      public void onClick(View v) {
      
try
{
      
tView.setText("");
        // Perform action on click
        
URL url = new URL(eText.getText().toString());
          URLConnection conn = url.openConnection();
          // Get the response
          BufferedReader rd = new BufferedReader(new 
InputStreamReader(conn.getInputStream()));
          String line = "";
          while ((line = rd.readLine()) != null) {
        
Message lmsg;
            lmsg = new Message();
            lmsg.obj = line;
            lmsg.what = 0;
            GetWebPage.this.h.sendMessage(lmsg);
          }
      
}
      
catch (Exception e)
{
      
}
      }
    });    
  }
}

  這些代碼可以分解成一些常見的部分。這裡使用一些重要(必需)的導入語句來恰當地引用 UI、數據傳遞以及應用程序中使用的與網絡有關的類。所有與網絡相關的代碼出現在 OnClickListener 的 OnClick 方法中。在選擇 圖 1 所示的標簽為 go! 的按鈕之後調用這些代碼。

  URL 和 URLConnection 類共同提供與用戶所選的 Web 站點的連接。BufferedReader 的一個實例負責從 Web 站點連接中讀取傳入的數據。每讀取一行代碼,文本就被附加到一個 TextView。數據並沒有直接指定給 TextView(但是在本例中可以)。我們引入了一種設計模式,即創建一個消息對象並將該對象發送到一個處理程序的實例。這是更新 UI 的一種比較可取的方法,對可能需要同時運行多個線程的應用程序而言尤其如此。

  在示例中,Android 應用程序與 HTTP Web 服務器進行通信,比如 Apache 或 Internet Information Server(IIS 位於 Microsoft® 服務器上)。如果應用程序直接與 TCP socket 對話,那麼您將以不同的方式實現應用程序。清單 3 所示的代碼片段展示了另一種與遠程服務器交互的方式。這個清單被實現為一個單獨的線程。

  清單 3. Daytime 客戶機

  public class Requester extends Thread {
    Socket requestSocket;
    String message;
    StringBuilder returnStringBuffer = new StringBuilder();
    Message lmsg;
    int ch;
    @Override
    public void run() {
      try {
        this.requestSocket = new Socket("remote.servername.com", 13);
        InputStreamReader isr = new InputStreamReader(this.requestSocket.
getInputStream(), "ISO-8859-1");
        while ((this.ch = isr.read()) != -1) {
          this.returnStringBuffer.append((char) this.ch);
        }
        this.message = this.returnStringBuffer.toString();
        this.lmsg = new Message();
        this.lmsg.obj = this.message;
        this.lmsg.what = 0;
        h.sendMessage(this.lmsg);
        this.requestSocket.close();
      } catch (Exception ee) {
        Log.d("sample application", "failed to read data" + ee.getMessage());
      }
    }
  }

  與前面的示例類似,上面的代碼使用消息和處理程序方法來將數據發送給調用者,調用者將更新 UI 並執行後續處理。與 清單 1 不同,這個例子並沒有與 HTTP 服務器通信,因此沒有使用 URLConnection 類。相反,使用了較低級的 Socket 類在端口 13 打開與遠程服務器的基於流的 socket 連接。端口 13 是典型的 “Daytime Server” 應用程序。

  Daytime Server 接受傳入的 socket 連接並以文本的形式將日期和時間發送給調用 socket。一旦發送完數據,服務器將關閉 socket。示例也展示了 InputStreamReader 的使用和一個特定字符編碼。

  發送文本消息是您需要使用 Android 完成的另一項任務。清單 4 展示了一個示例。

  清單 4. 發送一條文本消息

void sendMessage(String recipient,String myMessage) {
 SmsManager sm = SmsManager.getDefault();
 sm.sendTextMessage("destination number",null,"hello there",null,null);
}

  發送文本消息非常簡單。首先,使用靜態方法 getDefault() 獲取對 SmsManager 的引用。然後調用 sendTextMessage 方法。參數為:

  接收者的手機號 包括區號。 服務中心電話號碼 使用 null 值表示您同意使用默認服務中心來處理消息。除了非常特殊的應用程序外,幾乎所有應用程序都對這個參數使用 null 值。 消息的實際內容 將消息長度保持在 160 字節以內,除非您可以接受將數據分為多個消息發送。 未收到消息 intent 如果消息被發送或出現了錯誤,那麼將開始一個可選的 intent。如果不需要這類通知,那麼可以為此參數傳遞一個 null 值。(參見 參考資料 了解有關 intent 和 Android 基本原理的更多信息)。 收到消息 intent 當收到發送確認後,將開始一個可選的 Intent。如果發送通知不重要的話,那麼可以為這個參數傳遞一個 null 值。

  不管是連接到 Web 頁面還是連接到定制 TCP 應用程序,Android 平台都可以立即反應並且能夠提供幫助。如 清單 4 所示,發送文本消息非常簡單。通過使用可選的 intent 參數,甚至可以在消息被發送並交付後采取操作。這是其他移動平台所不具備的強大特性。

  下一節將快速浏覽一個真實的應用程序設計。

  環境監控系統

  在這個場景中,我們假設您是企業所在的若干辦公場所的資產管理員。管理資產與管理數據中心沒有太大的差別 — 一般情況下都很枯燥,只有出現緊急的情況下工作才會比較有意思。幾天前,一台使用了 10 年的熱水器突然漏水,滲到一個裝滿老式 PC 和培訓手冊的存儲櫃,您必須檢查一下清理情況。幸運的是,您當時沒有外出。如果您在旅途中的話,那麼情形將非常糟糕。此類災難性事故促使我們考慮使用 Android 來幫助監視資產的維護情況。圖 2 展示了此類系統的一個高級方框圖。

  圖 2. 監控系統的高級方框圖

  此架構是一種比較傳統的方法,使用一個微控制器與一些簡單場景進行交互以收集數據。數據隨後通過一個串行通信協議(比如 RS232 或 RS485)發送到控制器。控制器可以是一個 PC 或類似的機器。隨後可以穿過防火牆通過 Internet 訪問數據。Android 電話(比如 TMobile G1)之間使用的協議可以是 HTTP 或私有協定。

  在控制器和配備 Android 的設備之間發送的數據將是表示以下內容的基本數據:

  出現漏水

  當前溫度

  消耗的功率

  可能包含一些通用的類似數據和數字值

  為什麼需要關注消耗的功率?一個可能的原因就是有些人忘記關閉機器,因此電費單上的數字會一直增長。第二個理由有些復雜:假設您有一台非常大的冰箱,並且電源可能已被關閉。那麼情況就復雜了,而且處理起來也需要很高的代價。或者,空調設備的斷路器出現故障,因此機房無法保持恆定的溫度。

  基本的設計看上去是可行的。如果使用的是 Android,那麼可以使用任何移動平台來替換 圖 2 中的 Android。但如果使用配備了 Android 的設備替換微控制器,那應該怎麼做呢?下一節將討論對這個應用程序的擴展以及通過使用 Android 而啟用的特性。

  擴展應用程序

  本文的第一個架構以一個微控制器為中心。微控制器可分為不同的外形和大小,從 Microchip 的 6 pin “10F” 到添加了外圍設備、pin 和代碼空間的 32 位大型微控制器。如果使用 Android 取代傳統的微控制器放到設備中,會怎麼樣?對於某些應用程序而言,在成本方面是不可取的,但是根據圖 3 的判斷,這種方法也是可行的。

  圖 3. 在設備中使用 Android 的可能架構

  使用嵌入式的方式部署 Android 為您提供了更加豐富的編程環境。您可以和以前一樣繼續監視濕度、溫度和功率消耗特征,同時還可以觀察到記錄音頻、視頻和振動。您將擁有一個微報警、訪問控制系統,以及一個環節監控工具。由於 Android 已經可以實現聯網,您不需要使用控制器 PC 就可以實現監控並與網絡直接對話。

  這種方法還為現場更新軟件提供了額外的好處。假設您希望為監控軟件添加新的特性(或修復 bug)。如果使用傳統的微控制器方法,那麼任務執行起來將十分繁瑣並且代價昂貴,甚至根本不可能實現。而對於 Android 而言,您可以獲得更整潔的部署模型並擁有更好的靈活性。

  Android 如今主要運行在移動手機中,但是它已經被移植到 NetBooks 和其他平台上。希望本文為您提供了一些好的思考內容。我現在該去運行我的系統了。您永遠也不會知道下一次熱水器漏水會在什麼時候發生。

  結束語

  在本文中,我們大體介紹了 Android 的聯網功能。您了解了一些自己可以創建的樣例應用程序,包括與 Web 服務器交互和發送文本消息。您看到了如何將 Android 連接到一個真實的環境監控系統。通過代碼示例,您了解到應該在什麼時候將 Android 擴展到一些特殊應用程序中,比如嵌入式控制器。

  請繼續關注我的下一篇文章,它將介紹如何使用基於 Android 的電話構建一個嬰兒監控系統。

  本文示例源代碼或素材下載

編緝推薦閱讀以下文章

  • Windows Mobile應用開發(1):使用Win32 SDK 開發屏幕手電程序
  • Android SDK 1.0下載(最終版)
  • 什麼是Android-Android中文SDK
  • Android新手入門-Android中文SDK
  • 你好Android-Android中文SDK
  • 剖析Android程序結構-Android中文SDK
  • Android 0.9 SDK中Browser和MapView的改變
  • Android SDK 0.9版升級注意點
  • Android SDK安裝教程
  • UIQ3.0 sdk最終版模擬器中文的顯示
  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved