private void GetDaylightChangeRules(ref DateTime time, TzDatabase.TzZone targetZone, DateTimeKind inflectionKind, out TzDatabase.TzRule one, out TzDatabase.TzRule two, out DaylightTime daylightTime) { one = two = null; daylightTime = null; // First, figure out which zone we're in if (targetZone != null) { // The zone might not have any daylight savings time rules if (targetZone.RuleName != TzDatabase.NotApplicableValue) { int index = FindRuleIndex(targetZone, time); if (index != -1) { one = m_info.Rules[index]; two = GetCompanionRule(targetZone, one, index, time); if (one != null && two != null) { DateTime from = one.GetDateTime(time.Year, targetZone.UtcOffset, two); DateTime to = two.GetDateTime(time.Year, targetZone.UtcOffset, one); if (from > to && Info.IsLatitudeNorth) { DateTime swap = to; to = from; from = swap; TzDatabase.TzRule swapRule = one; one = two; two = swapRule; } else if (from < to && !Info.IsLatitudeNorth) { DateTime swap = to; to = from; from = swap; TzDatabase.TzRule swapRule = one; one = two; two = swapRule; } TimeSpan delta = one.SaveTime; if (delta.Ticks == 0) { delta = two.SaveTime; } daylightTime = new DaylightTime(from, to, delta); } } } } }
private PublicDomain.TzDatabase.TzRule GetCompanionRule(TzDatabase.TzZone zone, PublicDomain.TzDatabase.TzRule rule, int ruleIndex, DateTime point) { TzDatabase.TzRule result = null; int companionIndex = FindRuleIndex(zone, point, rule.Modifier, rule.Modifier == TzDatabase.NotApplicableValue ? ruleIndex : -1, false); if (companionIndex != -1) { result = m_info.Rules[companionIndex]; } return result; }
/// <summary> /// Finds the index of the rule. /// </summary> /// <param name="zone">The zone.</param> /// <param name="point">The point.</param> /// <returns></returns> public int FindRuleIndex(TzDatabase.TzZone zone, DateTime point) { return FindRuleIndex(zone, point, null, -1, true); }
/// <summary> /// Finds the rule. /// </summary> /// <param name="zone">The zone.</param> /// <param name="point">The point.</param> /// <param name="avoidModifier">The avoid modifier.</param> /// <param name="avoidIndex">Index of the avoid.</param> /// <param name="exactComparison">if set to <c>true</c> [exact comparison].</param> /// <returns></returns> public int FindRuleIndex(TzDatabase.TzZone zone, DateTime point, string avoidModifier, int avoidIndex, bool exactComparison) { // Now, we have the zone, we can start to figure out the amount // of time to add to UTC to get standard time // Get the standard time from the UTC Offset for the zone // Use the rules to see if we need to apply daylight savings time // "If this field is - then standard time // always applies in the time zone." string ruleName = zone.RuleName; int curRuleIndex = -1; if (ruleName != TzDatabase.NotApplicableValue) { // Iterate over the rules to find the // applicable rule int rulesLength = m_info.Rules.Count; if (rulesLength == 0 && !string.IsNullOrEmpty(ruleName)) { throw new BaseException("No rules found for rule name {0}", ruleName); } for (int j = 0; j < rulesLength; j++) { PublicDomain.TzDatabase.TzRule r = m_info.Rules[j]; if (r.RuleName == ruleName && (avoidIndex == -1 || (avoidIndex != -1 && avoidIndex != j))) { curRuleIndex = j; if ((exactComparison && point >= r.GetFromDateTime(zone.UtcOffset) && point < r.GetToDateTime(zone.UtcOffset)) || (!exactComparison && point.Year >= r.FromYear && point.Year <= r.ToYear)) { if (avoidModifier == null || avoidModifier != r.Modifier || avoidIndex != -1) { break; } } } } if (curRuleIndex == -1) { throw new TzException("Could not find rule"); } } return curRuleIndex; }
/// <summary> /// Finds the rule. /// </summary> /// <param name="zone">The zone.</param> /// <param name="point">The point.</param> /// <returns></returns> public TzDatabase.TzRule FindRule(TzDatabase.TzZone zone, DateTime point) { int ruleIndex = FindRuleIndex(zone, point); return ruleIndex == -1 ? null : m_info.Rules[ruleIndex]; }