Репозитории ALT
S: | 2.1.41-alt23 |
5.1: | 2.1.41-alt9 |
4.1: | 2.1.41-alt3.M41.1 |
4.0: | 2.1.35-alt5 |
3.0: | 2.1.25-alt3 |
+backports: | 2.1.29-alt4.0.M30 |
Группа :: Система/Основа
Пакет: menu
Главная Изменения Спек Патчи Sources Загрузить Gear Bugs and FR Repocop
Патч: menu-2.1.25-xdginput.patch
Скачать
Скачать
--- menu-2.1.25/update-menus/common.h~ 2005-08-07 21:54:54 +0400
+++ menu-2.1.25/update-menus/common.h 2005-08-07 21:55:38 +0400
@@ -32,6 +32,9 @@ const int MAX_LINE = 10240;
#define PACKAGEMENUS "/usr/share/menu/"
#define MENUMENUS "/usr/share/menu/default/"
#define USERMENUS ".menu/"
+#define XDGMENUS "/usr/share/applications/"
+#define XDGMENUS_KDE "/usr/share/applications/kde/"
+#define XDGMENUS_GNOME "/usr/share/applications/gnome/"
#define MENUMETHODS "/etc/menu-methods/"
#define USERMETHODS ".menu-methods/"
--- menu-2.1.25/update-menus/update-menus.h~ 2005-08-07 21:52:18 +0400
+++ menu-2.1.25/update-menus/update-menus.h 2005-08-07 21:52:28 +0400
@@ -122,6 +122,7 @@ public:
typedef enum { report_quiet, report_normal, report_verbose, report_debug} verbosity_type;
parsestream::eol_type compat;
std::vector<std::string> menufilesdir;
+ std::vector<std::string> desktopfilesdir;
std::string menumethod;
bool usedefaultmenufilesdirs;
bool onlyoutput_to_stdout;
--- menu-2.1.25/update-menus/update-menus.cc~ 2005-07-24 15:39:26 +0400
+++ menu-2.1.25/update-menus/update-menus.cc 2005-09-11 20:59:10 +0400
@@ -57,6 +57,7 @@ static const char * home_dir;
set<string> installed_packages;
set<string> menufiles_processed;
+set<string> desktopfiles_processed;
int total_menuentries;
int verbose=0;
@@ -463,6 +464,234 @@ void read_pkginfo()
pclose(status);
}
+/** Read a XDG desktopfile and create one menu entry for it.
+ *
+ * Returns 0 or 1 of menu entries read. */
+int read_desktopfile(const string &filename, const string &shortfilename,
+ vector<string> &menudata)
+{
+ FILE *desktop_file = fopen(filename.c_str(), "r");
+ if (desktop_file == NULL) return 0;
+
+ char firstline[MAX_LINE];
+ if (fgets(firstline, MAX_LINE, desktop_file) == NULL)
+ {
+ pclose(desktop_file);
+ return 0;
+ }
+ if (strcmp(firstline, "[Desktop Entry]\n") != 0)
+ {
+ pclose(desktop_file);
+ return 0;
+ }
+// cerr << __FUNCTION__ << " read " << filename << std::endl;
+
+ bool have_section = false;
+ bool have_title = false;
+ std::string d_onlyshowin;
+ std::string d_terminal;
+ std::string d_extra;
+ std::string menu_line;
+
+ // create menu entry start
+ menu_line += "package=\"_local.xdg_desktop_files\" xdg_desktopfile=\"true\"";
+// int n_line = 2;
+ while (!feof(desktop_file))
+ {
+ std::string line;
+ char tmp[MAX_LINE];
+ fgets(tmp, MAX_LINE, desktop_file);
+ int len = strlen(tmp);
+
+ // ignore empty lines
+ if ( len <= 1) continue;
+
+ // quote
+ for(int i=0; i < MAX_LINE; i++)
+ {
+ if( tmp[i] == '\"' )
+ line += "\\\"";
+ else if( tmp[i] == '\n' )
+ break;
+ else
+ line += tmp[i];
+ }
+
+// if( tmp[len-1] == '\n' )
+// line = std::string(tmp, 0, len-1);
+// else
+// line = tmp;
+// cerr << " line " << n_line++ << ":" << line << std::endl;
+
+ int sz = line.size();
+
+ if( line.compare(0, 5, "Name=") == 0 )
+ {
+ // take title
+// cerr << __FUNCTION__ << " take title" << std::endl;
+ if(sz > 5)
+ {
+ menu_line += " title=\""+line.substr(5, sz-5)+"\"";
+ have_title = true;
+ }
+ }
+ else if( line.compare(0, 11, "Categories=") == 0 )
+ {
+ // take section
+// cerr << __FUNCTION__ << " take section" << std::endl;
+ if(sz > 11)
+ {
+ std::string categories( line.substr(11, sz-11) );
+ std::list<string> ctglist;
+ for(std::string::iterator it = categories.begin(); it != categories.end(); ++it)
+ {
+ std::string ctg;
+
+ while( it != categories.end() && *it != ';' )
+ {
+ ctg += *it;
+ ++it;
+ }
+ if( it == categories.end() ) --it;
+
+ if( ctg.size() > 0 )
+ ctglist.push_front(ctg);
+ }
+ for(std::list<string>::iterator it = ctglist.begin(); it != ctglist.end(); ++it)
+ {
+ if( *it != "X-KDE-More" )
+ {
+ menu_line += " section=\""+*it+"\"";
+ have_section = true;
+ break;
+ }
+ }
+ }
+ }
+ else if( line.compare(0, 8, "Comment=") == 0 )
+ {
+ // take longtitle
+ if(sz > 8)
+ {
+ menu_line += " longtitle=\""+line.substr(8, sz-8)+"\"";
+ }
+ }
+ else if( line.compare(0, 5, "Icon=") == 0 )
+ {
+ // take icon
+ if(sz > 5)
+ {
+ menu_line += " icon=\""+line.substr(5, sz-5)+"\"";
+ }
+ }
+ else if( line.compare(0, 9, "MimeType=") == 0 )
+ {
+ // take mimetypes
+ // FIXME? replace ; by ,
+ if(sz > 9)
+ {
+ menu_line += " mimetypes=\""+line.substr(9, sz-9)+"\"";
+ }
+ }
+ else if( line.compare(0, 5, "Exec=") == 0 )
+ {
+ // take command && xdg_command
+ if(sz > 5)
+ {
+ menu_line += " xdg_command=\""+line.substr(5, sz-5)+"\"";
+ int sps_pos = line.find(' ');
+ if( sps_pos > 5 )
+ menu_line += " command=\""+line.substr(5, sps_pos-5)+"\"";
+ else
+ menu_line += " command=\""+line.substr(5, sz-5)+"\"";
+ }
+ }
+ else if( line.compare(0, 12, "GenericName=") == 0 )
+ {
+ if(sz > 12)
+ {
+ menu_line += " xdg_genericname=\""+line.substr(12, sz-12)+"\"";
+ }
+ }
+ else if( line.compare(0, 9, "Terminal=") == 0 )
+ {
+ // fill d_terminal
+ if(sz > 9)
+ {
+ d_terminal = line.substr(9, sz-9);
+ }
+ }
+ else if( line.compare(0, 11, "OnlyShowIn=") == 0 )
+ {
+ // fill d_onlyshowin
+ if(sz > 11)
+ {
+ int start = sz - 3;
+ int end = sz - 1 ;
+ while( line[start] != ';' && line[start] != '=' && start >= 0 )
+ start--;
+ start++;
+ end = start;
+ while( line[end] != ';' && line[end] != '\n' && end < sz )
+ end++;
+ std::string onlyshowin(line.substr(start, end-start));
+ d_onlyshowin = onlyshowin;
+ }
+ }
+ else
+ {
+ if( line.compare(0, 9, "Encoding=") != 0 )
+ {
+ // fill xdg_extra
+ d_extra += line+"\\n";
+ }
+ }
+
+ }
+// cerr << __FUNCTION__ << " end while" << std::endl;
+
+ // skip wrong entries
+ if ( !have_section || !have_title )
+ {
+// cerr << __FUNCTION__ << " !have_section || !have_title " << filename << std::endl;
+ pclose(desktop_file);
+ return 0;
+ }
+
+ // take needs
+ if( d_terminal.size() > 0 || d_onlyshowin.size() > 0 )
+ {
+ if( d_terminal == "1" || d_terminal == "true" )
+ menu_line += " needs=\"text\"";
+ else if( d_onlyshowin.size() > 0 )
+ menu_line += " needs=\""+d_onlyshowin+"\"";
+ else
+ menu_line += " needs=\"X11\"";
+ }
+ else
+ menu_line += " needs=\"X11\"";
+
+ // take xdg_filename
+ {
+ int slash_pos = shortfilename.rfind("/");
+ if( slash_pos >= 0 )
+ menu_line += " xdg_filename=\""+shortfilename.substr(slash_pos+1, shortfilename.size()-slash_pos-1)+"\"";
+ else
+ menu_line += " xdg_filename=\""+shortfilename+"\"";
+ }
+
+ // add xdg_extra
+ if( d_extra.size() > 0 )
+ menu_line += " xdg_extra=\""+d_extra+"\"";
+
+ menudata.push_back(string("!F ") + filename + '\n');
+ menudata.push_back(menu_line + '\n');
+// cerr << __FUNCTION__ << " add " << filename << std::endl;
+
+ pclose(desktop_file);
+ return 1;
+}
+
/** Read a menufile and create one (or more) menu entries for it.
*
* Returns the number of menu entries read. */
@@ -591,6 +820,47 @@ void read_menufilesdir(vector<string> &m
}
}
+/** Read a XDG directory full of desktop files */
+void read_desktopfilesdir(vector<string> &menudata)
+{
+ int menuentries = 0;
+ for(vector<string>::const_iterator method_i = config.desktopfilesdir.begin();
+ method_i != config.desktopfilesdir.end();
+ ++method_i)
+ {
+ string dirname = *method_i;
+ config.report(String::compose(_("Reading menu-entry files in %1."), dirname),
+ configinfo::report_verbose);
+ try {
+ struct dirent *entry;
+ DIR *dir = open_dir_check(dirname);
+ while((entry = readdir(dir)))
+ {
+ string name = entry->d_name;
+ if ((name != "README") && (name != "core") && (name[0] != '.') &&
+ (name.find(".bak") == string::npos) &&
+ (name[name.length()-1] != '~'))
+
+ if (desktopfiles_processed.find(name) == desktopfiles_processed.end()) {
+ desktopfiles_processed.insert(name);
+ name = dirname+name;
+ struct stat st;
+ int r = stat(name.c_str(),&st);
+ try {
+ if ((!r) && (S_ISREG(st.st_mode)||S_ISLNK(st.st_mode)) && (st.st_size < 30720))
+ menuentries += read_desktopfile(name,entry->d_name, menudata);
+ }
+ catch (endofline p) {
+ cerr << String::compose(_("Error reading %1.\n"), name);
+ }
+ }
+ }
+ } catch (dir_error_read p) { }
+ total_menuentries += menuentries;
+ config.report(String::compose(_("%1 menu entries found (%2 total)."), menuentries, total_menuentries), configinfo::report_verbose);
+ }
+}
+
/** Run a menu method */
void run_menumethod(string methodname, const vector<string> &menudata)
{
@@ -1037,7 +1307,12 @@ int main (int argc, char **argv)
config.menufilesdir.push_back(MENUMENUS);
}
+ config.desktopfilesdir.push_back(XDGMENUS);
+ config.desktopfilesdir.push_back(XDGMENUS_KDE);
+ config.desktopfilesdir.push_back(XDGMENUS_GNOME);
+
read_menufilesdir(menudata);
+ read_desktopfilesdir(menudata);
if (config.onlyoutput_to_stdout) {
for(vector<string>::const_iterator i = menudata.begin(); i != menudata.end(); ++i)