More validation for Settings.

pull/3113/head
Mark McDowall 13 years ago
parent 8f3d4e3128
commit c0e0bf7e66

@ -111,3 +111,17 @@
color: #FFFFFF; color: #FFFFFF;
font-weight: normal; font-weight: normal;
} }
/* Common Validation Settings */
.field-validation-error {
color: red;
}
.input-validation-error {
background-color: #FFEEEE;
border: 1px solid #FF0000;
}
.settingsForm .validation-error {
background: url("../Content/jQueryUI/images/ui-bg_flat_30_b40404_40x100.png") repeat-x scroll 50% 50% #B40404;
}

@ -4,6 +4,7 @@ using System.ComponentModel.DataAnnotations;
using System.Web.Mvc; using System.Web.Mvc;
using NzbDrone.Core.Model; using NzbDrone.Core.Model;
using NzbDrone.Core.Model.Sabnzbd; using NzbDrone.Core.Model.Sabnzbd;
using NzbDrone.Web.Helpers.Validation;
namespace NzbDrone.Web.Models namespace NzbDrone.Web.Models
{ {
@ -12,16 +13,16 @@ namespace NzbDrone.Web.Models
public SelectList PrioritySelectList = public SelectList PrioritySelectList =
new SelectList(new[] {"Default", "Paused", "Low", "Normal", "High", "Force"}); new SelectList(new[] {"Default", "Paused", "Low", "Normal", "High", "Force"});
[Required(ErrorMessage = "Please enter a valid host")]
[DataType(DataType.Text)] [DataType(DataType.Text)]
[DisplayName("SABnzbd Host")] [DisplayName("SABnzbd Host")]
[Description("Hostname or IP Address running SABnzbd")] [Description("Hostname or IP Address running SABnzbd")]
[RequiredIf("DownloadClient", (int)DownloadClientType.Sabnzbd, ErrorMessage = "Required when Download Client is SABnzbd")]
public String SabHost { get; set; } public String SabHost { get; set; }
[Required(ErrorMessage = "Please enter a valid port")]
[DataType(DataType.Text)] [DataType(DataType.Text)]
[DisplayName("SABnzbd Port")] [DisplayName("SABnzbd Port")]
[Description("Port for SABnzbd web interface")] [Description("Port for SABnzbd web interface")]
[RequiredIf("DownloadClient", (int)DownloadClientType.Sabnzbd, ErrorMessage = "Required when Download Client is SABnzbd")]
public int SabPort { get; set; } public int SabPort { get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]
@ -53,14 +54,16 @@ namespace NzbDrone.Web.Models
[Description("Priority to use when sending NZBs to SABnzbd")] [Description("Priority to use when sending NZBs to SABnzbd")]
public SabPriorityType SabTvPriority { get; set; } public SabPriorityType SabTvPriority { get; set; }
[Required(ErrorMessage = "Required so NzbDrone can sort downloads")]
[DisplayName("Download Client TV Directory")] [DisplayName("Download Client TV Directory")]
[Description("The directory where your download client downloads TV shows to (NzbDrone will sort them for you)")] [Description("The directory where your download client downloads TV shows to")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
public string DownloadClientDropDirectory { get; set; } public string DownloadClientDropDirectory { get; set; }
[DisplayName("Blackhole Directory")] [DisplayName("Blackhole Directory")]
[Description("The directory where your download client will pickup NZB files")] [Description("The directory where your download client will pickup NZB files")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("DownloadClient", (int)DownloadClientType.Blackhole, ErrorMessage = "Required when Download Client is Blackhole")]
public string BlackholeDirectory { get; set; } public string BlackholeDirectory { get; set; }
[DisplayName("Download Client")] [DisplayName("Download Client")]

@ -13,7 +13,7 @@ namespace NzbDrone.Web.Models
[DisplayName("Username")] [DisplayName("Username")]
[Description("Username for NZB Matrix")] [Description("Username for NZB Matrix")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("NzbMatrixEnabled", true, ErrorMessage = "USername Required when NZBMatrix is enabled")] [RequiredIf("NzbMatrixEnabled", true, ErrorMessage = "Username Required when NZBMatrix is enabled")]
public String NzbMatrixUsername { get; set; } public String NzbMatrixUsername { get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]

@ -1,6 +1,8 @@
using System.ComponentModel; using System.ComponentModel;
using System.ComponentModel.DataAnnotations; using System.ComponentModel.DataAnnotations;
using System.Web.Mvc; using System.Web.Mvc;
using NzbDrone.Core.Model;
using NzbDrone.Web.Helpers.Validation;
namespace NzbDrone.Web.Models namespace NzbDrone.Web.Models
{ {
@ -31,6 +33,7 @@ namespace NzbDrone.Web.Models
[DisplayName("Hosts")] [DisplayName("Hosts")]
[Description("XBMC hosts with port, comma separated")] [Description("XBMC hosts with port, comma separated")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("XbmcEnabled", true, ErrorMessage = "Required when XBMC Notifications are enabled")]
public string XbmcHosts { get; set; } public string XbmcHosts { get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]
@ -62,12 +65,14 @@ namespace NzbDrone.Web.Models
[DisplayName("Server")] [DisplayName("Server")]
[Description("SMTP Server Hostname")] [Description("SMTP Server Hostname")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("SmtpEnabled", true, ErrorMessage = "Required when SMTP Notifications are enabled")]
public string SmtpServer{ get; set; } public string SmtpServer{ get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]
[DisplayName("Port")] [DisplayName("Port")]
[Description("SMTP Server Port")] [Description("SMTP Server Port")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("SmtpEnabled", true, ErrorMessage = "Required when SMTP Notifications are enabled")]
public int SmtpPort { get; set; } public int SmtpPort { get; set; }
[DisplayName("SSL")] [DisplayName("SSL")]
@ -91,12 +96,14 @@ namespace NzbDrone.Web.Models
[DisplayName("Send From Address")] [DisplayName("Send From Address")]
[Description("Sender Email address")] [Description("Sender Email address")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("SmtpEnabled", true, ErrorMessage = "Required when SMTP Notifications are enabled")]
public string SmtpFromAddress { get; set; } public string SmtpFromAddress { get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]
[DisplayName("Send To Addresses")] [DisplayName("Send To Addresses")]
[Description("Comma separated list of addresses to email")] [Description("Comma separated list of addresses to email")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("SmtpEnabled", true, ErrorMessage = "Required when SMTP Notifications are enabled")]
public string SmtpToAddresses { get; set; } public string SmtpToAddresses { get; set; }
//Twitter //Twitter
@ -129,6 +136,7 @@ namespace NzbDrone.Web.Models
[DisplayName("Host running Growl")] [DisplayName("Host running Growl")]
[Description("Host or IP Address:Port")] [Description("Host or IP Address:Port")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("GrowlEnabled", true, ErrorMessage = "Required when Growl Notifications are enabled")]
public string GrowlHost { get; set; } public string GrowlHost { get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]
@ -155,6 +163,7 @@ namespace NzbDrone.Web.Models
[DisplayName("API Keys")] [DisplayName("API Keys")]
[Description("Comma-Separated list of API Keys")] [Description("Comma-Separated list of API Keys")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("ProwlEnabled", true, ErrorMessage = "Required when Prowl Notifications are enabled")]
public string ProwlApiKeys { get; set; } public string ProwlApiKeys { get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]
@ -186,11 +195,13 @@ namespace NzbDrone.Web.Models
[DisplayName("Server Host")] [DisplayName("Server Host")]
[Description("Plex Server host with port")] [Description("Plex Server host with port")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
[RequiredIf("PlexUpdateLibrary", true, ErrorMessage = "Required when Plex Library Update is Enabled")]
public string PlexServerHost { get; set; } public string PlexServerHost { get; set; }
[DataType(DataType.Text)] [DataType(DataType.Text)]
[DisplayName("Client Hosts")] [DisplayName("Client Hosts")]
[Description("Plex client hosts with port, comma separated for multiple clients")] [Description("Plex client hosts with port, comma separated for multiple clients")]
[RequiredIf("PlexNotifyOnGrab", true, ErrorMessage = "Required when Plex Notifications are enabled")]
[DisplayFormat(ConvertEmptyStringToNull = false)] [DisplayFormat(ConvertEmptyStringToNull = false)]
public string PlexClientHosts { get; set; } public string PlexClientHosts { get; set; }

@ -11,6 +11,7 @@ namespace NzbDrone.Web.Models
[DisplayName("Port")] [DisplayName("Port")]
[Description("Port that NzbDrone runs on")] [Description("Port that NzbDrone runs on")]
[Range(1, 65535, ErrorMessage = "Port must be between 1 and 65535")] [Range(1, 65535, ErrorMessage = "Port must be between 1 and 65535")]
[Required(ErrorMessage = "Port must be between 1 and 65535")]
public int Port { get; set; } public int Port { get; set; }
[DisplayName("Launch Browser")] [DisplayName("Launch Browser")]

@ -8,6 +8,7 @@
<div class="downloadClient"> <div class="downloadClient">
<label class="labelClass">@Html.LabelFor(m => m.BlackholeDirectory) <label class="labelClass">@Html.LabelFor(m => m.BlackholeDirectory)
<span class="small">@Html.DescriptionFor(m => m.BlackholeDirectory)</span> <span class="small">@Html.DescriptionFor(m => m.BlackholeDirectory)</span>
<span class="small">@Html.ValidationMessageFor(m => m.BlackholeDirectory)</span>
</label> </label>
@Html.TextBoxFor(m => m.BlackholeDirectory, new { @class = "inputClass folderLookup" }) @Html.TextBoxFor(m => m.BlackholeDirectory, new { @class = "inputClass folderLookup" })
</div> </div>

@ -35,6 +35,7 @@
@Html.DropDownListFor(m => m.DownloadClient, Model.DownloadClientSelectList, new { @class = "inputClass selectClass" }) @Html.DropDownListFor(m => m.DownloadClient, Model.DownloadClientSelectList, new { @class = "inputClass selectClass" })
<label class="labelClass">@Html.LabelFor(m => m.DownloadClientDropDirectory) <label class="labelClass">@Html.LabelFor(m => m.DownloadClientDropDirectory)
<span class="small">@Html.DescriptionFor(m => m.DownloadClientDropDirectory)</span> <span class="small">@Html.DescriptionFor(m => m.DownloadClientDropDirectory)</span>
<span class="small">@Html.ValidationMessageFor(m => m.DownloadClientDropDirectory)</span>
</label> </label>
@Html.TextBoxFor(m => m.DownloadClientDropDirectory, new { @class = "inputClass folderLookup" }) @Html.TextBoxFor(m => m.DownloadClientDropDirectory, new { @class = "inputClass folderLookup" })
</div> </div>
@ -58,6 +59,38 @@
<script type="text/javascript"> <script type="text/javascript">
$(document).ready(function () { $(document).ready(function () {
$('#downloadClientAccordion').accordion("activate", false); $('#downloadClientAccordion').accordion("activate", false);
//Allow unobstrusive validation of the AJAX loaded form
$.validator.unobtrusive.parse('#DownloadClientForm');
//Validator Settings
var settings = $.data($('#DownloadClientForm')[0], 'validator').settings;
settings.ignore = [];
settings.focusInvalid = false;
settings.onfocusout = function (element) { $(element).valid(); };
var oldHighlight = settings.highlight;
var oldUnhighlight = settings.unhighlight;
settings.highlight = function (element, errorClass, validClass) {
oldHighlight(element, errorClass, validClass);
$(element).parents('div.ui-accordion-content').prev('h3.ui-accordion-header').addClass('validation-error');
};
settings.unhighlight = function (element, errorClass, validClass) {
oldUnhighlight(element, errorClass, validClass);
var container = $(element).parents('div.ui-accordion-content');
if ($(container).children('.' + errorClass).length == 0)
$(container).prev('h3.ui-accordion-header').removeClass('validation-error');
};
});
$(document).on('change', '#DownloadClient', function () {
$("#DownloadClientForm").validate().form();
var container = $('div.ui-accordion-content');
if ($(container).children('.input-validation-error').length == 0)
$(container).prev('h3.ui-accordion-header').removeClass('validation-error');
}); });
var autoConfigureSabUrl = '@Url.Action("AutoConfigureSab", "Settings")'; var autoConfigureSabUrl = '@Url.Action("AutoConfigureSab", "Settings")';

@ -7,32 +7,33 @@
<div class="notifier"> <div class="notifier">
<label class="labelClass">@Html.LabelFor(m => m.GrowlEnabled) <label class="labelClass">@Html.LabelFor(m => m.GrowlEnabled)
<span class="small">@Html.DescriptionFor(m => m.GrowlEnabled)</span> <span class="small">@Html.DescriptionFor(m => m.GrowlEnabled)</span>
</label> </label>
@Html.CheckBoxFor(m => m.GrowlEnabled, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.GrowlEnabled, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.GrowlNotifyOnGrab) <label class="labelClass">@Html.LabelFor(m => m.GrowlNotifyOnGrab)
<span class="small">@Html.DescriptionFor(m => m.GrowlNotifyOnGrab)</span> <span class="small">@Html.DescriptionFor(m => m.GrowlNotifyOnGrab)</span>
</label> </label>
@Html.CheckBoxFor(m => m.GrowlNotifyOnGrab, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.GrowlNotifyOnGrab, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.GrowlNotifyOnDownload) <label class="labelClass">@Html.LabelFor(m => m.GrowlNotifyOnDownload)
<span class="small">@Html.DescriptionFor(m => m.GrowlNotifyOnDownload)</span> <span class="small">@Html.DescriptionFor(m => m.GrowlNotifyOnDownload)</span>
</label> </label>
@Html.CheckBoxFor(m => m.GrowlNotifyOnDownload, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.GrowlNotifyOnDownload, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.GrowlHost) <label class="labelClass">@Html.LabelFor(m => m.GrowlHost)
<span class="small">@Html.DescriptionFor(m => m.GrowlHost)</span> <span class="small">@Html.DescriptionFor(m => m.GrowlHost)</span>
<span class="small">@Html.ValidationMessageFor(m => m.GrowlHost)</span>
</label> </label>
@Html.TextBoxFor(m => m.GrowlHost, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.GrowlHost, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.GrowlPassword) <label class="labelClass">@Html.LabelFor(m => m.GrowlPassword)
<span class="small">@Html.DescriptionFor(m => m.GrowlPassword)</span> <span class="small">@Html.DescriptionFor(m => m.GrowlPassword)</span>
</label> </label>
@Html.TextBoxFor(m => m.GrowlPassword, new { @class = "inputClass", type = "password" }) @Html.TextBoxFor(m => m.GrowlPassword, new { @class = "inputClass", type = "password" })
<label class="labelClass">Register & Test <label class="labelClass">Register & Test
<span class="small">Register NzbDrone in Growl, must be done before notifications will work</span> <span class="small">Register NzbDrone in Growl, must be done before notifications will work</span>
</label> </label>
<input type="button" onclick="registerGrowl();" value="Register & Test" class="inputClass"/> <input type="button" onclick="registerGrowl();" value="Register & Test" class="inputClass"/>
</div> </div>

@ -6,23 +6,6 @@
.indexerStatusContainer { .indexerStatusContainer {
margin-left: 14px; margin-left: 14px;
} }
.field-validation-error {
color: red;
}
.input-validation-error {
background-color: #FFEEEE;
border: 1px solid #FF0000;
}
#IndexersForm .validation-error {
background: url("../../Content/jQueryUI/images/ui-bg_flat_30_b40404_40x100.png") repeat-x scroll 50% 50% #B40404;
}
#validation-error-summary {
display: none;
color: red;
}
</style> </style>
<div class="infoBox"> <div class="infoBox">
RSS feeds are checked every 25 minutes for new episodes.</div> RSS feeds are checked every 25 minutes for new episodes.</div>
@ -148,13 +131,12 @@
@Html.ValidationSummary(true, "Unable to save your settings. Please correct the errors and try again.") @Html.ValidationSummary(true, "Unable to save your settings. Please correct the errors and try again.")
<label class="labelClass">@Html.LabelFor(m => m.Retention) <label class="labelClass">@Html.LabelFor(m => m.Retention)
<span class="small">@Html.DescriptionFor(m => m.Retention)</span> <span class="small">@Html.DescriptionFor(m => m.Retention)</span>
<span class="small">@Html.ValidationMessageFor(m => m.Retention)</span>
</label> </label>
@Html.TextBoxFor(m => m.Retention, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.Retention, new { @class = "inputClass" })
</div> </div>
<button type="submit" class="save_button" disabled="disabled">Save</button> <button type="submit" class="save_button" disabled="disabled">Save</button>
<span id="validation-error-summary">Please check your settings and re-save</span>
} }
</div> </div>
@ -177,18 +159,18 @@
settings.highlight = function (element, errorClass, validClass) { settings.highlight = function (element, errorClass, validClass) {
oldHighlight(element, errorClass, validClass); oldHighlight(element, errorClass, validClass);
$(element).parents('div.indexerPanel').prev('h3.ui-accordion-header').addClass('validation-error'); $(element).parents('div.ui-accordion-content').prev('h3.ui-accordion-header').addClass('validation-error');
}; };
settings.unhighlight = function (element, errorClass, validClass) { settings.unhighlight = function (element, errorClass, validClass) {
oldUnhighlight(element, errorClass, validClass); oldUnhighlight(element, errorClass, validClass);
var container = $(element).parents('div.indexerPanel'); var container = $(element).parents('div.ui-accordion-content');
if ($(container).children('.' + errorClass).length == 0) if ($(container).children('.' + errorClass).length == 0)
$(container).prev('h3.ui-accordion-header').removeClass('validation-error'); $(container).prev('h3.ui-accordion-header').removeClass('validation-error');
}; };
}); });
$('.enabledCheck').on('change', function () { $(document).on('change', '.enabledCheck', function () {
var id = $(this).prop('id'); var id = $(this).prop('id');
var checked = $(this).prop('checked'); var checked = $(this).prop('checked');
@ -211,7 +193,7 @@
reValidate(); reValidate();
}); });
$('.indexerStatusButton').on('change', function () { $(document).on('change', '.indexerStatusButton', function () {
var id = $(this).prop('id'); var id = $(this).prop('id');
var checked = $(this).prop('checked'); var checked = $(this).prop('checked');
@ -236,7 +218,7 @@
function reValidate() { function reValidate() {
$("#IndexersForm").validate().form(); $("#IndexersForm").validate().form();
var container = $('div.indexerPanel'); var container = $('div.ui-accordion-content');
if ($(container).children('.input-validation-error').length == 0) if ($(container).children('.input-validation-error').length == 0)
$(container).prev('h3.ui-accordion-header').removeClass('validation-error'); $(container).prev('h3.ui-accordion-header').removeClass('validation-error');
} }

@ -55,6 +55,40 @@
} }
</div> </div>
<script type="text/javascript"> <script type="text/javascript">
$(document).ready(function () {
//Allow unobstrusive validation of the AJAX loaded form
$.validator.unobtrusive.parse('#NotificationForm');
//Validator Settings
var settings = $.data($('#NotificationForm')[0], 'validator').settings;
settings.ignore = [];
settings.focusInvalid = false;
settings.onfocusout = function (element) { $(element).valid(); };
var oldHighlight = settings.highlight;
var oldUnhighlight = settings.unhighlight;
settings.highlight = function (element, errorClass, validClass) {
oldHighlight(element, errorClass, validClass);
$(element).parents('div.ui-accordion-content').prev('h3.ui-accordion-header').addClass('validation-error');
};
settings.unhighlight = function (element, errorClass, validClass) {
oldUnhighlight(element, errorClass, validClass);
var container = $(element).parents('div.ui-accordion-content');
if ($(container).children('.' + errorClass).length == 0)
$(container).prev('h3.ui-accordion-header').removeClass('validation-error');
};
});
$(document).on('change', '.checkClass', function () {
$("#NotificationForm").validate().form();
var container = $('div.ui-accordion-content');
if ($(container).children('.input-validation-error').length == 0)
$(container).prev('h3.ui-accordion-header').removeClass('validation-error');
});
//Twitter //Twitter
getAuthorizationUrl = '../Command/GetTwitterAuthorization'; getAuthorizationUrl = '../Command/GetTwitterAuthorization';
verifyAuthorizationUrl = '../Command/VerifyTwitterAuthorization'; verifyAuthorizationUrl = '../Command/VerifyTwitterAuthorization';

@ -7,42 +7,44 @@
<div class="notifier"> <div class="notifier">
<label class="labelClass">@Html.LabelFor(m => m.PlexEnabled) <label class="labelClass">@Html.LabelFor(m => m.PlexEnabled)
<span class="small">@Html.DescriptionFor(m => m.PlexEnabled)</span> <span class="small">@Html.DescriptionFor(m => m.PlexEnabled)</span>
</label> </label>
@Html.CheckBoxFor(m => m.PlexEnabled, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.PlexEnabled, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.PlexNotifyOnGrab) <label class="labelClass">@Html.LabelFor(m => m.PlexNotifyOnGrab)
<span class="small">@Html.DescriptionFor(m => m.PlexNotifyOnGrab)</span> <span class="small">@Html.DescriptionFor(m => m.PlexNotifyOnGrab)</span>
</label> </label>
@Html.CheckBoxFor(m => m.PlexNotifyOnGrab, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.PlexNotifyOnGrab, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.PlexNotifyOnDownload) <label class="labelClass">@Html.LabelFor(m => m.PlexNotifyOnDownload)
<span class="small">@Html.DescriptionFor(m => m.PlexNotifyOnDownload)</span> <span class="small">@Html.DescriptionFor(m => m.PlexNotifyOnDownload)</span>
</label> </label>
@Html.CheckBoxFor(m => m.PlexNotifyOnDownload, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.PlexNotifyOnDownload, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.PlexUpdateLibrary) <label class="labelClass">@Html.LabelFor(m => m.PlexUpdateLibrary)
<span class="small">@Html.DescriptionFor(m => m.PlexUpdateLibrary)</span> <span class="small">@Html.DescriptionFor(m => m.PlexUpdateLibrary)</span>
</label> </label>
@Html.CheckBoxFor(m => m.PlexUpdateLibrary, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.PlexUpdateLibrary, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.PlexServerHost) <label class="labelClass">@Html.LabelFor(m => m.PlexServerHost)
<span class="small">@Html.DescriptionFor(m => m.PlexServerHost)</span> <span class="small">@Html.DescriptionFor(m => m.PlexServerHost)</span>
<span class="small">@Html.ValidationMessageFor(m => m.PlexServerHost)</span>
</label> </label>
@Html.TextBoxFor(m => m.PlexServerHost, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.PlexServerHost, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.PlexClientHosts) <label class="labelClass">@Html.LabelFor(m => m.PlexClientHosts)
<span class="small">@Html.DescriptionFor(m => m.PlexClientHosts)</span> <span class="small">@Html.DescriptionFor(m => m.PlexClientHosts)</span>
<span class="small">@Html.ValidationMessageFor(m => m.PlexClientHosts)</span>
</label> </label>
@Html.TextBoxFor(m => m.PlexClientHosts, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.PlexClientHosts, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.PlexUsername) <label class="labelClass">@Html.LabelFor(m => m.PlexUsername)
<span class="small">@Html.DescriptionFor(m => m.PlexUsername)</span> <span class="small">@Html.DescriptionFor(m => m.PlexUsername)</span>
</label> </label>
@Html.TextBoxFor(m => m.PlexUsername, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.PlexUsername, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.PlexPassword) <label class="labelClass">@Html.LabelFor(m => m.PlexPassword)
<span class="small">@Html.DescriptionFor(m => m.PlexPassword)</span> <span class="small">@Html.DescriptionFor(m => m.PlexPassword)</span>
</label> </label>
@Html.TextBoxFor(m => m.PlexPassword, new { @class = "inputClass", type = "password" }) @Html.TextBoxFor(m => m.PlexPassword, new { @class = "inputClass", type = "password" })
</div> </div>

@ -7,27 +7,28 @@
<div class="notifier"> <div class="notifier">
<label class="labelClass">@Html.LabelFor(m => m.ProwlEnabled) <label class="labelClass">@Html.LabelFor(m => m.ProwlEnabled)
<span class="small">@Html.DescriptionFor(m => m.ProwlEnabled)</span> <span class="small">@Html.DescriptionFor(m => m.ProwlEnabled)</span>
</label> </label>
@Html.CheckBoxFor(m => m.ProwlEnabled, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.ProwlEnabled, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.ProwlNotifyOnGrab) <label class="labelClass">@Html.LabelFor(m => m.ProwlNotifyOnGrab)
<span class="small">@Html.DescriptionFor(m => m.ProwlNotifyOnGrab)</span> <span class="small">@Html.DescriptionFor(m => m.ProwlNotifyOnGrab)</span>
</label> </label>
@Html.CheckBoxFor(m => m.ProwlNotifyOnGrab, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.ProwlNotifyOnGrab, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.ProwlNotifyOnDownload) <label class="labelClass">@Html.LabelFor(m => m.ProwlNotifyOnDownload)
<span class="small">@Html.DescriptionFor(m => m.ProwlNotifyOnDownload)</span> <span class="small">@Html.DescriptionFor(m => m.ProwlNotifyOnDownload)</span>
</label> </label>
@Html.CheckBoxFor(m => m.ProwlNotifyOnDownload, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.ProwlNotifyOnDownload, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.ProwlApiKeys) <label class="labelClass">@Html.LabelFor(m => m.ProwlApiKeys)
<span class="small">@Html.DescriptionFor(m => m.ProwlApiKeys)</span> <span class="small">@Html.DescriptionFor(m => m.ProwlApiKeys)</span>
<span class="small">@Html.ValidationMessageFor(m => m.ProwlApiKeys)</span>
</label> </label>
@Html.TextBoxFor(m => m.ProwlApiKeys, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.ProwlApiKeys, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.ProwlPriority) <label class="labelClass">@Html.LabelFor(m => m.ProwlPriority)
<span class="small">@Html.DescriptionFor(m => m.ProwlPriority)</span> <span class="small">@Html.DescriptionFor(m => m.ProwlPriority)</span>
</label> </label>
@Html.DropDownListFor(m => m.ProwlPriority, Model.ProwlPrioritySelectList, new { @class = "inputClass selectClass" }) @Html.DropDownListFor(m => m.ProwlPriority, Model.ProwlPrioritySelectList, new { @class = "inputClass selectClass" })
</div> </div>

@ -15,11 +15,13 @@
<label class="labelClass">@Html.LabelFor(m => m.SabHost) <label class="labelClass">@Html.LabelFor(m => m.SabHost)
<span class="small">@Html.DescriptionFor(m => m.SabHost)</span> <span class="small">@Html.DescriptionFor(m => m.SabHost)</span>
<span class="small">@Html.ValidationMessageFor(m => m.SabHost)</span>
</label> </label>
@Html.TextBoxFor(m => m.SabHost, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.SabHost, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.SabPort) <label class="labelClass">@Html.LabelFor(m => m.SabPort)
<span class="small">@Html.DescriptionFor(m => m.SabPort)</span> <span class="small">@Html.DescriptionFor(m => m.SabPort)</span>
<span class="small">@Html.ValidationMessageFor(m => m.SabPort)</span>
</label> </label>
@Html.TextBoxFor(m => m.SabPort, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.SabPort, new { @class = "inputClass" })

@ -7,52 +7,56 @@
<div class="notifier"> <div class="notifier">
<label class="labelClass">@Html.LabelFor(m => m.SmtpEnabled) <label class="labelClass">@Html.LabelFor(m => m.SmtpEnabled)
<span class="small">@Html.DescriptionFor(m => m.SmtpEnabled)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpEnabled)</span>
</label> </label>
@Html.CheckBoxFor(m => m.SmtpEnabled, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.SmtpEnabled, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpNotifyOnGrab) <label class="labelClass">@Html.LabelFor(m => m.SmtpNotifyOnGrab)
<span class="small">@Html.DescriptionFor(m => m.SmtpNotifyOnGrab)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpNotifyOnGrab)</span>
</label> </label>
@Html.CheckBoxFor(m => m.SmtpNotifyOnGrab, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.SmtpNotifyOnGrab, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpNotifyOnDownload) <label class="labelClass">@Html.LabelFor(m => m.SmtpNotifyOnDownload)
<span class="small">@Html.DescriptionFor(m => m.SmtpNotifyOnDownload)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpNotifyOnDownload)</span>
</label> </label>
@Html.CheckBoxFor(m => m.SmtpNotifyOnDownload, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.SmtpNotifyOnDownload, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpServer) <label class="labelClass">@Html.LabelFor(m => m.SmtpServer)
<span class="small">@Html.DescriptionFor(m => m.SmtpServer)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpServer)</span>
<span class="small">@Html.ValidationMessageFor(m => m.SmtpServer)</span>
</label> </label>
@Html.TextBoxFor(m => m.SmtpServer, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.SmtpServer, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpPort) <label class="labelClass">@Html.LabelFor(m => m.SmtpPort)
<span class="small">@Html.DescriptionFor(m => m.SmtpPort)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpPort)</span>
<span class="small">@Html.ValidationMessageFor(m => m.SmtpPort)</span>
</label> </label>
@Html.TextBoxFor(m => m.SmtpPort, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.SmtpPort, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpUseSsl) <label class="labelClass">@Html.LabelFor(m => m.SmtpUseSsl)
<span class="small">@Html.DescriptionFor(m => m.SmtpUseSsl)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpUseSsl)</span>
</label> </label>
@Html.CheckBoxFor(m => m.SmtpUseSsl, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.SmtpUseSsl, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpUsername) <label class="labelClass">@Html.LabelFor(m => m.SmtpUsername)
<span class="small">@Html.DescriptionFor(m => m.SmtpUsername)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpUsername)</span>
</label> </label>
@Html.TextBoxFor(m => m.SmtpUsername, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.SmtpUsername, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpPassword) <label class="labelClass">@Html.LabelFor(m => m.SmtpPassword)
<span class="small">@Html.DescriptionFor(m => m.SmtpPassword)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpPassword)</span>
</label> </label>
@Html.TextBoxFor(m => m.SmtpPassword, new { @class = "inputClass", type = "password" }) @Html.TextBoxFor(m => m.SmtpPassword, new { @class = "inputClass", type = "password" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpFromAddress) <label class="labelClass">@Html.LabelFor(m => m.SmtpFromAddress)
<span class="small">@Html.DescriptionFor(m => m.SmtpFromAddress)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpFromAddress)</span>
<span class="small">@Html.ValidationMessageFor(m => m.SmtpFromAddress)</span>
</label> </label>
@Html.TextBoxFor(m => m.SmtpFromAddress, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.SmtpFromAddress, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.SmtpToAddresses) <label class="labelClass">@Html.LabelFor(m => m.SmtpToAddresses)
<span class="small">@Html.DescriptionFor(m => m.SmtpToAddresses)</span> <span class="small">@Html.DescriptionFor(m => m.SmtpToAddresses)</span>
<span class="small">@Html.ValidationMessageFor(m => m.SmtpToAddresses)</span>
</label> </label>
@Html.TextBoxFor(m => m.SmtpToAddresses, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.SmtpToAddresses, new { @class = "inputClass" })

