mirror of
https://github.com/OrchardCMS/Orchard.git
synced 2025-10-15 19:54:57 +08:00
Implementing support for user-configured default site calendar, plus related extensibility points (ICalendarSelector, ICalendarManager).
This commit is contained in:

committed by
Sebastien Ros

parent
60a7159f18
commit
a306759748
@@ -66,6 +66,11 @@ namespace Orchard.Tests.Stubs {
|
||||
set { throw new NotImplementedException(); }
|
||||
}
|
||||
|
||||
public string SiteCalendar {
|
||||
get { throw new NotImplementedException(); }
|
||||
set { throw new NotImplementedException(); }
|
||||
}
|
||||
|
||||
public ResourceDebugMode ResourceDebugMode {
|
||||
get { throw new NotImplementedException(); }
|
||||
set { throw new NotImplementedException(); }
|
||||
|
@@ -18,16 +18,19 @@ namespace Orchard.Core.Settings.Drivers {
|
||||
public class SiteSettingsPartDriver : ContentPartDriver<SiteSettingsPart> {
|
||||
private readonly ISiteService _siteService;
|
||||
private readonly ICultureManager _cultureManager;
|
||||
private readonly ICalendarManager _calendarProvider;
|
||||
private readonly IMembershipService _membershipService;
|
||||
private readonly INotifier _notifier;
|
||||
|
||||
public SiteSettingsPartDriver(
|
||||
ISiteService siteService,
|
||||
ICultureManager cultureManager,
|
||||
ICultureManager cultureManager,
|
||||
ICalendarManager calendarProvider,
|
||||
IMembershipService membershipService,
|
||||
INotifier notifier) {
|
||||
_siteService = siteService;
|
||||
_cultureManager = cultureManager;
|
||||
_calendarProvider = calendarProvider;
|
||||
_membershipService = membershipService;
|
||||
_notifier = notifier;
|
||||
|
||||
@@ -46,6 +49,7 @@ namespace Orchard.Core.Settings.Drivers {
|
||||
var model = new SiteSettingsPartViewModel {
|
||||
Site = site,
|
||||
SiteCultures = _cultureManager.ListCultures(),
|
||||
SiteCalendars = _calendarProvider.ListCalendars(),
|
||||
TimeZones = TimeZoneInfo.GetSystemTimeZones()
|
||||
};
|
||||
|
||||
@@ -58,7 +62,8 @@ namespace Orchard.Core.Settings.Drivers {
|
||||
var model = new SiteSettingsPartViewModel {
|
||||
Site = site,
|
||||
SiteCultures = _cultureManager.ListCultures(),
|
||||
TimeZones = TimeZoneInfo.GetSystemTimeZones()
|
||||
SiteCalendars = _calendarProvider.ListCalendars(),
|
||||
TimeZones = TimeZoneInfo.GetSystemTimeZones()
|
||||
};
|
||||
|
||||
var previousBaseUrl = model.Site.BaseUrl;
|
||||
|
@@ -35,6 +35,11 @@ namespace Orchard.Core.Settings.Models {
|
||||
set { this.Store(x => x.SiteCulture, value); }
|
||||
}
|
||||
|
||||
public string SiteCalendar {
|
||||
get { return this.Retrieve(x => x.SiteCalendar); }
|
||||
set { this.Store(x => x.SiteCalendar, value); }
|
||||
}
|
||||
|
||||
public ResourceDebugMode ResourceDebugMode {
|
||||
get { return this.Retrieve(x => x.ResourceDebugMode); }
|
||||
set { this.Store(x => x.ResourceDebugMode, value); }
|
||||
|
@@ -8,6 +8,7 @@ namespace Orchard.Core.Settings.ViewModels {
|
||||
public class SiteSettingsPartViewModel {
|
||||
public SiteSettingsPart Site { get; set; }
|
||||
public IEnumerable<string> SiteCultures { get; set; }
|
||||
public IEnumerable<string> SiteCalendars { get; set; }
|
||||
public IEnumerable<TimeZoneInfo> TimeZones { get; set; }
|
||||
|
||||
[HiddenInput(DisplayValue = false)]
|
||||
@@ -30,6 +31,11 @@ namespace Orchard.Core.Settings.ViewModels {
|
||||
set { Site.SiteCulture = value; }
|
||||
}
|
||||
|
||||
public string SiteCalendar {
|
||||
get { return Site.SiteCalendar; }
|
||||
set { Site.SiteCalendar = value; }
|
||||
}
|
||||
|
||||
public string SuperUser {
|
||||
get { return Site.SuperUser; }
|
||||
set { Site.SuperUser = value; }
|
||||
|
@@ -15,22 +15,30 @@
|
||||
@Html.ValidationMessage("SiteName", "*")
|
||||
</div>
|
||||
<div>
|
||||
<label for="@Html.FieldIdFor(m => m.BaseUrl)">@T("Base url ")</label>
|
||||
<label for="@Html.FieldIdFor(m => m.BaseUrl)">@T("Base URL")</label>
|
||||
@Html.TextBoxFor(m => m.BaseUrl, new { @class = "text medium" })
|
||||
<span class="hint">@T("Enter the fully qualified base url of your website.")</span>
|
||||
<span class="hint">@T("Enter the fully qualified base URL of the web site.")</span>
|
||||
<span class="hint">@T("e.g., http://localhost:30320/orchardlocal, http://www.yourdomain.com")</span>
|
||||
</div>
|
||||
<div>
|
||||
<label for="SiteCulture">@T("Default Site Culture")</label>
|
||||
@Html.DropDownList("SiteCulture", new SelectList(Model.SiteCultures, Model.SiteCulture))
|
||||
@Html.ValidationMessage("SiteCulture", "*")
|
||||
<p>@Html.ActionLink(T("Add or remove supported cultures for the site.").ToString(), "Culture")</p>
|
||||
</div>
|
||||
<div>
|
||||
<label for="SiteCulture">@T("Default Site Culture")</label>
|
||||
@Html.DropDownList("SiteCulture", new SelectList(Model.SiteCultures, Model.SiteCulture))
|
||||
@Html.ValidationMessage("SiteCulture", "*")
|
||||
<span class="hint">@T("Determines the default culture used to localize strings and to format and parse numbers, date and times.")</span>
|
||||
<p>@Html.ActionLink(T("Add or remove supported cultures for the site").ToString(), "Culture")</p>
|
||||
</div>
|
||||
<div>
|
||||
<label for="SiteCalendar">@T("Default Site Calendar")</label>
|
||||
@Html.DropDownList("SiteCalendar", new[] { new SelectListItem { Text = T("Culture calendar").Text, Value = "" } }.Union(new SelectList(Model.SiteCalendars, Model.SiteCalendar)))
|
||||
@Html.ValidationMessage("SiteCalendar", "*")
|
||||
<span class="hint">@T("Determines the default calendar used when displaying and editing dates and times.")</span>
|
||||
<span class="hint">@T("The 'Culture calendar' option means the default calendar for the culture of the current request will be used (not necessarily the configured default site culture).")</span>
|
||||
</div>
|
||||
<div>
|
||||
<label for="TimeZone">@T("Default Time Zone")</label>
|
||||
@Html.DropDownList("TimeZone", new[] { new SelectListItem { Text = T("Local to server").Text, Value = "" } }.Union(new SelectList(Model.TimeZones, "Id", "", Model.TimeZone)))
|
||||
@Html.ValidationMessage("TimeZone", "*")
|
||||
<span class="hint">@T("Determines the default time zone which will should be used to display date and times.")</span>
|
||||
<span class="hint">@T("Determines the default time zone used when displaying and editing dates and times.")</span>
|
||||
</div>
|
||||
<div>
|
||||
<label for="PageTitleSeparator">@T("Page title separator")</label>
|
||||
|
@@ -176,6 +176,11 @@ namespace Orchard.Setup {
|
||||
set { throw new NotImplementedException(); }
|
||||
}
|
||||
|
||||
public string SiteCalendar {
|
||||
get { return ""; }
|
||||
set { throw new NotImplementedException(); }
|
||||
}
|
||||
|
||||
public ResourceDebugMode ResourceDebugMode {
|
||||
get { return ResourceDebugMode.FromAppSetting; }
|
||||
set { throw new NotImplementedException(); }
|
||||
|
@@ -70,6 +70,11 @@ namespace Orchard.Tokens.Tests {
|
||||
set { throw new NotImplementedException(); }
|
||||
}
|
||||
|
||||
public string SiteCalendar {
|
||||
get { throw new NotImplementedException(); }
|
||||
set { throw new NotImplementedException(); }
|
||||
}
|
||||
|
||||
public ResourceDebugMode ResourceDebugMode {
|
||||
get { throw new NotImplementedException(); }
|
||||
set { throw new NotImplementedException(); }
|
||||
|
@@ -1,4 +1,4 @@
|
||||
@using Orchard.Core.Shapes.Localization
|
||||
@using Orchard.Localization.Services
|
||||
@using System.Globalization
|
||||
|
||||
@{
|
||||
|
@@ -1,4 +1,4 @@
|
||||
@using Orchard.Core.Shapes.Localization
|
||||
@using Orchard.Localization.Services
|
||||
@using System.Globalization
|
||||
|
||||
@{
|
||||
|
@@ -0,0 +1,18 @@
|
||||
using System;
|
||||
|
||||
namespace Orchard.Localization.Services {
|
||||
public class CurrentCalendarWorkContext : IWorkContextStateProvider {
|
||||
private readonly ICalendarManager _calendarManager;
|
||||
|
||||
public CurrentCalendarWorkContext(ICalendarManager calendarManager) {
|
||||
_calendarManager = calendarManager;
|
||||
}
|
||||
|
||||
public Func<WorkContext, T> Get<T>(string name) {
|
||||
if (name == "CurrentCalendar") {
|
||||
return ctx => (T)(object)_calendarManager.GetCurrentCalendar(ctx.HttpContext);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
93
src/Orchard/Localization/Services/DefaultCalendarManager.cs
Normal file
93
src/Orchard/Localization/Services/DefaultCalendarManager.cs
Normal file
@@ -0,0 +1,93 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using System.Web;
|
||||
using Orchard.Caching;
|
||||
using Orchard.Data;
|
||||
using Orchard.Localization.Records;
|
||||
|
||||
namespace Orchard.Localization.Services {
|
||||
public class DefaultCalendarManager : ICalendarManager {
|
||||
private readonly IEnumerable<ICalendarSelector> _calendarSelectors;
|
||||
|
||||
public DefaultCalendarManager(IEnumerable<ICalendarSelector> calendarSelectors) {
|
||||
_calendarSelectors = calendarSelectors;
|
||||
}
|
||||
|
||||
public IEnumerable<string> ListCalendars() {
|
||||
// Return all the calendar implementations in System.Globalization.
|
||||
// Could be done more dynamically using reflection, but that doesn't seem worth the performance hit.
|
||||
return new[] {
|
||||
"ChineseLunisolarCalendar",
|
||||
"GregorianCalendar",
|
||||
"HebrewCalendar",
|
||||
"HijriCalendar",
|
||||
"JapaneseCalendar",
|
||||
"JapaneseLunisolarCalendar",
|
||||
"JulianCalendar",
|
||||
"KoreanCalendar",
|
||||
"KoreanLunisolarCalendar",
|
||||
"PersianCalendar",
|
||||
"TaiwanCalendar",
|
||||
"TaiwanLunisolarCalendar",
|
||||
"ThaiBuddhistCalendar",
|
||||
"UmAlQuraCalendar"
|
||||
};
|
||||
}
|
||||
|
||||
public string GetCurrentCalendar(HttpContextBase requestContext) {
|
||||
var requestCalendar = _calendarSelectors
|
||||
.Select(x => x.GetCalendar(requestContext))
|
||||
.Where(x => x != null)
|
||||
.OrderByDescending(x => x.Priority);
|
||||
|
||||
if (!requestCalendar.Any())
|
||||
return String.Empty;
|
||||
|
||||
foreach (var calendar in requestCalendar) {
|
||||
if (!String.IsNullOrEmpty(calendar.CalendarName)) {
|
||||
return calendar.CalendarName;
|
||||
}
|
||||
}
|
||||
|
||||
return String.Empty;
|
||||
}
|
||||
|
||||
public Calendar GetCalendarByName(string calendarName) {
|
||||
switch (calendarName) {
|
||||
case "ChineseLunisolarCalendar":
|
||||
return new ChineseLunisolarCalendar();
|
||||
case "GregorianCalendar":
|
||||
return new GregorianCalendar();
|
||||
case "HebrewCalendar":
|
||||
return new HebrewCalendar();
|
||||
case "HijriCalendar":
|
||||
return new HijriCalendar();
|
||||
case "JapaneseCalendar":
|
||||
return new JapaneseCalendar();
|
||||
case "JapaneseLunisolarCalendar":
|
||||
return new JapaneseLunisolarCalendar();
|
||||
case "JulianCalendar":
|
||||
return new JulianCalendar();
|
||||
case "KoreanCalendar":
|
||||
return new KoreanCalendar();
|
||||
case "KoreanLunisolarCalendar":
|
||||
return new KoreanLunisolarCalendar();
|
||||
case "PersianCalendar":
|
||||
return new PersianCalendar();
|
||||
case "TaiwanCalendar":
|
||||
return new TaiwanCalendar();
|
||||
case "TaiwanLunisolarCalendar":
|
||||
return new TaiwanLunisolarCalendar();
|
||||
case "ThaiBuddhistCalendar":
|
||||
return new ThaiBuddhistCalendar();
|
||||
case "UmAlQuraCalendar":
|
||||
return new UmAlQuraCalendar();
|
||||
default:
|
||||
throw new ArgumentException(String.Format("The calendar name '{0}' is not a recognized System.Globalization calendar name.", calendarName), "calendarName");
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -1,100 +1,173 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using Orchard;
|
||||
using Orchard.ContentManagement;
|
||||
using Orchard.Settings;
|
||||
|
||||
namespace Orchard.Localization.Services {
|
||||
|
||||
public class DefaultDateServices : IDateServices {
|
||||
public class DefaultDateServices : IDateServices {
|
||||
|
||||
private readonly IOrchardServices _orchardServices;
|
||||
private readonly IDateTimeLocalization _dateTimeLocalization;
|
||||
private readonly Lazy<CultureInfo> _cultureInfo;
|
||||
private readonly IOrchardServices _orchardServices;
|
||||
private readonly IDateTimeLocalization _dateTimeLocalization;
|
||||
private readonly ISiteService _siteService;
|
||||
private readonly ICalendarManager _calendarManager;
|
||||
|
||||
public DefaultDateServices(
|
||||
IOrchardServices orchardServices,
|
||||
IDateTimeLocalization dateTimeLocalization) {
|
||||
public DefaultDateServices(
|
||||
IOrchardServices orchardServices,
|
||||
IDateTimeLocalization dateTimeLocalization,
|
||||
ISiteService siteService,
|
||||
ICalendarManager calendarManager) {
|
||||
|
||||
_orchardServices = orchardServices;
|
||||
_dateTimeLocalization = dateTimeLocalization;
|
||||
_cultureInfo = new Lazy<CultureInfo>(() => CultureInfo.GetCultureInfo(_orchardServices.WorkContext.CurrentCulture));
|
||||
}
|
||||
_orchardServices = orchardServices;
|
||||
_dateTimeLocalization = dateTimeLocalization;
|
||||
_siteService = siteService;
|
||||
_calendarManager = calendarManager;
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertToLocal(DateTime date) {
|
||||
return ConvertToLocal(ToNullable(date));
|
||||
}
|
||||
public virtual DateTime? ConvertToLocal(DateTime date) {
|
||||
return ConvertToLocal(ToNullable(date));
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertToLocal(DateTime? date) {
|
||||
if (!date.HasValue) {
|
||||
return null;
|
||||
}
|
||||
return TimeZoneInfo.ConvertTimeFromUtc(date.Value, _orchardServices.WorkContext.CurrentTimeZone);
|
||||
}
|
||||
public virtual DateTime? ConvertToLocal(DateTime? date) {
|
||||
if (!date.HasValue) {
|
||||
return null;
|
||||
}
|
||||
return TimeZoneInfo.ConvertTimeFromUtc(date.Value, _orchardServices.WorkContext.CurrentTimeZone);
|
||||
}
|
||||
|
||||
public virtual string ConvertToLocalString(DateTime date, string nullText = null) {
|
||||
return ConvertToLocalString(ToNullable(date), _dateTimeLocalization.LongDateTimeFormat.Text, nullText);
|
||||
}
|
||||
public virtual string ConvertToLocalString(DateTime date, string nullText = null) {
|
||||
return ConvertToLocalString(ToNullable(date), _dateTimeLocalization.LongDateTimeFormat.Text, nullText);
|
||||
}
|
||||
|
||||
public virtual string ConvertToLocalString(DateTime date, string format, string nullText = null) {
|
||||
return ConvertToLocalString(ToNullable(date), format, nullText);
|
||||
}
|
||||
public virtual string ConvertToLocalString(DateTime date, string format, string nullText = null) {
|
||||
return ConvertToLocalString(ToNullable(date), format, nullText);
|
||||
}
|
||||
|
||||
public virtual string ConvertToLocalString(DateTime? date, string format, string nullText = null) {
|
||||
var localDate = ConvertToLocal(date);
|
||||
if (!localDate.HasValue) {
|
||||
return nullText;
|
||||
}
|
||||
return localDate.Value.ToString(format, _cultureInfo.Value);
|
||||
}
|
||||
public virtual string ConvertToLocalString(DateTime? date, string format, string nullText = null) {
|
||||
var localDate = ConvertToLocal(date);
|
||||
if (!localDate.HasValue) {
|
||||
return nullText;
|
||||
}
|
||||
|
||||
public virtual string ConvertToLocalDateString(DateTime date, string nullText = null) {
|
||||
return ConvertToLocalDateString(ToNullable(date), nullText);
|
||||
}
|
||||
// If the configured current calendar is different from the default calendar
|
||||
// of the configured current culture we must override the conversion process.
|
||||
// We do this by using a custom CultureInfo modified to use GregorianCalendar
|
||||
// (means no calendar conversion will be performed as part of the string
|
||||
// formatting) and instead perform the calendar conversion ourselves.
|
||||
|
||||
public virtual string ConvertToLocalDateString(DateTime? date, string nullText = null) {
|
||||
return ConvertToLocalString(date, _dateTimeLocalization.ShortDateFormat.Text, nullText);
|
||||
}
|
||||
var cultureInfo = CurrentCulture;
|
||||
var usingCultureCalendar = CurrentCulture.DateTimeFormat.Calendar.GetType().IsInstanceOfType(CurrentCalendar);
|
||||
if (!usingCultureCalendar) {
|
||||
cultureInfo = (CultureInfo)CurrentCulture.Clone();
|
||||
cultureInfo.DateTimeFormat.Calendar = new GregorianCalendar();
|
||||
var calendar = CurrentCalendar;
|
||||
localDate = new DateTime(calendar.GetYear(localDate.Value), calendar.GetMonth(localDate.Value), calendar.GetDayOfMonth(localDate.Value), calendar.GetHour(localDate.Value), calendar.GetMinute(localDate.Value), calendar.GetSecond(localDate.Value));
|
||||
}
|
||||
|
||||
public virtual string ConvertToLocalTimeString(DateTime date, string nullText = null) {
|
||||
return ConvertToLocalTimeString(ToNullable(date), nullText);
|
||||
}
|
||||
return localDate.Value.ToString(format, cultureInfo);
|
||||
}
|
||||
|
||||
public virtual string ConvertToLocalTimeString(DateTime? date, string nullText = null) {
|
||||
return ConvertToLocalString(date, _dateTimeLocalization.ShortTimeFormat.Text, nullText);
|
||||
}
|
||||
public virtual string ConvertToLocalDateString(DateTime date, string nullText = null) {
|
||||
return ConvertToLocalDateString(ToNullable(date), nullText);
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertFromLocal(DateTime date) {
|
||||
return ConvertToLocal(ToNullable(date));
|
||||
}
|
||||
public virtual string ConvertToLocalDateString(DateTime? date, string nullText = null) {
|
||||
return ConvertToLocalString(date, _dateTimeLocalization.ShortDateFormat.Text, nullText);
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertFromLocal(DateTime? date) {
|
||||
if (!date.HasValue) {
|
||||
return null;
|
||||
}
|
||||
return TimeZoneInfo.ConvertTimeToUtc(date.Value, _orchardServices.WorkContext.CurrentTimeZone);
|
||||
}
|
||||
public virtual string ConvertToLocalTimeString(DateTime date, string nullText = null) {
|
||||
return ConvertToLocalTimeString(ToNullable(date), nullText);
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertFromLocalString(string dateString) {
|
||||
if (String.IsNullOrWhiteSpace(dateString)) {
|
||||
return null;
|
||||
}
|
||||
var localDate = DateTime.Parse(dateString, _cultureInfo.Value);
|
||||
return ConvertFromLocal(localDate);
|
||||
}
|
||||
public virtual string ConvertToLocalTimeString(DateTime? date, string nullText = null) {
|
||||
return ConvertToLocalString(date, _dateTimeLocalization.ShortTimeFormat.Text, nullText);
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertFromLocalString(string dateString, string timeString) {
|
||||
if (String.IsNullOrWhiteSpace(dateString) && String.IsNullOrWhiteSpace(timeString)) {
|
||||
return null;
|
||||
}
|
||||
var localDate = !String.IsNullOrWhiteSpace(dateString) ? DateTime.Parse(dateString, _cultureInfo.Value) : new DateTime(1980, 1, 1);
|
||||
var localTime = !String.IsNullOrWhiteSpace(timeString) ? DateTime.Parse(timeString, _cultureInfo.Value) : new DateTime(1980, 1, 1, 12, 0, 0);
|
||||
var localDateTime = new DateTime(localDate.Year, localDate.Month, localDate.Day, localTime.Hour, localTime.Minute, localTime.Second);
|
||||
return ConvertFromLocal(localDateTime);
|
||||
}
|
||||
public virtual DateTime? ConvertFromLocal(DateTime date) {
|
||||
return ConvertToLocal(ToNullable(date));
|
||||
}
|
||||
|
||||
protected virtual DateTime? ToNullable(DateTime date) {
|
||||
return date == DateTime.MinValue ? new DateTime?() : new DateTime?(date);
|
||||
}
|
||||
}
|
||||
public virtual DateTime? ConvertFromLocal(DateTime? date) {
|
||||
if (!date.HasValue) {
|
||||
return null;
|
||||
}
|
||||
return TimeZoneInfo.ConvertTimeToUtc(date.Value, _orchardServices.WorkContext.CurrentTimeZone);
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertFromLocalString(string dateString) {
|
||||
if (String.IsNullOrWhiteSpace(dateString)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
// If the configured current calendar is different from the default calendar
|
||||
// of the configured current culture we must override the conversion process.
|
||||
// We do this by using a custom CultureInfo modified to use GregorianCalendar
|
||||
// (means no calendar conversion will be performed as part of the string
|
||||
// parsing) and instead perform the calendar conversion ourselves.
|
||||
|
||||
var cultureInfo = CurrentCulture;
|
||||
var usingCultureCalendar = CurrentCulture.DateTimeFormat.Calendar.GetType().IsInstanceOfType(CurrentCalendar);
|
||||
if (!usingCultureCalendar) {
|
||||
cultureInfo = (CultureInfo)CurrentCulture.Clone();
|
||||
cultureInfo.DateTimeFormat.Calendar = new GregorianCalendar();
|
||||
}
|
||||
|
||||
var localDate = DateTime.Parse(dateString, CurrentCulture);
|
||||
|
||||
if (!usingCultureCalendar) {
|
||||
var calendar = CurrentCalendar;
|
||||
localDate = calendar.ToDateTime(localDate.Year, localDate.Month, localDate.Day, localDate.Hour, localDate.Minute, localDate.Second, localDate.Millisecond);
|
||||
}
|
||||
|
||||
return ConvertFromLocal(localDate);
|
||||
}
|
||||
|
||||
public virtual DateTime? ConvertFromLocalString(string dateString, string timeString) {
|
||||
if (String.IsNullOrWhiteSpace(dateString) && String.IsNullOrWhiteSpace(timeString)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
// If the configured current calendar is different from the default calendar
|
||||
// of the configured current culture we must override the conversion process.
|
||||
// We do this by using a custom CultureInfo modified to use GregorianCalendar
|
||||
// (means no calendar conversion will be performed as part of the string
|
||||
// parsing) and instead perform the calendar conversion ourselves.
|
||||
|
||||
var cultureInfo = CurrentCulture;
|
||||
var usingCultureCalendar = CurrentCulture.DateTimeFormat.Calendar.GetType().IsInstanceOfType(CurrentCalendar);
|
||||
if (!usingCultureCalendar) {
|
||||
cultureInfo = (CultureInfo)CurrentCulture.Clone();
|
||||
cultureInfo.DateTimeFormat.Calendar = new GregorianCalendar();
|
||||
}
|
||||
|
||||
var localDate = !String.IsNullOrWhiteSpace(dateString) ? DateTime.Parse(dateString, cultureInfo) : new DateTime(1980, 1, 1);
|
||||
var localTime = !String.IsNullOrWhiteSpace(timeString) ? DateTime.Parse(timeString, cultureInfo) : new DateTime(1980, 1, 1, 12, 0, 0);
|
||||
var localDateTime = new DateTime(localDate.Year, localDate.Month, localDate.Day, localTime.Hour, localTime.Minute, localTime.Second);
|
||||
|
||||
if (!usingCultureCalendar) {
|
||||
var calendar = CurrentCalendar;
|
||||
localDateTime = calendar.ToDateTime(localDateTime.Year, localDateTime.Month, localDateTime.Day, localDateTime.Hour, localDateTime.Minute, localDateTime.Second, localDateTime.Millisecond);
|
||||
}
|
||||
|
||||
return ConvertFromLocal(localDateTime);
|
||||
}
|
||||
|
||||
protected virtual CultureInfo CurrentCulture {
|
||||
get {
|
||||
return CultureInfo.GetCultureInfo(_orchardServices.WorkContext.CurrentCulture);
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual Calendar CurrentCalendar {
|
||||
get {
|
||||
if (!String.IsNullOrEmpty(_orchardServices.WorkContext.CurrentCalendar))
|
||||
return _calendarManager.GetCalendarByName(_orchardServices.WorkContext.CurrentCalendar);
|
||||
return CurrentCulture.Calendar;
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual DateTime? ToNullable(DateTime date) {
|
||||
return date == DateTime.MinValue ? new DateTime?() : new DateTime?(date);
|
||||
}
|
||||
}
|
||||
}
|
11
src/Orchard/Localization/Services/ICalendarManager.cs
Normal file
11
src/Orchard/Localization/Services/ICalendarManager.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.Web;
|
||||
|
||||
namespace Orchard.Localization.Services {
|
||||
public interface ICalendarManager : IDependency {
|
||||
IEnumerable<string> ListCalendars();
|
||||
string GetCurrentCalendar(HttpContextBase requestContext);
|
||||
Calendar GetCalendarByName(string calendarName);
|
||||
}
|
||||
}
|
18
src/Orchard/Localization/Services/ICalendarSelector.cs
Normal file
18
src/Orchard/Localization/Services/ICalendarSelector.cs
Normal file
@@ -0,0 +1,18 @@
|
||||
using System.Web;
|
||||
|
||||
namespace Orchard.Localization.Services {
|
||||
public class CalendarSelectorResult {
|
||||
public int Priority {
|
||||
get;
|
||||
set;
|
||||
}
|
||||
public string CalendarName {
|
||||
get;
|
||||
set;
|
||||
}
|
||||
}
|
||||
|
||||
public interface ICalendarSelector : IDependency {
|
||||
CalendarSelectorResult GetCalendar(HttpContextBase context);
|
||||
}
|
||||
}
|
25
src/Orchard/Localization/Services/SiteCalendarSelector.cs
Normal file
25
src/Orchard/Localization/Services/SiteCalendarSelector.cs
Normal file
@@ -0,0 +1,25 @@
|
||||
using System;
|
||||
using System.Web;
|
||||
|
||||
namespace Orchard.Localization.Services {
|
||||
public class SiteCalendarSelector : ICalendarSelector {
|
||||
private readonly IWorkContextAccessor _workContextAccessor;
|
||||
|
||||
public SiteCalendarSelector(IWorkContextAccessor workContextAccessor) {
|
||||
_workContextAccessor = workContextAccessor;
|
||||
}
|
||||
|
||||
public CalendarSelectorResult GetCalendar(HttpContextBase context) {
|
||||
string currentCalendarName = _workContextAccessor.GetContext().CurrentSite.SiteCalendar;
|
||||
|
||||
if (String.IsNullOrEmpty(currentCalendarName)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return new CalendarSelectorResult {
|
||||
Priority = -5,
|
||||
CalendarName = currentCalendarName
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
@@ -266,13 +266,18 @@
|
||||
<Compile Include="FileSystems\Media\FileSystemStorageProvider.cs" />
|
||||
<Compile Include="FileSystems\Media\IMimeTypeProvider.cs" />
|
||||
<Compile Include="Indexing\ISearchBits.cs" />
|
||||
<Compile Include="Localization\Services\CurrentCalendarWorkContext.cs" />
|
||||
<Compile Include="Localization\Services\CurrentCultureWorkContext.cs" />
|
||||
<Compile Include="Localization\Services\DefaultCalendarManager.cs" />
|
||||
<Compile Include="Localization\Services\DefaultDateTimeLocalization.cs" />
|
||||
<Compile Include="Localization\Services\DefaultDateServices.cs" />
|
||||
<Compile Include="Localization\Services\DefaultLocalizedStringManager.cs" />
|
||||
<Compile Include="Localization\Services\ICalendarSelector.cs" />
|
||||
<Compile Include="Localization\Services\ICalendarManager.cs" />
|
||||
<Compile Include="Localization\Services\IDateServices.cs" />
|
||||
<Compile Include="Localization\Services\IDateTimeLocalization.cs" />
|
||||
<Compile Include="Localization\Services\ILocalizedStringManager.cs" />
|
||||
<Compile Include="Localization\Services\SiteCalendarSelector.cs" />
|
||||
<Compile Include="Logging\OrchardFileAppender.cs" />
|
||||
<Compile Include="Logging\OrchardLog4netFactory.cs" />
|
||||
<Compile Include="Logging\OrchardLog4netLogger.cs" />
|
||||
|
@@ -11,6 +11,7 @@ namespace Orchard.Settings {
|
||||
string SuperUser { get; }
|
||||
string HomePage { get; set; }
|
||||
string SiteCulture { get; set; }
|
||||
string SiteCalendar { get; set; }
|
||||
ResourceDebugMode ResourceDebugMode { get; set; }
|
||||
int PageSize { get; set; }
|
||||
string BaseUrl { get; }
|
||||
|
@@ -24,11 +24,9 @@ namespace Orchard {
|
||||
/// <returns>True if the dependency could be resolved, false otherwise</returns>
|
||||
public abstract bool TryResolve<T>(out T service);
|
||||
|
||||
|
||||
public abstract T GetState<T>(string name);
|
||||
public abstract T GetState<T>(string name);
|
||||
public abstract void SetState<T>(string name, T value);
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// The http context corresponding to the work context
|
||||
/// </summary>
|
||||
@@ -77,6 +75,14 @@ namespace Orchard {
|
||||
set { SetState("CurrentCulture", value); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Active calendar of the work context
|
||||
/// </summary>
|
||||
public string CurrentCalendar {
|
||||
get { return GetState<string>("CurrentCalendar"); }
|
||||
set { SetState("CurrentCalendar", value); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Time zone of the work context
|
||||
/// </summary>
|
||||
|
Reference in New Issue
Block a user