Latest web development tutorials

Content Provider Android (Content Provider)

Contenuti fornitore richiedendo componente fornisce i dati da un'applicazione a un'altra applicazione. Queste richieste da parte del modo di classe ContentResolver da affrontare. I fornitori di contenuti possono utilizzare diversi modi per memorizzare i dati. I dati possono essere memorizzati in un database, un file, o anche una rete.

immagine

A volte la necessità di condividere i dati tra le applicazioni. In questo caso il fornitore di contenuti diventa molto utile.

I fornitori di contenuti possono fare fuoco i contenuti, si può avere un certo numero di applicazioni diverse per l'accesso, se necessario. I fornitori di contenuti e si comporta come un database. È possibile interrogare, modificare il suo contenuto, usare insert (), update (), delete () e query () per aggiungere o eliminare contenuti. Nella maggior parte dei casi i dati sono memorizzati in un database SQLite.

Il fornitore di contenuti è implementato come una sottoclasse della classe di classe ContentProvider. Abbiamo bisogno di attuare una serie di API standard, in modo altre applicazioni per eseguire la transazione.

public class MyApplication extends  ContentProvider {

}

contenuti URI

Per interrogare il fornitore di contenuti, è necessario essere in forma di il seguente formato per specificare la stringa di query URI:

<prefix>://<authority>/<data_type>/<id>

Quanto segue è una descrizione specifica di ogni parte del URI:

sezione spiegazione
prefisso Prefisso: è stato impostato come contenuto: //
autorità Autorizzazione: Specifica il nome del provider di contenuti, come ad esempio i contatti, browser, ecc fornitori di contenuti di terze parti possono essere un nome completo, ad esempio: cn.programmer.statusprovider
data_type Tipo di dati: Questo indica che questo particolare tipo di fornitore di contenuto dei dati. Per esempio: Si desidera fornire da parte del fornitore di contenuti per ottenere tutti i contatti della rubrica, il percorso dei dati è il popolo, allora l'URI appariranno come segue: contenuto: // contatti / persone
id Questa richiesta specifica di un record particolare. Per esempio: si fornisce il provider di contenuti sui contatti contattare il numero ID è 5, quindi l'URI assomiglia a questo: contenuto: // contatti / persone / 5

Creazione di fornitore di contenuti

Semplici passaggi descritti qui provider di creare i propri contenuti.

  • In primo luogo, è necessario creare una classe derivata ContentProviderbase classe fornitore di contenuti.
  • In secondo luogo, è necessario definire i contenuti per l'accesso ai contenuti provider di indirizzi URI.
  • Successivamente, è necessario creare un database di Content Store. In genere, Android utilizza database SQLite e override onCreate () metodo utilizzato nel quadro del metodo di SQLiteOpenHelper per creare o aprire un provider di database. Quando si avvia l'applicazione, il metodo di ogni fornitore di contenuti onCreate () verrà chiamato nel thread principale dell'applicazione.
  • Infine, utilizzare il <fornitore ... /> tag registrato nel AndroidManifest.xml fornitore di contenuti.

Di seguito è riportato il fornitore di contenuti per ottenere il vostro lavoro, avete bisogno di qualche metodo nella classe riscritta ContentProvider:

immagine

  • onCreate (): Chiamato quando viene avviato il provider.
  • query (): Questo metodo accetta le richieste dal client. Il risultato è l'oggetto puntatore di ritorno (Cursore).
  • inserire (): i fornitori di questo contenuto metodo per inserire un nuovo record.
  • delete (): questo metodo viene eliminato dal fornitore di contenuti nel record esistente.
  • update (): Questo metodo aggiorna il fornitore di contenuti nel record esistente.
  • getType (): Questo metodo restituisce l'URI tipo di metadati.

Esempi

Questo esempio spiega come creare il proprio fornitore di contenuti. Seguiamo le istruzioni riportate di seguito:

passo descrizione
1 Creare applicazioni Android che utilizzano Studio Android chiamato provider di contenuti, nella cn.uprogrammer.contentprovider pacchetto, e la creazione di attività spaziali.
2 Modificare le principali attività MainActivity.java file per aggiungere due nuovi metodi onClickAddName () e onClickRetrieveStudents ().
3 Creato con il nuovo pacchetto Java cn.uprogrammer.contentprovider file di StudentsProvider.java per definire il provider attuale, e metodi associati.
4 Usa <fornitore ... /> tag in AndroidManifest.xml registrato fornitore di contenuti.
5 Modificare il / layout / file di activity_main.xml res contenuto predefinito per aggiungere il record studente contiene una semplice interfaccia.
6 Senza modificare strings.xml, Android Studio presterà file di strings.xml attenzione.
7 Avviare emulatore di Android per eseguire l'applicazione e verificare i risultati delle modifiche apportate all'applicazione.

