1 /* Gnome Music Player Client (GMPC)
2 * Copyright (C) 2004-2012 Qball Cow <qball@gmpclient.org>
3 * Project homepage: http://gmpclient.org/
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
23 #include "advanced-search.h"
25 static GRegex
*search_regex
= NULL
;
28 * Initialize the advanced_search system.
30 void advanced_search_init(void)
33 GString
*string
= g_string_new("(");
35 g_regex_unref(search_regex
);
38 for (i
= 0; i
< MPD_TAG_NUM_OF_ITEM_TYPES
; i
++)
40 if (mpd_server_tag_supported(connection
, i
))
42 g_string_append(string
, mpdTagItemKeys
[i
]);
43 if (i
< (MPD_TAG_NUM_OF_ITEM_TYPES
- 1))
44 g_string_append(string
, "|");
47 g_string_append(string
, ")[ ]*[=:][ ]*|[ ]*(\\|\\|)[ ]*");
48 search_regex
= g_regex_new(string
->str
, G_REGEX_CASELESS
, 0, NULL
);
49 g_string_free(string
, TRUE
);
53 * Update the advanced_search regex to include only the supported tags
55 void advanced_search_update_taglist(void)
57 advanced_search_init();
61 * Destroy all the advanced_search system and clean all allocated memory.
63 void advanced_search_destroy(void)
66 g_regex_unref(search_regex
);
72 * @param query the query to execute.
73 * @param playlist set to TRUE to search only songs in the playlist.
75 * @returns the search result in a #MpdData list.
77 MpdData
*advanced_search(const gchar
* query
, int in_playlist
)
79 MpdData
*data_return
= NULL
;
80 gchar
**text
= g_regex_split(search_regex
, query
, 0);
82 gboolean found
= FALSE
;
83 for (i
= 0; text
&& text
[i
]; i
++)
86 /* Or sign, if hit, a new query is started */
87 if (strcmp(text
[i
], "||") == 0)
90 /* Commit the currently in active search and append the results */
92 data
= mpd_playlist_search_commit(connection
);
94 data
= mpd_database_search_commit(connection
);
95 data_return
= mpd_data_concatenate(data_return
, data
);
100 if (text
[i
][0] == '\0')
103 /* Parse the tag name. */
104 type
= mpd_misc_get_tag_by_name(g_strstrip(text
[i
]));
105 if (type
!= MPD_TAG_NOT_FOUND
&& text
[i
+ 1])
107 gchar
**split
= tokenize_string(text
[i
+ 1]);
109 for (j
= 0; split
&& split
[j
]; j
++)
114 mpd_playlist_search_start(connection
, FALSE
);
116 mpd_database_search_start(connection
, FALSE
);
120 mpd_playlist_search_add_constraint(connection
, type
, g_strstrip(split
[j
]));
122 mpd_database_search_add_constraint(connection
, type
, g_strstrip(split
[j
]));
129 gchar
**split
= tokenize_string(text
[i
]);
131 for (j
= 0; split
&& split
[j
]; j
++)
136 mpd_playlist_search_start(connection
, FALSE
);
138 mpd_database_search_start(connection
, FALSE
);
142 mpd_playlist_search_add_constraint(connection
, MPD_TAG_ITEM_ANY
, split
[j
]);
144 mpd_database_search_add_constraint(connection
, MPD_TAG_ITEM_ANY
, split
[j
]);
152 /* Execute the active search and append the results */
157 data
= mpd_playlist_search_commit(connection
);
159 data
= mpd_database_search_commit(connection
);
160 data_return
= mpd_data_concatenate(data_return
, data
);
162 /* remove possible duplicates (because of concatenating queries) */
163 return misc_mpddata_remove_duplicate_songs(data_return
);
166 /* vim: set noexpandtab ts=4 sw=4 sts=4 tw=120: */