Custom Field for Uploading Documents and Images:
Scenario:
Solution:
Column types
Implementation:
Creating the Custom Field Class: [ImageEnhancerField.cs]
Creating FieldControl.ascx [ImageEnhancerFieldControl.ascx]
Creating Custom Field Control Class [ImageEnhancerFieldControl]
Creating Field type Deployment file [fldtypes_ImageEnhancer.xml]
Once we deploy the XML
file, we can see the New Field Type in Create Column of the List.
Configuring Image/Document Library:
New Item Form
In New Item form
we can browse through the file which needs to be uploaded and click on the Save button.
View Item Form
Scenario:
A Custom List has a column for Image and Document URL which is of type Hyperlink or Picture; it is used to store the URL of the Document
or Image.
In order to add an
item to this list, we need to perform two steps.
1.
Upload the Picture or
Document to some Library
2.
Copy the URL of the
uploaded Item and Paste them in the “Hyperlink
or Picture” field.
This seems to be a tedious process and looking for an option
to upload Image or Document in the same
page of Custom List Add Item/Edit Item form.
Solution:
To reduce the two step process, we have created a Custom field type. This Custom Field type allows us to upload
the Image/ Document directly in the
Custom list Dialog box itself, which generates a thumbnail/link to show the Image/Document
in the list view respectively. If we click on the thumbnail a popup with the real size picture will open and a Link to download the Document.
We have created an option to configure the default Document or Image library in the List settings, which is used to store all the Documents/Images and a reference to
this document will be maintained in the list column.
Column types
1. Enhanced Hyperlink - Field
to upload the Documents to the respective Document Library selected in the List
settings.
2. Enhanced Image – Field
to upload the Images to the respective Image Library selected in the List
settings.
Implementation:
1.
Create a public custom
field type class, which inherits from one of the built-in field type classes,
such as SPFieldBoolen, SPFieldChoice, or SPFieldText and name it as ImageEnhancerField.cs.
2.
Create another Class file
which needs to inherit from BaseFieldControl
and name it as ImageEnhancerFieldControl.cs.
3.
Add SharePoint mapped folders to Control
Templates and XML.
4.
Create a User Control under
Control Templates folder and name it
as ImageEnhancerFieldControl.ascx.
Note:
User Control must be deployed directly under Control Templates and not in any sub-folders.
5.
Create an XML file known as the field type deployment file under XML folder and name it as fldtypes_ImageEnhancer.xml.
Creating the Custom Field Class: [ImageEnhancerField.cs]
1.
Inherit the Class from SPFieldText and add two public
constructors using specific parameter list signatures and forward parameters to
base class constructors with matching signatures.
class ImageEnhancerCustomField:
SPFieldText
{
//constructors
public ImageEnhancerCustomField
(SPFieldCollection fields, string fieldName)
: base(fields,
fieldName) { }
public
ImageEnhancerCustomField (SPFieldCollection fields, string typeName, string
displayName)
: base(fields,
typeName, displayName) { }
|
2.
Override the FieldRenderingControl property and
define the get value.
public override
BaseFieldControl FieldRenderingControl
{
get
{
SPContext.Current.List.EnableAttachments
= false;
BaseFieldControl
fieldControl = new ImageEnhancerControl();
fieldControl.FieldName = this.InternalName;
return
fieldControl;
}
}
|
3.
Then Override the GetValidatedString method and return
the value which needs to store in the Field.
public override
string GetValidatedString(object value)
{
return value.ToString().ToUpper();
}
|
Creating FieldControl.ascx [ImageEnhancerFieldControl.ascx]
SharePoint Rendering
Template can work only when we place the ascx file directly under Control
Templates folder not into any sub folders. [Please check comments inside]
<SharePoint:RenderingTemplate Id="ImageEnhancerControlRender" runat="server">
<Template>
<asp:UpdatePanel ID="UpdatePanel1" runat="server">
<ContentTemplate>
<!-- To show
the preview of the image in Edit form -->
<asp:Image ID="ImgThumb" runat="server" />
<!-- To browse
to the file from the physical location -->
<asp:FileUpload runat="server" id="flUpload" size="40"/>
<!-- To Delete
the Image reference in the Edit form -->
<asp:Button runat="server" ID="btnDelete" Text="Delete"/>
<!-- To
validate the Type of File uplodaed -->
<asp:RegularExpressionValidator runat="server"
ErrorMessage="Please
upload png,jpeg or gif files only" ControlToValidate="flUpload" id="ImgRegularExpressionValidator" validationexpression="^.+\.(png|jpeg|jpg|gif)$"
SetFocusOnError="True"></asp:RegularExpressionValidator>
<!-- To Error
Message in case of any issues -->
<asp:Label runat="server" id="lblMessage" />
<asp:Label runat="server" id="lblMessage2" />
<asp:Label runat="server" id="lblMessage3" />
</ContentTemplate>
</asp:UpdatePanel>
</Template>
</SharePoint:RenderingTemplate>
|
Creating Custom Field Control Class [ImageEnhancerFieldControl]
1.
Inherit the Class from BaseFieldControl and override the
DefaultTemplateName property and define the get property value.
protected override
string DefaultTemplateName
{
//Name
of the SharePoint Rendering Template defined in the ascx file.
get
{ return "ImageEnhancerControlRender";
}
}
|
2.
Override the Value property and define the get &
set values. The Value of this field will be stored in this format “File location full path, Thumbnail URL”.
public override
object Value
{
get
{
EnsureChildControls();
if (hasfile)
//if
it’s a new file return the path to the file and the path to the thumbnail
return
httppath + filename + " ," +
thumbnailpath;
else
{
if
(!ImgThumb.Visible)
{
//if it’s going to be erase return a blank string
return "";
}
else
{ //if it’s not
been modified return the current string
return Field.FieldRenderingControl.ItemFieldValue;
}
}
}
set
{
try
{
EnsureChildControls();
if
(!value.ToString().Equals(",") || !value.ToString().Equals(""))
{
// Setting the Image
thumbnail url to the Image control added earlier
ImgThumb.ImageUrl = value.ToString().Substring(value.ToString().IndexOf(',') + 1);
//Setting the Image
control and Delete button control visible in Edit Form if value exists
ImgThumb.Visible = true;
btnDelete.Visible = true;
}
else
{
ImgThumb.Visible = false;
btnDelete.Visible = false;
}
}
catch
{ }
}
}
|
3.
Now define the control how
should it behave in New Form, Display
Form and Edit Form of List Item [Check the inline comments for
description].
protected override
void CreateChildControls()
{
try
{
if
(Field == null) return;
base.CreateChildControls();
if
(ControlMode == Microsoft.SharePoint.WebControls.SPControlMode.Display)
return;
if
(ControlMode == SPControlMode.New ||
ControlMode == SPControlMode.Edit)
{
Stream
fs = null;
// As we set the
Default Template name to the name of SharePoint rendering template name
defined in ascx file.
// Now get the
instance all the controls from the TemplateContanier.
flUpload = (FileUpload)TemplateContainer.FindControl("flUpload");
lblMessage = (Label)TemplateContainer.FindControl("lblMessage");
lblMessage2 = (Label)TemplateContainer.FindControl("lblMessage2");
lblMessage3 = (Label)TemplateContainer.FindControl("lblMessage3");
ImgThumb = (Image)TemplateContainer.FindControl("ImgThumb");
btnDelete = (Button)TemplateContainer.FindControl("btnDelete");
txtValue = (TextBox)TemplateContainer.FindControl("txtValue");
btnDelete.Click += new EventHandler(btnDelete_Click);
try
{
SPContext.Current.Item[Field.Title].Equals("null");
}
catch
(Exception E)
{
ImgThumb.Visible = false;
btnDelete.Visible = false;
}
// Checking
whether the File upload control has any file
if
(flUpload.HasFile)
{
//Checking the
File Content Length
if (flUpload.PostedFile.ContentLength <= 524288)
{
fs =
flUpload.PostedFile.InputStream;
filename =
flUpload.FileName;
hasfile = true;
flUpload.EnableViewState
= false;
flUpload =
filenull;
flUpload.Dispose();
flUpload.Enabled
= false;
fileSize = 0;
//TemplateContainer.fin
}
else
{
hasfile = true;
fileSize = 1;
return;
}
}
flUpload.TabIndex =
TabIndex;
flUpload.CssClass =
CssClass;
flUpload.ToolTip =
Field.Title + " Image";
// Checking the
Default Image library is defined or not. We can define the library in List
settings.
System.Collections.Specialized.NameValueCollection
PictureLibrarys;
PictureLibrarys = SharepointInformation.QueryCustType(SPContext.Current.Web.Url.ToString(), SPEncode.UrlDecodeAsUrl(SPContext.Current.List.ToString()),
"CustomImageStorage", "ImageEnhancerCustomField",Field.Title);
if
(PictureLibrarys[0].Equals("False"))
{
flUpload.Enabled = false;
lblMessage.Text = "Image cannot be uploaded as no Picture Library is
associated with this list. In order to setup Picture Library, go to ";
lblMessage2.Text = "'List Settings - General Settings - Enhanced Image
/ Document Library' ";
lblMessage3.Text = "and select existing Picture Library";
//lblMessage3.ForeColor = "Red";
//lblMessage.ForeColor = "Red";
//lblMessage2.ForeColor = "Red";
lblMessage.Font.Bold
= true;
lblMessage2.Font.Bold
= true;
lblMessage3.Font.Bold
= true;
lblMessage2.Font.Italic = true;
}
else
{
flUpload.Enabled = true;
if (lblMessage != null)
lblMessage.Visible = false;
}
//IF
THE UPLOAD FIELD HAS INFORMATION
if
(hasfile)
{
bool exist = false;
if (PictureLibrarys.HasKeys())
for (int i = 0; i < PictureLibrarys.Count; i++)
{
if
(PictureLibrarys.GetKey(i).Equals(Field.InternalName) ||
PictureLibrarys.GetKey(i).Equals(Field.Title))
{
exist = true;
break;
}
}
if (exist)
{
// Uploads the
File to the SharePoint Image library defined in the List settings if File
exist.
thumbnailpath = SharepointInformation.UploadImage(SPContext.Current.Web.Url.ToString(), fs,
PictureLibrarys[Field.Title], "",
filename, SPContext.Current.Web);
httppath = SPContext.Current.Web.Lists[PictureLibrarys[Field.Title]].ParentWebUrl.ToString()
+ "/" + SPContext.Current.Web.Lists[PictureLibrarys[Field.Title]].RootFolder.Url
+ "/";
}
else
{
thumbnailpath = "Go to List Settings - Enhanced Image
Settings";
}
}
}
}
catch
(Exception spe)
{
int
i = 0;
}
}
|
Creating Field type Deployment file [fldtypes_ImageEnhancer.xml]
Open fldtypes_ImageEnhancer.xml
file and copy the below code [Check the inline comments for description].
<?xml version="1.0" encoding="utf-8"?>
<FieldTypes>
<FieldType>
//Define the Field
Type Name here
<Field Name="TypeName">ImageEnhancerCustomField</Field>
//Define the
Parent Type from the new type is getting Inherited
<Field Name="ParentType">Text</Field>
//Provide the
Display name for the Field
<Field Name="TypeDisplayName">Enhanced Image</Field>
<Field Name="TypeShortDescription">Enhanced Image</Field>
<Field Name="UserCreatable">TRUE</Field>
//Specify where
all this column should be available
<Field Name="ShowInListCreate">TRUE</Field>
<Field Name="ShowInSurveyCreate">TRUE</Field>
<Field Name="ShowInDocumentLibrary">TRUE</Field>
<Field Name="ShowInColumnTemplateCreate">TRUE</Field>
<Field Name="Sortable">TRUE</Field>
<Field Name="Filterable">TRUE</Field>
// Specify the
NameSpace and class details where the implementation is done
<Field Name="FieldTypeClass">EnhancedPicture.ImageEnhancerCustomField,
EnhancedPicture, Version=1.0.0.0, Culture=neutral,
PublicKeyToken=b5ecf5690ed59344</Field>
<Field Name="SQLType">nvarchar</Field>
//Below part is to
define how the field should appear in Display Form
<RenderPattern Name="DisplayPattern">
<Switch>
<Expr>
<Column />
</Expr>
<Case Value="" />
<Default>
<HTML>
<![CDATA[<SCRIPT> function PopupPic(sPicURL) { window.open(
"/_layouts/EnhancedPicture/popup.aspx?"+sPicURL, "",
"HEIGHT=50,WIDTH=50"); } var
path=']]>
</HTML> <Column/>
<HTML>
<![CDATA['; if (path !=
"," || path != "" || path != " ") {var
xsep=path.lastIndexOf(','); var lastind=path.length; document.write("<a
href=\"javascript:PopupPic('" + path.substring(0,xsep) +
"')\"> <IMG
border=0 SRC='"+ path.substring(xsep+1,lastind)+"' ALT='" + path.substring(xsep+1,lastind) +
"' > </a>");}</SCRIPT>]]>
</HTML>
</Default>
</Switch>
</RenderPattern>
</FieldType>
</FieldTypes>
|
Configuring Image/Document Library:
To configure the default Image/Document library where the Images and Documents needs to be
uploaded, Navigate to List Settings à Enhanced Image / Document Library.
Select the Image and Library from the dropdown and Click Accept button. Once the Accept button is clicked we are
updating Fields XML of this current
list with the selected libraries.
To Add a link under General
Settings in List settings page
deploy the below Elements.xml.
<?xml version="1.0" encoding="utf-8"?>
<Elements xmlns="http://schemas.microsoft.com/sharepoint/">
<CustomAction
Id="ImageEnhacer"
GroupId="GeneralSettings"
Location="Microsoft.SharePoint.ListEdit"
Sequence="20"
Title="Enhanced Image /
Document Library"
RequireSiteAdministrator="TRUE"
>
<UrlAction Url="~site/_layouts/EnhancedPicture/PicturePicker.aspx?&siteId={SiteUrl}&listId={ListId}&itemId={ItemId}"/>
</CustomAction>
</Elements>
|
Once the Item is saved,
selected document will be uploaded to the respective library and these New
Columns will have a reference to the
Document / Image.
Navigate to the Libraries
selected in settings page to
verify the uploaded Document / Image.
In the View Item Form, we can see the Thumbnail image for the Image field type and a Link to the
document for Hyperlink field type.
Once clicking on the thumbnail, we can see the Full Image. Upon clicking on the link, document will be downloaded.
Edit Item FormOnce clicking on the thumbnail, we can see the Full Image. Upon clicking on the link, document will be downloaded.
In Edit Item Form,
we can change the Document/Image
reference by clicking the Delete
button, which will remove the reference and we can upload a new Item.
No comments:
Post a Comment