1

Listfragmentでは、 JSONの結果をオンライン サーバー(1,2,3,4) から読み込むことができますが、ホーム ボタンを押してアプリに戻ると、Listview に重複したリスト (1,2,3, 4,1,2,3,4)、画面を回転させると時々発生します。

私はたくさん読んでいます...そしてたくさんの投稿がありますが、さまざまなケースがあるので、ここに私のケースがあります...

私のUI ... ViewPager > ListFragment

ListFragment : ローダー、AsyncTaskLoader、BaseAdapter、JSON、HashMap

使用しない/私の場合ではない: Cursors、SQLite、ContentProvider、Activity、ListActivity、String[]

はい... httpclient を httpurlconnection に変更します:)

さらに良くなった...別のアクティビティから ListFragment に戻り、アイテムを選択すると... アプリがクラッシュします!!!、LogCat は次のように述べています:「アダプターのコンテンツが変更されましたが、ListView は通知を受け取りませんでした」アダプターのコンテンツがバックグラウンド スレッドからではなく、UI スレッドからのみ変更されていることを確認してください。

runOnUiThread()を試してみたかったのですが、明らかに ListFragment では機能しませんが、ListActivity では機能しません...私の場合はそうではありません。

履歴書:この 2 つの問題は、onLoadingBackground() のプロセスと onLoadingFinish() のプロセスがうまく解決できないためだと思います。:S

そして... 私は使っています... 私はandroid:configChanges="orientation|screenSize"気分が悪い、それは不正行為です!!! xD

念のため... 私は Volley を使用していません。なぜなら、JAVA/Android のロジックについてもっと学びたいからです。また、Volley で問題が発生した場合に...質問に答える人が少ないからです :S

私はこれを求めたくありませんでしたが... 数時間前に投稿を読みました.

なに???そして、私はこれで 3 週間以上立ち往生しています。:S (下手な英語でごめんなさい... がんばっています、スペイン語を話します)

public class miNewFragment extends ListFragment implements LoaderManager.LoaderCallbacks<List<Model>> {

