0

我一直在寻找我的问题的答案,但我似乎没有得到任何答案,尽管我遵循了多少教程,我经历了多少问题,以及我试图做多少我想做的事情。基本上,我偶然发现了一些好的技巧,但仍然无法做到想要的。

问题

我正在创建一个将使用片段(与选项卡一起)的 Android 应用程序。在这些片段中,我有与应用程序相关的重要信息,例如文本框和按钮。但是,我想做一些非常简单的事情,那就是在我回到它时更新我的​​一个片段(想象我滑回一个片段,并用相关信息更新它)。信息存储在哪里?在 node.js 服务器上,我每次需要信息时都会调用它。因此,我创建了以下结构。

结构

首先,我开始创建我的活动。

public class CentralActivity extends FragmentActivity {
    CentralPagerAdapter mCentralActivity;
    ViewPager mViewPager;

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

    public void tabHandler() {
        mCentralActivity = new CentralPagerAdapter(getSupportFragmentManager());
        mViewPager = (ViewPager) findViewById(R.id.CentralPager);
        mViewPager.setAdapter(mCentralActivity);

        mViewPager.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
            @Override
            public void onPageSelected(int position) {
                getActionBar().setSelectedNavigationItem(position);
            }
        });

        //Action Bar Stuff

    }

}

话虽如此,我需要我的 CentralPagerAdapter,我创建如下。

public class CentralPagerAdapter extends FragmentStatePagerAdapter {

    private int nSwipes = 3;

    public CentralPagerAdapter(FragmentManager fm) {
        super(fm);
    }

    @Override
    public Fragment getItem(int i) {
        Fragment fragment = new CentralFragment();
        Bundle args = new Bundle();
        args.putInt(CentralFragment.ARG_OBJECT, i + 1);
        fragment.setArguments(args);
        return fragment;
    }

    @Override
    public int getCount() {
        return nSwipes;
    }
}

现在,我的片段,它只是一个包含我所有视图和选项等的类。

public class CentralFragment extends Fragment {
    public static final String ARG_OBJECT = "object";
    private View rootView;
    private RESTFunction currentFunction;
    //Has the info I want
    private ArrayList<Integer> tickets = new ArrayList<Integer>();

    @SuppressLint("HandlerLeak")
    private Handler threadConnectionHandler = new Handler() {
        @Override
        public void handleMessage(Message msg) {
            switch (currentFunction) {
                case GET_CLIENT_TICKETS:
                    handleGetTickets(msg);
                    break;
                case BUY_CLIENT_TICKETS:
                    break;
                default:
                    break;
            }
        }
    };

    @Override
    public View onCreateView(final LayoutInflater inflater, final ViewGroup container,
            Bundle savedInstanceState) {
        final Bundle args = getArguments();
        handleFragments(inflater, container);
        getTicketInfo(null);    
        return rootView;
    }

    private void handleFragments(LayoutInflater inflater, ViewGroup container) {

        Bundle args = getArguments();

        if (args.getInt(ARG_OBJECT) == 1) {
            rootView = inflater.inflate(R.layout.fragment_show_tickets,
                    container, false);
            showTicketsHandler();
        } else if (args.getInt(ARG_OBJECT) == 2) {
            rootView = inflater.inflate(R.layout.fragment_buy_tickets,
                    container, false);
            buyTicketsHandler();
        } else {
            rootView = inflater.inflate(R.layout.fragment_history_tickets,
                    container, false);
        }
    }

    public void showTicketsHandler() {
        //Get stuff from the tickets array that the REST call will handle
        //And set them to boxes or radio buttons
    }

    public void buyTicketsHandler() {
        //Get stuff from the tickets array that the REST call will handle
        //And set them to boxes or radio buttons
        //As well as button click listeners
    }

    public void getTicketInfo(ProgressDialog progDialog) {
        //Connect to the thread to get the information
        //In this case, I have no parameters
        ConnectionThread dataThread = new ConnectionThread("myLink", Method.GET, null, threadConnectionHandler, progDialog);
        dataThread.start();
    }

