1

我正在尝试实现刷新值动态的 ListAdapter。如果我不需要从互联网连接中获取值(我的情况),这不是一个大问题。

为此,我在适配器中实现了一个 AsyncTask 内部类,但屏幕值的更新不起作用。所有过程都执行没有错误,但屏幕上的信息不会改变。

关于我的代码的一些评论如下:

我的方法 getView 被执行并调用 ConsultaPrevisaoBackGround (我的 AsyncTask)来咨询来自互联网的值,他在 getView 方法的末尾执行。

在 AsyncTask 类中,我从 Internet 获取值,并在 onPostExecuteMethod 中调用方法来刷新我的持有者(用于封装小部件的类)。它工作正常(正在运行),但不会反映在屏幕信息中。事实上,有时更新屏幕有时不。

我的疑问是:

1 - 我的策略是正确的?如果是,错误在哪里?2 - 我可以做些什么来执行这个过程一次,而不是每次用户滚动屏幕时执行?

我在这方面工作了很长时间,但找不到解决方案......帮助!

package br.com.teste.adapters;

import java.text.SimpleDateFormat;
import java.util.Collections;
import java.util.List;
import java.util.StringTokenizer;

import android.content.Context;
import android.os.AsyncTask;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.LinearLayout;
import android.widget.TextView;
import br.com.teste.beans.horarios.Estimativa;
import br.com.teste.beans.horarios.Previsao;
import br.com.teste.beans.linhas.Linha;
import br.com.teste.R;
import br.com.teste.util.PrevisaoUtil;

public class ListaLinhasAdapter extends BaseAdapter {
private Context context;
private List<Linha> linhas;
private String pontoId;
private LayoutInflater inflater;
private ViewHolder holder;
private String idLinha;
private Previsao p;

public ListaLinhasAdapter(Context context, List<Linha> listaLinhas,
        String pontoID) {
    this.context = context;
    this.linhas = listaLinhas;
    this.pontoId = pontoID;
    this.inflater = LayoutInflater.from(context);
}

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

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

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

@Override
public View getView(int position, View view, ViewGroup parent) {
    // Recupera o estado da posição atual
    Linha linha = linhas.get(position);

    if (view == null) {
        view = inflater.inflate(R.layout.listadadoslinhas, null);
        holder = new ViewHolder(context);
        // Número da linha
        holder.txtIdLinha = (TextView) view.findViewById(R.id.txtIdLinha);
        // Nome da linha
        holder.txtNomeLinha = (TextView) view
                .findViewById(R.id.txtNomeLinha);

        // Seta campo de informação sem parada
        holder.txtMsgSemParada = (TextView) view
                .findViewById(R.id.msgSemParada);

        // seta layouts de previsão
        holder.llLinha1 = (LinearLayout) view
                .findViewById(R.id.linearPrevisoes1);
        holder.llLinha2 = (LinearLayout) view
                .findViewById(R.id.linearPrevisoes2);
        holder.llLinha3 = (LinearLayout) view
                .findViewById(R.id.linearPrevisoes3);

        // Seta campos de previsão
        holder.txtPrev1 = (TextView) view.findViewById(R.id.txtPrev1);
        holder.txtPrev2 = (TextView) view.findViewById(R.id.txtPrev2);
        holder.txtPrev3 = (TextView) view.findViewById(R.id.txtPrev3);
        holder.txtPrev4 = (TextView) view.findViewById(R.id.txtPrev4);
        holder.txtPrev5 = (TextView) view.findViewById(R.id.txtPrev5);
        holder.txtPrev6 = (TextView) view.findViewById(R.id.txtPrev5);

        view.setTag(holder);
    } else {
        holder = (ViewHolder) view.getTag();
        holder.reset();
    }

    String lin = linha.getLinha().trim();
    StringTokenizer stk = new StringTokenizer(lin, "-");

    // Número da linha
    idLinha = stk.nextToken();
    holder.txtIdLinha.setText(idLinha);

    // Nome da linha
    holder.txtNomeLinha.setText(stk.nextToken());

    new ConsultaPrevisaoBackGround().execute("");

    return view;
}

static class ViewHolder {
    Context context;
    TextView txtIdLinha;
    TextView txtNomeLinha;
    TextView txtMsgSemParada;

    LinearLayout llLinha1;
    LinearLayout llLinha2;
    LinearLayout llLinha3;

    TextView txtPrev1;
    TextView txtPrev2;
    TextView txtPrev3;
    TextView txtPrev4;
    TextView txtPrev5;
    TextView txtPrev6;

    public ViewHolder(Context cont) {
        this.context = cont;
    }

    public void reset() {
        txtIdLinha.setText(null);
        txtNomeLinha.setText(null);
        limpaPrevisoes();
    }

    //Clear fields
    private void limpaPrevisoes() {
        llLinha1.setVisibility(View.GONE);
        llLinha2.setVisibility(View.GONE);
        llLinha3.setVisibility(View.GONE);
        txtMsgSemParada.setVisibility(View.GONE);

        txtPrev1.setText(null);
        txtPrev2.setText(null);
        txtPrev3.setText(null);
        txtPrev4.setText(null);
        txtPrev5.setText(null);
        txtPrev6.setText(null);
    }

    //Show message error in textview
    public void showError() {
        showMsg(context.getResources().getString(R.string.msgErroPrevisao));
    }

    public void showMsg(String msg) {
        limpaPrevisoes();
        txtMsgSemParada.setText(msg);
    }

