头像选择控件[原创]
闲着没事,弄了个大家常见的头像选择控件。
虽然是个小东东,但是用处还是蛮多的。比如大道论坛、Blog、聊天室;小到留言本都有可能用的到。麻雀虽小,五脏俱全。开放源代码让大家砸吧。
主要思路:
用System.IO读取指定文件夹下的所有图片,select中optoins的Value为图片的相对路径,Text为图片的名字。不使用数据库(这样如果头像很多效率可能不是太高),当选择的option变化的时候,显示预览图片(无刷新)。这样,就不能单纯的通过继承DropDownList来实现了,所以只好选择继承WebControl。同时,为了实现数据回发并能够在服务器端取得选择的值,还要继承IPostBackDataHandler接口。
public class FaceSelect : WebControl, IPostBackDataHandler
{
……
}
{
……
}
绘制select和img控件的代码如下:
绘制select:
/// <summary>
/// 产生选择列表
/// </summary>
/// <param name="writer"></param>
/// 作者:张伟
/// 日期:2006-10-20
private void RenderFaceSelectControl(HtmlTextWriter writer)
{
//获取当前选中的头像
string dFace = SelectedFace;
//向下拉列表表添加属性
writer.AddAttribute(HtmlTextWriterAttribute.Name, this.ClientID + "_FaceSelect");
writer.AddAttribute(HtmlTextWriterAttribute.Id, this.ClientID + "_FaceSelect");
//注册JS
writer.AddAttribute(HtmlTextWriterAttribute.Onchange, string.Format(HEADER_SELECT_HOOK, this.ClientID + "_FaceSelect", this.ClientID + "_FaceImageShow"));
//取得服务器端头像存储的文件夹
string strServerFacePath = HttpContext.Current.Server.MapPath(FaceUrl);
if (!Directory.Exists(strServerFacePath))//如果文件夹不存在
{
writer.WriteLine(string.Format("<option value=\"ERROR\">头像系统出错</option>"));
return;
}
//获取所有头像
string[] faceImages = Directory.GetFiles(strServerFacePath);
//开始输出下拉列表
writer.RenderBeginTag(HtmlTextWriterTag.Select);
if (bIsShowNoticeText)//如果显示提示文字
{
//添加提示文字
if (dFace == strNoSelectImage || dFace == "NULL")
{
writer.WriteLine("<option value=\"" + strNoSelectImage + "\" selected>" + strSelectNoticeText + "</option>");
}
else
{
writer.WriteLine("<option value=\"" + strNoSelectImage + "\">" + strSelectNoticeText + "</option>");
}
}
foreach (string faceImage in faceImages)
{
string[] parts = faceImage.Split('\\');
string faceImageName = parts[parts.Length - 1];
FileInfo faceImageInfo = new FileInfo(faceImage);
string strExtension = faceImageInfo.Extension.ToUpper();
if (strExtension == ".GIF" || strExtension == ".JPG" || strExtension == ".PNG" || strExtension == ".BMP")
{
if (faceImage == HttpContext.Current.Server.MapPath(dFace))
{
writer.WriteLine(string.Format("<option value=\"{0}\" selected>{1}</option>", FaceUrl + faceImageName, faceImageName.Remove(faceImageName.LastIndexOf('.'))));
}
else
{
writer.WriteLine(string.Format("<option value=\"{0}\">{1}</option>", FaceUrl + faceImageName, faceImageName.Remove(faceImageName.LastIndexOf('.'))));
}
}
}
writer.RenderEndTag();
}
/// 产生选择列表
/// </summary>
/// <param name="writer"></param>
/// 作者:张伟
/// 日期:2006-10-20
private void RenderFaceSelectControl(HtmlTextWriter writer)
{
//获取当前选中的头像
string dFace = SelectedFace;
//向下拉列表表添加属性
writer.AddAttribute(HtmlTextWriterAttribute.Name, this.ClientID + "_FaceSelect");
writer.AddAttribute(HtmlTextWriterAttribute.Id, this.ClientID + "_FaceSelect");
//注册JS
writer.AddAttribute(HtmlTextWriterAttribute.Onchange, string.Format(HEADER_SELECT_HOOK, this.ClientID + "_FaceSelect", this.ClientID + "_FaceImageShow"));
//取得服务器端头像存储的文件夹
string strServerFacePath = HttpContext.Current.Server.MapPath(FaceUrl);
if (!Directory.Exists(strServerFacePath))//如果文件夹不存在
{
writer.WriteLine(string.Format("<option value=\"ERROR\">头像系统出错</option>"));
return;
}
//获取所有头像
string[] faceImages = Directory.GetFiles(strServerFacePath);
//开始输出下拉列表
writer.RenderBeginTag(HtmlTextWriterTag.Select);
if (bIsShowNoticeText)//如果显示提示文字
{
//添加提示文字
if (dFace == strNoSelectImage || dFace == "NULL")
{
writer.WriteLine("<option value=\"" + strNoSelectImage + "\" selected>" + strSelectNoticeText + "</option>");
}
else
{
writer.WriteLine("<option value=\"" + strNoSelectImage + "\">" + strSelectNoticeText + "</option>");
}
}
foreach (string faceImage in faceImages)
{
string[] parts = faceImage.Split('\\');
string faceImageName = parts[parts.Length - 1];
FileInfo faceImageInfo = new FileInfo(faceImage);
string strExtension = faceImageInfo.Extension.ToUpper();
if (strExtension == ".GIF" || strExtension == ".JPG" || strExtension == ".PNG" || strExtension == ".BMP")
{
if (faceImage == HttpContext.Current.Server.MapPath(dFace))
{
writer.WriteLine(string.Format("<option value=\"{0}\" selected>{1}</option>", FaceUrl + faceImageName, faceImageName.Remove(faceImageName.LastIndexOf('.'))));
}
else
{
writer.WriteLine(string.Format("<option value=\"{0}\">{1}</option>", FaceUrl + faceImageName, faceImageName.Remove(faceImageName.LastIndexOf('.'))));
}
}
}
writer.RenderEndTag();
}
绘制Img控件:
/// <summary>
/// 产生图片显示控件
/// </summary>
/// <param name="writer"></param>
/// 作者:张伟
/// 日期:2006-10-20
private void RenderImageShow(HtmlTextWriter writer)
{
writer.AddAttribute(HtmlTextWriterAttribute.Name, this.ClientID + "_FaceImageShow");
writer.AddAttribute(HtmlTextWriterAttribute.Id, this.ClientID + "_FaceImageShow");
//如果没有选头像
if (string.IsNullOrEmpty(strSelectedFace) || strSelectedFace == "NULL" || strSelectedFace == "ERROR")
{
if (bIsShowNoticeText)//如果显示提示文字
{
if (strNoSelectImage != "NULL" && !string.IsNullOrEmpty(strNoSelectImage))
{
writer.AddAttribute(HtmlTextWriterAttribute.Src, strNoSelectImage);
}
else
{
writer.AddStyleAttribute(HtmlTextWriterStyle.Display, "none");
writer.AddStyleAttribute(HtmlTextWriterStyle.Visibility, "hidden");
}
}
else
{
//取得服务器端头像存储的文件夹
string strServerFacePath = HttpContext.Current.Server.MapPath(FaceUrl);
if (!Directory.Exists(strServerFacePath))//如果文件夹不存在
{
writer.WriteLine(string.Format("<option value=\"ERROR\">头像系统出错</option>"));
return;
}
//获取所有头像
string[] faceImages = Directory.GetFiles(strServerFacePath);
//是否现实图片
bool bShowFace = false;
foreach (string faceImage in faceImages)
{
string[] parts = faceImage.Split('\\');
string faceImageName = parts[parts.Length - 1];
FileInfo faceImageInfo = new FileInfo(faceImage);
string strExtension = faceImageInfo.Extension.ToUpper();
if (strExtension == ".GIF" || strExtension == ".JPG" || strExtension == ".PNG" || strExtension == ".BMP")
{
writer.AddAttribute(HtmlTextWriterAttribute.Src, strFaceUrl + faceImageName);
bShowFace = true;//显示
break;
}
}
if (!bShowFace)
{
writer.AddStyleAttribute(HtmlTextWriterStyle.Display, "none");
writer.AddStyleAttribute(HtmlTextWriterStyle.Visibility, "hidden");
}
}
}
else
{
writer.AddAttribute(HtmlTextWriterAttribute.Src, strSelectedFace);
}
writer.RenderBeginTag(HtmlTextWriterTag.Img);
writer.RenderEndTag();
}
/// 产生图片显示控件
/// </summary>
/// <param name="writer"></param>
/// 作者:张伟
/// 日期:2006-10-20
private void RenderImageShow(HtmlTextWriter writer)
{
writer.AddAttribute(HtmlTextWriterAttribute.Name, this.ClientID + "_FaceImageShow");
writer.AddAttribute(HtmlTextWriterAttribute.Id, this.ClientID + "_FaceImageShow");
//如果没有选头像
if (string.IsNullOrEmpty(strSelectedFace) || strSelectedFace == "NULL" || strSelectedFace == "ERROR")
{
if (bIsShowNoticeText)//如果显示提示文字
{
if (strNoSelectImage != "NULL" && !string.IsNullOrEmpty(strNoSelectImage))
{
writer.AddAttribute(HtmlTextWriterAttribute.Src, strNoSelectImage);
}
else
{
writer.AddStyleAttribute(HtmlTextWriterStyle.Display, "none");
writer.AddStyleAttribute(HtmlTextWriterStyle.Visibility, "hidden");
}
}
else
{
//取得服务器端头像存储的文件夹
string strServerFacePath = HttpContext.Current.Server.MapPath(FaceUrl);
if (!Directory.Exists(strServerFacePath))//如果文件夹不存在
{
writer.WriteLine(string.Format("<option value=\"ERROR\">头像系统出错</option>"));
return;
}
//获取所有头像
string[] faceImages = Directory.GetFiles(strServerFacePath);
//是否现实图片
bool bShowFace = false;
foreach (string faceImage in faceImages)
{
string[] parts = faceImage.Split('\\');
string faceImageName = parts[parts.Length - 1];
FileInfo faceImageInfo = new FileInfo(faceImage);
string strExtension = faceImageInfo.Extension.ToUpper();
if (strExtension == ".GIF" || strExtension == ".JPG" || strExtension == ".PNG" || strExtension == ".BMP")
{
writer.AddAttribute(HtmlTextWriterAttribute.Src, strFaceUrl + faceImageName);
bShowFace = true;//显示
break;
}
}
if (!bShowFace)
{
writer.AddStyleAttribute(HtmlTextWriterStyle.Display, "none");
writer.AddStyleAttribute(HtmlTextWriterStyle.Visibility, "hidden");
}
}
}
else
{
writer.AddAttribute(HtmlTextWriterAttribute.Src, strSelectedFace);
}
writer.RenderBeginTag(HtmlTextWriterTag.Img);
writer.RenderEndTag();
}
各位应该看到了,注册在Selec中注册了一个JS事件,主要实现当选择的图片变化时显示预览图片的功能。相关代码如下:
private const string HEADER_SELECT_SCRIPT =
@"<script language='javascript'>
function ShowFace(ddlSelect, imgFaceShow)
{
var selectedValue = ddlSelect.options[ddlSelect.selectedIndex].value;
if(selectedValue == 'NULL' || selectedValue == '')
{
imgFaceShow.style.visibility='hidden';
imgFaceShow.style.display='none';
}
else if(selectedValue == 'ERROR')
{
ddlSelect.disabled='disabled';
}
else
{
imgFaceShow.src = ddlSelect.options[ddlSelect.selectedIndex].value;
imgFaceShow.style.visibility='visible';
imgFaceShow.style.display='block';
}
}
</script>";
private const string HEADER_SELECT_SCRIPT_ID = "a84f2d22-1cc6-473d-ae14-9cc3e7843e46";
private const string HEADER_SELECT_HOOK = "ShowFace({0}, {1});";
@"<script language='javascript'>
function ShowFace(ddlSelect, imgFaceShow)
{
var selectedValue = ddlSelect.options[ddlSelect.selectedIndex].value;
if(selectedValue == 'NULL' || selectedValue == '')
{
imgFaceShow.style.visibility='hidden';
imgFaceShow.style.display='none';
}
else if(selectedValue == 'ERROR')
{
ddlSelect.disabled='disabled';
}
else
{
imgFaceShow.src = ddlSelect.options[ddlSelect.selectedIndex].value;
imgFaceShow.style.visibility='visible';
imgFaceShow.style.display='block';
}
}
</script>";
private const string HEADER_SELECT_SCRIPT_ID = "a84f2d22-1cc6-473d-ae14-9cc3e7843e46";
private const string HEADER_SELECT_HOOK = "ShowFace({0}, {1});";
这样,在重写OnPreRender的时候就可以注册这段JS了。
protected override void OnPreRender(EventArgs e)
{
base.OnPreRender(e);
Page.RegisterRequiresPostBack(this);
Page.ClientScript.GetPostBackClientHyperlink(this, "");
if (!Page.ClientScript.IsClientScriptBlockRegistered(HEADER_SELECT_SCRIPT_ID))
{
Page.ClientScript.RegisterClientScriptBlock(Type.GetType("System.String"), HEADER_SELECT_SCRIPT_ID, HEADER_SELECT_SCRIPT);
}
}
{
base.OnPreRender(e);
Page.RegisterRequiresPostBack(this);
Page.ClientScript.GetPostBackClientHyperlink(this, "");
if (!Page.ClientScript.IsClientScriptBlockRegistered(HEADER_SELECT_SCRIPT_ID))
{
Page.ClientScript.RegisterClientScriptBlock(Type.GetType("System.String"), HEADER_SELECT_SCRIPT_ID, HEADER_SELECT_SCRIPT);
}
}
实现IPostBackDataHandler并保存选择状态,这里定义了一个属性来取得选择的值:
[Description("获取选中的头像"), Browsable(false)]
public string SelectedFace
{
get
{
if (string.IsNullOrEmpty(strSelectedFace) || strSelectedFace == "NULL" || strSelectedFace == "ERROR")
{
return strNoSelectImage;
}
else
{
return strSelectedFace;
}
}
set
{
strSelectedFace = value;
}
}
...............public string SelectedFace
{
get
{
if (string.IsNullOrEmpty(strSelectedFace) || strSelectedFace == "NULL" || strSelectedFace == "ERROR")
{
return strNoSelectImage;
}
else
{
return strSelectedFace;
}
}
set
{
strSelectedFace = value;
}
}
public bool LoadPostData(string postDataKey, NameValueCollection postCollection)
{
//获取选中的头像Url
string selectedFaceUrl = (string)postCollection[this.ClientID + "_FaceSelect"];
if (!string.IsNullOrEmpty(selectedFaceUrl) && selectedFaceUrl != "NULL")
{
SelectedFace = selectedFaceUrl;
return true;
}
return false;
}
{
//获取选中的头像Url
string selectedFaceUrl = (string)postCollection[this.ClientID + "_FaceSelect"];
if (!string.IsNullOrEmpty(selectedFaceUrl) && selectedFaceUrl != "NULL")
{
SelectedFace = selectedFaceUrl;
return true;
}
return false;
}
另外给控件添加了一个事件,就是当选择的头像变化的时候执行回发:
private static object FaceChangeEvent = new object();
public event EventHandler FaceChanged
{
add
{
Events.AddHandler(FaceChangeEvent, value);
}
remove
{
Events.RemoveHandler(FaceChangeEvent, value);
}
}
protected virtual void OnFaceChanged(EventArgs args)
{
EventHandler handler = (EventHandler)Events[FaceChangeEvent];
if (handler != null)
{
handler(this, args);
}
}
……
//IPostBackDataHandler的方法实现
public void RaisePostDataChangedEvent()
{
//注册事件
OnFaceChanged(EventArgs.Empty);
}
public event EventHandler FaceChanged
{
add
{
Events.AddHandler(FaceChangeEvent, value);
}
remove
{
Events.RemoveHandler(FaceChangeEvent, value);
}
}
protected virtual void OnFaceChanged(EventArgs args)
{
EventHandler handler = (EventHandler)Events[FaceChangeEvent];
if (handler != null)
{
handler(this, args);
}
}
……
//IPostBackDataHandler的方法实现
public void RaisePostDataChangedEvent()
{
//注册事件
OnFaceChanged(EventArgs.Empty);
}
到这里就基本上差不多了,另外加了一些是否出现头像选择提示文字之类的功能,具体请看源代码吧!
运行效果:
默认有提示选择头像的文字!
选定头像
提交
后记:
这里仅仅是通过文件系统来获取头像,如果能跟XML结合起来使用想必效果会更好。
废话不说了,上源代码:
TW.Web.UI.rar