【问题标题】:Iterate through deeply nested object to generate html optgroup/options遍历深度嵌套的对象以生成 html optgroup/options
【发布时间】:2021-02-06 01:27:42
【问题描述】:

我正在尝试获取我的对象的键并创建一个 optgroup(如果它包含子项),然后创建 optgroup 的子项选项。如果一个孩子也是一个对象,那么我想在父 optgroup 中嵌套另一个 optgroup。下面是我的对象 myTypes

let myTypes = {
    women: 
    {
        tops:
        {
            poloshirts:"polo shirts",
            tshirts: "t-shirts",
            buttondown: "button down",
            longsleeve:"long sleeve",
            vneck:"vneck",
            tanktop:"tanktop",
            blouse:"blouse",
            croptop:"croptop",
            drifit: "dri-fit",
            dressshirt:"dress shirt"
        },
        bottoms:
        {
            shorts:"shorts",
            jeans:"jeans",
            joggers:"joggers",
            skirts:"skirts",
            dresspants:"dresspants",
            leggings:"leggings"
        },
        shoes:
        {
            boots:"boots",
            sneakers: "sneakers",
            sandals:"sandals",
            flats:"flats",
            heels:"heels"
        },
        jewelry:
        {
            rings: "rings",
            bracelets:"bracelets",
            necklaces: "necklaces",
            anklets: "anklets"
        },
        sweaters: "sweaters",
        sweatshirts: "sweatshirts",
        hoodies: "hoodies",
        dresses:
        {
            sundress: "sundress",
            short: "short",
            long: "long",
            maxidress: "maxidress"
        },
        accessories:
        {
            watches:"watches",
            glasses:
            {
                sunglasses: "sunglasses",
                reading:"reading"
            },
            wallets: "wallets",
            keychains: "keychains",
            lanyards:"lanyards",
            belts:"belts",
            purses:"purses"
        }
    },
    
men: 
    {
        tops:
        {
            poloshirts:"polo shirts",
            tshirts: "t-shirts",
            buttondown: "button down",
            longsleeve:"long sleeve",
            vneck:"vneck",
            tanktop:"tanktop",
            drifit: "dri-fit",
            dressshirt: "dress shirt"
        },
        bottoms:
        {
            shorts:"shorts",
            jeans:"jeans",
            joggers:"joggers",
            dresspants:"dress pants",
            leggings:"leggings"
        },
        shoes:
        {
            boots:"boots",
            sneakers: "sneakers",
            sandals:"sandals",
            flats:"flats"
        },
        jewelry:
        {
            rings: "rings",
            bracelets:"bracelets",
            necklaces: "necklaces",
            anklets: "anklets"
        },
        sweaters: "sweaters",
        sweatshirts: "sweatshirts",
        hoodies: "hoodies",
        accessories:
        {
            watches:"watches",
            glasses:
            {
                sunglasses: "sunglasses",
                reading:"reading"
            },
            wallets: "wallets",
            keychains: "keychains",
            lanyards:"lanyards",
            belts:"belts"
        }
    },
kids: 
    {
    girl: 
        {
            tops:
            {
                poloshirts:"polo shirts",
                tshirts: "t-shirts",
                buttondown: "button down",
                longsleeve:"long sleeve",
                vneck:"vneck",
                tanktop:"tanktop",
                blouse:"blouse",
                croptop:"croptop",
                drifit: "dri-fit",
                dressshirt:"dress shirt"
            },
            bottoms:
            {
                shorts:"shorts",
                jeans:"jeans",
                joggers:"joggers",
                skirts:"skirts",
                dresspants:"dresspants",
                leggings:"leggings"
            },
            shoes:
            {
                boots:"boots",
                sneakers: "sneakers",
                sandals:"sandals",
                flats:"flats",
                heels:"heels"
            },
            jewelry:
            {
                rings: "rings",
                bracelets:"bracelets",
                necklaces: "necklaces",
                anklets: "anklets"
            },
            sweaters: "sweaters",
            sweatshirts: "sweatshirts",
            hoodies: "hoodies",
            dresses:
            {
                sundress: "sundress",
                short: "short",
                long: "long",
                maxidress: "maxidress"
            },
            accessories:
            {
                watches:"watches",
                glasses:
                {
                    sunglasses: "sunglasses",
                    reading:"reading"
                },
                wallets: "wallets",
                keychains: "keychains",
                lanyards:"lanyards",
                belts:"belts",
                purses:"purses"
            }
        },
    boy: 
        {
            tops:
            {
                poloshirts:"polo shirts",
                tshirts: "t-shirts",
                buttondown: "button down",
                longsleeve:"long sleeve",
                vneck:"vneck",
                tanktop:"tanktop",
                drifit: "dri-fit",
                dressshirt: "dress shirt"
            },
            bottoms:
            {
                shorts:"shorts",
                jeans:"jeans",
                joggers:"joggers",
                dresspants:"dress pants",
                leggings:"leggings"
            },
            shoes:
            {
                boots:"boots",
                sneakers: "sneakers",
                sandals:"sandals",
                flats:"flats"
            },
            jewelry:
            {
                rings: "rings",
                bracelets:"bracelets",
                necklaces: "necklaces",
                anklets: "anklets"
            },
            sweaters: "sweaters",
            sweatshirts: "sweatshirts",
            hoodies: "hoodies",
            accessories:
            {
                watches:"watches",
                glasses:
                {
                    sunglasses: "sunglasses",
                    reading:"reading"
                },
                wallets: "wallets",
                keychains: "keychains",
                lanyards:"lanyards",
                belts:"belts"
            }
        }
    }
}

