Macro qtTrIdx() replaced by tr() and QT_TRANSLATE_NOOP()
[mafwsubrenderer] / mafw-gst-subtitles-renderer / libmafw-gst-renderer / mafw-gst-renderer-utils.c
1 /*
2  * This file is a part of MAFW
3  *
4  * Copyright (C) 2007, 2008, 2009 Nokia Corporation, all rights reserved.
5  *
6  * Contact: Visa Smolander <visa.smolander@nokia.com>
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public License
10  * as published by the Free Software Foundation; version 2.1 of
11  * the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful, but
14  * WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
21  * 02110-1301 USA
22  *
23  */
24
25 #ifdef HAVE_CONFIG_H
26 #include "config.h"
27 #endif
28
29 #include <glib.h>
30
31 #include <string.h>
32 #include <gio/gio.h>
33
34 #include "mafw-gst-renderer-utils.h"
35
36 #undef  G_LOG_DOMAIN
37 #define G_LOG_DOMAIN "mafw-gst-renderer-utils"
38
39 /**
40  * convert_utf8:
41  * @src: string.
42  * @dst: location for utf8 version of @src.
43  *
44  * Tries to convert @src into UTF-8, placing it into @dst.
45  *
46  * Returns: TRUE on success.
47  */
48 gboolean convert_utf8(const gchar *src, gchar **dst)
49 {
50         GError *error;
51
52         if (!src)
53                 return FALSE;
54         if (g_utf8_validate(src, -1, NULL)) {
55                 *dst = g_strdup(src);
56                 return TRUE;
57         }
58         error = NULL;
59         *dst = g_locale_to_utf8(src, -1, NULL, NULL, &error);
60         if (error) {
61                 g_warning("utf8 conversion failed '%s' (%d: %s)",
62                           src, error->code, error->message);
63                 g_error_free(error);
64                 return FALSE;
65         }
66         return TRUE;
67 }
68
69 gboolean uri_is_playlist(const gchar *uri) {
70         /* TODO: Return if the uri is a playlist or not, using the mime type
71            instead of the file extension. */
72         if ((g_str_has_suffix(uri, ".pls")) ||
73             (g_str_has_suffix(uri, ".m3u")) ||
74             (g_str_has_suffix(uri, ".smil")) ||
75             (g_str_has_suffix(uri, ".smi")) ||
76             (g_str_has_suffix(uri, ".wpl")) ||
77             (g_str_has_suffix(uri, ".wax")) ||
78             (g_str_has_suffix(uri, ".uni")) ||
79             (g_str_has_suffix(uri, ".ram")) ||
80 /*          (g_str_has_suffix(uri, ".ra")) || */
81             (g_str_has_suffix(uri, ".asx")) ||
82             (g_str_has_suffix(uri, ".rpm")))
83                 {
84                         return TRUE;
85                 }
86         return FALSE;
87 }
88
89 /**
90  * uri_is_stream:
91  * @uri: the URI to be checked.
92  *
93  * Check if given URI is a stream (not a local resource).  To not depend on
94  * gnomevfs for this, we assume everything that doesn't start with "file://" is
95  * a stream.
96  *
97  * Returns: TRUE if the URI is not local.
98  */
99 gboolean uri_is_stream(const gchar *uri)
100 {
101         if (uri == NULL) {
102                 return FALSE;
103         } else {
104                 return !g_str_has_prefix(uri, "file://");
105         }
106 }
107
108 /*
109  * Imported from totem-uri.c
110  * Copyright (C) 2004 Bastien Nocera
111  */
112
113 /* List from xine-lib's demux_sputext.c */
114 static const char subtitle_ext[][4] = {
115         "sub",
116         "srt",
117         "smi",
118         "ssa",
119         "ass",
120         "asc"
121 };
122
123 static inline gboolean
124 uri_exists (const char *uri)
125 {
126         GFile *file = g_file_new_for_uri (uri);
127         if (file != NULL) {
128                 if (g_file_query_exists (file, NULL)) {
129                         g_object_unref (file);
130                         return TRUE;
131                 }
132                 g_object_unref (file);
133         }
134         return FALSE;
135 }
136
137 static char *
138 uri_get_subtitle_for_uri (const char *uri)
139 {
140         char *subtitle;
141         guint len, i;
142         gint suffix;
143
144         /* Find the filename suffix delimiter */
145         len = strlen (uri);
146         for (suffix = len - 1; suffix > 0; suffix--) {
147                 if (uri[suffix] == G_DIR_SEPARATOR ||
148                     (uri[suffix] == '/')) {
149                         /* This filename has no extension; we'll need to 
150                          * add one */
151                         suffix = len;
152                         break;
153                 }
154                 if (uri[suffix] == '.') {
155                         /* Found our extension marker */
156                         break;
157                 }
158         }
159         if (suffix < 0)
160                 return NULL;
161
162         /* Generate a subtitle string with room at the end to store the
163          * 3 character extensions for which we want to search */
164         subtitle = g_malloc0 (suffix + 4 + 1);
165         g_return_val_if_fail (subtitle != NULL, NULL);
166         g_strlcpy (subtitle, uri, suffix + 4 + 1);
167         g_strlcpy (subtitle + suffix, ".???", 5);
168
169         /* Search for any files with one of our known subtitle extensions */
170         for (i = 0; i < G_N_ELEMENTS (subtitle_ext) ; i++) {
171                 char *subtitle_ext_upper;
172                 memcpy (subtitle + suffix + 1, subtitle_ext[i], 3);
173
174                 if (uri_exists (subtitle))
175                         return subtitle;
176
177                 /* Check with upper-cased extension */
178                 subtitle_ext_upper = g_ascii_strup (subtitle_ext[i], -1);
179                 memcpy (subtitle + suffix + 1, subtitle_ext_upper, 3);
180                 g_free (subtitle_ext_upper);
181
182                 if (uri_exists (subtitle))
183                         return subtitle;
184         }
185         g_free (subtitle);
186         return NULL;
187 }
188
189 static char *
190 uri_get_subtitle_in_subdir (GFile *file, const char *subdir)
191 {
192         char *filename, *subtitle, *full_path_str;
193         GFile *parent, *full_path, *directory;
194
195         /* Get the sibling directory @subdir of the file @file */
196         parent = g_file_get_parent (file);
197         directory = g_file_get_child (parent, subdir);
198         g_object_unref (parent);
199
200         /* Get the file of the same name as @file in the @subdir directory */
201         filename = g_file_get_basename (file);
202         full_path = g_file_get_child (directory, filename);
203         g_object_unref (directory);
204         g_free (filename);
205
206         /* Get the subtitles from that URI */
207         full_path_str = g_file_get_uri (full_path);
208         g_object_unref (full_path);
209         subtitle = uri_get_subtitle_for_uri (full_path_str);
210         g_free (full_path_str);
211
212         return subtitle;
213 }
214
215 char *
216 uri_get_subtitle_uri (const char *uri)
217 {
218         GFile *file;
219         char *subtitle;
220
221         if (g_str_has_prefix (uri, "http") != FALSE)
222                 return NULL;
223
224         /* Has the user specified a subtitle file manually? */
225         if (strstr (uri, "#subtitle:") != NULL)
226                 return NULL;
227
228         /* Does the file exist? */
229         file = g_file_new_for_uri (uri);
230         if (g_file_query_exists (file, NULL) != TRUE) {
231                 g_object_unref (file);
232                 return NULL;
233         }
234
235         /* Try in the current directory */
236         subtitle = uri_get_subtitle_for_uri (uri);
237         if (subtitle != NULL) {
238                 g_object_unref (file);
239                 return subtitle;
240         }
241
242         subtitle = uri_get_subtitle_in_subdir (file, "subtitles");
243         g_object_unref (file);
244
245         return subtitle;
246 }
247
248 /* vi: set noexpandtab ts=8 sw=8 cino=t0,(0: */