我正在学习Android内容提供商和内容。我无法弄清楚为什么没有使用ProductProvider添加数据。 我查看了每个类,但数据从数据库插入或查询的方式有问题,但我无法弄清楚什么是坏的。
以下是代码文件
活动
HomePage.java
package com.example.tanmay.shoppingapp;
import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.provider.BaseColumns;
import android.support.v7.app.AppCompatActivity;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.View;
import android.view.ViewGroup;
import android.widget.CursorAdapter;
import android.widget.ListView;
import android.widget.TextView;
import com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry;
public class HomePage extends AppCompatActivity {
TextView idBox;
TextView nameBox;
String TAG = "com.whatever.tag";
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.home_page, menu);
return true;
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_home_page);
//Adding custom toolbar
android.support.v7.widget.Toolbar toolbar = findViewById(R.id.homePageToolBar);
setSupportActionBar(toolbar);
insertProduct();
//Projection is just the name of the columns we would like to receive
String[] projection = {
ProductEntry._ID,
ProductEntry.COLUMN_NAME_PRODUCT_NAME
};
Cursor cursorNew = getContentResolver().query(ProductEntry.CONTENT_URI, projection, null, null, null);
cursorNew.moveToNext();
int uweh = cursorNew.getInt(cursorNew.getColumnIndex(ProductEntry.COLUMN_NAME_PRODUCT_NAME));
TextView coco = findViewById(R.id.e83957);
coco.setText(uweh);
ListView listView = findViewById(R.id.productList_homepage);
listView.setAdapter(new productListAdapter(HomePage.this, cursorNew));
}
private void insertProduct() {
ContentValues values = new ContentValues();
//The values contains all the data to be entered into the table
values.put(ProductEntry._ID, 67);
values.put(ProductEntry.COLUMN_NAME_PRODUCT_NAME, R.string.product1Name);
values.put(ProductEntry.COLUMN_NAME_PRODUCT_PRICE, R.integer.product1Price);
values.put(ProductEntry.COLUMN_NAME_PRODUCT_THUMBNAIL, R.drawable.product1thumbnail);
values.put(ProductEntry.COLUMN_NAME_PRODUCT_IMAGE, R.drawable.product1image);
// values.put(ProductEntry.COLUMN_NAME_PRODUCT_NAME, R.string.product2Name);
Uri newUri = getContentResolver().insert(ProductEntry.CONTENT_URI, values);
}
private class productListAdapter extends CursorAdapter {
public productListAdapter(Context context, Cursor c) {
super(context, c);
}
//Returns a new blank view
@Override
public View newView(Context context, Cursor cursor, ViewGroup viewGroup) {
return LayoutInflater.from(context).inflate(R.layout.dummy_item, viewGroup, false);
}
//Actually responsible for the data binding
@Override
public void bindView(View view, Context context, Cursor cursor) {
idBox = (TextView) findViewById(R.id.dummy_item_id_box);
nameBox = (TextView) findViewById(R.id.dummy_item_name_box);
id.setText(cursor.getInt(cursor.getColumnIndexOrThrow(ProductEntry._ID)));
name.setText(getResources().getString(cursor.getInt(cursor.getColumnIndexOrThrow(ProductEntry.COLUMN_NAME_PRODUCT_NAME))));
}
}
}
ProductDbHelper
package com.example.tanmay.shoppingapp.DataSet;
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import static com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry.COLUMN_NAME_PRODUCT_IMAGE;
import static com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry.COLUMN_NAME_PRODUCT_NAME;
import static com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry.COLUMN_NAME_PRODUCT_PRICE;
import static com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry.COLUMN_NAME_PRODUCT_THUMBNAIL;
import static com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry.TABLE_NAME;
import static com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry._ID;
/**
* Created by tanmay on 3/3/18.
*/
public class ProductDbHelper extends SQLiteOpenHelper {
//Name of the database file
public static final String DATABASE_NAME = "products.db";
//Database version to be incremented on change in schema
public static final int DATABASE_VERSION = 1;
// SQL command to create the table
// All columns contain integers because they don't contain the actual Strings and Images,
// instead they hold the integral resource identifiers (R.string.* / R.integer.* / R.drawable.*).
public static final String SQL_CREATE_ENTRIES =
"CREATE TABLE " + TABLE_NAME + " (" +
_ID + " INTEGER PRIMARY KEY, " +
COLUMN_NAME_PRODUCT_NAME + " INTEGER, " +
COLUMN_NAME_PRODUCT_PRICE + "INTEGER, " +
COLUMN_NAME_PRODUCT_THUMBNAIL + "INTEGER, " +
COLUMN_NAME_PRODUCT_IMAGE + "INTEGER)";
// Checks if a particular table already exists and then deletes it.
private static final String SQL_DELETE_ENTRIES =
"DROP TABLE IF EXISTS " + TABLE_NAME;
//Default constructor
public ProductDbHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
// Creates the database bu executing String as SQL command
sqLiteDatabase.execSQL(ProductDbHelper.SQL_CREATE_ENTRIES);
}
@Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
// Firsts deletes the old database then creates a new one
sqLiteDatabase.execSQL(ProductDbHelper.SQL_DELETE_ENTRIES);
onCreate(sqLiteDatabase);
}
@Override
public void onDowngrade(SQLiteDatabase db, int oldVersion, int newVersion) {
onUpgrade(db, oldVersion, newVersion);
}
}
ProductListContract
package com.example.tanmay.shoppingapp.DataSet;
import android.content.ContentResolver;
import android.net.Uri;
import android.provider.BaseColumns;
/**
* Created by tanmay on 26/2/18.
*/
public class ProductListContract {
// Refers to this particular application
public static final String CONTENT_AUTHORITY = "com.example.tanmay.shoppingapp";
public static final Uri BASE_CONTENT_URI = Uri.parse("content://" + CONTENT_AUTHORITY);
//Empty constructor to prevent instantiation
private ProductListContract() {
}
public static class ProductEntry implements BaseColumns {
// Name of the table
public static final String TABLE_NAME = "productListPrimary";
// Uri pointing to this particular table
public static final Uri CONTENT_URI = Uri.withAppendedPath(BASE_CONTENT_URI, ProductEntry.TABLE_NAME);
//MIME type
public static final String CONTENT_LIST_TYPE = ContentResolver.CURSOR_DIR_BASE_TYPE + "/" + CONTENT_AUTHORITY + "/" + TABLE_NAME;
public static final String CONTENT_ITEM_TYPE = ContentResolver.CURSOR_ITEM_BASE_TYPE + "/" + CONTENT_AUTHORITY + "/" + TABLE_NAME;
// Names of various columns
public static final String COLUMN_NAME_PRODUCT_NAME = "name";
public static final String _ID = BaseColumns._ID;
public static final String COLUMN_NAME_PRODUCT_PRICE = "price";
public static final String COLUMN_NAME_PRODUCT_THUMBNAIL = "thumbnail";
public static final String COLUMN_NAME_PRODUCT_IMAGE = "image";
}
}
ProductProvider.java
package com.example.tanmay.shoppingapp.DataSet;
import android.content.ContentProvider;
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.UriMatcher;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.util.Log;
import com.example.tanmay.shoppingapp.DataSet.ProductListContract.ProductEntry;
/**
* Created by tanmay on 28/2/18.
*/
public class ProductProvider extends ContentProvider {
private static final int ProductListTable = 1;
private static final int ProductListRow = 2;
private static final UriMatcher sUriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
static {
sUriMatcher.addURI(ProductListContract.CONTENT_AUTHORITY, ProductEntry.TABLE_NAME, ProductListTable);
sUriMatcher.addURI(ProductListContract.CONTENT_AUTHORITY, ProductEntry.TABLE_NAME + "/#", ProductListRow);
}
private ProductDbHelper mDbHelper;
@Override
public boolean onCreate() {
//Creates a new DbHelper object
mDbHelper = new ProductDbHelper(getContext());
return true;
}
@Nullable
@Override
public Cursor query(@NonNull Uri uri, @Nullable String[] projection, @Nullable String selection, @Nullable String[] selectionArgs, @Nullable String sortOrder) {
// Obtain a read-only copy of the database
SQLiteDatabase sqLiteDatabase = mDbHelper.getReadableDatabase();
// This cursor holds the result from the query.
Cursor cursor = null;
// Switch to perform specific kind of query based on type of Uri
switch (sUriMatcher.match(uri)) {
// Uri demanding entire table with the criteria defined in the fundtion params
case ProductListTable:
// All the argumnets are the ones passed
cursor = sqLiteDatabase.query(ProductEntry.TABLE_NAME, projection, selection, selectionArgs, null, null, sortOrder);
break;
// Uri demanding a particular row item.
case ProductListRow:
// "?" is a wildcard which gets replaced by any integer
selection = ProductEntry._ID + "=?";
selectionArgs = new String[]{String.valueOf((ContentUris.parseId(uri)))};
cursor = sqLiteDatabase.query(ProductEntry.TABLE_NAME, projection, selection, selectionArgs, null, null, sortOrder);
break;
default:
throw new IllegalArgumentException("Cannot query unkown URI " + uri);
}
//Return the cursor containing query results
return cursor;
}
@Nullable
@Override
public String getType(@NonNull Uri uri) {
final int match = sUriMatcher.match(uri);
switch (match) {
case ProductListTable:
return ProductEntry.CONTENT_LIST_TYPE;
case ProductListRow:
return ProductEntry.CONTENT_ITEM_TYPE;
default:
throw new IllegalStateException("Unkown URI " + uri + " with match " + match);
}
}
@Nullable
@Override
public Uri insert(@NonNull Uri uri, @Nullable ContentValues contentValues) {
final int match = sUriMatcher.match(uri);
switch (match) {
case ProductListTable:
return insertProduct(uri, contentValues);
default:
throw new IllegalArgumentException("Insertion is not supported for " + uri);
}
}
public Uri insertProduct(Uri uri, ContentValues contentValues) {
SQLiteDatabase db = mDbHelper.getWritableDatabase();
long id = db.insert(ProductEntry.TABLE_NAME, null, contentValues);
if (id == -1) {
Log.e("com.whatever.tag", "Failed to insert row for " + uri);
return null;
}
return ContentUris.withAppendedId(uri, id);
}
@Override
public int delete(@NonNull Uri uri, @Nullable String s, @Nullable String[] strings) {
return 0;
}
@Override
public int update(@NonNull Uri uri, @Nullable ContentValues contentValues, @Nullable String s, @Nullable String[] strings) {
return 0;
}
}
LayoutFiles 主页活动布局文件
<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout
android:orientation="vertical" xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.tanmay.shoppingapp.HomePage">
<android.support.v7.widget.Toolbar
android:id="@+id/homePageToolBar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
android:background="?attr/colorPrimary"
android:elevation="4dp"
android:theme="@style/ThemeOverlay.AppCompat.ActionBar"
app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
app:title="@string/app_name">
</android.support.v7.widget.Toolbar>
<TextView
android:id="@+id/e83957"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
android:layout_marginEnd="8dp"
android:layout_marginStart="8dp"
android:layout_marginTop="8dp"
android:text="wwt49832"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<ListView
android:layout_marginTop="?attr/actionBarSize"
android:id="@+id/productList_homepage"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
</android.support.constraint.ConstraintLayout>
一个ListView元素的布局 DummyItem,因为一旦一切正常,将应用不同的布局。
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:layout_margin="8dp"
android:text="327"
android:id="@+id/dummy_item_id_box"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:layout_margin="8dp"
android:text="placeholder"
android:id="@+id/dummy_item_name_box"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>