【问题标题】:Android-RecyclerView Set Image And Text From JSONAndroid-RecyclerView 从 JSON 中设置图像和文本
【发布时间】:2016-08-05 02:45:19
【问题描述】:

嗨,我正在尝试从 JSON 制作 RecyclerView 列表,它正在发送图像 URL 和名称 (我现在只需要向 RecyclerView 显示这些)。我从过去 2 天开始尝试使用 Google 和 Stack,但 仍然没有解决方案将文本和图像从 JSON 设置为 RecyclerView 大多数教程使用 Volley 或其他库,并且他们在同一类中使用 AsyncTask(解决数据传递问题 )。我没有使用

我已经成功地制作了 recyclerView,其中本地图像和文本存储在 Drawable 文件夹和字符串数组中(Values-->String.xml) 并且工作正常

但我的情况与大多数解决方案不同

1) 我正在从 Fragment 的父 Activity 调用 AsyncTask.Execute 方法

2) 我的 AsyncTask 类不在我调用 AsyncTask.Execute 方法的同一类中。

3) 我正在尝试从 AsyncTask 获取 Fragment 中的值,即使在设置 setter 和 getter 方法后,它也总是返回 Null(很难将 Images[] 和 Name[] 传输到 Fragment)

4) 当我在 String[] 中获取图像路径时,如何将路径设置到 Recycler View 中

这是我的课程

