1 /* 2 ***************************************************************************** 3 * Copyright (C) 2014-2015, International Business Machines Corporation and 4 * others. 5 * All Rights Reserved. 6 ***************************************************************************** 7 * 8 * File RELDATEFMT.H 9 ***************************************************************************** 10 */ 11 12 #ifndef __RELDATEFMT_H 13 #define __RELDATEFMT_H 14 15 #include "unicode/utypes.h" 16 #include "unicode/uobject.h" 17 #include "unicode/udisplaycontext.h" 18 #include "unicode/locid.h" 19 20 /** 21 * \file 22 * \brief C++ API: Formats relative dates such as "1 day ago" or "tomorrow" 23 */ 24 25 #if !UCONFIG_NO_FORMATTING && !UCONFIG_NO_BREAK_ITERATION 26 27 #ifndef U_HIDE_DRAFT_API 28 29 /** 30 * The formatting style 31 * @draft ICU 54 32 */ 33 typedef enum UDateRelativeDateTimeFormatterStyle { 34 35 /** 36 * Everything spelled out. 37 * @draft ICU 54 38 */ 39 UDAT_STYLE_LONG, 40 41 /** 42 * Abbreviations used when possible. 43 * @draft ICU 54 44 */ 45 UDAT_STYLE_SHORT, 46 47 /** 48 * Use the shortest possible form. 49 * @draft ICU 54 50 */ 51 UDAT_STYLE_NARROW, 52 53 /** 54 * The number of styles. 55 * @draft ICU 54 56 */ 57 UDAT_STYLE_COUNT 58 } UDateRelativeDateTimeFormatterStyle; 59 60 #endif /* U_HIDE_DRAFT_API */ 61 62 /** 63 * Represents the unit for formatting a relative date. e.g "in 5 days" 64 * or "in 3 months" 65 * @stable ICU 53 66 */ 67 typedef enum UDateRelativeUnit { 68 69 /** 70 * Seconds 71 * @stable ICU 53 72 */ 73 UDAT_RELATIVE_SECONDS, 74 75 /** 76 * Minutes 77 * @stable ICU 53 78 */ 79 UDAT_RELATIVE_MINUTES, 80 81 /** 82 * Hours 83 * @stable ICU 53 84 */ 85 UDAT_RELATIVE_HOURS, 86 87 /** 88 * Days 89 * @stable ICU 53 90 */ 91 UDAT_RELATIVE_DAYS, 92 93 /** 94 * Weeks 95 * @stable ICU 53 96 */ 97 UDAT_RELATIVE_WEEKS, 98 99 /** 100 * Months 101 * @stable ICU 53 102 */ 103 UDAT_RELATIVE_MONTHS, 104 105 /** 106 * Years 107 * @stable ICU 53 108 */ 109 UDAT_RELATIVE_YEARS, 110 111 /** 112 * Count of items in this enum. 113 * @stable ICU 53 114 */ 115 UDAT_RELATIVE_UNIT_COUNT 116 } UDateRelativeUnit; 117 118 /** 119 * Represents an absolute unit. 120 * @stable ICU 53 121 */ 122 typedef enum UDateAbsoluteUnit { 123 124 // Days of week have to remain together and in order from Sunday to 125 // Saturday. 126 /** 127 * Sunday 128 * @stable ICU 53 129 */ 130 UDAT_ABSOLUTE_SUNDAY, 131 132 /** 133 * Monday 134 * @stable ICU 53 135 */ 136 UDAT_ABSOLUTE_MONDAY, 137 138 /** 139 * Tuesday 140 * @stable ICU 53 141 */ 142 UDAT_ABSOLUTE_TUESDAY, 143 144 /** 145 * Wednesday 146 * @stable ICU 53 147 */ 148 UDAT_ABSOLUTE_WEDNESDAY, 149 150 /** 151 * Thursday 152 * @stable ICU 53 153 */ 154 UDAT_ABSOLUTE_THURSDAY, 155 156 /** 157 * Friday 158 * @stable ICU 53 159 */ 160 UDAT_ABSOLUTE_FRIDAY, 161 162 /** 163 * Saturday 164 * @stable ICU 53 165 */ 166 UDAT_ABSOLUTE_SATURDAY, 167 168 /** 169 * Day 170 * @stable ICU 53 171 */ 172 UDAT_ABSOLUTE_DAY, 173 174 /** 175 * Week 176 * @stable ICU 53 177 */ 178 UDAT_ABSOLUTE_WEEK, 179 180 /** 181 * Month 182 * @stable ICU 53 183 */ 184 UDAT_ABSOLUTE_MONTH, 185 186 /** 187 * Year 188 * @stable ICU 53 189 */ 190 UDAT_ABSOLUTE_YEAR, 191 192 /** 193 * Now 194 * @stable ICU 53 195 */ 196 UDAT_ABSOLUTE_NOW, 197 198 /** 199 * Count of items in this enum. 200 * @stable ICU 53 201 */ 202 UDAT_ABSOLUTE_UNIT_COUNT 203 } UDateAbsoluteUnit; 204 205 /** 206 * Represents a direction for an absolute unit e.g "Next Tuesday" 207 * or "Last Tuesday" 208 * @stable ICU 53 209 */ 210 typedef enum UDateDirection { 211 212 /** 213 * Two before. Not fully supported in every locale. 214 * @stable ICU 53 215 */ 216 UDAT_DIRECTION_LAST_2, 217 218 /** 219 * Last 220 * @stable ICU 53 221 */ 222 UDAT_DIRECTION_LAST, 223 224 /** 225 * This 226 * @stable ICU 53 227 */ 228 UDAT_DIRECTION_THIS, 229 230 /** 231 * Next 232 * @stable ICU 53 233 */ 234 UDAT_DIRECTION_NEXT, 235 236 /** 237 * Two after. Not fully supported in every locale. 238 * @stable ICU 53 239 */ 240 UDAT_DIRECTION_NEXT_2, 241 242 /** 243 * Plain, which means the absence of a qualifier. 244 * @stable ICU 53 245 */ 246 UDAT_DIRECTION_PLAIN, 247 248 /** 249 * Count of items in this enum. 250 * @stable ICU 53 251 */ 252 UDAT_DIRECTION_COUNT 253 } UDateDirection; 254 255 256 U_NAMESPACE_BEGIN 257 258 class RelativeDateTimeCacheData; 259 class SharedNumberFormat; 260 class SharedPluralRules; 261 class SharedBreakIterator; 262 class NumberFormat; 263 class UnicodeString; 264 265 /** 266 * Formats simple relative dates. There are two types of relative dates that 267 * it handles: 268 * <ul> 269 * <li>relative dates with a quantity e.g "in 5 days"</li> 270 * <li>relative dates without a quantity e.g "next Tuesday"</li> 271 * </ul> 272 * <p> 273 * This API is very basic and is intended to be a building block for more 274 * fancy APIs. The caller tells it exactly what to display in a locale 275 * independent way. While this class automatically provides the correct plural 276 * forms, the grammatical form is otherwise as neutral as possible. It is the 277 * caller's responsibility to handle cut-off logic such as deciding between 278 * displaying "in 7 days" or "in 1 week." This API supports relative dates 279 * involving one single unit. This API does not support relative dates 280 * involving compound units, 281 * e.g "in 5 days and 4 hours" nor does it support parsing. 282 * <p> 283 * This class is mostly thread safe and immutable with the following caveats: 284 * 1. The assignment operator violates Immutability. It must not be used 285 * concurrently with other operations. 286 * 2. Caller must not hold onto adopted pointers. 287 * <p> 288 * This class is not intended for public subclassing. 289 * <p> 290 * Here are some examples of use: 291 * <blockquote> 292 * <pre> 293 * UErrorCode status = U_ZERO_ERROR; 294 * UnicodeString appendTo; 295 * RelativeDateTimeFormatter fmt(status); 296 * // Appends "in 1 day" 297 * fmt.format( 298 * 1, UDAT_DIRECTION_NEXT, UDAT_RELATIVE_DAYS, appendTo, status); 299 * // Appends "in 3 days" 300 * fmt.format( 301 * 3, UDAT_DIRECTION_NEXT, UDAT_RELATIVE_DAYS, appendTo, status); 302 * // Appends "3.2 years ago" 303 * fmt.format( 304 * 3.2, UDAT_DIRECTION_LAST, UDAT_RELATIVE_YEARS, appendTo, status); 305 * // Appends "last Sunday" 306 * fmt.format(UDAT_DIRECTION_LAST, UDAT_ABSOLUTE_SUNDAY, appendTo, status); 307 * // Appends "this Sunday" 308 * fmt.format(UDAT_DIRECTION_THIS, UDAT_ABSOLUTE_SUNDAY, appendTo, status); 309 * // Appends "next Sunday" 310 * fmt.format(UDAT_DIRECTION_NEXT, UDAT_ABSOLUTE_SUNDAY, appendTo, status); 311 * // Appends "Sunday" 312 * fmt.format(UDAT_DIRECTION_PLAIN, UDAT_ABSOLUTE_SUNDAY, appendTo, status); 313 * 314 * // Appends "yesterday" 315 * fmt.format(UDAT_DIRECTION_LAST, UDAT_ABSOLUTE_DAY, appendTo, status); 316 * // Appends "today" 317 * fmt.format(UDAT_DIRECTION_THIS, UDAT_ABSOLUTE_DAY, appendTo, status); 318 * // Appends "tomorrow" 319 * fmt.format(UDAT_DIRECTION_NEXT, UDAT_ABSOLUTE_DAY, appendTo, status); 320 * // Appends "now" 321 * fmt.format(UDAT_DIRECTION_PLAIN, UDAT_ABSOLUTE_NOW, appendTo, status); 322 * 323 * </pre> 324 * </blockquote> 325 * <p> 326 * In the future, we may add more forms, such as abbreviated/short forms 327 * (3 secs ago), and relative day periods ("yesterday afternoon"), etc. 328 * 329 * The RelativeDateTimeFormatter class is not intended for public subclassing. 330 * 331 * @stable ICU 53 332 */ 333 class U_I18N_API RelativeDateTimeFormatter : public UObject { 334 public: 335 336 /** 337 * Create RelativeDateTimeFormatter with default locale. 338 * @stable ICU 53 339 */ 340 RelativeDateTimeFormatter(UErrorCode& status); 341 342 /** 343 * Create RelativeDateTimeFormatter with given locale. 344 * @stable ICU 53 345 */ 346 RelativeDateTimeFormatter(const Locale& locale, UErrorCode& status); 347 348 /** 349 * Create RelativeDateTimeFormatter with given locale and NumberFormat. 350 * 351 * @param locale the locale 352 * @param nfToAdopt Constructed object takes ownership of this pointer. 353 * It is an error for caller to delete this pointer or change its 354 * contents after calling this constructor. 355 * @status Any error is returned here. 356 * @stable ICU 53 357 */ 358 RelativeDateTimeFormatter( 359 const Locale& locale, NumberFormat *nfToAdopt, UErrorCode& status); 360 361 #ifndef U_HIDE_DRAFT_API 362 /** 363 * Create RelativeDateTimeFormatter with given locale, NumberFormat, 364 * and capitalization context. 365 * 366 * @param locale the locale 367 * @param nfToAdopt Constructed object takes ownership of this pointer. 368 * It is an error for caller to delete this pointer or change its 369 * contents after calling this constructor. Caller may pass NULL for 370 * this argument if they want default number format behavior. 371 * @param style the format style. The UDAT_RELATIVE bit field has no effect. 372 * @param capitalizationContext A value from UDisplayContext that pertains to 373 * capitalization. 374 * @status Any error is returned here. 375 * @draft ICU 54 376 */ 377 RelativeDateTimeFormatter( 378 const Locale& locale, 379 NumberFormat *nfToAdopt, 380 UDateRelativeDateTimeFormatterStyle style, 381 UDisplayContext capitalizationContext, 382 UErrorCode& status); 383 #endif /* U_HIDE_DRAFT_API */ 384 385 /** 386 * Copy constructor. 387 * @stable ICU 53 388 */ 389 RelativeDateTimeFormatter(const RelativeDateTimeFormatter& other); 390 391 /** 392 * Assignment operator. 393 * @stable ICU 53 394 */ 395 RelativeDateTimeFormatter& operator=( 396 const RelativeDateTimeFormatter& other); 397 398 /** 399 * Destructor. 400 * @stable ICU 53 401 */ 402 virtual ~RelativeDateTimeFormatter(); 403 404 /** 405 * Formats a relative date with a quantity such as "in 5 days" or 406 * "3 months ago" 407 * @param quantity The numerical amount e.g 5. This value is formatted 408 * according to this object's NumberFormat object. 409 * @param direction NEXT means a future relative date; LAST means a past 410 * relative date. If direction is anything else, this method sets 411 * status to U_ILLEGAL_ARGUMENT_ERROR. 412 * @param unit the unit e.g day? month? year? 413 * @param appendTo The string to which the formatted result will be 414 * appended 415 * @param status ICU error code returned here. 416 * @return appendTo 417 * @stable ICU 53 418 */ 419 UnicodeString& format( 420 double quantity, 421 UDateDirection direction, 422 UDateRelativeUnit unit, 423 UnicodeString& appendTo, 424 UErrorCode& status) const; 425 426 /** 427 * Formats a relative date without a quantity. 428 * @param direction NEXT, LAST, THIS, etc. 429 * @param unit e.g SATURDAY, DAY, MONTH 430 * @param appendTo The string to which the formatted result will be 431 * appended. If the value of direction is documented as not being fully 432 * supported in all locales then this method leaves appendTo unchanged if 433 * no format string is available. 434 * @param status ICU error code returned here. 435 * @return appendTo 436 * @stable ICU 53 437 */ 438 UnicodeString& format( 439 UDateDirection direction, 440 UDateAbsoluteUnit unit, 441 UnicodeString& appendTo, 442 UErrorCode& status) const; 443 444 /** 445 * Combines a relative date string and a time string in this object's 446 * locale. This is done with the same date-time separator used for the 447 * default calendar in this locale. 448 * 449 * @param relativeDateString the relative date, e.g 'yesterday' 450 * @param timeString the time e.g '3:45' 451 * @param appendTo concatenated date and time appended here 452 * @param status ICU error code returned here. 453 * @return appendTo 454 * @stable ICU 53 455 */ 456 UnicodeString& combineDateAndTime( 457 const UnicodeString& relativeDateString, 458 const UnicodeString& timeString, 459 UnicodeString& appendTo, 460 UErrorCode& status) const; 461 462 /** 463 * Returns the NumberFormat this object is using. 464 * 465 * @stable ICU 53 466 */ 467 const NumberFormat& getNumberFormat() const; 468 469 #ifndef U_HIDE_DRAFT_API 470 /** 471 * Returns the capitalization context. 472 * 473 * @draft ICU 54 474 */ 475 UDisplayContext getCapitalizationContext() const; 476 477 /** 478 * Returns the format style. 479 * 480 * @draft ICU 54 481 */ 482 UDateRelativeDateTimeFormatterStyle getFormatStyle() const; 483 #endif /* U_HIDE_DRAFT_API */ 484 485 private: 486 const RelativeDateTimeCacheData* fCache; 487 const SharedNumberFormat *fNumberFormat; 488 const SharedPluralRules *fPluralRules; 489 UDateRelativeDateTimeFormatterStyle fStyle; 490 UDisplayContext fContext; 491 const SharedBreakIterator *fOptBreakIterator; 492 Locale fLocale; 493 void init( 494 NumberFormat *nfToAdopt, 495 BreakIterator *brkIter, 496 UErrorCode &status); 497 void adjustForContext(UnicodeString &) const; 498 }; 499 500 U_NAMESPACE_END 501 502 #endif /* !UCONFIG_NO_FORMATTING && !UCONFIG_NO_BREAK_ITERATION*/ 503 #endif 504