Coverage Report

Created: 2018-09-25 14:53

/src/mozilla-central/intl/icu/source/i18n/udat.cpp
Line
Count
Source (jump to first uncovered line)
1
// © 2016 and later: Unicode, Inc. and others.
2
// License & terms of use: http://www.unicode.org/copyright.html
3
/*
4
*******************************************************************************
5
*   Copyright (C) 1996-2015, International Business Machines
6
*   Corporation and others.  All Rights Reserved.
7
*******************************************************************************
8
*/
9
10
#include "unicode/utypes.h"
11
12
#if !UCONFIG_NO_FORMATTING
13
14
#include "unicode/udat.h"
15
16
#include "unicode/uloc.h"
17
#include "unicode/datefmt.h"
18
#include "unicode/timezone.h"
19
#include "unicode/smpdtfmt.h"
20
#include "unicode/fieldpos.h"
21
#include "unicode/parsepos.h"
22
#include "unicode/calendar.h"
23
#include "unicode/numfmt.h"
24
#include "unicode/dtfmtsym.h"
25
#include "unicode/ustring.h"
26
#include "unicode/udisplaycontext.h"
27
#include "unicode/ufieldpositer.h"
28
#include "cpputils.h"
29
#include "reldtfmt.h"
30
#include "umutex.h"
31
32
U_NAMESPACE_USE
33
34
/**
35
 * Verify that fmt is a SimpleDateFormat. Invalid error if not.
36
 * @param fmt the UDateFormat, definitely a DateFormat, maybe something else
37
 * @param status error code, will be set to failure if there is a familure or the fmt is NULL.
38
 */
39
0
static void verifyIsSimpleDateFormat(const UDateFormat* fmt, UErrorCode *status) {
40
0
   if(U_SUCCESS(*status) &&
41
0
       dynamic_cast<const SimpleDateFormat*>(reinterpret_cast<const DateFormat*>(fmt))==NULL) {
42
0
       *status = U_ILLEGAL_ARGUMENT_ERROR;
43
0
   }
44
0
}
45
46
// This mirrors the correspondence between the
47
// SimpleDateFormat::fgPatternIndexToDateFormatField and
48
// SimpleDateFormat::fgPatternIndexToCalendarField arrays.
49
static UCalendarDateFields gDateFieldMapping[] = {
50
    UCAL_ERA,                  // UDAT_ERA_FIELD = 0
51
    UCAL_YEAR,                 // UDAT_YEAR_FIELD = 1
52
    UCAL_MONTH,                // UDAT_MONTH_FIELD = 2
53
    UCAL_DATE,                 // UDAT_DATE_FIELD = 3
54
    UCAL_HOUR_OF_DAY,          // UDAT_HOUR_OF_DAY1_FIELD = 4
55
    UCAL_HOUR_OF_DAY,          // UDAT_HOUR_OF_DAY0_FIELD = 5
56
    UCAL_MINUTE,               // UDAT_MINUTE_FIELD = 6
57
    UCAL_SECOND,               // UDAT_SECOND_FIELD = 7
58
    UCAL_MILLISECOND,          // UDAT_FRACTIONAL_SECOND_FIELD = 8
59
    UCAL_DAY_OF_WEEK,          // UDAT_DAY_OF_WEEK_FIELD = 9
60
    UCAL_DAY_OF_YEAR,          // UDAT_DAY_OF_YEAR_FIELD = 10
61
    UCAL_DAY_OF_WEEK_IN_MONTH, // UDAT_DAY_OF_WEEK_IN_MONTH_FIELD = 11
62
    UCAL_WEEK_OF_YEAR,         // UDAT_WEEK_OF_YEAR_FIELD = 12
63
    UCAL_WEEK_OF_MONTH,        // UDAT_WEEK_OF_MONTH_FIELD = 13
64
    UCAL_AM_PM,                // UDAT_AM_PM_FIELD = 14
65
    UCAL_HOUR,                 // UDAT_HOUR1_FIELD = 15
66
    UCAL_HOUR,                 // UDAT_HOUR0_FIELD = 16
67
    UCAL_ZONE_OFFSET,          // UDAT_TIMEZONE_FIELD = 17
68
    UCAL_YEAR_WOY,             // UDAT_YEAR_WOY_FIELD = 18
69
    UCAL_DOW_LOCAL,            // UDAT_DOW_LOCAL_FIELD = 19
70
    UCAL_EXTENDED_YEAR,        // UDAT_EXTENDED_YEAR_FIELD = 20
71
    UCAL_JULIAN_DAY,           // UDAT_JULIAN_DAY_FIELD = 21
72
    UCAL_MILLISECONDS_IN_DAY,  // UDAT_MILLISECONDS_IN_DAY_FIELD = 22
73
    UCAL_ZONE_OFFSET,          // UDAT_TIMEZONE_RFC_FIELD = 23 (also UCAL_DST_OFFSET)
74
    UCAL_ZONE_OFFSET,          // UDAT_TIMEZONE_GENERIC_FIELD = 24 (also UCAL_DST_OFFSET)
75
    UCAL_DOW_LOCAL,            // UDAT_STANDALONE_DAY_FIELD = 25
76
    UCAL_MONTH,                // UDAT_STANDALONE_MONTH_FIELD = 26
77
    UCAL_MONTH,                // UDAT_QUARTER_FIELD = 27
78
    UCAL_MONTH,                // UDAT_STANDALONE_QUARTER_FIELD = 28
79
    UCAL_ZONE_OFFSET,          // UDAT_TIMEZONE_SPECIAL_FIELD = 29 (also UCAL_DST_OFFSET)
80
    UCAL_YEAR,                 // UDAT_YEAR_NAME_FIELD = 30
81
    UCAL_ZONE_OFFSET,          // UDAT_TIMEZONE_LOCALIZED_GMT_OFFSET_FIELD = 31 (also UCAL_DST_OFFSET)
82
    UCAL_ZONE_OFFSET,          // UDAT_TIMEZONE_ISO_FIELD = 32 (also UCAL_DST_OFFSET)
83
    UCAL_ZONE_OFFSET,          // UDAT_TIMEZONE_ISO_LOCAL_FIELD = 33 (also UCAL_DST_OFFSET)
84
    UCAL_EXTENDED_YEAR,        // UDAT_RELATED_YEAR_FIELD = 34 (not an exact match)
85
    UCAL_FIELD_COUNT,          // UDAT_FIELD_COUNT = 35
86
    // UCAL_IS_LEAP_MONTH is not the target of a mapping
87
};
88
89
U_CAPI UCalendarDateFields U_EXPORT2
90
0
udat_toCalendarDateField(UDateFormatField field) {
91
0
  return gDateFieldMapping[field];
92
0
}
93
94
/* For now- one opener. */
95
static UDateFormatOpener gOpener = NULL;
96
97
U_INTERNAL void U_EXPORT2
98
udat_registerOpener(UDateFormatOpener opener, UErrorCode *status)
99
0
{
100
0
  if(U_FAILURE(*status)) return;
101
0
  umtx_lock(NULL);
102
0
  if(gOpener==NULL) {
103
0
    gOpener = opener;
104
0
  } else {
105
0
    *status = U_ILLEGAL_ARGUMENT_ERROR;
106
0
  }
107
0
  umtx_unlock(NULL);
108
0
}
109
110
U_INTERNAL UDateFormatOpener U_EXPORT2
111
udat_unregisterOpener(UDateFormatOpener opener, UErrorCode *status)
112
0
{
113
0
  if(U_FAILURE(*status)) return NULL;
114
0
  UDateFormatOpener oldOpener = NULL;
115
0
  umtx_lock(NULL);
116
0
  if(gOpener==NULL || gOpener!=opener) {
117
0
    *status = U_ILLEGAL_ARGUMENT_ERROR;
118
0
  } else {
119
0
    oldOpener=gOpener;
120
0
    gOpener=NULL;
121
0
  }
122
0
  umtx_unlock(NULL);
123
0
  return oldOpener;
124
0
}
125
126
127
128
U_CAPI UDateFormat* U_EXPORT2
129
udat_open(UDateFormatStyle  timeStyle,
130
          UDateFormatStyle  dateStyle,
131
          const char        *locale,
132
          const UChar       *tzID,
133
          int32_t           tzIDLength,
134
          const UChar       *pattern,
135
          int32_t           patternLength,
136
          UErrorCode        *status)
