More Calendar!

This commit is contained in:
Mark McDowall 2013-02-24 16:00:17 -08:00
parent 334d4d1e9b
commit ed3a503342
21 changed files with 72 additions and 54 deletions

View File

@ -48,14 +48,14 @@ namespace NzbDrone.Api
//Upcoming //Upcoming
Mapper.CreateMap<Episode, UpcomingResource>() Mapper.CreateMap<Episode, UpcomingResource>()
.ForMember(dest => dest.SeriesTitle, opt => opt.MapFrom(src => src.Series.Title)) .ForMember(dest => dest.SeriesTitle, opt => opt.MapFrom(src => src.Series.Title))
.ForMember(dest => dest.EpisodeTitle, opt => opt.MapFrom(src => src.Title)) .ForMember(dest => dest.EpisodeTitle, opt => opt.MapFrom(src => src.Title));
.ForMember(dest => dest.AirTime, opt => opt.ResolveUsing<AirTimeResolver>());
//Calendar //Calendar
Mapper.CreateMap<Episode, CalendarResource>() Mapper.CreateMap<Episode, CalendarResource>()
.ForMember(dest => dest.SeriesTitle, opt => opt.MapFrom(src => src.Series.Title)) .ForMember(dest => dest.SeriesTitle, opt => opt.MapFrom(src => src.Series.Title))
.ForMember(dest => dest.EpisodeTitle, opt => opt.MapFrom(src => src.Title)) .ForMember(dest => dest.EpisodeTitle, opt => opt.MapFrom(src => src.Title))
.ForMember(dest => dest.AirTime, opt => opt.ResolveUsing<AirTimeResolver>()); .ForMember(dest => dest.Start, opt => opt.MapFrom(src => src.AirDate))
.ForMember(dest => dest.End, opt => opt.ResolveUsing<EndTimeResolver>());
} }
} }
} }

View File

@ -23,7 +23,9 @@ namespace NzbDrone.Api.Calendar
private Response Calendar() private Response Calendar()
{ {
var year = DateTime.Now.Year; var year = DateTime.Now.Year;
var month = DateTime.Now.Month; //Todo: This is just for testing
//var month = DateTime.Now.Month;
var month = 1;
var yearQuery = Request.Query.Year; var yearQuery = Request.Query.Year;
var monthQuery = Request.Query.Month; var monthQuery = Request.Query.Month;

View File

@ -13,7 +13,8 @@ namespace NzbDrone.Api.Calendar
public String EpisodeTitle { get; set; } public String EpisodeTitle { get; set; }
public Int32 SeasonNumber { get; set; } public Int32 SeasonNumber { get; set; }
public Int32 EpisodeNumber { get; set; } public Int32 EpisodeNumber { get; set; }
public DateTime? AirTime { get; set; } public DateTime Start { get; set; }
public DateTime End { get; set; }
public Int32 Status { get; set; } public Int32 Status { get; set; }
public String Overview { get; set; } public String Overview { get; set; }
} }

View File

@ -118,7 +118,7 @@
<Compile Include="FrontendModule\IndexModule.cs" /> <Compile Include="FrontendModule\IndexModule.cs" />
<Compile Include="FrontendModule\BootstrapModule.cs" /> <Compile Include="FrontendModule\BootstrapModule.cs" />
<Compile Include="FrontendModule\LessService.cs" /> <Compile Include="FrontendModule\LessService.cs" />
<Compile Include="Resolvers\AirTimeResolver.cs" /> <Compile Include="Resolvers\EndTimeResolver.cs" />
<Compile Include="Resolvers\NextAiringResolver.cs" /> <Compile Include="Resolvers\NextAiringResolver.cs" />
<Compile Include="Resolvers\NullableDatetimeToString.cs" /> <Compile Include="Resolvers\NullableDatetimeToString.cs" />
<Compile Include="RootFolders\RootFolderModule.cs" /> <Compile Include="RootFolders\RootFolderModule.cs" />

View File

