1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/os/textandloc/fontservices/textshaperplugin/IcuSource/common/serv.h Fri Jun 15 03:10:57 2012 +0200
1.3 @@ -0,0 +1,1006 @@
1.4 +/**
1.5 + *******************************************************************************
1.6 + * Copyright (C) 2001-2005, International Business Machines Corporation. *
1.7 + * All Rights Reserved. *
1.8 + *******************************************************************************
1.9 + */
1.10 +
1.11 +#ifndef ICUSERV_H
1.12 +#define ICUSERV_H
1.13 +
1.14 +#include "unicode/utypes.h"
1.15 +
1.16 +#if UCONFIG_NO_SERVICE
1.17 +
1.18 +U_NAMESPACE_BEGIN
1.19 +
1.20 +/*
1.21 + * Allow the declaration of APIs with pointers to ICUService
1.22 + * even when service is removed from the build.
1.23 + */
1.24 +class ICUService;
1.25 +
1.26 +U_NAMESPACE_END
1.27 +
1.28 +#else
1.29 +
1.30 +#include "unicode/unistr.h"
1.31 +#include "unicode/locid.h"
1.32 +
1.33 +#include "hash.h"
1.34 +#include "uvector.h"
1.35 +#include "servnotf.h"
1.36 +
1.37 +class ICUServiceTest;
1.38 +
1.39 +U_NAMESPACE_BEGIN
1.40 +
1.41 +class ICUServiceKey;
1.42 +class ICUServiceFactory;
1.43 +class SimpleFactory;
1.44 +class ServiceListener;
1.45 +class ICUService;
1.46 +
1.47 +class DNCache;
1.48 +
1.49 +/*******************************************************************
1.50 + * ICUServiceKey
1.51 + */
1.52 +
1.53 +/**
1.54 + * <p>ICUServiceKeys are used to communicate with factories to
1.55 + * generate an instance of the service. ICUServiceKeys define how
1.56 + * ids are canonicalized, provide both a current id and a current
1.57 + * descriptor to use in querying the cache and factories, and
1.58 + * determine the fallback strategy.</p>
1.59 + *
1.60 + * <p>ICUServiceKeys provide both a currentDescriptor and a currentID.
1.61 + * The descriptor contains an optional prefix, followed by '/'
1.62 + * and the currentID. Factories that handle complex keys,
1.63 + * for example number format factories that generate multiple
1.64 + * kinds of formatters for the same locale, use the descriptor
1.65 + * to provide a fully unique identifier for the service object,
1.66 + * while using the currentID (in this case, the locale string),
1.67 + * as the visible IDs that can be localized.</p>
1.68 + *
1.69 + * <p>The default implementation of ICUServiceKey has no fallbacks and
1.70 + * has no custom descriptors.</p>
1.71 + */
1.72 +class U_COMMON_API ICUServiceKey : public UObject {
1.73 + private:
1.74 + const UnicodeString _id;
1.75 +
1.76 + protected:
1.77 + static const UChar PREFIX_DELIMITER;
1.78 +
1.79 + public:
1.80 +
1.81 + /**
1.82 + * <p>Construct a key from an id.</p>
1.83 + *
1.84 + * @param id the ID from which to construct the key.
1.85 + */
1.86 + ICUServiceKey(const UnicodeString& id);
1.87 +
1.88 + /**
1.89 + * <p>Virtual destructor.</p>
1.90 + */
1.91 + virtual ~ICUServiceKey();
1.92 +
1.93 + /**
1.94 + * <p>Return the original ID used to construct this key.</p>
1.95 + *
1.96 + * @return the ID used to construct this key.
1.97 + */
1.98 + virtual const UnicodeString& getID() const;
1.99 +
1.100 + /**
1.101 + * <p>Return the canonical version of the original ID. This implementation
1.102 + * appends the original ID to result. Result is returned as a convenience.</p>
1.103 + *
1.104 + * @param result the output parameter to which the id will be appended.
1.105 + * @return the modified result.
1.106 + */
1.107 + virtual UnicodeString& canonicalID(UnicodeString& result) const;
1.108 +
1.109 + /**
1.110 + * <p>Return the (canonical) current ID. This implementation appends
1.111 + * the canonical ID to result. Result is returned as a convenience.</p>
1.112 + *
1.113 + * @param result the output parameter to which the current id will be appended.
1.114 + * @return the modified result.
1.115 + */
1.116 + virtual UnicodeString& currentID(UnicodeString& result) const;
1.117 +
1.118 + /**
1.119 + * <p>Return the current descriptor. This implementation appends
1.120 + * the current descriptor to result. Result is returned as a convenience.</p>
1.121 + *
1.122 + * <p>The current descriptor is used to fully
1.123 + * identify an instance of the service in the cache. A
1.124 + * factory may handle all descriptors for an ID, or just a
1.125 + * particular descriptor. The factory can either parse the
1.126 + * descriptor or use custom API on the key in order to
1.127 + * instantiate the service.</p>
1.128 + *
1.129 + * @param result the output parameter to which the current id will be appended.
1.130 + * @return the modified result.
1.131 + */
1.132 + virtual UnicodeString& currentDescriptor(UnicodeString& result) const;
1.133 +
1.134 + /**
1.135 + * <p>If the key has a fallback, modify the key and return true,
1.136 + * otherwise return false. The current ID will change if there
1.137 + * is a fallback. No currentIDs should be repeated, and fallback
1.138 + * must eventually return false. This implementation has no fallbacks
1.139 + * and always returns false.</p>
1.140 + *
1.141 + * @return TRUE if the ICUServiceKey changed to a valid fallback value.
1.142 + */
1.143 + virtual UBool fallback();
1.144 +
1.145 + /**
1.146 + * <p>Return TRUE if a key created from id matches, or would eventually
1.147 + * fallback to match, the canonical ID of this ICUServiceKey.</p>
1.148 + *
1.149 + * @param id the id to test.
1.150 + * @return TRUE if this ICUServiceKey's canonical ID is a fallback of id.
1.151 + */
1.152 + virtual UBool isFallbackOf(const UnicodeString& id) const;
1.153 +
1.154 + /**
1.155 + * <p>Return the prefix. This implementation leaves result unchanged.
1.156 + * Result is returned as a convenience.</p>
1.157 + *
1.158 + * @param result the output parameter to which the prefix will be appended.
1.159 + * @return the modified result.
1.160 + */
1.161 + virtual UnicodeString& prefix(UnicodeString& result) const;
1.162 +
1.163 + /**
1.164 + * <p>A utility to parse the prefix out of a descriptor string. Only
1.165 + * the (undelimited) prefix, if any, remains in result. Result is returned as a
1.166 + * convenience.</p>
1.167 + *
1.168 + * @param result an input/output parameter that on entry is a descriptor, and
1.169 + * on exit is the prefix of that descriptor.
1.170 + * @return the modified result.
1.171 + */
1.172 + static UnicodeString& parsePrefix(UnicodeString& result);
1.173 +
1.174 + /**
1.175 + * <p>A utility to parse the suffix out of a descriptor string. Only
1.176 + * the (undelimited) suffix, if any, remains in result. Result is returned as a
1.177 + * convenience.</p>
1.178 + *
1.179 + * @param result an input/output parameter that on entry is a descriptor, and
1.180 + * on exit is the suffix of that descriptor.
1.181 + * @return the modified result.
1.182 + */
1.183 + static UnicodeString& parseSuffix(UnicodeString& result);
1.184 +
1.185 +public:
1.186 + /**
1.187 + * UObject RTTI boilerplate.
1.188 + */
1.189 + static UClassID U_EXPORT2 getStaticClassID();
1.190 +
1.191 + /**
1.192 + * UObject RTTI boilerplate.
1.193 + */
1.194 + virtual UClassID getDynamicClassID() const;
1.195 +
1.196 +#ifdef SERVICE_DEBUG
1.197 + public:
1.198 + virtual UnicodeString& debug(UnicodeString& result) const;
1.199 + virtual UnicodeString& debugClass(UnicodeString& result) const;
1.200 +#endif
1.201 +
1.202 +};
1.203 +
1.204 + /*******************************************************************
1.205 + * ICUServiceFactory
1.206 + */
1.207 +
1.208 + /**
1.209 + * <p>An implementing ICUServiceFactory generates the service objects maintained by the
1.210 + * service. A factory generates a service object from a key,
1.211 + * updates id->factory mappings, and returns the display name for
1.212 + * a supported id.</p>
1.213 + */
1.214 +class U_COMMON_API ICUServiceFactory : public UObject {
1.215 + public:
1.216 +
1.217 + /**
1.218 + * <p>Create a service object from the key, if this factory
1.219 + * supports the key. Otherwise, return NULL.</p>
1.220 + *
1.221 + * <p>If the factory supports the key, then it can call
1.222 + * the service's getKey(ICUServiceKey, String[], ICUServiceFactory) method
1.223 + * passing itself as the factory to get the object that
1.224 + * the service would have created prior to the factory's
1.225 + * registration with the service. This can change the
1.226 + * key, so any information required from the key should
1.227 + * be extracted before making such a callback.</p>
1.228 + *
1.229 + * @param key the service key.
1.230 + * @param service the service with which this factory is registered.
1.231 + * @param status the error code status.
1.232 + * @return the service object, or NULL if the factory does not support the key.
1.233 + */
1.234 + virtual UObject* create(const ICUServiceKey& key, const ICUService* service, UErrorCode& status) const = 0;
1.235 +
1.236 + /**
1.237 + * <p>Update result to reflect the IDs (not descriptors) that this
1.238 + * factory publicly handles. Result contains mappings from ID to
1.239 + * factory. On entry it will contain all (visible) mappings from
1.240 + * previously-registered factories.</p>
1.241 + *
1.242 + * <p>This function, together with getDisplayName, are used to
1.243 + * support ICUService::getDisplayNames. The factory determines
1.244 + * which IDs (of those it supports) it will make visible, and of
1.245 + * those, which it will provide localized display names for. In
1.246 + * most cases it will register mappings from all IDs it supports
1.247 + * to itself.</p>
1.248 + *
1.249 + * @param result the mapping table to update.
1.250 + * @param status the error code status.
1.251 + */
1.252 + virtual void updateVisibleIDs(Hashtable& result, UErrorCode& status) const = 0;
1.253 +
1.254 + /**
1.255 + * <p>Return, in result, the display name of the id in the provided locale.
1.256 + * This is an id, not a descriptor. If the id is
1.257 + * not visible, sets result to bogus. If the
1.258 + * incoming result is bogus, it remains bogus. Result is returned as a
1.259 + * convenience. Results are not defined if id is not one supported by this
1.260 + * factory.</p>
1.261 + *
1.262 + * @param id a visible id supported by this factory.
1.263 + * @param locale the locale for which to generate the corresponding localized display name.
1.264 + * @param result output parameter to hold the display name.
1.265 + * @return result.
1.266 + */
1.267 + virtual UnicodeString& getDisplayName(const UnicodeString& id, const Locale& locale, UnicodeString& result) const = 0;
1.268 +};
1.269 +
1.270 +/*
1.271 + ******************************************************************
1.272 + */
1.273 +
1.274 + /**
1.275 + * <p>A default implementation of factory. This provides default
1.276 + * implementations for subclasses, and implements a singleton
1.277 + * factory that matches a single ID and returns a single
1.278 + * (possibly deferred-initialized) instance. This implements
1.279 + * updateVisibleIDs to add a mapping from its ID to itself
1.280 + * if visible is true, or to remove any existing mapping
1.281 + * for its ID if visible is false. No localization of display
1.282 + * names is performed.</p>
1.283 + */
1.284 +class U_COMMON_API SimpleFactory : public ICUServiceFactory {
1.285 + protected:
1.286 + UObject* _instance;
1.287 + const UnicodeString _id;
1.288 + const UBool _visible;
1.289 +
1.290 + public:
1.291 + /**
1.292 + * <p>Construct a SimpleFactory that maps a single ID to a single
1.293 + * service instance. If visible is TRUE, the ID will be visible.
1.294 + * The instance must not be NULL. The SimpleFactory will adopt
1.295 + * the instance, which must not be changed subsequent to this call.</p>
1.296 + *
1.297 + * @param instanceToAdopt the service instance to adopt.
1.298 + * @param id the ID to assign to this service instance.
1.299 + * @param visible if TRUE, the ID will be visible.
1.300 + */
1.301 + SimpleFactory(UObject* instanceToAdopt, const UnicodeString& id, UBool visible = TRUE);
1.302 +
1.303 + /**
1.304 + * <p>Destructor.</p>
1.305 + */
1.306 + virtual ~SimpleFactory();
1.307 +
1.308 + /**
1.309 + * <p>This implementation returns a clone of the service instance if the factory's ID is equal to
1.310 + * the key's currentID. Service and prefix are ignored.</p>
1.311 + *
1.312 + * @param key the service key.
1.313 + * @param service the service with which this factory is registered.
1.314 + * @param status the error code status.
1.315 + * @return the service object, or NULL if the factory does not support the key.
1.316 + */
1.317 + virtual UObject* create(const ICUServiceKey& key, const ICUService* service, UErrorCode& status) const;
1.318 +
1.319 + /**
1.320 + * <p>This implementation adds a mapping from ID -> this to result if visible is TRUE,
1.321 + * otherwise it removes ID from result.</p>
1.322 + *
1.323 + * @param result the mapping table to update.
1.324 + * @param status the error code status.
1.325 + */
1.326 + virtual void updateVisibleIDs(Hashtable& result, UErrorCode& status) const;
1.327 +
1.328 + /**
1.329 + * <p>This implementation returns the factory ID if it equals id and visible is TRUE,
1.330 + * otherwise it returns the empty string. (This implementation provides
1.331 + * no localized id information.)</p>
1.332 + *
1.333 + * @param id a visible id supported by this factory.
1.334 + * @param locale the locale for which to generate the corresponding localized display name.
1.335 + * @param result output parameter to hold the display name.
1.336 + * @return result.
1.337 + */
1.338 + virtual UnicodeString& getDisplayName(const UnicodeString& id, const Locale& locale, UnicodeString& result) const;
1.339 +
1.340 +public:
1.341 + /**
1.342 + * UObject RTTI boilerplate.
1.343 + */
1.344 + static UClassID U_EXPORT2 getStaticClassID();
1.345 +
1.346 + /**
1.347 + * UObject RTTI boilerplate.
1.348 + */
1.349 + virtual UClassID getDynamicClassID() const;
1.350 +
1.351 +#ifdef SERVICE_DEBUG
1.352 + public:
1.353 + virtual UnicodeString& debug(UnicodeString& toAppendTo) const;
1.354 + virtual UnicodeString& debugClass(UnicodeString& toAppendTo) const;
1.355 +#endif
1.356 +
1.357 +};
1.358 +
1.359 +/*
1.360 + ******************************************************************
1.361 + */
1.362 +
1.363 +/**
1.364 + * <p>ServiceListener is the listener that ICUService provides by default.
1.365 + * ICUService will notifiy this listener when factories are added to
1.366 + * or removed from the service. Subclasses can provide
1.367 + * different listener interfaces that extend EventListener, and modify
1.368 + * acceptsListener and notifyListener as appropriate.</p>
1.369 + */
1.370 +class U_COMMON_API ServiceListener : public EventListener {
1.371 +public:
1.372 + /**
1.373 + * <p>This method is called when the service changes. At the time of the
1.374 + * call this listener is registered with the service. It must
1.375 + * not modify the notifier in the context of this call.</p>
1.376 + *
1.377 + * @param service the service that changed.
1.378 + */
1.379 + virtual void serviceChanged(const ICUService& service) const = 0;
1.380 +
1.381 +public:
1.382 + /**
1.383 + * UObject RTTI boilerplate.
1.384 + */
1.385 + static UClassID U_EXPORT2 getStaticClassID();
1.386 +
1.387 + /**
1.388 + * UObject RTTI boilerplate.
1.389 + */
1.390 + virtual UClassID getDynamicClassID() const;
1.391 +
1.392 +};
1.393 +
1.394 +/*
1.395 + ******************************************************************
1.396 + */
1.397 +
1.398 +/**
1.399 + * <p>A StringPair holds a displayName/ID pair. ICUService uses it
1.400 + * as the array elements returned by getDisplayNames.
1.401 + */
1.402 +class U_COMMON_API StringPair : public UMemory {
1.403 +public:
1.404 + /**
1.405 + * <p>The display name of the pair.</p>
1.406 + */
1.407 + const UnicodeString displayName;
1.408 +
1.409 + /**
1.410 + * <p>The ID of the pair.</p>
1.411 + */
1.412 + const UnicodeString id;
1.413 +
1.414 + /**
1.415 + * <p>Creates a string pair from a displayName and an ID.</p>
1.416 + *
1.417 + * @param displayName the displayName.
1.418 + * @param id the ID.
1.419 + * @param status the error code status.
1.420 + * @return a StringPair if the creation was successful, otherwise NULL.
1.421 + */
1.422 + static StringPair* create(const UnicodeString& displayName,
1.423 + const UnicodeString& id,
1.424 + UErrorCode& status);
1.425 +
1.426 + /**
1.427 + * <p>Return TRUE if either string of the pair is bogus.</p>
1.428 + * @return TRUE if either string of the pair is bogus.
1.429 + */
1.430 + UBool isBogus() const;
1.431 +
1.432 +private:
1.433 + StringPair(const UnicodeString& displayName, const UnicodeString& id);
1.434 +};
1.435 +
1.436 +/**
1.437 + * Deleter for StringPairs
1.438 + */
1.439 +U_CAPI void U_EXPORT2
1.440 +userv_deleteStringPair(void *obj);
1.441 +
1.442 +/**
1.443 + * Opaque type returned by registerInstance and registerFactory.
1.444 + */
1.445 +typedef const void* URegistryKey;
1.446 +
1.447 +/*******************************************************************
1.448 + * ICUService
1.449 + */
1.450 +
1.451 + /**
1.452 + * <p>A Service provides access to service objects that implement a
1.453 + * particular service, e.g. transliterators. Users provide a String
1.454 + * id (for example, a locale string) to the service, and get back an
1.455 + * object for that id. Service objects can be any kind of object. A
1.456 + * new service object is returned for each query. The caller is
1.457 + * responsible for deleting it.</p>
1.458 + *
1.459 + * <p>Services 'canonicalize' the query ID and use the canonical ID to
1.460 + * query for the service. The service also defines a mechanism to
1.461 + * 'fallback' the ID multiple times. Clients can optionally request
1.462 + * the actual ID that was matched by a query when they use an ID to
1.463 + * retrieve a service object.</p>
1.464 + *
1.465 + * <p>Service objects are instantiated by ICUServiceFactory objects
1.466 + * registered with the service. The service queries each
1.467 + * ICUServiceFactory in turn, from most recently registered to
1.468 + * earliest registered, until one returns a service object. If none
1.469 + * responds with a service object, a fallback ID is generated, and the
1.470 + * process repeats until a service object is returned or until the ID
1.471 + * has no further fallbacks.</p>
1.472 + *
1.473 + * <p>In ICU 2.4, UObject (the base class of service instances) does
1.474 + * not define a polymorphic clone function. ICUService uses clones to
1.475 + * manage ownership. Thus, for now, ICUService defines an abstract
1.476 + * method, cloneInstance, that clients must implement to create clones
1.477 + * of the service instances. This may change in future releases of
1.478 + * ICU.</p>
1.479 + *
1.480 + * <p>ICUServiceFactories can be dynamically registered and
1.481 + * unregistered with the service. When registered, an
1.482 + * ICUServiceFactory is installed at the head of the factory list, and
1.483 + * so gets 'first crack' at any keys or fallback keys. When
1.484 + * unregistered, it is removed from the service and can no longer be
1.485 + * located through it. Service objects generated by this factory and
1.486 + * held by the client are unaffected.</p>
1.487 + *
1.488 + * <p>If a service has variants (e.g., the different variants of
1.489 + * BreakIterator) an ICUServiceFactory can use the prefix of the
1.490 + * ICUServiceKey to determine the variant of a service to generate.
1.491 + * If it does not support all variants, it can request
1.492 + * previously-registered factories to handle the ones it does not
1.493 + * support.</p>
1.494 + *
1.495 + * <p>ICUService uses ICUServiceKeys to query factories and perform
1.496 + * fallback. The ICUServiceKey defines the canonical form of the ID,
1.497 + * and implements the fallback strategy. Custom ICUServiceKeys can be
1.498 + * defined that parse complex IDs into components that
1.499 + * ICUServiceFactories can more easily use. The ICUServiceKey can
1.500 + * cache the results of this parsing to save repeated effort.
1.501 + * ICUService provides convenience APIs that take UnicodeStrings and
1.502 + * generate default ICUServiceKeys for use in querying.</p>
1.503 + *
1.504 + * <p>ICUService provides API to get the list of IDs publicly
1.505 + * supported by the service (although queries aren't restricted to
1.506 + * this list). This list contains only 'simple' IDs, and not fully
1.507 + * unique IDs. ICUServiceFactories are associated with each simple ID
1.508 + * and the responsible factory can also return a human-readable
1.509 + * localized version of the simple ID, for use in user interfaces.
1.510 + * ICUService can also provide an array of the all the localized
1.511 + * visible IDs and their corresponding internal IDs.</p>
1.512 + *
1.513 + * <p>ICUService implements ICUNotifier, so that clients can register
1.514 + * to receive notification when factories are added or removed from
1.515 + * the service. ICUService provides a default EventListener
1.516 + * subinterface, ServiceListener, which can be registered with the
1.517 + * service. When the service changes, the ServiceListener's
1.518 + * serviceChanged method is called with the service as the
1.519 + * argument.</p>
1.520 + *
1.521 + * <p>The ICUService API is both rich and generic, and it is expected
1.522 + * that most implementations will statically 'wrap' ICUService to
1.523 + * present a more appropriate API-- for example, to declare the type
1.524 + * of the objects returned from get, to limit the factories that can
1.525 + * be registered with the service, or to define their own listener
1.526 + * interface with a custom callback method. They might also customize
1.527 + * ICUService by overriding it, for example, to customize the
1.528 + * ICUServiceKey and fallback strategy. ICULocaleService is a
1.529 + * subclass of ICUService that uses Locale names as IDs and uses
1.530 + * ICUServiceKeys that implement the standard resource bundle fallback
1.531 + * strategy. Most clients will wish to subclass it instead of
1.532 + * ICUService.</p>
1.533 + */
1.534 +class U_COMMON_API ICUService : public ICUNotifier {
1.535 + protected:
1.536 + /**
1.537 + * Name useful for debugging.
1.538 + */
1.539 + const UnicodeString name;
1.540 +
1.541 + private:
1.542 +
1.543 + /**
1.544 + * single lock used by this service.
1.545 + */
1.546 + UMTX lock;
1.547 +
1.548 + /**
1.549 + * Timestamp so iterators can be fail-fast.
1.550 + */
1.551 + uint32_t timestamp;
1.552 +
1.553 + /**
1.554 + * All the factories registered with this service.
1.555 + */
1.556 + UVector* factories;
1.557 +
1.558 + /**
1.559 + * The service cache.
1.560 + */
1.561 + Hashtable* serviceCache;
1.562 +
1.563 + /**
1.564 + * The ID cache.
1.565 + */
1.566 + Hashtable* idCache;
1.567 +
1.568 + /**
1.569 + * The name cache.
1.570 + */
1.571 + DNCache* dnCache;
1.572 +
1.573 + /**
1.574 + * Constructor.
1.575 + */
1.576 + public:
1.577 + /**
1.578 + * <p>Construct a new ICUService.</p>
1.579 + */
1.580 + ICUService();
1.581 +
1.582 + /**
1.583 + * <p>Construct with a name (useful for debugging).</p>
1.584 + *
1.585 + * @param name a name to use in debugging.
1.586 + */
1.587 + ICUService(const UnicodeString& name);
1.588 +
1.589 + /**
1.590 + * <p>Destructor.</p>
1.591 + */
1.592 + virtual ~ICUService();
1.593 +
1.594 + /**
1.595 + * <p>Return the name of this service. This will be the empty string if none was assigned.
1.596 + * Returns result as a convenience.</p>
1.597 + *
1.598 + * @param result an output parameter to contain the name of this service.
1.599 + * @return the name of this service.
1.600 + */
1.601 + UnicodeString& getName(UnicodeString& result) const;
1.602 +
1.603 + /**
1.604 + * <p>Convenience override for get(ICUServiceKey&, UnicodeString*). This uses
1.605 + * createKey to create a key for the provided descriptor.</p>
1.606 + *
1.607 + * @param descriptor the descriptor.
1.608 + * @param status the error code status.
1.609 + * @return the service instance, or NULL.
1.610 + */
1.611 + UObject* get(const UnicodeString& descriptor, UErrorCode& status) const;
1.612 +
1.613 + /**
1.614 + * <p>Convenience override for get(ICUServiceKey&, UnicodeString*). This uses
1.615 + * createKey to create a key from the provided descriptor.</p>
1.616 + *
1.617 + * @param descriptor the descriptor.
1.618 + * @param actualReturn a pointer to a UnicodeString to hold the matched descriptor, or NULL.
1.619 + * @param status the error code status.
1.620 + * @return the service instance, or NULL.
1.621 + */
1.622 + UObject* get(const UnicodeString& descriptor, UnicodeString* actualReturn, UErrorCode& status) const;
1.623 +
1.624 + /**
1.625 + * <p>Convenience override for get(ICUServiceKey&, UnicodeString*).</p>
1.626 + *
1.627 + * @param key the key.
1.628 + * @param status the error code status.
1.629 + * @return the service instance, or NULL.
1.630 + */
1.631 + UObject* getKey(ICUServiceKey& key, UErrorCode& status) const;
1.632 +
1.633 + /**
1.634 + * <p>Given a key, return a service object, and, if actualReturn
1.635 + * is not NULL, the descriptor with which it was found in the
1.636 + * first element of actualReturn. If no service object matches
1.637 + * this key, returns NULL and leaves actualReturn unchanged.</p>
1.638 + *
1.639 + * <p>This queries the cache using the key's descriptor, and if no
1.640 + * object in the cache matches, tries the key on each
1.641 + * registered factory, in order. If none generates a service
1.642 + * object for the key, repeats the process with each fallback of
1.643 + * the key, until either a factory returns a service object, or the key
1.644 + * has no fallback. If no object is found, the result of handleDefault
1.645 + * is returned.</p>
1.646 + *
1.647 + * <p>Subclasses can override this method to further customize the
1.648 + * result before returning it.
1.649 + *
1.650 + * @param key the key.
1.651 + * @param actualReturn a pointer to a UnicodeString to hold the matched descriptor, or NULL.
1.652 + * @param status the error code status.
1.653 + * @return the service instance, or NULL.
1.654 + */
1.655 + virtual UObject* getKey(ICUServiceKey& key, UnicodeString* actualReturn, UErrorCode& status) const;
1.656 +
1.657 + /**
1.658 + * <p>This version of getKey is only called by ICUServiceFactories within the scope
1.659 + * of a previous getKey call, to determine what previously-registered factories would
1.660 + * have returned. For details, see getKey(ICUServiceKey&, UErrorCode&). Subclasses
1.661 + * should not call it directly, but call through one of the other get functions.</p>
1.662 + *
1.663 + * @param key the key.
1.664 + * @param actualReturn a pointer to a UnicodeString to hold the matched descriptor, or NULL.
1.665 + * @param factory the factory making the recursive call.
1.666 + * @param status the error code status.
1.667 + * @return the service instance, or NULL.
1.668 + */
1.669 + UObject* getKey(ICUServiceKey& key, UnicodeString* actualReturn, const ICUServiceFactory* factory, UErrorCode& status) const;
1.670 +
1.671 + /**
1.672 + * <p>Convenience override for getVisibleIDs(String) that passes null
1.673 + * as the fallback, thus returning all visible IDs.</p>
1.674 + *
1.675 + * @param result a vector to hold the returned IDs.
1.676 + * @param status the error code status.
1.677 + * @return the result vector.
1.678 + */
1.679 + UVector& getVisibleIDs(UVector& result, UErrorCode& status) const;
1.680 +
1.681 + /**
1.682 + * <p>Return a snapshot of the visible IDs for this service. This
1.683 + * list will not change as ICUServiceFactories are added or removed, but the
1.684 + * supported IDs will, so there is no guarantee that all and only
1.685 + * the IDs in the returned list will be visible and supported by the
1.686 + * service in subsequent calls.</p>
1.687 + *
1.688 + * <p>The IDs are returned as pointers to UnicodeStrings. The
1.689 + * caller owns the IDs. Previous contents of result are discarded before
1.690 + * new elements, if any, are added.</p>
1.691 + *
1.692 + * <p>matchID is passed to createKey to create a key. If the key
1.693 + * is not NULL, its isFallbackOf method is used to filter out IDs
1.694 + * that don't match the key or have it as a fallback.</p>
1.695 + *
1.696 + * @param result a vector to hold the returned IDs.
1.697 + * @param matchID an ID used to filter the result, or NULL if all IDs are desired.
1.698 + * @param status the error code status.
1.699 + * @return the result vector.
1.700 + */
1.701 + UVector& getVisibleIDs(UVector& result, const UnicodeString* matchID, UErrorCode& status) const;
1.702 +
1.703 + /**
1.704 + * <p>Convenience override for getDisplayName(const UnicodeString&, const Locale&, UnicodeString&) that
1.705 + * uses the current default locale.</p>
1.706 + *
1.707 + * @param id the ID for which to retrieve the localized displayName.
1.708 + * @param result an output parameter to hold the display name.
1.709 + * @return the modified result.
1.710 + */
1.711 + UnicodeString& getDisplayName(const UnicodeString& id, UnicodeString& result) const;
1.712 +
1.713 + /**
1.714 + * <p>Given a visible ID, return the display name in the requested locale.
1.715 + * If there is no directly supported ID corresponding to this ID, result is
1.716 + * set to bogus.</p>
1.717 + *
1.718 + * @param id the ID for which to retrieve the localized displayName.
1.719 + * @param result an output parameter to hold the display name.
1.720 + * @param locale the locale in which to localize the ID.
1.721 + * @return the modified result.
1.722 + */
1.723 + UnicodeString& getDisplayName(const UnicodeString& id, UnicodeString& result, const Locale& locale) const;
1.724 +
1.725 + /**
1.726 + * <p>Convenience override of getDisplayNames(const Locale&, const UnicodeString*) that
1.727 + * uses the current default Locale as the locale and NULL for
1.728 + * the matchID.</p>
1.729 + *
1.730 + * @param result a vector to hold the returned displayName/id StringPairs.
1.731 + * @param status the error code status.
1.732 + * @return the modified result vector.
1.733 + */
1.734 + UVector& getDisplayNames(UVector& result, UErrorCode& status) const;
1.735 +
1.736 + /**
1.737 + * <p>Convenience override of getDisplayNames(const Locale&, const UnicodeString*) that
1.738 + * uses NULL for the matchID.</p>
1.739 + *
1.740 + * @param result a vector to hold the returned displayName/id StringPairs.
1.741 + * @param locale the locale in which to localize the ID.
1.742 + * @param status the error code status.
1.743 + * @return the modified result vector.
1.744 + */
1.745 + UVector& getDisplayNames(UVector& result, const Locale& locale, UErrorCode& status) const;
1.746 +
1.747 + /**
1.748 + * <p>Return a snapshot of the mapping from display names to visible
1.749 + * IDs for this service. This set will not change as factories
1.750 + * are added or removed, but the supported IDs will, so there is
1.751 + * no guarantee that all and only the IDs in the returned map will
1.752 + * be visible and supported by the service in subsequent calls,
1.753 + * nor is there any guarantee that the current display names match
1.754 + * those in the result.</p>
1.755 + *
1.756 + * <p>The names are returned as pointers to StringPairs, which
1.757 + * contain both the displayName and the corresponding ID. The
1.758 + * caller owns the StringPairs. Previous contents of result are
1.759 + * discarded before new elements, if any, are added.</p>
1.760 + *
1.761 + * <p>matchID is passed to createKey to create a key. If the key
1.762 + * is not NULL, its isFallbackOf method is used to filter out IDs
1.763 + * that don't match the key or have it as a fallback.</p>
1.764 + *
1.765 + * @param result a vector to hold the returned displayName/id StringPairs.
1.766 + * @param locale the locale in which to localize the ID.
1.767 + * @param matchID an ID used to filter the result, or NULL if all IDs are desired.
1.768 + * @param status the error code status.
1.769 + * @return the result vector. */
1.770 + UVector& getDisplayNames(UVector& result,
1.771 + const Locale& locale,
1.772 + const UnicodeString* matchID,
1.773 + UErrorCode& status) const;
1.774 +
1.775 + /**
1.776 + * <p>A convenience override of registerInstance(UObject*, const UnicodeString&, UBool)
1.777 + * that defaults visible to TRUE.</p>
1.778 + *
1.779 + * @param objToAdopt the object to register and adopt.
1.780 + * @param id the ID to assign to this object.
1.781 + * @param status the error code status.
1.782 + * @return a registry key that can be passed to unregister to unregister
1.783 + * (and discard) this instance.
1.784 + */
1.785 + URegistryKey registerInstance(UObject* objToAdopt, const UnicodeString& id, UErrorCode& status);
1.786 +
1.787 + /**
1.788 + * <p>Register a service instance with the provided ID. The ID will be
1.789 + * canonicalized. The canonicalized ID will be returned by
1.790 + * getVisibleIDs if visible is TRUE. The service instance will be adopted and
1.791 + * must not be modified subsequent to this call.</p>
1.792 + *
1.793 + * <p>This issues a serviceChanged notification to registered listeners.</p>
1.794 + *
1.795 + * <p>This implementation wraps the object using
1.796 + * createSimpleFactory, and calls registerFactory.</p>
1.797 + *
1.798 + * @param objToAdopt the object to register and adopt.
1.799 + * @param id the ID to assign to this object.
1.800 + * @param visible TRUE if getVisibleIDs is to return this ID.
1.801 + * @param status the error code status.
1.802 + * @return a registry key that can be passed to unregister() to unregister
1.803 + * (and discard) this instance.
1.804 + */
1.805 + virtual URegistryKey registerInstance(UObject* objToAdopt, const UnicodeString& id, UBool visible, UErrorCode& status);
1.806 +
1.807 + /**
1.808 + * <p>Register an ICUServiceFactory. Returns a registry key that
1.809 + * can be used to unregister the factory. The factory
1.810 + * must not be modified subsequent to this call. The service owns
1.811 + * all registered factories. In case of an error, the factory is
1.812 + * deleted.</p>
1.813 + *
1.814 + * <p>This issues a serviceChanged notification to registered listeners.</p>
1.815 + *
1.816 + * <p>The default implementation accepts all factories.</p>
1.817 + *
1.818 + * @param factoryToAdopt the factory to register and adopt.
1.819 + * @param status the error code status.
1.820 + * @return a registry key that can be passed to unregister to unregister
1.821 + * (and discard) this factory.
1.822 + */
1.823 + virtual URegistryKey registerFactory(ICUServiceFactory* factoryToAdopt, UErrorCode& status);
1.824 +
1.825 + /**
1.826 + * <p>Unregister a factory using a registry key returned by
1.827 + * registerInstance or registerFactory. After a successful call,
1.828 + * the factory will be removed from the service factory list and
1.829 + * deleted, and the key becomes invalid.</p>
1.830 + *
1.831 + * <p>This issues a serviceChanged notification to registered
1.832 + * listeners.</p>
1.833 + *
1.834 + * @param rkey the registry key.
1.835 + * @param status the error code status.
1.836 + * @return TRUE if the call successfully unregistered the factory.
1.837 + */
1.838 + virtual UBool unregister(URegistryKey rkey, UErrorCode& status);
1.839 +
1.840 + /**
1.841 + * </p>Reset the service to the default factories. The factory
1.842 + * lock is acquired and then reInitializeFactories is called.</p>
1.843 + *
1.844 + * <p>This issues a serviceChanged notification to registered listeners.</p>
1.845 + */
1.846 + virtual void reset(void);
1.847 +
1.848 + /**
1.849 + * <p>Return TRUE if the service is in its default state.</p>
1.850 + *
1.851 + * <p>The default implementation returns TRUE if there are no
1.852 + * factories registered.</p>
1.853 + */
1.854 + virtual UBool isDefault(void) const;
1.855 +
1.856 + /**
1.857 + * <p>Create a key from an ID. If ID is NULL, returns NULL.</p>
1.858 + *
1.859 + * <p>The default implementation creates an ICUServiceKey instance.
1.860 + * Subclasses can override to define more useful keys appropriate
1.861 + * to the factories they accept.</p>
1.862 + *
1.863 + * @param a pointer to the ID for which to create a default ICUServiceKey.
1.864 + * @param status the error code status.
1.865 + * @return the ICUServiceKey corresponding to ID, or NULL.
1.866 + */
1.867 + virtual ICUServiceKey* createKey(const UnicodeString* id, UErrorCode& status) const;
1.868 +
1.869 + /**
1.870 + * <p>Clone object so that caller can own the copy. In ICU2.4, UObject doesn't define
1.871 + * clone, so we need an instance-aware method that knows how to do this.
1.872 + * This is public so factories can call it, but should really be protected.</p>
1.873 + *
1.874 + * @param instance the service instance to clone.
1.875 + * @return a clone of the passed-in instance, or NULL if cloning was unsuccessful.
1.876 + */
1.877 + virtual UObject* cloneInstance(UObject* instance) const = 0;
1.878 +
1.879 +
1.880 + /************************************************************************
1.881 + * Subclassing API
1.882 + */
1.883 +
1.884 + protected:
1.885 +
1.886 + /**
1.887 + * <p>Create a factory that wraps a single service object. Called by registerInstance.</p>
1.888 + *
1.889 + * <p>The default implementation returns an instance of SimpleFactory.</p>
1.890 + *
1.891 + * @param instanceToAdopt the service instance to adopt.
1.892 + * @param id the ID to assign to this service instance.
1.893 + * @param visible if TRUE, the ID will be visible.
1.894 + * @param status the error code status.
1.895 + * @return an instance of ICUServiceFactory that maps this instance to the provided ID.
1.896 + */
1.897 + virtual ICUServiceFactory* createSimpleFactory(UObject* instanceToAdopt, const UnicodeString& id, UBool visible, UErrorCode& status);
1.898 +
1.899 + /**
1.900 + * <p>Reinitialize the factory list to its default state. After this call, isDefault()
1.901 + * must return TRUE.</p>
1.902 + *
1.903 + * <p>This issues a serviceChanged notification to registered listeners.</p>
1.904 + *
1.905 + * <p>The default implementation clears the factory list.
1.906 + * Subclasses can override to provide other default initialization
1.907 + * of the factory list. Subclasses must not call this method
1.908 + * directly, since it must only be called while holding write
1.909 + * access to the factory list.</p>
1.910 + */
1.911 + virtual void reInitializeFactories(void);
1.912 +
1.913 + /**
1.914 + * <p>Default handler for this service if no factory in the factory list
1.915 + * handled the key passed to getKey.</p>
1.916 + *
1.917 + * <p>The default implementation returns NULL.</p>
1.918 + *
1.919 + * @param key the key.
1.920 + * @param actualReturn a pointer to a UnicodeString to hold the matched descriptor, or NULL.
1.921 + * @param status the error code status.
1.922 + * @return the service instance, or NULL.
1.923 + */
1.924 + virtual UObject* handleDefault(const ICUServiceKey& key, UnicodeString* actualReturn, UErrorCode& status) const;
1.925 +
1.926 + /**
1.927 + * <p>Clear caches maintained by this service.</p>
1.928 + *
1.929 + * <p>Subclasses can override if they implement additional caches
1.930 + * that need to be cleared when the service changes. Subclasses
1.931 + * should generally not call this method directly, as it must only
1.932 + * be called while synchronized on the factory lock.</p>
1.933 + */
1.934 + virtual void clearCaches(void);
1.935 +
1.936 + /**
1.937 + * <p>Return true if the listener is accepted.</p>
1.938 + *
1.939 + * <p>The default implementation accepts the listener if it is
1.940 + * a ServiceListener. Subclasses can override this to accept
1.941 + * different listeners.</p>
1.942 + *
1.943 + * @param l the listener to test.
1.944 + * @return TRUE if the service accepts the listener.
1.945 + */
1.946 + virtual UBool acceptsListener(const EventListener& l) const;
1.947 +
1.948 + /**
1.949 + * <p>Notify the listener of a service change.</p>
1.950 + *
1.951 + * <p>The default implementation assumes a ServiceListener.
1.952 + * If acceptsListener has been overridden to accept different
1.953 + * listeners, this should be overridden as well.</p>
1.954 + *
1.955 + * @param l the listener to notify.
1.956 + */
1.957 + virtual void notifyListener(EventListener& l) const;
1.958 +
1.959 + /************************************************************************
1.960 + * Utilities for subclasses.
1.961 + */
1.962 +
1.963 + /**
1.964 + * <p>Clear only the service cache.</p>
1.965 + *
1.966 + * <p>This can be called by subclasses when a change affects the service
1.967 + * cache but not the ID caches, e.g., when the default locale changes
1.968 + * the resolution of IDs also changes, requiring the cache to be
1.969 + * flushed, but not the visible IDs themselves.</p>
1.970 + */
1.971 + void clearServiceCache(void);
1.972 +
1.973 + /**
1.974 + * <p>Return a map from visible IDs to factories.
1.975 + * This must only be called when the mutex is held.</p>
1.976 + *
1.977 + * @param status the error code status.
1.978 + * @return a Hashtable containing mappings from visible
1.979 + * IDs to factories.
1.980 + */
1.981 + const Hashtable* getVisibleIDMap(UErrorCode& status) const;
1.982 +
1.983 + /**
1.984 + * <p>Allow subclasses to read the time stamp.</p>
1.985 + *
1.986 + * @return the timestamp.
1.987 + */
1.988 + int32_t getTimestamp(void) const;
1.989 +
1.990 + /**
1.991 + * <p>Return the number of registered factories.</p>
1.992 + *
1.993 + * @return the number of factories registered at the time of the call.
1.994 + */
1.995 + int32_t countFactories(void) const;
1.996 +
1.997 +private:
1.998 +
1.999 + friend class ::ICUServiceTest; // give tests access to countFactories.
1.1000 +};
1.1001 +
1.1002 +U_NAMESPACE_END
1.1003 +
1.1004 + /* UCONFIG_NO_SERVICE */
1.1005 +#endif
1.1006 +
1.1007 + /* ICUSERV_H */
1.1008 +#endif
1.1009 +