@ -4,7 +4,7 @@
<div class="infoBox"> <div class="infoBox">
You must manually restart NzbDrone for these changes to take effect. (Automatic restart comming soon!) You must manually restart NzbDrone for these changes to take effect. (Automatic restart coming soon!)
</div> </div>
<div id="stylized"> <div id="stylized">
@ -18,6 +18,7 @@
<label class="labelClass">@Html.LabelFor(m => m.Port) <label class="labelClass">@Html.LabelFor(m => m.Port)
<span class="small">@Html.DescriptionFor(m => m.Port)</span> <span class="small">@Html.DescriptionFor(m => m.Port)</span>
<span class="small">@Html.ValidationMessageFor(m => m.Port)</span>
</label> </label>
@Html.TextBoxFor(m => m.Port, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.Port, new { @class = "inputClass" })
@ -35,3 +36,31 @@
Save</button> Save</button>
} }
</div> </div>
<script type="text/javascript">
$(document).ready(function () {
//Allow unobstrusive validation of the AJAX loaded form
$.validator.unobtrusive.parse('#SystemForm');
//Validator Settings
var settings = $.data($('#SystemForm')[0], 'validator').settings;
settings.ignore = [];
settings.focusInvalid = false;
settings.onfocusout = function (element) { $(element).valid(); };
var oldHighlight = settings.highlight;
var oldUnhighlight = settings.unhighlight;
settings.highlight = function (element, errorClass, validClass) {
oldHighlight(element, errorClass, validClass);
$(element).parents('div.ui-accordion-content').prev('h3.ui-accordion-header').addClass('validation-error');
};
settings.unhighlight = function (element, errorClass, validClass) {
oldUnhighlight(element, errorClass, validClass);
var container = $(element).parents('div.ui-accordion-content');
if ($(container).children('.' + errorClass).length == 0)
$(container).prev('h3.ui-accordion-header').removeClass('validation-error');
};
});
</script>

