diff --git a/src/screen_search.c b/src/screen_search.c
index 3829f8dfa1bcbbd3d037265db62906c4058cd6f7..3abda9d9c574e116c5e417043f100f866250a1ef 100644 (file)
--- a/src/screen_search.c
+++ b/src/screen_search.c
/* ncmpc (Ncurses MPD Client)
- * (c) 2004-2009 The Music Player Daemon Project
+ * (c) 2004-2010 The Music Player Daemon Project
* Project homepage: http://musicpd.org
-
+ *
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
-
+ *
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
-
+ *
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
-*/
+ */
#include "screen_search.h"
#include "screen_interface.h"
-#include "screen_message.h"
+#include "screen_status.h"
#include "screen.h"
#include "i18n.h"
#include "options.h"
enum {
SEARCH_URI = MPD_TAG_COUNT + 100,
+ SEARCH_ARTIST_TITLE
};
static const struct {
return -1;
}
-#define SEARCH_ARTIST_TITLE 999
-
typedef struct {
enum mpd_tag_type table;
const char *label;
{ MPD_TAG_TITLE, N_("Title") },
{ MPD_TAG_ARTIST, N_("Artist") },
{ MPD_TAG_ALBUM, N_("Album") },
- { SEARCH_URI, N_("file") },
+ { SEARCH_URI, N_("Filename") },
{ SEARCH_ARTIST_TITLE, N_("Artist + Title") },
{ 0, NULL }
};
static struct screen_browser browser;
+static const char *const help_text[] = {
+ "Quick - Enter a string and ncmpc will search according",
+ " to the current search mode (displayed above).",
+ "",
+ "Advanced - <tag>:<search term> [<tag>:<search term>...]",
+ " Example: artist:radiohead album:pablo honey",
+ "",
+ " Available tags: artist, album, title, track,",
+ " name, genre, date composer, performer, comment, file",
+ "",
+};
/* search info */
static const char *
-lw_search_help_callback(unsigned idx, G_GNUC_UNUSED bool *highlight,
- G_GNUC_UNUSED char** sc, G_GNUC_UNUSED void *data)
+lw_search_help_callback(unsigned idx, G_GNUC_UNUSED void *data)
{
- unsigned text_rows;
- static const char *text[] = {
- "Quick - Enter a string and ncmpc will search according",
- " to the current search mode (displayed above).",
- "",
- "Advanced - <tag>:<search term> [<tag>:<search term>...]",
- " Example: artist:radiohead album:pablo honey",
- "",
- " Available tags: artist, album, title, track,",
- " name, genre, date composer, performer, comment, file",
- "",
- NULL
- };
-
- text_rows=0;
- while (text[text_rows])
- text_rows++;
-
- if (idx < text_rows)
- return text[idx];
- return NULL;
+ assert(idx < G_N_ELEMENTS(help_text));
+
+ return help_text[idx];
}
static void
if (browser.filelist) {
filelist_free(browser.filelist);
browser.filelist = filelist_new();
+ list_window_set_length(browser.lw, 0);
}
if (clear_pattern && pattern) {
g_free(pattern);
}
static struct filelist *
-filelist_search(struct mpdclient *c, G_GNUC_UNUSED int exact_match, int table,
- gchar *local_pattern)
+search_simple_query(struct mpd_connection *connection, bool exact_match,
+ int table, gchar *local_pattern)
{
- struct filelist *list, *list2;
+ struct filelist *list;
gchar *filter_utf8 = locale_to_utf8(local_pattern);
if (table == SEARCH_ARTIST_TITLE) {
- list = mpdclient_filelist_search(c, FALSE, MPD_TAG_ARTIST,
- filter_utf8);
- if (list == NULL)
- list = filelist_new();
-
- list2 = mpdclient_filelist_search(c, FALSE, MPD_TAG_TITLE,
- filter_utf8);
- if (list2 != NULL) {
- filelist_move(list, list2);
- filelist_free(list2);
- }
+ mpd_command_list_begin(connection, false);
- filelist_sort_all(list, compare_filelistentry_format);
+ mpd_search_db_songs(connection, exact_match);
+ mpd_search_add_tag_constraint(connection, MPD_OPERATOR_DEFAULT,
+ MPD_TAG_ARTIST, filter_utf8);
+ mpd_search_commit(connection);
+
+ mpd_search_db_songs(connection, exact_match);
+ mpd_search_add_tag_constraint(connection, MPD_OPERATOR_DEFAULT,
+ MPD_TAG_TITLE, filter_utf8);
+ mpd_search_commit(connection);
+
+ mpd_command_list_end(connection);
+
+ list = filelist_new_recv(connection);
+ filelist_no_duplicates(list);
+ } else if (table == SEARCH_URI) {
+ mpd_search_db_songs(connection, exact_match);
+ mpd_search_add_uri_constraint(connection, MPD_OPERATOR_DEFAULT,
+ filter_utf8);
+ mpd_search_commit(connection);
+
+ list = filelist_new_recv(connection);
} else {
- list = mpdclient_filelist_search(c, FALSE, table, filter_utf8);
- if (list == NULL)
- list = filelist_new();
+ mpd_search_db_songs(connection, exact_match);
+ mpd_search_add_tag_constraint(connection, MPD_OPERATOR_DEFAULT,
+ table, filter_utf8);
+ mpd_search_commit(connection);
+
+ list = filelist_new_recv(connection);
}
g_free(filter_utf8);
*-----------------------------------------------------------------------
*/
static struct filelist *
-search_advanced_query(char *query, struct mpdclient *c)
+search_advanced_query(struct mpd_connection *connection, char *query)
{
int i,j;
char **strv;
struct filelist *fl = NULL;
advanced_search_mode = FALSE;
- if( g_strrstr(query, ":") == NULL )
+ if (strchr(query, ':') == NULL)
return NULL;
strv = g_strsplit_set(query, ": ", 0);
- i=0;
- while (strv[i]) {
- i++;
- }
-
memset(table, 0, 10*sizeof(int));
memset(arg, 0, 10*sizeof(char *));
g_strfreev(strv);
+ if (!advanced_search_mode || j == 0) {
+ for (i = 0; arg[i] != NULL; ++i)
+ g_free(arg[i]);
+ return NULL;
+ }
- if (advanced_search_mode && j > 0) {
- int iter;
- struct mpd_entity *entity;
-
- /*-----------------------------------------------------------------------
- * NOTE (again): This code exists to test a new search ui,
- * Its ugly and MUST be redesigned before the next release!
- * + the code below should live in mpdclient.c
- *-----------------------------------------------------------------------
- */
- /** stupid - but this is just a test...... (fulhack) */
- mpd_search_db_songs(c->connection, false);
-
- for(iter = 0; iter < 10 && arg[iter] != NULL; iter++) {
- if (table[iter] == SEARCH_URI)
- mpd_search_add_uri_constraint(c->connection,
- MPD_OPERATOR_DEFAULT,
- arg[iter]);
- else
- mpd_search_add_tag_constraint(c->connection,
- MPD_OPERATOR_DEFAULT,
- table[iter], arg[iter]);
- }
+ /*-----------------------------------------------------------------------
+ * NOTE (again): This code exists to test a new search ui,
+ * Its ugly and MUST be redesigned before the next release!
+ * + the code below should live in mpdclient.c
+ *-----------------------------------------------------------------------
+ */
+ /** stupid - but this is just a test...... (fulhack) */
+ mpd_search_db_songs(connection, false);
+
+ for (i = 0; i < 10 && arg[i] != NULL; i++) {
+ if (table[i] == SEARCH_URI)
+ mpd_search_add_uri_constraint(connection,
+ MPD_OPERATOR_DEFAULT,
+ arg[i]);
+ else
+ mpd_search_add_tag_constraint(connection,
+ MPD_OPERATOR_DEFAULT,
+ table[i], arg[i]);
+ }
- mpd_search_commit(c->connection);
+ mpd_search_commit(connection);
+ fl = filelist_new_recv(connection);
+ if (!mpd_response_finish(connection)) {
+ filelist_free(fl);
+ fl = NULL;
+ }
- fl = filelist_new();
+ for (i = 0; arg[i] != NULL; ++i)
+ g_free(arg[i]);
- while ((entity = mpd_recv_entity(c->connection)) != NULL)
- filelist_append(fl, entity);
+ return fl;
+}
- if (!mpd_response_finish(c->connection)) {
- filelist_free(fl);
- fl = NULL;
+static struct filelist *
+do_search(struct mpdclient *c, char *query)
+{
+ struct mpd_connection *connection = mpdclient_get_connection(c);
+ if (connection == NULL)
+ return NULL;
- mpdclient_handle_error(c);
- }
- }
+ struct filelist *fl = search_advanced_query(connection, query);
+ if (fl != NULL)
+ return fl;
- i=0;
- while( arg[i] )
- g_free(arg[i++]);
+ if (mpd_connection_get_error(connection) != MPD_ERROR_SUCCESS) {
+ mpdclient_handle_error(c);
+ return NULL;
+ }
+ fl = search_simple_query(connection, FALSE,
+ mode[options.search_mode].table,
+ query);
+ if (fl == NULL)
+ mpdclient_handle_error(c);
return fl;
}
+static void
+screen_search_reload(struct mpdclient *c)
+{
+ if (pattern == NULL)
+ return;
+
+ if (browser.filelist != NULL) {
+ filelist_free(browser.filelist);
+ browser.filelist = NULL;
+ }
+
+ browser.filelist = do_search(c, pattern);
+ if (browser.filelist == NULL)
+ browser.filelist = filelist_new();
+ list_window_set_length(browser.lw, filelist_length(browser.filelist));
+
+ screen_browser_sync_highlights(browser.filelist, &c->playlist);
+}
+
static void
search_new(struct mpdclient *c)
{
return;
}
- if (browser.filelist != NULL) {
- filelist_free(browser.filelist);
- browser.filelist = NULL;
- }
-
- if (mpd_connection_cmp_server_version(c->connection, 0, 12, 0) >= 0)
- browser.filelist = search_advanced_query(pattern, c);
-
- if (!advanced_search_mode && browser.filelist == NULL)
- browser.filelist = filelist_search(c, FALSE,
- mode[options.search_mode].table,
- pattern);
-
- if (browser.filelist == NULL)
- browser.filelist = filelist_new();
-
- screen_browser_sync_highlights(browser.filelist, &c->playlist);
- list_window_check_selected(browser.lw, filelist_length(browser.filelist));
+ screen_search_reload(c);
}
static void
screen_search_init(WINDOW *w, int cols, int rows)
{
browser.lw = list_window_init(w, cols, rows);
+ list_window_set_length(browser.lw, G_N_ELEMENTS(help_text));
}
static void
// search_new(screen, c);
// else
screen_status_printf(_("Press %s for a new search"),
- get_key_names(CMD_SCREEN_SEARCH,0));
+ get_key_names(CMD_SCREEN_SEARCH, false));
search_check_mode();
}
static void
screen_search_resize(int cols, int rows)
{
- browser.lw->cols = cols;
- browser.lw->rows = rows;
+ list_window_resize(browser.lw, cols, rows);
}
static void
{
if (browser.filelist) {
browser.lw->hide_cursor = false;
- list_window_paint(browser.lw, browser_lw_callback, browser.filelist);
+ screen_browser_paint(&browser);
} else {
browser.lw->hide_cursor = true;
list_window_paint(browser.lw, lw_search_help_callback, NULL);
_(mode[options.search_mode].label));
else
g_snprintf(str, size, _("Search: Press %s for a new search [%s]"),
- get_key_names(CMD_SCREEN_SEARCH,0),
+ get_key_names(CMD_SCREEN_SEARCH, false),
_(mode[options.search_mode].label));
return str;
static void
screen_search_update(struct mpdclient *c)
{
- if (browser.filelist != NULL && c->events & MPD_IDLE_PLAYLIST) {
+ if (browser.filelist != NULL && c->events & MPD_IDLE_QUEUE) {
screen_browser_sync_highlights(browser.filelist, &c->playlist);
search_repaint();
}
_(mode[options.search_mode].label));
/* continue and update... */
case CMD_SCREEN_UPDATE:
- if (pattern) {
- search_clear(false);
- browser.filelist = filelist_search(c,
- FALSE,
- mode[options.search_mode].table,
- pattern);
- screen_browser_sync_highlights(browser.filelist,
- &c->playlist);
- }
+ screen_search_reload(c);
search_repaint();
return true;