@ -1,22 +0,0 @@
using System;
using System.Collections.Generic;
using System.Linq;
using AutoMapper;
using NzbDrone.Api.QualityProfiles;
using NzbDrone.Core.Repository.Quality;
using NzbDrone.Core.Tv;
namespace NzbDrone.Api.Resolvers
{
public class AirTimeResolver : ValueResolver<Episode, DateTime?>
{
protected override DateTime? ResolveCore(Episode source)
{
if(String.IsNullOrWhiteSpace(source.Series.AirTime) || !source.AirDate.HasValue)
return source.AirDate;
return source.AirDate.Value.Add(Convert.ToDateTime(source.Series.AirTime).TimeOfDay)
.AddHours(source.Series.UtcOffset * -1);
}
}
}

View File

@ -0,0 +1,18 @@
using System;
using System.Collections.Generic;
using System.Linq;
using AutoMapper;
using NzbDrone.Api.QualityProfiles;
using NzbDrone.Core.Repository.Quality;
using NzbDrone.Core.Tv;
namespace NzbDrone.Api.Resolvers
{
public class EndTimeResolver : ValueResolver<Episode, DateTime>
{
protected override DateTime ResolveCore(Episode source)
{
return source.AirDate.Value.AddMinutes(source.Series.Runtime);
}
}
}

View File

@ -1 +1,3 @@
<div id="calendar"></div> <div id="calendar">
</div>
<div id="fakeContainer"></div>

View File

@ -3,33 +3,34 @@
define(['app', 'Calendar/CalendarItemView'], function (app) { define(['app', 'Calendar/CalendarItemView'], function (app) {
NzbDrone.Calendar.CalendarCollectionView = Backbone.Marionette.CompositeView.extend({ NzbDrone.Calendar.CalendarCollectionView = Backbone.Marionette.CompositeView.extend({
itemView: NzbDrone.Calendar.CalendarItemView, itemView: NzbDrone.Calendar.CalendarItemView,
itemViewContainer: '#fakeContainer',
template: 'Calendar/CalendarCollectionTemplate', template: 'Calendar/CalendarCollectionTemplate',
itemViewContainer: 'table',
ui: { ui: {
calendar: '#calendar' calendar: '#calendar'
}, },
initialize: function () { initialize: function (context, collection) {
this.collection = new NzbDrone.Calendar.CalendarCollection(); this.collection = collection;
this.collection.fetch();
this.collection.bind('reset', this.addAll);
}, },
render: function() { onRender: function() {
this.ui.calendar.fullCalendar({ $(this.ui.calendar).fullCalendar({
header: { header: {
left: 'prev,next today', left: 'prev,next today',
center: 'title', center: 'title',
right: 'month,basicWeek,basicDay', right: 'month,basicWeek',
ignoreTimezone: false ignoreTimezone: false
}, },
selectable: true, buttonText: {
selectHelper: true, prev: '<i class="icon-arrow-left"></i>',
editable: true next: '<i class="icon-arrow-right"></i>'
}
}); });
$(this.ui.calendar).fullCalendar('addEventSource', this.collection.toJSON());
}, },
addAll: function(){ addAll: function(){
this.el.fullCalendar('addEventSource', this.collection.toJSON()); $(this.ui.calendar).fullCalendar('addEventSource', this.collection.toJSON());
} }
}); });
}); });

View File

