Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/181.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android 将房间中的预填充数据获取到微调器适配器_Android_Spinner_Android Room - Fatal编程技术网

Android 将房间中的预填充数据获取到微调器适配器

Android 将房间中的预填充数据获取到微调器适配器,android,spinner,android-room,Android,Spinner,Android Room,大家好!今天我试图解决下一个问题:我为语言列表创建了room数据库,为不同的语言预先填充了五个ready对象,然后我试图将它们传输到spinner adapter中,类似这样: @Database(entities = {Language.class}, version = 1) public abstract class AppDatabase extends RoomDatabase { private static AppDatabase INSTANCE; public

大家好!今天我试图解决下一个问题:我为语言列表创建了room数据库,为不同的语言预先填充了五个ready对象,然后我试图将它们传输到spinner adapter中,类似这样:

@Database(entities = {Language.class}, version = 1)
public abstract class AppDatabase extends RoomDatabase {
    private static AppDatabase INSTANCE;
    public abstract LanguageDao languageDao();

    public synchronized static AppDatabase getInstance(Context context) {
        if (INSTANCE == null) {
            INSTANCE = buildDatabase(context);
        }
        return INSTANCE;
    }

    private static AppDatabase buildDatabase(final Context context) {
        return Room.databaseBuilder(context, AppDatabase.class, "my-database")
                .addCallback(new Callback() {
                    @Override
                    public void onCreate(@NonNull SupportSQLiteDatabase db) {
                        super.onCreate(db);
                        Executors.newSingleThreadScheduledExecutor().execute(new Runnable() {
                            @Override
                            public void run() {
                                getInstance(context).languageDao()
                                        .insertAll(Language.populateData());
                            }
                        });
                    }
                })
                .allowMainThreadQueries()
                .build();
    }
}
语言
对象的实体和DAO代码:

@Entity
public class Language {

    @PrimaryKey
    private long id;

    @ColumnInfo(name = "language")
    private String language;

    public Language(String language) {
        this.language = language;
    }

    public static Language[] populateData() {
        return new Language[]{new Language("English"), new Language("French"), new Language(
                "Spanish"), new Language("Russian"), new Language("Italian")};
    }

    public String getLanguage() {
        return language;
    }

    public void setLanguage(String language) {
        this.language = language;
    }

    public long getId() {

        return id;
    }

    public void setId(long id) {
        this.id = id;
    }
}

@Dao
public interface LanguageDao {

    @Query("SELECT * FROM language")
    List<Language> getAll();

    @Insert
    void insertAll(Language... languages);
}
如您所见,我已将语言对象的预填充数据插入到数据库实例中。我知道这里不推荐使用
allowMainThreadQueries()
方法(只需使用它来简化当前的培训)

此外,我还创建了以下方法,该方法返回微调器对象并将其放入活动代码中:

private Spinner createLanguageSpinner(){
    Spinner spinner = findViewById(R.id.language_spinner);
    List<Language> languages = AppDatabase.getInstance(this).languageDao().getAll();
    List<String>languageStrings = new LinkedList<>();
    for(int i = 0; i < languages.size(); i++){
        languageStrings.add(languages.get(i).getLanguage());
    }
    ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,
            android.R.layout.simple_dropdown_item_1line,
            languageStrings);
    adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
    spinner.setAdapter(adapter);
    return spinner;
}
private微调器createLanguageSpinner(){
微调器微调器=findviewbyd(R.id.language\u微调器);
List languages=AppDatabase.getInstance(this.languageDao().getAll();
ListLanguageString=新建LinkedList();
对于(int i=0;i
我的问题是:

 List<Language> languages = AppDatabase.getInstance(this).languageDao().getAll();
List languages=AppDatabase.getInstance(this.languageDao().getAll();

我无法用预定义对象填充当前列表,这将导致没有选项可供选择的空微调器。你能告诉我哪里错了吗?我还想听听关于如何简化适配器创建的意见。

我来晚了一点,但万一有人也有这个问题

问题是您试图插入没有PrimaryKey
id
值的新对象。因此,您将在数据库中获得一个空表

您可以手动设置
id
值,例如:

@Entity
public class Language {

    ...

    public Language(long id, String language) {
        this.id = id; // or create method to generate a unique id as a PrimaryKey value must be unique
        this.language = language;
    }

    public static Language[] populateData() {
        return new Language[]{
                new Language(1, "English"),
                new Language(2, "French"),
                new Language(3, "Spanish"),
                new Language(4, "Russian"),
                new Language(5, "Italian")
        };
    }
}
或者使用PrimaryKey的
autoGenerate
属性让SQLite生成唯一id:

@PrimaryKey(autoGenerate = true)
private long id;
有关更多信息,请参阅

不需要对代码进行其他更改


关于第二个问题:

我还想听听关于如何简化程序的意见 适配器的创建

您可以为微调器创建自定义适配器,并将
列表直接传递给它:

public class MyAdapter extends BaseAdapter implements SpinnerAdapter {

    private LayoutInflater mInflater;
    private List<Language> mItems;

    public MyAdapter(Context context, List<Language> items) {
        mInflater = LayoutInflater.from(context);
        mItems = items;
    }

    @Override
    public int getCount() {
        return mItems.size();
    }

    @Override
    public Object getItem(int position) {
        return mItems.get(position);
    }

    @Override
    public long getItemId(int position) {
        return mItems.get(position).getId();
    }

    // This is for the default ("idle") state of the spinner.
    // You can use a custom layout or use the default one.
    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        View view = convertView;
        if (view == null) {
            view = mInflater.inflate(R.layout.spinner_item, parent, false);
        }
        Language item = (Language) getItem(position);
        TextView textView = view.findViewById(R.id.text);
        textView.setText(item.getTitle());
        return view;
    }

    // Drop down item view as stated in the method name.
    @Override
    public View getDropDownView(int position, View convertView, ViewGroup parent) {
        View view = convertView;
        if (view == null) {
            view = mInflater.inflate(R.layout.spinner_dropdown_item, parent, false);
        }
        Language item = (Language) getItem(position);
        TextView textView = view.findViewById(R.id.text);
        textView.setText(item.getTitle());
        return view;
    }
}
在你的活动中:

List<Language> languages = AppDatabase.getInstance(this).languageDao().getAll();

Spinner spinner = findViewById(R.id.spinner);
MyAdapter myAdapter = new MyAdapter(this, languages);
spinner.setAdapter(myAdapter);
List<Language> languages = AppDatabase.getInstance(this).languageDao().getAll();

Spinner spinner = findViewById(R.id.spinner);
// Pass your list as the third parameter. No need to convert it to List<String>
ArrayAdapter<Language> adapter = new ArrayAdapter<>(this, android.R.layout.simple_dropdown_item_1line, languages);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
spinner.setAdapter(adapter);
List languages=AppDatabase.getInstance(this.languageDao().getAll();
微调器微调器=findViewById(R.id.Spinner);
//将列表作为第三个参数传递。无需将其转换为列表
ArrayAdapter=新的ArrayAdapter(这是android.R.layout.simple\u下拉列表\u item\u 1line,语言);
setDropDownViewResource(android.R.layout.simple\u微调器\u下拉菜单\u项);
旋转器。设置适配器(适配器);

根据android设计模式,您应该使用存储库,而不是调用dao来填充微调器,否则您可能会得到exception@Zhar当然但是这个答案是基于这个问题,为了便于理解,我使用了与OP相同的方法。Does
R.layout.spinner_item
layout是spinner放置的布局吗?
List<Language> languages = AppDatabase.getInstance(this).languageDao().getAll();

Spinner spinner = findViewById(R.id.spinner);
// Pass your list as the third parameter. No need to convert it to List<String>
ArrayAdapter<Language> adapter = new ArrayAdapter<>(this, android.R.layout.simple_dropdown_item_1line, languages);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
spinner.setAdapter(adapter);