You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

LocaleUtil.java 5.6KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. /* ====================================================================
  2. Licensed to the Apache Software Foundation (ASF) under one or more
  3. contributor license agreements. See the NOTICE file distributed with
  4. this work for additional information regarding copyright ownership.
  5. The ASF licenses this file to You under the Apache License, Version 2.0
  6. (the "License"); you may not use this file except in compliance with
  7. the License. You may obtain a copy of the License at
  8. http://www.apache.org/licenses/LICENSE-2.0
  9. Unless required by applicable law or agreed to in writing, software
  10. distributed under the License is distributed on an "AS IS" BASIS,
  11. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. See the License for the specific language governing permissions and
  13. limitations under the License.
  14. ==================================================================== */
  15. package org.apache.poi.util;
  16. import java.nio.charset.Charset;
  17. import java.util.Calendar;
  18. import java.util.Locale;
  19. import java.util.TimeZone;
  20. /**
  21. * This utility class is used to set locale and time zone settings beside
  22. * of the JDK internal {@link java.util.Locale#setDefault(Locale)} and
  23. * {@link java.util.TimeZone#setDefault(TimeZone)} methods, because
  24. * the locale/time zone specific handling of certain office documents -
  25. * maybe for different time zones / locales ... - shouldn't affect
  26. * other java components.
  27. *
  28. * The settings are saved in a {@link java.lang.ThreadLocal},
  29. * so they only apply to the current thread and can't be set globally.
  30. */
  31. public final class LocaleUtil {
  32. private LocaleUtil() {
  33. // no instances of this class
  34. }
  35. /**
  36. * Excel doesn't store TimeZone information in the file, so if in doubt,
  37. * use UTC to perform calculations
  38. */
  39. public static final TimeZone TIMEZONE_UTC = TimeZone.getTimeZone("UTC");
  40. /**
  41. * Default encoding for unknown byte encodings of native files
  42. * (at least it's better than to rely on a platform dependent encoding
  43. * for legacy stuff ...)
  44. */
  45. public static final Charset CHARSET_1252 = Charset.forName("CP1252");
  46. private static final ThreadLocal<TimeZone> userTimeZone = new ThreadLocal<>();
  47. private static final ThreadLocal<Locale> userLocale = new ThreadLocal<>();
  48. /**
  49. * As time zone information is not stored in any format, it can be
  50. * set before any date calculations take place.
  51. * This setting is specific to the current thread.
  52. *
  53. * @param timezone the timezone under which date calculations take place
  54. */
  55. public static void setUserTimeZone(TimeZone timezone) {
  56. userTimeZone.set(timezone);
  57. }
  58. /**
  59. * @return the time zone which is used for date calculations. If not set, returns {@link TimeZone#getDefault()}.
  60. */
  61. @SuppressForbidden("implementation around default locales in POI")
  62. public static TimeZone getUserTimeZone() {
  63. TimeZone timeZone = userTimeZone.get();
  64. return (timeZone != null) ? timeZone : TimeZone.getDefault();
  65. }
  66. /**
  67. * Clear the thread-local user time zone.
  68. */
  69. public static void resetUserTimeZone() {
  70. userTimeZone.remove();
  71. }
  72. /**
  73. * Sets default user locale.
  74. * This setting is specific to the current thread.
  75. */
  76. public static void setUserLocale(Locale locale) {
  77. userLocale.set(locale);
  78. }
  79. /**
  80. * @return the default user locale. If not set, returns {@link Locale#getDefault()}.
  81. */
  82. @SuppressForbidden("implementation around default locales in POI")
  83. public static Locale getUserLocale() {
  84. Locale locale = userLocale.get();
  85. return (locale != null) ? locale : Locale.getDefault();
  86. }
  87. public static void resetUserLocale() {
  88. userLocale.remove();
  89. }
  90. /**
  91. * @return a calendar for the user locale and time zone
  92. */
  93. public static Calendar getLocaleCalendar() {
  94. return getLocaleCalendar(getUserTimeZone());
  95. }
  96. /**
  97. * Convenience method - month is 0-based as in java.util.Calendar
  98. *
  99. * @return a calendar for the user locale and time zone, and the given date
  100. */
  101. public static Calendar getLocaleCalendar(int year, int month, int day) {
  102. return getLocaleCalendar(year, month, day, 0, 0, 0);
  103. }
  104. /**
  105. * Convenience method - month is 0-based as in java.util.Calendar
  106. *
  107. * @return a calendar for the user locale and time zone, and the given date
  108. */
  109. public static Calendar getLocaleCalendar(int year, int month, int day, int hour, int minute, int second) {
  110. Calendar cal = getLocaleCalendar();
  111. cal.set(year, month, day, hour, minute, second);
  112. cal.clear(Calendar.MILLISECOND);
  113. return cal;
  114. }
  115. /**
  116. * @return a calendar for the user locale and time zone
  117. */
  118. public static Calendar getLocaleCalendar(TimeZone timeZone) {
  119. return Calendar.getInstance(timeZone, getUserLocale());
  120. }
  121. /**
  122. * Decode the language ID from LCID value
  123. *
  124. * @param lcid the LCID value
  125. * @return the locale/language ID
  126. */
  127. public static String getLocaleFromLCID(int lcid) {
  128. LocaleID lid = LocaleID.lookupByLcid(lcid & 0xFFFF);
  129. return (lid == null) ? "invalid" : lid.getLanguageTag();
  130. }
  131. /**
  132. * Get default code page from LCID value
  133. *
  134. * @param lcid the LCID value
  135. * @return the default code page
  136. */
  137. public static int getDefaultCodePageFromLCID(int lcid) {
  138. LocaleID lid = LocaleID.lookupByLcid(lcid & 0xFFFF);
  139. return (lid == null) ? 0 : lid.getDefaultCodepage();
  140. }
  141. }