1 | // © 2016 and later: Unicode, Inc. and others. |
2 | // License & terms of use: http://www.unicode.org/copyright.html |
3 | /* |
4 | ******************************************************************************* |
5 | * Copyright (C) 2009-2015, International Business Machines Corporation and * |
6 | * others. All Rights Reserved. * |
7 | ******************************************************************************* |
8 | */ |
9 | |
10 | #ifndef FPHDLIMP_H |
11 | #define FPHDLIMP_H |
12 | |
13 | #include "unicode/utypes.h" |
14 | |
15 | #if !UCONFIG_NO_FORMATTING |
16 | |
17 | #include "unicode/fieldpos.h" |
18 | #include "unicode/fpositer.h" |
19 | #include "unicode/formattedvalue.h" |
20 | |
21 | U_NAMESPACE_BEGIN |
22 | |
23 | // utility FieldPositionHandler |
24 | // base class, null implementation |
25 | |
26 | class U_I18N_API FieldPositionHandler: public UMemory { |
27 | protected: |
28 | int32_t fShift = 0; |
29 | |
30 | public: |
31 | virtual ~FieldPositionHandler(); |
32 | virtual void addAttribute(int32_t id, int32_t start, int32_t limit) = 0; |
33 | virtual void shiftLast(int32_t delta) = 0; |
34 | virtual UBool isRecording(void) const = 0; |
35 | |
36 | void setShift(int32_t delta); |
37 | }; |
38 | |
39 | |
40 | // utility subclass FieldPositionOnlyHandler |
41 | |
42 | class FieldPositionOnlyHandler : public FieldPositionHandler { |
43 | FieldPosition& pos; |
44 | UBool acceptFirstOnly = FALSE; |
45 | UBool seenFirst = FALSE; |
46 | |
47 | public: |
48 | FieldPositionOnlyHandler(FieldPosition& pos); |
49 | virtual ~FieldPositionOnlyHandler(); |
50 | |
51 | void addAttribute(int32_t id, int32_t start, int32_t limit) U_OVERRIDE; |
52 | void shiftLast(int32_t delta) U_OVERRIDE; |
53 | UBool isRecording(void) const U_OVERRIDE; |
54 | |
55 | /** |
56 | * Enable this option to lock in the FieldPosition value after seeing the |
57 | * first occurrence of the field. The default behavior is to take the last |
58 | * occurrence. |
59 | */ |
60 | void setAcceptFirstOnly(UBool acceptFirstOnly); |
61 | }; |
62 | |
63 | |
64 | // utility subclass FieldPositionIteratorHandler |
65 | |
66 | class FieldPositionIteratorHandler : public FieldPositionHandler { |
67 | FieldPositionIterator* iter; // can be NULL |
68 | UVector32* vec; |
69 | UErrorCode status; |
70 | UFieldCategory fCategory; |
71 | |
72 | // Note, we keep a reference to status, so if status is on the stack, we have |
73 | // to be destroyed before status goes out of scope. Easiest thing is to |
74 | // allocate us on the stack in the same (or narrower) scope as status has. |
75 | // This attempts to encourage that by blocking heap allocation. |
76 | static void* U_EXPORT2 operator new(size_t) U_NOEXCEPT = delete; |
77 | static void* U_EXPORT2 operator new[](size_t) U_NOEXCEPT = delete; |
78 | #if U_HAVE_PLACEMENT_NEW |
79 | static void* U_EXPORT2 operator new(size_t, void*) U_NOEXCEPT = delete; |
80 | #endif |
81 | |
82 | public: |
83 | FieldPositionIteratorHandler(FieldPositionIterator* posIter, UErrorCode& status); |
84 | /** If using this constructor, you must call getError() when done formatting! */ |
85 | FieldPositionIteratorHandler(UVector32* vec, UErrorCode& status); |
86 | ~FieldPositionIteratorHandler(); |
87 | |
88 | void addAttribute(int32_t id, int32_t start, int32_t limit) U_OVERRIDE; |
89 | void shiftLast(int32_t delta) U_OVERRIDE; |
90 | UBool isRecording(void) const U_OVERRIDE; |
91 | |
92 | /** Copies a failed error code into _status. */ |
93 | inline void getError(UErrorCode& _status) { |
94 | if (U_SUCCESS(_status) && U_FAILURE(status)) { |
95 | _status = status; |
96 | } |
97 | } |
98 | |
99 | inline void setCategory(UFieldCategory category) { |
100 | fCategory = category; |
101 | } |
102 | }; |
103 | |
104 | U_NAMESPACE_END |
105 | |
106 | #endif /* !UCONFIG_NO_FORMATTING */ |
107 | |
108 | #endif /* FPHDLIMP_H */ |
109 | |