@ -7,42 +7,43 @@
<div class="notifier"> <div class="notifier">
<label class="labelClass">@Html.LabelFor(m => m.XbmcEnabled) <label class="labelClass">@Html.LabelFor(m => m.XbmcEnabled)
<span class="small">@Html.DescriptionFor(m => m.XbmcEnabled)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcEnabled)</span>
</label> </label>
@Html.CheckBoxFor(m => m.XbmcEnabled, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.XbmcEnabled, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.XbmcNotifyOnGrab) <label class="labelClass">@Html.LabelFor(m => m.XbmcNotifyOnGrab)
<span class="small">@Html.DescriptionFor(m => m.XbmcNotifyOnGrab)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcNotifyOnGrab)</span>
</label> </label>
@Html.CheckBoxFor(m => m.XbmcNotifyOnGrab, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.XbmcNotifyOnGrab, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.XbmcNotifyOnDownload) <label class="labelClass">@Html.LabelFor(m => m.XbmcNotifyOnDownload)
<span class="small">@Html.DescriptionFor(m => m.XbmcNotifyOnDownload)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcNotifyOnDownload)</span>
</label> </label>
@Html.CheckBoxFor(m => m.XbmcNotifyOnDownload, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.XbmcNotifyOnDownload, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.XbmcUpdateLibrary) <label class="labelClass">@Html.LabelFor(m => m.XbmcUpdateLibrary)
<span class="small">@Html.DescriptionFor(m => m.XbmcUpdateLibrary)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcUpdateLibrary)</span>
</label> </label>
@Html.CheckBoxFor(m => m.XbmcUpdateLibrary, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.XbmcUpdateLibrary, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.XbmcCleanLibrary) <label class="labelClass">@Html.LabelFor(m => m.XbmcCleanLibrary)
<span class="small">@Html.DescriptionFor(m => m.XbmcCleanLibrary)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcCleanLibrary)</span>
</label> </label>
@Html.CheckBoxFor(m => m.XbmcCleanLibrary, new { @class = "inputClass checkClass" }) @Html.CheckBoxFor(m => m.XbmcCleanLibrary, new { @class = "inputClass checkClass" })
<label class="labelClass">@Html.LabelFor(m => m.XbmcHosts) <label class="labelClass">@Html.LabelFor(m => m.XbmcHosts)
<span class="small">@Html.DescriptionFor(m => m.XbmcHosts)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcHosts)</span>
<span class="small">@Html.ValidationMessageFor(m => m.XbmcHosts)</span>
</label> </label>
@Html.TextBoxFor(m => m.XbmcHosts, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.XbmcHosts, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.XbmcUsername) <label class="labelClass">@Html.LabelFor(m => m.XbmcUsername)
<span class="small">@Html.DescriptionFor(m => m.XbmcUsername)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcUsername)</span>
</label> </label>
@Html.TextBoxFor(m => m.XbmcUsername, new { @class = "inputClass" }) @Html.TextBoxFor(m => m.XbmcUsername, new { @class = "inputClass" })
<label class="labelClass">@Html.LabelFor(m => m.XbmcPassword) <label class="labelClass">@Html.LabelFor(m => m.XbmcPassword)
<span class="small">@Html.DescriptionFor(m => m.XbmcPassword)</span> <span class="small">@Html.DescriptionFor(m => m.XbmcPassword)</span>
</label> </label>
@Html.TextBoxFor(m => m.XbmcPassword, new { @class = "inputClass", type = "password" }) @Html.TextBoxFor(m => m.XbmcPassword, new { @class = "inputClass", type = "password" })
</div> </div>
Loading…
Cancel
Save