/*******************************************************************************
*                         Goggles Music Manager                                *
********************************************************************************
*           Copyright (C) 2006-2010 by Sander Jansen. All Rights Reserved      *
*                               ---                                            *
* This program is free software: you can redistribute it and/or modify         *
* it under the terms of the GNU General Public License as published by         *
* the Free Software Foundation, either version 3 of the License, or            *
* (at your option) any later version.                                          *
*                                                                              *
* This program is distributed in the hope that it will be useful,              *
* but WITHOUT ANY WARRANTY; without even the implied warranty of               *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                *
* GNU General Public License for more details.                                 *
*                                                                              *
* You should have received a copy of the GNU General Public License            *
* along with this program.  If not, see http://www.gnu.org/licenses.           *
********************************************************************************/
#include "gmdefs.h"
#include "icons.h"

#include <FXPNGIcon.h>
#include <xine.h>

#include "GMPlayer.h"
#include "GMWindow.h"
#include "GMTrackList.h"
#include "GMList.h"
#include "GMRemote.h"
#include "GMHeaderButton.h"
#include "GMSource.h"
#include "GMPlayerManager.h"
#include "GMDatabaseSource.h"
#include "GMTrackView.h"
#include "GMSourceView.h"
#include "GMAudioScrobbler.h"
#include "GMIconTheme.h"
#include "GMPreferencesDialog.h"
#include "GMApp.h"
#include "GMTrayIcon.h"
#include "GMImageView.h"
#include "GMFontDialog.h"

#define DEFAULT_ICON_DIRECTORY MAKESTR(DEFAULT_ICON_PATH)


ColorTheme::ColorTheme() {
  base      = FXApp::instance()->getBaseColor();
  border    = FXApp::instance()->getBorderColor();
  back      = FXApp::instance()->getBackColor();
  fore      = FXApp::instance()->getForeColor();
  selfore	  = FXApp::instance()->getSelforeColor();
  selback	  = FXApp::instance()->getSelbackColor();
  tipfore	  = FXApp::instance()->getTipforeColor();
  tipback	  = FXApp::instance()->getTipbackColor();
  menufore  = FXApp::instance()->getSelMenuTextColor();
  menuback  = FXApp::instance()->getSelMenuBackColor();
  shadow    = FXApp::instance()->getShadowColor();
  hilite    = FXApp::instance()->getHiliteColor();
  playfore  = GMPlayerManager::instance()->getPreferences().gui_playtext_color;
  playback  = GMPlayerManager::instance()->getPreferences().gui_play_color;
  sourcefore= GMPlayerManager::instance()->getPreferences().gui_sourceselecttext_color;
  sourceback= GMPlayerManager::instance()->getPreferences().gui_sourceselect_color;
  altback   = GMPlayerManager::instance()->getPreferences().gui_row_color;
  trayback  = GMPlayerManager::instance()->getPreferences().gui_tray_color;
  }

ColorTheme::ColorTheme(const FXchar * _name,FXColor _base,FXColor _border,FXColor _back,FXColor _altback,FXColor _fore,FXColor _selback,FXColor _selfore,FXColor _tipback,FXColor _tipfore,FXColor _psback,FXColor _psfore) :
  name(_name),
  base(_base),
  border(_border),
  back(_back),
  altback(_altback),
  fore(_fore),
  selback(_selback),
  selfore(_selfore),
  tipback(_tipback),
  tipfore(_tipfore),
  menuback(_selback),
  menufore(_selfore),
  sourcefore(_psfore),
  sourceback(_psback),
  playfore(_psfore),
  playback(_psback),
  hilite(makeHiliteColor(base)),
  shadow(makeShadowColor(base)),
  trayback(_base) {
  }


void ColorTheme::save() const {
  FXApp::instance()->setBaseColor(base);
  FXApp::instance()->setBorderColor(border);
  FXApp::instance()->setBackColor(back);
  FXApp::instance()->setForeColor(fore);
  FXApp::instance()->setSelbackColor(selback);
  FXApp::instance()->setSelforeColor(selfore);
  FXApp::instance()->setTipbackColor(tipback);
  FXApp::instance()->setTipforeColor(tipfore);
  FXApp::instance()->setSelMenuBackColor(menuback);
  FXApp::instance()->setSelMenuTextColor(menufore);
  FXApp::instance()->setShadowColor(shadow);
  FXApp::instance()->setHiliteColor(hilite);
  GMPlayerManager::instance()->getPreferences().gui_playtext_color=playfore;
  GMPlayerManager::instance()->getPreferences().gui_play_color=playback;
  GMPlayerManager::instance()->getPreferences().gui_sourceselecttext_color=sourcefore;
  GMPlayerManager::instance()->getPreferences().gui_sourceselect_color=sourceback;
  GMPlayerManager::instance()->getPreferences().gui_row_color=altback;
  GMPlayerManager::instance()->getPreferences().gui_tray_color=trayback;

  }

bool operator==(const ColorTheme& t1,const ColorTheme& t2) {
  return (t1.base==t2.base &&
      t1.border==t2.border &&
      t1.back==t2.back &&
      t1.altback==t2.altback &&
      t1.fore==t2.fore &&
      t1.selback==t2.selback &&
      t1.selfore==t2.selfore &&
      t1.tipback==t2.tipback &&
      t1.tipfore==t2.tipfore &&
      t1.menuback==t2.menuback &&
      t1.menufore==t2.menufore &&
      t1.sourcefore==t2.sourcefore &&
      t1.sourceback==t2.sourceback &&
      t1.playfore==t2.playfore &&
      t1.playback==t2.playback &&
      t1.hilite==t2.hilite &&
      t1.shadow==t2.shadow //&&
//      t1.trayback==t2.trayback
      );
  }


