com.eyekabob.ArtistInfo.java Source code

Java tutorial

Introduction

Here is the source code for com.eyekabob.ArtistInfo.java

Source

/**
 *  2014 Brien Coffield
 *
 * This file is subject to the terms and conditions defined in
 * file 'LICENSE', which is part of this source code package.
 */
package com.eyekabob;

import android.app.Dialog;
import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.Color;
import android.net.Uri;
import android.os.Bundle;
import android.text.Html;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.Toast;
import android.widget.TextView;
import android.widget.ToggleButton;
import com.eyekabob.models.Artist;
import com.eyekabob.models.Event;
import com.eyekabob.models.Venue;
import com.eyekabob.util.EyekabobHelper;
import com.eyekabob.util.ImageTask;
import com.eyekabob.util.JSONTask;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;

public class ArtistInfo extends EyekabobActivity {
    private Artist artist;
    private ArrayList<Event> futureEvents = new ArrayList<Event>() {
    };
    private boolean artistInfoReturned = false;
    private boolean futureEventsInfoReturned = false;
    private boolean imageInfoReturned = false;

    private OnClickListener onClickListener = new OnClickListener() {
        @Override
        public void onClick(View view) {
            if (view.getId() == R.id.findLiveMusicButton) {
                Intent findMusicIntent = new Intent(ArtistInfo.this, SearchIntermediate.class);
                startActivity(findMusicIntent);
            } else if (view.getId() == R.id.aboutButton) {
                Dialog aboutDialog = EyekabobHelper.createAboutDialog(ArtistInfo.this);
                aboutDialog.show();
            } else if (view.getId() == R.id.contactButton) {
                EyekabobHelper.launchEmail(ArtistInfo.this);
            } else if (view.getId() == R.id.infoBioToggleButton) {
                ToggleButton tb = (ToggleButton) findViewById(R.id.infoBioToggleButton);
                toggleBioText(tb.isChecked());
            } else {
                // Must be a future event
                FutureEventView row = (FutureEventView) view;
                Event event = row.getEvent();
                Intent intent = new Intent(getApplicationContext(), EventInfo.class);
                intent.putExtra("event", event);
                startActivity(intent);
            }
        }
    };

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.artist_info);
        artist = (Artist) getIntent().getExtras().get("artist");
        Log.d(getClass().getName(), "Artist name is: " + artist.getName());
        findViewById(R.id.findLiveMusicButton).setOnClickListener(onClickListener);
        findViewById(R.id.aboutButton).setOnClickListener(onClickListener);
        findViewById(R.id.contactButton).setOnClickListener(onClickListener);
        findViewById(R.id.infoBioToggleButton).setOnClickListener(onClickListener);

        Map<String, String> params = new HashMap<String, String>();
        if (artist.getMbid() == null) {
            params.put("artist", artist.getName());
        } else {
            params.put("mbid", artist.getMbid());
        }
        Uri artistInfoUri = EyekabobHelper.LastFM.getUri("artist.getInfo", params);

        // Send the request for artist info.
        new ArtistRequestTask().execute(artistInfoUri.toString());

        // Send last.fm request.
        Map<String, String> lastFMParams = new HashMap<String, String>();
        lastFMParams.put("artist", artist.getName());
        lastFMParams.put("limit", "10");
        Uri lastFMUri = EyekabobHelper.LastFM.getUri("artist.getEvents", lastFMParams);
        new FutureEventsRequestTask().execute(lastFMUri.toString());
    }

    /**
     * This method is called after the last.fm response is received. It will
     * parse the XML document response and put attributes on the Artist object.
     */
    protected void handleArtistResponse(JSONObject response) {
        try {
            JSONObject jsonArtist = response.optJSONObject("artist");
            if (jsonArtist == null) {
                Toast.makeText(this, R.string.no_results, Toast.LENGTH_SHORT).show();
                artistInfoReturned = true;
                dismissDialogIfReady();
                return;
            }
            artist.setName(jsonArtist.getString("name"));
            artist.setMbid(jsonArtist.getString("mbid"));
            artist.setUrl(jsonArtist.getString("url"));
            JSONObject jsonImage = EyekabobHelper.LastFM.getLargestJSONImage(jsonArtist.getJSONArray("image"));

            // Get artist image, if one exists.
            if (null != jsonImage) {
                new ArtistImageTask().execute(new URL(jsonImage.getString("#text")));
            } else {
                imageInfoReturned = true;
                dismissDialogIfReady();
            }

            JSONObject bio = jsonArtist.getJSONObject("bio");
            artist.setSummary(bio.getString("summary"));
            artist.setContent(bio.getString("content"));
        } catch (JSONException e) {
            Log.e(getClass().getName(), "", e);
        } catch (MalformedURLException e) {
            Log.e(getClass().getName(), "", e);
        }

        TextView artistNameView = (TextView) findViewById(R.id.infoMainHeader);
        artistNameView.setText(artist.getName());

        if (!(artist.getSummary() == null) && !artist.getSummary().equals("")) {
            TextView bioHeaderView = (TextView) findViewById(R.id.infoBioHeader);
            // TODO: I18N
            bioHeaderView.setText("Bio");
            TextView bioView = (TextView) findViewById(R.id.infoBioContent);
            String contentHtml = artist.getSummary();
            bioView.setText(Html.fromHtml(contentHtml));
            bioView.setVisibility(View.VISIBLE);
        }
        if (!(artist.getContent() == null) && !artist.getContent().equals("")) {
            ToggleButton tb = (ToggleButton) findViewById(R.id.infoBioToggleButton);
            tb.setVisibility(View.VISIBLE);
        }

        artistInfoReturned = true;
        dismissDialogIfReady();
    }

    /**
     * This method is called after the last.fm response is received. It will
     * parse the JSON response and put attributes on the Artist object.
     */
    protected void handleFutureEventsResponse(JSONObject response) {
        try {
            JSONObject jsonEvents = response.optJSONObject("events");
            if (jsonEvents == null || !jsonEvents.has("event")) {
                futureEventsInfoReturned = true;
                dismissDialogIfReady();
                return;
            }

            JSONArray jsonEventsArray = jsonEvents.getJSONArray("event");
            for (int i = 0; i < jsonEventsArray.length(); i++) {
                Event event = new Event();
                Venue venue = new Venue();
                event.setVenue(venue);

                JSONObject jsonEvent = jsonEventsArray.getJSONObject(i);
                JSONObject jsonVenue = jsonEvent.getJSONObject("venue");
                JSONObject jsonLocation = jsonVenue.getJSONObject("location");
                JSONObject jsonGeo = jsonLocation.optJSONObject("geo:point");

                event.setId(jsonEvent.getString("id"));
                event.setName(jsonEvent.getString("title"));
                event.setDate(EyekabobHelper.LastFM.toReadableDate(jsonEvent.getString("startDate")));
                JSONObject jsonImage = EyekabobHelper.LastFM.getJSONImage("large", jsonEvent.getJSONArray("image"));
                event.addImageURL("large", jsonImage.getString("#text"));

                venue.setName(jsonVenue.getString("name"));
                venue.setCity(jsonLocation.getString("city"));

                if (jsonGeo != null) {
                    venue.setLat(jsonGeo.optString("geo:lat"));
                    venue.setLon(jsonGeo.getString("geo:long"));
                }

                futureEvents.add(event);
            }
        } catch (JSONException e) {
            Log.e(getClass().getName(), "", e);
        }

        TextView nextConcertDateView = (TextView) findViewById(R.id.infoSubHeaderOne);
        TextView nextConcertLocationView = (TextView) findViewById(R.id.infoSubHeaderTwo);
        Event nextEvent;
        if (futureEvents.size() > 0) {
            nextEvent = futureEvents.get(0);
            // TODO: I18N
            nextConcertDateView.setText("Next Concert: " + nextEvent.getDate() + " @");
            nextConcertLocationView
                    .setText(nextEvent.getVenue().getName() + " in " + nextEvent.getVenue().getCity());
            TextView futureEventsHeaderView = (TextView) findViewById(R.id.infoFutureEventsHeader);
            // TODO: I18N
            futureEventsHeaderView.setText("Future Events");
            LinearLayout futureEventsContentView = (LinearLayout) findViewById(R.id.infoFutureEventsContent);
            int i;
            for (i = 0; i < futureEvents.size(); i++) {
                Event event = futureEvents.get(i);
                String futureText = event.getDate() + "\n";
                // TODO: I18N
                futureText += "@ " + event.getVenue().getName() + " in " + event.getVenue().getCity();
                FutureEventView row = new FutureEventView(this);
                row.setTextColor(Color.WHITE);
                row.setPadding(0, 0, 0, 20); // Bottom padding
                row.setText(futureText);
                row.setEvent(event);
                row.setOnClickListener(onClickListener);
                futureEventsContentView.addView(row);
            }
        } else {
            // TODO: I18N
            nextConcertDateView.setText("Next Concert: UNKNOWN");
        }

        futureEventsInfoReturned = true;
        dismissDialogIfReady();
    }

    // TODO: this is identical to the handleImageResponse in EventInfo,
    // and should be refactored.
    private void handleImageResponse(Bitmap img) {
        DisplayMetrics metrics = new DisplayMetrics();
        getWindowManager().getDefaultDisplay().getMetrics(metrics);
        float metWidth = metrics.widthPixels;
        float imgWidth = img.getWidth();
        float ratio = metWidth / imgWidth;
        // Add a little buffer room
        int newWidth = (int) Math.floor(img.getWidth() * ratio) - 50;
        int newHeight = (int) Math.floor(img.getHeight() * ratio) - 50;

        ImageView iv = (ImageView) findViewById(R.id.infoImageView);
        Bitmap rescaledImg = Bitmap.createScaledBitmap(img, newWidth, newHeight, false);
        iv.setImageBitmap(rescaledImg);
        imageInfoReturned = true;
        dismissDialogIfReady();
    }

    private void dismissDialogIfReady() {
        if (imageInfoReturned && artistInfoReturned && futureEventsInfoReturned) {
            dismissDialog();
        }
    }

    private void toggleBioText(boolean detailed) {
        TextView bioView = (TextView) findViewById(R.id.infoBioContent);

        String contentHtml = "";
        if (artist != null && !"".equals(artist.getContent())) {
            if (detailed) {
                contentHtml = artist.getContent();
            } else {
                contentHtml = artist.getSummary();
            }
        }

        bioView.setText(Html.fromHtml(contentHtml));
    }

    // Handles the asynchronous request, away from the UI thread.
    private class ArtistRequestTask extends JSONTask {
        protected void onPreExecute() {
            ArtistInfo.this.showDialog();
        }

        protected void onPostExecute(JSONObject result) {
            ArtistInfo.this.handleArtistResponse(result);
        }
    }

    private class FutureEventView extends TextView {
        private Event event;

        public FutureEventView(Context context) {
            super(context);
        }

        public void setEvent(Event event) {
            this.event = event;
        }

        public Event getEvent() {
            return event;
        }
    }

    // Handles the asynchronous request, away from the UI thread.
    private class FutureEventsRequestTask extends JSONTask {
        protected void onPostExecute(JSONObject result) {
            ArtistInfo.this.handleFutureEventsResponse(result);
        }
    }

    private class ArtistImageTask extends ImageTask {
        protected void onPostExecute(Bitmap img) {
            ArtistInfo.this.handleImageResponse(img);
        }
    }
}