我已经创建了一个包含汽车信息(品牌/型号/里程/等)的虚拟表,我想在用户点击搜索按钮后将其显示在ListView中,但是到目前为止无法使代码正常工作
我创建了一个CursorAdapter尝试将信息转换为ListView,但我尝试过的任何方法都没有用。
搜索片段
class HomeFragment : Fragment(){
override fun onCreateView(inflater: LayoutInflater,
container: ViewGroup?, savedInstanceState: Bundle?): View? {
// Inflate the layout for this fragment
val view = inflater?.inflate(R.layout.fragment_home,
container, false)
val spinner: Spinner = view.findViewById(R.id.spinner)
// ArrayAdapter using the string array and a default spinner layout
ArrayAdapter.createFromResource(
this.context,
R.array.vehicle_types,
android.R.layout.simple_spinner_item
).also { adapter ->
// Layout to use when the list of choices appears
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item)
// Apply the adapter to the spinner
spinner.adapter = adapter
}
val btnSearch: Button = view.findViewById(R.id.btn_search)
val lv: ListView = view.findViewById<ListView>(R.id.lv_search)
btnSearch.setOnClickListener {
val dbTable = DatabaseTable(this.context)
val cursor = dbTable.getAllCars()
val carCursorAdapter = CarCursorAdapter(this.context, cursor)
lv.adapter = carCursorAdapter
}
return view
}
}
CursorAdapter
class CarCursorAdapter(context:Context?, cursor:Cursor): CursorAdapter(context, cursor, true) {
override fun newView(context: Context?, cursor: Cursor?, parent: ViewGroup?): View {
return LayoutInflater.from(context).inflate(R.layout.item_car, parent, false)
}
override fun bindView(view: View?, context: Context?, cursor: Cursor?) {
//Find fields to populate in template
val tvMake = view?.findViewById<TextView>(R.id.tv_make)
val tvModel = view?.findViewById<TextView>(R.id.tv_model)
val tvYear = view?.findViewById<TextView>(R.id.tv_year)
val tvMileage = view?.findViewById<TextView>(R.id.tv_mileage)
val tvPrice = view?.findViewById<TextView>(R.id.tv_price)
//Extract properties from cursor
val make = cursor?.getString(cursor.getColumnIndexOrThrow("make"))
val model = cursor?.getString(cursor.getColumnIndexOrThrow("model"))
val year = cursor?.getString(cursor.getColumnIndexOrThrow("year"))
val mileage = cursor?.getString(cursor.getColumnIndexOrThrow("mileage"))
val price = cursor?.getString(cursor.getColumnIndexOrThrow("price"))
//Populate fields with extracted properties
if (tvMake != null) {
tvMake.setText(make)
}
if (tvModel != null) {
tvModel.setText(model)
}
if (tvYear != null) {
tvYear.setText(year)
}
if (tvMileage != null) {
tvMileage.setText(mileage)
}
if (tvPrice != null) {
tvPrice.setText(price)
}
}
}
数据库表
private const val TAG = "CarDatabase"
//Columns in the table
const val COL_TYPE = "TYPE"
const val COL_MAKE = "MAKE"
const val COL_MODEL = "MODEL"
const val COL_YEAR = "YEAR"
const val COL_MILEAGE = "MILEAGE"
const val COL_PRICE = "PRICE"
private const val DATABASE_NAME = "CARS"
private const val FTS_VIRTUAL_TABLE = "FTS"
private const val DATABASE_VERSION = 1
private const val FTS_TABLE_CREATE =
"CREATE VIRTUAL TABLE $FTS_VIRTUAL_TABLE USING fts3 ($COL_TYPE, $COL_MAKE, $COL_MODEL, $COL_YEAR, $COL_MILEAGE, " +
"$COL_PRICE)"
class DatabaseTable (context: Context?) {
private val databaseOpenHelper: DatabaseOpenHelper
init {
databaseOpenHelper = DatabaseOpenHelper(context)
}
private class DatabaseOpenHelper internal constructor(private val helperContext: Context?) :
SQLiteOpenHelper(helperContext, DATABASE_NAME, null, DATABASE_VERSION) {
private lateinit var mDatabase: SQLiteDatabase
override fun onCreate(db: SQLiteDatabase) {
mDatabase = db
mDatabase.execSQL(FTS_TABLE_CREATE)
loadDatabase()
}
override fun onUpgrade(db: SQLiteDatabase, oldVersion: Int, newVersion: Int) {
Log.w(
TAG,
"Upgrading database from $oldVersion to $newVersion , which will destroy all old data"
)
db.execSQL("DROP TABLE IF EXISTS $FTS_VIRTUAL_TABLE")
onCreate(db)
}
private fun loadDatabase() {
Thread(Runnable {
try {
loadCars()
} catch (e: IOException) {
throw RuntimeException(e)
}
}).start()
}
@Throws(IOException::class)
private fun loadCars() {
val inputStream = helperContext?.resources?.openRawResource(R.raw.cars)
BufferedReader(InputStreamReader(inputStream)).use {reader ->
var line: String? = reader.readLine()
while (line != null) {
val strings: List<String> = line.split(" ").map {it.trim()}
if (strings.size < 2) continue
val id = addCar(strings[0], strings[1], strings[2], strings[3], strings[4], strings[5])
if (id < 0) {
Log.e(TAG, "unable to add car: ${strings[1]} ${strings[2]}")
}
line = reader.readLine()
}
}
}
fun addCar(type: String, make: String, model: String, year: String, mileage: String, price: String) : Long {
val initialValues = ContentValues().apply {
put(COL_TYPE, type)
put(COL_MAKE, make)
put(COL_MODEL, model)
put(COL_YEAR, year)
put(COL_MILEAGE, mileage)
put(COL_PRICE, price)
}
return mDatabase.insert(FTS_VIRTUAL_TABLE, null, initialValues)
}
fun getAllCars(): Cursor? {
val db = this.readableDatabase
return db.rawQuery("SELECT * FROM $FTS_VIRTUAL_TABLE", null)
}
}
}
这时我的问题是,使用我目前采用的方法,从getAllCars()函数访问光标,但是我是Kotlin / Android开发的新手,可能只是完全以错误的方式进行操作。 ..