    //Get stuff from the resulting JSON and store it in the tickets ArrayList
    private void handleGetTickets(Message msg) {
    JSONObject ticketListing = (JSONObject) msg.obj;
        try {
            tickets.add(ticketListing.getInt("t1"));
            tickets.add(ticketListing.getInt("t2"));
            tickets.add(ticketListing.getInt("t3"));
        } catch (JSONException e) {
            e.printStackTrace();
        }
    }
}

然后,我有我的线程..

public class ConnectionThread extends Thread {

    private ConnectionRunnable runConnection;
    private Handler mHandler;
    private ProgressDialog progDialog;

    public ConnectionThread(String link, Method method, ArrayList<NameValuePair> payload, Handler handler, ProgressDialog progDialog) {
        runConnection = new ConnectionRunnable(link, method.toString(), payload);
        mHandler = handler;
        this.progDialog = progDialog;
    }

    @Override
    public void run() {
        runConnection.run();
        threadMsg();

        if(progDialog != null)
            progDialog.dismiss();
    }

    public JSONObject getJSON() {
        return runConnection.getResultObject();
    }

    private void threadMsg() {
        Message msgObj = mHandler.obtainMessage();
        msgObj.obj = getJSON();
        mHandler.sendMessage(msgObj);
    }

}

ConnectionRunnable 是我运行 HttpURLConnection 的地方。

那么我需要什么?

基本上,我要做的是在加载所有视图并更新它们之前从 ConnectionThread 获取票证信息。另外,我希望能够来回滑动,并在我滑动屏幕时更新我在阵列上的信息(如果我转到第二个屏幕,票会更新,如果我回到第一个屏幕,他们将重新更新)。所以基本上,每次我滑动时都调用 ConnectionThread。如果那是可能的,那就是。

我尝试了什么?

我已经尝试了几件事,但实际上都没有帮助..

  • 在fragment的onCreateView方法上使用ProgressDialogs来停止UI Thread(没用,因为它在处理所有事情之前返回了rootView);
  • 使 UI 线程休眠 1 秒(我不知道为什么,它会阻塞所有线程);
  • 覆盖Adapter的instantiateMethod(),虽然我觉得我没做对;
  • 覆盖Adapter的saveState(),以防止其保存状态,进而获取新的ticket信息;
  • 给 Fragments 标签以更新它们在 Adapter 上的 rootViews,但无济于事;
  • 在活动中获取信息,每次购买(第二个片段)时,重新启动整个活动以获取门票,我认为这是一个非常非常糟糕的解决方案。

我已经阅读了几篇文章,但我仍然找不到我的答案。这真的很令人沮丧。然而,因为它是如此简单,所以我必须在不同的线程上运行 HTTP 调用这一事实延迟了整个 UI 更新过程。

我还阅读了 AsyncTask 的方法。但是,我觉得 Threads 和 AsyncTasks 最终都是一样的。

现在要做什么?

嗯,这就是我希望找到的。因为它最终会很烦人。

可能的原因

是不是因为我将所有类都分成了散布文件,因此使我的工作变得困难?

谢谢你的时间,伙计们,希望我们能找到解决方案或其他东西。

编辑

所以基本上,在阅读了 4 个小时的文档和教程之后,我发现我需要的是 setOffscreenPageLimit( int)。但是,它不能设置为 0,所以我将不得不使用 setOnPageChangeListener。现在,要弄清楚如何刷新片段,我会像新的一样。

好的,它完美运行!基本上,我这样做了:

    mViewPager.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
                @Override
                public void onPageSelected(int position) {
                    ((CentralFragment)((CentralPagerAdapter) mViewPager.getAdapter()).instantiateItem(mViewPager, position)).refresh();
                    getActionBar().setSelectedNavigationItem(position);
                }
            });

我的 .refresh 在哪里:

public void refresh() {
    Bundle args = getArguments();
    if (args.getInt(ARG_OBJECT) == 0) {
        getTicketInfo(0);
    } else if (args.getInt(ARG_OBJECT) == 1) {
        getTicketInfo(1);
        buyTicketsHandler();
    } else {
        //To Handle Later
    }       
}

就像在访问之前刷新页面一样简单。为什么我以前不记得这个..?所以,这里是那些有需要的人的参考!

4

0 回答 0