***从我调用 AsyncTask.Execute 方法的地方。

      public class Navigation_Drawer extends AppCompatActivity {

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        //Handle Item Selection
        switch (item.getItemId()){
            case R.id.action_websearch:    
                Toast.makeText(getBaseContext(), "You have Clicked WebSearch", Toast.LENGTH_LONG).show();
                break;
            case R.id.parseJson:
                 new JsonParsing().execute();//AYSNCTASK EXECUTE
        }

那么Aysnctask Execute调用这个类

   public class JsonParsing extends AsyncTask<String, Void, List<String[]>> {

private String URL_Path="http://www.example.com/test/Android/Data/showUers.php";
private static final String TAG="JSON PARSER******";
HttpURLConnection connection;
BufferedReader reader;
private Context context;



@Override
protected String[] doInBackground(String... params) {
    try {
        URL url=new URL(URL_Path);
        connection= (HttpURLConnection) url.openConnection();
        connection.connect();
        Log.d(TAG,connection.toString());

        InputStream inputStream=connection.getInputStream();
        reader=new BufferedReader(new InputStreamReader(inputStream));
        String line;
        StringBuffer stringBuffer=new StringBuffer();
        while ((line=reader.readLine())!=null){
            stringBuffer.append(line);

        }
        String completeJSON=stringBuffer.toString();

        JSONArray parentArray=new JSONArray(completeJSON);
        String[] Name=new String[parentArray.length()];
        String[] ImagePath=new String[parentArray.length()];
        for (int i = 0; i <parentArray.length() ; i++) {
            JSONObject childObject=parentArray.getJSONObject(i);

            String Fname=childObject.getString("First_Name") ;
            String Lname=childObject.getString("Last_Name") ;

            Name[i]=Fname+" "+Lname;
            ImagePath[i]=childObject.getString("Image");
            Log.d(TAG,"String Arrays "+Name[i]+" "+ ImagePath[i]);
            //THIS LOG SUCCESSFULLY SHOWING RESULT IN LOG


        }

          List<String[]> results=new ArrayList<>(2);
          results.add(Name);
          results.add(ImagePath);
          return results;

    } catch (MalformedURLException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    } catch (JSONException e) {
        e.printStackTrace();
    } finally {

        try {
            connection.disconnect();
            if (reader!=null) {
                reader.close();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    return null;
}





 @Override
    protected void onPostExecute(List<String[]> results) {
    Log.d(TAG,"ON POST EXECUTE CALLING START");
    String[] Name=results.get(0);
    String[] Image=results.get(1);
    Log.d(TAG,"ON POST EXECUTE CALLING Bundle");
    FriendsList friendsListFragment=new FriendsList();
    Bundle dataToPass=new Bundle();
    dataToPass.putStringArray("Names",Name);
    dataToPass.putStringArray("ImagePath",Image);
    friendsListFragment.setArguments(dataToPass);
    friendsListFragment.getData(dataToPass);
    Log.d(TAG,"ON POST EXECUTE CALLING LAST "+Name.toString());

}

这是我调用 RecyclerView 的片段

public class FriendsList extends Fragment {

    RecyclerView recyclerView;
    RecyclerView.Adapter adapter;
    RecyclerView.LayoutManager layoutManager;
    TypedArray Image;

    public static final String TAG="Friends List******";

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // Inflate the layout for this fragment
        View view=inflater.inflate(R.layout.activity_friend_list,container,false);
        recyclerView= (RecyclerView) view.findViewById(R.id.RecyclerViewForFriendList);

        Name=getResources().getStringArray(R.array.left_Drawer_Menu);
        Image=getResources().obtainTypedArray(R.array.user_image);

        recyclerView.setHasFixedSize(true);
    adapter=new RecyclerFriendListAdapter(getActivity(),Name,Image);
        recyclerView.setAdapter(adapter);
        recyclerView.setAdapter(adapter);
        layoutManager=new LinearLayoutManager(getActivity());
        recyclerView.setLayoutManager(layoutManager);


        String[] Name=getArguments().getStringArray("Names");//Returns Null
        String[] Image=getArguments().getStringArray("ImagePath");

    return view;
}



public void getData(Bundle savedInstanceState){
        if (savedInstanceState!=null) {
            Log.d(TAG, "GET DATA CALLING ");
           String[] New_Name = getArguments().getStringArray("Names");
           String[] New_ImagePath =getArguments().getStringArray("ImagePath");
            Log.d(TAG, "ON CREATE SETTING NAME AND IMAGEPATH INTO ARRAY " + New_ImagePath[2]+" "+New_Name[1]);
            adapter=new RecyclerFriendListAdapter(getActivity(),New_Name,New_ImagePath);
            recyclerView.setAdapter(adapter);//*************RETURNS NULL 
            Log.d(TAG, "GET DATA CALLING FINISHED ");


        }
}}

回收器适配器类

    public class RecyclerFriendListAdapter extends RecyclerView.Adapter<RecyclerFriendListAdapter.ViewHolder> {
    String[] Name,ImagePath;
    TypedArray Image;
    Context context;
    static final String TAG="FRIEND LIST ADAPTER****";


    public RecyclerFriendListAdapter(Context context,String[] name,TypedArray image) {
        this.context = context;
        Image = image;
        Name = name;
    }

 public RecyclerFriendListAdapter(Context context,String[] image, String[] name) {
        this.context=context;
        ImagePath = image;
        Name = name;
    }


    @Override
    public RecyclerFriendListAdapter.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        LayoutInflater layoutInflater= (LayoutInflater) parent.getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        View view=layoutInflater.inflate(R.layout.listview_item_recycler,null);
        Log.d(TAG,"Constructor Calling");
        return new ViewHolder(view);
    }

    @Override
    public void onBindViewHolder(RecyclerFriendListAdapter.ViewHolder holder, int position) {
        Log.d(TAG,"Holder "+position);
        holder.UserImage.setImageResource(Image.getResourceId(position,0));
        holder.Name.setText(Name[position]);
       }

    @Override
    public int getItemCount() {
        return Name.length;
    }

    public static class ViewHolder extends RecyclerView.ViewHolder {
        TextView Name;
        ImageView UserImage;
        Context context;

        public ViewHolder(View v) {
            super(v);
            Log.d(TAG,"View Holder");

            Name= (TextView) v.findViewById(R.id.User_Name_Item);
            UserImage= (ImageView) v.findViewById(R.id.UserImage);
        }


    }

我知道我在代码中犯了一些错误但我需要做这些事情

从 doinbackground 获取图像和名称字符串数组,然后在 Fragment 中获取这些值,并将两个数组发送到 RecyclerView 适配器以显示在 recyclerview 列表中。

这是一个小问题,只有专家才能解决这个问题,所以请帮我解决这个问题

@Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        new JsonParsing.execute();   
        showSkipButton(true);
        setProgressButtonEnabled(true);

    }


      @Override
        public void onDonePressed(Fragment currentFragment) {
            super.onDonePressed(currentFragment);
            Intent intent=new Intent(this,Parent_Activty.class);
            startActivity(intent);
        }

这是附加片段的父活动

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

    //First set up toolbar
    setupToolbar();

    //Add the Fragment to the container
    FragmentTransaction transaction=getFragmentManager().beginTransaction();
    FriendsList friendList=new FriendsList();
    transaction.replace(R.id.Parent_Main_Layout,friendList);
    transaction.commit();
}

作为@Cricket_007 Suggest 和 Wrapper 类的新接口

public interface onResultReceived {
    public void onResultRececivedFuc(List<String[]> users);
}

包装类

 public  class WrapperClass {

        String[] Name,Image;

        public String[] getName() {
            return Name;
        }

        public void setName(String[] name) {
            Name = name;
        }

        public String[] getImage() {
            return Image;
        }

        public void setImage(String[] image) {
            Image = image;
        }

    }

最后是我的日志

    08-07 02:17:57.490 32184-32184/com.recyclerview_pro_working1 D/Friends List******: ON CREATE CALLING 
08-07 02:17:57.490 32184-32184/com.recyclerview_pro_working1 D/Friends List******: ON CREATE VIEW START
08-07 02:17:57.490 32184-32184/com.recyclerview_pro_working1 D/Friends List******: PUTTING VALUE INTO NAME AND IMAGE
08-07 02:17:57.490 32184-32184/com.recyclerview_pro_working1 D/Friends List******: ON CREATE VIEW [Ljava.lang.String;@437092e0
08-07 02:17:57.550 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Constructor Calling
08-07 02:17:57.550 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: View Holder
08-07 02:17:57.550 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Holder 0
08-07 02:17:57.600 32184-32188/com.recyclerview_pro_working1 D/dalvikvm: GC_CONCURRENT freed 1791K, 42% free 24608K/41927K, paused 2ms+3ms, total 33ms
08-07 02:17:57.600 32184-32184/com.recyclerview_pro_working1 D/dalvikvm: WAIT_FOR_CONCURRENT_GC blocked 17ms
08-07 02:17:57.640 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Constructor Calling
08-07 02:17:57.640 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: View Holder
08-07 02:17:57.640 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Holder 1
08-07 02:17:57.650 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Constructor Calling
08-07 02:17:57.650 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: View Holder
08-07 02:17:57.650 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Holder 2
08-07 02:17:57.660 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Constructor Calling
08-07 02:17:57.660 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: View Holder
08-07 02:17:57.660 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Holder 3
08-07 02:17:57.670 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Constructor Calling
08-07 02:17:57.670 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: View Holder
08-07 02:17:57.670 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Holder 4
08-07 02:17:57.680 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Constructor Calling
08-07 02:17:57.680 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: View Holder
08-07 02:17:57.680 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Holder 5
08-07 02:17:57.680 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Constructor Calling
08-07 02:17:57.680 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: View Holder
08-07 02:17:57.690 32184-32184/com.recyclerview_pro_working1 D/FRIEND LIST ADAPTER****: Holder 6
08-07 02:17:57.700 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position0
08-07 02:17:57.700 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position1
08-07 02:17:57.710 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position2
08-07 02:17:57.720 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position3
08-07 02:17:57.720 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position4
08-07 02:17:57.730 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position5
08-07 02:17:57.730 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position6
08-07 02:17:57.740 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position7
08-07 02:17:57.740 32184-32184/com.recyclerview_pro_working1 D/ADAPTER*********: Value of Position8
08-07 02:18:19.830 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: DO IN BACKGROUND START 
08-07 02:18:20.580 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: libcore.net.http.HttpURLConnectionImpl:DOMAIN NAME/test/Android/Data/showUers.php
08-07 02:18:21.200 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: GET INPUT STREAM AND PUUTING INTO READER
08-07 02:18:21.200 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: JSON ARRAY START
08-07 02:18:21.210 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: String Arrays Julien Blin DOMAIN NAME/test/Android/Data/uploads/Julien.jpg
08-07 02:18:21.210 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: String Arrays Iveta Benesova DOMAIN NAME/test/Android/Data/uploads/Iveta.jpg
08-07 02:18:21.210 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: String Arrays Varun Razora DOMAIN NAME/test/Android/Data/uploads/Varun.jpg
08-07 02:18:21.210 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: JSON PARSING FINISHED
08-07 02:18:21.210 32184-3367/com.recyclerview_pro_working1 D/JSON PARSER******: Return Statement
08-07 02:18:21.210 32184-32184/com.recyclerview_pro_working1 D/JSON PARSER******: ON POST EXECUTE CALLING START
08-07 02:18:21.210 32184-32184/com.recyclerview_pro_working1 D/JSON PARSER******: ON POST EXECUTE CALLING STOP
08-07 02:18:21.210 32184-32184/com.recyclerview_pro_working1 D/Friends List******: GET DATA CALLING 
08-07 02:18:21.210 32184-32184/com.recyclerview_pro_working1 D/Friends List******: ON CREATE SETTING NAME AND IMAGEPATH INTO ARRAY DOMAIN NAME/test/Android/Data/uploads/Varun.jpg Iveta Benesova
08-07 02:18:21.210 32184-32184/com.recyclerview_pro_working1 D/AndroidRuntime: Shutting down VM
08-07 02:18:21.210 32184-32184/com.recyclerview_pro_working1 W/dalvikvm: threadid=1: thread exiting with uncaught exception (group=0x416dd378)
08-07 02:18:21.220 32184-32184/com.recyclerview_pro_working1 E/AndroidRuntime: FATAL EXCEPTION: main
                                                                               java.lang.NullPointerException
                                                                                   at com.recyclerview_pro_working1.mainScreenFragments.FriendsList.getData(FriendsList.java:99)
                                                                                   at com.recyclerview_pro_working1.Sending_Image_To_Server.onPostExecute(Sending_Image_To_Server.java:130)
                                                                                   at com.recyclerview_pro_working1.Sending_Image_To_Server.onPostExecute(Sending_Image_To_Server.java:29)
                                                                                   at android.os.AsyncTask.finish(AsyncTask.java:631)
                                                                                   at android.os.AsyncTask.access$600(AsyncTask.java:177)
                                                                                   at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:644)
                                                                                   at android.os.Handler.dispatchMessage(Handler.java:99)
                                                                                   at android.os.Looper.loop(Looper.java:213)
                                                                                   at android.app.ActivityThread.main(ActivityThread.java:4787)
                                                                                   at java.lang.reflect.Method.invokeNative(Native Method)
                                                                                   at java.lang.reflect.Method.invoke(Method.java:511)
                                                                                   at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:789)
                                                                                   at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:556)
                                                                                   at dalvik.system.NativeStart.main(Native Method)