137
0
{
138
0
    DateFormat *fmt;
139
0
    if(U_FAILURE(*status)) {
140
0
        return 0;
141
0
    }
142
0
    if(gOpener!=NULL) { // if it's registered
143
0
      fmt = (DateFormat*) (*gOpener)(timeStyle,dateStyle,locale,tzID,tzIDLength,pattern,patternLength,status);
144
0
      if(fmt!=NULL) {
145
0
        return (UDateFormat*)fmt;
146
0
      } // else fall through.
147
0
    }
148
0
    if(timeStyle != UDAT_PATTERN) {
149
0
        if(locale == 0) {
150
0
            fmt = DateFormat::createDateTimeInstance((DateFormat::EStyle)dateStyle,
151
0
                (DateFormat::EStyle)timeStyle);
152
0
        }
153
0
        else {
154
0
            fmt = DateFormat::createDateTimeInstance((DateFormat::EStyle)dateStyle,
155
0
                (DateFormat::EStyle)timeStyle,
156
0
                Locale(locale));
157
0
        }
158
0
    }
159
0
    else {
160
0
        UnicodeString pat((UBool)(patternLength == -1), pattern, patternLength);
161
0
162
0
        if(locale == 0) {
163
0
            fmt = new SimpleDateFormat(pat, *status);
164
0
        }
165
0
        else {
166
0
            fmt = new SimpleDateFormat(pat, Locale(locale), *status);
167
0
        }
168
0
    }
169
0
170
0
    if(fmt == 0) {
171
0
        *status = U_MEMORY_ALLOCATION_ERROR;
172
0
        return 0;
173
0
    }
174
0
175
0
    if(tzID != 0) {
176
0
        TimeZone *zone = TimeZone::createTimeZone(UnicodeString((UBool)(tzIDLength == -1), tzID, tzIDLength));
177
0
        if(zone == 0) {
178
0
            *status = U_MEMORY_ALLOCATION_ERROR;
179
0
            delete fmt;
180
0
            return 0;
181
0
        }
182
0
        fmt->adoptTimeZone(zone);
183
0
    }
184
0
185
0
    return (UDateFormat*)fmt;
186
0
}
187
188
189
U_CAPI void U_EXPORT2
190
udat_close(UDateFormat* format)
191
0
{
192
0
    delete (DateFormat*)format;
193
0
}
194
195
U_CAPI UDateFormat* U_EXPORT2
196
udat_clone(const UDateFormat *fmt,
197
       UErrorCode *status)
198
0
{
199
0
    if(U_FAILURE(*status)) return 0;
200
0
201
0
    Format *res = ((DateFormat*)fmt)->clone();
202
0
203
0
    if(res == 0) {
204
0
        *status = U_MEMORY_ALLOCATION_ERROR;
205
0
        return 0;
206
0
    }
207
0
208
0
    return (UDateFormat*) res;
209
0
}
210
211
U_CAPI int32_t U_EXPORT2
212
udat_format(    const    UDateFormat*    format,
213
        UDate           dateToFormat,
214
        UChar*          result,
215
        int32_t         resultLength,
216
        UFieldPosition* position,
217
        UErrorCode*     status)
218
0
{
219
0
    if(U_FAILURE(*status)) {
220
0
        return -1;
221
0
    }
222
0
    if (result == NULL ? resultLength != 0 : resultLength < 0) {
223
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
224
0
        return -1;
225
0
    }
226
0
227
0
    UnicodeString res;
228
0
    if (result != NULL) {
229
0
        // NULL destination for pure preflighting: empty dummy string
230
0
        // otherwise, alias the destination buffer
231
0
        res.setTo(result, 0, resultLength);
232
0
    }
233
0
234
0
    FieldPosition fp;
235
0
236
0
    if(position != 0)
237
0
        fp.setField(position->field);
238
0
239
0
    ((DateFormat*)format)->format(dateToFormat, res, fp);
240
0
241
0
    if(position != 0) {
242
0
        position->beginIndex = fp.getBeginIndex();
243
0
        position->endIndex = fp.getEndIndex();
244
0
    }
245
0
246
0
    return res.extract(result, resultLength, *status);
247
0
}
248
249
U_CAPI int32_t U_EXPORT2
250
udat_formatCalendar(const UDateFormat*  format,
251
        UCalendar*      calendar,
252
        UChar*          result,
253
        int32_t         resultLength,
254
        UFieldPosition* position,
255
        UErrorCode*     status)
256
0
{
257
0
    if(U_FAILURE(*status)) {
258
0
        return -1;
259
0
    }
260
0
    if (result == NULL ? resultLength != 0 : resultLength < 0) {
261
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
262
0
        return -1;
263
0
    }
264
0
265
0
    UnicodeString res;
266
0
    if (result != NULL) {
267
0
        // NULL destination for pure preflighting: empty dummy string
268
0
        // otherwise, alias the destination buffer
269
0
        res.setTo(result, 0, resultLength);
270
0
    }
271
0
272
0
    FieldPosition fp;
273
0
274
0
    if(position != 0)
275
0
        fp.setField(position->field);
276
0
277
0
    ((DateFormat*)format)->format(*(Calendar*)calendar, res, fp);
278
0
279
0
    if(position != 0) {
280
0
        position->beginIndex = fp.getBeginIndex();
281
0
        position->endIndex = fp.getEndIndex();
282
0
    }
283
0
284
0
    return res.extract(result, resultLength, *status);
285
0
}
286
287
U_CAPI int32_t U_EXPORT2
288
udat_formatForFields(    const    UDateFormat*    format,
289
        UDate           dateToFormat,
290
        UChar*          result,
291
        int32_t         resultLength,
292
        UFieldPositionIterator* fpositer,
293
        UErrorCode*     status)
