// My File Manager (MFM).
//
// Copyright 2005-2006 by Stefano Gatti.
//
// 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 2
// 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, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
// USA.
//
//=====================================================================

#include "mfm_util.hxx"
#include "mfm_main_ui.hxx"
#include "mfm_get_path_ui.hxx"
#include "mfm_input_ui.hxx"
#include "mfm_confirm_ui.hxx"
#include "mfm_attrib_ui.hxx"
#include "mfm_stat_ui.hxx"
#include "mfm_dir_ui.hxx"

#include "file_info.hxx"
#include "fl_file_sort.hxx"

#include <time.h>
#include <locale.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <malloc.h>
#include <fnmatch.h>
#include <pwd.h>
#include <grp.h>
// Added to convert mfmr_history_select_button from string to char*:
#include <string>

#define MAX_STIME 40


/**************************************************************************
*
*  get_color
*
*  return color associated to passed file
*
**************************************************************************/

Fl_Color get_color(char *name) {

  size_t start = 0;

  struct_ext_data *ext_ptr;

  Fl_Color color = FL_BLACK;

  for (size_t i = 1; i < strlen(name); i++)

    if (name[i] == '.') start = i;

  if (start>0 && ext_list != NULL) {

    ext_ptr = ext_list;

    do {

      if (strcasecmp(name+start, ext_ptr->ext) == 0) {

        color = ext_ptr->color;

        break;

      }

      ext_ptr = ext_ptr->next;

    } while (ext_ptr != NULL);

  }

  return color;

} // get_color


/**************************************************************************
*
*  get_prog
*
*  return a string with programs associated to passed file
*
**************************************************************************/

  char* get_prog(char *name) {

  size_t start = 0;

  struct_ext_data *ext_ptr;

  char *prog = NULL;

  for (size_t i = 1; i < strlen(name); i++)

    if (name[i] == '.') start = i;

  if (start>0 && ext_list != NULL) {

    ext_ptr = ext_list;

    do {

      if (strcasecmp(name+start, ext_ptr->ext) == 0) {

        prog = ext_ptr->prog;

        break;

      }

      ext_ptr = ext_ptr->next;

    } while (ext_ptr != NULL);

  }

  if (prog == NULL) prog = "";

  return prog;

} // get_prog


/**************************************************************************
* refresh_dir
*
* load dir for windows with passed path or for all windows
*
****************************************************************************/

void refresh_dir(char *path, bool force) {

  for (int i = 0; i< mfm_window_index.num_window_index; i++)

    if (path == NULL || strcmp(mfm_window_index.ptr_window_index[i]->path, path) == 0) 

      if (force || mfm_window_index.ptr_window_index[i]->get_dir_time(mfm_window_index.ptr_window_index[i]->path) > mfm_window_index.ptr_window_index[i]->dir_time) {
      
        int y = mfm_window_index.ptr_window_index[i]->mfm_window_table->group_table->yposition();

        mfm_window_index.ptr_window_index[i]->mfm_window_table->group_table->position(0, 0);
        
        mfm_window_index.ptr_window_index[i]->load_dir(false);             
        
        mfm_window_index.ptr_window_index[i]->mfm_window_table->group_table->position(0, y);
       
      }                           

} // refresh_dir


/**************************************************************************
* Metodi di class_mfm_window
****************************************************************************/

/**************************************************************************
* Costruttore
****************************************************************************/

class_mfm_window::class_mfm_window(char *dir) : class_mfm_window_fluid(){

  Fl_Menu_Item *old_menu_ptr = (Fl_Menu_Item *) mfm_menu->menu();
  
  mfm_menu->copy(mfm_menu->menu());  
  
  menu_offset = (mfm_menu->menu() - old_menu_ptr);  

  load_vars();
  
  mfm_window->size(w_window, h_window);
  
  Fl_Group::current((Fl_Group *) mfm_window_group);  

  mfm_window_table = new class_mfm_main_table(mfm_window_group->x(), mfm_window_group->y(), mfm_window_group->w(), mfm_window_group->h(), "", this);

  if (strlen(dir) > 3 && dir[0] == '-' && dir[2] == '=') {
  
    asprintf(&path, "%s", dir+3);    
    
    open_mode = dir[1];
    
  }   
    
  else { 
  
    asprintf(&path, "%s", dir);   
    
    open_mode = 'n';    
    
  }   

  if (open_mode == 'm' || open_mode == 't') { 
  
    char *command;
    
    asprintf(&open_dir, "%s", path);    
      
    asprintf(&command, "mount %s", open_dir);
      
    system(command);
      
    free(command);
    
  }   

// Add History FL_Menu_Button:
  Fl_Menu_Button* mfmr_history_select_button;

  mfmr_history_select_button = NULL;

  popup = mfm_popup_prog_menu;

  mfm_window->show();
  
  str_options = NULL;
  
  set_str_options();

	if (verbose)
	
	  (mfm_menu_opt_verbose + menu_offset)->set();
		
	else	
	
	  (mfm_menu_opt_verbose + menu_offset)->clear();

	if (overwrite)
	
	  (mfm_menu_opt_overwrite + menu_offset)->set();
		
	else	
	
	  (mfm_menu_opt_overwrite + menu_offset)->clear();
    
	if (localized_date)
	
	  (mfm_menu_view_localized + menu_offset)->set();
		
	else	
	
	  (mfm_menu_view_localized + menu_offset)->clear();
    
	if (right_filename)
	
	  (mfm_menu_view_right + menu_offset)->set();
		
	else	
	
	  (mfm_menu_view_right + menu_offset)->clear();    
    
  if (sort == SORT_NAME) (mfm_menu_sort_name + menu_offset)->setonly();
		
  else if (sort == SORT_EXT) (mfm_menu_sort_ext + menu_offset)->setonly();
	
	else if (sort == SORT_SIZE) (mfm_menu_sort_size + menu_offset)->setonly();
				
  else if (sort == SORT_DATE) (mfm_menu_sort_date + menu_offset)->setonly();

	else if (sort == SORT_MODE) (mfm_menu_sort_mode + menu_offset)->setonly();
	
	else if (sort == SORT_USER) (mfm_menu_sort_user + menu_offset)->setonly();
		
	else if (sort == SORT_GROUP) (mfm_menu_sort_group + menu_offset)->setonly();	
			
	else	(mfm_menu_sort_none + menu_offset)->setonly();
  	
  if (sort_case_sensitive) (mfm_menu_sort_case_sensitive + menu_offset)->set();
  else (mfm_menu_sort_case_sensitive + menu_offset)->clear();

  if (sort_inverse) (mfm_menu_sort_inverse + menu_offset)->set();
  else (mfm_menu_sort_inverse + menu_offset)->clear();

  if (sort_directory) (mfm_menu_sort_directory + menu_offset)->set();
  else (mfm_menu_sort_directory + menu_offset)->clear();

  if (permission == 0) (mfm_menu_view_permission_all + menu_offset)->setonly();
  if (permission == 1) (mfm_menu_view_permission_user + menu_offset)->setonly();
  if (permission == 2) (mfm_menu_view_permission_none + menu_offset)->setonly();
  if (owner == 0) (mfm_menu_view_owner_usergroup + menu_offset)->setonly();
  if (owner == 1) (mfm_menu_view_owner_user + menu_offset)->setonly();
  if (owner == 2) (mfm_menu_view_owner_none + menu_offset)->setonly();
  if (size == 0) (mfm_menu_view_size_bytes + menu_offset)->setonly();
  if (size == 1) (mfm_menu_view_size_kbytes + menu_offset)->setonly();
  if (size == 2) (mfm_menu_view_size_compact + menu_offset)->setonly();
  if (size == 3) (mfm_menu_view_size_none + menu_offset)->setonly();
  if (age == 0) (mfm_menu_view_age_datetime + menu_offset)->setonly();
  if (age == 1) (mfm_menu_view_age_date + menu_offset)->setonly();
  if (age == 2) (mfm_menu_view_age_none + menu_offset)->setonly();

  if (show_dir) (mfm_menu_view_show_dir + menu_offset)->set();
  else (mfm_menu_view_show_dir + menu_offset)->clear();

  if (show_hidden) (mfm_menu_view_show_hidden + menu_offset)->set();
  else (mfm_menu_view_show_hidden + menu_offset)->clear();

  if (show_color) (mfm_menu_view_show_color + menu_offset)->set();
  else (mfm_menu_view_show_color + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  load_dir(true);

  mfm_window_index.add(this);

} //class_mfm_window::class_mfm_window


/**************************************************************************
* Inizializza le variabili di configurazione
****************************************************************************/

void class_mfm_window::load_vars() {

  FILE   *stream = NULL;
  char   *config_file = NULL;

  asprintf(&config_file, "%s/.mfm/mfm-def.cfg", HOMEDIR);

  permission = 0;
  owner = 0;
  size = 2;
  age = 0;
  show_dir = true;
  show_hidden = true;
  show_color = true;
  sort = 6;
  sort_case_sensitive = false;
  sort_inverse = false;
  sort_directory = true;
  localized_date = true;
  right_filename = false;
  verbose = true;
  overwrite = false;
  w_window = mfm_window->w();
  h_window = mfm_window->h();
  scroll_speed = 1;

  if ((stream = fopen (config_file,"r"))!=NULL) {
  
    char *stringa = NULL,
         command[21];

    int  num, value;
    size_t dim;
  
    while (getline(&stringa, &dim, stream)>0) {

      num = sscanf(stringa, "%20s %i", command, &value);

      if (strcmp(command, "show_permission") == 0)

        permission = value;

      else if (strcmp(command, "show_owner") == 0)      
      
        owner = value;
        
      else if (strcmp(command, "show_size") == 0)      
      
        size = value;      

      else if (strcmp(command, "show_age") == 0)      
      
        age = value;     
        
      else if (strcmp(command, "show_dir") == 0)      
      
        show_dir = value;     
        
      else if (strcmp(command, "show_hidden") == 0)      
      
        show_hidden = value;     
        
      else if (strcmp(command, "show_color") == 0)      
      
        show_color = value;     
        
      else if (strcmp(command, "sort") == 0)      
      
        sort = value;     

      else if (strcmp(command, "sort_case_sensitive") == 0)      
      
        sort_case_sensitive = value;     

      else if (strcmp(command, "sort_inverse") == 0)      
      
        sort_inverse = value;     
        
      else if (strcmp(command, "localized_date") == 0)      
      
        localized_date = value;     
        
      else if (strcmp(command, "right_filename") == 0)      
      
        right_filename = value;                   

      else if (strcmp(command, "mode_verbose") == 0)      
      
        verbose = value;
             
      else if (strcmp(command, "mode_overwrite") == 0)      
      
        overwrite = value;                                        
        
      else if (strcmp(command, "width_window") == 0)      
      
        w_window = value;                                        

      else if (strcmp(command, "height_window") == 0)      
      
        h_window = value;   
        
      else if (strcmp(command, "scroll_speed") == 0)      
      
        scroll_speed = value;                   
                          
    }

    fclose(stream);
    
    xfree(&stringa);    
    
  }

  xfree(&config_file);

} // class_mfm_window::load_vars


/**************************************************************************
* Salva le variabili di configurazione
****************************************************************************/

void class_mfm_window::save_vars() {

  FILE   *stream = NULL;
  char *config_file = NULL;

  asprintf(&config_file, "%s/.mfm/mfm-def.cfg", HOMEDIR);

  if ((stream = fopen (config_file,"w"))!=NULL) {

    fprintf(stream, "show_permission %i\n", permission);
    fprintf(stream, "show_owner %i\n", owner);
    fprintf(stream, "show_size %i\n", size);
    fprintf(stream, "show_age %i\n", age);
    fprintf(stream, "show_dir %i\n", show_dir);
    fprintf(stream, "show_hidden %i\n", show_hidden);
    fprintf(stream, "show_color %i\n", show_color);
    fprintf(stream, "sort %i\n", sort);
    fprintf(stream, "sort_case_sensitive %i\n", sort_case_sensitive);
    fprintf(stream, "sort_inverse %i\n", sort_inverse);
    fprintf(stream, "localized_date %i\n", localized_date);
    fprintf(stream, "right_filename %i\n", right_filename);
    fprintf(stream, "mode_verbose %i\n", verbose);
    fprintf(stream, "mode_overwrite %i\n", overwrite);
    fprintf(stream, "width_window %i\n", mfm_window->w());
    fprintf(stream, "height_window %i\n", mfm_window->h());
    fprintf(stream, "scroll_speed %i\n", scroll_speed);

    fclose(stream);

  }

  xfree(&config_file);

} // class_mfm_window::save_vars


/**************************************************************************
* Set str_options string
****************************************************************************/

void class_mfm_window::set_str_options() {

  if (str_options != NULL)

    free(str_options);

// Busybox notes:
// mv -f don't prompt before overwrite
// mv -i interactive, prompt before overwrite
// mv -n don't overwrite an existing file
// cp -f overwrite
// cp -i prompt before overwrite

  if (verbose && overwrite)

// Busybox does not recognize -b argument
//  asprintf(&str_options, " -v -b ");
    asprintf(&str_options, " -v -f ");

  else if (verbose && !overwrite)  

    asprintf(&str_options, " -v -i");

  else if (!verbose && overwrite)

// Busybox does not recognize -b argument
//  asprintf(&str_options, " -b ");
    asprintf(&str_options, " -f ");  
    
  else {

// No verbose, no overwrite option still overwrites!
// Comment out str_options, add new asprintf line
// Not perfect but improved behaviour

    asprintf(&str_options, " -i");

//  str_options = (char *) malloc(1);

//  str_options[0] = 0;

  }  
    
} // class_mfm_window::set_str_options
    

/**************************************************************************
* Ordina la lista dei file
****************************************************************************/

long int class_mfm_window::filename_list(dirent ***files) {

  PATH = path;
 
  if (chdir(path))
  
    return 0;    
    
  if (!sort_directory) {

    if (sort == SORT_NAME && !sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_casealphasort);

    else if (sort == SORT_NAME && sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_alphasort);

    else if (sort == SORT_NAME && !sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_invcasealphasort);

    else if (sort == SORT_NAME && sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_invalphasort);


    else if (sort == SORT_EXT && !sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_caseextsort);

    else if (sort == SORT_EXT && sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_extsort);

    else if (sort == SORT_EXT && !sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_invcaseextsort);

    else if (sort == SORT_EXT && sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_invextsort);


    else if (sort == SORT_SIZE && !sort_inverse)

      return fl_filename_list(path, files, fl_sizesort);

    else if (sort == SORT_SIZE && sort_inverse)

      return fl_filename_list(path, files, fl_invsizesort);


    else if (sort == SORT_DATE && !sort_inverse)

      return fl_filename_list(path, files, fl_datesort);

    else if (sort == SORT_DATE && sort_inverse)

      return fl_filename_list(path, files, fl_invdatesort);


    else if (sort == SORT_MODE && !sort_inverse)

      return fl_filename_list(path, files, fl_modesort);

    else if (sort == SORT_MODE && sort_inverse)

      return fl_filename_list(path, files, fl_invmodesort);


    else if (sort == SORT_USER && !sort_inverse)

      return fl_filename_list(path, files, fl_usersort);

    else if (sort == SORT_USER && sort_inverse)

      return fl_filename_list(path, files, fl_invusersort);


    else if (sort == SORT_GROUP && !sort_inverse)

      return fl_filename_list(path, files, fl_groupsort);

    else if (sort == SORT_GROUP && sort_inverse)

      return fl_filename_list(path, files, fl_invgroupsort);


    else

      return fl_filename_list(path, files, fl_unsort);

  }

  else {


    if (sort == SORT_NAME && !sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_dircasealphasort);

    else if (sort == SORT_NAME && sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_diralphasort);

    else if (sort == SORT_NAME && !sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvcasealphasort);

    else if (sort == SORT_NAME && sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvalphasort);


    else if (sort == SORT_EXT && !sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_dircaseextsort);

    else if (sort == SORT_EXT && sort_case_sensitive && !sort_inverse)

      return fl_filename_list(path, files, fl_dirextsort);

    else if (sort == SORT_EXT && !sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvcaseextsort);

    else if (sort == SORT_EXT && sort_case_sensitive && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvextsort);


    else if (sort == SORT_SIZE && !sort_inverse)

      return fl_filename_list(path, files, fl_dirsizesort);

    else if (sort == SORT_SIZE && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvsizesort);


    else if (sort == SORT_DATE && !sort_inverse)

      return fl_filename_list(path, files, fl_dirdatesort);

    else if (sort == SORT_DATE && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvdatesort);


    else if (sort == SORT_MODE && !sort_inverse)

      return fl_filename_list(path, files, fl_dirmodesort);

    else if (sort == SORT_MODE && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvmodesort);


    else if (sort == SORT_USER && !sort_inverse)

      return fl_filename_list(path, files, fl_dirusersort);

    else if (sort == SORT_USER && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvusersort);


    else if (sort == SORT_GROUP && !sort_inverse)

      return fl_filename_list(path, files, fl_dirgroupsort);

    else if (sort == SORT_GROUP && sort_inverse)

      return fl_filename_list(path, files, fl_dirinvgroupsort);


    else

      return fl_filename_list(path, files, fl_dirunsort);

  }
  
} // class_mfm_window::filename_list


/**************************************************************************
* Imposta una directory nuova
****************************************************************************/

void class_mfm_window::set_dir(char *dir) {

  xfree(&path);
  
  if (dir[strlen(dir)-1] != '/')	

    asprintf(&path, "%s/", dir);

  else

    asprintf(&path, "%s", dir);


} // class_mfm_window::set_dir

// Trim MFMR history menu:
void class_mfm_window::remove_history_item() {

  mfmr_history_select_button->remove(0);

} // class_mfm_window::remove_history_item


/**************************************************************************
* Carica la directory
****************************************************************************/

void class_mfm_window::load_dir(bool flag_header) {

  long int num_files, num;
	
	int ncol;

  dirent  **files;

	if (strlen(path) > 0 && path[0]=='~') { 
	
	  char *tmpstr;
		
  	if (strlen(path) > 1 && path[1]=='/') 
		
  		asprintf(&tmpstr, "%s", path+2);
			
		else	
		
  		asprintf(&tmpstr, "%s", path+1);
		
		free(path);
		
		asprintf(&path, "%s%s", HOMEDIR, tmpstr);
		
		free(tmpstr);
	
  }		
  
  chdir(path);
  
  free(path);
  
  char *dir;
  
  dir = getcwd(NULL, 0); 

// Added mfmr_history_select_button:
  mfmr_history_select_button->add(dir);

  int list_length = mfmr_history_select_button->size();

  int max_length = 18;

  if (list_length >= max_length) {

    remove_history_item();

    }

// Ensure history button is not keyboard activated
// fl_menu_button bug breaks keyboard shortcuts:
  mfmr_history_select_button->clear_visible_focus();

  if (dir[strlen(dir)-1] != '/') { 

    asprintf(&path, "%s/", dir);

    free(dir);

  }		

  else

    path = dir;

  mfm_window->label(path);

  ncol = 0;
  
  if (!right_filename) {

    col_name = ncol;

    ncol++;

  }   

  if (permission < 2) {

    col_mode = ncol;

    ncol++;

  }

  else

   col_mode = -1;

  if (owner == 0) {

    col_user = ncol;
    col_group = ncol + 1;

    ncol=ncol+2;

  }

  else if (owner == 1) {

    col_user = ncol;
    col_group = -1;

    ncol++;

  }

  else

    col_user = col_group = -1;

  if (size < 3) {

    col_size = ncol;

    ncol++;

  }

  else

    col_size = -1;

  if (age <= 1) {

    col_date = ncol;

    ncol++;

  }

  else

    col_date = -1;
    
  if (right_filename) {

    col_name = ncol;

    ncol++;

  }       
  
  num_files = filename_list(&files);

  num = file_list(num_files, &files);

  if (flag_header) {

    mfm_window_table->create_header(ncol, true);

    write_header();
    
  }

  mfm_window_table->create_table(num, true);

  write_table(num_files, &files);

  for (long int i = 0; i<num_files; i++)

    free(files[i]);

	if (num_files>0)	

    free(files);

  dir_time = get_dir_time(path);

  return;

} // class_mfm_window::load_dir


/*********************************************************************
*
* file_list
*
* Create files list
*
*********************************************************************/

long int class_mfm_window::file_list(long int num_files, dirent ***files) {

  long int num = 0;
  
  for (long int i=0; i<num_files; i++) {

    if (strcmp((*files)[i]->d_name, ".") == 0)

      (*files)[i]->d_name[0] = (char) 0;

    else if (strcmp((*files)[i]->d_name, "./") == 0)

      (*files)[i]->d_name[0] = (char) 0;
      
    else if (strcmp((*files)[i]->d_name, "..") == 0)

      (*files)[i]->d_name[0] = (char) 0;

    else if (strcmp((*files)[i]->d_name, "../") == 0)

      (*files)[i]->d_name[0] = (char) 0;
      
    else if (!show_dir && is_dir((*files)[i]->d_name))

      (*files)[i]->d_name[0] = (char) 0;

    else if (!show_hidden && (*files)[i]->d_name[0] == '.')

      (*files)[i]->d_name[0] = (char) 0;

    else

      num++;

  }

  return num;

} // class_mfm_window::file_list


/*********************************************************************
*
* is_dir
*
* Return if a file is a directory
*
*********************************************************************/

bool class_mfm_window::is_dir(char* file) {

  file_info file_stat;

  file_stat.set_file(path, file);

  return file_stat.is_dir();

} // is_dir


/*********************************************************************
*
* get_dir_time
*
* Return timestamp of a directory
*
*********************************************************************/

time_t class_mfm_window::get_dir_time(char* dir) {

  file_info file_stat;

  file_stat.set_file("", dir);

  return file_stat.get_time();

} // get_dir_time


/*********************************************************************
*
* write_header
*
* Write table's header
*
*********************************************************************/

void class_mfm_window::write_header() {
 
  int i = (right_filename) ? 0 : 1;
  
  int width = 0;
  
  if (permission == 0) {

// Wider default MODE header width:
    mfm_window_table->header_label(i, MODE);

//  mfm_window_table->col_width(i, 90);
    mfm_window_table->col_width(i, 100);

    mfm_window_table->set_col_align(i, FL_ALIGN_LEFT);

    i++;

//  width += 90;
    width += 100;

  }

  else if (permission == 1) {

// Looks odd when Mode changes to M when viewing only user permissions:
// mfm_window_table->header_label(i, M);
   mfm_window_table->header_label(i, MODE);

// Less drastic shortening of user permissions header width:
//  mfm_window_table->col_width(i, 40);
    mfm_window_table->col_width(i, 60);

    mfm_window_table->set_col_align(i, FL_ALIGN_LEFT);

    i++;

//  width += 40;
    width += 60;

  }

  if (owner <= 1) {

    mfm_window_table->header_label(i, USER);

// Narrower User header width:
//  mfm_window_table->col_width(i, 80);
    mfm_window_table->col_width(i, 70);

    mfm_window_table->set_col_align(i, FL_ALIGN_LEFT);

    i++;

//  width += 80;
    width += 70;

  }

  if (owner == 0) {

    mfm_window_table->header_label(i, GROUP);

// Narrower Group header width:
//  mfm_window_table->col_width(i, 80);
    mfm_window_table->col_width(i, 70);

    mfm_window_table->set_col_align(i, FL_ALIGN_LEFT);

    i++;

//  width += 80;
    width += 70; 

  }

  if (size <= 2) {

    mfm_window_table->header_label(i, SIZE);

// Narrower Size header width:
//  mfm_window_table->col_width(i, 80);
    mfm_window_table->col_width(i, 70);

    mfm_window_table->set_col_align(i, FL_ALIGN_RIGHT);

    i++;

//  width += 80;  
    width += 70;  

  }

  if (age == 0) {

    mfm_window_table->header_label(i, DATE);

// Create spacing between centered Date and right justified Size:
//  mfm_window_table->col_width(i, 150);
    mfm_window_table->col_width(i, 170);


// Center align date to create seperation from size and right name:
//  mfm_window_table->set_col_align(i, FL_ALIGN_LEFT);
    mfm_window_table->set_col_align(i, FL_ALIGN_CENTER);

    i++;

// Create more spacing between centered Date and right justified Size:
//  width += 150;
    width += 170;

  }

  else if (age == 1) {

    mfm_window_table->header_label(i, DATE);

// Less drastic shortening of date header width:
//  mfm_window_table->col_width(i, 80);
    mfm_window_table->col_width(i, 100);

// Center align date to create sepatation from size and right name:
//  mfm_window_table->set_col_align(i, FL_ALIGN_LEFT);
    mfm_window_table->set_col_align(i, FL_ALIGN_CENTER);

    i++;

//  width += 80;    
    width += 100;

  }

  if (!right_filename)

    i = 0;

  mfm_window_table->header_label(i, NAME);

  int width_name = mfm_window_group->w()-width-17;

  if (width_name < 10) width_name = 10;

  mfm_window_table->col_width(i, width_name);

  mfm_window_table->set_col_align(i, FL_ALIGN_LEFT);

  mfm_window_table->sort_col = -1;

  if (sort == SORT_NAME) mfm_window_table->sort_table_header(col_name, !sort_inverse);

  else if (sort == SORT_SIZE) mfm_window_table->sort_table_header(col_size, !sort_inverse);

  else if (sort == SORT_DATE) mfm_window_table->sort_table_header(col_date, !sort_inverse);
		
  else if (sort == SORT_MODE) mfm_window_table->sort_table_header(col_mode, !sort_inverse);		
		
	else if (sort == SORT_USER) mfm_window_table->sort_table_header(col_user, !sort_inverse);			

	else if (sort == SORT_GROUP) mfm_window_table->sort_table_header(col_group, !sort_inverse);			

} // class_mfm_window::write_header


/*********************************************************************
*
* write_table
*
* Write table's list
*
*********************************************************************/

void class_mfm_window::write_table(long int num_files, dirent ***files) {

  long int i;

  long int row = 0;

  Fl_Color color;

  long long int x;

  struct tm *ltime = NULL;

  time_t time;

  char stime[MAX_STIME],
       *filesize = NULL,
       mode[11],
       *label, 
       *name, 
       *link_name;

  file_info file_stat;
	
  for (i = 0; i < num_files; i++) {

    if ((*files)[i]->d_name[0] != 0) {
    
      if (path == NULL)

        file_stat.set_file("", (*files)[i]->d_name);

      else

        file_stat.set_file(path, (*files)[i]->d_name);

      strcpy(mode, file_stat.get_mode());

      color = FL_BLACK;

      if (show_color)

        if (mode[0] == 'd' || mode[0] == 'D')

          color = dir_color;

        else if (mode[3] == 'x' || mode[3] == 's')

          color = exec_color;

        else {

          color = get_color((*files)[i]->d_name);

        }

      mfm_window_table->set_row_color(row ,color);

      if (permission == 0) 
			
        mfm_window_table->cell_label(col_mode, row, mode);
				
			else if (permission == 1)	{
			
			  char short_mode[5];
				
				int start;
				
				uid_t uid;
				
				uid = getuid();
				
				if (uid == file_stat.get_uid())

				  start = 1;
					
				else {	
			
          group *ptr_group;
	
	        passwd *ptr_user;
					
					bool found = false;
					
					int i = 0;
	
	        ptr_user = getpwuid(uid);
	
	        ptr_group = getgrgid(file_stat.get_gid());
	
          while (ptr_group->gr_mem[i] != NULL && !found) 
					
					  if (strcmp(ptr_group->gr_mem[i], ptr_user->pw_name) == 0)
						
						  found = true;
							
						else	
					
  					  i++;																
			
				  if (found) 

				    start = 4;
					
				  else 	
					
				    start = 7;
					
				}												
					
				for (int i=0; i<3; i++)
				
				  short_mode[i+1]	= mode[i+start];
					
        short_mode[0]	= mode[0];					
				short_mode[4]	= 0;
							
			  mfm_window_table->cell_label(col_mode, row, short_mode);
								
      }								

      if (owner <= 1) {

        mfm_window_table->cell_label(col_user, row, file_stat.get_user());

        if (owner == 0) 

          mfm_window_table->cell_label(col_group, row, file_stat.get_group());

      }

      switch (size) {

        case 0:

          asprintf(&filesize, "%lli", file_stat.get_size());

          break;

        case 1:

          asprintf(&filesize, "%lli KB", file_stat.get_size()/1024);

          break;

        case 2:

          x = file_stat.get_size();

          if (x < 1024) {

            asprintf(&filesize, "%lli  B", x);

          }

          else {

            x = (long long int) x/1024;

            if (x < 1024) {

              asprintf(&filesize, "%lli KB", x);

            }

            else {

              x = (long long int) x/1024;

              if (x < 1024) {

                asprintf(&filesize, "%lli MB", x);

              }

              else {

                x = (long long int) x/1024;

                asprintf(&filesize, "%lli GB", x);

              }

            }

          }

          break;

      }

      if (size <= 2) {

        mfm_window_table->cell_label(col_size, row, filesize);

        xfree(&filesize);

      }

      switch (age) {

        case 0:

          time = file_stat.get_time();

          ltime = localtime(&time);
          
          if (localized_date)

            strftime (stime, MAX_STIME, "%x %X", ltime);
            
          else
          
            strftime (stime, MAX_STIME, "%F %X", ltime);              

          break;

        case 1:

          time = file_stat.get_time();

          ltime = localtime(&time);

          if (localized_date)

            strftime (stime, MAX_STIME, "%x", ltime);
            
          else  
            
            strftime (stime, MAX_STIME, "%F", ltime);

          break;


      }

      if (age <= 1)

        mfm_window_table->cell_label(col_date, row, stime);

// If file is a directory remove last char if it is a '/'

      if ((mode[0] == 'd' || mode[0] == 'D') && (*files)[i]->d_name[strlen((*files)[i]->d_name)-1] == '/')
      
        (*files)[i]->d_name[strlen((*files)[i]->d_name)-1] = 0;   

// If file is a link, add linked file indication

      if (mode[0] == 'l' || (mode[0] < 91 && mode[0] > 64)) {

        int size = file_stat.get_size();

        name = (char *) malloc(size+1);

        asprintf(&link_name, "%s%s", path,(*files)[i]->d_name);	

        readlink(link_name, name, size);

        name[size] = 0;							

        asprintf(&label, "%s -> %s", (*files)[i]->d_name, name);

        free(link_name);		
        free(name);

      }

			else

        asprintf(&label, "%s", (*files)[i]->d_name);

// Replace '@' with "@@"
        
      bool name_flag = false;  
      
      int name_count = 0;      
        
      for (size_t j=0; j<strlen(label); j++)
      
        if (label[j] == '@') {
        
          name_count++;
          
          name_flag = true;
          
        }		  
      
      if (name_flag)  {
      
        char *label_tmp = (char *) malloc(name_count+strlen(label)+1);
        
        for (size_t j=0, k=0; j<=strlen(label); j++,k++) {
        
          label_tmp[k] = label[j];
        
          if (label_tmp[k] == '@') 
        
            label_tmp[++k] = '@';     
      
        }	
        
        free(label);
        
        label = label_tmp;
              
      }	

      mfm_window_table->cell_label(col_name, row, label);

      free(label);				

      row++;

    }

  }

  return;

} // class_mfm_window::write_table()


/**************************************************************************
* Va alla directory superiore
****************************************************************************/

void class_mfm_window::cdup() {

  size_t i;
  int j;
  
  char *dir;

  for(i = 0, j = -1; i < strlen(path)-1; i++)

    if (path[i] == (char) '/') j = i;

  if (j >= 0) path[j+1] = (char) 0;
  
  asprintf(&dir, "%s", path);

  set_dir(dir);
  
  xfree(&dir);

} // class_mfm_window::cdup


/**************************************************************************
* Apre un file con l'azione di default
****************************************************************************/

void class_mfm_window::open_file_default() {

  char mode[12],
       *prog,
       *exec,
       *command,
       *name,
       *file_list;
       
  int row;
	
  file_info file_stat;
  
  if (mfm_window_table->get_selected_rows() > 0) {
  
    for (row = 0; !mfm_window_table->row_selected(row); row++);       
    
    name = convert_names(mfm_window_table->cell_label(col_name, row), false);    

    file_stat.set_file(path, name);

    strcpy(mode, file_stat.get_mode());

    if (mode[0] == 'd' || mode[0] == 'D') {

      asprintf(&exec, "%s%s/", path, name);
			
			xfree(&path);
			
			asprintf(&path, "%s", exec);
			
			xfree(&exec);

      load_dir(false);
			
    }
    
    
    else if (mode[3] == 'x' || mode[3] == 's') {

      asprintf(&exec, "%s%s &", path, name);

      system(exec); 

      xfree(&exec);

    }				
    
    else {

      asprintf(&prog, "%s", get_prog(name));

      for (size_t i=0, start=0, flag=0; i<=strlen(prog); i++) {

        switch (flag) {

          case 0:

            if (prog[i] != (char) ' ') {

              start = i;

              flag=1;

            }

            break;

          case 1:

            if (prog[i] == (char) ' ' || prog[i] == (char) 0) {

              flag=2;

              exec = (char*) xmalloc(i-start+1);

              for (size_t j=start; j<i; j++)

                exec[j-start] = prog[j];

              exec[i-start] = (char) 0;
              
              file_list = get_list_file(false);

              asprintf(&command, "%s %s &", exec, file_list);
							
							chdir(path);

              system(command);

              xfree(&exec);

              xfree(&command);
              
              xfree(&file_list);
							
            }

            break;

        }

        if (flag == 2)

          break;

      }

    }
				
		xfree(&name);
    
  }

} // class_mfm_window::open_file_default()


/**************************************************************************
* Visualizza il menù per l'apertura di un file
****************************************************************************/

void class_mfm_window::open_file_menu() {

  char mode[12],
       *prog,
       *exec = NULL,
       *command,
       *name,
       *file_list;

  int row;
	
  bool found_action = false;							

  file_info file_stat;

  if (mfm_window_table->get_selected_rows() > 0) {

    for (row = 0; !mfm_window_table->row_selected(row); row++);
    
    name = convert_names(mfm_window_table->cell_label(col_name, row), false);        
				
    file_stat.set_file(path, name);

    strcpy(mode, file_stat.get_mode());
	
    popup->clear();
    popup->menu(NULL);    
		
    if (mode[0] == 'd' || mode[0] == 'D') {
		
      asprintf(&exec, "%s%s/", path, name);
						
      new class_mfm_window(exec);			
			
			xfree(&exec);
			
      found_action = true;										

    }

    else {

      asprintf(&prog, "%s", get_prog(name));

      for (size_t i=0, start=0, flag=0; i<=strlen(prog); i++)

        switch (flag) {

          case 0:
          
            if (prog[i] == (char) '"') {
            
              start = i;

              flag=2;

            }       
            
            else if (prog[i] == (char) '(') {
            
              start = i;

              flag=3;

            }
            
            else if (prog[i] != (char) ' ') {

              start = i;

              flag=1;

            }
            
            break;

          case 1:

            if (prog[i] == (char) ' ' || prog[i] == (char) 0) {

              flag=0;

              exec = (char*) xmalloc(i-start+1);

              for (size_t j=start; j<i; j++)

                exec[j-start] = prog[j];

              exec[i-start] = (char) 0;

              popup->add(exec);

              xfree(&exec);
							
              found_action = true;	
						 
            }                                 

            break;
            
          case 2:

            if (prog[i] == (char) '"' || prog[i] == (char) 0) {

              flag=0;
              
              if (i>start){

                exec = (char*) xmalloc(i-start);

                for (size_t j=start+1; j<i; j++)

                  exec[j-start-1] = prog[j];

                exec[i-start-1] = (char) 0;

                popup->add(exec);

                xfree(&exec);
							
                found_action = true;	
                
              }                                 
						 
            }                                 

            break;            
            
          case 3:

            if (prog[i] == (char) ')' || prog[i] == (char) 0)

              flag=0;              

            break;            

        }

      if (popup->size() > 0) {

        popup->position(Fl::event_x(), Fl::event_y());

        popup->popup();

        int val=popup->value();
        
        int num =-1;

        for (size_t i=0, start=0, flag=0; i<=strlen(prog); i++) {

          switch (flag) {

            case 0:

              if (prog[i] == (char) '"') {
            
                start = i;

                flag=2;

              }                        
              
              else if (prog[i] == (char) '(') {
            
                start = i;

                flag=3;

              }              
              
              else if (prog[i] != (char) ' ') {

                start = i;

                flag=1;

              }

              break;

            case 1:

              if (prog[i] == (char) ' ' || prog[i] == (char) 0) {
              
                num++;
                
                if (num == val) {

                  exec = (char*) xmalloc(i-start+1);

                  for (size_t j=start; j<i; j++)

                    exec[j-start] = prog[j];

                  exec[i-start] = (char) 0;

                }

                flag = 0;

              }

              break;
              
            case 2:

              if (prog[i] == (char) '"' || prog[i] == (char) 0) {
              
                num++;
                
                if (num == val) {

                  exec = (char*) xmalloc(i-start);
                  
                  for (size_t j=start+1; j<i; j++)

                    exec[j-start-1] = prog[j];

                  exec[i-start-1] = (char) 0;

                }

                flag = 0;

              }

              break;
          
            case 3:

              if (prog[i] == (char) ')' || prog[i] == (char) 0) {
              
                if (num == val) {

                  free(exec);
                  
                  start++;

                  exec = (char*) xmalloc(i-start+1);

                  for (size_t j=start; j<i; j++)

                    exec[j-start] = prog[j];

                  exec[i-start] = (char) 0;
              
                }
                
                flag=0;          
                
              }      

              break;  
            
          }                      

          if (flag == 4) break;

        }
        
        if (exec != NULL) {
        
          file_list = get_list_file(false);

          asprintf(&command, "%s %s &", exec, file_list);
									
          chdir(path);

          system(command);

          xfree(&exec);

          xfree(&command);
                  
          xfree(&file_list);
                            
        }

      }
      
      xfree(&prog);

    }
		
    if (!found_action && (mode[3] == 'x' || mode[3] == 's')) {

      asprintf(&exec, "mfmexec '%s' '%s' '%s 2>&1' &", name, path, name);

      system(exec); 

      xfree(&exec);

    }
		
	  xfree(&name);
    
  }

} // class_mfm_window::open_file_menu


/**************************************************************************
* Visualizza il menù di popup di un file
****************************************************************************/

void class_mfm_window::open_popup_menu() {

  mfm_popup_menu->position(Fl::event_x(), Fl::event_y());

  mfm_popup_menu->popup();

} // open_popup_menu


/**************************************************************************
* Ritorna una stringa con la lista dei file selezionati, con o senza path
****************************************************************************/

char* class_mfm_window::get_list_file(bool absolute) {

  char *list_file = NULL,
       *old_list,
			 *mod_file,
			 *mod_path;

//  list_file = (char *) malloc(1);

//  list_file[0] = 0;

  for (int i=0; i<mfm_window_table->get_rows(); i++)

    if (mfm_window_table->row_selected(i)) {
		
      mod_file = convert_names(mfm_window_table->cell_label(col_name, i), true);	
      
      if (list_file == NULL) {	
      
	  		if (absolute) {
			
		  		mod_path = convert_names(path, true);
			
          asprintf(&list_file, "%s%s", mod_path, mod_file);			
				
				  free(mod_path);
				
        } 														
			
	  		else

          asprintf(&list_file, "%s", mod_file);
      
      }              
      
      else {		
									
        old_list = list_file;
			
	  		if (absolute) {
			
		  		mod_path = convert_names(path, true);
			
          asprintf(&list_file, "%s %s%s", old_list, mod_path, mod_file);			
				
				  free(mod_path);
				
        } 														
			
	  		else

          asprintf(&list_file, "%s %s", old_list, mod_file);
			
        xfree(&old_list);
        
      }        
      
  	  xfree(&mod_file);

    }
		
  return list_file;

} // get_list_file


/**************************************************************************
* Callback dei widget dell'interfaccia
****************************************************************************/

void class_mfm_window::mfm_window_callback() {

  mfm_menu_quit_window_callback();

}


void class_mfm_window::mfm_menu_new_callback() {

  new class_mfm_window(HOMEDIR);

}


void class_mfm_window::mfm_menu_new_actual_callback() {

  new class_mfm_window(path);

}


void class_mfm_window::mfm_menu_new_home_callback() {

  new class_mfm_window(HOMEDIR);

}


void class_mfm_window::mfm_menu_new_launch_callback() {

  new class_mfm_window(LAUNCHDIR);

}


void class_mfm_window::mfm_menu_new_select_dir_callback() {

  char *dir_selected = NULL;

  dir_selected = fl_dir_chooser("CHANGE DIRECTORY...", path);

  if (dir_selected != NULL)

    new class_mfm_window(dir_selected);

}


void class_mfm_window::mfm_menu_new_trash_callback() {

  new class_mfm_window(TRASHCANDIR);

}


void class_mfm_window::mfm_menu_new_tree_callback() {

  new class_mfm_dir();

}


void class_mfm_window::mfm_menu_new_dir_callback() {

  char *new_dir,
       *full_path;

  new_dir = get_input("NEW DIRECTORY...", "");

  if (new_dir != NULL) {
	
	  if (new_dir[0] != 0) {

    asprintf(&full_path, "%s%s", path, new_dir);

    mkdir(full_path,  S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH);

// Add new directory to mfmr_history_select_button:
    mfmr_history_select_button->add(full_path);

    refresh_dir(path, false);
		
    xfree(&full_path);

    }
		
    xfree(&new_dir);

    start_timeout();
		
  }

}


void class_mfm_window::mfm_menu_new_file_callback() {

  char *new_file,
       *full_name;

  new_file = get_input("NEW FILE...", "");

  if (new_file != NULL) {
	
	  if (new_file[0] != 0) {

      asprintf(&full_name, "%s%s", path, new_file);

      open (full_name, O_WRONLY | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);

      refresh_dir(path, false);

      xfree(&full_name);
			
    }

    xfree(&new_file);
    
    start_timeout();    
      
  }

}


void class_mfm_window::mfm_menu_new_terminal_callback() {

  char *exec;
	
	asprintf(&exec, "%s &", TERMINAL);
	
  chdir(path);  
 		
  if (mfm_window_table->get_selected_rows() == 1)	
	
    for (int i=0; i<mfm_window_table->get_rows(); i++)

      if (mfm_window_table->row_selected(i)) {
			
			  char *name;
			
        name = convert_names(mfm_window_table->cell_label(col_name, i), false);

				if (is_dir(name))
				
          chdir(name);  				
					
				free(name);	

        break;

      }
	

	system(exec);
	
	free(exec);

}


// Add root terminal button to MFMR menubar:
void class_mfm_window::mfm_menu_root_terminal_callback() {

  char *exec;
	
	asprintf(&exec, "sudo %s &", TERMINAL);
	
  chdir(path);  
 		
  if (mfm_window_table->get_selected_rows() == 1)	
	
    for (int i=0; i<mfm_window_table->get_rows(); i++)

      if (mfm_window_table->row_selected(i)) {

        char *name;

        name = convert_names(mfm_window_table->cell_label(col_name, i), false);

        if (is_dir(name))
				
        chdir(name);  				
					
        free(name);	

        break;

      }	

	system(exec);
	
	free(exec);

}


void class_mfm_window::mfm_menu_chdir_callback() {

// Double-click Go-> reloads (created seperate UP button):
//mfm_menu_chdir_up_callback();
  mfm_menu_chdir_reload_callback();

}


void class_mfm_window::mfm_menu_chdir_up_callback() {

  cdup();

  load_dir(false);

}


// Added new change to root directory functon:
void class_mfm_window::mfm_menu_chdir_root_callback() {

  char *dir = "";

  set_dir(dir);

  load_dir(false);

}


// Added new change to /opt directory functon:
void class_mfm_window::mfm_menu_chdir_opt_callback() {

  char *dir = "/opt";

  set_dir(dir);

  load_dir(false);

}


void class_mfm_window::mfm_menu_chdir_home_callback() {

  set_dir(HOMEDIR);

  load_dir(false);

}


void class_mfm_window::mfm_menu_chdir_launch_callback() {

  set_dir(LAUNCHDIR);

  load_dir(false);

}


void class_mfm_window::mfm_menu_chdir_open_callback() {

  set_dir(path);
  load_dir(false);

}


void class_mfm_window::mfm_menu_chdir_select_dir_callback() {

  char *dir_selected = NULL;

  dir_selected = fl_dir_chooser("CHANGE DIRECTORY...", path);

  if (dir_selected != NULL) {

    xfree(&path);

    if (dir_selected[strlen(dir_selected)-1] != '/')

      asprintf(&path, "%s/", dir_selected);
      
    else  
    
      asprintf(&path, "%s", dir_selected);  

    load_dir(false);

  }

}


void class_mfm_window::mfm_menu_chdir_trash_callback() {

  set_dir(TRASHCANDIR);

  load_dir(false);

}


void class_mfm_window::mfm_menu_chdir_reload_callback() {

  load_dir(false);

}


void class_mfm_window::mfm_menu_select_callback() {

  mfm_menu_select_all_callback();

}


void class_mfm_window::mfm_menu_select_all_callback() {

  for (int i = 0; i < mfm_window_table->nrows; i++)

      mfm_window_table->select_row(i, true);

}


void class_mfm_window::mfm_menu_select_all_files_callback() {

  for (int i = 0; i < mfm_window_table->nrows; i++)

    if (is_dir(mfm_window_table->cell_label(col_name, i)))

      mfm_window_table->select_row(i, false);

    else

      mfm_window_table->select_row(i, true);

}


void class_mfm_window::mfm_menu_select_none_callback() {

  for (int i = 0; i < mfm_window_table->nrows; i++)

    mfm_window_table->select_row(i, false);

}


void class_mfm_window::mfm_menu_select_wildcard_callback() {

  char *wildcard;

  wildcard = get_input("WILDCARD...", "*");

  if (wildcard != NULL) {
	
	  if (wildcard[0] != 0) {

      for (int i = 0; i < mfm_window_table->nrows; i++)

        if (is_dir(mfm_window_table->cell_label(col_name, i)) ||
             fnmatch(wildcard, mfm_window_table->cell_label(col_name, i), 0))

          mfm_window_table->select_row(i, false);

        else

          mfm_window_table->select_row(i, true);
					
    }	

    xfree(&wildcard);

  }

}


void class_mfm_window::mfm_menu_files_callback() {

  if (mfm_window_table->get_selected_rows()) {

  mfm_menu_files_stat_callback();

  }

}


void class_mfm_window::mfm_menu_files_copy_callback() {

  if (mfm_window_table->get_selected_rows()) {

    char *dir_selected = NULL;

    dir_selected = get_path("COPY FILES TO...", path);

    if (dir_selected != NULL) {

      char *command = NULL,
           *file_list = NULL;

      file_list = get_list_file(false);

// Busybox cp -a equals -dpR (preserve symlinks, preserve file attributes, recurse)
//    asprintf(&command, "mfmexec 'Copy files' '%s' 'cp -r%s %s %s 2>&1' &", path, str_options, file_list, dir_selected);
//    asprintf(&command, "mfmexec 'Copy files' '%s' 'cp -a %s %s %s 2>&1' &", path, str_options, file_list, dir_selected);
// cp -a was overwriting during copy:
      asprintf(&command, "mfmexec 'COPYING...' '%s' 'cp -R %s %s %s 2>&1' &", path, str_options, file_list, dir_selected);

      system(command);

// Add target directory to history dropdown:
    mfmr_history_select_button->add(dir_selected);

      xfree(&command);
          
      xfree(&file_list);
			
      xfree(&dir_selected);

      start_timeout();      

    }

  }

}


void class_mfm_window::mfm_menu_files_move_callback() {

  if (mfm_window_table->get_selected_rows()) {
  
    char *dir_selected = NULL;

    dir_selected = get_path("MOVE FILES TO...", path);

    if (dir_selected != NULL) {

      char *command = NULL,
           *file_list = NULL;

      file_list = get_list_file(false);

// problems with move command, can't instigate -n (don't overwrite above, so need here)
//if (verbose && overwrite)

// Busybox does not recognize -b argument
//  asprintf(&str_options, " -v -f ");

//else if (verbose && !overwrite)  

// Busybox mv -n means don't overwrite existing file
//  asprintf(&str_options, " -v ");

// Original:
//    asprintf(&command, "mfmexec 'Move files' '%s' 'mv %s %s %s 2>&1' &", path, str_options, file_list, dir_selected);
      asprintf(&command, "mfmexec 'MOVING...' '%s' 'mv -n %s %s %s 2>&1' &", path, str_options, file_list, dir_selected);

      system(command);

// Add target directory to history dropdown:
    mfmr_history_select_button->add(dir_selected);

      xfree(&command);

      xfree(&file_list);
			
      xfree(&dir_selected);

      start_timeout();

    }

  }

}


void class_mfm_window::mfm_menu_files_soft_link_callback() {

  if (mfm_window_table->get_selected_rows()) {

    char *dir_selected = NULL;

    dir_selected = get_path("SOFT LINK TO...", path);
		
    if (dir_selected != NULL) {

      char *command = NULL,
           *file_list = NULL;

      file_list = get_list_file(true);

// Linking fails with str_options -i, removed from str_options:
//    asprintf(&command, "mfmexec 'Soft link files' '%s' 'ln -s %s %s %s 2>&1' &", path, str_options, file_list, dir_selected);
//    asprintf(&command, "mfmexec 'Soft link files' '%s' 'ln -s %s %s 2>&1' &", path, file_list, dir_selected);
      asprintf(&command, "mfmexec 'SOFT LINKING...' '%s' 'ln -s -f -v %s %s 2>&1' &", path, file_list, dir_selected);

      system(command);

// Add target directory to history dropdown:
      mfmr_history_select_button->add(dir_selected);

      xfree(&command);
          
      xfree(&file_list);
			
      xfree(&dir_selected);

      start_timeout();
      
    }

  }

}
		

void class_mfm_window::mfm_menu_files_hard_link_callback() {

  if (mfm_window_table->get_selected_rows()) {

    char *dir_selected = NULL;
         
    dir_selected = get_path("HARD LINK TO...", path);
		
    if (dir_selected != NULL) {

      char *command = NULL,
           *file_list = NULL;

      file_list = get_list_file(false);

// Linking fails with str_options -i, removed from str_options:
//    asprintf(&command, "mfmexec 'Hard link files' '%s' 'ln %s %s %s 2>&1' &", path, str_options, file_list, dir_selected);
      asprintf(&command, "mfmexec 'HARD LINKING...' '%s' 'ln -f -v %s %s 2>&1' &", path, file_list, dir_selected);
			
      system(command);

// Add target directory to history dropdown:
      mfmr_history_select_button->add(dir_selected);

      xfree(&command);
          
      xfree(&file_list);
			
      xfree(&dir_selected);

      start_timeout();
      
    }

  }

}

void class_mfm_window::mfm_menu_files_open_default_callback() {

  open_file_default();

}


void class_mfm_window::mfm_menu_files_open_menu_callback() {

  open_file_menu();

}


void class_mfm_window::mfm_menu_files_open_with_callback() {

  if (mfm_window_table->get_selected_rows()) {

    char *command,
         *program,
         *list_file;

    program = get_input("OPEN WITH...", "");

    if (program != NULL) {
 
      if (program[0]  != 0) {
 
        list_file = get_list_file(false);
			
		  	chdir(path);

        asprintf(&command, "%s %s &", program, list_file);

        system(command);

        xfree(&command);

        xfree(&list_file);
				
      }

      xfree(&program);

    }

  }

}


void class_mfm_window::mfm_menu_files_open_editor_callback() {

  char *command,
       *list_file;

  list_file = get_list_file(false);

  chdir(path);

  asprintf(&command, "%s %s &", EDITOR, list_file);

  system(command);

  xfree(&command);

  xfree(&list_file);

}


void class_mfm_window::mfm_menu_files_open_popup_callback() {

  open_popup_menu();

}


void class_mfm_window::mfm_menu_files_rename_callback() {

  if (mfm_window_table->get_selected_rows()>1) {
  
    char *command;
    
    asprintf(&command, "mfmrename %s &", get_list_file(false));
    
    chdir(path);
  
    system(command);
    
    free(command);
    
    start_timeout();        

  }

  else if (mfm_window_table->get_selected_rows()==1) {

    char *new_name,
         *old_mod_name,
         *new_mod_name,         
         *name,
         *command;

    int i;

    for (i=0; i<mfm_window_table->get_rows(); i++) {

      if (mfm_window_table->row_selected(i)) {

        name = convert_names(mfm_window_table->cell_label(col_name, i), false);

        new_name = get_input("RENAME...", name);

        if (new_name != NULL) {
				
				  if (new_name[0] != 0) {
				
  				  chdir(path);
            
            old_mod_name = convert_names(mfm_window_table->cell_label(col_name, i), true);            
            
            new_mod_name = convert_names(new_name, true);

// Replaced with if else below:
//          asprintf(&command, "mv %s %s %s &", str_options, old_mod_name, new_mod_name);

            if (overwrite) 

              asprintf(&command, "mv -f %s %s &", old_mod_name, new_mod_name);

            else 

              asprintf(&command, "mv -n %s %s &", old_mod_name, new_mod_name);

            system(command);
            
            xfree(&old_mod_name);

            xfree(&new_mod_name);     
       
            xfree(&command);
						
          }
					
          xfree(&new_name);
          
          start_timeout();          

        }

        break;

      }

    }

    xfree(&name);
    
  }
  
}


void class_mfm_window::mfm_menu_files_stat_callback() {
  
  if (mfm_window_table->get_selected_rows()) {

  new class class_mfm_stat(this);

  }

}


void class_mfm_window::mfm_menu_files_attributes_callback() {

  if (mfm_window_table->get_selected_rows()) {

    class_mfm_attrib *mfm_attrib_ptr = new class class_mfm_attrib(this);

    while (mfm_attrib_ptr->mfm_attrib != NULL)

      Fl::wait();

    delete mfm_attrib_ptr;

    refresh_dir(path, true);

  }

}


void class_mfm_window::mfm_menu_files_find_callback() {

  char *command = NULL;
	
  asprintf(&command, "mfmfind %s &", path);
	
  system(command);
	
	xfree(&command);

}


void class_mfm_window::mfm_menu_files_compress_callback() {

  int num;

  num = mfm_window_table->get_selected_rows();

  if (num) {

    char *command = NULL,
         *exec = NULL,
         *archive = NULL,
         *list_file = NULL;

    int lun;

    archive = get_input("CREATE ARCHIVE: filename.tar.gz, gz, tar.bz2, tar or tgz", "");

    if (archive != NULL) {

      list_file = get_list_file(false);

      lun = strlen(archive);

      if (lun == 0)
			
			  if (num == 1)
				
          asprintf(&command, "tar zcvf %s.tar.gz", list_file);
					
				else {	

          int i;        
          
          char *name;
          
          for (i=strlen(path)-2; i>=0; i--)

            if (path[i] == '/')

              break;
              
          asprintf(&name, "%s", path + i + 1);
          
          name[strlen(name)-1] = 0;
  				
          asprintf(&command, "tar zcvf %s.tar.gz", name);				
          
          free(name);
          
        }

// Add ability to compress to .gz format:
      else if (!memcmp(archive+lun-3, ".gz",3))

        asprintf(&command, "tar zcvf %s", archive);

      else if (!memcmp(archive+lun-7, ".tar.gz",7))

        asprintf(&command, "tar zcvf %s", archive);

      else if (!memcmp(archive+lun-8, ".tar.bz2",8))

        asprintf(&command, "tar jcvf %s", archive);

      else if (!memcmp(archive+lun-4, ".zip",4))

        asprintf(&command, "zip -r %s", archive);

      else if (!memcmp(archive+lun-4, ".tar",4))

        asprintf(&command, "tar cvf %s", archive);

      else if (!memcmp(archive+lun-4, ".tgz",4))

        asprintf(&command, "tar zcvf %s", archive);

			else

        asprintf(&command, "tar zcvf %s.tar.gz", archive);

      if (verbose) 
			
        asprintf(&exec,"mfmexec 'CREATE ARCHIVE' '%s' '%s %s 2>&1' &", path, command, list_file);	
				
			else	

        asprintf(&exec,"mfmexec 'CREATE ARCHIVE' '%s' '%s %s 2>&1 > /dev/null' &", path, command, list_file);
				
      system(exec);

      xfree(&command);
			
      xfree(&exec);

      xfree(&list_file);

      xfree(&archive);
      
      start_timeout();
      
    }

  }

}


void class_mfm_window::mfm_menu_files_burn_callback() {

  if (mfm_window_table->get_selected_rows()) {

    char *command;
    
    asprintf(&command, "mfmburn %s &", get_list_file(false));
    
    chdir(path);
  
    system(command);
    
    free(command);

  }

}


void class_mfm_window::mfm_menu_files_trash_callback() {

  if (mfm_window_table->get_selected_rows()) {

      char *command = NULL;

      char *file_list = NULL;

      file_list = get_list_file(false);
			
      chdir(path);

	if (overwrite)

          asprintf(&command, "mv -f %s '%s'", file_list, TRASHCANDIR);

        else

          asprintf(&command, "mv -n %s '%s'", file_list, TRASHCANDIR);

      system(command);

      xfree(&command);

      xfree(&file_list);
      
      start_timeout();      

      }

}


void class_mfm_window::mfm_menu_files_empity_trash_callback() {

  char *command;

  if (get_confirm("EMPTY TRASH BIN...", "OK to empty trash bin ?")) {

//  Empty trash now removes regular and .dot files:
//  asprintf(&command, "rm -Rf '%s'* &", TRASHCANDIR);
    asprintf(&command, "rm -Rf '%s'* && rm -Rf '%s'.??* &", TRASHCANDIR, TRASHCANDIR);

    system(command);

    xfree(&command);  
    
    start_timeout();          

  }

}


void class_mfm_window::mfm_menu_files_delete_callback() {

  if (mfm_window_table->get_selected_rows()) 

    if (get_confirm("DELETE ITEM(S)...", "OK to permanently delete selected item(s) ?")) {

      char *command = NULL;
      char *file_list = NULL;

      file_list = get_list_file(false);

			chdir(path);		

      asprintf(&command, "rm -Rf %s &", file_list);

      system(command);
      
      xfree(&command);

      xfree(&file_list);
      
      start_timeout();

    }

}


void class_mfm_window::mfm_menu_sort_callback() {

  if ((mfm_menu_sort_inverse + menu_offset)->value())
  
    (mfm_menu_sort_inverse + menu_offset)->clear();
    
  else  
  
    (mfm_menu_sort_inverse + menu_offset)->set();  

  mfm_menu_sort_inverse_callback();

}


void class_mfm_window::mfm_menu_sort_mode_callback() {

  sort = SORT_MODE;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(col_mode, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_user_callback() {

  sort = SORT_USER;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(col_user, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_group_callback() {

  sort = SORT_GROUP;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(col_group, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_size_callback() {

  sort = SORT_SIZE;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(col_size, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_date_callback() {

  sort = SORT_DATE;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(col_date, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_name_callback() {

  sort = SORT_NAME;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(col_name, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_ext_callback() {

  sort = SORT_EXT;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(-1, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_none_callback() {

  sort = SORT_NONE;

  sort_inverse = false;

  (mfm_menu_sort_inverse + menu_offset)->clear();

  mfm_window_table->up_dir = !sort_inverse;

  mfm_window_table->sort_table_header(-1, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_case_sensitive_callback() {

  sort_case_sensitive = (mfm_menu_sort_case_sensitive + menu_offset)->value();
  
  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_inverse_callback() {

  sort_inverse = (mfm_menu_sort_inverse + menu_offset)->value();

  mfm_window_table->sort_table_header(mfm_window_table->sort_col, !sort_inverse);

  load_dir(false);

}


void class_mfm_window::mfm_menu_sort_directory_callback() {

  sort_directory = (mfm_menu_sort_directory + menu_offset)->value();

  load_dir(false);

}

// Double-click menubar View displays selected file attributes
void class_mfm_window::mfm_menu_view_callback() {

mfm_menu_files_attributes_callback();

}


void class_mfm_window::mfm_menu_view_permission_all_callback() {

  permission = 0;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_permission_user_callback() {

  permission = 1;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_permission_none_callback() {

  permission = 2;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_owner_usergroup_callback() {

  owner = 0;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_owner_user_callback() {

  owner = 1;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_owner_none_callback() {

  owner = 2;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_size_bytes_callback() {

  size = 0;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_size_kbytes_callback() {

  size = 1;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_size_compact_callback() {

  size = 2;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_size_none_callback() {

  size = 3;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_age_datetime_callback() {

  age = 0;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_age_date_callback() {

  age = 1;

  load_dir(true);

}


void class_mfm_window::mfm_menu_view_age_none_callback() {

  age = 2;

  load_dir(true);

}

/*Redundant and rarely used, removed to shorten View dropdown menu

void class_mfm_window::mfm_menu_view_permission_toggle_callback() {

  permission++;
	
	if (permission == 3) permission = 0; 
	
	switch (permission) {
	
	  case 0:	(mfm_menu_view_permission_all + menu_offset)->setonly();	break;
	  case 1:	(mfm_menu_view_permission_user + menu_offset)->setonly();	break;
	  case 2:	(mfm_menu_view_permission_none + menu_offset)->setonly();	break;

  }

  load_dir(true);

}
*/

/*Redundant and rarely used, removed to shorten View dropdown menu

void class_mfm_window::mfm_menu_view_owner_toggle_callback() {

  owner++;
	
	if (owner == 3) owner = 0; 
	
	switch (owner) {
	
	  case 0:	(mfm_menu_view_owner_usergroup + menu_offset)->setonly();	break;
	  case 1:	(mfm_menu_view_owner_user + menu_offset)->setonly();	break;
	  case 2:	(mfm_menu_view_owner_none + menu_offset)->setonly();	break;

  }	

  load_dir(true);

}
*/

/*Redundant and rarely used, removed to shorten View dropdown menu

void class_mfm_window::mfm_menu_view_size_toggle_callback() {

  size++;
	
	if (size == 4) size = 0; 

	switch (size) {
	
	  case 0:	(mfm_menu_view_size_bytes + menu_offset)->setonly();	break;
	  case 1:	(mfm_menu_view_size_kbytes + menu_offset)->setonly();	break;
	  case 2:	(mfm_menu_view_size_compact + menu_offset)->setonly();	break;		
	  case 3:	(mfm_menu_view_size_none + menu_offset)->setonly();	break;

  }	

  load_dir(true);

}
*/

/*Redundant and rarely used, removed to shorten View dropdown menu

void class_mfm_window::mfm_menu_view_age_toggle_callback() {

  age++;
	
	if (age == 3) age = 0; 
	
	switch (age) {
	
	  case 0:	(mfm_menu_view_age_datetime + menu_offset)->setonly();	break;
	  case 1:	(mfm_menu_view_age_date + menu_offset)->setonly();	break;
	  case 2:	(mfm_menu_view_age_none + menu_offset)->setonly();	break;

  }		

  load_dir(true);

}
*/

void class_mfm_window::mfm_menu_view_show_dir_callback() {

  show_dir = (mfm_menu_view_show_dir + menu_offset)->value();

  load_dir(false);
  
}


void class_mfm_window::mfm_menu_view_show_hidden_callback() {
  
  show_hidden = (mfm_menu_view_show_hidden + menu_offset)->value();  
  
  load_dir(false);

}


void class_mfm_window::mfm_menu_view_show_color_callback() {

  show_color = (mfm_menu_view_show_color + menu_offset)->value();

  load_dir(false);

}


void class_mfm_window::mfm_menu_view_localized_callback() {

  localized_date = (mfm_menu_view_localized + menu_offset)->value();

  load_dir(false);

}


void class_mfm_window::mfm_menu_view_right_callback() {

  right_filename = (mfm_menu_view_right + menu_offset)->value();

  load_dir(true);

}


// Double-click menubar Options opens MFMR Configure:
void class_mfm_window::mfm_menu_opt_callback() {

  system("mfmcfg &");

}


void class_mfm_window::mfm_menu_opt_verbose_callback() {

  verbose = (mfm_menu_opt_verbose + menu_offset)->value();
  
  set_str_options();

// Added:
  save_vars();

  printf("Preference saved to mfm-def.cfg...\n");

}

void class_mfm_window::mfm_menu_opt_overwrite_callback() {

  overwrite = (mfm_menu_opt_overwrite + menu_offset)->value();
  
  set_str_options();

// Added:
  save_vars();

  printf("Preference saved to mfm-def.cfg...\n");

}


void class_mfm_window::mfm_menu_opt_wheel_callback() {

  char *new_value,
       *old_value;
  
  int i;

  asprintf(&old_value, "%i", scroll_speed);

  new_value = get_input("SCROLL VALUE...", old_value);

  free(old_value);

  if (new_value != NULL) {

     sscanf(new_value, "%i", &i);

     free(new_value);

     if (i |= 0)

       scroll_speed = i;
       
  }

// Added:
  save_vars();

  printf("Scroll preference saved to mfm-def.cfg...\n");

}


void class_mfm_window::mfm_menu_opt_zip_callback() {

  if (mfm_window_table->get_selected_rows() == 0) 
  
    system("mfmzip &");
    
  else { 
  
    char *command = NULL;
    char *file_list = NULL;
    int index;   

    file_list = get_list_file(false);

	  chdir(path);		
    
    for (index = strlen(file_list)-1; index > 0; index--)
    
      if (file_list[index] == ' ' && file_list[index-1] != '\\') {
      
        asprintf(&command, "mfmzip %s &", file_list+index+1);

        file_list[index] = 0; 
        
        system(command);
  
        free(command);            

        start_timeout();
    
      } 
      
    asprintf(&command, "mfmzip %s &", file_list);
        
    system(command);

    free(command);            
  
    free(file_list);
    
    start_timeout();    
  
  }  

}


void class_mfm_window::mfm_menu_opt_mount_callback() {

  system("mfmmount &");


}


void class_mfm_window::mfm_menu_opt_config_callback() {

  system("mfmcfg &");

}


void class_mfm_window::mfm_menu_opt_save_callback() {

  save_vars();

  printf("Preferences saved to mfm-def.cfg ...\n");

}


void class_mfm_window::mfm_menu_quit_callback() {

  mfm_menu_quit_window_callback();

}


void class_mfm_window::mfm_menu_quit_window_callback() {

  mfm_window_index.del(this);

  chdir("/");

  printf("Unmounting partition if temporary mounted...\n");

  if (open_mode == 't') {

    char *command;

//  Tiny Core umount requires sudo
//  asprintf(&command, "umount %s", open_dir);
    asprintf(&command, "sudo umount %s", open_dir);

    system(command);

    free(command);

    free(open_dir);

  }

// Added 2 lines:
  save_vars();

  printf("Preferences saved to mfm-def.cfg...\n");

  free(path);

  delete this->mfm_window;

  delete this;

}


void class_mfm_window::mfm_menu_quit_all_callback() {

  printf("Exit all selected.\n");

  printf("All browser windows closing.\n");

    for (int i = mfm_window_index.num_window_index - 1; i>=0; i--)

      if (mfm_window_index.ptr_window_index[i] != this)

        mfm_window_index.ptr_window_index[i]->mfm_menu_quit_window_callback();

    mfm_menu_quit_window_callback();

}


void class_mfm_window::mfm_menu_help_callback() {

  system("mfmhelp /usr/local/share/doc/mfm.html &");
      
}


// Add mfmr history_select_button_function:
void class_mfm_window::mfmr_history_select_callback() {

  int item = mfmr_history_select_button->value();

  printf("Selected item %d: %s \n", item, mfmr_history_select_button->text());

  std::string str = ("%s", mfmr_history_select_button->text());

  char *dir = &str[0u];

  set_dir(dir);

  load_dir(false);

// Deactivate interference from keyboard commands:
  mfmr_history_select_button->clear_visible_focus();
      
}


void class_mfm_window::mfmr_menu_clear_history_callback() {

  mfmr_history_select_button->clear();

  mfmr_history_select_button->clear_visible_focus();

}


void class_mfm_window::mfm_popup_copy_callback() {

  mfm_menu_files_copy_callback();

}


void class_mfm_window::mfm_popup_move_callback() {

  mfm_menu_files_move_callback();

}


void class_mfm_window::mfm_popup_open_default_callback() {

  mfm_menu_files_open_default_callback();

}


void class_mfm_window::mfm_popup_open_menu_callback() {

  mfm_menu_files_open_menu_callback();

}


void class_mfm_window::mfm_popup_open_with_callback() {

  mfm_menu_files_open_with_callback();
  
}


void class_mfm_window::mfm_popup_open_editor_callback() {

  mfm_menu_files_open_editor_callback();

}


void class_mfm_window::mfm_popup_rename_callback() {

  mfm_menu_files_rename_callback();

}


void class_mfm_window::mfm_popup_attributes_callback() {

  mfm_menu_files_attributes_callback();
  
}


// Added statistics to right click popup menu:
void class_mfm_window::mfm_popup_stat_callback() {

  if (mfm_window_table->get_selected_rows()) {

  mfm_menu_files_stat_callback();

  }
  
}


void class_mfm_window::mfm_popup_compress_callback() {

  mfm_menu_files_compress_callback();

}


void class_mfm_window::mfm_popup_trash_callback() {

  mfm_menu_files_trash_callback();

}


void class_mfm_window::mfm_popup_delete_callback() {

  mfm_menu_files_delete_callback();

}


void class_mfm_window::mfm_popup_new_dir_callback() {

  mfm_menu_new_dir_callback();

}


void class_mfm_window::mfm_popup_new_file_callback() {

  mfm_menu_new_file_callback();

}


void class_mfm_window::mfm_popup_new_terminal_callback() {

  mfm_menu_new_terminal_callback();

}


void class_mfm_window::mfm_popup_chdir_up_callback() {

  mfm_menu_chdir_up_callback();

}


void class_mfm_window::mfm_popup_select_all_callback() {

  mfm_menu_select_all_callback();

}
