Thursday, January 22, 2009

Custom AutoComplete 5: Build an additional row on the top of AutoComplete List

Before anything, please check this(http://www.globrix.com/):



We know we can customize AutoComplete. In this image, we can achieve the red background, Font style and seting some shining picture as the background. But one thing we need to notice is that there is an arrowhead on the top of row. So we have to make an additional row for it. And this row is not an item in the list; mouse event should be unavailable here.

Let code speak anything:

In this sample, you can define autocomplete_firstRow css style. In this case, you can define a background image in firstrow.


.autocomplete_firstrow
{
background-color:Red;
height:20px;


}



After you create an AutoComplete on the page, the below JavaScript will be worked of it. It will create an addition row on the top of AutoComplete. Suppose that the behaviorID of AutoComplete is "AutoCompleteEx".

<script type="text/javascript">


        function ClientPopulated() {
            var comletionList = $find("AutoCompleteEx").get_completionList();
           



            var firstrow=document.createElement("div");
            firstrow.id="firstrow";
            firstrow.className = "autocomplete_firstrow";

            comletionList.insertBefore(firstrow, comletionList.firstChild);
  



        }

       

        function pageLoad() {
            var autoc = $find("AutoCompleteEx");
//redefine highlightitem function
            autoc._highlightItem = function(item) {

                var children = autoc._completionListElement.childNodes;
                if (item === children[0])
                    return;

                for (var i = 0; i < children.length; i++) {
                    var child = children[i];
                    if (child._highlighted) {
                        if (autoc._completionListItemCssClass) {
                            Sys.UI.DomElement.removeCssClass(child, autoc._highlightedItemCssClass);
                            Sys.UI.DomElement.addCssClass(child, autoc._completionListItemCssClass);
                        } else {
                            if (Sys.Browser.agent === Sys.Browser.Safari) {
                                child.style.backgroundColor = 'white';
                                child.style.color = 'black';
                            } else {
                                child.style.backgroundColor = autoc._textBackground;
                                child.style.color = autoc._textColor;
                            }
                        }
                        autoc.raiseItemOut(new AjaxControlToolkit.AutoCompleteItemEventArgs(child, child.firstChild.nodeValue, child._value));
                    }
                }

                // Highlight the new item
                if (this._highlightedItemCssClass) {
                    Sys.UI.DomElement.removeCssClass(item, this._completionListItemCssClass);
                    Sys.UI.DomElement.addCssClass(item, this._highlightedItemCssClass);
                } else {
                    if (Sys.Browser.agent === Sys.Browser.Safari) {
                        item.style.backgroundColor = 'lemonchiffon';
                    } else {
                        item.style.backgroundColor = 'highlight';
                        item.style.color = 'highlighttext';
                    }

                }
                item._highlighted = true;

                this.raiseItemOver(new AjaxControlToolkit.AutoCompleteItemEventArgs(item, item.firstChild.nodeValue, item._value));


            };

//redefine settext function
            autoc._setText = function(item) {
            var children = autoc._completionListElement.childNodes;
                if (item === children[0])
                    return;
                var text = (item && item.firstChild) ? item.firstChild.nodeValue : null;

                autoc._timer.set_enabled(false);

                var element = autoc.get_element();
                var control = element.control;
                if (control && control.set_text) {
                    control.set_text(text);
                    $common.tryFireEvent(control, "change");
                }
                else {
                    element.value = text;
                    $common.tryFireEvent(element, "change");
                }
                autoc.raiseItemSelected(new AjaxControlToolkit.AutoCompleteItemEventArgs(item, text, item ? item._value : null));

                autoc._currentPrefix = autoc._currentCompletionWord();
                autoc._hideCompletionList();
            };

      }
       


    </script>

Custom AutoComplete 6: MultiColumn Autocomplete(Mutiple columns message for each Item)

Hello all, I made "Mutiple rows message for each Item" several months ago. Now I'd like to build a MultiColumn Autocomplete. They applies same principle, so it's not a trouble if you checked previous post.

Here is the code in aspx:

<head runat="server">
    <title></title>
    <link href="../Default.css" rel="stylesheet" type="text/css" />
    <style>
    .cloumnspan
    {
        width:35px;
        padding:0px;
        border-color:Black;
        border-style:solid;
        border-width:1px;

    }
   
    </style>
</head>
<body>
    <form id="form1"  runat="server">
        <ajaxToolkit:ToolkitScriptManager runat="server" ID="ScriptManager1" />

           <asp:TextBox runat="server" ID="myTextBox" Width="300" autocomplete="off" />
            <ajaxToolkit:AutoCompleteExtender
                runat="server"  OnClientPopulated="dd" OnClientItemSelected="itemSelected"
                BehaviorID="AutoCompleteEx"
                ID="autoComplete1"
                TargetControlID="myTextBox"
                ServicePath="AutoComplete.asmx"
                ServiceMethod="GetCompletionList5"
                MinimumPrefixLength="2"
                CompletionInterval="1000"
                EnableCaching="true"
                CompletionSetCount="8"
                CompletionListCssClass="autocomplete_completionListElement"
                CompletionListItemCssClass="autocomplete_listItem"
                CompletionListHighlightedItemCssClass="autocomplete_highlightedListItem"
                DelimiterCharacters=";, :">
            </ajaxToolkit:AutoCompleteExtender>

    </form>
    <script type="text/javascript">
function itemSelected(ev)
{
    var index=$find("AutoCompleteEx")._selectIndex;
    var value=$find("AutoCompleteEx").get_completionList().childNodes[index]._value;
    $find("AutoCompleteEx").get_element().value = value;
}
function dd()
{
    var comletionList=$find("AutoCompleteEx").get_completionList();
    for(i=0;i<comletionList.childNodes.length;i++) {
        var itemobj=new Object();
        var _data = comletionList.childNodes[i]._value;
        itemobj.name= _data.substring(_data.lastIndexOf('|') + 1); // parse name as item value
        comletionList.childNodes[i]._value = itemobj.name;
        _data = _data.substring(0, _data.lastIndexOf('|'));
        itemobj.age = _data.substring(_data.lastIndexOf('|') + 1);
        _data = _data.substring(0, _data.lastIndexOf('|'));
        itemobj.id = _data.substring(_data.lastIndexOf('|') + 1);


        comletionList.childNodes[i].innerHTML = "<div class='cloumnspan' style='width:10%;float:left'>" + itemobj.id + "</div>"
                                              + "<div class='cloumnspan' style='width:70%;float:left'>" + itemobj.name + "</div>"
                                              + "<div class='cloumnspan' style='width:18%;'>" + itemobj.age + "</div>";

    }
   
}



</script>
</body>



Web Method:

[WebMethod]
public string[] GetCompletionList5(string prefixText, int count)
{

    if (count == 0)
    {
        count = 10;
    }

    if (prefixText.Equals("xyz"))
    {
        return new string[0];
    }

    Random random = new Random();
    List<string> items = new List<string>(count);

    for (int i = 0; i < count; i++)
    {

        char c1 = (char)random.Next(65, 90);
        char c2 = (char)random.Next(97, 122);
        char c3 = (char)random.Next(97, 122);
        int id = i;
        int age = random.Next(18, 70);
        items.Add(id.ToString() + "|" + age.ToString() + "|" + prefixText + c1 + c2 + c3);
    }

    return items.ToArray();
}


If you want to add a header for MutiColumn table, you should add an additional row/div at the top of complete list. Please check this: http://vincexu.blogspot.com/2009/01/custom-autocomplete-5-build-additional.html

Wednesday, January 21, 2009

Create a Vertical Tab

In this post, if you are familiar with Css Style and JavaScript, it should not be a difficult thing for you.

This time let's hit to create a Vertical Tab like the tab control in http://www.microsoft.com/. Have you seen the bottom tab content navigation in Microsoft home page http://www.microsoft.com/?

If you used TabContainer before, you must have thought it is really a vertical TabContainer. Now, we get to start from Zero, to create one by css and JavaScript.



See the line in the left section of image, it seems to be faded out and it's like a tail to the end. To achieve this, we have to prepare several images for it. The rest things are simple. (Just create some div in related sections)

Check the below code:

HTML:

<head runat="server">
    <title></title>
    <link href="AutoReport.css" rel="stylesheet" type="text/css" />

    <script src="AutoReport.js" type="text/javascript"></script>

</head>
<body>
    <form id="form1" runat="server">
    <div id="divAdmin">
        <div id="divAdmin_Content">
            <div id="divAdmin_LeftMenu">
                <div id="li-toptail">
                </div>
                <div id="liManager_User" onmouseover="HighLight_Li('liManager_User','liAdd_User','divManager_User','divAdd_User');">
                    Member</div>
                <div id="liAdd_User" onmouseover="HighLight_Li('liAdd_User','liManager_User','divAdd_User','divManager_User');">
                    Add User</div>
                <div class="li">
                </div>
                <div class="li">
                </div>
                <div class="li">
                </div>
                <div class="li">
                </div>
                <div class="li">
                </div>
                <div id="li-bottomtail">
                </div>
            </div>
            <div id="divAdmin_RightView">
                <div id="divManager_User">this is panel1
                </div>
                <div id="divAdd_User">this is panel2
                </div>
            </div>
        </div>
    </div>
    </form>
</body>


AutoReport.css

body
{
    /*font-family: "Trebuchet MS", Verdana, Tahoma, sans-serif;*/
    font-family:Tahoma,Verdana,Segoe,sans-serif;
    font-size: 12px;
    text-align: center;

    color: #666;

}
/*Admin*/
#divAdmin
{
    width: 550px;
}

#divAdmin_Header
{
    padding: 5px;
    background: url(Images/sprite.png) repeat-x 0px 0px;
    height: 22px;
    border: thin solid #D6D6C0;
    text-align: right;
    color: #666666;
}

#divAdmin_Content
{

}

#divAdmin_LeftMenu
{
    float:left;
    height: 350px;
    width: 86px;
    background-image: url('Images/leftmenu.png');
   
    border-left-width: thin;
    border-left-style: solid;
    border-left-color: #CFCFCF;
    border-bottom-style: solid;
    border-bottom-width: thin;
    border-bottom-color: #CFCFCF;
}

#divAdmin_RightView
{
    float: left;
    background-color: #EEEEEE;
    width: 460px;
    height: 350px;
    border-right-width: thin;
    border-right-style: solid;
    border-right-color: #CFCFCF;
    border-bottom-style: solid;
    border-bottom-width: thin;
    border-bottom-color: #CFCFCF;
}
.li
{
    height: 30px;
    width: 86px;
    background-image: url('Images/leftmenu-line.png') ;
}
#li-toptail
{
    background-image: url('Images/leftmenu-toptail.png') ;
    height: 30px;
    list-style-type:none;
    width: 86px;
   
}
#li-bottomtail
{
    background-image: url('Images/leftmenu-bottomtail.png') ;
    height: 30px;
    list-style-type:none;
    width: 86px;
   
}
#divManager_User
{
    padding-left:80px;
    display:block;
    text-align:left;
    padding-top: 5px;
}
#divAdd_User
{
    padding-left:80px;
    display:none;
    text-align:left;
    padding-top: 5px;
           
}
#liManager_User
{
    background-image: url('Images/leftmenu-litail.png') ;
    height: 30px;
    list-style-type:none;
    width: 86px;
}
#liAdd_User
{
    background-image: url(Images/leftmenu-line.png) ;
    height: 30px;
    list-style-type:none;
    width: 86px;
}


AutoReport.js

/*leftmenu onmouseover*/
function HighLight_Li(HighLight_Li,LowLight_Li,Display_div,Hidden_div)
{
    document.getElementById(HighLight_Li).style.backgroundImage='url(Images/leftmenu-litail.png)';
    document.getElementById(LowLight_Li).style.backgroundImage='url(Images/leftmenu-line.png)';
    document.getElementById(Display_div).style.display='block';
    document.getElementById(Hidden_div).style.display='none';
}




Several images need to download, and please put them in Image folder:
leftmenu-toptail.png


leftmenu-litail.png



leftmenu-line.png


leftmenu-bottomtail.png




leftmenu.png



sprite.png