Merge branch 'ct' of git.pipapo.org:cinelerra-ct into ct
[cinelerra_cv/ct.git] / cinelerra / preferences.C
blob38d9d6c6e6dacf1f633c978bef1a1413a4a2401c
1 #include "asset.h"
2 #include "audioconfig.h"
3 #include "audiodevice.inc"
4 #include "bcmeter.inc"
5 #include "cache.inc"
6 #include "clip.h"
7 #include "bchash.h"
8 #include "file.inc"
9 #include "filesystem.h"
10 #include "guicast.h"
11 #include "mutex.h"
12 #include "preferences.h"
13 #include "theme.h"
14 #include "videoconfig.h"
15 #include "videodevice.inc"
16 #include <string.h>
18 //#define CLAMP(x, y, z) (x) = ((x) < (y) ? (y) : ((x) > (z) ? (z) : (x)))
31 Preferences::Preferences()
33 // Set defaults
34         FileSystem fs;
36         preferences_lock = new Mutex("Preferences::preferences_lock");
37         sprintf(index_directory, BCASTDIR);
38         if(strlen(index_directory))
39                 fs.complete_path(index_directory);
40         cache_size = 0xa00000;
41         index_size = 0x300000;
42         index_count = 100;
43         use_thumbnails = 1;
44         theme[0] = 0;
45         use_renderfarm = 0;
46         force_uniprocessor = 0;
47         renderfarm_port = DEAMON_PORT;
48         render_preroll = 0.5;
49         brender_preroll = 0;
50         renderfarm_mountpoint[0] = 0;
51         renderfarm_vfs = 0;
52         renderfarm_job_count = 20;
53         processors = calculate_processors(0);
54         real_processors = calculate_processors(1);
56 // Default brender asset
57         brender_asset = Asset_GC(new Asset);
58         brender_asset->audio_data = 0;
59         brender_asset->video_data = 1;
60         sprintf(brender_asset->path, "/tmp/brender");
61         brender_asset->format = FILE_JPEG_LIST;
62         brender_asset->jpeg_quality = 80;
64         use_brender = 0;
65         brender_fragment = 1;
66         local_rate = 0.0;
68         use_tipwindow = 1;
70         for(int i = 0; i < MAXCHANNELS; i++)
71         {
72                 for(int j = 0; j < i + 1; j++)
73                 {
74                         int position = 180 - (360 * j / (i + 1));
75                         while(position < 0) position += 360;
76                         channel_positions[i * MAXCHANNELS + j] = position;
77                 }
78         }
81 Preferences::~Preferences()
83         delete preferences_lock;
86 void Preferences::copy_rates_from(Preferences *preferences)
88         preferences_lock->lock("Preferences::copy_rates_from");
89 // Need to match node titles in case the order changed and in case
90 // one of the nodes in the source is the master node.
91         local_rate = preferences->local_rate;
93         for(int j = 0; 
94                 j < preferences->renderfarm_nodes.total; 
95                 j++)
96         {
97                 double new_rate = preferences->renderfarm_rate.values[j];
98 // Put in the master node
99                 if(preferences->renderfarm_nodes.values[j][0] == '/')
100                 {
101                         if(!EQUIV(new_rate, 0.0))
102                                 local_rate = new_rate;
103                 }
104                 else
105 // Search for local node and copy it to that node
106                 if(!EQUIV(new_rate, 0.0))
107                 {
108                         for(int i = 0; i < renderfarm_nodes.total; i++)
109                         {
110                                 if(!strcmp(preferences->renderfarm_nodes.values[j], renderfarm_nodes.values[i]) &&
111                                         preferences->renderfarm_ports.values[j] == renderfarm_ports.values[i])
112                                 {
113                                         renderfarm_rate.values[i] = new_rate;
114                                         break;
115                                 }
116                         }
117                 }
118         }
120 //printf("Preferences::copy_rates_from 1 %f %f\n", local_rate, preferences->local_rate);
121         preferences_lock->unlock();
124 void Preferences::copy_from(Preferences *that)
126 // ================================= Performance ================================
127         strcpy(index_directory, that->index_directory);
128         index_size = that->index_size;
129         index_count = that->index_count;
130         use_thumbnails = that->use_thumbnails;
131         strcpy(global_plugin_dir, that->global_plugin_dir);
132         strcpy(theme, that->theme);
134         use_tipwindow = that->use_tipwindow;
136         cache_size = that->cache_size;
137         force_uniprocessor = that->force_uniprocessor;
138         processors = that->processors;
139         real_processors = that->real_processors;
140         renderfarm_nodes.remove_all_objects();
141         renderfarm_ports.remove_all();
142         renderfarm_enabled.remove_all();
143         renderfarm_rate.remove_all();
144         local_rate = that->local_rate;
145         for(int i = 0; i < that->renderfarm_nodes.total; i++)
146         {
147                 add_node(that->renderfarm_nodes.values[i], 
148                         that->renderfarm_ports.values[i],
149                         that->renderfarm_enabled.values[i],
150                         that->renderfarm_rate.values[i]);
151         }
152         use_renderfarm = that->use_renderfarm;
153         renderfarm_port = that->renderfarm_port;
154         render_preroll = that->render_preroll;
155         brender_preroll = that->brender_preroll;
156         renderfarm_job_count = that->renderfarm_job_count;
157         renderfarm_vfs = that->renderfarm_vfs;
158         strcpy(renderfarm_mountpoint, that->renderfarm_mountpoint);
159         renderfarm_consolidate = that->renderfarm_consolidate;
160         use_brender = that->use_brender;
161         brender_fragment = that->brender_fragment;
162         *brender_asset = *that->brender_asset;
164 // Check boundaries
166         FileSystem fs;
167         if(strlen(index_directory))
168         {
169                 fs.complete_path(index_directory);
170                 fs.add_end_slash(index_directory);
171         }
172         
173         if(strlen(global_plugin_dir))
174         {
175                 fs.complete_path(global_plugin_dir);
176                 fs.add_end_slash(global_plugin_dir);
177         }
179         boundaries();
182 void Preferences::boundaries()
184         renderfarm_job_count = MAX(renderfarm_job_count, 1);
185         CLAMP(cache_size, MIN_CACHE_SIZE, MAX_CACHE_SIZE);
188 Preferences& Preferences::operator=(Preferences &that)
190 printf("Preferences::operator=\n");
191         copy_from(&that);
192         return *this;
195 void Preferences::print_channels(char *string, 
196         int *channel_positions, 
197         int channels)
199         char string3[BCTEXTLEN];
200         string[0] = 0;
201         for(int j = 0; j < channels; j++)
202         {
203                 sprintf(string3, "%d", channel_positions[j]);
204                 strcat(string, string3);
205                 if(j < channels - 1)
206                         strcat(string, ",");
207         }
210 void Preferences::scan_channels(char *string, 
211         int *channel_positions, 
212         int channels)
214         char string2[BCTEXTLEN];
215         int len = strlen(string);
216         int current_channel = 0;
217         for(int i = 0; i < len; i++)
218         {
219                 strcpy(string2, &string[i]);
220                 for(int j = 0; j < BCTEXTLEN; j++)
221                 {
222                         if(string2[j] == ',' || string2[j] == 0)
223                         {
224                                 i += j;
225                                 string2[j] = 0;
226                                 break;
227                         }
228                 }
229                 channel_positions[current_channel++] = atoi(string2);
230                 if(current_channel >= channels) break;
231         }
234 int Preferences::load_defaults(BC_Hash *defaults)
236         char string[BCTEXTLEN];
238         use_tipwindow = defaults->get("USE_TIPWINDOW", use_tipwindow);
239         defaults->get("INDEX_DIRECTORY", index_directory);
240         index_size = defaults->get("INDEX_SIZE", index_size);
241         index_count = defaults->get("INDEX_COUNT", index_count);
242         use_thumbnails = defaults->get("USE_THUMBNAILS", use_thumbnails);
244         sprintf(global_plugin_dir, PLUGIN_DIR);
245 //      defaults->get("GLOBAL_PLUGIN_DIR", global_plugin_dir);
246         if(getenv("GLOBAL_PLUGIN_DIR"))
247         {
248                 strcpy(global_plugin_dir, getenv("GLOBAL_PLUGIN_DIR"));
249         }
251         strcpy(theme, DEFAULT_THEME);
252         defaults->get("THEME", theme);
254         for(int i = 0; i < MAXCHANNELS; i++)
255         {
256                 char string2[BCTEXTLEN];
257                 sprintf(string, "CHANNEL_POSITIONS%d", i);
258                 print_channels(string2, 
259                         &channel_positions[i * MAXCHANNELS], 
260                         i + 1);
262                 defaults->get(string, string2);
263                 
264                 scan_channels(string2,
265                         &channel_positions[i * MAXCHANNELS], 
266                         i + 1);
267         }
269         brender_asset->load_defaults(defaults, 
270                 "BRENDER_", 
271                 1,
272                 1,
273                 1,
274                 0,
275                 0);
279         force_uniprocessor = defaults->get("FORCE_UNIPROCESSOR", 0);
280         use_brender = defaults->get("USE_BRENDER", use_brender);
281         brender_fragment = defaults->get("BRENDER_FRAGMENT", brender_fragment);
282         cache_size = defaults->get("CACHE_SIZE", cache_size);
283         local_rate = defaults->get("LOCAL_RATE", local_rate);
284         use_renderfarm = defaults->get("USE_RENDERFARM", use_renderfarm);
285         renderfarm_port = defaults->get("RENDERFARM_PORT", renderfarm_port);
286         render_preroll = defaults->get("RENDERFARM_PREROLL", render_preroll);
287         brender_preroll = defaults->get("BRENDER_PREROLL", brender_preroll);
288         renderfarm_job_count = defaults->get("RENDERFARM_JOBS_COUNT", renderfarm_job_count);
289         renderfarm_consolidate = defaults->get("RENDERFARM_CONSOLIDATE", renderfarm_consolidate);
290 //      renderfarm_vfs = defaults->get("RENDERFARM_VFS", renderfarm_vfs);
291         defaults->get("RENDERFARM_MOUNTPOINT", renderfarm_mountpoint);
292         int renderfarm_total = defaults->get("RENDERFARM_TOTAL", 0);
294         for(int i = 0; i < renderfarm_total; i++)
295         {
296                 sprintf(string, "RENDERFARM_NODE%d", i);
297                 char result[BCTEXTLEN];
298                 int result_port = 0;
299                 int result_enabled = 0;
300                 float result_rate = 0.0;
302                 result[0] = 0;
303                 defaults->get(string, result);
305                 sprintf(string, "RENDERFARM_PORT%d", i);
306                 result_port = defaults->get(string, renderfarm_port);
308                 sprintf(string, "RENDERFARM_ENABLED%d", i);
309                 result_enabled = defaults->get(string, result_enabled);
311                 sprintf(string, "RENDERFARM_RATE%d", i);
312                 result_rate = defaults->get(string, result_rate);
314                 if(result[0] != 0)
315                 {
316                         add_node(result, result_port, result_enabled, result_rate);
317                 }
318         }
320         boundaries();
322         return 0;
325 int Preferences::save_defaults(BC_Hash *defaults)
327         char string[BCTEXTLEN];
330         defaults->update("USE_TIPWINDOW", use_tipwindow);
332         defaults->update("CACHE_SIZE", cache_size);
333         defaults->update("INDEX_DIRECTORY", index_directory);
334         defaults->update("INDEX_SIZE", index_size);
335         defaults->update("INDEX_COUNT", index_count);
336         defaults->update("USE_THUMBNAILS", use_thumbnails);
337 //      defaults->update("GLOBAL_PLUGIN_DIR", global_plugin_dir);
338         defaults->update("THEME", theme);
341         for(int i = 0; i < MAXCHANNELS; i++)
342         {
343                 char string2[BCTEXTLEN];
344                 sprintf(string, "CHANNEL_POSITIONS%d", i);
345                 print_channels(string2, &channel_positions[i * MAXCHANNELS], i + 1);
346                 defaults->update(string, string2);
347         }
349         defaults->update("FORCE_UNIPROCESSOR", force_uniprocessor);
350         brender_asset->save_defaults(defaults, 
351                 "BRENDER_",
352                 1,
353                 1,
354                 1,
355                 0,
356                 0);
357         defaults->update("USE_BRENDER", use_brender);
358         defaults->update("BRENDER_FRAGMENT", brender_fragment);
359         defaults->update("USE_RENDERFARM", use_renderfarm);
360         defaults->update("LOCAL_RATE", local_rate);
361         defaults->update("RENDERFARM_PORT", renderfarm_port);
362         defaults->update("RENDERFARM_PREROLL", render_preroll);
363         defaults->update("BRENDER_PREROLL", brender_preroll);
364 //      defaults->update("RENDERFARM_VFS", renderfarm_vfs);
365         defaults->update("RENDERFARM_MOUNTPOINT", renderfarm_mountpoint);
366         defaults->update("RENDERFARM_JOBS_COUNT", renderfarm_job_count);
367         defaults->update("RENDERFARM_CONSOLIDATE", renderfarm_consolidate);
368         defaults->update("RENDERFARM_TOTAL", (int64_t)renderfarm_nodes.total);
369         for(int i = 0; i < renderfarm_nodes.total; i++)
370         {
371                 sprintf(string, "RENDERFARM_NODE%d", i);
372                 defaults->update(string, renderfarm_nodes.values[i]);
373                 sprintf(string, "RENDERFARM_PORT%d", i);
374                 defaults->update(string, renderfarm_ports.values[i]);
375                 sprintf(string, "RENDERFARM_ENABLED%d", i);
376                 defaults->update(string, renderfarm_enabled.values[i]);
377                 sprintf(string, "RENDERFARM_RATE%d", i);
378                 defaults->update(string, renderfarm_rate.values[i]);
379         }
380         return 0;
384 void Preferences::add_node(char *text, int port, int enabled, float rate)
386         if(text[0] == 0) return;
388         preferences_lock->lock("Preferences::add_node");
389         char *new_item = new char[strlen(text) + 1];
390         strcpy(new_item, text);
391         renderfarm_nodes.append(new_item);
392         renderfarm_nodes.set_array_delete();
393         renderfarm_ports.append(port);
394         renderfarm_enabled.append(enabled);
395         renderfarm_rate.append(rate);
396         preferences_lock->unlock();
399 void Preferences::delete_node(int number)
401         preferences_lock->lock("Preferences::delete_node");
402         if(number < renderfarm_nodes.total)
403         {
404                 delete [] renderfarm_nodes.values[number];
405                 renderfarm_nodes.remove_number(number);
406                 renderfarm_ports.remove_number(number);
407                 renderfarm_enabled.remove_number(number);
408                 renderfarm_rate.remove_number(number);
409         }
410         preferences_lock->unlock();
413 void Preferences::delete_nodes()
415         preferences_lock->lock("Preferences::delete_nodes");
416         for(int i = 0; i < renderfarm_nodes.total; i++)
417                 delete [] renderfarm_nodes.values[i];
418         renderfarm_nodes.remove_all();
419         renderfarm_ports.remove_all();
420         renderfarm_enabled.remove_all();
421         renderfarm_rate.remove_all();
422         preferences_lock->unlock();
425 void Preferences::reset_rates()
427         for(int i = 0; i < renderfarm_nodes.total; i++)
428         {
429                 renderfarm_rate.values[i] = 0.0;
430         }
431         local_rate = 0.0;
434 void Preferences::set_rate(float rate, int node)
436 //printf("Preferences::set_rate %f %d\n", rate, node);
437         if(node < 0)
438         {
439                 local_rate = rate;
440         }
441         else
442         {
443                 int total = 0;
444                 for(int i = 0; i < renderfarm_nodes.total; i++)
445                 {
446                         if(renderfarm_enabled.values[i]) total++;
447                         if(total == node + 1)
448                         {
449                                 renderfarm_rate.values[i] = rate;
450                                 return;
451                         }
452                 }
453         }
456 float Preferences::get_avg_rate(int use_master_node)
458         preferences_lock->lock("Preferences::get_avg_rate");
459         float total = 0.0;
460         if(renderfarm_rate.total)
461         {
462                 int enabled = 0;
463                 if(use_master_node)
464                 {
465                         if(EQUIV(local_rate, 0.0))
466                         {
467                                 preferences_lock->unlock();
468                                 return 0.0;
469                         }
470                         else
471                         {
472                                 enabled++;
473                                 total += local_rate;
474                         }
475                 }
477                 for(int i = 0; i < renderfarm_rate.total; i++)
478                 {
479                         if(renderfarm_enabled.values[i])
480                         {
481                                 enabled++;
482                                 total += renderfarm_rate.values[i];
483                                 if(EQUIV(renderfarm_rate.values[i], 0.0)) 
484                                 {
485                                         preferences_lock->unlock();
486                                         return 0.0;
487                                 }
488                         }
489                 }
491                 if(enabled)
492                         total /= enabled;
493                 else
494                         total = 0.0;
495         }
496         preferences_lock->unlock();
498         return total;
501 void Preferences::sort_nodes()
503         int done = 0;
505         while(!done)
506         {
507                 done = 1;
508                 for(int i = 0; i < renderfarm_nodes.total - 1; i++)
509                 {
510                         if(strcmp(renderfarm_nodes.values[i], renderfarm_nodes.values[i + 1]) > 0)
511                         {
512                                 char *temp = renderfarm_nodes.values[i];
513                                 int temp_port = renderfarm_ports.values[i];
515                                 renderfarm_nodes.values[i] = renderfarm_nodes.values[i + 1];
516                                 renderfarm_nodes.values[i + 1] = temp;
518                                 renderfarm_ports.values[i] = renderfarm_ports.values[i + 1];
519                                 renderfarm_ports.values[i + 1] = temp_port;
521                                 renderfarm_enabled.values[i] = renderfarm_enabled.values[i + 1];
522                                 renderfarm_enabled.values[i + 1] = temp_port;
524                                 renderfarm_rate.values[i] = renderfarm_rate.values[i + 1];
525                                 renderfarm_rate.values[i + 1] = temp_port;
526                                 done = 0;
527                         }
528                 }
529         }
532 void Preferences::edit_node(int number, 
533         char *new_text, 
534         int new_port, 
535         int new_enabled)
537         char *new_item = new char[strlen(new_text) + 1];
538         strcpy(new_item, new_text);
540         delete [] renderfarm_nodes.values[number];
541         renderfarm_nodes.values[number] = new_item;
542         renderfarm_ports.values[number] = new_port;
543         renderfarm_enabled.values[number] = new_enabled;
546 int Preferences::get_enabled_nodes()
548         int result = 0;
549         for(int i = 0; i < renderfarm_enabled.total; i++)
550                 if(renderfarm_enabled.values[i]) result++;
551         return result;
554 char* Preferences::get_node_hostname(int number)
556         int total = 0;
557         for(int i = 0; i < renderfarm_nodes.total; i++)
558         {
559                 if(renderfarm_enabled.values[i])
560                 {
561                         if(total == number)
562                                 return renderfarm_nodes.values[i];
563                         else
564                                 total++;
565                 }
566         }
567         return "";
570 int Preferences::get_node_port(int number)
572         int total = 0;
573         for(int i = 0; i < renderfarm_ports.total; i++)
574         {
575                 if(renderfarm_enabled.values[i])
576                 {
577                         if(total == number)
578                                 return renderfarm_ports.values[i];
579                         else
580                                 total++;
581                 }
582         }
583         return -1;
587 int Preferences::calculate_processors(int interactive)
589 /* Get processor count */
590         int result = 1;
591         FILE *proc;
593         if(force_uniprocessor && !interactive) return 1;
595         if(proc = fopen("/proc/cpuinfo", "r"))
596         {
597                 char string[BCTEXTLEN];
598                 while(!feof(proc))
599                 {
600                         fgets(string, BCTEXTLEN, proc);
601                         if(!strncasecmp(string, "processor", 9))
602                         {
603                                 char *ptr = strchr(string, ':');
604                                 if(ptr)
605                                 {
606                                         ptr++;
607                                         result = atol(ptr) + 1;
608                                 }
609                         }
610                         else
611                         if(!strncasecmp(string, "cpus detected", 13))
612                         {
613                                 char *ptr = strchr(string, ':');
614                                 if(ptr)
615                                 {
616                                         ptr++;
617                                         result = atol(ptr);
618                                 }
619                         }
620                 }
621                 fclose(proc);
622         }
624         return result;
641 //      Local Variables:
642 //      mode: C++
643 //      c-file-style: "linux"
644 //      End: