using System;
using System.Linq;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Xml.XPath;
using umbraco.cms.businesslogic.datatype;
namespace umbraco.editorControls.XPathDropDownList
{
class XPathDropDownListPreValueEditor : AbstractJsonPrevalueEditor
{
///
/// Radio buttons to select type of node to pick from: Content / Media / Members
///
private RadioButtonList typeRadioButtonList = new RadioButtonList();
///
/// TextBox control to get the XPath expression
///
private TextBox xPathTextBox = new TextBox();
///
/// RequiredFieldValidator to ensure an XPath expression has been entered
///
private RequiredFieldValidator xPathRequiredFieldValidator = new RequiredFieldValidator();
///
/// Server side validation of XPath expression
///
private CustomValidator xPathCustomValidator = new CustomValidator();
///
/// Drop Down List to pick either Node Name or Node Id
///
private DropDownList valueTypeDropDownList = new DropDownList();
///
/// Data object used to define the configuration status of this PreValueEditor
///
private XPathDropDownListOptions options = null;
///
/// Gets the options data object that represents the current state of this datatypes configuration
///
internal XPathDropDownListOptions Options
{
get
{
if (this.options == null)
{
// Deserialize any stored settings for this PreValueEditor instance
this.options = this.GetPreValueOptions();
// If still null, ie, object couldn't be de-serialized from PreValue[0] string value
if (this.options == null)
{
// Create a new Options data object with the default values
this.options = new XPathDropDownListOptions();
}
}
return this.options;
}
}
///
/// Initialize a new instance of XPathCheckBoxlistPreValueEditor
///
/// XPathCheckBoxListDataType
public XPathDropDownListPreValueEditor(umbraco.cms.businesslogic.datatype.BaseDataType dataType)
: base(dataType, umbraco.cms.businesslogic.datatype.DBTypes.Nvarchar)
{
}
///
/// Creates all of the controls and assigns all of their properties
///
protected override void CreateChildControls()
{
//radio buttons to select type of nodes that can be picked (Document, Media or Member)
this.typeRadioButtonList.Items.Add(new ListItem(uQuery.UmbracoObjectType.Document.GetFriendlyName(), uQuery.UmbracoObjectType.Document.GetGuid().ToString()));
this.typeRadioButtonList.Items.Add(new ListItem(uQuery.UmbracoObjectType.Media.GetFriendlyName(), uQuery.UmbracoObjectType.Media.GetGuid().ToString()));
this.typeRadioButtonList.Items.Add(new ListItem(uQuery.UmbracoObjectType.Member.GetFriendlyName(), uQuery.UmbracoObjectType.Member.GetGuid().ToString()));
this.xPathTextBox.ID = "xPathTextBox";
this.xPathTextBox.CssClass = "umbEditorTextField";
this.xPathRequiredFieldValidator.ControlToValidate = this.xPathTextBox.ID;
this.xPathRequiredFieldValidator.Display = ValidatorDisplay.Dynamic;
this.xPathRequiredFieldValidator.ErrorMessage = " XPath expression required";
this.xPathCustomValidator.ControlToValidate = this.xPathTextBox.ID;
this.xPathCustomValidator.Display = ValidatorDisplay.Dynamic;
this.xPathCustomValidator.ServerValidate += new ServerValidateEventHandler(this.XPathCustomValidator_ServerValidate);
this.valueTypeDropDownList.ID = "valueTypeDropDownList";
this.valueTypeDropDownList.Items.Add(new ListItem("Node Id", bool.TrueString));
this.valueTypeDropDownList.Items.Add(new ListItem("Node Name", bool.FalseString));
this.Controls.AddPrevalueControls(
this.typeRadioButtonList,
this.xPathTextBox,
this.xPathRequiredFieldValidator,
this.xPathCustomValidator,
this.valueTypeDropDownList);
}
///
///
///
///
protected override void OnLoad(EventArgs e)
{
base.OnLoad(e);
// Read in stored configuration values
this.typeRadioButtonList.SelectedValue = this.Options.Type;
this.xPathTextBox.Text = this.Options.XPath;
this.valueTypeDropDownList.SelectedValue = this.Options.UseId.ToString();
}
///
/// Will run the entered XPath expression to ensure it returns a collection
///
/// xPathCustomValidator
///
private void XPathCustomValidator_ServerValidate(object source, ServerValidateEventArgs args)
{
string xPath = args.Value;
bool isValid = false;
try
{
switch (this.options.UmbracoObjectType)
{
case uQuery.UmbracoObjectType.Document:
if (uQuery.GetNodesByXPath(xPath).Count() >= 0)
{
isValid = true;
}
break;
case uQuery.UmbracoObjectType.Media:
if (uQuery.GetMediaByXPath(xPath).Count() >= 0)
{
isValid = true;
}
break;
case uQuery.UmbracoObjectType.Member:
if (uQuery.GetMembersByXPath(xPath).Count() >= 0)
{
isValid = true;
}
break;
}
}
catch (XPathException)
{
this.xPathCustomValidator.ErrorMessage = " Syntax error in XPath expression";
}
args.IsValid = isValid;
}
///
/// Saves the pre value data to Umbraco
///
public override void Save()
{
if (this.Page.IsValid)
{
this.Options.Type = this.typeRadioButtonList.SelectedValue;
this.Options.XPath = this.xPathTextBox.Text;
this.Options.UseId = bool.Parse(this.valueTypeDropDownList.SelectedValue);
this.SaveAsJson(this.Options); // Serialize to Umbraco database field
}
}
///
/// Replaces the base class writer and instead uses the shared uComponents extension method, to inject consistant markup
///
///
protected override void RenderContents(HtmlTextWriter writer)
{
writer.AddPrevalueRow(
"Type",
"the xml schema to query",
this.typeRadioButtonList);
writer.AddPrevalueRow(
"XPath Expression",
"can use the tokens $ancestorOrSelf, $parentPage and $currentPage",
this.xPathTextBox,
this.xPathRequiredFieldValidator,
this.xPathCustomValidator);
writer.AddPrevalueRow(
"Value",
"store the node id or the name",
this.valueTypeDropDownList);
}
}
}