1 /*
2     Musical Spectrum plugin for the DeaDBeeF audio player
3 
4     Copyright (C) 2015 Christian Boxdörfer <christian.boxdoerfer@posteo.de>
5 
6     Based on DeaDBeeFs stock spectrum.
7     Copyright (c) 2009-2015 Alexey Yakovenko <waker@users.sourceforge.net>
8     Copyright (c) 2011 William Pitcock <nenolod@dereferenced.org>
9 
10     This program is free software; you can redistribute it and/or
11     modify it under the terms of the GNU General Public License
12     as published by the Free Software Foundation; either version 2
13     of the License, or (at your option) any later version.
14 
15     This program is distributed in the hope that it will be useful,
16     but WITHOUT ANY WARRANTY; without even the implied warranty of
17     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18     GNU General Public License for more details.
19 
20     You should have received a copy of the GNU General Public License
21     along with this program; if not, write to the Free Software
22     Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
23 */
24 
25 #include <sys/types.h>
26 #include <sys/stat.h>
27 #include <stdlib.h>
28 #include <string.h>
29 #include <assert.h>
30 #include <math.h>
31 #include <fcntl.h>
32 
33 #include <gtk/gtk.h>
34 
35 #include "spectrum.h"
36 #include "config.h"
37 
38 int CONFIG_REFRESH_INTERVAL = 25;
39 int CONFIG_DB_RANGE = 70;
40 int CONFIG_ENABLE_HGRID = 1;
41 int CONFIG_ENABLE_VGRID = 1;
42 int CONFIG_ENABLE_OCTAVE_GRID = 0;
43 int CONFIG_ALIGNMENT = 0;
44 int CONFIG_ENABLE_BAR_MODE = 0;
45 int CONFIG_DISPLAY_OCTAVES = 0;
46 int CONFIG_BAR_FALLOFF = -1;
47 int CONFIG_BAR_DELAY = 0;
48 int CONFIG_PEAK_FALLOFF = 90;
49 int CONFIG_PEAK_DELAY = 500;
50 int CONFIG_GRADIENT_ORIENTATION = 0;
51 int CONFIG_NUM_COLORS = 6;
52 int CONFIG_FFT_SIZE = 8192;
53 int CONFIG_WINDOW = 0;
54 int CONFIG_NUM_BARS = 132;
55 int CONFIG_BAR_W = 0;
56 int CONFIG_GAPS = TRUE;
57 int CONFIG_DRAW_STYLE = FALSE;
58 int CONFIG_FILL_SPECTRUM = TRUE;
59 GdkColor CONFIG_COLOR_BG;
60 GdkColor CONFIG_COLOR_VGRID;
61 GdkColor CONFIG_COLOR_HGRID;
62 GdkColor CONFIG_COLOR_OCTAVE_GRID;
63 GdkColor CONFIG_GRADIENT_COLORS[MAX_NUM_COLORS];
64 uint32_t CONFIG_COLOR_BG32 = 0xff222222;
65 uint32_t CONFIG_COLOR_VGRID32 = 0xff000000;
66 uint32_t CONFIG_COLOR_HGRID32 = 0xff666666;
67 uint32_t CONFIG_COLOR_OCTAVE_GRID32 = 0xff666666;
68 
69 int FFT_INDEX = 4;
70 
71 static char *default_colors[] = {"65535 0 0",
72                                  "65535 32896 0",
73                                  "65535 65535 0",
74                                  "32896 65535 30840",
75                                  "0 38036 41120",
76                                  "0 8224 25700" };
77 
78 void
save_config(void)79 save_config (void)
80 {
81     deadbeef->conf_set_int (CONFSTR_MS_REFRESH_INTERVAL,            CONFIG_REFRESH_INTERVAL);
82     deadbeef->conf_set_int (CONFSTR_MS_FFT_SIZE,                    CONFIG_FFT_SIZE);
83     deadbeef->conf_set_int (CONFSTR_MS_DB_RANGE,                    CONFIG_DB_RANGE);
84     deadbeef->conf_set_int (CONFSTR_MS_ENABLE_HGRID,                CONFIG_ENABLE_HGRID);
85     deadbeef->conf_set_int (CONFSTR_MS_ENABLE_VGRID,                CONFIG_ENABLE_VGRID);
86     deadbeef->conf_set_int (CONFSTR_MS_ENABLE_OCTAVE_GRID,          CONFIG_ENABLE_OCTAVE_GRID);
87     deadbeef->conf_set_int (CONFSTR_MS_ALIGNMENT,                   CONFIG_ALIGNMENT);
88     deadbeef->conf_set_int (CONFSTR_MS_ENABLE_BAR_MODE,             CONFIG_ENABLE_BAR_MODE);
89     deadbeef->conf_set_int (CONFSTR_MS_DISPLAY_OCTAVES,             CONFIG_DISPLAY_OCTAVES);
90     deadbeef->conf_set_int (CONFSTR_MS_NUM_BARS,                    CONFIG_NUM_BARS);
91     deadbeef->conf_set_int (CONFSTR_MS_BAR_W,                       CONFIG_BAR_W);
92     deadbeef->conf_set_int (CONFSTR_MS_GAPS,                        CONFIG_GAPS);
93     deadbeef->conf_set_int (CONFSTR_MS_DRAW_STYLE,                  CONFIG_DRAW_STYLE);
94     deadbeef->conf_set_int (CONFSTR_MS_FILL_SPECTRUM,               CONFIG_FILL_SPECTRUM);
95     deadbeef->conf_set_int (CONFSTR_MS_BAR_FALLOFF,                 CONFIG_BAR_FALLOFF);
96     deadbeef->conf_set_int (CONFSTR_MS_BAR_DELAY,                   CONFIG_BAR_DELAY);
97     deadbeef->conf_set_int (CONFSTR_MS_PEAK_FALLOFF,                CONFIG_PEAK_FALLOFF);
98     deadbeef->conf_set_int (CONFSTR_MS_PEAK_DELAY,                  CONFIG_PEAK_DELAY);
99     deadbeef->conf_set_int (CONFSTR_MS_GRADIENT_ORIENTATION,        CONFIG_GRADIENT_ORIENTATION);
100     deadbeef->conf_set_int (CONFSTR_MS_WINDOW,                      CONFIG_WINDOW);
101     deadbeef->conf_set_int (CONFSTR_MS_NUM_COLORS,                  CONFIG_NUM_COLORS);
102     char color[100];
103     char conf_str[100];
104     for (int i = 0; i < CONFIG_NUM_COLORS; i++) {
105         snprintf (color, sizeof (color), "%d %d %d", CONFIG_GRADIENT_COLORS[i].red, CONFIG_GRADIENT_COLORS[i].green, CONFIG_GRADIENT_COLORS[i].blue);
106         snprintf (conf_str, sizeof (conf_str), "%s%02d", CONFSTR_MS_COLOR_GRADIENT, i);
107         deadbeef->conf_set_str (conf_str, color);
108     }
109     snprintf (color, sizeof (color), "%d %d %d", CONFIG_COLOR_BG.red, CONFIG_COLOR_BG.green, CONFIG_COLOR_BG.blue);
110     deadbeef->conf_set_str (CONFSTR_MS_COLOR_BG, color);
111     snprintf (color, sizeof (color), "%d %d %d", CONFIG_COLOR_VGRID.red, CONFIG_COLOR_VGRID.green, CONFIG_COLOR_VGRID.blue);
112     deadbeef->conf_set_str (CONFSTR_MS_COLOR_VGRID, color);
113     snprintf (color, sizeof (color), "%d %d %d", CONFIG_COLOR_HGRID.red, CONFIG_COLOR_HGRID.green, CONFIG_COLOR_HGRID.blue);
114     deadbeef->conf_set_str (CONFSTR_MS_COLOR_HGRID, color);
115     snprintf (color, sizeof (color), "%d %d %d", CONFIG_COLOR_OCTAVE_GRID.red, CONFIG_COLOR_OCTAVE_GRID.green, CONFIG_COLOR_OCTAVE_GRID.blue);
116     deadbeef->conf_set_str (CONFSTR_MS_COLOR_OCTAVE_GRID, color);
117 }
118 
119 void
load_config(void)120 load_config (void)
121 {
122     deadbeef->conf_lock ();
123     CONFIG_GRADIENT_ORIENTATION = deadbeef->conf_get_int (CONFSTR_MS_GRADIENT_ORIENTATION,   0);
124     CONFIG_WINDOW = deadbeef->conf_get_int (CONFSTR_MS_WINDOW,                 BLACKMAN_HARRIS);
125     CONFIG_FFT_SIZE = deadbeef->conf_get_int (CONFSTR_MS_FFT_SIZE,                        8192);
126     FFT_INDEX = log2 (CONFIG_FFT_SIZE) - 9;
127     CONFIG_DB_RANGE = deadbeef->conf_get_int (CONFSTR_MS_DB_RANGE,                          70);
128     CONFIG_ENABLE_HGRID = deadbeef->conf_get_int (CONFSTR_MS_ENABLE_HGRID,                   1);
129     CONFIG_ENABLE_VGRID = deadbeef->conf_get_int (CONFSTR_MS_ENABLE_VGRID,                   1);
130     CONFIG_ENABLE_OCTAVE_GRID = deadbeef->conf_get_int (CONFSTR_MS_ENABLE_OCTAVE_GRID,       0);
131     CONFIG_ALIGNMENT = deadbeef->conf_get_int (CONFSTR_MS_ALIGNMENT,                      LEFT);
132     CONFIG_ENABLE_BAR_MODE = deadbeef->conf_get_int (CONFSTR_MS_ENABLE_BAR_MODE,             0);
133     CONFIG_DISPLAY_OCTAVES = deadbeef->conf_get_int (CONFSTR_MS_DISPLAY_OCTAVES,             0);
134     CONFIG_REFRESH_INTERVAL = deadbeef->conf_get_int (CONFSTR_MS_REFRESH_INTERVAL,          25);
135     CONFIG_NUM_BARS = deadbeef->conf_get_int (CONFSTR_MS_NUM_BARS,                         132);
136     CONFIG_BAR_W = deadbeef->conf_get_int (CONFSTR_MS_BAR_W,                                 0);
137     CONFIG_GAPS = deadbeef->conf_get_int (CONFSTR_MS_GAPS,                                TRUE);
138     CONFIG_DRAW_STYLE = deadbeef->conf_get_int (CONFSTR_MS_DRAW_STYLE,                   FALSE);
139     CONFIG_FILL_SPECTRUM = deadbeef->conf_get_int (CONFSTR_MS_FILL_SPECTRUM,              TRUE);
140     CONFIG_BAR_FALLOFF = deadbeef->conf_get_int (CONFSTR_MS_BAR_FALLOFF,                    -1);
141     CONFIG_BAR_DELAY = deadbeef->conf_get_int (CONFSTR_MS_BAR_DELAY,                         0);
142     CONFIG_PEAK_FALLOFF = deadbeef->conf_get_int (CONFSTR_MS_PEAK_FALLOFF,                  90);
143     CONFIG_PEAK_DELAY = deadbeef->conf_get_int (CONFSTR_MS_PEAK_DELAY,                     500);
144     CONFIG_NUM_COLORS = deadbeef->conf_get_int (CONFSTR_MS_NUM_COLORS,                       6);
145     const char *color;
146     char conf_str[100];
147     color = deadbeef->conf_get_str_fast (CONFSTR_MS_COLOR_BG,                   "8738 8738 8738");
148     sscanf (color, "%hd %hd %hd", &CONFIG_COLOR_BG.red, &CONFIG_COLOR_BG.green, &CONFIG_COLOR_BG.blue);
149     color = deadbeef->conf_get_str_fast (CONFSTR_MS_COLOR_VGRID,                         "0 0 0");
150     sscanf (color, "%hd %hd %hd", &CONFIG_COLOR_VGRID.red, &CONFIG_COLOR_VGRID.green, &CONFIG_COLOR_VGRID.blue);
151     color = deadbeef->conf_get_str_fast (CONFSTR_MS_COLOR_HGRID,             "26214 26214 26214");
152     sscanf (color, "%hd %hd %hd", &CONFIG_COLOR_HGRID.red, &CONFIG_COLOR_HGRID.green, &CONFIG_COLOR_HGRID.blue);
153     color = deadbeef->conf_get_str_fast (CONFSTR_MS_COLOR_OCTAVE_GRID,             "26214 26214 26214");
154     sscanf (color, "%hd %hd %hd", &CONFIG_COLOR_OCTAVE_GRID.red, &CONFIG_COLOR_OCTAVE_GRID.green, &CONFIG_COLOR_OCTAVE_GRID.blue);
155     for (int i = 0; i < CONFIG_NUM_COLORS; i++) {
156         snprintf (conf_str, sizeof (conf_str), "%s%02d", CONFSTR_MS_COLOR_GRADIENT, i);
157         if (i < NUM_DEFAULT_COLORS) {
158             color = deadbeef->conf_get_str_fast (conf_str, default_colors[i]);
159         }
160         else {
161             color = deadbeef->conf_get_str_fast (conf_str, "0 0 0");
162         }
163         sscanf (color, "%hd %hd %hd", &(CONFIG_GRADIENT_COLORS[i].red), &(CONFIG_GRADIENT_COLORS[i].green), &(CONFIG_GRADIENT_COLORS[i].blue));
164     }
165 
166     float scale = 255/65535.f;
167     CONFIG_COLOR_BG32 = ((uint32_t)(CONFIG_COLOR_BG.red * scale) & 0xFF) << 16 |
168                         ((uint32_t)(CONFIG_COLOR_BG.green * scale) & 0xFF) << 8 |
169                         ((uint32_t)(CONFIG_COLOR_BG.blue * scale) & 0xFF) << 0;
170 
171     CONFIG_COLOR_VGRID32 = ((uint32_t)(CONFIG_COLOR_VGRID.red * scale) & 0xFF) << 16 |
172                         ((uint32_t)(CONFIG_COLOR_VGRID.green * scale) & 0xFF) << 8 |
173                         ((uint32_t)(CONFIG_COLOR_VGRID.blue * scale) & 0xFF) << 0;
174 
175     CONFIG_COLOR_HGRID32 = ((uint32_t)(CONFIG_COLOR_HGRID.red * scale) & 0xFF) << 16 |
176                         ((uint32_t)(CONFIG_COLOR_HGRID.green * scale) & 0xFF) << 8 |
177                         ((uint32_t)(CONFIG_COLOR_HGRID.blue * scale) & 0xFF) << 0;
178     CONFIG_COLOR_OCTAVE_GRID32 = ((uint32_t)(CONFIG_COLOR_OCTAVE_GRID.red * scale) & 0xFF) << 16 |
179                         ((uint32_t)(CONFIG_COLOR_OCTAVE_GRID.green * scale) & 0xFF) << 8 |
180                         ((uint32_t)(CONFIG_COLOR_OCTAVE_GRID.blue * scale) & 0xFF) << 0;
181     deadbeef->conf_unlock ();
182 }
183 
184