EDIT #1 As @Hendra Wijaya Djiono 建议我编辑我的代码,它仍然返回 Null,我认为它更多的原因是在没有价值的情况下启动片段(我之前也调用过 AsyncTask)我在哪里开始这样的父活动

EDIT #2 @Hendra Wijaya Djiono@cricket_007 都建议这两个答案都按我的预期工作,但@Hendra Bundle Point 似乎很容易并且清除和@cricket_007代码建议避免使用捆绑我同意他的观点,即在创建片段时捆绑将是空的,但只是为了让应用程序正常工作我更新了日志并将其发送数据编码为通过捆绑成功进行片段但它首先还有2个问题你可以看到 recyclerview.setAdapter(adapter) throws null pointer 以及如何在适配器中将 imagePath(URL of Image) 设置为 ImageView。

EDIT #3 @Cricket_007 建议我添加了接口和包装类,但将字符串(Name[] 和 Image[])都放入 List List=new ArrayList();让我很难过。所以我使用了 Noraml 列表函数并将两个字符串都放入其中,然后将其放入 onPostExecute。

【问题讨论】:

  • 请注意,有比 AsyncTask 更容易用于网络请求和 JSON 解析的库。您可以查看 Retrofit 以查看它是否符合您的需求。
  • 基本上,您正在尝试从 AsyncTask 返回结果以填充适配器。这篇文章涵盖了数据传递部分。 stackoverflow.com/questions/12575068/…
  • @cricket_007 我知道这些存在并且会更容易,但我不想将任何第三方库包含到当前应用程序中。它会增加应用程序负载这件事我避免这就是为什么我坚持基本功能
  • @cricket_007 我已经尝试过这个链接,你可以看到我写道我尝试了 setter 和 getter 方法和接口,但还没有运气
  • 在您的 onPostExecute 中,您创建了一个全新的 Fragment,设置了它的 Arguments,但没有对该 Fragment 执行任何操作,因此它从未加载过,onCreateView 也从未运行过。