294
0
{
295
0
    if(U_FAILURE(*status)) {
296
0
        return -1;
297
0
    }
298
0
    if (result == NULL ? resultLength != 0 : resultLength < 0) {
299
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
300
0
        return -1;
301
0
    }
302
0
303
0
    UnicodeString res;
304
0
    if (result != NULL) {
305
0
        // NULL destination for pure preflighting: empty dummy string
306
0
        // otherwise, alias the destination buffer
307
0
        res.setTo(result, 0, resultLength);
308
0
    }
309
0
310
0
    ((DateFormat*)format)->format(dateToFormat, res, (FieldPositionIterator*)fpositer, *status);
311
0
312
0
    return res.extract(result, resultLength, *status);
313
0
}
314
315
U_CAPI int32_t U_EXPORT2
316
udat_formatCalendarForFields(const UDateFormat*  format,
317
        UCalendar*      calendar,
318
        UChar*          result,
319
        int32_t         resultLength,
320
        UFieldPositionIterator* fpositer,
321
        UErrorCode*     status)
322
0
{
323
0
    if(U_FAILURE(*status)) {
324
0
        return -1;
325
0
    }
326
0
    if (result == NULL ? resultLength != 0 : resultLength < 0) {
327
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
328
0
        return -1;
329
0
    }
330
0
331
0
    UnicodeString res;
332
0
    if (result != NULL) {
333
0
        // NULL destination for pure preflighting: empty dummy string
334
0
        // otherwise, alias the destination buffer
335
0
        res.setTo(result, 0, resultLength);
336
0
    }
337
0
338
0
    ((DateFormat*)format)->format(*(Calendar*)calendar, res, (FieldPositionIterator*)fpositer, *status);
339
0
340
0
    return res.extract(result, resultLength, *status);
341
0
}
342
343
U_CAPI UDate U_EXPORT2
344
udat_parse(    const    UDateFormat*        format,
345
        const    UChar*          text,
346
        int32_t         textLength,
347
        int32_t         *parsePos,
348
        UErrorCode      *status)
349
0
{
350
0
    if(U_FAILURE(*status)) return (UDate)0;
351
0
352
0
    const UnicodeString src((UBool)(textLength == -1), text, textLength);
353
0
    ParsePosition pp;
354
0
    int32_t stackParsePos = 0;
355
0
    UDate res;
356
0
357
0
    if(parsePos == NULL) {
358
0
        parsePos = &stackParsePos;
359
0
    }
360
0
361
0
    pp.setIndex(*parsePos);
362
0
363
0
    res = ((DateFormat*)format)->parse(src, pp);
364
0
365
0
    if(pp.getErrorIndex() == -1)
366
0
        *parsePos = pp.getIndex();
367
0
    else {
368
0
        *parsePos = pp.getErrorIndex();
369
0
        *status = U_PARSE_ERROR;
370
0
    }
371
0
372
0
    return res;
373
0
}
374
375
U_CAPI void U_EXPORT2
376
udat_parseCalendar(const    UDateFormat*    format,
377
                            UCalendar*      calendar,
378
                   const    UChar*          text,
379
                            int32_t         textLength,
380
                            int32_t         *parsePos,
381
                            UErrorCode      *status)
382
0
{
383
0
    if(U_FAILURE(*status)) return;
384
0
385
0
    const UnicodeString src((UBool)(textLength == -1), text, textLength);
386
0
    ParsePosition pp;
387
0
    int32_t stackParsePos = 0;
388
0
389
0
    if(parsePos == NULL) {
390
0
        parsePos = &stackParsePos;
391
0
    }
392
0
393
0
    pp.setIndex(*parsePos);
394
0
395
0
    ((DateFormat*)format)->parse(src, *(Calendar*)calendar, pp);
396
0
397
0
    if(pp.getErrorIndex() == -1)
398
0
        *parsePos = pp.getIndex();
399
0
    else {
400
0
        *parsePos = pp.getErrorIndex();
401
0
        *status = U_PARSE_ERROR;
402
0
    }
403
0
}
404
405
U_CAPI UBool U_EXPORT2
406
udat_isLenient(const UDateFormat* fmt)
407
0
{
408
0
    return ((DateFormat*)fmt)->isLenient();
409
0
}
410
411
U_CAPI void U_EXPORT2
412
udat_setLenient(    UDateFormat*    fmt,
413
            UBool          isLenient)
414
0
{
415
0
    ((DateFormat*)fmt)->setLenient(isLenient);
416
0
}
417
418
U_DRAFT UBool U_EXPORT2
419
udat_getBooleanAttribute(const UDateFormat* fmt, 
420
                         UDateFormatBooleanAttribute attr, 
421
                         UErrorCode* status)
422
0
{
423
0
    if(U_FAILURE(*status)) return FALSE;
424
0
    return ((DateFormat*)fmt)->getBooleanAttribute(attr, *status);
425
0
    //return FALSE;
426
0
}
427
428
U_DRAFT void U_EXPORT2
429
udat_setBooleanAttribute(UDateFormat *fmt, 
430
                         UDateFormatBooleanAttribute attr, 
431
                         UBool newValue, 
432
                         UErrorCode* status)
433
0
{
434
0
    if(U_FAILURE(*status)) return;
435
0
    ((DateFormat*)fmt)->setBooleanAttribute(attr, newValue, *status);
436
0
}
437
438
U_CAPI const UCalendar* U_EXPORT2
439
udat_getCalendar(const UDateFormat* fmt)
440
0
{
441
0
    return (const UCalendar*) ((DateFormat*)fmt)->getCalendar();
442
0
}
443
444
U_CAPI void U_EXPORT2
445
udat_setCalendar(UDateFormat*    fmt,
446
                 const   UCalendar*      calendarToSet)
447
0
{
448
0
    ((DateFormat*)fmt)->setCalendar(*((Calendar*)calendarToSet));
449
0
}
450
451
U_DRAFT const UNumberFormat* U_EXPORT2 
452
udat_getNumberFormatForField(const UDateFormat* fmt, UChar field)
453
0
{
454
0
    UErrorCode status = U_ZERO_ERROR;
455
0
    verifyIsSimpleDateFormat(fmt, &status);
456
0
    if (U_FAILURE(status)) return (const UNumberFormat*) ((DateFormat*)fmt)->getNumberFormat();
457
0
    return (const UNumberFormat*) ((SimpleDateFormat*)fmt)->getNumberFormatForField(field);
458
0
}
459
460
U_CAPI const UNumberFormat* U_EXPORT2
461
udat_getNumberFormat(const UDateFormat* fmt)
462
0
{
463
0
    return (const UNumberFormat*) ((DateFormat*)fmt)->getNumberFormat();
464
0
}
465
466
U_DRAFT void U_EXPORT2 
467
udat_adoptNumberFormatForFields(           UDateFormat*    fmt,
468
                                    const  UChar*          fields,
469
                                           UNumberFormat*  numberFormatToSet,
470
                                           UErrorCode*     status)
471
0
{
472
0
    verifyIsSimpleDateFormat(fmt, status);
473
0
    if (U_FAILURE(*status)) return;
474
0
    
475
0
    if (fields!=NULL) {
476
0
        UnicodeString overrideFields(fields);
477
0
        ((SimpleDateFormat*)fmt)->adoptNumberFormat(overrideFields, (NumberFormat*)numberFormatToSet, *status);
478
0
    }
479
0
}
480
481
U_CAPI void U_EXPORT2
482
udat_setNumberFormat(UDateFormat*    fmt,
483
                     const   UNumberFormat*  numberFormatToSet)