    public void fillPrevisao(Previsao p) {
        Collections.sort(p.getPonto());

        if (p.getPonto().size() > 6) {
            // get only first 6 occurs
            for (int i = 6; i < p.getPonto().size(); i++)
                p.getPonto().remove(i);
        }

        int cont = 1;
        for (Estimativa estimativa : p.getPonto()) {
            setPrevisao(cont, estimativa, p);
            cont++;
        }

        if (p.getPonto().size() <= 2) {
            llLinha2.setVisibility(View.GONE);
            llLinha3.setVisibility(View.GONE);
        }

        if ((p.getPonto().size() > 2) && (p.getPonto().size() <= 4))
            llLinha3.setVisibility(View.GONE);

    }

    // Preenche o campo referente à estimativa
    private void setPrevisao(int id, Estimativa estimativa,
            Previsao previsao) {

        switch (id) {
        case 1:
            txtPrev1.setText(getPrevisaoFormatada(previsao, estimativa));
            setBackGroundColor(estimativa, txtPrev1);
            break;
        case 2:
            txtPrev2.setText(getPrevisaoFormatada(previsao, estimativa));
            setBackGroundColor(estimativa, txtPrev2);
            break;
        case 3:
            txtPrev3.setText(getPrevisaoFormatada(previsao, estimativa));
            setBackGroundColor(estimativa, txtPrev3);
            break;
        case 4:
            txtPrev4.setText(getPrevisaoFormatada(previsao, estimativa));
            setBackGroundColor(estimativa, txtPrev4);
            break;
        case 5:
            txtPrev5.setText(getPrevisaoFormatada(previsao, estimativa));
            setBackGroundColor(estimativa, txtPrev5);
            break;
        case 6:
            txtPrev6.setText(getPrevisaoFormatada(previsao, estimativa));
            setBackGroundColor(estimativa, txtPrev6);
            break;
        default:
            break;
        }

    }

    private String getPrevisaoFormatada(Previsao previsao,
            Estimativa estimativa) {
        String horaStr;
        String minutoStr;
        long horaAtual = Long.parseLong(previsao.getHorarioAtual());
        long segundos = (estimativa.getHorarioPacote() - horaAtual) / 1000;
        int semanas = (int) Math.floor(segundos / 604800);
        segundos -= semanas * 604800;
        int dias = (int) Math.floor(segundos / 86400);
        segundos -= dias * 86400;
        int horas = (int) Math.floor(segundos / 3600);
        segundos -= horas * 3600;
        int minutos = (int) Math.floor(segundos / 60);
        segundos -= minutos * 60;

        minutos += 1;

        if (horas < 10)
            horaStr = "0" + horas;
        else
            horaStr = String.valueOf(horas);

        if (minutos < 10)
            minutoStr = "0" + minutos;
        else
            minutoStr = String.valueOf(minutos);

        String tempo;
        if (horas > 0)
            tempo = horaStr + "h " + minutoStr + "min";
        else
            tempo = minutoStr + "min";

        SimpleDateFormat spf = new SimpleDateFormat("HH:mm:ss");
        tempo = tempo + " às "
                + spf.format(estimativa.getHorarioEstimado());
        return tempo;
    }

    private void setBackGroundColor(Estimativa estimativa, TextView txtView) {
        // Imagem a ser exibida
        switch (estimativa.getStatus()) {
        case 0:
            txtView.setBackgroundColor(context.getResources().getColor(
                    R.color.previsaoVerde));
            break;
        case 1:
            txtView.setBackgroundColor(context.getResources().getColor(
                    R.color.previsaoLaranja));
            break;
        case 2:
            txtView.setBackgroundColor(context.getResources().getColor(
                    R.color.previsaoVermelha));
            break;
        default:
            break;
        }
    }
}

private class ConsultaPrevisaoBackGround extends AsyncTask<String, Void, String> {

    @Override
    protected String doInBackground(String... params) {
            try {
                PrevisaoUtil pUtil = new PrevisaoUtil(pontoId.trim(), idLinha.trim(),
                        context);
                p = pUtil.getPrevisao();
            } catch (Exception e) {
                return "error";
            }
        return "Executed";
    }

    @Override
    protected void onPostExecute(String result) {
        if(result.equals("error"))
        {
            holder.showError();
            return;
        }
        if ((p.getErro() != null) && (p.getErro().trim().length() > 0))
            holder.showMsg(p.getErro());

        if ((p.getPonto() == null) || (p.getPonto().size() == 0))
            holder.showMsg(context.getResources().getString(
                    R.string.msgSemPrevisao));

        holder.fillPrevisao(p);
    }
}
}

对不起,大帖子,但信息多于信息少

更新

问题解决了,我从适配器中删除了 AsynkTask 内部类并投入活动。

4

3 回答 3

0

覆盖ConsultaPrevisaoBackGround

private class ConsultaPrevisaoBackGround extends AsyncTask<String, Void, String> {
    ViewHolder holder;
    public  ConsultaPrevisaoBackGround(ViewHolder holder){
        this.holder = holder;
    }

使用 Holder 刷新 UI

于 2013-09-12T05:41:50.303 回答
0

对不起,这更容易理解

private class ConsultaPrevisaoBackGround extends AsyncTask<String, Void, String> {
    ViewHolder holder;
    public  ConsultaPrevisaoBackGround(ViewHolder holder){
        this.holder = holder;
    }

@Override
protected String doInBackground(String... params) {
        try {
            PrevisaoUtil pUtil = new PrevisaoUtil(pontoId.trim(), idLinha.trim(),
                    context);
            p = pUtil.getPrevisao();
        } catch (Exception e) {
            return "error";
        }
    return "Executed";
}

}

于 2013-09-12T05:44:00.757 回答
0

如果要刷新ListView,请致电

 notifyDataSetChanged()

在您的适配器上。

也看看ListView.invalidateViews()

也看看这个问题和答案:如何刷新 Android 列表视图?

于 2013-09-11T22:16:52.433 回答