/// Think you have a great color theme, mail them to s.jansen@gmail.com
const ColorTheme ColorThemes[]={
  ColorTheme("FOX", // name
             FXRGB(212,208,200), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB(255,255,255), // back
             FXRGB(240,240,240), // alt back
             FXRGB(  0,  0,  0), // fore
             FXRGB( 10, 36,106), // selback
             FXRGB(255,255,255), // selfore
             FXRGB(255,255,225), // tipback
             FXRGB(0,0,0)), // tipfore

  ColorTheme("Clearlooks"     , // name
             FXRGB(237,236,235), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB(255,255,255), // back
             FXRGB(240,240,240), // alt back
             FXRGB( 26, 26, 25), // fore
             FXRGB(134,171,217), // selback
             FXRGB(255,255,255), // selfore
             FXRGB(245,245,181), // tipback
             FXRGB(  0,  0,  0)),   // tipfore

  ColorTheme("Honeycomb"       , // name
             FXRGB(213,215,209), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB(255,255,255), // back
             FXRGB(238,238,238), // alt back
             FXRGB( 0, 0, 0), // fore
             FXRGB(227,167,  0), // selback
             FXRGB(255,255,255), // selfore
             FXRGB(255,242,153), // tipback
             FXRGB( 64, 48, 0)), // tipfore

  ColorTheme("Norway"          , // name
             FXRGB(235,226,210), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB(253,252,251), // back
             FXRGB(238,238,238), // alt back
             FXRGB(  0,  0,  0), // fore
             FXRGB( 29,135,205), // selback
             FXRGB(255,255,255), // selfore
             FXRGB(253,252,251), // tipback
             FXRGB(  0,  0,  0)),   // tipfore

  ColorTheme("Oxygen"          , // name
             FXRGB(224,223,223), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB(255,255,255), // back
             FXRGB(238,238,238), // alt back
             FXRGB( 20, 19, 18), // fore
             FXRGB( 65,141,212), // selback
             FXRGB(255,255,255), // selfore
             FXRGB(192,218,255), // tipback
             FXRGB( 20, 19, 18)), // tipfore

  ColorTheme("Obsidian Coast" ,  // name
             FXRGB( 48, 47, 47), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB( 32, 31, 31), // back
             FXRGB( 38, 38, 38), // alt back
             FXRGB(224,223,220), // fore
             FXRGB(  24,72,128), // selback
             FXRGB(255,255,255), // selfore
             FXRGB( 16, 48, 80), // tipback
             FXRGB(196,209,224),// tipfore
             FXRGB(24,128,73), // psback
             FXRGB(224,223,220)), // psfore

  ColorTheme("Steel"       , // name
             FXRGB(224,223,216), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB(255,255,255), // back
             FXRGB(238,238,238), // alt back
             FXRGB( 0, 0, 0), // fore
             FXRGB(123,161,173), // selback
             FXRGB(255,255,255), // selfore
             FXRGB(220,231,235), // tipback
             FXRGB( 37, 34, 28)), // tipfore

  ColorTheme("Wonton Soup"     , // name
             FXRGB (71, 76, 86), // base
             FXRGB(  0,  0,  0), // boder
             FXRGB( 58, 62, 70), // back
             FXRGB( 62, 66, 75), // alt back
             FXRGB(182,193,208), // fore
             FXRGB(117,133,153), // selback
             FXRGB(209,225,244), // selfore
             FXRGB(182,193,208), // tipback
             FXRGB(42,44,48),		 // tipfore
             FXRGB(134,147,134), // psback
             FXRGB(209,225,244)),// psfore
  };



FXDEFMAP(GMPreferencesDialog) GMPreferencesDialogMap[]={
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_LASTFM_SCROBBLE,GMPreferencesDialog::onCmdLastFMScrobble),
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_LASTFM_USERNAME,GMPreferencesDialog::onCmdLastFMUserName),
  FXMAPFUNC(SEL_CHANGED,GMPreferencesDialog::ID_LASTFM_USERNAME,GMPreferencesDialog::onCmdLastFMUserName),
  FXMAPFUNC(SEL_FOCUSIN,GMPreferencesDialog::ID_LASTFM_PASSWORD,GMPreferencesDialog::onFocusLastFMPassWord),
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_LASTFM_PASSWORD,GMPreferencesDialog::onCmdLastFMPassWord),
  FXMAPFUNCS(SEL_COMMAND,GMPreferencesDialog::ID_BASE_COLOR,GMPreferencesDialog::ID_BORDER_COLOR,GMPreferencesDialog::onCmdElementColor),
  FXMAPFUNCS(SEL_UPDATE,GMPreferencesDialog::ID_BASE_COLOR,GMPreferencesDialog::ID_BORDER_COLOR,GMPreferencesDialog::onUpdElementColor),
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_COLOR_THEME,GMPreferencesDialog::onCmdColorTheme),
  FXMAPFUNC(SEL_UPDATE,GMPreferencesDialog::ID_COLOR_THEME,GMPreferencesDialog::onUpdColorTheme),
  FXMAPFUNC(SEL_UPDATE,GMPreferencesDialog::ID_FONT,GMPreferencesDialog::onUpdFont),
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_CHANGE_FONT,GMPreferencesDialog::onCmdChangeFont),
  FXMAPFUNC(SEL_COMMAND,FXDialogBox::ID_ACCEPT,GMPreferencesDialog::onCmdAccept),
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_AUDIO_DRIVER,GMPreferencesDialog::onCmdAudioDriver),
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_REPLAY_GAIN,GMPreferencesDialog::onCmdReplayGain),
  FXMAPFUNC(SEL_COMMAND,GMPreferencesDialog::ID_ICON_THEME,GMPreferencesDialog::onCmdIconTheme)
  };

FXIMPLEMENT(GMPreferencesDialog,FXDialogBox,GMPreferencesDialogMap,ARRAYNUMBER(GMPreferencesDialogMap))

