21 #include <kiconloader.h>
22 #include <tdeglobal.h>
23 #include <kstandarddirs.h>
24 #include <tdelocale.h>
26 #include <ksortablevaluelist.h>
28 #include "kservicefactory.h"
29 #include "kservicegroupfactory.h"
30 #include "kservicegroup.h"
32 #include "tdesycoca.h"
34 class KServiceGroup::Private
37 Private() { m_bNoDisplay =
false; m_bShowEmptyMenu =
false;m_bShowInlineHeader=
false;m_bInlineAlias=
false; m_bAllowInline =
false; m_inlineValue = 4; m_bShortMenu =
false; m_bGeneralDescription =
false;}
40 bool m_bGeneralDescription;
41 bool m_bShowEmptyMenu;
42 bool m_bShowInlineHeader;
48 TQStringList sortOrder;
52 : KSycocaEntry(name), m_childCount(-1)
54 d =
new KServiceGroup::Private;
60 : KSycocaEntry(_relpath), m_childCount(-1)
62 d =
new KServiceGroup::Private;
66 TQString cfg = configFile;
68 cfg = _relpath+
".directory";
70 d->directoryEntryPath = cfg;
72 KDesktopFile config( cfg,
true,
"apps" );
74 m_strCaption = config.readName();
75 m_strIcon = config.readIcon();
76 m_strComment = config.readComment();
77 m_bDeleted = config.readBoolEntry(
"Hidden",
false );
78 d->m_bNoDisplay = config.readBoolEntry(
"NoDisplay",
false );
79 if (d->directoryEntryPath.startsWith(TQDir::homeDirPath()))
80 d->m_bShortMenu =
false;
82 d->m_bShortMenu = config.readBoolEntry(
"X-SuSE-AutoShortMenu",
false );
83 d->m_bGeneralDescription = config.readBoolEntry(
"X-SuSE-GeneralDescription",
false );
85 if (config.hasKey(
"OnlyShowIn"))
87 #ifdef WITH_OLD_XDG_STD
88 if ((!config.readListEntry(
"OnlyShowIn",
';').contains(
"TDE")) && (!config.readListEntry(
"OnlyShowIn",
';').contains(
"KDE")))
89 d->m_bNoDisplay =
true;
91 if (!config.readListEntry(
"OnlyShowIn",
';').contains(
"TDE"))
92 d->m_bNoDisplay =
true;
95 if (config.hasKey(
"NotShowIn"))
97 #ifdef WITH_OLD_XDG_STD
98 if ((config.readListEntry(
"NotShowIn",
';').contains(
"TDE")) || (config.readListEntry(
"NotShowIn",
';').contains(
"KDE")))
99 d->m_bNoDisplay =
true;
101 if (config.readListEntry(
"NotShowIn",
';').contains(
"TDE"))
102 d->m_bNoDisplay =
true;
106 m_strBaseGroupName = config.readEntry(
"X-TDE-BaseGroup" );
107 d->suppressGenericNames = config.readListEntry(
"X-TDE-SuppressGenericNames" );
108 d->sortOrder = config.readListEntry(
"SortOrder");
111 if (m_strCaption.isEmpty())
113 m_strCaption = _relpath;
114 if (m_strCaption.right(1) ==
"/")
115 m_strCaption = m_strCaption.left(m_strCaption.length()-1);
116 int i = m_strCaption.findRev(
'/');
118 m_strCaption = m_strCaption.mid(i+1);
120 if (m_strIcon.isEmpty())
121 m_strIcon =
"folder";
125 KSycocaEntry( _str, offset )
127 d =
new KServiceGroup::Private;
132 KServiceGroup::~KServiceGroup()
139 if (m_childCount == -1)
141 TDEConfig global(
"kdeglobals");
142 global.setGroup(
"KDE");
143 bool showUnimportant = global.readBoolEntry(
"showUnimportant",
true);
147 for( List::ConstIterator it = m_serviceList.begin();
148 it != m_serviceList.end(); it++)
150 KSycocaEntry *p = (*it);
151 if (p->isType(KST_KService))
158 else if (p->isType(KST_KServiceGroup))
171 return d->m_bShowInlineHeader;
176 return d->m_bShowEmptyMenu;
181 return d->m_bInlineAlias;
184 void KServiceGroup::setInlineAlias(
bool _b)
186 d->m_bInlineAlias = _b;
189 void KServiceGroup::setShowEmptyMenu(
bool _b)
191 d->m_bShowEmptyMenu=_b;
194 void KServiceGroup::setShowInlineHeader(
bool _b)
196 d->m_bShowInlineHeader=_b;
201 return d->m_inlineValue;
204 void KServiceGroup::setInlineValue(
int _val)
206 d->m_inlineValue = _val;
211 return d->m_bAllowInline;
214 void KServiceGroup::setAllowInline(
bool _b)
216 d->m_bAllowInline = _b;
221 return d->m_bNoDisplay || m_strCaption.startsWith(
".");
226 return d->suppressGenericNames;
229 bool KServiceGroup::SuSEgeneralDescription()
const
231 return d->m_bGeneralDescription;
236 return d->m_bShortMenu;
239 void KServiceGroup::load( TQDataStream& s )
241 TQStringList groupList;
243 TQ_INT8 _showEmptyMenu;
244 TQ_INT8 inlineHeader;
245 TQ_INT8 _inlineAlias;
246 TQ_INT8 _allowInline;
247 s >> m_strCaption >> m_strIcon >>
248 m_strComment >> groupList >> m_strBaseGroupName >> m_childCount >>
249 noDisplay >> d->suppressGenericNames >> d->directoryEntryPath >>
250 d->sortOrder >> _showEmptyMenu >> inlineHeader >> _inlineAlias >>
251 _allowInline >> d->m_bShortMenu >> d->m_bGeneralDescription;
254 d->m_bShowEmptyMenu = ( _showEmptyMenu != 0 );
255 d->m_bShowInlineHeader = ( inlineHeader != 0 );
256 d->m_bInlineAlias = ( _inlineAlias != 0 );
257 d->m_bAllowInline = ( _allowInline != 0 );
261 for(TQStringList::ConstIterator it = groupList.begin();
262 it != groupList.end(); it++)
265 if (path[path.length()-1] ==
'/')
268 serviceGroup = KServiceGroupFactory::self()->findGroupByDesktopPath(path,
false);
270 m_serviceList.append( SPtr(serviceGroup) );
275 service = KServiceFactory::self()->findServiceByDesktopPath(path);
277 m_serviceList.append( SPtr(service) );
283 void KServiceGroup::addEntry( KSycocaEntry *entry)
285 m_serviceList.append(entry);
288 void KServiceGroup::save( TQDataStream& s )
290 KSycocaEntry::save( s );
292 TQStringList groupList;
293 for( List::ConstIterator it = m_serviceList.begin();
294 it != m_serviceList.end(); it++)
296 KSycocaEntry *p = (*it);
297 if (p->isType(KST_KService))
302 else if (p->isType(KST_KServiceGroup))
305 groupList.append( serviceGroup->
relPath());
315 TQ_INT8
noDisplay = d->m_bNoDisplay ? 1 : 0;
316 TQ_INT8 _showEmptyMenu = d->m_bShowEmptyMenu ? 1 : 0;
317 TQ_INT8 inlineHeader = d->m_bShowInlineHeader ? 1 : 0;
318 TQ_INT8 _inlineAlias = d->m_bInlineAlias ? 1 : 0;
319 TQ_INT8 _allowInline = d->m_bAllowInline ? 1 : 0;
320 s << m_strCaption << m_strIcon <<
321 m_strComment << groupList << m_strBaseGroupName << m_childCount <<
322 noDisplay << d->suppressGenericNames << d->directoryEntryPath <<
323 d->sortOrder <<_showEmptyMenu <<inlineHeader<<_inlineAlias<<_allowInline <<
324 d->m_bShortMenu << d->m_bGeneralDescription;
336 return entries(sort, excludeNoDisplay,
false);
339 static void addItem(KServiceGroup::List &sorted,
const KSycocaEntry::Ptr &p,
bool &addSeparator)
341 if (addSeparator && !sorted.isEmpty())
342 sorted.append(
new KServiceSeparator());
344 addSeparator =
false;
350 return SuSEentries(sort, excludeNoDisplay, allowSeparators, sortByGenericName);
354 KServiceGroup::SuSEentries(
bool sort,
bool excludeNoDisplay,
bool allowSeparators,
bool sortByGenericName,
bool excludeSuSEunimportant)
365 KServiceGroupFactory::self()->findGroupByDesktopPath(
relPath(),
true);
372 return group->m_serviceList;
377 KSortableValueList<SPtr,TQCString> slist;
378 KSortableValueList<SPtr,TQCString> glist;
379 for (List::ConstIterator it(
group->m_serviceList.begin()); it !=
group->m_serviceList.end(); ++it)
381 KSycocaEntry *p = (*it);
384 bool noDisplay = p->isType(KST_KServiceGroup) ?
389 bool SuSEunimportant = p->isType(KST_KService) &&
390 static_cast<KService *
>(p)->SuSEunimportant();
391 if (excludeSuSEunimportant && SuSEunimportant)
395 KSortableValueList<SPtr,TQCString> & list = p->isType(KST_KServiceGroup) ? glist : slist;
397 if (p->isType(KST_KServiceGroup))
399 else if (sortByGenericName)
402 name = p->name() +
" " +
static_cast<KService *
>(p)->genericName();
404 TQCString key(
name.length() * 4 + 1 );
408 size_t ln = strxfrm( key.data(),
name.local8Bit().data(), key.size());
409 if( ln !=
size_t( -1 ))
411 if( ln >= key.size())
413 key.resize( ln + 1 );
414 if( strxfrm( key.data(),
name.local8Bit().data(), key.size()) ==
size_t( -1 ))
415 key =
name.local8Bit();
421 key =
name.local8Bit();
423 list.insert(key,SPtr(*it));
426 return group->SuSEsortEntries( slist, glist, excludeNoDisplay, allowSeparators );
430 KServiceGroup::SuSEsortEntries( KSortableValueList<SPtr,TQCString> slist, KSortableValueList<SPtr,TQCString> glist,
bool excludeNoDisplay,
bool allowSeparators )
438 if (d->sortOrder.isEmpty())
440 d->sortOrder <<
":M";
441 d->sortOrder <<
":F";
442 d->sortOrder <<
":OIH IL[4]";
446 if(rp ==
"/") rp = TQString::null;
450 for (TQStringList::ConstIterator it(d->sortOrder.begin()); it != d->sortOrder.end(); ++it)
452 const TQString &item = *it;
453 if (item.isEmpty())
continue;
456 TQString groupPath = rp + item.mid(1) +
"/";
458 for(KSortableValueList<SPtr,TQCString>::Iterator it2 = glist.begin(); it2 != glist.end(); ++it2)
461 if (
group->relPath() == groupPath)
468 else if (item[0] !=
':')
473 for(KSortableValueList<SPtr,TQCString>::Iterator it2 = slist.begin(); it2 != slist.end(); ++it2)
475 if (!(*it2).value()->isType(KST_KService))
478 if (service->
menuId() == item)
489 bool needSeparator =
false;
492 for (TQStringList::ConstIterator it(d->sortOrder.begin()); it != d->sortOrder.end(); ++it)
494 const TQString &item = *it;
495 if (item.isEmpty())
continue;
502 needSeparator =
true;
504 else if ( item.contains(
":O" ) )
507 TQString tmp( item );
508 tmp = tmp.remove(
":O");
509 TQStringList optionAttribute = TQStringList::split(
" ",tmp);
510 if( optionAttribute.count()==0)
511 optionAttribute.append(tmp);
513 bool showInline =
false;
515 bool showInlineAlias =
false;
518 for ( TQStringList::Iterator it3 = optionAttribute.begin(); it3 != optionAttribute.end(); ++it3 )
522 for(KSortableValueList<SPtr,TQCString>::Iterator it2 = glist.begin(); it2 != glist.end(); ++it2)
526 group->setAllowInline( showInline );
528 group->setInlineAlias( showInlineAlias );
533 else if (item ==
":M")
536 for(KSortableValueList<SPtr,TQCString>::Iterator it2 = glist.begin(); it2 != glist.end(); ++it2)
538 addItem(sorted, (*it2).value(), needSeparator);
541 else if (item ==
":F")
544 for(KSortableValueList<SPtr,TQCString>::Iterator it2 = slist.begin(); it2 != slist.end(); ++it2)
546 addItem(sorted, (*it2).value(), needSeparator);
549 else if (item ==
":A")
552 KSortableValueList<SPtr,TQCString>::Iterator it_s = slist.begin();
553 KSortableValueList<SPtr,TQCString>::Iterator it_g = glist.begin();
557 if (it_s == slist.end())
559 if (it_g == glist.end())
563 addItem(sorted, (*it_g).value(), needSeparator);
566 else if (it_g == glist.end())
569 addItem(sorted, (*it_s).value(), needSeparator);
572 else if ((*it_g).index() < (*it_s).index())
575 addItem(sorted, (*it_g).value(), needSeparator);
581 addItem(sorted, (*it_s).value(), needSeparator);
587 else if (item[0] ==
'/')
589 TQString groupPath = rp + item.mid(1) +
"/";
591 for (List::ConstIterator it2(
group->m_serviceList.begin()); it2 !=
group->m_serviceList.end(); ++it2)
593 if (!(*it2)->isType(KST_KServiceGroup))
596 if (
group->relPath() == groupPath)
598 if (!excludeNoDisplay || !
group->noDisplay())
600 const TQString &nextItem = *( ++it );
601 if ( nextItem.startsWith(
":O" ) )
603 TQString tmp( nextItem );
604 tmp = tmp.remove(
":O");
605 TQStringList optionAttribute = TQStringList::split(
" ",tmp);
606 if( optionAttribute.count()==0)
607 optionAttribute.append(tmp);
608 bool bShowEmptyMenu =
false;
609 bool bShowInline =
false;
610 bool bShowInlineHeader =
false;
611 bool bShowInlineAlias =
false;
613 for ( TQStringList::Iterator it3 = optionAttribute.begin(); it3 != optionAttribute.end(); ++it3 )
616 group->setShowEmptyMenu( bShowEmptyMenu );
617 group->setAllowInline( bShowInline );
618 group->setShowInlineHeader( bShowInlineHeader );
619 group->setInlineAlias( bShowInlineAlias );
626 addItem(sorted, (
group), needSeparator);
634 for (List::ConstIterator it2(
group->m_serviceList.begin()); it2 !=
group->m_serviceList.end(); ++it2)
636 if (!(*it2)->isType(KST_KService))
639 if (service->
menuId() == item)
641 if (!excludeNoDisplay || !service->
noDisplay())
642 addItem(sorted, (*it2), needSeparator);
652 void KServiceGroup::parseAttribute(
const TQString &item ,
bool &showEmptyMenu,
bool &showInline,
bool &showInlineHeader,
bool & showInlineAlias ,
int &inlineValue )
656 else if ( item ==
"NME")
658 else if( item ==
"I")
660 else if ( item ==
"NI")
662 else if( item ==
"IH")
664 else if ( item ==
"NIH")
666 else if( item ==
"IA")
667 showInlineAlias =
true;
668 else if ( item ==
"NIA")
669 showInlineAlias =
false;
670 else if( ( item ).contains(
"IL" ))
672 TQString tmp( item );
673 tmp = tmp.remove(
"IL[" );
674 tmp = tmp.remove(
"]" );
676 int _inlineValue = tmp.toInt(&ok);
682 kdDebug()<<
" This attribute is not supported :"<<item<<endl;
685 void KServiceGroup::setLayoutInfo(
const TQStringList &layout)
687 d->sortOrder = layout;
690 TQStringList KServiceGroup::layoutInfo()
const
698 return KServiceGroupFactory::self()->findBaseGroup(_baseGroupName,
true);
704 return KServiceGroupFactory::self()->findGroupByDesktopPath(
"/",
true);
711 return KServiceGroupFactory::self()->findGroupByDesktopPath(
relPath,
true);
717 return KServiceGroupFactory::self()->findGroupByDesktopPath(
"#parent#"+parent,
true);
723 return d->directoryEntryPath;
727 void KServiceGroup::virtual_hook(
int id,
void* data )
728 { KSycocaEntry::virtual_hook(
id, data ); }
731 KServiceSeparator::KServiceSeparator( )
732 : KSycocaEntry(
"separator")