484
0
{
485
0
    ((DateFormat*)fmt)->setNumberFormat(*((NumberFormat*)numberFormatToSet));
486
0
}
487
488
U_DRAFT void U_EXPORT2
489
udat_adoptNumberFormat(      UDateFormat*    fmt,
490
                             UNumberFormat*  numberFormatToAdopt)
491
0
{
492
0
    ((DateFormat*)fmt)->adoptNumberFormat((NumberFormat*)numberFormatToAdopt);
493
0
}
494
495
U_CAPI const char* U_EXPORT2
496
udat_getAvailable(int32_t index)
497
0
{
498
0
    return uloc_getAvailable(index);
499
0
}
500
501
U_CAPI int32_t U_EXPORT2
502
udat_countAvailable()
503
0
{
504
0
    return uloc_countAvailable();
505
0
}
506
507
U_CAPI UDate U_EXPORT2
508
udat_get2DigitYearStart(    const   UDateFormat     *fmt,
509
                        UErrorCode      *status)
510
0
{
511
0
    verifyIsSimpleDateFormat(fmt, status);
512
0
    if(U_FAILURE(*status)) return (UDate)0;
513
0
    return ((SimpleDateFormat*)fmt)->get2DigitYearStart(*status);
514
0
}
515
516
U_CAPI void U_EXPORT2
517
udat_set2DigitYearStart(    UDateFormat     *fmt,
518
                        UDate           d,
519
                        UErrorCode      *status)
520
0
{
521
0
    verifyIsSimpleDateFormat(fmt, status);
522
0
    if(U_FAILURE(*status)) return;
523
0
    ((SimpleDateFormat*)fmt)->set2DigitYearStart(d, *status);
524
0
}
525
526
U_CAPI int32_t U_EXPORT2
527
udat_toPattern(    const   UDateFormat     *fmt,
528
        UBool          localized,
529
        UChar           *result,
530
        int32_t         resultLength,
531
        UErrorCode      *status)
532
0
{
533
0
    if(U_FAILURE(*status)) {
534
0
        return -1;
535
0
    }
536
0
    if (result == NULL ? resultLength != 0 : resultLength < 0) {
537
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
538
0
        return -1;
539
0
    }
540
0
541
0
    UnicodeString res;
542
0
    if (result != NULL) {
543
0
        // NULL destination for pure preflighting: empty dummy string
544
0
        // otherwise, alias the destination buffer
545
0
        res.setTo(result, 0, resultLength);
546
0
    }
547
0
548
0
    const DateFormat *df=reinterpret_cast<const DateFormat *>(fmt);
549
0
    const SimpleDateFormat *sdtfmt=dynamic_cast<const SimpleDateFormat *>(df);
550
0
    const RelativeDateFormat *reldtfmt;
551
0
    if (sdtfmt!=NULL) {
552
0
        if(localized)
553
0
            sdtfmt->toLocalizedPattern(res, *status);
554
0
        else
555
0
            sdtfmt->toPattern(res);
556
0
    } else if (!localized && (reldtfmt=dynamic_cast<const RelativeDateFormat *>(df))!=NULL) {
557
0
        reldtfmt->toPattern(res, *status);
558
0
    } else {
559
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
560
0
        return -1;
561
0
    }
562
0
563
0
    return res.extract(result, resultLength, *status);
564
0
}
565
566
// TODO: should this take an UErrorCode?
567
// A: Yes. Of course.
568
U_CAPI void U_EXPORT2
569
udat_applyPattern(  UDateFormat     *format,
570
                    UBool          localized,
571
                    const   UChar           *pattern,
572
                    int32_t         patternLength)
573
0
{
574
0
    const UnicodeString pat((UBool)(patternLength == -1), pattern, patternLength);
575
0
    UErrorCode status = U_ZERO_ERROR;
576
0
577
0
    verifyIsSimpleDateFormat(format, &status);
578
0
    if(U_FAILURE(status)) {
579
0
        return;
580
0
    }
581
0
    
582
0
    if(localized)
583
0
        ((SimpleDateFormat*)format)->applyLocalizedPattern(pat, status);
584
0
    else
585
0
        ((SimpleDateFormat*)format)->applyPattern(pat);
586
0
}
587
588
U_CAPI int32_t U_EXPORT2
589
udat_getSymbols(const   UDateFormat     *fmt,
590
                UDateFormatSymbolType   type,
591
                int32_t                 index,
592
                UChar                   *result,
593
                int32_t                 resultLength,
594
                UErrorCode              *status)
595
0
{
596
0
    const DateFormatSymbols *syms;
597
0
    const SimpleDateFormat* sdtfmt;
598
0
    const RelativeDateFormat* rdtfmt;
599
0
    if ((sdtfmt = dynamic_cast<const SimpleDateFormat*>(reinterpret_cast<const DateFormat*>(fmt))) != NULL) {
600
0
        syms = sdtfmt->getDateFormatSymbols();
601
0
    } else if ((rdtfmt = dynamic_cast<const RelativeDateFormat*>(reinterpret_cast<const DateFormat*>(fmt))) != NULL) {
602
0
        syms = rdtfmt->getDateFormatSymbols();
603
0
    } else {
604
0
        return -1;
605
0
    }
606
0
    int32_t count;
607
0
    const UnicodeString *res = NULL;
608
0
609
0
    switch(type) {
610
0
    case UDAT_ERAS:
611
0
        res = syms->getEras(count);
612
0
        break;
613
0
614
0
    case UDAT_ERA_NAMES:
615
0
        res = syms->getEraNames(count);
616
0
        break;
617
0
618
0
    case UDAT_MONTHS:
619
0
        res = syms->getMonths(count);
620
0
        break;
621
0
622
0
    case UDAT_SHORT_MONTHS:
623
0
        res = syms->getShortMonths(count);
624
0
        break;
625
0
626
0
    case UDAT_WEEKDAYS:
627
0
        res = syms->getWeekdays(count);
628
0
        break;
629
0
630
0
    case UDAT_SHORT_WEEKDAYS:
631
0
        res = syms->getShortWeekdays(count);
632
0
        break;
633
0
634
0
    case UDAT_AM_PMS:
635
0
        res = syms->getAmPmStrings(count);
636
0
        break;
637
0
638
0
    case UDAT_LOCALIZED_CHARS:
639
0
        {
640
0
            UnicodeString res1;
641
0
            if(!(result==NULL && resultLength==0)) {
642
0
                // NULL destination for pure preflighting: empty dummy string
643
0
                // otherwise, alias the destination buffer
644
0
                res1.setTo(result, 0, resultLength);
645
0
            }
646
0
            syms->getLocalPatternChars(res1);
647
0
            return res1.extract(result, resultLength, *status);
648
0
        }
649
0
650
0
    case UDAT_NARROW_MONTHS:
651
0
        res = syms->getMonths(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
652
0
        break;
653
0
654
0
    case UDAT_SHORTER_WEEKDAYS:
655
0
        res = syms->getWeekdays(count, DateFormatSymbols::FORMAT, DateFormatSymbols::SHORT);
656
0
        break;
657
0
658
0
    case UDAT_NARROW_WEEKDAYS:
659
0
        res = syms->getWeekdays(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
660
0
        break;
661
0
662
0
    case UDAT_STANDALONE_MONTHS:
663
0
        res = syms->getMonths(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::WIDE);
664
0
        break;
665
0
666
0
    case UDAT_STANDALONE_SHORT_MONTHS:
667
0
        res = syms->getMonths(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::ABBREVIATED);
668
0
        break;
669
0
670
0
    case UDAT_STANDALONE_NARROW_MONTHS:
671
0
        res = syms->getMonths(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::NARROW);
672
0
        break;
673
0
674
0
    case UDAT_STANDALONE_WEEKDAYS:
675
0
        res = syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::WIDE);
676
0
        break;
677
0
678
0
    case UDAT_STANDALONE_SHORT_WEEKDAYS:
679
0
        res = syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::ABBREVIATED);
680
0
        break;
681
0
682
0
    case UDAT_STANDALONE_SHORTER_WEEKDAYS:
683
0
        res = syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::SHORT);
684
0
        break;
685
0
686
0
    case UDAT_STANDALONE_NARROW_WEEKDAYS:
687
0
        res = syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::NARROW);