    static ParseadorJSON_func ParseadorJSON_objeto = new ParseadorJSON_func();
    static ArrayList<HashMap<String, String>> arrayListaCompleta;
    private static String urlPagina2 = "http://www.domain.com/json/mi_json.php";
    private static final String TAG_SUCCESS = "success";
    private static final String TAG_CATEGORIAS = "categorias";
    private static final String TAG_PID = "idItem";
    private static final String TAG_NAME = "name";
    static JSONArray jsonCategorias = null;
    private ListView miListView;
    myBaseAdapter miAdapter;

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View rootView = inflater.inflate(R.layout.categorias, container, false);
        miListView = (ListView)rootView.findViewById(android.R.id.list);
        arrayListaCompleta = new ArrayList<HashMap<String, String>>();
        Log.e("onCreateView = ", "miListView > arrayListacompleta > return rootView");
        return rootView;
    }

    @Override
    public void onActivityCreated(Bundle savedInstanceState) {
        myBaseAdapter miAdapter = new myBaseAdapter(getActivity());
        miListView.setAdapter(miAdapter);
        super.onActivityCreated(savedInstanceState);
        getLoaderManager().initLoader(0, null, this);
        Log.e("onActivityCreated = ", "myBaseAdapter > setAdapter > getLoaderManager");
    }

    @Override
    public Loader<List<Model>> onCreateLoader(int arg0, Bundle arg1) {
        Log.e("Loader/onCreateLoader = ", "myAsyncTaskLoader");
        return new myAsyncTaskLoader(getActivity());
    }

    @Override
    public void onLoadFinished(Loader<List<Model>> arg0, List<Model> data) {
        miAdapter = new myBaseAdapter(getActivity());
        miListView.setAdapter(miAdapter);
        miAdapter.notifyDataSetChanged();
        Log.e("Loader/onLoadFinished = ", "myBaseAdapter > setAdapter > notifyDataSetChanged");
    }

    @Override
    public void onLoaderReset(Loader<List<Model>> arg0) {
        Log.e("Loader/onLoaderReset = ", "Nothing");
    }

    @Override
    public void onListItemClick(ListView l, View v, int position, long id) {
        Log.e("onListItemClick = ", "Nothing");

    }



    public class myBaseAdapter extends BaseAdapter {    
        private Context mContext;
        public myBaseAdapter(Context c) {
            mContext = c;
        }
        public int getCount() {
            return arrayListaCompleta.size();
        }
        public Object getItem(int position) {
            return null;
        }
        public long getItemId(int position) {
            return position;
        }
        public View getView(int position, View convertView, ViewGroup parent) {
            Holder holder = null;
            if (convertView == null) {
                holder = new Holder();
                LayoutInflater ltInflate = (LayoutInflater) mContext.getSystemService( Context.LAYOUT_INFLATER_SERVICE );
                convertView = ltInflate.inflate(R.layout.categorias_list_item, null);
                holder.h_categTag = (TextView) convertView.findViewById(R.id.categTag);
                holder.h_categIdItem = (TextView) convertView.findViewById(R.id.categIdItem);
                convertView.setTag(holder); 
            } else {
                holder = (Holder) convertView.getTag();
            }
            holder.h_categTag.setText( arrayListaCompleta.get(position).get("name").toString() );
            holder.h_categIdItem.setText( arrayListaCompleta.get(position).get("idItem").toString() );
            return convertView;
        }
        class Holder {
            TextView h_categTag;
            TextView h_categIdItem;
        }
    }

    public static class myAsyncTaskLoader extends AsyncTaskLoader<List<Model>> {
        List<Model> mModels;
        public myAsyncTaskLoader(Context context) {
            super(context);
        }
        @Override
        public List<Model> loadInBackground() {
            Log.e("Async/loadInBackground = ", "Creating Array from JSON");  
            List<NameValuePair> arrayDelServidor = new ArrayList<NameValuePair>();
            JSONObject jsonCompleto = ParseadorJSON_objeto.makeHttpRequest(urlPagina2, "GET", arrayDelServidor);
            try {
                int success = jsonCompleto.getInt(TAG_SUCCESS);
                if (success == 1) { 
                    jsonCategorias = jsonCompleto.getJSONArray(TAG_CATEGORIAS);
                    for (int i = 0; i < jsonCategorias.length(); i++) {
                        JSONObject jsonFila = jsonCategorias.getJSONObject(i);
                        String id = jsonFila.getString(TAG_PID);
                        String name = jsonFila.getString(TAG_NAME);
                        HashMap<String, String> mapaDatos = new HashMap<String, String>();
                        mapaDatos.put(TAG_PID, id);
                        mapaDatos.put(TAG_NAME, name);
                        arrayListaCompleta.add(mapaDatos);
                    }  
                } else {
                    //nada
                }
            } catch (JSONException e) {
                e.printStackTrace();
            }
            return null;
        }

        @Override
        public void deliverResult(List<Model> listOfData) {
            if (isReset()) {
                Log.e("Async/deliverResult = ", "isReset()");
                if (listOfData != null) {
                    onReleaseResources(listOfData);
                }
            }
            List<Model> oldApps = listOfData;
            mModels = listOfData;
            if (isStarted()) {
                Log.e("Async/deliverResult = ", "isStarted()");
                super.deliverResult(listOfData);
            }
            if (oldApps != null) {
                Log.e("Async/deliverResult = ", "oldApps");
                onReleaseResources(oldApps);
            }
        }

        @Override
        protected void onStartLoading() {
            if (mModels != null) {
                deliverResult(mModels);
                Log.e("Async/onStartLoading = ", "mModels != null");
            }
            if (takeContentChanged()) {
                forceLoad();
                Log.e("Async/onStartLoading = ", "takeContentChanged()");
            }
            if (mModels == null) {
                forceLoad();
                Log.e("Async/onStartLoading = ", "mModels == null");
            }
        }

        @Override
        protected void onStopLoading() {
            cancelLoad();
            Log.e("Async/onStopLoading = ", "cancelLoad()");
        }

        @Override
        public void onCanceled(List<Model> apps) {
            super.onCanceled(apps);
            onReleaseResources(apps);
            Log.e("Async/onCanceled = ", "onReleaseResources(apps)");
        }

        @Override
        protected void onReset() {
            super.onReset();
            onStopLoading();
            if (mModels != null) {
                onReleaseResources(mModels);
                mModels = null;
                Log.e("Async/onReset = ", "onReleaseResources(mModels)");
            }
        }

        protected void onReleaseResources(List<Model> apps) {
            Log.e("Async/onReleaseResources = ", "Entró pero no hizo nada");
        }

    }
}

そして、誰かがこれらのコードを必要とする場合...

final class Model {
    private String name;
    private String id;
    public Model(String name, String id) {
        this.name = name;
        this.id = id;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getId() {
        return id;
    }
    public void setId(String id) {
        this.id = id;
    }
}

        public static class ParseadorJSON_func {
        InputStream is = null;
        JSONObject jObj = null;
        String json = "";
        public ParseadorJSON_func() {
        }

