1 /* EasyTAG - tag editor for audio files
2  * Copyright (C) 2015  David King <amigadave@amigadave.com>
3  *
4  * This program is free software; you can redistribute it and/or modify it
5  * under the terms of the GNU General Public License as published by the Free
6  * Software Foundation; either version 2 of the License, or (at your option)
7  * any later version.
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
12  * more details.
13  *
14  * You should have received a copy of the GNU General Public License along with
15  * this program; if not, write to the Free Software Foundation, Inc., 51
16  * Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
17  */
18 
19 #include "file_name.h"
20 
21 #include "charset.h"
22 #include "misc.h"
23 
24 #include <string.h>
25 
26 /*
27  * Create a new File_Name structure
28  */
29 File_Name *
et_file_name_new(void)30 et_file_name_new (void)
31 {
32     File_Name *file_name;
33 
34     file_name = g_slice_new (File_Name);
35     file_name->key = et_undo_key_new ();
36     file_name->saved = FALSE;
37     file_name->value = NULL;
38     file_name->value_utf8 = NULL;
39     file_name->value_ck = NULL;
40 
41     return file_name;
42 }
43 
44 /*
45  * Frees a File_Name item.
46  */
47 void
et_file_name_free(File_Name * file_name)48 et_file_name_free (File_Name *file_name)
49 {
50     g_return_if_fail (file_name != NULL);
51 
52     g_free (file_name->value);
53     g_free (file_name->value_utf8);
54     g_free (file_name->value_ck);
55     g_slice_free (File_Name, file_name);
56 }
57 
58 /*
59  * Fill content of a FileName item according to the filename passed in argument (UTF-8 filename or not)
60  * Calculate also the collate key.
61  * It treats numbers intelligently so that "file1" "file10" "file5" is sorted as "file1" "file5" "file10"
62  */
63 void
ET_Set_Filename_File_Name_Item(File_Name * FileName,const gchar * filename_utf8,const gchar * filename)64 ET_Set_Filename_File_Name_Item (File_Name *FileName,
65                                 const gchar *filename_utf8,
66                                 const gchar *filename)
67 {
68     g_return_if_fail (FileName != NULL);
69 
70     if (filename_utf8 && filename)
71     {
72         FileName->value_utf8 = g_strdup (filename_utf8);
73         FileName->value = g_strdup (filename);
74         FileName->value_ck = g_utf8_collate_key_for_filename (FileName->value_utf8, -1);
75     }
76     else if (filename_utf8)
77     {
78         FileName->value_utf8 = g_strdup (filename_utf8);
79         FileName->value = filename_from_display (filename_utf8);
80         FileName->value_ck = g_utf8_collate_key_for_filename (FileName->value_utf8, -1);
81     }
82     else if (filename)
83     {
84         FileName->value_utf8 = g_filename_display_name (filename);
85         FileName->value = g_strdup (filename);
86         FileName->value_ck = g_utf8_collate_key_for_filename (FileName->value_utf8, -1);
87     }
88 }
89 
90 gboolean
et_file_name_set_from_components(File_Name * file_name,const gchar * new_name,const gchar * dir_name,gboolean replace_illegal)91 et_file_name_set_from_components (File_Name *file_name,
92                                   const gchar *new_name,
93                                   const gchar *dir_name,
94                                   gboolean replace_illegal)
95 {
96     /* Check if new filename seems to be correct. */
97     if (new_name)
98     {
99         gchar *filename_new;
100         gchar *path_new;
101 
102         filename_new = g_strdup (new_name);
103 
104         /* Convert the illegal characters. */
105         et_filename_prepare (filename_new, replace_illegal);
106 
107         /* Set the new filename (in file system encoding). */
108         path_new = g_build_filename (dir_name, filename_new, NULL);
109         ET_Set_Filename_File_Name_Item (file_name, NULL, path_new);
110 
111         g_free (path_new);
112         g_free (filename_new);
113         return TRUE;
114     }
115     else
116     {
117         file_name->value = NULL;
118         file_name->value_utf8 = NULL;
119         file_name->value_ck = NULL;
120 
121         return FALSE;
122     }
123 }
124 
125 /*
126  * Compares two File_Name items :
127  *  - returns TRUE if there aren't the same
128  *  - else returns FALSE
129  */
130 gboolean
et_file_name_detect_difference(const File_Name * a,const File_Name * b)131 et_file_name_detect_difference (const File_Name *a,
132                                 const File_Name *b)
133 {
134     const gchar *filename1_ck;
135     const gchar *filename2_ck;
136 
137     g_return_val_if_fail (a && b, FALSE);
138 
139     if (a && !b) return TRUE;
140     if (!a && b) return TRUE;
141 
142     /* Both a and b are != NULL. */
143     if (!a->value && !b->value) return FALSE;
144     if (a->value && !b->value) return TRUE;
145     if (!a->value && b->value) return TRUE;
146 
147     /* Compare collate keys (with FileName->value converted to UTF-8 as it
148      * contains raw data). */
149     filename1_ck = a->value_ck;
150     filename2_ck = b->value_ck;
151 
152     /* Filename changed ? (we check path + file). */
153     if (strcmp (filename1_ck, filename2_ck) != 0)
154     {
155         return TRUE;
156     }
157     else
158     {
159         return FALSE;
160     }
161 }
162