GMPreferencesDialog::GMPreferencesDialog(FXWindow * p) : FXDialogBox(p,FXString::null,DECOR_BORDER|DECOR_TITLE,0,0,0,0,0,0,0,0,0,0),
  password_set(false) {

  setTitle(tr("Preferences"));

  target_alwaysremote.connect(GMPlayerManager::instance()->getPreferences().gui_always_show_remote);
  target_closeishide.connect(GMPlayerManager::instance()->getPreferences().gui_hide_player_when_close);
  target_keywords.connect(keywords);

  target_close_audio.connect(GMPlayerManager::instance()->getPreferences().play_close_stream);
  target_pause_close_device.connect(GMPlayerManager::instance()->getPreferences().play_pause_close_device);
  target_gapless.connect(GMPlayerManager::instance()->getPreferences().play_gapless);
  target_open_device_on_startup.connect(GMPlayerManager::instance()->getPreferences().play_open_device_on_startup);
  target_show_playing_albumcover.connect(GMPlayerManager::instance()->getPreferences().gui_show_playing_albumcover);
  target_show_albumcovers.connect(GMPlayerManager::instance()->getPreferences().gui_show_albumcovers);
#ifdef HAVE_DBUS
  target_dbus_notify_daemon.connect(GMPlayerManager::instance()->getPreferences().dbus_notify_daemon);
#endif
  target_gui_tray_icon.connect(GMPlayerManager::instance()->getPreferences().gui_tray_icon);
  target_replaygain.connect(GMPlayerManager::instance()->getPreferences().play_replaygain,this,ID_REPLAY_GAIN);
  target_gui_format_title.connect(GMPlayerManager::instance()->getPreferences().gui_format_title);
  target_gui_show_playing_titlebar.connect(GMPlayerManager::instance()->getPreferences().gui_show_playing_titlebar);

  GMPlayerManager::instance()->getPlayer()->checkInitialized();
  GMPlayerManager::instance()->getPreferences().getKeyWords(keywords);

  const FXuint labelstyle=LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT;
  const FXuint textfieldstyle=TEXTFIELD_ENTER_ONLY|LAYOUT_FILL_X|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FILL_COLUMN;

  FXGroupBox * grpbox;
  FXMatrix   * matrix;
  FXVerticalFrame * vframe;
  FXVerticalFrame * vframe2;

  icon_lastfm = new FXPNGIcon(getApp(),x20_lastfm_png);
  icon_lastfm->blend(getApp()->getBaseColor());

  FXVerticalFrame * main=new FXVerticalFrame(this,LAYOUT_FILL_X|LAYOUT_FILL_Y);
  FXTabBook * tabbook=new FXTabBook(main,NULL,0,LAYOUT_FILL_X|LAYOUT_FILL_Y|LAYOUT_RIGHT,0,0,0,0,0,0,0,0);


  new FXTabItem(tabbook,tr("&General"),NULL,TAB_TOP_NORMAL,0,0,0,0,5,5);
  vframe = new FXVerticalFrame(tabbook,FRAME_THICK|FRAME_RAISED);

  grpbox =  new FXGroupBox(vframe,tr("Sort Options"),FRAME_GROOVE|LAYOUT_FILL_X);
  matrix = new FXMatrix(grpbox,2,MATRIX_BY_COLUMNS|LAYOUT_FILL_X,0,0,0,0,0,0,0,0);
  new FXLabel(matrix,tr("Ignore leading words"),NULL,labelstyle);
  new FXTextField(matrix,10,&target_keywords,FXDataTarget::ID_VALUE,textfieldstyle);

  grpbox =  new FXGroupBox(vframe,tr("Album Covers"),FRAME_GROOVE|LAYOUT_FILL_X);
  new FXCheckButton(grpbox,tr("Show album cover of playing track\tShow album cover of playing track"),&target_show_playing_albumcover,FXDataTarget::ID_VALUE);
  new FXCheckButton(grpbox,tr("Show album covers in album browser\tShow album covers in album browser"),&target_show_albumcovers,FXDataTarget::ID_VALUE);

  grpbox =  new FXGroupBox(vframe,tr("System Tray"),FRAME_GROOVE|LAYOUT_FILL_X);
  new FXCheckButton(grpbox,tr("Show Tray Icon\tShow tray icon in the system tray."),&target_gui_tray_icon,FXDataTarget::ID_VALUE);
#ifdef HAVE_DBUS
  if (GMPlayerManager::instance()->hasSessionBus()) {
    new FXCheckButton(grpbox,tr("Show Track Change Notifications\tInform notification daemon of track changes."),&target_dbus_notify_daemon,FXDataTarget::ID_VALUE);
    }
#endif

  grpbox =  new FXGroupBox(vframe,tr("Last.fm"),FRAME_GROOVE|LAYOUT_FILL_X,0,0,0,0,3,3,0,0,0,0);
  vframe2 = new FXVerticalFrame(grpbox,LAYOUT_SIDE_RIGHT|PACK_UNIFORM_WIDTH,0,0,0,0,3,3,0,3,0,0);

  new FXLabel(vframe2,FXString::null,icon_lastfm,JUSTIFY_LEFT,0,0,0,0,8,0,0,0);
  FXButton * linkbutton = new FXButton(vframe2,tr("&Sign up for last.fm…"),NULL,GMPlayerManager::instance()->getMainWindow(),GMWindow::ID_JOIN_LASTFM,ICON_AFTER_TEXT|FRAME_RAISED|JUSTIFY_CENTER_Y|JUSTIFY_LEFT|BUTTON_TOOLBAR,0,0,0,0,7);
  linkbutton->setTextColor(FXRGB(0,0,255));
  linkbutton->setDefaultCursor(GMIconTheme::instance()->cursor_hand);
  linkbutton = new FXButton(vframe2,tr("&Join GMM on last.fm…\tJoin the Goggles Music Manager group on last.fm…\tJoin the Goggles Music Manager group on last.fm…"),NULL,GMPlayerManager::instance()->getMainWindow(),GMWindow::ID_JOIN_GMM_LASTFM,ICON_AFTER_TEXT|FRAME_RAISED|JUSTIFY_CENTER_Y|JUSTIFY_LEFT|BUTTON_TOOLBAR,0,0,0,0,7);
  linkbutton->setTextColor(FXRGB(0,0,255));
  linkbutton->setDefaultCursor(GMIconTheme::instance()->cursor_hand);
  if (GMPlayerManager::instance()->getAudioScrobbler()->isBanned()) {
    new FXLabel(grpbox,tr("This version of Goggles Music Manager is\n"
                       "not supported by Last-FM. Please upgrade\n"
                       "to a newer version of GMM."),NULL,JUSTIFY_LEFT);
    }
  else {
    matrix = new FXMatrix(grpbox,2,MATRIX_BY_COLUMNS|LAYOUT_FILL_X,0,0,0,0);
    new FXLabel(matrix,tr("Username:"),NULL,labelstyle);
    lastfm_username = new FXTextField(matrix,20,this,ID_LASTFM_USERNAME,FRAME_SUNKEN|FRAME_THICK);
    new FXLabel(matrix,tr("Password:"),NULL,labelstyle);
    lastfm_password = new FXTextField(matrix,20,this,ID_LASTFM_PASSWORD,FRAME_SUNKEN|FRAME_THICK|TEXTFIELD_PASSWD);
    new FXFrame(matrix,FRAME_NONE);
    lastfm_scrobble = new FXCheckButton(grpbox,tr("Last.fm"),this,ID_LASTFM_SCROBBLE,LAYOUT_FIX_X|LAYOUT_FIX_Y|CHECKBUTTON_NORMAL,6,0);

    lastfm_username->setText(GMPlayerManager::instance()->getAudioScrobbler()->getUsername());
    if (GMPlayerManager::instance()->getAudioScrobbler()->hasPassword())
      lastfm_password->setText("1234567890");

    lastfm_scrobble->setCheck(GMPlayerManager::instance()->getAudioScrobbler()->isEnabled());
    }


  new FXTabItem(tabbook,tr("&Window"),NULL,TAB_TOP_NORMAL,0,0,0,0,5,5);
  vframe = new FXVerticalFrame(tabbook,FRAME_THICK|FRAME_RAISED);

  grpbox =  new FXGroupBox(vframe,tr("Window"),FRAME_GROOVE|LAYOUT_FILL_X);
  new FXCheckButton(grpbox,tr("Always Show Remote"),&target_alwaysremote,FXDataTarget::ID_VALUE);
  new FXCheckButton(grpbox,tr("Close button hides Main Window"),&target_closeishide,FXDataTarget::ID_VALUE);
  statusbarbutton = new FXCheckButton(grpbox,tr("Show Status Bar"),NULL,0);
  statusbarbutton->setCheck(GMPlayerManager::instance()->getPreferences().gui_show_status_bar);
  browser_icons = new FXCheckButton(grpbox,tr("Show Icons in Track Browser"),NULL,0);
  browser_icons->setCheck(GMPlayerManager::instance()->getPreferences().gui_show_browser_icons);
  new FXCheckButton(grpbox,tr("Display playing track in title bar"),&target_gui_show_playing_titlebar,FXDataTarget::ID_VALUE);

  grpbox =  new FXGroupBox(vframe,tr("Player Controls"),FRAME_GROOVE|LAYOUT_FILL_X);
  matrix = new FXMatrix(grpbox,2,MATRIX_BY_COLUMNS);
  new FXLabel(matrix,tr("Location:"),NULL,labelstyle);
  toolbar_docktop = new GMListBox(matrix,NULL,0,FRAME_SUNKEN|FRAME_THICK|LAYOUT_FILL_COLUMN|LAYOUT_FILL_X);
  toolbar_docktop->appendItem(tr("Top"));
  toolbar_docktop->appendItem(tr("Bottom"));
  toolbar_docktop->setNumVisible(2);

  if (GMPlayerManager::instance()->getPreferences().gui_toolbar_docktop)
    toolbar_docktop->setCurrentItem(0);
  else
    toolbar_docktop->setCurrentItem(1);

  new FXLabel(matrix,tr("Title Format:"),NULL,labelstyle);
  new FXTextField(matrix,20,&target_gui_format_title,FXDataTarget::ID_VALUE,TEXTFIELD_NORMAL|LAYOUT_FILL_COLUMN|LAYOUT_FILL_X);


  new FXLabel(matrix,tr("Style:"),NULL,labelstyle);
  toolbar_showlabels = new FXCheckButton(matrix,tr("Show Labels"),NULL,0);
  toolbar_showlabels->setCheck(GMPlayerManager::instance()->getPreferences().gui_toolbar_showlabels);
  new FXFrame(matrix,FRAME_NONE);
  toolbar_bigicons = new FXCheckButton(matrix,tr("Large Icons"),NULL,0);
  toolbar_bigicons->setCheck(GMPlayerManager::instance()->getPreferences().gui_toolbar_bigicons);


  new FXTabItem(tabbook,tr("A&ppearance"),NULL,TAB_TOP_NORMAL,0,0,0,0,5,5);
  vframe = new FXVerticalFrame(tabbook,FRAME_THICK|FRAME_RAISED);
  grpbox =  new FXGroupBox(vframe,tr("Colors"),FRAME_GROOVE|LAYOUT_FILL_X,0,0,0,0,2,2,0,2);

  matrix = new FXMatrix(grpbox,6,MATRIX_BY_COLUMNS|LAYOUT_SIDE_LEFT,0,0,0,0,0,0,0,0,0,0);

  new FXFrame(matrix,FRAME_NONE);
  new FXLabel(matrix,tr("fg\tForeground Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_CENTER_X);
  new FXLabel(matrix,tr("bg\tBackground Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_CENTER_X);
  new FXLabel(matrix,tr("alt bg\tAlternative Background Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_CENTER_X);
  new FXFrame(matrix,FRAME_NONE);
  new FXFrame(matrix,FRAME_NONE);

  new FXFrame(matrix,FRAME_NONE);
  new FXSeparator(matrix,SEPARATOR_LINE|LAYOUT_FILL_X);
  new FXSeparator(matrix,SEPARATOR_LINE|LAYOUT_FILL_X);
  new FXSeparator(matrix,SEPARATOR_LINE|LAYOUT_FILL_X);
  new FXFrame(matrix,FRAME_NONE);
  new FXFrame(matrix,FRAME_NONE);

  new FXLabel(matrix,tr("Normal\tNormal Text Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_FORE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXColorWell(matrix,0,this,ID_BACK_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXColorWell(matrix,0,this,ID_ALTERNATIVE_BACK_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXLabel(matrix,tr("Base\tBase Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_BASE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);

  new FXLabel(matrix,tr("Selected\tSelected Text Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_SEL_FORE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXColorWell(matrix,0,this,ID_SEL_BACK_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXFrame(matrix,FRAME_NONE);
  new FXLabel(matrix,tr("Border\tBorder Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_BORDER_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);

  new FXLabel(matrix,tr("Menu\tMenu Text Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_MENU_FORE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXColorWell(matrix,0,this,ID_MENU_BACK_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXFrame(matrix,FRAME_NONE);
  new FXLabel(matrix,tr("Hilite\tHilite Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_HILITE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);

  new FXLabel(matrix,tr("Tooltip\tTooltip Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_TIP_FORE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXColorWell(matrix,0,this,ID_TIP_BACK_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXFrame(matrix,FRAME_NONE);
  new FXLabel(matrix,tr("Shadow\tShadow Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_SHADOW_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);


  new FXLabel(matrix,tr("Source\tActive Source Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_SOURCE_FORE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXColorWell(matrix,0,this,ID_SOURCE_BACK_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXFrame(matrix,FRAME_NONE);
  new FXLabel(matrix,tr("Tray\tTray Background Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_TRAY_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);

  new FXLabel(matrix,tr("Playing\tPlaying Track Color"),NULL,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_RIGHT);
  new FXColorWell(matrix,0,this,ID_PLAY_FORE_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXColorWell(matrix,0,this,ID_PLAY_BACK_COLOR,COLORWELL_OPAQUEONLY|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FIX_WIDTH|LAYOUT_FIX_HEIGHT|LAYOUT_FILL_ROW|LAYOUT_CENTER_Y,0,0,40,24);
  new FXFrame(matrix,FRAME_NONE);
  new FXFrame(matrix,FRAME_NONE);
  new FXFrame(matrix,FRAME_NONE);

  new FXSeparator(grpbox,SEPARATOR_GROOVE|LAYOUT_FILL_Y|LAYOUT_SIDE_LEFT);

  vframe2 = new FXVerticalFrame(grpbox,LAYOUT_SIDE_RIGHT|LAYOUT_FILL_X|LAYOUT_FILL_Y,0,0,0,0,0,0,0,0,0,0);
  new FXLabel(vframe2,tr("Presets:"));
  FXVerticalFrame * sunken = new FXVerticalFrame(vframe2,LAYOUT_SIDE_RIGHT|FRAME_SUNKEN|FRAME_THICK|LAYOUT_FILL_X|LAYOUT_FILL_Y,0,0,0,0,0,0,0,0);
  colorpresets = new FXList(sunken,this,ID_COLOR_THEME,LIST_BROWSESELECT|LAYOUT_FILL_X|LAYOUT_FILL_Y);
  colorpresets->setNumVisible(9);

  initColorThemes();

  grpbox =  new FXGroupBox(vframe,tr("Fonts & Icons"),FRAME_GROOVE|LAYOUT_FILL_X,0,0,0,0);


  matrix = new FXMatrix(grpbox,3,MATRIX_BY_COLUMNS|LAYOUT_FILL_X,0,0,0,0,20);

  new FXLabel(matrix,tr("Default Font"),NULL,LAYOUT_RIGHT|LAYOUT_CENTER_Y);
  new FXTextField(matrix,20,this,ID_FONT,LAYOUT_CENTER_Y|LABEL_NORMAL|LAYOUT_FILL_X|LAYOUT_FILL_COLUMN|TEXTFIELD_NORMAL|TEXTFIELD_READONLY);
  new FXButton(matrix,tr("Change…"),NULL,this,ID_CHANGE_FONT,BUTTON_NORMAL|LAYOUT_CENTER_Y);

/*
  new FXLabel(matrix,tr("Display DPI"),NULL,LAYOUT_RIGHT|LAYOUT_CENTER_Y);
  FXSpinner * dpi_spinner = new FXSpinner(matrix,4,this,ID_DISPLAY_DPI,LAYOUT_FILL_COLUMN);
  dpi_spinner->setValue(dpi);
  dpi_spinner->setRange(72,200);
  new FXFrame(matrix,FRAME_NONE);
*/
  new FXLabel(matrix,tr("Icons"),NULL,LAYOUT_RIGHT|LAYOUT_CENTER_Y);

  if (GMIconTheme::instance()->getNumThemes()==0)
    GMIconTheme::instance()->listThemes();

  themelist = new GMListBox(matrix,this,ID_ICON_THEME,FRAME_SUNKEN|FRAME_THICK|LAYOUT_FILL_COLUMN|LAYOUT_FILL_X);
    for (FXint i=0;i<GMIconTheme::instance()->getNumThemes();i++) {
      themelist->appendItem(GMIconTheme::instance()->getThemeName(i),NULL,(void*)(FXival)i);
      }
  themelist->setSortFunc(FXList::ascending);
  themelist->sortItems();
  themelist->setNumVisible(FXMIN(9,themelist->getNumItems()));
  for (FXint i=0;i<themelist->getNumItems();i++) {
    if (GMIconTheme::instance()->getCurrentTheme()==(FXint)(FXival)themelist->getItemData(i)) {
      themelist->setCurrentItem(i);
      break;
      }
    }

  new FXTabItem(tabbook,tr("&Audio"),NULL,TAB_TOP_NORMAL,0,0,0,0,5,5);
  vframe = new FXVerticalFrame(tabbook,FRAME_THICK|FRAME_RAISED);

  grpbox =  new FXGroupBox(vframe,tr("Engine"),FRAME_GROOVE|LAYOUT_FILL_X);
  matrix = new FXMatrix(grpbox,2,MATRIX_BY_COLUMNS|LAYOUT_SIDE_TOP,0,0,0,0,0,0,0,0);
  new FXLabel(matrix,tr("Audio Driver:"),NULL,labelstyle);

  driverlist = new GMListBox(matrix,this,ID_AUDIO_DRIVER);
  FXString available,current;
  GMPlayerManager::instance()->getPlayer()->getAvailableDrivers(available);
  GMPlayerManager::instance()->getPlayer()->getCurrentDriver(current);
  driverlist->clearItems();
  driverlist->fillItems(available);
  driverlist->setCurrentItem(driverlist->findItem(current));
  driverlist->setNumVisible(FXMIN(9,driverlist->getNumItems()));

  new FXCheckButton(grpbox,tr("Close audio device on pause."),&target_pause_close_device,FXDataTarget::ID_VALUE);
  new FXCheckButton(grpbox,tr("Turn off playback engine on stop."),&target_close_audio,FXDataTarget::ID_VALUE);
  new FXCheckButton(grpbox,tr("Turn on playback engine on startup.\tFor faster startup, playback engine is normally started when first track is played.\tFor faster startup, playback engine is normally started when first track is played."),&target_open_device_on_startup,FXDataTarget::ID_VALUE);


  grpbox =  new FXGroupBox(vframe,tr("Playback"),FRAME_GROOVE|LAYOUT_FILL_X);
  matrix = new FXMatrix(grpbox,2,MATRIX_BY_COLUMNS|LAYOUT_SIDE_TOP,0,0,0,0,0,0,0,0);

  new FXLabel(matrix,tr("Replay Gain:"),NULL,labelstyle);
  GMListBox * gainlist = new GMListBox(matrix,&target_replaygain,FXDataTarget::ID_VALUE);
  gainlist->appendItem(tr("Off"));
  gainlist->appendItem(tr("Track"));
  gainlist->appendItem(tr("Album"));
  gainlist->setNumVisible(3);

  new FXCheckButton(grpbox,tr("Gapless playback"),&target_gapless,FXDataTarget::ID_VALUE);
  check_audio_normalization = new FXCheckButton(grpbox,tr("Volume Normalization"));


  if (GMPlayerManager::instance()->getPlayer()->hasVolumeNormalization() && GMPlayerManager::instance()->getPlayer()->getVolumeNormalization())
    check_audio_normalization->setCheck(true);

  FXHorizontalFrame *closebox=new FXHorizontalFrame(main,LAYOUT_BOTTOM|LAYOUT_FILL_X|PACK_UNIFORM_WIDTH,0,0,0,0,0,0,0,0);
  new FXButton(closebox,tr("&Close"),NULL,this,FXDialogBox::ID_ACCEPT,BUTTON_INITIAL|BUTTON_DEFAULT|LAYOUT_RIGHT|FRAME_RAISED|FRAME_THICK,0,0,0,0, 20,20);

  }

GMPreferencesDialog::~GMPreferencesDialog(){
  }


long GMPreferencesDialog::onCmdAudioDriver(FXObject*,FXSelector,void*){
  FXString selected=driverlist->getItemText(driverlist->getCurrentItem());
  FXString current;
  FXString available;

  /// Stop Playback
  GMPlayerManager::instance()->stop();

  if (!GMPlayerManager::instance()->getPlayer()->changeDriver(selected)) {

      //FXMessageBox::error(this,MBOX_OK,"Audio Device Error","Failed to open requested audio driver: %s",selected.text());


    driverlist->disable();
    }
  else {
    GMPlayerManager::instance()->getPlayer()->getCurrentDriver(current);
    if (selected!=current) {
      FXMessageBox::error(this,MBOX_OK,tr("Audio Device Error"),fxtrformat("Failed to open requested audio driver: %s"),selected.text());
      }
    GMPlayerManager::instance()->getPlayer()->getAvailableDrivers(available);
    driverlist->clearItems();
    driverlist->fillItems(available);
    driverlist->setCurrentItem(driverlist->findItem(current));
    driverlist->setNumVisible(FXMIN(9,driverlist->getNumItems()));
    }
  return 1;
  }

long GMPreferencesDialog::onCmdReplayGain(FXObject*,FXSelector,void*){
  GMPlayerManager::instance()->update_replay_gain();
  return 1;
  }



long GMPreferencesDialog::onCmdAccept(FXObject*,FXSelector,void*) {
  getApp()->stopModal(this,TRUE);
  hide();

  GMWindow * mainwindow = GMPlayerManager::instance()->getMainWindow();

  if (!GMPlayerManager::instance()->getAudioScrobbler()->isBanned() && password_set) {
    GMPlayerManager::instance()->getAudioScrobbler()->login(lastfm_username->getText(),lastfm_password->getText());
    }

  GMPlayerManager::instance()->getPreferences().setKeyWords(keywords);

  if (check_audio_normalization->getCheck()) {
    GMPlayerManager::instance()->getPlayer()->setVolumeNormalization(true);
    }
  else {
    GMPlayerManager::instance()->getPlayer()->setVolumeNormalization(false);
    }
  GMPlayerManager::instance()->getPlayer()->setupGapless();

  if (browser_icons->getCheck()!=GMPlayerManager::instance()->getPreferences().gui_show_browser_icons){
    GMPlayerManager::instance()->getPreferences().gui_show_browser_icons=browser_icons->getCheck();
    mainwindow->getTrackView()->updateIcons();
    }

  if (!(selected==current)) {
    GMIconTheme::instance()->load();
    redraw();
    }

  mainwindow->configureToolbar((toolbar_docktop->getCurrentItem()==0),toolbar_showlabels->getCheck(),toolbar_bigicons->getCheck());
  mainwindow->configureStatusbar(statusbarbutton->getCheck());

  if (GMPlayerManager::instance()->getPreferences().gui_always_show_remote)
    GMPlayerManager::instance()->showRemote();
  else
    GMPlayerManager::instance()->hideRemote();

  if (GMPlayerManager::instance()->getPreferences().gui_show_playing_albumcover) {
    if (GMPlayerManager::instance()->playing())
      GMPlayerManager::instance()->update_track_display(false);
    }
  else {
    mainwindow->loadCover(FXString::null);
    }

  GMPlayerManager::instance()->update_tray_icon();

  // Key Words may have changed.
  mainwindow->getTrackView()->resort();
  mainwindow->getSourceView()->resort();
  return 1;
  }




void GMPreferencesDialog::initColorThemes() {
  for(FXuint i=0;i<ARRAYNUMBER(ColorThemes);i++){
    colorpresets->appendItem(ColorThemes[i].name,NULL,(void*)&ColorThemes[i]);
    }

  theme=-1;
  for(FXuint i=0;i<ARRAYNUMBER(ColorThemes);i++){
    if (current==ColorThemes[i]){
      theme=i;
      break;
      }
    }

  if (theme==-1){
    colorpresets->prependItem(tr("Current"),NULL,(void*)&current);
    theme=0;
    }
  }


void GMPreferencesDialog::updateColorThemes() {
  theme=-1;

  for (FXint i=0;i<colorpresets->getNumItems();i++){
    if (selected==*(ColorTheme*)colorpresets->getItemData(i)){
      theme=i;
      return;
      }
    }

  if (theme==-1) {
    theme=colorpresets->getNumItems();
    colorpresets->appendItem(tr("Custom"),NULL,(void*)&selected);
    }
  else if (theme<colorpresets->getNumItems()-1) {
    if (colorpresets->getItemData(colorpresets->getNumItems()-1)==&selected)
      colorpresets->removeItem(colorpresets->getNumItems()-1);
    }
  }


long GMPreferencesDialog::onCmdIconTheme(FXObject*,FXSelector,void*){
  GMIconTheme::instance()->setCurrentTheme((FXint)(FXival)themelist->getItemData(themelist->getCurrentItem()));
  GMIconTheme::instance()->load();
  redraw();
  return 1;
  }


long GMPreferencesDialog::onCmdLastFMScrobble(FXObject*,FXSelector,void*){
  if (lastfm_scrobble->getCheck())
    GMPlayerManager::instance()->getAudioScrobbler()->enable();
  else
    GMPlayerManager::instance()->getAudioScrobbler()->disable();
  return 1;
  }


long GMPreferencesDialog::onCmdLastFMPassWord(FXObject*,FXSelector,void*){
//  fxmessage("onCmdLastFMPassWord %d\n",password_set);
  if (!GMPlayerManager::instance()->getAudioScrobbler()->isBanned() && password_set) {
    lastfm_scrobble->setCheck(true);
    GMPlayerManager::instance()->getAudioScrobbler()->login(lastfm_username->getText(),lastfm_password->getText());
    }
  return 1;
  }

long GMPreferencesDialog::onFocusLastFMPassWord(FXObject*,FXSelector,void*){
//  fxmessage("onFocusLastFMPassWord %d\n",password_set);
  if (password_set==false) {
    password_set=true;
    lastfm_password->setText(FXString::null,false);
    }
  return 0;
  }

long GMPreferencesDialog::onCmdLastFMUserName(FXObject*,FXSelector sel,void*){
 // if (GMPlayerManager::instance()->getAudioScrobbler()->getUsername()!=lastfm_username->getText()){
    lastfm_password->setText(FXString::null,false);
    password_set=true;
    if (FXSELTYPE(sel)==SEL_COMMAND) lastfm_password->setFocus();
 //   }
  return 1;
  }


long GMPreferencesDialog::onCmdElementColor(FXObject*,FXSelector sel,void* rgba) {
  FXColor color = (FXColor)(FXuval)rgba;

  switch(FXSELID(sel)){
    case ID_BASE_COLOR : selected.base = color;
                         selected.shadow = makeShadowColor(selected.base);
                         selected.hilite = makeHiliteColor(selected.base);
                         break;
   case ID_BORDER_COLOR : selected.border = color; break;
   case ID_BACK_COLOR   : selected.back = color; break;
    case ID_FORE_COLOR  : selected.fore = color; break;
    case ID_SHADOW_COLOR : selected.shadow=color; break;
    case ID_HILITE_COLOR : selected.hilite=color; break;


    case ID_SEL_BACK_COLOR: selected.selback=color; break;
    case ID_SEL_FORE_COLOR: selected.selfore=color; break;
    case ID_MENU_BACK_COLOR: selected.menuback=color; break;
    case ID_MENU_FORE_COLOR: selected.menufore=color; break;
    case ID_TIP_BACK_COLOR: selected.tipback=color; break;
    case ID_TIP_FORE_COLOR: selected.tipfore=color; break;
    case ID_PLAY_BACK_COLOR: selected.playback=color; break;
    case ID_PLAY_FORE_COLOR: selected.playfore=color; break;
    case ID_SOURCE_BACK_COLOR: selected.sourceback=color; break;
    case ID_SOURCE_FORE_COLOR: selected.sourcefore=color; break;
    case ID_TRAY_COLOR: selected.trayback=color; break;
    case ID_ALTERNATIVE_BACK_COLOR: selected.altback=color; break;

     }
  updateColors();

  updateColorThemes();
  return 1;
  }

long GMPreferencesDialog::onUpdElementColor(FXObject*sender,FXSelector sel,void*) {
  FXuval rgba = 0;
  switch(FXSELID(sel)){
    case ID_BASE_COLOR : rgba=selected.base; break;
    case ID_BORDER_COLOR : rgba=selected.border; break;
    case ID_BACK_COLOR : rgba=selected.back; break;
    case ID_FORE_COLOR : rgba=selected.fore; break;
    case ID_SHADOW_COLOR : rgba=selected.shadow; break;
    case ID_HILITE_COLOR : rgba=selected.hilite; break;

    case ID_SEL_BACK_COLOR: rgba=selected.selback; break;
    case ID_SEL_FORE_COLOR: rgba=selected.selfore; break;
    case ID_MENU_BACK_COLOR: rgba=selected.menuback; break;
    case ID_MENU_FORE_COLOR: rgba=selected.menufore; break;
    case ID_TIP_BACK_COLOR: rgba=selected.tipback; break;
    case ID_TIP_FORE_COLOR: rgba=selected.tipfore; break;
    case ID_PLAY_BACK_COLOR: rgba=selected.playback; break;
    case ID_PLAY_FORE_COLOR: rgba=selected.playfore; break;

    case ID_SOURCE_BACK_COLOR: rgba=selected.sourceback; break;
    case ID_SOURCE_FORE_COLOR: rgba=selected.sourcefore; break;
    case ID_TRAY_COLOR: rgba=selected.trayback; break;
    case ID_ALTERNATIVE_BACK_COLOR: rgba=selected.altback; break;


    }
  sender->tryHandle(this,FXSEL(SEL_COMMAND,FXColorWell::ID_SETINTVALUE),&rgba);
  return 1;
  }
long GMPreferencesDialog::onCmdColorTheme(FXObject*,FXSelector,void*ptr) {
  theme=(FXint)(FXival)ptr;
  ColorTheme *theme_selected=reinterpret_cast<ColorTheme*>(colorpresets->getItemData(theme));

  selected.base = theme_selected->base;
  selected.border = theme_selected->border;
  selected.back = theme_selected->back;
  selected.altback = theme_selected->altback;
  selected.fore = theme_selected->fore;
  selected.selfore	= theme_selected->selfore;
  selected.selback	= theme_selected->selback;
  selected.tipfore	= theme_selected->tipfore;
  selected.tipback	= theme_selected->tipback;
  selected.menufore= theme_selected->menufore;
  selected.menuback= theme_selected->menuback;
  selected.shadow = makeShadowColor(selected.base);
  selected.hilite   = makeHiliteColor(selected.base);
  selected.playback = theme_selected->playback;
  selected.playfore = theme_selected->playfore;
  selected.sourceback = theme_selected->sourceback;
  selected.sourcefore = theme_selected->sourcefore;
  selected.trayback = theme_selected->base;

  updateColors();
  return 1;
  }

long GMPreferencesDialog::onUpdColorTheme(FXObject*sender,FXSelector,void*) {
  sender->tryHandle(this,FXSEL(SEL_COMMAND,FXWindow::ID_SETINTVALUE),&theme);
  return 1;
  }



void GMPreferencesDialog::updateColors(){
  register FXWindow *w=FXApp::instance()->getRootWindow();

  FX7Segment * sevensegment;
  FXTextField * textfield;
  FXIconList * iconlist;
  FXList * list;
  FXListBox * listbox;
  FXTreeList * treelist;
  FXComboBox * combobox;
  FXButton * button;
  FXFrame * frame;
  FXLabel * label;
  FXPopup * popup;
  FXMenuTitle * menutitle;
  FXMenuCheck * menucheck;
  FXMenuRadio * menuradio;
  FXMenuCaption * menucaption;
  FXMenuSeparator * menuseparator;
  FXText * text;
  FXFoldingList * foldinglist;
  FXMDIChild * mdichild;
  FXTable * table;
  FXDockTitle * docktitle;
  FXPacker * packer;
  FXHeader * header;
  FXGroupBox * groupbox;
  FXScrollBar * scrollbar;
  FXSlider * slider;
  FXStatusLine * statusline;
  FXDragCorner * dragcorner;
  GMTreeList * gmtreelist;
  GMTrackList * gmtracklist;
  GMList * gmlist;
  FXRadioButton * radiobutton;
  FXCheckButton * checkbutton;
  FXToolTip * tooltip;
  FXImageFrame * imageframe;
  GMImageView * gmimageview;

  while(w){

    w->setBackColor(selected.base);

    if ((frame=dynamic_cast<FXFrame*>(w))) {

      frame->setBaseColor(selected.base);
      frame->setBackColor(selected.base);
      frame->setShadowColor(selected.shadow);
      frame->setHiliteColor(selected.hilite);
      frame->setBorderColor(selected.border);

      if ((label=dynamic_cast<FXLabel*>(w))) {
        label->setTextColor(selected.fore);
        if ((button=dynamic_cast<FXButton*>(w))) {
          if (dynamic_cast<GMListBox*>(button->getParent())){
            w->setBackColor(selected.back);
            }
          else {
            w->setBackColor(selected.base);
            }
          }
        else if ((checkbutton=dynamic_cast<FXCheckButton*>(w))) {
          checkbutton->setCheckColor(selected.fore);
          checkbutton->setBoxColor(selected.back);
          }
        else if ((radiobutton=dynamic_cast<FXRadioButton*>(w))) {
          radiobutton->setRadioColor(selected.fore);
          radiobutton->setDiskColor(selected.back);
          }
        }
      else if ((textfield=dynamic_cast<FXTextField*>(w))) {
        w->setBackColor(selected.back);
        textfield->setTextColor(selected.fore);
        textfield->setSelTextColor(selected.selfore);
        textfield->setSelBackColor(selected.selback);
        }
      else if ((docktitle=dynamic_cast<FXDockTitle*>(w))) {
        docktitle->setCaptionColor(selected.selfore);
        docktitle->setBackColor(selected.selback);
        }
      else if ((header=dynamic_cast<FXHeader*>(w))) {
        header->setTextColor(selected.fore);
        }
      else if ((statusline=dynamic_cast<FXStatusLine*>(w))) {
        statusline->setTextColor(selected.fore);
        }
      else if ((sevensegment=dynamic_cast<FX7Segment*>(w))) {
        sevensegment->setTextColor(selected.fore);
        }
      else if ((slider=dynamic_cast<FXSlider*>(w))) {
        slider->setSlotColor(selected.back);
        }
     else if ((imageframe=dynamic_cast<FXImageFrame*>(w))) {
        imageframe->setBackColor(selected.back); /// fixme, only for coverframe in mainwindow
        imageframe->getParent()->setBackColor(selected.back);
        }
     }
    else if ((packer=dynamic_cast<FXPacker*>(w))) {
      packer->setBaseColor(selected.base);
      packer->setBackColor(selected.base);
      packer->setShadowColor(selected.shadow);
      packer->setHiliteColor(selected.hilite);
      packer->setBorderColor(selected.border);
      if ((combobox=dynamic_cast<FXComboBox*>(w))) {
        w->setBackColor(selected.back);
        }
      else if ((listbox=dynamic_cast<FXListBox*>(w))) {
        w->setBackColor(selected.back);
        }
      else if ((groupbox=dynamic_cast<FXGroupBox*>(w))) {
        groupbox->setTextColor(selected.fore);
        }
      }
    else if ((popup=dynamic_cast<FXPopup*>(w))){
      popup->setBaseColor(selected.base);
      popup->setShadowColor(selected.shadow);
      popup->setHiliteColor(selected.hilite);
      popup->setBorderColor(selected.border);
      }
    else if ((menucaption=dynamic_cast<FXMenuCaption*>(w))) {
      w->setBackColor(selected.base);
      menucaption->setTextColor(selected.fore);
      menucaption->setSelTextColor(selected.menufore);
      menucaption->setSelBackColor(selected.menuback);
      menucaption->setShadowColor(selected.shadow);
      menucaption->setHiliteColor(selected.hilite);

      if ((menucheck=dynamic_cast<FXMenuCheck*>(w))) {
        menucheck->setBoxColor(selected.back);
        }
      else if ((menuradio=dynamic_cast<FXMenuRadio*>(w))) {
        menuradio->setRadioColor(selected.back);
        }
      else if ((menutitle=dynamic_cast<FXMenuTitle*>(w))) {
        menutitle->setTextColor(selected.fore);
        menutitle->setSelTextColor(selected.fore);
        menutitle->setSelBackColor(selected.base);
        }
      }
    else if ((menuseparator=dynamic_cast<FXMenuSeparator*>(w))) {
      menuseparator->setShadowColor(selected.shadow);
      menuseparator->setHiliteColor(selected.hilite);
      }
    else if ((scrollbar=dynamic_cast<FXScrollBar*>(w))) {
      scrollbar->setShadowColor(selected.shadow);
      scrollbar->setHiliteColor(selected.hilite);
      scrollbar->setBorderColor(selected.border);
      scrollbar->setArrowColor(selected.fore);
      }
    else if ((dragcorner=dynamic_cast<FXDragCorner*>(w))) {
      dragcorner->setShadowColor(selected.shadow);
      dragcorner->setHiliteColor(selected.hilite);
      }
    else if (dynamic_cast<FXScrollArea*>(w)) {
      if ((text=dynamic_cast<FXText*>(w))) {
        w->setBackColor(selected.back);
        text->setTextColor(selected.fore);
        text->setSelTextColor(selected.selfore);
        text->setSelBackColor(selected.selback);
        }
      else if ((list=dynamic_cast<FXList*>(w))) {
        w->setBackColor(selected.back);
        list->setTextColor(selected.fore);
        list->setSelTextColor(selected.selfore);
        list->setSelBackColor(selected.selback);
        if ((gmlist=dynamic_cast<GMList*>(w))) {
          gmlist->setRowColor(selected.altback);
          }
        }
      else if ((treelist=dynamic_cast<FXTreeList*>(w))) {
        w->setBackColor(selected.back);
        treelist->setTextColor(selected.fore);
        treelist->setLineColor(selected.shadow);
        if ((gmtreelist=dynamic_cast<GMTreeList*>(w))) {
          gmtreelist->setSelBackColor(selected.sourceback);
          gmtreelist->setSelTextColor(selected.sourcefore);
          gmtreelist->setRowColor(selected.altback);
          }
        else {
          treelist->setSelTextColor(selected.selfore);
          treelist->setSelBackColor(selected.selback);
          }
        }
      else if ((iconlist=dynamic_cast<FXIconList*>(w))) {
        w->setBackColor(selected.back);
        iconlist->setTextColor(selected.fore);
        iconlist->setSelTextColor(selected.selfore);
        iconlist->setSelBackColor(selected.selback);
        }
      else if ((gmtracklist=dynamic_cast<GMTrackList*>(w))) {
        w->setBackColor(selected.back);
        gmtracklist->setTextColor(selected.fore);
        gmtracklist->setSelTextColor(selected.selfore);
        gmtracklist->setSelBackColor(selected.selback);
        gmtracklist->setRowColor(selected.altback);
        gmtracklist->setActiveTextColor(selected.playfore);
        gmtracklist->setActiveColor(selected.playback);
        }
      else if ((foldinglist=dynamic_cast<FXFoldingList*>(w))) {
        w->setBackColor(selected.back);
        foldinglist->setTextColor(selected.fore);
        foldinglist->setSelTextColor(selected.selfore);
        foldinglist->setSelBackColor(selected.selback);
        foldinglist->setLineColor(selected.shadow);
        }
      else if ((table=dynamic_cast<FXTable*>(w))) {
        w->setBackColor(selected.back);
        table->setTextColor(selected.fore);
        table->setSelTextColor(selected.selfore);
        table->setSelBackColor(selected.selback);
        }
      }
    else if ((mdichild=dynamic_cast<FXMDIChild*>(w))) {
      mdichild->setBackColor(selected.base);
      mdichild->setBaseColor(selected.base);
      mdichild->setShadowColor(selected.shadow);
      mdichild->setHiliteColor(selected.hilite);
      mdichild->setBorderColor(selected.border);
      mdichild->setTitleColor(selected.selfore);
      mdichild->setTitleBackColor(selected.selback);
      }
    else if ((tooltip=dynamic_cast<FXToolTip*>(w))){
      tooltip->setTextColor(selected.tipfore);
      tooltip->setBackColor(selected.tipback);
      }
    else if ((gmimageview=dynamic_cast<GMImageView*>(w))){
      gmimageview->setBackColor(selected.back);
      gmimageview->getParent()->setBackColor(selected.back);
      }
    w->update();
    if(w->getFirst()){
      w=w->getFirst();
      continue;
      }
    while(!w->getNext() && w->getParent()){
      w=w->getParent();
      }
    w=w->getNext();
    }
  selected.save();

  if (GMPlayerManager::instance()->getTrayIcon())
    GMPlayerManager::instance()->getTrayIcon()->updateIcon();

  }


void GMPreferencesDialog::redraw(){
  register FXWindow *w=GMPlayerManager::instance()->getMainWindow();
  while(w){
    w->recalc();
    w->update();
    if(w->getFirst()){
      w=w->getFirst();
      continue;
      }
    while(!w->getNext() && w->getParent()){
      w=w->getParent();
      }
    w=w->getNext();
    }
  }



long GMPreferencesDialog::onCmdChangeFont(FXObject*,FXSelector,void*){
  GMFontDialog dialog(this,tr("Select Normal Font"));
  FXFont * font = FXApp::instance()->getNormalFont();
  FXFontDesc fontdescription;
#if FOXVERSION < FXVERSION(1,7,17)
  font->getFontDesc(fontdescription);
  fontdescription.size     = font->getActualSize();
  fontdescription.weight   = font->getActualWeight();
  fontdescription.setwidth = font->getActualSetWidth();
  fontdescription.slant    = font->getActualSlant();
#else
  fontdescription =  font->getActualFontDesc();
#endif
  strncpy(fontdescription.face,font->getActualName().text(),sizeof(fontdescription.face));
  dialog.setFontDesc(fontdescription);
  if(dialog.execute(PLACEMENT_SCREEN)){
    fontdescription=dialog.getFontDesc();
    GMApp::instance()->setFont(fontdescription);
    updateFonts();
    }
  return 1;
  }

void GMPreferencesDialog::updateFonts() {
  GMPlayerManager::instance()->getMainWindow()->layoutToolBarButtons();
  GMPlayerManager::instance()->getMainWindow()->getTrackView()->updateFont();
  redraw();
  FXint nw =getDefaultWidth();
  FXint nh = getDefaultHeight();
  resize(nw,nh);
  }


static void fancyfontname(FXFont * font,FXString & name) {
  name = font->getActualName().before('[').trimEnd();
  const FXchar *wgt=NULL,*slt=NULL,*wid=NULL;
  const FXint size=font->getActualSize()/10;

  switch(font->getActualSetWidth()){
     case FXFont::UltraCondensed: wid="Ultra Condensed"; break;
     case FXFont::ExtraCondensed: wid="Extra Condensed"; break;
     case FXFont::Condensed:      wid="Condensed"; break;
     case FXFont::SemiCondensed:  wid="Semi Condensed"; break;
     case FXFont::NonExpanded:    wid=NULL; break;
     case FXFont::SemiExpanded:   wid="Semi Expanded"; break;
     case FXFont::Expanded:       wid="Expanded"; break;
     case FXFont::ExtraExpanded:  wid="Extra Expanded"; break;
     case FXFont::UltraExpanded:  wid="Ultra Expanded"; break;
     default: wid=NULL; break;
     }

  switch(font->getActualWeight()){
    case FXFont::Thin      : wgt=fxtr("Thin"); break;
    case FXFont::ExtraLight: wgt=fxtr("Extra Light"); break;
    case FXFont::Light     : wgt=fxtr("Light"); break;
    case FXFont::Normal    : wgt=NULL; break;
    case FXFont::Medium    : wgt=fxtr("Medium"); break;
    case FXFont::DemiBold  : wgt=fxtr("Demibold"); break;
    case FXFont::Bold      : wgt=fxtr("Bold"); break;
    case FXFont::ExtraBold : wgt=fxtr("Extra Bold"); break;
    case FXFont::Black     : wgt=fxtr("Heavy"); break;
    default: wgt=NULL; break;
    }

  switch(font->getActualSlant()){
    case FXFont::ReverseOblique: slt="Reverse Oblique"; break;
    case FXFont::ReverseItalic: slt="Reverse Italic"; break;
    case FXFont::Straight: slt=NULL; break;
    case FXFont::Italic: slt="Italic"; break;
    case FXFont::Oblique: slt="Oblique"; break;
    default: slt=NULL; break;
    }

  if (wgt && slt && wid)
    name+=GMStringFormat(", %s %s %s, %d",wgt,wid,slt,size);
  else if (wgt && slt)
    name+=GMStringFormat(", %s %s, %d",wgt,slt,size);
  else if (wgt && wid)
    name+=GMStringFormat(", %s %s, %d",wgt,wid,size);
  else if (wid && slt)
    name+=GMStringFormat(", %s %s, %d",wid,slt,size);
  else if (slt)
    name+=GMStringFormat(", %s, %d",slt,size);
  else if (wgt)
    name+=GMStringFormat(", %s, %d",wgt,size);
  else if (wid)
    name+=GMStringFormat(", %s, %d",wid,size);
  else
    name+=GMStringFormat(", %d",size);
  }




long GMPreferencesDialog::onUpdFont(FXObject*sender,FXSelector,void*){
  FXString fontname;
  FXFont * font = FXApp::instance()->getNormalFont();
  fancyfontname(font,fontname);
  sender->tryHandle(this,FXSEL(SEL_COMMAND,FXWindow::ID_SETSTRINGVALUE),&fontname);
  return 1;
  }