        public JSONObject makeHttpRequest(String url, String method, List<NameValuePair> arrayDesdeServidor) {
            try {
                if(method == "POST"){
                    DefaultHttpClient httpClient = new DefaultHttpClient();
                    HttpPost httpPost = new HttpPost(url);
                    httpPost.setEntity(new UrlEncodedFormEntity(arrayDesdeServidor));
                    HttpResponse httpResponse = httpClient.execute(httpPost);
                    HttpEntity httpEntity = httpResponse.getEntity();
                    is = httpEntity.getContent();
                }else if(method == "GET"){
                    DefaultHttpClient httpClient = new DefaultHttpClient();
                    String paramString = URLEncodedUtils.format(arrayDesdeServidor, "utf-8");
                    url += "?" + paramString;
                    HttpGet httpGet = new HttpGet(url);
                    HttpResponse httpResponse = httpClient.execute(httpGet);
                    HttpEntity httpEntity = httpResponse.getEntity();
                    is = httpEntity.getContent();
                }          

            } catch (UnsupportedEncodingException e) {
                e.printStackTrace();
            } catch (ClientProtocolException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }

            try {
                BufferedReader reader = new BufferedReader(new InputStreamReader(is, "iso-8859-1"), 8);
                StringBuilder sb = new StringBuilder();
                String line = null;
                while ((line = reader.readLine()) != null) {
                    sb.append(line + "\n");
                }
                is.close();
                json = sb.toString();
            } catch (Exception e) {
                Log.e("Buffer Error", "Error converting result " + e.toString());
            }
            try {
                jObj = new JSONObject(json);
            } catch (JSONException e) {
                Log.e("JSON Parser", "Error parsing data " + e.toString());
            }
            return jObj;
        }
    }

.

編集: loadInBackground()

アクティビティからこの Listfragment に戻り、アイテムを選択すると、loadInBackground がアダプターのコンテンツを変更し、コンテンツを更新しないため、アプリがクラッシュしました。さて、これでif else ...アダプターがnullかどうかをチェックし、loadInBackgroundを実行するかどうかを確認するため、アプリはクラッシュしませんが...

私がやった方法は...おそらく最も適切な方法ではないと思います.私はそこに到達していませんが、結果を更新または追加したいときは...この方法はうまくいかないかもしれません. ヘルプ/例はありますか?

        @Override
        public List<Model> loadInBackground() {
            Log.e("Async/loadInBackground = ", "Creating Array from JSON");
            //NEW if else...
            if(  miAdapter != null  ){
                adaptadorEstado = "No es Null";
            }else{
                adaptadorEstado = "Si es Null";

                List<NameValuePair> arrayDelServidor = new ArrayList<NameValuePair>();
                JSONObject jsonCompleto = ParseadorJSON_objeto.makeHttpRequest(urlPagina2, "GET", arrayDelServidor);
                try {
                    int success = jsonCompleto.getInt(TAG_SUCCESS);
                    if (success == 1) { 
                        jsonCategorias = jsonCompleto.getJSONArray(TAG_CATEGORIAS);
                        for (int i = 0; i < jsonCategorias.length(); i++) {
                            JSONObject jsonFila = jsonCategorias.getJSONObject(i);
                            String id = jsonFila.getString(TAG_PID);
                            String name = jsonFila.getString(TAG_NAME);
                            HashMap<String, String> mapaDatos = new HashMap<String, String>();
                            mapaDatos.put(TAG_PID, id);
                            mapaDatos.put(TAG_NAME, name);
                            arrayListaCompleta.add(mapaDatos);
                        }  
                    } else {
                        //nada
                    }
                } catch (JSONException e) {
                    e.printStackTrace();
                }
            }//end new if else
            Log.e("Async/loadInBackground = ", "Adaptador > "+adaptadorEstado);
            return null;
        }

.

新規: onConfigurationChanged()

私は不正行為をしていたので、android:configChanges="orientation|screenSize"試してみましたが、これがマニフェストに残っているonConfigurationChanged()場合にのみ機能/応答します。configChangesしたがって、この問題は、loadInBackground() を解決しようとする方法に関係していると思いますが、よくわかりません。

一方...私onCreateはMainActivityの作成について多くのことを読んで、 savedInstanceStatenullかどうかを確認してから、「getSupportFragmentManager()。beginTransaction()。findFragmentByTag()」のようなものを使用し、試してみると...私の MainActivity ではmiPagerAdapter = new funcionPagerAdapter(getSupportFragmentManager());、おそらく私の場合は...別の方法で解決すると思うので、このことは機能しないことがわかりました...しかし、方法がわかりません! :S

//In my ListFragment...
@Override
public void onConfigurationChanged(Configuration congfValues) {
    super.onConfigurationChanged(congfValues);
    Log.e("onConfigurationChanged = ", "Si entró");
    if(  miAdapter != null  ){
        Log.e("onConfigurationChanged = ", "Adaptador Lleno");
    }else{
        miAdapter = new myBaseAdapter(getActivity());
        miListView.setAdapter(miAdapter);
        Log.e("onConfigurationChanged = ", "Adaptador estaba Vacío (ya no)");
    }
}


//In my MainActivity (onCreate)
public void onCreate(Bundle savedInstanceState){
    super.onCreate(savedInstanceState);
    setContentView(R.layout.home_viewpager);

    Fragment_categorias miFragCategoria;
    if (savedInstanceState!= null) {
        miFragCategoria = (Fragment_categorias) getSupportFragmentManager().findFragmentByTag("tagCategoria");
    } else {
        miFragCategoria = new Fragment_categorias();
        getSupportFragmentManager().beginTransaction().add(R.id.(i dont know), miFragCategoria, "tagCategoria").commit(); 
    }

    //viewpager
    miPagerAdapter = new funcionPagerAdapter(getSupportFragmentManager());
    miViewPager = (ViewPager) findViewById(R.id.vpContenedor);
    miViewPager.setOffscreenPageLimit(5);
    miViewPager.setAdapter(miPagerAdapter);
}
4

0 に答える 0