标签: java android json string android-fragments


【解决方案1】:

说实话,您提供的代码不够简洁/健壮,但为了让您了解一些情况,我将使用您提供的代码。 第一个,如果你想同时传递 String[] Name 和 ImagePath,你可以创建一个 2D 数组或将两者都放入 List 或任何东西作为包装器

public class JsonParsing extends AsyncTask<String, Void, List<String[]>> {

    private String URL_Path = "http://www.example.com/test/Android/Data/showUers.php";
    private static final String TAG = "JSON PARSER******";
    HttpURLConnection connection;
    BufferedReader reader;
    private Context context;

    @Override
    protected String[] doInBackground(String... params) {
        try {
            URL url = new URL(URL_Path);
            connection = (HttpURLConnection) url.openConnection();
            connection.connect();
            Log.d(TAG, connection.toString());

            InputStream inputStream = connection.getInputStream();
            reader = new BufferedReader(new InputStreamReader(inputStream));
            String line;
            StringBuffer stringBuffer = new StringBuffer();
            while ((line = reader.readLine()) != null) {
                stringBuffer.append(line);

            }
            String completeJSON = stringBuffer.toString();

            JSONArray parentArray = new JSONArray(completeJSON);
            String[] Name = new String[parentArray.length()];
            String[] ImagePath = new String[parentArray.length()];
            for (int i = 0; i < parentArray.length(); i++) {
                JSONObject childObject = parentArray.getJSONObject(i);

                String Fname = childObject.getString("First_Name");
                String Lname = childObject.getString("Last_Name");

                Name[i] = Fname + " " + Lname;
                ImagePath[i] = childObject.getString("Image");
                Log.d(TAG, "String Arrays " + Name[i] + " " + ImagePath[i]);
                //THIS LOG SUCCESSFULLY SHOWING RESULT IN LOG

            }

            List<String[]> result = new ArrayList<>(2);
            result.add(Name);
            result.add(ImagePath);

            return result; // CONFUSE IN HOW TO RETURN 2 ARRAY STRING NAME AND IMAGE

        } catch (MalformedURLException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (JSONException e) {
            e.printStackTrace();
        } finally {

            try {
                connection.disconnect();
                if (reader != null) {
                    reader.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }

        return null;
    }

    @Override
    protected void onPostExecute(List<String[]> results) {
        //SOMETHING TODO WITH RESULTS
        String[] Name = results.get(0);
        String[] ImagePath = results.get(1);
    }
}

要将结果从活动传递给您的片段,您可以使用 Bundle

FriendsList friendsListFragment = new FriendsList();
Bundle dataToPass = new Bundle();
dataToPass.putStringArray("names", Name);
dataToPass.putStringArray("imagePaths", ImagePath);
friendsListFragment.setArguments(dataToPass);

在您的片段上,您可以获取数据

String[] names = getArguments().getStringArray("names");
String[] imagePaths = getArguments().getStringArray("imagePaths");

在您的 RecyclerView 适配器上,创建一个构造函数来传递数据

private String[] dataName, dataImagePath;

public RecyclerFriendListAdapter(Context context, String[] dataName, String[] dataImagePath) {
    this.context = context;
    this.dataName = dataName;
    this.dataImagePath = dataImagePath;
}

然后您可以通过该构造函数将片段中的数据传递给适配器

【讨论】:

  • 感谢您的回答和帮助我刚刚尝试了您向我展示的代码,但在 Fragment 上同样的事情它返回 Null。这就是我在 AsyncTask onPostExecute String[] Name=results.get(0); String[] Image=results.get(1); FriendsList friendsListFragment=new FriendsList(); Bundle dataToPass=new Bundle(); dataToPass.putStringArray("Names",Name); dataToPass.putStringArray("ImagePath",Image); friendsListFragment.setArguments(dataToPass); 中所做的并且像这样进入 Fragments String[] Name=getArguments().getStringArray("Names");
  • 真的吗?您可以编辑您的问题并包含新代码吗?并包含有关错误的堆栈跟踪
  • 请检查我更新了完整代码并感谢您的关注
  • 您的 RecyclerFriendListAdapter 和 FriendsList.onCreateView 配置不正确,请重新检查
  • 首先我应该在 oncreateview 上获取字符串数组的值,然后它将它发送到 RecyclerFriendListAdapter 但我在 CreateView 上得到空值。谢谢
【解决方案2】:

解决更新

getActivity 在您声明适配器时返回 null,因为您创建了一个全新的空 Fragment,未将其附加到 Activity。

然后,第二个问题是您将新的 Bundle 传递给 getData 方法,但您甚至没有使用 savedInstanceState 参数,而是使用了 getArguments。总的来说,如下所述,停止使用 Fragment Bundle 参数


首先,创建一个类来解析你的 JSON。如果您想简化该过程,可以使用 Gson 或 Jackson,但是将这些 String[] 封装到对象列表中将使该过程更容易。并且地址在 AsyncTask 中返回多个 String[]

public class User {
    private String name;
    private String imageUrl;
    // getters, setters, etc.
}

其次,(在How to get the result of OnPostExecute() ... because AsyncTask is a separate class? 之后)您可以定义一个接口,以使用您的结果列表“回调”到 UI 线程。

public interface AsyncUserResponse {
    public void onUsersReceived(List<User> users);
}

接下来,您希望 AsyncTask 向您返回 List&lt;User&gt;,并且您没有使用字符串参数,因此您可以使用 Void

public class GetUsersTask extends AsyncTask<Void, Void, List<User>> {

    private AsyncUserResponse delegate;
    public GetUsersTask(AsyncUserResponse delegate) {
        this.delegate = delegate;
    }    

    public List<User> doInBackground(Void... params) {
        List<User> users = new ArraryList<User>();
        // TODO: HTTP Request

        // TODO: Parse JSON string - store into list
        // Loop over some JSON array 
            String name = json.get("name");
            String image = json.get("image_url");
            User u = new User(name, image);
            users.add(u);
        // End loop 
        return users;
    }

    public void onPostExecute(List<User> result) {
        if (delegate != null) {
            delegate.onUsersReceived(result);
        } 
        // nothing else goes here - this method is done 
    }
}

最后,为了在 Fragment 类中调用 AsyncTask 并将结果返回给适配器,您的类可以实现该接口,或者您可以内联匿名类。您的选择。

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    // Inflate the layout for this fragment
    View view=inflater.inflate(R.layout.activity_friend_list,container,false);

    recyclerView= (RecyclerView) view.findViewById(R.id.RecyclerViewForFriendList);
    recyclerView.setHasFixedSize(true);
    layoutManager=new LinearLayoutManager(getActivity());
    recyclerView.setLayoutManager(layoutManager);

    AsyncUserResponse listener = new AsyncUserResponse() {
        @Override
        public void onUsersReceived(List<User> users) {
            adapter=new RecyclerFriendListAdapter(getActivity(), users);
            recyclerView.setAdapter(adapter);
        }
    };

    new GetUsersTask(listener).execute();


    return view;
}

注意:您还需要修改适配器以采用 List&lt;User&gt; 而不是两个字符串数组。

带走这里——忘记捆绑参数。您正在运行异步代码,因此在创建 Fragment 的视图时您将没有要获取的参数。这与 Volley、OkHttp、Retrofit 等使用的模式相同。了解它们的工作原理是很好的。

【讨论】:

  • 我会尽快回复你,我正在检查代码。非常感谢
  • 请检查更新的日志 cat 我认为 String 数组在将值存储在 doinbackground 的数组中之前正在调用,以及为什么 onPostExecute Log 在完成 doinbackground 后没有调用或应用程序停止日志的原因
  • 您的日志与代码不匹配,所以我不知道我在看什么。不过,总的来说,正如我所说 - 忘记 Fragment 的 Bundle 参数。
  • @androidXP 这是一种不同的方法,您可以直接从片段中使用它,因此您不需要将包从活动传递到片段。我同意,您可以将 1 个参数作为对象传递,而不是传递 2 个参数。它将更具可读性和可维护性
  • @cricket_007 现在它与代码匹配并检查我合并两个代码并在片段中创建新方法来调用 recycleradapter 请检查
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2017-10-16
  • 1970-01-01
  • 2018-11-22
  • 2016-12-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多