Ecco il contenuto del file di attività principale src / cn.uprogrammer.contentprovider / MainActivity.java modificata. Questo file contiene ciascuno dei approccio di base del ciclo di vita. Abbiamo aggiunto due nuovi metodi, onClickAddName () e onClickRetrieveStudents () per permettere l'interazione con l'utente maniglia applicazione.

package cn.uprogrammer.contentprovider;

import android.net.Uri;
import android.os.Bundle;
import android.app.Activity;
import android.content.ContentValues;
import android.content.CursorLoader;
import android.database.Cursor;
import android.view.Menu;
import android.view.View;
import android.widget.EditText;
import android.widget.Toast;
import cn.uprogrammer.contentprovider.R;

public class MainActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu_main, menu);
        return true;
    }

    public void onClickAddName(View view) {
        // Add a new student record
        ContentValues values = new ContentValues();

        values.put(StudentsProvider.NAME,
                ((EditText)findViewById(R.id.editText2)).getText().toString());

        values.put(StudentsProvider.GRADE,
                ((EditText)findViewById(R.id.editText3)).getText().toString());

        Uri uri = getContentResolver().insert(
                StudentsProvider.CONTENT_URI, values);

        Toast.makeText(getBaseContext(),
                uri.toString(), Toast.LENGTH_LONG).show();
    }

    public void onClickRetrieveStudents(View view) {

        // Retrieve student records
        String URL = "content://com.example.provider.College/students";

        Uri students = Uri.parse(URL);
        Cursor c = managedQuery(students, null, null, null, "name");

        if (c.moveToFirst()) {
            do{
                Toast.makeText(this,
                        c.getString(c.getColumnIndex(StudentsProvider._ID)) +
                                ", " +  c.getString(c.getColumnIndex( StudentsProvider.NAME)) +
                                ", " + c.getString(c.getColumnIndex( StudentsProvider.GRADE)),
                        Toast.LENGTH_SHORT).show();
            } while (c.moveToNext());
        }
    }
}

Creare un nuovo file nel pacchetto StudentsProvider.java cn.uprogrammer.contentprovider. Quanto segue è il contenuto di src / cn.uprogrammer.contentprovider / StudentsProvider.java di.

package cn.uprogrammer.contentprovider;

import java.util.HashMap;

import android.content.ContentProvider;
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.Context;
import android.content.UriMatcher;

import android.database.Cursor;
import android.database.SQLException;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.database.sqlite.SQLiteQueryBuilder;

import android.net.Uri;
import android.text.TextUtils;

public class StudentsProvider extends ContentProvider {

    static final String PROVIDER_NAME = "com.example.provider.College";
    static final String URL = "content://" + PROVIDER_NAME + "/students";
    static final Uri CONTENT_URI = Uri.parse(URL);

    static final String _ID = "_id";
    static final String NAME = "name";
    static final String GRADE = "grade";

    private static HashMap<String, String> STUDENTS_PROJECTION_MAP;

    static final int STUDENTS = 1;
    static final int STUDENT_ID = 2;

    static final UriMatcher uriMatcher;
    static{
        uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
        uriMatcher.addURI(PROVIDER_NAME, "students", STUDENTS);
        uriMatcher.addURI(PROVIDER_NAME, "students/#", STUDENT_ID);
    }

    /**
     * 数据库特定常量声明
     */
    private SQLiteDatabase db;
    static final String DATABASE_NAME = "College";
    static final String STUDENTS_TABLE_NAME = "students";
    static final int DATABASE_VERSION = 1;
    static final String CREATE_DB_TABLE =
            " CREATE TABLE " + STUDENTS_TABLE_NAME +
                    " (_id INTEGER PRIMARY KEY AUTOINCREMENT, " +
                    " name TEXT NOT NULL, " +
                    " grade TEXT NOT NULL);";