688
0
        break;
689
0
690
0
    case UDAT_QUARTERS:
691
0
        res = syms->getQuarters(count, DateFormatSymbols::FORMAT, DateFormatSymbols::WIDE);
692
0
        break;
693
0
694
0
    case UDAT_SHORT_QUARTERS:
695
0
        res = syms->getQuarters(count, DateFormatSymbols::FORMAT, DateFormatSymbols::ABBREVIATED);
696
0
        break;
697
0
698
0
    case UDAT_STANDALONE_QUARTERS:
699
0
        res = syms->getQuarters(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::WIDE);
700
0
        break;
701
0
702
0
    case UDAT_STANDALONE_SHORT_QUARTERS:
703
0
        res = syms->getQuarters(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::ABBREVIATED);
704
0
        break;
705
0
706
0
    case UDAT_CYCLIC_YEARS_WIDE:
707
0
        res = syms->getYearNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::WIDE);
708
0
        break;
709
0
710
0
    case UDAT_CYCLIC_YEARS_ABBREVIATED:
711
0
        res = syms->getYearNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::ABBREVIATED);
712
0
        break;
713
0
714
0
    case UDAT_CYCLIC_YEARS_NARROW:
715
0
        res = syms->getYearNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
716
0
        break;
717
0
718
0
    case UDAT_ZODIAC_NAMES_WIDE:
719
0
        res = syms->getZodiacNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::WIDE);
720
0
        break;
721
0
722
0
    case UDAT_ZODIAC_NAMES_ABBREVIATED:
723
0
        res = syms->getZodiacNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::ABBREVIATED);
724
0
        break;
725
0
726
0
    case UDAT_ZODIAC_NAMES_NARROW:
727
0
        res = syms->getZodiacNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
728
0
        break;
729
0
730
0
    }
731
0
732
0
    if(index < count) {
733
0
        return res[index].extract(result, resultLength, *status);
734
0
    }
735
0
    return 0;
736
0
}
737
738
// TODO: also needs an errorCode.
739
U_CAPI int32_t U_EXPORT2
740
udat_countSymbols(    const    UDateFormat                *fmt,
741
            UDateFormatSymbolType    type)
742
0
{
743
0
    const DateFormatSymbols *syms;
744
0
    const SimpleDateFormat* sdtfmt;
745
0
    const RelativeDateFormat* rdtfmt;
746
0
    if ((sdtfmt = dynamic_cast<const SimpleDateFormat*>(reinterpret_cast<const DateFormat*>(fmt))) != NULL) {
747
0
        syms = sdtfmt->getDateFormatSymbols();
748
0
    } else if ((rdtfmt = dynamic_cast<const RelativeDateFormat*>(reinterpret_cast<const DateFormat*>(fmt))) != NULL) {
749
0
        syms = rdtfmt->getDateFormatSymbols();
750
0
    } else {
751
0
        return 0;
752
0
    }
753
0
    int32_t count = 0;
754
0
755
0
    switch(type) {
756
0
    case UDAT_ERAS:
757
0
        syms->getEras(count);
758
0
        break;
759
0
760
0
    case UDAT_MONTHS:
761
0
        syms->getMonths(count);
762
0
        break;
763
0
764
0
    case UDAT_SHORT_MONTHS:
765
0
        syms->getShortMonths(count);
766
0
        break;
767
0
768
0
    case UDAT_WEEKDAYS:
769
0
        syms->getWeekdays(count);
770
0
        break;
771
0
772
0
    case UDAT_SHORT_WEEKDAYS:
773
0
        syms->getShortWeekdays(count);
774
0
        break;
775
0
776
0
    case UDAT_AM_PMS:
777
0
        syms->getAmPmStrings(count);
778
0
        break;
779
0
780
0
    case UDAT_LOCALIZED_CHARS:
781
0
        count = 1;
782
0
        break;
783
0
784
0
    case UDAT_ERA_NAMES:
785
0
        syms->getEraNames(count);
786
0
        break;
787
0
788
0
    case UDAT_NARROW_MONTHS:
789
0
        syms->getMonths(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
790
0
        break;
791
0
792
0
    case UDAT_SHORTER_WEEKDAYS:
793
0
        syms->getWeekdays(count, DateFormatSymbols::FORMAT, DateFormatSymbols::SHORT);
794
0
        break;
795
0
796
0
    case UDAT_NARROW_WEEKDAYS:
797
0
        syms->getWeekdays(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
798
0
        break;
799
0
800
0
    case UDAT_STANDALONE_MONTHS:
801
0
        syms->getMonths(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::WIDE);
802
0
        break;
803
0
804
0
    case UDAT_STANDALONE_SHORT_MONTHS:
805
0
        syms->getMonths(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::ABBREVIATED);
806
0
        break;
807
0
808
0
    case UDAT_STANDALONE_NARROW_MONTHS:
809
0
        syms->getMonths(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::NARROW);
810
0
        break;
811
0
812
0
    case UDAT_STANDALONE_WEEKDAYS:
813
0
        syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::WIDE);
814
0
        break;
815
0
816
0
    case UDAT_STANDALONE_SHORT_WEEKDAYS:
817
0
        syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::ABBREVIATED);
818
0
        break;
819
0
820
0
    case UDAT_STANDALONE_SHORTER_WEEKDAYS:
821
0
        syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::SHORT);
822
0
        break;
823
0
824
0
    case UDAT_STANDALONE_NARROW_WEEKDAYS:
825
0
        syms->getWeekdays(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::NARROW);
826
0
        break;
827
0
828
0
    case UDAT_QUARTERS:
829
0
        syms->getQuarters(count, DateFormatSymbols::FORMAT, DateFormatSymbols::WIDE);
830
0
        break;
831
0
832
0
    case UDAT_SHORT_QUARTERS:
833
0
        syms->getQuarters(count, DateFormatSymbols::FORMAT, DateFormatSymbols::ABBREVIATED);
834
0
        break;
835
0
836
0
    case UDAT_STANDALONE_QUARTERS:
837
0
        syms->getQuarters(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::WIDE);
838
0
        break;
839
0
840
0
    case UDAT_STANDALONE_SHORT_QUARTERS:
841
0
        syms->getQuarters(count, DateFormatSymbols::STANDALONE, DateFormatSymbols::ABBREVIATED);
842
0
        break;
843
0
844
0
    case UDAT_CYCLIC_YEARS_WIDE:
845
0
        syms->getYearNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::WIDE);
