Commit 62998c352e0900657aeefc111a712403f009e711

  • avatar
  • Kevin James Purdy <pountaar @mo…a.sandbenders.org>
  • Wed Sep 09 03:32:23 CEST 2009
Implemented search functionality.  Partial implementation of auto pause on calls.
  
11<?xml version="1.0" encoding="utf-8"?>
22<manifest xmlns:android="http://schemas.android.com/apk/res/android"
3 package="com.sound.ampache"
4 android:versionCode="1"
5 android:versionName="0.8.5" >
6 <uses-sdk android:minSdkVersion="1" />
7 <uses-permission android:name="android.permission.INTERNET" />
8 <application android:label="@string/app_name"
9 android:name="amdroid"
10 android:icon="@drawable/amdroid_logo">
11 <activity android:name="dashActivity" >
12 <intent-filter>
13 <action android:name="android.intent.action.MAIN" />
14 <category android:name="android.intent.category.LAUNCHER" />
15 </intent-filter>
16 </activity>
17 <activity android:name="collectionActivity">
18 <intent-filter>
19 <action android:name="android.intent.action.VIEW" />
20 </intent-filter>
21 </activity>
22 <activity android:name="prefsActivity"
23 android:label="@string/prefs_name">
24 <intent-filter>
25 <action android:name="android.intent.action.VIEW" />
26 <category android:name="andriod.intent.category.PREFERENCE" />
27 </intent-filter>
28 </activity>
29 <activity android:name="playlistActivity"
30 android:label="@string/play_name">
31 <intent-filter>
32 <action android:name="android.intent.action.VIEW" />
33 </intent-filter>
34 </activity>
35 </application>
3 package="com.sound.ampache"
4 android:versionCode="2"
5 android:versionName="0.9.0" >
6 <uses-sdk android:minSdkVersion="1" />
7 <uses-permission android:name="android.permission.INTERNET" />
8 <uses-permission android:name="android.permission.READ_PHONE_STATE"/>
9 <application android:label="@string/app_name"
10 android:name="amdroid"
11 android:icon="@drawable/amdroid_logo">
12 <!-- Dashboard -->
13 <activity android:name="dashActivity" >
14 <intent-filter>
15 <action android:name="android.intent.action.MAIN" />
16 <category android:name="android.intent.category.LAUNCHER" />
17 </intent-filter>
18 <meta-data android:name="android.app.default_searchable" android:value=".songSearch" />
19 </activity>
20 <!-- Collection Browser -->
21 <activity android:name="collectionActivity">
22 <intent-filter>
23 <action android:name="android.intent.action.VIEW" />
24 </intent-filter>
25 <meta-data android:name="android.app.default_searchable" android:value=".songSearch" />
26 </activity>
27 <!-- Preferences -->
28 <activity android:name="prefsActivity"
29 android:label="@string/prefs_name">
30 <intent-filter>
31 <action android:name="android.intent.action.VIEW" />
32 <category android:name="andriod.intent.category.PREFERENCE" />
33 </intent-filter>
34 </activity>
35 <!-- Playlist Activity -->
36 <activity android:name="playlistActivity"
37 android:label="@string/play_name">
38 <intent-filter>
39 <action android:name="android.intent.action.VIEW" />
40 </intent-filter>
41 </activity>
42 <!-- Search Activity -->
43 <activity android:name="songSearch"
44 android:launchMode="singleTop">
45 <intent-filter>
46 <action android:name="android.intent.action.SEARCH" />
47 <category android:name="android.intent.category.DEFAULT" />
48 </intent-filter>
49 <meta-data android:name="android.app.searchable"
50 android:resource="@xml/searchable" />
51 </activity>
52 </application>
3653</manifest>
  
1313 <string name="title_password_preference">Ampache Password</string>
1414 <string name="summary_password_preference"></string>
1515 <string name="dialog_password_preference">password</string>
16 <string name="search_label">Songs</string>
1617</resources>
  
1<?xml version="1.0" encoding="utf-8"?>
2<searchable xmlns:android="http://schemas.android.com/apk/res/android"
3 android:label="@string/search_label" />
  