我尝试遍历此内容,然后使用适当的选项生成 html 选择,但我无法弄清楚。我得到的最远的是这个

    let selectionHTML = "";
    let paths = (arr)=>{
        for(let i in arr){
            if(typeof arr[i] == "object" && arr[i] !== null){
                selectionHTML += "<optgroup label = '" + i + "'></optgroup>";
                paths(arr[i]);
            }
        }
    }
    paths(myTypes);

我不知道如何生成我的代码。

【问题讨论】:

    标签: javascript html recursion nested javascript-objects


    【解决方案1】:

    你需要知道使用optgroup元素嵌套在一起的方法是行不通的,因为只会显示optgroup的第一层:https://developer.mozilla.org/en-US/docs/Web/HTML/Element/optgroup

    尝试使用类似的东西:

    const path = (source = {}) => {
      // Let the initial string be empty
      let returnedString = '';
    
      // Convert the object into an array using key/value pair and then iterate through it
      Object.entries(source)
        .forEach(([key, value]) => {
          if (typeof value === 'object' && value !== null) {
            // value is an object, iterate through it
            returnedString += `<optgroup label="${key}">${path(value)}</optgroup>`;
          } else {
            // value should be a string
            returnedString += `<option value="${key}">${value}</option>`;
          }
        });
    
      // Return the string
      return returnedString;
    }
    
    

    另外,在操作 DOM 时,建议使用内置方法来操作元素而不是字符串:

    // Create the "root" element
    // const root = document.createElement('select');
    
    const path = (source = {}, rootElement = undefined) => {
      // Define the root element if not an instance of Element
      const root= rootElement instanceof Element ? rootElement : document.createElement('select');
    
      // Convert the object into an array using key/value pair and then iterate through it
      Object.entries(source)
        .forEach(([key, value]) => {
          if (typeof value === 'object' && value !== null) { // value is an object, iterate through it
            // Create an optgroup element
            const optgroup = document.createElement('optgroup');
    
            // Defines the attributes
            optgroup.setAttribute('label', key);
    
            // Add "content" inside the optgroup
            path(value, optgroup);
    
            // Append the newly created optgroup element to the root
            root.appendChild(optgroup);
          } else { // value should be a string
            // Create an option element
            const option = document.createElement('option');
    
            // Defines the attributes
            option.setAttribute('value', key);
            option.text = value;
    
            // Append the newly created option element to the root
            root.appendChild(option);
          }
        });
    
      // Return the root element
      return root;
    }
    

    编辑 1:在答案中添加了 DOM 方式

    编辑 2:添加了 optgroup 嵌套警告

    【讨论】:

      【解决方案2】:

      function getMyTypes(obj_myTypes) {
      
          var targetHTML = $("");
          
          for (const key in obj_myTypes) {
              if (obj_myTypes.hasOwnProperty(key)) {
                  var element = obj_myTypes[key];
                  console.log(key)
                  targetHTML.prepend(`<optgroup id="one" label="${key}"> ${key} </optgroup>`);
                  //each in obj
                  //console.log(element)
                  stepTwo(element)
              }
          }
      }
      getMyTypes(myTypes);
      
      function stepOne() {
          var step_one = $('optgroup').filter('[id="one"]');
              step_one.each((index) => {
                 // var result = $(this).text()
                  step_one.prepend(`<optgroup id="two" label=""> two </optgroup>`)
              });
      }
      stepOne()
      
      function stepTwo(obj_elem) {
      
          var step_two = $('optgroup').filter('[id="two"]');
          
          for (const key in obj_elem) {
              if (obj_elem.hasOwnProperty(key)) {
                  var item_of_element = obj_elem[key];
                  console.log('KEY: '+key)
      
                  step_two.each((index,html_element) => {
                      $(html_element).attr("label", value)
                      console.log(value)
                      //return value
                  });
              }
          }
      }

      【讨论】:

      • 我相信你必须通过对象三遍。在每个循环的响应中,必须将其添加到 html 中。
      猜你喜欢
      • 1970-01-01
      • 2015-11-17
      • 1970-01-01
      • 2021-11-05
      • 1970-01-01
      • 2015-11-24
      • 2011-04-10
      • 1970-01-01
      • 2018-05-13
      相关资源
      最近更新 更多