com.keysolutions.meteorparties.PartyDetailFragment.java Source code

Java tutorial

Introduction

Here is the source code for com.keysolutions.meteorparties.PartyDetailFragment.java

Source

/*
* (c)Copyright 2013 Ken Yee, KEY Enterprise Solutions 
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package com.keysolutions.meteorparties;

import java.util.Map;

import com.keysolutions.ddpclient.android.DDPBroadcastReceiver;
import com.keysolutions.meteorparties.R;

import android.annotation.SuppressLint;
import android.content.BroadcastReceiver;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.content.LocalBroadcastManager;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.view.ViewGroup;
import android.view.animation.DecelerateInterpolator;
import android.view.animation.OvershootInterpolator;
import android.widget.RadioGroup;
import android.widget.RadioGroup.OnCheckedChangeListener;
import android.widget.TableLayout;
import android.widget.TableRow;
import android.widget.TextView;
import android.widget.ToggleButton;

/**
 * A fragment representing a single Party detail screen. This fragment is either
 * contained in a {@link PartyMapActivity} in two-pane mode (on tablets) or a
 * {@link PartyDetailActivity} on handsets.
 */
public class PartyDetailFragment extends Fragment {
    /**
     * The fragment argument representing the item ID that this fragment
     * represents.
     */
    public static final String ARG_ITEM_ID = "item_id";

    /** The dummy content this fragment is presenting. */
    private Party mParty;

    /** Make receiver a member variable of a class to be able to unregister it later */
    private BroadcastReceiver mReceiver;

    DecelerateInterpolator sDecelerator = new DecelerateInterpolator();
    OvershootInterpolator sOverShooter = new OvershootInterpolator(10f);

    /**
     * Mandatory empty constructor for the fragment manager to instantiate the
     * fragment (e.g. upon screen orientation changes).
     */
    public PartyDetailFragment() {
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        if (getArguments().containsKey(ARG_ITEM_ID)) {
            String docId = getArguments().getString(ARG_ITEM_ID);
            mParty = MyDDPState.getInstance().getParty(docId);
        }
    }

    /**
     * Initial display of view and fields is done here
     */
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View rootView = inflater.inflate(R.layout.fragment_party_detail, container, false);

        // Show the party details.
        if (mParty != null) {
            showPartyInfo(savedInstanceState, rootView);
            updateMyRsvpDisplay(rootView);
        }