3030import android.os.Debug;
3131import android.os.Bundle;
3232import android.media.MediaPlayer;
33import android.telephony.PhoneStateListener;
34import android.telephony.TelephonyManager;
35import android.media.AudioManager;
36import android.content.Context;
3337
3438public final class amdroid extends Application {
3539
4747 public static Boolean playListVisible;
4848 public static Boolean confChanged;
4949 protected static Bundle cache;
50 private static Boolean mResumeAfterCall;
5051
52 //Handle phone calls
53 private PhoneStateListener mPhoneStateListener = new PhoneStateListener() {
54 @Override
55 public void onCallStateChanged(int state, String incomingNumber) {
56 if (state == TelephonyManager.CALL_STATE_RINGING) {
57 AudioManager audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
58 int ringvolume = audioManager.getStreamVolume(AudioManager.STREAM_RING);
59 if (ringvolume > 0) {
60 mResumeAfterCall = (mp.isPlaying() || mResumeAfterCall);
61 mp.pause();
62 }
63 } else if (state == TelephonyManager.CALL_STATE_OFFHOOK) {
64 // pause the music while a conversation is in progress
65 mResumeAfterCall = (mp.isPlaying() || mResumeAfterCall);
66 mp.pause();
67 } else if (state == TelephonyManager.CALL_STATE_IDLE) {
68 // start playing again
69 if (mResumeAfterCall) {
70 // resume playback only if music was playing
71 // when the call was answered
72 mp.start();
73 mResumeAfterCall = false;
74 }
75 }
76 }
77 };
78
5179 public void onCreate() {
5280 //Debug.waitForDebugger();
5381 PreferenceManager.setDefaultValues(this, R.xml.preferences, false);
8686 bufferPC = 0;
8787
8888 cache = new Bundle();
89
90 //Make sure we check for phone calls
91 //TelephonyManager tmgr = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
92 //tmgr.listen(mPhoneStateListener, PhoneStateListener.LISTEN_CALL_STATE);
8993
9094 try {
9195 comm = new ampacheCommunicator(prefs, this);
101101 }
102102 playlistCurrent = new ArrayList();
103103 }
104
105104}
  
175175 hand = new ampachePlaylistParser();
176176 } else if (directive[0].equals("songs")) {
177177 hand = new ampacheSongParser();
178 } else if (directive[0].equals("tags")) {
179 hand = new ampacheTagParser();
180 } else if (directive[0].equals("search_songs")) {
181 hand = new ampacheSongParser();
182 append += "&filter=tool";
178 } else if (directive[0].equals("tags")) {
179 hand = new ampacheTagParser();
180 } else if (directive[0].equals("search_songs")) {
181 hand = new ampacheSongParser();
182 append += "&filter=" + directive[1];
183183 } else {
184184 return; // new ArrayList();
185185 }
  
1package com.sound.ampache;
2
3/* Copyright (c) 2008-2009 Kevin James Purdy <purdyk@gmail.com>
4 *
5 * +------------------------------------------------------------------------+
6 * | This program is free software; you can redistribute it and/or |
7 * | modify it under the terms of the GNU General Public License |
8 * | as published by the Free Software Foundation; either version 2 |
9 * | of the License, or (at your option) any later version. |
10 * | |
11 * | This program is distributed in the hope that it will be useful, |
12 * | but WITHOUT ANY WARRANTY; without even the implied warranty of |
13 * | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 * | GNU General Public License for more details. |
15 * | |
16 * | You should have received a copy of the GNU General Public License |
17 * | along with this program; if not, write to the Free Software |
18 * | Foundation, Inc., 59 Temple Place - Suite 330, |
19 * | Boston, MA 02111-1307, USA. |
20 * +------------------------------------------------------------------------+
21 */
22
23import android.widget.TextView;
24
25public final class bI {
26 TextView title;
27 TextView other;
28}
  
275275 case (0x1338):
276276 /* handle an error */
277277 setProgressBarIndeterminateVisibility(false);
278 Toast.makeText(collectionActivity.this, "Error:" + (String) msg.obj, Toast.LENGTH_LONG).show();
278 Toast.makeText(collectionActivity.this, "Communicator error:" + (String) msg.obj, Toast.LENGTH_LONG).show();
279279 isFetching = false;
280280 break;
281281 case (0x1339):
284284 break;
285285 }
286286 }
287 }
288
289 private class collectionAdapter extends ArrayAdapter
290 {
291
292 private Context mCtx;
293 private int resid;
294 private LayoutInflater mInflater;
295
296 public collectionAdapter(Context context, int resid, ArrayList list) {
297 super(context, resid, list);
298 this.resid = resid;
299 mCtx = context;
300 mInflater = LayoutInflater.from(context);
301 }
302
303 public View getView(int position, View convertView, ViewGroup parent) {
304 bI holder;
305 ampacheObject cur = (ampacheObject) getItem(position);
306
307 /* we don't reuse */
308 if (convertView == null) {
309 convertView = mInflater.inflate(resid, null);
310 holder = new bI();
311
312 holder.title = (TextView) convertView.findViewById(R.id.title);
313 holder.other = (TextView) convertView.findViewById(R.id.other);
314
315 convertView.setTag(holder);
316 } else {
317 holder = (bI) convertView.getTag();
318 }
319
320 if (cur != null) {
321 holder.title.setText(cur.toString());
322 holder.other.setText(cur.extraString());
323 }
324 return convertView;
325 }
326 }
327
328 static class bI {
329 TextView title;
330 TextView other;
331287 }
332288}
  
