package com.fatima.life2;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Iterator;
import java.util.Set;
import com.fatima.life2.R;
import com.limegroup.gnutella.ActivityCallback;
import com.limegroup.gnutella.Connection;
import com.limegroup.gnutella.Downloader;
import com.limegroup.gnutella.Endpoint;
import com.limegroup.gnutella.GUID;
import com.limegroup.gnutella.MediaType;
import com.limegroup.gnutella.RemoteFileDesc;
import com.limegroup.gnutella.RouterService;
import com.limegroup.gnutella.chat.Chatter;
import com.limegroup.gnutella.downloader.AlreadyDownloadingException;
import com.limegroup.gnutella.downloader.FileExistsException;
import com.limegroup.gnutella.search.HostData;
import com.limegroup.gnutella.security.User;
import com.limegroup.gnutella.settings.SharingSettings;
import com.limegroup.gnutella.util.StringUtils;
import android.app.Activity;
import android.app.AlertDialog;
import android.app.Dialog;
import android.app.ProgressDialog;
import android.content.ComponentName;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.ServiceConnection;
import android.media.MediaPlayer;
import android.media.MediaPlayer.OnCompletionListener;
import android.media.MediaPlayer.OnErrorListener;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Debug;
import android.os.Handler;
import android.os.IBinder;
import android.text.TextUtils;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.view.View.OnClickListener;
import android.widget.AdapterView;
import android.widget.BaseAdapter;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;
import android.widget.AdapterView.OnItemClickListener;
public class SearchResultActivity extends Activity {
private static final String TAG = Utils.TAG;
private static final int DIALOG_WAITING_FOR_SERVER = 1;
private static final int DIALOG_MUSIC_OPTIONS = 2;
private static final int DIALOG_MUSIC_STREAMING = 3;
private static final int MUSIC_OPTION_DOWNLOAD = 0;
private static final int MUSIC_OPTION_PREVIEW = 1;
private static final int MAX_SEARCH_DELAY = 60000;
private SearchResult mCurrentResult;
private static volatile SogouMusicSearcher sSogouMusicSearcher = new SogouMusicSearcher();
private static FetchMp3ListTask sFetchMp3ListTask;
private static WaitForRouterServiceTask sWaitForRouterServiceTask;
private SearchBar mSearch;
private String mQuery;
private ProgressDialog mProgressDialog;
private ProgressDialog mStreaming;
private DownloadService mDownloadService;
private byte[] mGuid;
private Handler mHandler = new Handler();
private ActivityCallback mListener;
private ListView mListView;
private Mp3ListAdapter mAdapter;
private volatile SearchAdapter mSearchAdapter;
private static volatile MediaPlayer sPlayer;
private static volatile Thread sPreviewThread;
private static volatile SearchResultActivity sSearchResultActivity;
private ServiceConnection mConnection = new ServiceConnection() {
public void onServiceConnected(ComponentName className, IBinder service) {
mDownloadService = ((DownloadService.LocalBinder)service).getService();
}
public void onServiceDisconnected(ComponentName className) {
mDownloadService = null;
}
};
private void download(SearchResult mp3) {
if (mp3 instanceof P2pSearchResult) {
P2pDownloadInfo download = new P2pDownloadInfo((P2pSearchResult) mp3);
download.setFileName(mp3.getFileName());
mDownloadService.insertDownload(download);
} else if (mp3 instanceof SogouSearchResult) {
SogouDownloadInfo download = new SogouDownloadInfo((SogouSearchResult) mp3);
mDownloadService.insertDownload(download);
}
Intent intent = new Intent(SearchResultActivity.this, DownloadActivity.class);
startActivity(intent);
}
private static String getURL(String link) throws IOException {
URL url = new URL(link);
HttpURLConnection connection = (HttpURLConnection)url.openConnection();
connection.setConnectTimeout(1000);
connection.connect();
StringBuilder builder = new StringBuilder(1024);
InputStreamReader is = new InputStreamReader(connection.getInputStream());
BufferedReader reader = new BufferedReader(is, 1024);
String line = null;
while ((line = reader.readLine()) != null) {
builder.append(line + "\n");
}
return builder.toString();
}
private void preview(final SearchResult mp3) {
if (mp3 instanceof P2pSearchResult) {
if (mDownloadService.fileBeingDownloaded((P2pSearchResult) mp3)) {
runOnUiThread(new Runnable() {
@Override
public void run() {
if (mStreaming != null) {
mStreaming.dismiss();
}
Utils.Error(SearchResultActivity.this, "You can't preivew the music while it is being downloaded");
}
});
return;
}
} else if (mp3 instanceof SogouSearchResult) {
if (mDownloadService.fileBeingDownloaded((SogouSearchResult) mp3)) {
runOnUiThread(new Runnable() {
@Override
public void run() {
if (mStreaming != null) {
mStreaming.dismiss();
}
Utils.Error(SearchResultActivity.this, "You can't preivew the music while it is being downloaded");
}
});
return;
}
}
if (sPreviewThread != null) {
sPreviewThread.interrupt();
sPreviewThread = null;
}
if (mp3 instanceof P2pSearchResult) {
sPreviewThread = new Thread(new Runnable() {
@SuppressWarnings("unchecked")
@Override
public void run() {
boolean previewError = false;
Downloader downloader = null;
MediaPlayer player = null;
try {
RemoteFileDesc rfd = ((P2pSearchResult)mp3).getFirstRFD();
if (rfd == null) {
previewError = true;
Log.e(TAG, "No rfd for preview.");
return;
}
RemoteFileDesc rfds[] = new RemoteFileDesc[] { rfd };
player = sPlayer;
if (player != null) {
player.release();
}
downloader = RouterService.download(rfds,
Collections.EMPTY_SET,
true,
new GUID(((P2pSearchResult)mp3).getGuid()));
if (downloader == null) {
previewError = true;
Log.e(TAG, "No downloader for preview.");
return;
}
String targetFile = downloader.getFile().getName();
int state = downloader.getState();
// Wait until we start to download.
while (state != Downloader.DOWNLOADING) {
// But if we can't continue, break the loop.
if (state == Downloader.ABORTED ||
state == Downloader.GAVE_UP ||
state == Downloader.DISK_PROBLEM ||
state == Downloader.CORRUPT_FILE ||
state == Downloader.WAITING_FOR_USER ||
state == Downloader.RECOVERY_FAILED ||
state == Downloader.PAUSED) {
previewError = true;
Log.e(TAG, "Invalid preview state: " + state);
break;
}
Thread.sleep(1000);
state = downloader.getState();
}
while (!previewError) {
String readyUrl = "http://localhost:" + Constants.MINI_SERVER_PORT +
"/cmd=ready&file=" + URLEncoder.encode(targetFile);
String ready = getURL(readyUrl).trim();
state = downloader.getState();
Utils.D("isReady: " + ready);
Utils.D("state: " + state);
if (ready.equals("true")) {
break;
}
Thread.sleep(1000);
}
if (!previewError) {
if (TextUtils.isEmpty(mp3.getFileName())) {
previewError = true;
Log.e(TAG, "Empty preview filename.");
return;
}
String previewUrl = "http://localhost:" + Constants.MINI_SERVER_PORT +
"/file=" + URLEncoder.encode(downloader.getFile().getName()) +
"&dwfile=" + URLEncoder.encode(mp3.getFileName());
player = new MediaPlayer();
player.reset();
Utils.D("preview url: " + previewUrl);
player.setDataSource(previewUrl);
Utils.D("+++ player data source set");
player.prepare();
Utils.D("+++ player prepared");
player.start();
Utils.D("+++ player started");
player.setOnCompletionListener(new OnCompletionListener () {
@Override
public void onCompletion(MediaPlayer mp) {
sPlayer = null;
Utils.D("+++ player completed");
if (sPreviewThread != null)
sPreviewThread.interrupt();
sPreviewThread = null;
if (sSearchResultActivity != null) {
sSearchResultActivity.runOnUiThread(new Runnable() {
@Override
public void run() {
sSearchResultActivity.dismissStreamingDialog();
}
});
}
}
});
sPlayer = player;
state = downloader.getState();
while ((DownloadService.isDownloading(state) &&
state != Downloader.WAITING_FOR_USER) ||
state == Downloader.COMPLETE) {
if (state == Downloader.ABORTED ||
state == Downloader.GAVE_UP ||
state == Downloader.DISK_PROBLEM ||
state == Downloader.CORRUPT_FILE ||
state == Downloader.WAITING_FOR_USER ||
state == Downloader.RECOVERY_FAILED ||
state == Downloader.PAUSED) {
previewError = true;
Log.e(TAG, "Invalid preview state: " + state);
break;
}
Thread.sleep(1000);
state = downloader.getState();
Utils.D("preview state: " + state);
}
Utils.D("+++ Exit state: " + state);
}
} catch (FileExistsException e) {
previewError = true;
e.printStackTrace();
} catch (FileNotFoundException e) {
previewError = true;
e.printStackTrace();
} catch (AlreadyDownloadingException e) {
previewError = true;
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
previewError = true;
e.printStackTrace();
} catch (IllegalStateException e) {
previewError = true;
e.printStackTrace();
} catch (IOException e) {
previewError = true;
e.printStackTrace();
} finally {
sPlayer = null;
if (player != null)
player.release();
// Delete the target file.
if (downloader != null) {
downloader.stop();
Utils.D("+++ Downloader stopped");
if (downloader.getFile() == null)
return;
String targetFile = downloader.getFile().getName();
if (targetFile == null)
return;
File file = new File(SharingSettings.INCOMPLETE_DIRECTORY, targetFile);
if (file.exists()) {
file.delete();
}
downloader = null;
}
runOnUiThread(new Runnable() {
@Override
public void run() {
if (mStreaming != null) {
mStreaming.dismiss();
}
}
});
if (previewError) {
runOnUiThread(new Runnable() {
@Override
public void run() {
Toast.makeText(getApplication(),
"Something was wrong", Toast.LENGTH_LONG).show();
}
});
}
sPreviewThread = null;
}
}
});
sPreviewThread.start();
} else if (mp3 instanceof SogouSearchResult) {
final SogouSearchResult sogouMp3 = (SogouSearchResult)mp3;
if (sogouMp3.getDownloadUrl() != null && sogouMp3.getDownloadUrl().startsWith("http:")) {
sPreviewThread = new Thread(new Runnable() {
@Override
public void run() {
try {
MediaPlayer player = sPlayer;
if (player != null) {
player.release();
}
sPlayer = new MediaPlayer();
player = sPlayer;
player.reset();
player.setDataSource(sogouMp3.getDownloadUrl());
player.prepare();
player.start();
player.setOnCompletionListener(new OnCompletionListener () {
@Override
public void onCompletion(MediaPlayer mp) {
sPlayer = null;
runOnUiThread(new Runnable() {
@Override
public void run() {
if (mStreaming != null) {
mStreaming.dismiss();
}
}
});
}
});
player.setOnErrorListener(new OnErrorListener() {
@Override
public boolean onError(MediaPlayer mp, int what, int extra) {
onPlayError();
return true;
}
});
if (sPlayer == null) {
// Someone requested us to stop.
player.release();
}
} catch (IllegalArgumentException e) {
onPlayError();
e.printStackTrace();
} catch (IllegalStateException e) {
//onPlayError();
e.printStackTrace();
} catch (IOException e) {
onPlayError();
e.printStackTrace();
} finally {
sPreviewThread = null;
}
}
});
sPreviewThread.start();
}
}
}
private void onPlayError() {
MediaPlayer player = sPlayer;
sPlayer = null;
if (player != null)
player.release();
runOnUiThread(new Runnable() {
@Override
public void run() {
if (mStreaming != null) {
mStreaming.dismiss();
}
Toast.makeText(getApplication(), "Streaming error", Toast.LENGTH_LONG).show();
}
});
}
@Override
protected Dialog onCreateDialog(int id) {
Utils.D("onCreateDialog() " + id);
switch (id) {
case DIALOG_WAITING_FOR_SERVER: {
if (mProgressDialog == null) {
mProgressDialog = new ProgressDialog(this);
mProgressDialog.setMessage(getString(R.string.wait));
mProgressDialog.setIndeterminate(true);
mProgressDialog.setCancelable(true);
}
return mProgressDialog;
}
case DIALOG_MUSIC_OPTIONS:
return new AlertDialog.Builder(SearchResultActivity.this)
.setItems(R.array.music_item_options, new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
switch(which) {
case MUSIC_OPTION_DOWNLOAD:
if (mCurrentResult == null)
return;
download(mCurrentResult);
break;
case MUSIC_OPTION_PREVIEW:
if (mCurrentResult == null)
return;
if (mCurrentResult instanceof SogouSearchResult) {
SogouSearchResult sogouResult = (SogouSearchResult)mCurrentResult;
mHandler.post(new Runnable() {
@Override
public void run() {
showDialog(DIALOG_MUSIC_STREAMING);
}
});
if (sogouResult.getDownloadUrl() == null) {
new FetchMp3LinkTaskForPreview().execute(sogouResult);
break;
}
} else {
mHandler.post(new Runnable() {
@Override
public void run() {
showDialog(DIALOG_MUSIC_STREAMING);
}
});
preview(mCurrentResult);
break;
}
}
}
})
.create();
case DIALOG_MUSIC_STREAMING:
if (mStreaming == null) {
mStreaming = new ProgressDialog(SearchResultActivity.this);
mStreaming.setTitle("Streaming music...");
mStreaming.setMessage(getString(R.string.wait));
mStreaming.setIndeterminate(true);
mStreaming.setCancelable(false);
mStreaming.setButton(getString(R.string.stop), new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
if (mStreaming != null) {
mStreaming.dismiss();
mStreaming = null;
}
MediaPlayer player = sPlayer;
sPlayer = null;
if (player != null) {
player.release();
}
if (sPreviewThread != null) {
sPreviewThread.interrupt();
sPreviewThread = null;
}
}
});
}
return mStreaming;
}
return null;
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.search_result_menu, menu);
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.dowloads:
Intent intent = new Intent(SearchResultActivity.this, DownloadActivity.class);
startActivity(intent);
return true;
}
return false;
}
private void startQuery(Intent intent) {
mQuery = mSearch.getQuery();
mAdapter.setStatus(ListStatusView.Status.SEARCHING);
mAdapter.notifyDataSetChanged();
if (TextUtils.isEmpty(mQuery)) {
mQuery = StringUtils.removeIllegalChars(intent.getStringExtra(Constants.QUERY));
}
mSearchAdapter = new SearchAdapter(null);
sWaitForRouterServiceTask = new WaitForRouterServiceTask(intent, mQuery);
sWaitForRouterServiceTask.execute();
if (!TextUtils.isEmpty(mQuery)) {
sSogouMusicSearcher.setQuery(mQuery);
sFetchMp3ListTask = new FetchMp3ListTask(getApplication());
sFetchMp3ListTask.execute();
}
}
@Override
protected void onNewIntent(Intent intent) {
Utils.D("onNewIntent");
startQuery(intent);
}
public void dismissStreamingDialog() {
if (mStreaming != null && mStreaming.isShowing()) {
mStreaming.dismiss();
}
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Utils.D("onCreate");
sSearchResultActivity = this;
bindService(new Intent(this, DownloadService.class),
mConnection, Context.BIND_AUTO_CREATE);
setContentView(R.layout.result_list);
Utils.addMixedAds(this);
mListView = (ListView)findViewById(R.id.result_list);
mAdapter = new Mp3ListAdapter(
SearchResultActivity.this,
R.layout.result_item);
mListView.setAdapter(mAdapter);
mListView.setOnItemClickListener(new OnItemClickListener() {
public void onItemClick(AdapterView<?> parent, View v, int position, long id) {
if (mSearchAdapter != null && position < mSearchAdapter.displaySize()) {
mCurrentResult = mSearchAdapter.get(position);
showDialog(DIALOG_MUSIC_OPTIONS);
}
}
});
mQuery = getIntent().getStringExtra(Constants.QUERY);
mSearch = new SearchBar(this, mQuery);
mListener = new RouterServiceListener();
App.init(getApplication());
App.getRouterService(mListener);
mHandler.post(new Runnable() {
@Override
public void run() {
startQuery(getIntent());
}
});
}
@Override
protected void onResume() {
super.onResume();
//Debug.stopMethodTracing();
}
@Override
protected void onDestroy() {
super.onDestroy();
stopQuery();
unbindService(mConnection);
sSearchResultActivity = null;
}
private void stopQuery() {
if (mGuid != null) {
RouterService.stopQuery(new GUID(mGuid));
mGuid = null;
}
}
private class RouterServiceListener implements ActivityCallback {
public RouterServiceListener() {}
@Override
public void acceptChat(Chatter ctr) {
}
@Override
public void addDownload(Downloader d) {
}
@Override
public void addressStateChanged() {
}
@Override
public void browseHostFailed(GUID guid) {
}
@Override
public void chatErrorMessage(Chatter chatter, String str) {
// TODO Auto-generated method stub
}
@Override
public void chatUnavailable(Chatter chatter) {
// TODO Auto-generated method stub
}
@Override
public void componentLoading(String component) {
// TODO Auto-generated method stub
}
@Override
public void connectionClosed(Connection c) {
// TODO Auto-generated method stub
}
@Override
public void connectionInitialized(Connection c) {
// TODO Auto-generated method stub
}
@Override
public void connectionInitializing(Connection c) {
// TODO Auto-generated method stub
}
@Override
public void downloadsComplete() {
// TODO Auto-generated method stub
}
@Override
public String getHostValue(String key) {
// TODO Auto-generated method stub
return null;
}
@Override
public User getUserAuthenticationInfo(String host) {
// TODO Auto-generated method stub
return null;
}
@Override
public void retryQueryAfterConnect() {
stopQuery();
/*
(new Thread(new Runnable () {
@Override
public void run() {
try {
while (!RouterService.isConnected()) {
Thread.sleep(300);
}
} catch (InterruptedException e) {
e.printStackTrace();
}
SearchResultActivity.this.runOnUiThread(new Runnable() {
@Override
public void run() {
startQuery(getIntent());
}
});
}
})).start();
*/
try {
while (!RouterService.isConnected()) {
Thread.sleep(300);
}
} catch (InterruptedException e) {
e.printStackTrace();
}
//SearchResultActivity.this.runOnUiThread(new Runnable() {
mHandler.post(new Runnable() {
@Override
public void run() {
startQuery(getIntent());
}
});
}
@Override
public synchronized void handleQueryResult(
final RemoteFileDesc rfd, final HostData data, final Set<Endpoint> locs) {
if (mGuid == null)
return;
if (data == null || rfd == null) {
return;
}
final byte[] replyGuid = data.getMessageGUID();
mHandler.post(new Runnable() {
@Override
public void run() {
//if (!mSearchAdapter.sameGuid(replyGuid) && mSearchAdapter.size() > 3) {
if (!mSearchAdapter.sameGuid(replyGuid)) {
return;
}
/*
if (mShowNoResult != null) {
mHandler.removeCallbacks(mShowNoResult);
mShowNoResult = null;
}
*/
boolean shouldRefresh = mSearchAdapter.add(rfd, data, locs);
int oldDisplaySize = mSearchAdapter.displaySize();
//Utils.D("shouldRefresh: " + shouldRefresh);
if (shouldRefresh) {
if (mSearchAdapter.isBatchFull()) {
mAdapter.setStatus(ListStatusView.Status.LOAD_MORE);
} else {
mAdapter.setStatus(ListStatusView.Status.SEARCHING);
}
mAdapter.notifyDataSetChanged();
} else {
if (mSearchAdapter.displaySize() != oldDisplaySize) {
throw new IllegalStateException("display size does not match: " + mSearchAdapter.displaySize() + " vs " + oldDisplaySize);
}
}
//mAdapter.notifyDataSetChanged();
}
});
if (Utils.DEBUG) {
synchronized(System.out) {
Utils.D("Query hit from " + rfd.getHost() + ":" + rfd.getPort() + ":");
Utils.D("filename: " + rfd.getFileName());
//Utils.D("filesize: " + rfd.getSize());
//Utils.D("speed: " + rfd.getSpeed());
//Utils.D("Quality: " + rfd.getQuality());
//Utils.D("Wait time: " + rfd.getWaitTime());
}
}
}
@Override
public void handleQueryString(String query) {
// TODO Auto-generated method stub
}
@Override
public boolean isQueryAlive(GUID guid) {
// TODO Auto-generated method stub
return false;
}
@Override
public void promptAboutCorruptDownload(Downloader dloader) {
// TODO Auto-generated method stub
}
@Override
public void receiveMessage(Chatter chr) {
// TODO Auto-generated method stub
}
@Override
public void removeDownload(Downloader d) {
// TODO Auto-generated method stub
}
@Override
public void restoreApplication() {
// TODO Auto-generated method stub
}
@Override
public void setAnnotateEnabled(boolean enabled) {
// TODO Auto-generated method stub
}
@Override
public void showDownloads() {
// TODO Auto-generated method stub
}
}
private final class Mp3ListAdapter extends BaseAdapter {
private final static int VIEW_TYPE_NORMAL = 0;
private final static int VIEW_TYPE_FOOTER = 1;
private int mResource;
private LayoutInflater mInflater;
private ListStatusView.Status mStatus;
public Mp3ListAdapter(Context context, int resource) {
mResource = resource;
mInflater = (LayoutInflater)context.getSystemService(
Context.LAYOUT_INFLATER_SERVICE);
mStatus = ListStatusView.Status.OFFLINE;
}
public void setStatus(ListStatusView.Status status) {
mStatus = status;
}
@Override
public int getCount() {
boolean showFooter =
mStatus == ListStatusView.Status.LOAD_MORE ||
mStatus == ListStatusView.Status.SEARCHING ||
mStatus == ListStatusView.Status.NO_RESULT;
int footerCount = showFooter ? 1 : 0;
int count = 0;
if (mSearchAdapter == null)
count = footerCount;
else
count = mSearchAdapter.displaySize() + footerCount;
//Utils.D("getCount: " + count);
return count;
}
@Override
public Object getItem(int position) {
if (mSearchAdapter == null)
return null;
if (position < mSearchAdapter.displaySize())
return mSearchAdapter.get(position);
return null; // footer.
}
@Override
public long getItemId(int position) {
if (mSearchAdapter == null)
return -1;
if (position < mSearchAdapter.displaySize())
return position;
return -1; // footer.
}
@Override
public int getViewTypeCount() {
return 2;
}
@Override
public int getItemViewType(int position) {
if (mSearchAdapter == null || position == mSearchAdapter.displaySize())
return VIEW_TYPE_FOOTER;
return VIEW_TYPE_NORMAL;
}
OnClickListener mLoadMoreListener = new OnClickListener() {
@Override
public void onClick(View v) {
if (mStatus == ListStatusView.Status.LOAD_MORE) {
mSearchAdapter.nextBatch();
if (mSearchAdapter.isBatchFull()) {
// If the next page has enough results (full), we
// are ok, waiting for user to load more.
mAdapter.setStatus(ListStatusView.Status.LOAD_MORE);
} else {
// Otherwise we don't have enough result.
mAdapter.setStatus(ListStatusView.Status.SEARCHING);
sFetchMp3ListTask = new FetchMp3ListTask(getApplication());
sFetchMp3ListTask.execute();
}
notifyDataSetChanged();
}
}
};
@Override
public View getView(int position, View convertView, ViewGroup parent) {
boolean isFooter = (mSearchAdapter == null || position == mSearchAdapter.displaySize());
if (isFooter) {
ListStatusView footerView = (ListStatusView) convertView;
if (footerView == null) {
footerView = (ListStatusView) mInflater.inflate(
R.layout.liststatus, null);
}
if (mStatus == ListStatusView.Status.LOAD_MORE) {
footerView.setStatusLoadMore();
footerView.setOnClickListener(mLoadMoreListener);
} else if (mStatus == ListStatusView.Status.SEARCHING) {
footerView.setStatusSearching();
footerView.setOnClickListener(null);
} else if (mStatus == ListStatusView.Status.NO_RESULT) {
footerView.setStatusNoResult();
footerView.setOnClickListener(null);
}
return footerView;
}
View v;
Object item = mSearchAdapter.get(position);
if (convertView == null) {
v = mInflater.inflate(mResource, parent, false);
} else {
v = convertView;
}
SearchResult rs = (SearchResult)item;
((TextView)v.findViewById(R.id.name)).setText(rs.getFileName());
((TextView)v.findViewById(R.id.size)).setText(Utils.displaySizeInMB(rs.getFileSize()));
//Utils.D(rs.getFileName() + " : " + rs.getSize());
return v;
}
}
private class WaitForRouterServiceTask extends AsyncTask<Void, Void, Integer> {
Intent mIntent;
String mQuery;
public WaitForRouterServiceTask(Intent intent, String query) {
mIntent = intent;
mQuery = query;
}
@Override
protected void onPostExecute(Integer result) {
if (sWaitForRouterServiceTask != this) {
return;
}
sWaitForRouterServiceTask = null;
String xml = mIntent == null ? null : mIntent.getStringExtra(Constants.XML);
if (xml == null)
xml = "";
if (!TextUtils.isEmpty(mQuery) ||
!TextUtils.isEmpty(xml)) {
stopQuery();
mAdapter.notifyDataSetChanged();
mGuid = RouterService.newQueryGUID();
mSearchAdapter.setGuid(mGuid);
RouterService.query(mGuid, mQuery, xml, MediaType.TYPE_MP3);
}
}
@Override
protected Integer doInBackground(Void... params) {
try {
while (!RouterService.isConnected()) {
Utils.D("RouterService not ready");
Thread.sleep(500);
}
} catch (InterruptedException e) {
e.printStackTrace();
}
return 0;
}
}
private static class FetchMp3ListTask extends AsyncTask<Void, Void, ArrayList<SogouSearchResult>> {
Context mContext;
public FetchMp3ListTask(Context context) {
super();
mContext = context;
}
@Override
protected void onPostExecute(ArrayList<SogouSearchResult> mp3List) {
if (sFetchMp3ListTask != this) {
// Another query is going on.
return;
}
sFetchMp3ListTask = null;
if (sSearchResultActivity != null) {
sSearchResultActivity.handleSogouSearchResult(mp3List);
}
}
@Override
protected ArrayList<SogouSearchResult> doInBackground(Void... params) {
return sSogouMusicSearcher.getNextResultList(mContext);
}
}
private void handleSogouSearchResult(ArrayList<SogouSearchResult> mp3List) {
ArrayList<SogouSearchResult> newList = Utils.dedup(mp3List);
if (newList != null && mSearchAdapter != null) {
for (Iterator<SogouSearchResult> it = newList.iterator(); it.hasNext();) {
SogouSearchResult result = it.next();
boolean shouldRefresh = mSearchAdapter.add(result);
int oldDisplaySize = mSearchAdapter.displaySize();
if (shouldRefresh) {
if (mSearchAdapter.isBatchFull()) {
mAdapter.setStatus(ListStatusView.Status.LOAD_MORE);
} else {
mAdapter.setStatus(ListStatusView.Status.SEARCHING);
}
mAdapter.notifyDataSetChanged();
} else {
if (mSearchAdapter.displaySize() != oldDisplaySize) {
throw new IllegalStateException("display size does not match: " + mSearchAdapter.displaySize() + " vs " + oldDisplaySize);
}
}
}
}
}
private class FetchMp3LinkTaskForPreview extends AsyncTask<SogouSearchResult, Void, SogouSearchResult> {
protected SogouSearchResult doInBackground(SogouSearchResult... mp3s) {
SogouSearchResult mp3 = mp3s[0];
SogouMusicSearcher.setMusicDownloadUrl(getApplication(), mp3);
return mp3;
}
protected void onPostExecute(SogouSearchResult mp3) {
if (mp3.getDownloadUrl() == null) {
if (mStreaming != null) {
mStreaming.dismiss();
}
Toast.makeText(SearchResultActivity.this, R.string.no_download_link, Toast.LENGTH_SHORT).show();
return;
}
preview(mp3);
}
}
public static void handleMp3ListIntent(Context context, String key, String keyWords) {
Intent intent = new Intent(context, SearchResultActivity.class);
intent.putExtra(key, keyWords);
context.startActivity(intent);
}
public static void handleMp3ListSimpleIntent(Context context, String keyWords) {
Intent intent = new Intent(context, SearchResultActivity.class);
intent.putExtra(Constants.QUERY, keyWords);
context.startActivity(intent);
}
public static void handleMp3ListXMLIntent(Context context, String keyWords, String xml) {
Intent intent = new Intent(context, SearchResultActivity.class);
intent.putExtra(Constants.QUERY, keyWords);
intent.putExtra(Constants.XML, xml);
context.startActivity(intent);
}
}