    /**
     * 创建和管理提供者内部数据源的帮助类.
     */
    private static class DatabaseHelper extends SQLiteOpenHelper {
        DatabaseHelper(Context context){
            super(context, DATABASE_NAME, null, DATABASE_VERSION);
        }

        @Override
        public void onCreate(SQLiteDatabase db)
        {
            db.execSQL(CREATE_DB_TABLE);
        }

        @Override
        public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
            db.execSQL("DROP TABLE IF EXISTS " +  STUDENTS_TABLE_NAME);
            onCreate(db);
        }
    }

    @Override
    public boolean onCreate() {
        Context context = getContext();
        DatabaseHelper dbHelper = new DatabaseHelper(context);

        /**
         * 如果不存在,则创建一个可写的数据库。
         */
        db = dbHelper.getWritableDatabase();
        return (db == null)? false:true;
    }

    @Override
    public Uri insert(Uri uri, ContentValues values) {
        /**
         * 添加新学生记录
         */
        long rowID = db.insert( STUDENTS_TABLE_NAME, "", values);

        /**
         * 如果记录添加成功
         */

        if (rowID > 0)
        {
            Uri _uri = ContentUris.withAppendedId(CONTENT_URI, rowID);
            getContext().getContentResolver().notifyChange(_uri, null);
            return _uri;
        }
        throw new SQLException("Failed to add a record into " + uri);
    }

    @Override
    public Cursor query(Uri uri, String[] projection, String selection,String[] selectionArgs, String sortOrder) {
        SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
        qb.setTables(STUDENTS_TABLE_NAME);

        switch (uriMatcher.match(uri)) {
            case STUDENTS:
                qb.setProjectionMap(STUDENTS_PROJECTION_MAP);
                break;

            case STUDENT_ID:
                qb.appendWhere( _ID + "=" + uri.getPathSegments().get(1));
                break;

            default:
                throw new IllegalArgumentException("Unknown URI " + uri);
        }

        if (sortOrder == null || sortOrder == ""){
            /**
             * 默认按照学生姓名排序
             */
            sortOrder = NAME;
        }
        Cursor c = qb.query(db, projection, selection, selectionArgs,null, null, sortOrder);

        /**
         * 注册内容URI变化的监听器
         */
        c.setNotificationUri(getContext().getContentResolver(), uri);
        return c;
    }

    @Override
    public int delete(Uri uri, String selection, String[] selectionArgs) {
        int count = 0;

        switch (uriMatcher.match(uri)){
            case STUDENTS:
                count = db.delete(STUDENTS_TABLE_NAME, selection, selectionArgs);
                break;

            case STUDENT_ID:
                String id = uri.getPathSegments().get(1);
                count = db.delete( STUDENTS_TABLE_NAME, _ID +  " = " + id +
                        (!TextUtils.isEmpty(selection) ? " AND (" + selection + ')' : ""), selectionArgs);
                break;

            default:
                throw new IllegalArgumentException("Unknown URI " + uri);
        }

        getContext().getContentResolver().notifyChange(uri, null);
        return count;
    }

    @Override
    public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
        int count = 0;

        switch (uriMatcher.match(uri)){
            case STUDENTS:
                count = db.update(STUDENTS_TABLE_NAME, values, selection, selectionArgs);
                break;

            case STUDENT_ID:
                count = db.update(STUDENTS_TABLE_NAME, values, _ID + " = " + uri.getPathSegments().get(1) +
                        (!TextUtils.isEmpty(selection) ? " AND (" +selection + ')' : ""), selectionArgs);
                break;

            default:
                throw new IllegalArgumentException("Unknown URI " + uri );
        }
        getContext().getContentResolver().notifyChange(uri, null);
        return count;
    }

    @Override
    public String getType(Uri uri) {
        switch (uriMatcher.match(uri)){
            /**
             * 获取所有学生记录
             */
            case STUDENTS:
                return "vnd.android.cursor.dir/vnd.example.students";

            /**
             * 获取一个特定的学生
             */
            case STUDENT_ID:
                return "vnd.android.cursor.item/vnd.example.students";

            default:
                throw new IllegalArgumentException("Unsupported URI: " + uri);
        }
    }
}

Ciò che segue è le modifiche di file AndroidManifest.xml. Qui Aggiunto <fornitore ... /> tag per includere i nostri fornitori di contenuti:

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="cn.uprogrammer.contentprovider"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="8"
        android:targetSdkVersion="22" />

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >

        <activity
            android:name="cn.uprogrammer.contentprovider.MainActivity"
            android:label="@string/app_name" >

            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>

        </activity>

        <provider android:name="StudentsProvider"
            android:authorities="com.example.provider.College" >
        </provider>

    </application>