1package com.sound.ampache;
2
3/* Copyright (c) 2008-2009 Kevin James Purdy <purdyk@gmail.com>
4 *
5 * +------------------------------------------------------------------------+
6 * | This program is free software; you can redistribute it and/or |
7 * | modify it under the terms of the GNU General Public License |
8 * | as published by the Free Software Foundation; either version 2 |
9 * | of the License, or (at your option) any later version. |
10 * | |
11 * | This program is distributed in the hope that it will be useful, |
12 * | but WITHOUT ANY WARRANTY; without even the implied warranty of |
13 * | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 * | GNU General Public License for more details. |
15 * | |
16 * | You should have received a copy of the GNU General Public License |
17 * | along with this program; if not, write to the Free Software |
18 * | Foundation, Inc., 59 Temple Place - Suite 330, |
19 * | Boston, MA 02111-1307, USA. |
20 * +------------------------------------------------------------------------+
21 */
22
23import android.content.Context;
24import android.content.Intent;
25import android.view.LayoutInflater;
26import android.view.View;
27import android.view.ViewGroup;
28import android.widget.ArrayAdapter;
29import android.widget.TextView;
30import com.sound.ampache.objects.*;
31import android.os.Bundle;
32import java.util.ArrayList;
33
34public final class collectionAdapter extends ArrayAdapter
35{
36
37 private Context mCtx;
38 private int resid;
39 private LayoutInflater mInflater;
40
41 public collectionAdapter(Context context, int resid, ArrayList list) {
42 super(context, resid, list);
43 this.resid = resid;
44 mCtx = context;
45 mInflater = LayoutInflater.from(context);
46 }
47
48 public View getView(int position, View convertView, ViewGroup parent) {
49 bI holder;
50 ampacheObject cur = (ampacheObject) getItem(position);
51
52 /* we don't reuse */
53 if (convertView == null) {
54 convertView = mInflater.inflate(resid, null);
55 holder = new bI();
56
57 holder.title = (TextView) convertView.findViewById(R.id.title);
58 holder.other = (TextView) convertView.findViewById(R.id.other);
59
60 convertView.setTag(holder);
61 } else {
62 holder = (bI) convertView.getTag();
63 }
64
65 if (cur != null) {
66 holder.title.setText(cur.toString());
67 holder.other.setText(cur.extraString());
68 }
69 return convertView;
70 }
71}
  
2222
2323import com.sound.ampache.R;
2424import android.app.Activity;
25import android.app.SearchManager;
2526import android.os.Bundle;
2627import android.widget.Button;
2728import android.widget.Toast;
4040 protected void onCreate(Bundle savedInstanceState) {
4141 super.onCreate(savedInstanceState);
4242
43 setContentView(R.layout.dash);
43 //setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
44 setContentView(R.layout.dash);
4445
4546 /* We need a listener for all of the buttons */
4647 Button temp;
7272
7373 @Override
7474 public boolean onCreateOptionsMenu(Menu menu) {
75 super.onCreateOptionsMenu(menu);
76 menu.add(0, SETTINGS, 0, "Settings").setIcon(android.R.drawable.ic_menu_preferences);
77 menu.add(0, SEARCH_MUSIC, 0, "Search Music").setIcon(android.R.drawable.ic_menu_search);
78 return true;
75 super.onCreateOptionsMenu(menu);
76 menu.add(0, SETTINGS, 0, "Settings").setIcon(android.R.drawable.ic_menu_preferences);
77 menu.add(0, SEARCH_MUSIC, 0, "Search Music").setIcon(android.R.drawable.ic_menu_search);
78 return true;
7979 }
80
80
8181 public void onClick(View v) {
8282 Intent intent = null;
8383 String[] dir = new String[2];
103103 dir[0] = "playlists";
104104 intent = new Intent().setClass(this, collectionActivity.class).putExtra("directive", dir).putExtra("title", "Playlists");
105105 break;
106
106
107107 case (R.id.nowplaying):
108108 intent = new Intent().setClass(this, playlistActivity.class);
109109 break;
110110
111111 default:
112 return;
112 return;
113113 }
114114 startActivity(intent);
115115 }
116116
117117 @Override
118118 public boolean onOptionsItemSelected(MenuItem item) {
119 Intent intent = null;
120 try {
121 switch (item.getItemId()) {
122 case SETTINGS:
123 intent = new Intent().setClass(this, prefsActivity.class);
124 break;
125
126 case SEARCH_MUSIC:
127 intent = new Intent().setClass(this, playlistActivity.class);
128 break;
129
130 default:
131 return false;
132 }
133 } catch (Exception poo) {
134 }
135 startActivity(intent);
136 return true;
119 Intent intent = null;
120 switch (item.getItemId()) {
121 case SETTINGS:
122 intent = new Intent().setClass(this, prefsActivity.class);
123 break;
124
125 case SEARCH_MUSIC:
126 onSearchRequested();
127 break;
128
129 default:
130 return false;
131 }
132 if (intent != null) {
133 startActivity(intent);
134 return true;
135 }
136 return false;
137137 }
138
139138}
  