@ -1,7 +1,12 @@
define(['app'], function (app) { define(['app'], function (app) {
NzbDrone.Calendar.CalendarModel = Backbone.Model.extend({ NzbDrone.Calendar.CalendarModel = Backbone.Model.extend({
mutators: { mutators: {
title: function () {
return this.get('seriesTitle') + ' - ' + this.get('seasonNumber') + 'x' + this.get('episodeNumber').pad(2);
},
allDay: function(){
return false;
}
}, },
defaults: { defaults: {
status: 0 status: 0

View File

@ -21,7 +21,9 @@
calendar: function (action, query) { calendar: function (action, query) {
this.setTitle('Calendar'); this.setTitle('Calendar');
NzbDrone.mainRegion.show(new NzbDrone.Calendar.CalendarCollectionView(this, action, query)); var calendarCollection = new NzbDrone.Calendar.CalendarCollection();
calendarCollection.fetch();
NzbDrone.mainRegion.show(new NzbDrone.Calendar.CalendarCollectionView(this, calendarCollection, action, query));
}, },
notFound: function () { notFound: function () {

View File

@ -51,7 +51,6 @@
<li><a href="settings"><i class="icon-cogs"></i><br>Settings</a></li> <li><a href="settings"><i class="icon-cogs"></i><br>Settings</a></li>
<li><a href="system" class="active"><i class="icon-plane"></i><br>System</a></li> <li><a href="system" class="active"><i class="icon-plane"></i><br>System</a></li>
<li><a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=KRTE52U3XJDSQ" target="_blank"><i class="icon-star"></i><br>Donate</a></li> <li><a href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=KRTE52U3XJDSQ" target="_blank"><i class="icon-star"></i><br>Donate</a></li>
</ul> </ul>
</div> </div>
</div> </div>
@ -93,6 +92,7 @@
<script src="/static/JsLibraries/jquery.tablesorter.js"></script> <script src="/static/JsLibraries/jquery.tablesorter.js"></script>
<script src="/static/JsLibraries/jquery.tablesorter.bootstrap.js"></script> <script src="/static/JsLibraries/jquery.tablesorter.bootstrap.js"></script>
<script src="/static/JsLibraries/sugar.js"></script> <script src="/static/JsLibraries/sugar.js"></script>
<script src="/static/JsLibraries/fullcalendar.js"></script>
<script src="/static/Mixins/backbone.marionette.templates.js"></script> <script src="/static/Mixins/backbone.marionette.templates.js"></script>
<script src="/static/Mixins/backbone.ajax.js"></script> <script src="/static/Mixins/backbone.ajax.js"></script>

View File

@ -253,6 +253,7 @@ function Calendar(element, options, eventSources) {
function initialRender() { function initialRender() {
element.html('');
tm = options.theme ? 'ui' : 'fc'; tm = options.theme ? 'ui' : 'fc';
element.addClass('fc'); element.addClass('fc');
if (options.isRTL) { if (options.isRTL) {

View File

@ -106,7 +106,7 @@ namespace NzbDrone.Core.Test.TvTests.EpisodeProviderTests
var fakeEpisode = Builder<Episode>.CreateNew() var fakeEpisode = Builder<Episode>.CreateNew()
.With(e => e.SeriesId = seriesId) .With(e => e.SeriesId = seriesId)
.With(e => e.TvDbEpisodeId = null) .With(e => e.TvDbEpisodeId = 0)
.Build(); .Build();
WithRealDb(); WithRealDb();

View File

@ -7,7 +7,7 @@ namespace NzbDrone.Core.Tv
{ {
public class Episode : ModelBase public class Episode : ModelBase
{ {
public int? TvDbEpisodeId { get; set; } public int TvDbEpisodeId { get; set; }
public int SeriesId { get; set; } public int SeriesId { get; set; }
public int SeasonNumber { get; set; } public int SeasonNumber { get; set; }
@ -26,7 +26,6 @@ namespace NzbDrone.Core.Tv
//Todo: This should be UTC //Todo: This should be UTC
public DateTime? GrabDate { get; set; } public DateTime? GrabDate { get; set; }
public bool HasFile public bool HasFile
{ {
get { return EpisodeFile != null; } get { return EpisodeFile != null; }

View File

@ -235,6 +235,7 @@ namespace NzbDrone.Core.Tv
} }
episodeToUpdate.SeriesId = series.OID; episodeToUpdate.SeriesId = series.OID;
episodeToUpdate.Series = series;
episodeToUpdate.TvDbEpisodeId = episode.Id; episodeToUpdate.TvDbEpisodeId = episode.Id;
episodeToUpdate.EpisodeNumber = episode.EpisodeNumber; episodeToUpdate.EpisodeNumber = episode.EpisodeNumber;
episodeToUpdate.SeasonNumber = episode.SeasonNumber; episodeToUpdate.SeasonNumber = episode.SeasonNumber;
@ -243,8 +244,14 @@ namespace NzbDrone.Core.Tv
episodeToUpdate.Overview = episode.Overview.Truncate(3500); episodeToUpdate.Overview = episode.Overview.Truncate(3500);
if (episode.FirstAired.Year > 1900) if(episode.FirstAired.Year > 1900)
{
episodeToUpdate.AirDate = episode.FirstAired.Date; episodeToUpdate.AirDate = episode.FirstAired.Date;
if (!String.IsNullOrWhiteSpace(series.AirTime))
episodeToUpdate.AirDate = episodeToUpdate.AirDate.Value.Add(Convert.ToDateTime(series.AirTime).TimeOfDay)
.AddHours(series.UtcOffset * -1);
}
else else
episodeToUpdate.AirDate = null; episodeToUpdate.AirDate = null;
@ -313,7 +320,7 @@ namespace NzbDrone.Core.Tv
if (!tvdbEpisodes.Any()) return; if (!tvdbEpisodes.Any()) return;
var seriesEpisodeIds = _episodeRepository.GetEpisodes(series.OID).Select(c => c.OID); var seriesEpisodeIds = _episodeRepository.GetEpisodes(series.OID).Select(c => c.TvDbEpisodeId);
var toBeDeleted = seriesEpisodeIds.Except(tvdbEpisodes.Select(e => e.Id)); var toBeDeleted = seriesEpisodeIds.Except(tvdbEpisodes.Select(e => e.Id));

View File

@ -33,7 +33,11 @@ namespace NzbDrone.Core.Tv
public bool IsIgnored(int seriesId, int seasonNumber) public bool IsIgnored(int seriesId, int seasonNumber)
{ {
return Queryable.Single(c => c.SeriesId == seriesId && c.SeasonNumber == seasonNumber).Ignored; var season = Queryable.SingleOrDefault(c => c.OID == seriesId && c.SeasonNumber == seasonNumber);
if(season == null) return false;
return season.Ignored;
} }
public List<Season> GetSeasonBySeries(int seriesId) public List<Season> GetSeasonBySeries(int seriesId)

View File

@ -29,9 +29,8 @@ namespace NzbDrone.Core.Tv
public string Overview { get; set; } public string Overview { get; set; }
public DayOfWeek? AirsDayOfWeek { get; set; } //public DayOfWeek? AirsDayOfWeek { get; set; }
[Column("AirTimes")]
public String AirTime { get; set; } public String AirTime { get; set; }
public string Language { get; set; } public string Language { get; set; }

View File

@ -63,7 +63,7 @@ namespace NzbDrone.Core.Tv
series.Title = tvDbSeries.SeriesName; series.Title = tvDbSeries.SeriesName;
series.AirTime = CleanAirsTime(tvDbSeries.AirsTime); series.AirTime = CleanAirsTime(tvDbSeries.AirsTime);
series.AirsDayOfWeek = tvDbSeries.AirsDayOfWeek; //series.AirsDayOfWeek = tvDbSeries.AirsDayOfWeek;
series.Overview = tvDbSeries.Overview; series.Overview = tvDbSeries.Overview;
series.Status = tvDbSeries.Status; series.Status = tvDbSeries.Status;
series.Language = tvDbSeries.Language != null ? tvDbSeries.Language.Abbriviation : string.Empty; series.Language = tvDbSeries.Language != null ? tvDbSeries.Language.Abbriviation : string.Empty;

Binary file not shown.

After

Width:  |  Height:  |  Size: 168 KiB

View File

@ -2,7 +2,6 @@
<FileVersion>1</FileVersion> <FileVersion>1</FileVersion>
<AutoEnableOnStartup>False</AutoEnableOnStartup> <AutoEnableOnStartup>False</AutoEnableOnStartup>
<AllowParallelTestExecution>true</AllowParallelTestExecution> <AllowParallelTestExecution>true</AllowParallelTestExecution>
<AllowTestsToRunInParallelWithThemselves>true</AllowTestsToRunInParallelWithThemselves>
<FrameworkUtilisationTypeForNUnit>UseDynamicAnalysis</FrameworkUtilisationTypeForNUnit> <FrameworkUtilisationTypeForNUnit>UseDynamicAnalysis</FrameworkUtilisationTypeForNUnit>
<FrameworkUtilisationTypeForGallio>Disabled</FrameworkUtilisationTypeForGallio> <FrameworkUtilisationTypeForGallio>Disabled</FrameworkUtilisationTypeForGallio>
<FrameworkUtilisationTypeForMSpec>Disabled</FrameworkUtilisationTypeForMSpec> <FrameworkUtilisationTypeForMSpec>Disabled</FrameworkUtilisationTypeForMSpec>

Binary file not shown.