</manifest>

Ecco il contenuto della res / file di layout / activity_main.xml:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
    android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".MainActivity">

    <TextView
        android:id="@+id/textView1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="内容提供者实例"
        android:layout_alignParentTop="true"
        android:layout_centerHorizontal="true"
        android:textSize="30dp" />

    <TextView
        android:id="@+id/textView2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="www.uprogrammer.cn"
        android:textColor="#ff87ff09"
        android:textSize="30dp"
        android:layout_below="@+id/textView1"
        android:layout_centerHorizontal="true" />

    <ImageButton
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/imageButton"
        android:src="@drawable/ic_launcher"
        android:layout_below="@+id/textView2"
        android:layout_centerHorizontal="true" />

    <Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/button2"
        android:text="添加"
        android:layout_below="@+id/editText3"
        android:layout_alignRight="@+id/textView2"
        android:layout_alignEnd="@+id/textView2"
        android:layout_alignLeft="@+id/textView2"
        android:layout_alignStart="@+id/textView2"
        android:onClick="onClickAddName"/>

    <EditText
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/editText"
        android:layout_below="@+id/imageButton"
        android:layout_alignRight="@+id/imageButton"
        android:layout_alignEnd="@+id/imageButton" />

    <EditText
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/editText2"
        android:layout_alignTop="@+id/editText"
        android:layout_alignLeft="@+id/textView1"
        android:layout_alignStart="@+id/textView1"
        android:layout_alignRight="@+id/textView1"
        android:layout_alignEnd="@+id/textView1"
        android:hint="姓名"
        android:textColorHint="@android:color/holo_blue_light" />

    <EditText
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/editText3"
        android:layout_below="@+id/editText"
        android:layout_alignLeft="@+id/editText2"
        android:layout_alignStart="@+id/editText2"
        android:layout_alignRight="@+id/editText2"
        android:layout_alignEnd="@+id/editText2"
        android:hint="年级"
        android:textColorHint="@android:color/holo_blue_bright" />

    <Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="查询"
        android:id="@+id/button"
        android:layout_below="@+id/button2"
        android:layout_alignRight="@+id/editText3"
        android:layout_alignEnd="@+id/editText3"
        android:layout_alignLeft="@+id/button2"
        android:layout_alignStart="@+id/button2"
        android:onClick="onClickRetrieveStudents"/>

</RelativeLayout>

Garantire res / valori / file di strings.xml ha il seguente contenuto:

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

    <string name="app_name">Content Provider</string>
    <string name="action_settings">Settings</string>

</resources>

Diciamo solo eseguire un'applicazione provider di contenuti modificati. Presumo che hai creato AVD durante l'ambiente di installazione. Aprire il progetto nel file attivo, fare clic sulla barra degli strumenti immagine Icona per eseguire l'applicazione in Android Studio. Android Studio installare l'applicazione sul AVD e lo avvia. Se tutto va bene, sarà visualizzata la finestra di emulazione come segue:

immagine

Inserire il nome e l'anno, e fare clic sul pulsante "Aggiungi", che aggiungerà un record studente nei dati, e in fondo per eliminare un messaggio. Contenuto delle informazioni visualizza un numero di record aggiunti al fornitore del contenuto del database URI. Questa operazione utilizza il metodo insert (). Ripetere questa procedura per aggiungere più studenti nella banca dati del nostro fornitore di contenuti.

immagine

Una volta completato si aggiunge il record del database, è il momento di restituire al fornitore di contenuti richiede questi record. Fare clic sul pulsante "Cerca", che sarà di recuperare e visualizzare tutti i dati registrati implementando il metodo query ().

È possibile fornire metodo di callback MainActivity.java per preparare aggiornare e cancellare le operazioni, e modificare l'interfaccia utente di aggiungere aggiornare e cancellare le operazioni.

È possibile utilizzare i contenuti esistenti fornite in questo modo da tali contatti. È possibile anche in questo modo per sviluppare una buona applicazione di database-oriented, si può essere eseguito come descritto sopra è conosciuto come un caso di operazioni di database, come la lettura, scrittura, aggiornare e cancellare.