1package com.sound.ampache;
2
3/* Copyright (c) 2008-2009 Kevin James Purdy <purdyk@gmail.com>
4 *
5 * +------------------------------------------------------------------------+
6 * | This program is free software; you can redistribute it and/or |
7 * | modify it under the terms of the GNU General Public License |
8 * | as published by the Free Software Foundation; either version 2 |
9 * | of the License, or (at your option) any later version. |
10 * | |
11 * | This program is distributed in the hope that it will be useful, |
12 * | but WITHOUT ANY WARRANTY; without even the implied warranty of |
13 * | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
14 * | GNU General Public License for more details. |
15 * | |
16 * | You should have received a copy of the GNU General Public License |
17 * | along with this program; if not, write to the Free Software |
18 * | Foundation, Inc., 59 Temple Place - Suite 330, |
19 * | Boston, MA 02111-1307, USA. |
20 * +------------------------------------------------------------------------+
21 */
22
23import android.app.ListActivity;
24import android.app.ProgressDialog;
25import android.app.SearchManager;
26import android.content.Intent;
27import android.view.Menu;
28import android.view.MenuItem;
29import android.view.View;
30import android.view.Window;
31import android.os.Bundle;
32import android.os.Handler;
33import android.os.Message;
34import android.os.Messenger;
35import android.widget.Toast;
36import android.widget.ListView;
37import com.sound.ampache.objects.*;
38import java.util.ArrayList;
39
40public final class songSearch extends ListActivity {
41
42 public searchHandler searchCompleteHandler;
43 private String[] directive;
44 private ArrayList<ampacheObject> list = null;
45 private ProgressDialog dlog;
46
47 protected void onCreate(Bundle savedInstanceState)
48 {
49 super.onCreate(savedInstanceState);
50
51 requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
52 amdroid.comm.ping();
53
54 final Intent queryIntent = getIntent();
55 final String queryAction = queryIntent.getAction();
56
57 setTitle("Music Search");
58
59 searchCompleteHandler = new searchHandler();
60
61 if (Intent.ACTION_SEARCH.equals(queryAction)) {
62 directive = new String[2];
63 directive[0] = "search_songs";
64 directive[1] = queryIntent.getStringExtra(SearchManager.QUERY);
65
66 Message searchMsg = new Message();
67 searchMsg.arg1 = 0;
68 searchMsg.what = 0x1337;
69 searchMsg.obj = directive;
70
71 dlog = ProgressDialog.show(this, "", "Searching...", true);
72
73 searchMsg.replyTo = new Messenger(searchCompleteHandler);
74 list = new ArrayList();
75 searchCompleteHandler.ca = new collectionAdapter(this, R.layout.browsable_item, list);
76
77 setListAdapter(searchCompleteHandler.ca);
78 amdroid.requestHandler.incomingRequestHandler.sendMessage(searchMsg);
79 }
80 }
81
82 @Override
83 public boolean onCreateOptionsMenu(Menu menu) {
84 super.onCreateOptionsMenu(menu);
85 menu.add(0, 0, 0, "Add All").setIcon(android.R.drawable.ic_menu_add);
86 return true;
87 }
88
89 @Override
90 public boolean onOptionsItemSelected(MenuItem item) {
91 switch (item.getItemId()) {
92 case 0:
93 amdroid.playlistCurrent.addAll((ArrayList)list);
94 break;
95
96 default:
97 return false;
98 }
99 return true;
100 }
101
102
103 protected void onListItemClick(ListView l, View v, int position, long id) {
104 ampacheObject val = (ampacheObject) l.getItemAtPosition(position);
105 Toast.makeText(this, "Enqueue " + val.getType() + ": " + val.toString(), Toast.LENGTH_LONG).show();
106 amdroid.playlistCurrent.add((Song) val);
107 return;
108 }
109
110 private class searchHandler extends Handler {
111 public collectionAdapter ca;
112
113 public void handleMessage(Message msg) {
114 switch(msg.what) {
115 case (0x1337):
116 list.addAll((ArrayList) msg.obj);
117 dlog.dismiss();
118 ca.notifyDataSetChanged();
119 break;
120 }
121 }
122
123 }
124}