        return rootView;
    }

    /**
     * Displays party info
     * @param savedInstanceState instance state
     * @param rootView view the party display elements are in
     */
    public void showPartyInfo(Bundle savedInstanceState, View rootView) {
        ((TextView) rootView.findViewById(R.id.party_title)).setText(mParty.getTitle());
        ((TextView) rootView.findViewById(R.id.party_description)).setText(mParty.getDescription());
        // get ready to show my RSVP info
        String myUserId = MyDDPState.getInstance().getUserId();
        // add RSVP list
        // NOTE: if you have a lot of RSVPs, you should be using a ListView
        // The TableLayout is used here to make it this demo simple to
        // understand
        if (mParty.getRsvps() != null) {
            TableLayout table = (TableLayout) rootView.findViewById(R.id.rsvp_list);
            table.removeAllViews();
            // add header
            TableRow tr = (TableRow) getLayoutInflater(savedInstanceState).inflate(R.layout.header_party_rsvp,
                    null);
            table.addView(tr);
            for (Map<String, String> rsvp : mParty.getRsvps()) {
                String rsvpValue = rsvp.get("rsvp");
                String rsvpUser = rsvp.get("user");
                if ((myUserId == null) || (!myUserId.equals(rsvpUser))) {
                    // don't add row for my RSVP because that's displayed later
                    tr = (TableRow) getLayoutInflater(savedInstanceState).inflate(R.layout.row_party_rsvp, null);
                    TextView tv;
                    tv = (TextView) tr.findViewById(R.id.user);
                    String email = MyDDPState.getInstance().getUserEmail(rsvpUser);
                    tv.setText(email);
                    tv = (TextView) tr.findViewById(R.id.rsvp);
                    String rsvpDisplayed = "";
                    int rsvpColor = 0;
                    if (rsvpValue.equals("yes")) {
                        rsvpDisplayed = "Going";
                        rsvpColor = 0xFF00FF00;
                    } else if (rsvpValue.equals("no")) {
                        rsvpDisplayed = "Declined";
                        rsvpColor = 0xFFFF0000;
                    } else if (rsvpValue.equals("maybe")) {
                        rsvpDisplayed = "Maybe";
                        rsvpColor = 0xFF0000FF;
                    }
                    tv.setText(rsvpDisplayed);
                    tv.setTextColor(rsvpColor);
                    table.addView(tr);
                }
            }
        }
    }

    /**
     * Looks up current user's RSVP
     * @return null, "yes", "no", or "maybe"
     */
    public String getMyRsvp() {
        String myRsvp = null;
        String myUserId = MyDDPState.getInstance().getUserId();
        for (Map<String, String> rsvp : mParty.getRsvps()) {
            String rsvpValue = rsvp.get("rsvp");
            String rsvpUser = rsvp.get("user");
            if ((myUserId != null) && (myUserId.equals(rsvpUser))) {
                myRsvp = rsvpValue;
            }
        }
        return myRsvp;
    }

    /**
     * Updates current RSVP display
     * @param rootView root view holding all the fields
     */
    @SuppressLint("NewApi")
    public void updateMyRsvpDisplay(View rootView) {
        // add info about my RSVP
        boolean isLoggedIn = MyDDPState.getInstance().isLoggedIn();
        ((View) (rootView.findViewById(R.id.login_for_rsvp)))
                .setVisibility(isLoggedIn ? View.INVISIBLE : View.VISIBLE);
        ((View) (rootView.findViewById(R.id.rsvp_buttons)))
                .setVisibility(isLoggedIn ? View.VISIBLE : View.INVISIBLE);
        ((View) (rootView.findViewById(R.id.label_my_rsvp)))
                .setVisibility(isLoggedIn ? View.VISIBLE : View.INVISIBLE);

        if (isLoggedIn) {
            RadioGroup rsvpButtons = ((RadioGroup) rootView.findViewById(R.id.rsvp_buttons));
            rsvpButtons.setOnCheckedChangeListener(new OnCheckedChangeListener() {
                @Override
                public void onCheckedChanged(RadioGroup radioGroup, int checkedId) {
                    for (int j = 0; j < radioGroup.getChildCount(); j++) {
                        final ToggleButton view = (ToggleButton) radioGroup.getChildAt(j);
                        view.setChecked(view.getId() == checkedId);
                    }
                }
            });
            ToggleButton btnYes = ((ToggleButton) rootView.findViewById(R.id.rsvp_yes));
            ToggleButton btnNo = ((ToggleButton) rootView.findViewById(R.id.rsvp_no));
            ToggleButton btnMaybe = ((ToggleButton) rootView.findViewById(R.id.rsvp_maybe));
            OnClickListener toggleListener = new OnClickListener() {
                @Override
                public void onClick(View v) {
                    onToggle(v);
                }
            };
            btnYes.setOnClickListener(toggleListener);
            btnNo.setOnClickListener(toggleListener);
            btnMaybe.setOnClickListener(toggleListener);
            String myRsvp = getMyRsvp();
            if (myRsvp != null) {
                if (myRsvp.equals("yes")) {
                    rsvpButtons.check(R.id.rsvp_yes);
                } else if (myRsvp.equals("no")) {
                    rsvpButtons.check(R.id.rsvp_no);
                } else if (myRsvp.equals("maybe")) {
                    rsvpButtons.check(R.id.rsvp_maybe);
                }
            }

            // if we can, add button animation on Yes because it's cool
            if (android.os.Build.VERSION.SDK_INT > 11) {
                btnYes.animate().setDuration(200);
                btnYes.setOnTouchListener(new OnTouchListener() {
                    @Override
                    public boolean onTouch(View button, MotionEvent event) {
                        if (event.getAction() == MotionEvent.ACTION_DOWN) {
                            ((ToggleButton) button).animate().setInterpolator(sDecelerator).scaleX(.7f).scaleY(.7f);
                        } else {
                            ((ToggleButton) button).animate().setInterpolator(sOverShooter).scaleX(1f).scaleY(1f);
                        }
                        return false;
                    }
                });
            }
        }
    }

    /**
     * Used to make a group of ToggleButtons act like radiobuttons
     * @param view
     */
    public void onToggle(View view) {
        int id = view.getId();
        ((RadioGroup) view.getParent()).check(0); // to make it behave not like a toggle
        ((RadioGroup) view.getParent()).check(id);
        MyDDPState ddp = MyDDPState.getInstance();
        switch (id) {
        case R.id.rsvp_yes:
            ddp.rsvp(mParty.getId(), "yes");
            break;
        case R.id.rsvp_no:
            ddp.rsvp(mParty.getId(), "no");
            break;
        case R.id.rsvp_maybe:
            ddp.rsvp(mParty.getId(), "maybe");
            break;
        }
    }

    @Override
    public void onPause() {
        super.onPause();

        if (mReceiver != null) {
            // unhook the receiver
            LocalBroadcastManager.getInstance(getActivity()).unregisterReceiver(mReceiver);
            mReceiver = null;
        }
    }

    @Override
    public void onResume() {
        super.onResume();

        // get ready to handle DDP events
        mReceiver = new DDPBroadcastReceiver(MyDDPState.getInstance(), getActivity()) {
            @Override
            protected void onSubscriptionUpdate(String changeType, String subscriptionName, String docId) {
                if ((mParty != null) && (mParty.getId().equals(docId))) {
                    // redisplay party
                    showPartyInfo(null, getView());
                }
            }

            @Override
            protected void onLogin() {
                showPartyInfo(null, getView());
                updateMyRsvpDisplay(getView());
            }

            @Override
            protected void onLogout() {
                showPartyInfo(null, getView());
                updateMyRsvpDisplay(getView());
            }
        };
    }

}