846
0
        break;
847
0
848
0
    case UDAT_CYCLIC_YEARS_ABBREVIATED:
849
0
        syms->getYearNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::ABBREVIATED);
850
0
        break;
851
0
852
0
    case UDAT_CYCLIC_YEARS_NARROW:
853
0
        syms->getYearNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
854
0
        break;
855
0
856
0
    case UDAT_ZODIAC_NAMES_WIDE:
857
0
        syms->getZodiacNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::WIDE);
858
0
        break;
859
0
860
0
    case UDAT_ZODIAC_NAMES_ABBREVIATED:
861
0
        syms->getZodiacNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::ABBREVIATED);
862
0
        break;
863
0
864
0
    case UDAT_ZODIAC_NAMES_NARROW:
865
0
        syms->getZodiacNames(count, DateFormatSymbols::FORMAT, DateFormatSymbols::NARROW);
866
0
        break;
867
0
868
0
    }
869
0
870
0
    return count;
871
0
}
872
873
U_NAMESPACE_BEGIN
874
875
/*
876
 * This DateFormatSymbolsSingleSetter class is a friend of DateFormatSymbols
877
 * solely for the purpose of avoiding to clone the array of strings
878
 * just to modify one of them and then setting all of them back.
879
 * For example, the old code looked like this:
880
 *  case UDAT_MONTHS:
881
 *    res = syms->getMonths(count);
882
 *    array = new UnicodeString[count];
883
 *    if(array == 0) {
884
 *      *status = U_MEMORY_ALLOCATION_ERROR;
885
 *      return;
886
 *    }
887
 *    uprv_arrayCopy(res, array, count);
888
 *    if(index < count)
889
 *      array[index] = val;
890
 *    syms->setMonths(array, count);
891
 *    break;
892
 *
893
 * Even worse, the old code actually cloned the entire DateFormatSymbols object,
894
 * cloned one value array, changed one value, and then made the SimpleDateFormat
895
 * replace its DateFormatSymbols object with the new one.
896
 *
897
 * markus 2002-oct-14
898
 */
