00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
#include "kservicetypefactory.h"
00020
#include "ksycoca.h"
00021
#include "ksycocatype.h"
00022
#include "ksycocadict.h"
00023
#include "kservicetype.h"
00024
#include "kmimetype.h"
00025
#include "kuserprofile.h"
00026
00027
#include <kapplication.h>
00028
#include <kdebug.h>
00029
#include <assert.h>
00030
#include <kstringhandler.h>
00031
#include <qfile.h>
00032
00033 KServiceTypeFactory::KServiceTypeFactory()
00034 : KSycocaFactory( KST_KServiceTypeFactory )
00035 {
00036 _self =
this;
00037 m_fastPatternOffset = 0;
00038 m_otherPatternOffset = 0;
00039
if (m_str)
00040 {
00041
00042 Q_INT32 i,n;
00043 (*m_str) >> i;
00044 m_fastPatternOffset = i;
00045 (*m_str) >> i;
00046 m_otherPatternOffset = i;
00047 (*m_str) >> n;
00048
00049
if (n > 1024)
00050 {
00051 KSycoca::flagError();
00052 }
00053
else
00054 {
00055
QString str;
00056
for(;n;n--)
00057 {
00058
KSycocaEntry::read(*m_str, str);
00059 (*m_str) >> i;
00060 m_propertyTypeDict.insert(str, i);
00061 }
00062 }
00063 }
00064 }
00065
00066
00067 KServiceTypeFactory::~KServiceTypeFactory()
00068 {
00069 _self = 0L;
00070
KServiceTypeProfile::clear();
00071 }
00072
00073 KServiceTypeFactory * KServiceTypeFactory::self()
00074 {
00075
if (!_self)
00076 _self =
new KServiceTypeFactory();
00077
return _self;
00078 }
00079
00080
KServiceType * KServiceTypeFactory::findServiceTypeByName(
const QString &_name)
00081 {
00082
if (!m_sycocaDict)
return 0L;
00083 assert (!KSycoca::self()->isBuilding());
00084
int offset = m_sycocaDict->find_string( _name );
00085
if (!offset)
return 0;
00086
KServiceType * newServiceType = createEntry(offset);
00087
00088
00089
if (newServiceType && (newServiceType->
name() != _name))
00090 {
00091
00092
delete newServiceType;
00093 newServiceType = 0;
00094 }
00095
return newServiceType;
00096 }
00097
00098 QVariant::Type KServiceTypeFactory::findPropertyTypeByName(
const QString &_name)
00099 {
00100
if (!m_sycocaDict)
00101
return QVariant::Invalid;
00102
00103 assert (!KSycoca::self()->isBuilding());
00104
00105
QMapConstIterator<QString,int> it = m_propertyTypeDict.find(_name);
00106
if (it != m_propertyTypeDict.end()) {
00107
return (QVariant::Type)it.
data();
00108 }
00109
00110
return QVariant::Invalid;
00111 }
00112
00113
KMimeType * KServiceTypeFactory::findFromPattern(
const QString &_filename,
QString *match)
00114 {
00115
00116
if (!m_str)
return 0;
00117
00118
00119
QDataStream *str = m_str;
00120
00121 str->
device()->at( m_fastPatternOffset );
00122
00123 Q_INT32 nrOfEntries;
00124 (*str) >> nrOfEntries;
00125 Q_INT32 entrySize;
00126 (*str) >> entrySize;
00127
00128 Q_INT32 fastOffset = str->
device()->at( );
00129
00130 Q_INT32 matchingOffset = 0;
00131
00132
00133 Q_INT32 left = 0;
00134 Q_INT32 right = nrOfEntries - 1;
00135 Q_INT32 middle;
00136
00137
int lastDot = _filename.
findRev(
'.');
00138
int ext_len = _filename.
length() - lastDot - 1;
00139
if (lastDot != -1 && ext_len <= 4)
00140 {
00141
QString extension = _filename.
right( ext_len );
00142 extension = extension.
leftJustify(4);
00143
00144
QString pattern;
00145
while (left <= right) {
00146 middle = (left + right) / 2;
00147
00148 str->
device()->at( middle * entrySize + fastOffset );
00149
KSycocaEntry::read(*str, pattern);
00150
int cmp = pattern.
compare( extension );
00151
if (cmp < 0)
00152 left = middle + 1;
00153
else if (cmp == 0)
00154 {
00155 (*str) >> matchingOffset;
00156
00157
00158
if (match)
00159 *match =
"*."+pattern;
00160
break;
00161 }
00162
else
00163 right = middle - 1;
00164 }
00165 }
00166
00167
00168
if ( m_patterns.isEmpty() ) {
00169 str->
device()->at( m_otherPatternOffset );
00170
00171
QString pattern;
00172 Q_INT32 mimetypeOffset;
00173
00174
while (
true)
00175 {
00176
KSycocaEntry::read(*str, pattern);
00177
if (pattern.
isEmpty())
00178
break;
00179 (*str) >> mimetypeOffset;
00180 m_patterns.push_back( pattern );
00181 m_pattern_offsets.push_back( mimetypeOffset );
00182 }
00183 }
00184
00185 assert( m_patterns.size() == m_pattern_offsets.size() );
00186
00187 QStringList::const_iterator it = m_patterns.begin();
00188 QStringList::const_iterator
end = m_patterns.end();
00189
QValueVector<Q_INT32>::const_iterator it_offset = m_pattern_offsets.begin();
00190
00191
for ( ; it !=
end; ++it, ++it_offset )
00192 {
00193
if (
KStringHandler::matchFileName( _filename, *it ) )
00194 {
00195
if ( !matchingOffset || !(*it).endsWith(
"*" ) )
00196 {
00197 matchingOffset = *it_offset;
00198
if (match)
00199 *match = *it;
00200
break;
00201 }
00202 }
00203 }
00204
00205
if ( matchingOffset ) {
00206
KServiceType *newServiceType = createEntry( matchingOffset );
00207 assert (newServiceType && newServiceType->
isType( KST_KMimeType ));
00208
return (
KMimeType *) newServiceType;
00209 }
00210
else
00211
return 0;
00212 }
00213
00214 KMimeType::List KServiceTypeFactory::allMimeTypes()
00215 {
00216 KMimeType::List result;
00217
KSycocaEntry::List list = allEntries();
00218
for( KSycocaEntry::List::Iterator it = list.
begin();
00219 it != list.
end();
00220 ++it)
00221 {
00222
KMimeType *newMimeType = dynamic_cast<KMimeType *>((*it).data());
00223
if (newMimeType)
00224 result.append( KMimeType::Ptr( newMimeType ) );
00225 }
00226
return result;
00227 }
00228
00229 KServiceType::List KServiceTypeFactory::allServiceTypes()
00230 {
00231 KServiceType::List result;
00232
KSycocaEntry::List list = allEntries();
00233
for( KSycocaEntry::List::Iterator it = list.
begin();
00234 it != list.
end();
00235 ++it)
00236 {
00237
#ifndef Q_WS_QWS
00238
KServiceType *newServiceType = dynamic_cast<KServiceType *>((*it).data());
00239
#else //FIXME
00240
KServiceType *newServiceType = (
KServiceType*)(*it).data();
00241
#endif
00242
if (newServiceType)
00243 result.append( KServiceType::Ptr( newServiceType ) );
00244 }
00245
return result;
00246 }
00247
00248
bool KServiceTypeFactory::checkMimeTypes()
00249 {
00250
QDataStream *str = KSycoca::self()->findFactory( factoryId() );
00251
if (!str)
return false;
00252
00253
00254
return (m_beginEntryOffset != m_endEntryOffset);
00255 }
00256
00257
KServiceType * KServiceTypeFactory::createEntry(
int offset)
00258 {
00259
KServiceType *newEntry = 0;
00260 KSycocaType type;
00261
QDataStream *str = KSycoca::self()->findEntry(offset, type);
00262
if (!str)
return 0;
00263
00264
switch(type)
00265 {
00266
case KST_KServiceType:
00267 newEntry =
new KServiceType(*str, offset);
00268
break;
00269
case KST_KMimeType:
00270 newEntry =
new KMimeType(*str, offset);
00271
break;
00272
case KST_KFolderType:
00273 newEntry =
new KFolderType(*str, offset);
00274
break;
00275
case KST_KDEDesktopMimeType:
00276 newEntry =
new KDEDesktopMimeType(*str, offset);
00277
break;
00278
case KST_KExecMimeType:
00279 newEntry =
new KExecMimeType(*str, offset);
00280
break;
00281
00282
default:
00283
kdError(7011) <<
QString(
"KServiceTypeFactory: unexpected object entry in KSycoca database (type = %1)").arg((
int)type) <<
endl;
00284
break;
00285 }
00286
if (!newEntry->
isValid())
00287 {
00288
kdError(7011) <<
"KServiceTypeFactory: corrupt object in KSycoca database!\n" <<
endl;
00289
delete newEntry;
00290 newEntry = 0;
00291 }
00292
return newEntry;
00293 }
00294
00295 KServiceTypeFactory *KServiceTypeFactory::_self = 0;
00296
00297
void KServiceTypeFactory::virtual_hook(
int id,
void* data )
00298 { KSycocaFactory::virtual_hook(
id, data ); }
00299
00300