0

So i've been messing around and searching and it triggers when i don't generated the code via my JS and put the output as html on the file. The menu is supposed to be dynamic and generate subs on it and subs have products and so on i was doing it and logically is correct but can't know if JS is confliting some part of this code.

JS Generate Menus:

$(function(){
var ul = $('#category-content');
var subcategoryLi = $('#sublist');
var productsLi = $('#productList');


init();

function init(){
    GetCategorys();
}

function BuildSubCategorys(id,sub){
    var content = '';
    if (typeof(sub) != 'undefined' && sub.length > 0){
        for(var i = 0; i < sub.length; i++){
            if (sub[i].c_parentcat == id){
                content += AddSubItem(sub[i].c_name,sub[i].c_id);
            }
        }
        return content;
    }
    else{
        return '';
    }
}

function hasSubs(j,d){
    for(var i=0;i<d.length;i++){
        if(d[i].c_parentcat == j ){
            return true;
        }
    }
}

function BuildCategorys(root){
    var content = AddCategoryHeader('Categorias');
    var subs = [];
    if (typeof(root) != 'undefined' && root.length > 0){
        for(var i = 0; i < root.length; i++){
            if (root[i].c_parentcat == -1){
                content += AddCategory(root[i].c_name,root[i].c_id);
                if (hasSubs(root[i].c_id, root) == true){
                    var subContent = BuildSubCategorys(root[i].c_id, root);
                    subs[root[i].c_id] = CreateSubList(subContent);
                }
            }
        }
        ul.append(content);
        ul.append(AddSeparator());
        for(var j = 0; j < root.length; j++){
            curr_id = root[j].c_id;
            ul.find('#category'+curr_id).append(subs[curr_id]);

        }
    }
    else {
        ul.append(AddCategoryHeader('Categorias'));
        ul.append(HandleNoSubData());
        ul.append(AddSeparator());
    }

    //Build the products
    GetCategoryProducts();
}


function BuildProducts(p){

        var content = AddCategoryHeader('Produtos sem categoria');
        var category_items = [];
        if (typeof(p) != 'undefined' && p.length > 0){
            for(var i=0; i < p.length; i++){
                if (p[i].p_categoryid == -1){
                    //he has no category so lets add it to the non category section
                    content += AddProduct(p[i].p_name,p[i].p_id);
                }
                else {
                    subcategoryLi.find('#subcategory'+ p[i].p_categoryid).append(AddProduct(p[i].p_name,p[i].p_id));
                }
            }

            ul.append(content);
            //LEFT: LINK ON THE PRODUCT WITH THEIR ID ON CREATE FUNCTION

        }else{
            ul.append(AddCategoryHeader('Produtos sem categoria'))
            ul.append(HandleNoProdData());
        }
}


    function AddSeparator(){
            return '<li role="separator" class="divider"></li>';
    }

    function AddCategoryHeader(name){
        return '<li class="dropdown-header">' + name +'</li>';
    }

    function AddCategory(name,id){
            return '<li class="dropdown-submenu" id="category'+id+'"><a id="menu-itex" tabindex="-1" href="javascript:;">' + name + ' <span class="caret"></span></a></li>';
    }

    function AddProduct(name,id){
        return '<li><a href="javascript:;" id="product'+ id +'">' + name + '</a></li>';
    }

    function AddSubItem(name,id){
            return '<li><a href="javascript:;" id="subcategory'+id+'"> '+ name + ' </a></li>';
    }

    function CreateSubList(c){
            return '<ul id="sublist" class="dropdown-menu">'+ c +'</ul>';
    }

    function CreateProductsList(){
        return '<li class="dropdown"><ul id="productList" class="dropdown-menu">'+ c +'</ul></li>';
    }

    function HandleNoData(){
        return '<li><a href="javascript:;"> Não existem categorias </a></li>';
    }
    function HandleNoSubData(){
        return '<li><a href="javascript:;"> Não existem sub-categorias </a></li>';
    }

    function HandleNoProdData(){
            return '<li><a href="javascript:;"> Não existem produtos </a></li>';
    }

    function GetCategorys(){
            var url = base_url + 'home/ajaxCategorys';
            $.post(url,function(js){
                if (js != null && js != 'false')
                    BuildCategorys(JSON.parse(js));
                else
                    return false;
            });
    }

    function GetCategoryProducts(){
        var url = base_url + 'home/ajaxCategoryProducts';
        $.post(url,function(js){
            if (js != null && js != 'false')
                BuildProducts(JSON.parse(js));
            else
                return false;
        });
    }

    $(document).ready(function(){
        $('#menu-itex').on("click" ,function(e){
            console.log('Click for menu');
            $(this).next('ul').toggle();
            e.stopPropagation();
            e.preventDefault();

        });
    });
});

The output of my code directly as html it works but if i do in this way with JS script on generating it it doesn't trigger on menu-itex id click and i also tried by using the class. Got the trigger idea from w3wschools boostrap advanced menus.

2
  • 1
    If you are using a select, use onchange event for it. Commented Dec 18, 2017 at 16:14
  • Doesn't work too Commented Dec 18, 2017 at 16:16

1 Answer 1

1

When you add a event listener to a generated element before the item is generated (happens sometimes), it'll not trigger the event on click.

The best solution is to append the click event to body (or the item container that is rendered on page load) and listen to click only if it's inside the desired element.

It goes something like this:

//$('body').on('click', <-- would work too, but it's not delimited to a certain section of your page.
$('#category-content').on('click', '#menu-itex', function(){
     //Your stuff here
})
Sign up to request clarification or add additional context in comments.

2 Comments

Thanks it worked, the thing is that js is quite tricky sometimes and debugging it's quite hard, maybe if i found some debug library to detect bad events bind's would be great.
You don't need a library to debug this. You can use chrome devtools (click an element, and on the right panel, select Event Listeners. Or you can use this javascript snippet: Visual Event 2

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.