899
class DateFormatSymbolsSingleSetter /* not : public UObject because all methods are static */ {
900
public:
901
    static void
902
        setSymbol(UnicodeString *array, int32_t count, int32_t index,
903
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
904
0
    {
905
0
        if(array!=NULL) {
906
0
            if(index>=count) {
907
0
                errorCode=U_INDEX_OUTOFBOUNDS_ERROR;
908
0
            } else if(value==NULL) {
909
0
                errorCode=U_ILLEGAL_ARGUMENT_ERROR;
910
0
            } else {
911
0
                array[index].setTo(value, valueLength);
912
0
            }
913
0
        }
914
0
    }
915
916
    static void
917
        setEra(DateFormatSymbols *syms, int32_t index,
918
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
919
0
    {
920
0
        setSymbol(syms->fEras, syms->fErasCount, index, value, valueLength, errorCode);
921
0
    }
922
923
    static void
924
        setEraName(DateFormatSymbols *syms, int32_t index,
925
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
926
0
    {
927
0
        setSymbol(syms->fEraNames, syms->fEraNamesCount, index, value, valueLength, errorCode);
928
0
    }
929
930
    static void
931
        setMonth(DateFormatSymbols *syms, int32_t index,
932
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
933
0
    {
934
0
        setSymbol(syms->fMonths, syms->fMonthsCount, index, value, valueLength, errorCode);
935
0
    }
936
937
    static void
938
        setShortMonth(DateFormatSymbols *syms, int32_t index,
939
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
940
0
    {
941
0
        setSymbol(syms->fShortMonths, syms->fShortMonthsCount, index, value, valueLength, errorCode);
942
0
    }
943
944
    static void
945
        setNarrowMonth(DateFormatSymbols *syms, int32_t index,
946
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
947
0
    {
948
0
        setSymbol(syms->fNarrowMonths, syms->fNarrowMonthsCount, index, value, valueLength, errorCode);
949
0
    }
950
951
    static void
952
        setStandaloneMonth(DateFormatSymbols *syms, int32_t index,
953
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
954
0
    {
955
0
        setSymbol(syms->fStandaloneMonths, syms->fStandaloneMonthsCount, index, value, valueLength, errorCode);
956
0
    }
957
958
    static void
959
        setStandaloneShortMonth(DateFormatSymbols *syms, int32_t index,
960
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
961
0
    {
962
0
        setSymbol(syms->fStandaloneShortMonths, syms->fStandaloneShortMonthsCount, index, value, valueLength, errorCode);
963
0
    }
964
965
    static void
966
        setStandaloneNarrowMonth(DateFormatSymbols *syms, int32_t index,
967
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
968
0
    {
969
0
        setSymbol(syms->fStandaloneNarrowMonths, syms->fStandaloneNarrowMonthsCount, index, value, valueLength, errorCode);
970
0
    }
971
972
    static void
973
        setWeekday(DateFormatSymbols *syms, int32_t index,
974
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
975
0
    {
976
0
        setSymbol(syms->fWeekdays, syms->fWeekdaysCount, index, value, valueLength, errorCode);
977
0
    }
978
979
    static void
980
        setShortWeekday(DateFormatSymbols *syms, int32_t index,
981
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
982
0
    {
983
0
        setSymbol(syms->fShortWeekdays, syms->fShortWeekdaysCount, index, value, valueLength, errorCode);
984
0
    }
985
986
    static void
987
        setShorterWeekday(DateFormatSymbols *syms, int32_t index,
988
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
989
0
    {
990
0
        setSymbol(syms->fShorterWeekdays, syms->fShorterWeekdaysCount, index, value, valueLength, errorCode);
991
0
    }
992
993
    static void
994
        setNarrowWeekday(DateFormatSymbols *syms, int32_t index,
995
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
996
0
    {
997
0
        setSymbol(syms->fNarrowWeekdays, syms->fNarrowWeekdaysCount, index, value, valueLength, errorCode);
998
0
    }
999
1000
    static void
1001
        setStandaloneWeekday(DateFormatSymbols *syms, int32_t index,
1002
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1003
0
    {
1004
0
        setSymbol(syms->fStandaloneWeekdays, syms->fStandaloneWeekdaysCount, index, value, valueLength, errorCode);
1005
0
    }
1006
1007
    static void
1008
        setStandaloneShortWeekday(DateFormatSymbols *syms, int32_t index,
1009
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1010
0
    {
1011
0
        setSymbol(syms->fStandaloneShortWeekdays, syms->fStandaloneShortWeekdaysCount, index, value, valueLength, errorCode);
1012
0
    }
1013
1014
    static void
1015
        setStandaloneShorterWeekday(DateFormatSymbols *syms, int32_t index,
1016
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1017
0
    {
1018
0
        setSymbol(syms->fStandaloneShorterWeekdays, syms->fStandaloneShorterWeekdaysCount, index, value, valueLength, errorCode);
1019
0
    }
1020
1021
    static void
1022
        setStandaloneNarrowWeekday(DateFormatSymbols *syms, int32_t index,
1023
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1024
0
    {
1025
0
        setSymbol(syms->fStandaloneNarrowWeekdays, syms->fStandaloneNarrowWeekdaysCount, index, value, valueLength, errorCode);
1026
0
    }
1027
1028
    static void
1029
        setQuarter(DateFormatSymbols *syms, int32_t index,
1030
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1031
0
    {
1032
0
        setSymbol(syms->fQuarters, syms->fQuartersCount, index, value, valueLength, errorCode);
1033
0
    }
1034
1035
    static void
1036
        setShortQuarter(DateFormatSymbols *syms, int32_t index,
1037
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1038
0
    {
1039
0
        setSymbol(syms->fShortQuarters, syms->fShortQuartersCount, index, value, valueLength, errorCode);
1040
0
    }
1041
1042
    static void
1043
        setStandaloneQuarter(DateFormatSymbols *syms, int32_t index,
1044
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1045
0
    {
1046
0
        setSymbol(syms->fStandaloneQuarters, syms->fStandaloneQuartersCount, index, value, valueLength, errorCode);
1047
0
    }
1048
1049
    static void
1050
        setStandaloneShortQuarter(DateFormatSymbols *syms, int32_t index,
1051
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1052
0
    {
1053
0
        setSymbol(syms->fStandaloneShortQuarters, syms->fStandaloneShortQuartersCount, index, value, valueLength, errorCode);
1054
0
    }
1055
1056
    static void
1057
        setShortYearNames(DateFormatSymbols *syms, int32_t index,
1058
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1059
0
    {
1060
0
        setSymbol(syms->fShortYearNames, syms->fShortYearNamesCount, index, value, valueLength, errorCode);
1061
0
    }
1062
1063
    static void
1064
        setShortZodiacNames(DateFormatSymbols *syms, int32_t index,
1065
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1066
0
    {
1067
0
        setSymbol(syms->fShortZodiacNames, syms->fShortZodiacNamesCount, index, value, valueLength, errorCode);
1068
0
    }
1069
1070
    static void
1071
        setAmPm(DateFormatSymbols *syms, int32_t index,
1072
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1073
0
    {
1074
0
        setSymbol(syms->fAmPms, syms->fAmPmsCount, index, value, valueLength, errorCode);
1075
0
    }
1076
1077
    static void
1078
        setLocalPatternChars(DateFormatSymbols *syms,
1079
        const UChar *value, int32_t valueLength, UErrorCode &errorCode)
1080
0
    {
1081
0
        setSymbol(&syms->fLocalPatternChars, 1, 0, value, valueLength, errorCode);
1082
0
    }
1083
};
1084
1085
U_NAMESPACE_END
1086
1087
U_CAPI void U_EXPORT2
1088
udat_setSymbols(    UDateFormat             *format,
1089
            UDateFormatSymbolType   type,
1090
            int32_t                 index,
1091
            UChar                   *value,
1092
            int32_t                 valueLength,
1093
            UErrorCode              *status)
1094
0
{
1095
0
    verifyIsSimpleDateFormat(format, status);
1096
0
    if(U_FAILURE(*status)) return;
1097
0
1098
0
    DateFormatSymbols *syms = (DateFormatSymbols *)((SimpleDateFormat *)format)->getDateFormatSymbols();
1099
0
1100
0
    switch(type) {
1101
0
    case UDAT_ERAS:
1102
0
        DateFormatSymbolsSingleSetter::setEra(syms, index, value, valueLength, *status);
1103
0
        break;
1104
0
1105
0
    case UDAT_ERA_NAMES:
1106
0
        DateFormatSymbolsSingleSetter::setEraName(syms, index, value, valueLength, *status);
1107
0
        break;
1108
0
1109
0
    case UDAT_MONTHS:
1110
0
        DateFormatSymbolsSingleSetter::setMonth(syms, index, value, valueLength, *status);
1111
0
        break;
1112
0
1113
0
    case UDAT_SHORT_MONTHS:
1114
0
        DateFormatSymbolsSingleSetter::setShortMonth(syms, index, value, valueLength, *status);
1115
0
        break;
1116
0
1117
0
    case UDAT_NARROW_MONTHS:
1118
0
        DateFormatSymbolsSingleSetter::setNarrowMonth(syms, index, value, valueLength, *status);
1119
0
        break;
1120
0
1121
0
    case UDAT_STANDALONE_MONTHS:
1122
0
        DateFormatSymbolsSingleSetter::setStandaloneMonth(syms, index, value, valueLength, *status);
1123
0
        break;
1124
0
1125
0
    case UDAT_STANDALONE_SHORT_MONTHS:
1126
0
        DateFormatSymbolsSingleSetter::setStandaloneShortMonth(syms, index, value, valueLength, *status);
1127
0
        break;
1128
0
1129
0
    case UDAT_STANDALONE_NARROW_MONTHS:
1130
0
        DateFormatSymbolsSingleSetter::setStandaloneNarrowMonth(syms, index, value, valueLength, *status);
1131
0
        break;
1132
0
1133
0
    case UDAT_WEEKDAYS:
1134
0
        DateFormatSymbolsSingleSetter::setWeekday(syms, index, value, valueLength, *status);
1135
0
        break;
1136
0
1137
0
    case UDAT_SHORT_WEEKDAYS:
1138
0
        DateFormatSymbolsSingleSetter::setShortWeekday(syms, index, value, valueLength, *status);
1139
0
        break;
1140
0
1141
0
    case UDAT_SHORTER_WEEKDAYS:
1142
0
        DateFormatSymbolsSingleSetter::setShorterWeekday(syms, index, value, valueLength, *status);
1143
0
        break;
1144
0
1145
0
    case UDAT_NARROW_WEEKDAYS:
1146
0
        DateFormatSymbolsSingleSetter::setNarrowWeekday(syms, index, value, valueLength, *status);
1147
0
        break;
1148
0
1149
0
    case UDAT_STANDALONE_WEEKDAYS:
1150
0
        DateFormatSymbolsSingleSetter::setStandaloneWeekday(syms, index, value, valueLength, *status);
1151
0
        break;
1152
0
1153
0
    case UDAT_STANDALONE_SHORT_WEEKDAYS:
1154
0
        DateFormatSymbolsSingleSetter::setStandaloneShortWeekday(syms, index, value, valueLength, *status);
1155
0
        break;
1156
0
1157
0
    case UDAT_STANDALONE_SHORTER_WEEKDAYS:
1158
0
        DateFormatSymbolsSingleSetter::setStandaloneShorterWeekday(syms, index, value, valueLength, *status);
1159
0
        break;
1160
0
1161
0
    case UDAT_STANDALONE_NARROW_WEEKDAYS:
1162
0
        DateFormatSymbolsSingleSetter::setStandaloneNarrowWeekday(syms, index, value, valueLength, *status);
1163
0
        break;
1164
0
1165
0
    case UDAT_QUARTERS:
1166
0
        DateFormatSymbolsSingleSetter::setQuarter(syms, index, value, valueLength, *status);
1167
0
        break;
1168
0
1169
0
    case UDAT_SHORT_QUARTERS:
1170
0
        DateFormatSymbolsSingleSetter::setShortQuarter(syms, index, value, valueLength, *status);
1171
0
        break;
1172
0
1173
0
    case UDAT_STANDALONE_QUARTERS:
1174
0
        DateFormatSymbolsSingleSetter::setStandaloneQuarter(syms, index, value, valueLength, *status);
1175
0
        break;
1176
0
1177
0
    case UDAT_STANDALONE_SHORT_QUARTERS:
1178
0
        DateFormatSymbolsSingleSetter::setStandaloneShortQuarter(syms, index, value, valueLength, *status);
1179
0
        break;
1180
0
1181
0
    case UDAT_CYCLIC_YEARS_ABBREVIATED:
1182
0
        DateFormatSymbolsSingleSetter::setShortYearNames(syms, index, value, valueLength, *status);
1183
0
        break;
1184
0
1185
0
    case UDAT_ZODIAC_NAMES_ABBREVIATED:
1186
0
        DateFormatSymbolsSingleSetter::setShortZodiacNames(syms, index, value, valueLength, *status);
1187
0
        break;
1188
0
1189
0
    case UDAT_AM_PMS:
1190
0
        DateFormatSymbolsSingleSetter::setAmPm(syms, index, value, valueLength, *status);
1191
0
        break;
1192
0
1193
0
    case UDAT_LOCALIZED_CHARS:
1194
0
        DateFormatSymbolsSingleSetter::setLocalPatternChars(syms, value, valueLength, *status);
1195
0
        break;
1196
0
1197
0
    default:
1198
0
        *status = U_UNSUPPORTED_ERROR;
1199
0
        break;
1200
0
        
1201
0
    }
1202
0
}
1203
1204
U_CAPI const char* U_EXPORT2
1205
udat_getLocaleByType(const UDateFormat *fmt,
1206
                     ULocDataLocaleType type,
1207
                     UErrorCode* status)
1208
0
{
1209
0
    if (fmt == NULL) {
1210
0
        if (U_SUCCESS(*status)) {
1211
0
            *status = U_ILLEGAL_ARGUMENT_ERROR;
1212
0
        }
1213
0
        return NULL;
1214
0
    }
1215
0
    return ((Format*)fmt)->getLocaleID(type, *status);
1216
0
}
1217
1218
U_CAPI void U_EXPORT2
1219
udat_setContext(UDateFormat* fmt, UDisplayContext value, UErrorCode* status)
1220
0
{
1221
0
    if (U_FAILURE(*status)) {
1222
0
        return;
1223
0
    }
1224
0
    ((DateFormat*)fmt)->setContext(value, *status);
1225
0
    return;
1226
0
}
1227
1228
U_CAPI UDisplayContext U_EXPORT2
1229
udat_getContext(const UDateFormat* fmt, UDisplayContextType type, UErrorCode* status)
1230
0
{
1231
0
    if (U_FAILURE(*status)) {
1232
0
        return (UDisplayContext)0;
1233
0
    }
1234
0
    return ((const DateFormat*)fmt)->getContext(type, *status);
1235
0
}
1236
1237
1238
/**
1239
 * Verify that fmt is a RelativeDateFormat. Invalid error if not.
1240
 * @param fmt the UDateFormat, definitely a DateFormat, maybe something else
1241
 * @param status error code, will be set to failure if there is a familure or the fmt is NULL.
1242
 */
1243
0
static void verifyIsRelativeDateFormat(const UDateFormat* fmt, UErrorCode *status) {
1244
0
   if(U_SUCCESS(*status) &&
1245
0
       dynamic_cast<const RelativeDateFormat*>(reinterpret_cast<const DateFormat*>(fmt))==NULL) {
1246
0
       *status = U_ILLEGAL_ARGUMENT_ERROR;
1247
0
   }
1248
0
}
1249
1250
1251
U_CAPI int32_t U_EXPORT2 
1252
udat_toPatternRelativeDate(const UDateFormat *fmt,
1253
                           UChar             *result,
1254
                           int32_t           resultLength,
1255
                           UErrorCode        *status)
1256
0
{
1257
0
    verifyIsRelativeDateFormat(fmt, status);
1258
0
    if(U_FAILURE(*status)) {
1259
0
        return -1;
1260
0
    }
1261
0
    if (result == NULL ? resultLength != 0 : resultLength < 0) {
1262
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
1263
0
        return -1;
1264
0
    }
1265
0
1266
0
    UnicodeString datePattern;
1267
0
    if (result != NULL) {
1268
0
        // NULL destination for pure preflighting: empty dummy string
1269
0
        // otherwise, alias the destination buffer
1270
0
        datePattern.setTo(result, 0, resultLength);
1271
0
    }
1272
0
    ((RelativeDateFormat*)fmt)->toPatternDate(datePattern, *status);
1273
0
    return datePattern.extract(result, resultLength, *status);
1274
0
}
1275
1276
U_CAPI int32_t U_EXPORT2 
1277
udat_toPatternRelativeTime(const UDateFormat *fmt,
1278
                           UChar             *result,
1279
                           int32_t           resultLength,
1280
                           UErrorCode        *status)
1281
0
{
1282
0
    verifyIsRelativeDateFormat(fmt, status);
1283
0
    if(U_FAILURE(*status)) {
1284
0
        return -1;
1285
0
    }
1286
0
    if (result == NULL ? resultLength != 0 : resultLength < 0) {
1287
0
        *status = U_ILLEGAL_ARGUMENT_ERROR;
1288
0
        return -1;
1289
0
    }
1290
0
1291
0
    UnicodeString timePattern;
1292
0
    if (result != NULL) {
1293
0
        // NULL destination for pure preflighting: empty dummy string
1294
0
        // otherwise, alias the destination buffer
1295
0
        timePattern.setTo(result, 0, resultLength);
1296
0
    }
1297
0
    ((RelativeDateFormat*)fmt)->toPatternTime(timePattern, *status);
1298
0
    return timePattern.extract(result, resultLength, *status);
1299
0
}
1300
1301
U_CAPI void U_EXPORT2 
1302
udat_applyPatternRelative(UDateFormat *format,
1303
                          const UChar *datePattern,
1304
                          int32_t     datePatternLength,
1305
                          const UChar *timePattern,
1306
                          int32_t     timePatternLength,
1307
                          UErrorCode  *status)
1308
0
{
1309
0
    verifyIsRelativeDateFormat(format, status);
1310
0
    if(U_FAILURE(*status)) return;
1311
0
    const UnicodeString datePat((UBool)(datePatternLength == -1), datePattern, datePatternLength);
1312
0
    const UnicodeString timePat((UBool)(timePatternLength == -1), timePattern, timePatternLength);
1313
0
    ((RelativeDateFormat*)format)->applyPatterns(datePat, timePat, *status);
1314
0
}
1315
1316
#endif /* #if !UCONFIG_NO_FORMATTING */