使用自定义对象在Asyctask之后刷新微调器

时间:2017-07-15 11:21:39

标签: android android-asynctask android-spinner android-adapter

我在使用自定义Spinner刷新Adapter时遇到问题。自定义适配器显示“名称”,但可以引用所有对象数据(例如“ID”,“年龄”)。

我使用Asynctask将在线数据导入为JSON并将它们存储在SQLite数据库中。

在我的MainActivity中,我有Spinner个自定义对象。 现在我尝试了很多,并且在使用'onPostExecute'更新SQLite数据库后无法更新spinneradapter。

我会跳过一些有效且不应影响的代码部分(导入,抓取数据,数据库内容......)以保持其清洁。

这是我的课程

users.java

package domain.project;

public class user{
    private String name;
    private int age;
    private long id;

public User(String name, int age, long id) {
        this.name = name;
        this.age= age;
        this.id = id;

    }


    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }


    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public long getId() {
        return id;
    }

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


    @Override
    public String toString() {
        String output = name;
        return output;
    }
}

UserDataSource.java

package domain.project;

// imports skipped

public class UserDataSource {

    private SQLiteDatabase database;

    public UserDataSource(Context context) {

    }
    public void open() {

       //Open database stuff

    }

    public void close() {
        //closing database stuff
    }

    public User createUser(String name, int age) {

        //writing users into SQLitedatabase stuff

        cursor.moveToFirst();
        User user = cursorToUser(cursor);
        cursor.close();

        return user;
    }

    public void deleteUser(User user) {
        //delete user from SQLitedatabase
    }

    public void refreshUser() {

        GetUsersTask getUsersTask = new GetUsersTask();
        getUsersTask.execute("Users");

    }

    public User updateUser(long id, String newName, int newAge) {
        //update User in SQLitedatabase
    }

    private User cursorToUser (Cursor cursor) {
        //getting User from SQLite Database

        User user = new User(name, age, id);

        return user;
    }


    public User[] allUsers() {
        {
        //filling Array with all Users from SQLitedatabase
        }
        return allUsers;
    }

    public class GetUsersTask extends AsyncTask<String, Integer, String[]> {

       private String[] readJsonUser(String jsonString) {

            try {
                JSONArray jArray = new JSONArray(jsonString);
                String[] returnArray = new String[jArray.length()];

                //parsing JSON String to Array

                }
                return returnArray ;

            } catch (final JSONException e) {

            }
            return null;
        }

        @Override
        protected String[] doInBackground(String... strings) {

            if (strings.length == 0) { 
                return null;
            }

            // grabbing JSON string from web and store it in userJsonString


            return readJsonUser(userJsonString);
        }


        @Override
        protected void onProgressUpdate(Integer... values) {

        }

        @Override
        protected void onPostExecute(String[] strings) {

            if (strings != null) {
                //write and update SQLite database

                }
            }
        }
    }

}

MainActivity.java

package domain.project;

//skipping the imports

public class MainActivity extends AppCompatActivity {

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

        dataSource = new UserDataSource(this);

    }

    @Override
    protected void onResume() {
        super.onResume();
        showAllListEntries();
    }

    @Override
    protected void onPause() {
        super.onPause();
        dataSource.close();
    }

    public void showAllListEntries() {

        final Spinner sqlUserSpinner = (Spinner) findViewById(R.id.spinner_user);
        final SpinAdapter userSpinAdapter = new SpinAdapter(this, android.R.layout.simple_spinner_dropdown_item, dataSource.allUsers());


        usersSpinner.setAdapter(userSpinAdapter);

        usersSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {

            public void onItemSelected(AdapterView<?> adapterView,
                                       View view, int i, long l) {
                // Testing the selected Item
                User user = userSpinAdapter.getItem(i);
                Toast.makeText(MainActivity.this, "Selected : " + user.getId() + "<-ID   age->" + user.getAge(), Toast.LENGTH_SHORT).show();

            }
            public void onNothingSelected(AdapterView<?> arg0) {


            }
        });
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {

        int id = item.getItemId();
        if (id == R.id.action_settings) {
            return true;
        }

        return super.onOptionsItemSelected(item);
    }



    public class SpinAdapter extends ArrayAdapter<User>{

        private Context context;
        private User[] values;

        public SpinAdapter(Context context, int textViewResourceId,
                           User[] values) {
            super(context, textViewResourceId, values);
            this.context = context;
            this.values = values;
        }

        public int getCount(){
            return values.length;
        }

        public SQLShot getItem(int position){
            return values[position];
        }

        public long getItemId(int position){
            return position;
        }


        @Override
        public View getView(int position, View convertView, ViewGroup parent) {

            TextView label = new TextView(context);
            label.setTextColor(Color.BLACK);
            label.setText(values[position].getName());
            return label;
        }

        @Override
        public View getDropDownView(int position, View convertView,
                                    ViewGroup parent) {
            TextView label = (TextView) super.getView(position, convertView, parent);
            label.setTextColor(Color.BLACK);
            label.setText(values[position].getName());

            return label;
        }
    }

}

2 个答案:

答案 0 :(得分:0)

默认情况下,适配器不会监听数据集,当数据集更改时,您必须将新数据传递给适配器并触发更新。

您需要在适配器内部更新它,更新和适配器始终是一个两步过程。 1.更新您的数据。 2.告诉适配器。

在适配器内创建:

public void update(List<String> data) {
  adapterDataList.clear();
  adapterDataList.addAll(data);
  notifyDatasetChanged();
}

您正在使用数组,我强烈建议您使用列表。数组的大小固定,会导致更多问题。

方法notifyDatasetChanged()使适配器知道数据列表中的更改。

由于您直接使用SQL,因此可以查看CursorAdapter。

如果您想要自动数据更新,Realm可以做到这一点。他们甚至还有适配器。 Realm是一个ORM我推荐ORM而不是原生的OpenHelper。另一个好的ORM是Sugar ORM,它不像Realm那样华丽,但使用起来非常简单,而且非常适合你的任务。

答案 1 :(得分:0)

我建议在适配器上调用notifyDataSetChangedmyAdapter.notifyDataSetChanged();。这将通知您的微调器数据集已更改,并且美国应相应更新。