Handlebars嵌套'each'语法 - 不迭代每个元素

问题描述 投票:15回答:2

我在这个Javascript / JSON / Handlebars事物上是全新的,我在使用两个嵌套级别获取JSON对象时无法在Handlebars模板中工作。

我已经用JSONLint验证了JSON对象,所以它是有效的JSON代码,但我不知道我是否有正确的JSON格式来使模板正常工作。 :)(我正在另一个系统中手动构建JSON。)或许它是我错误的模板的语法。这就是我希望找到的......

简短说明:此对象是目录。我有章节,然后是每章内的电影。因此,电影是每个章节元素的嵌套元素。

我希望HTML输出类似于:

Chapter1:  ChapterName
       Movie1: MovieName
       Movie2: MovieName
Chapter2:  Chaptername
       Movie1: MovieName
       Movie2: MovieName
       Movie3: MovieName

我似乎最终只得到了一个数据实例(我的JSON对象中的最后一个元素),或者我什么都没得到。 (取决于我尝试的小调整或版本。)浏览器控制台不显示任何错误。

这是我到目前为止尝试使用的所有代码(脚本,HTML,模板等):

<!DOCTYPE html>
<html>
<head>  <meta charset="UTF-8">
    <title>Handlebars Demo</title>
    <!-- dependant files -->
    <script src="Handlebars.js"></script>
</head>

<!-- template -->
<script id="template2" type="text/x-handlebars-template">
    <div>Chapter stuff:</div>
    <ul>{{#each Chapter}}
        <ol>{{@index}} {{ChapterName}}
        {{#each movies}}
            <li>Movie ID:{{movieIDnum}}</li>
        {{/each}}
        </ol>
        {{/each}}
    </ul>
</script>


<body><div id="main"></div></body>

<script>
    var source = document.getElementById('template2').innerHTML;
    var template = Handlebars.compile(source);
    var data = {
        "Chapter" : {
                "ChapterName" : "Introduction",
                "chapterNum" : "1",
                "movies" : [
                        {
                        "movieIDnum" : "16244028",
                        "movieName" : "Update Test Movie 0",
                        "movieFileName" : "Test0.mov",
                        "moviePositionInChapter" : "1"
                        }
                ]
        },

        "Chapter" : {
            "ChapterName" : "Welcome",
            "chapterNum" : "2",
            "movies" : [
                    {
                    "movieIDnum" : " 17322365",
                    "movieName" : "Update Test movie 1",
                    "movieFileName" : "Test1.mov",
                    "moviePositionInChapter" : "1"
                    },
                    {
                    "movieIDnum" : " 17326267",
                    "movieName" : "Update Test movie 3",
                    "movieFileName" : "Test3.mov",
                    "moviePositionInChapter" : "2"
                    }
            ]
        },

        "Chapter" : {
            "ChapterName" : "The new Interface",
            "chapterNum" : "2",
            "movies" : [
                {
                "movieIDnum" : " 1732123476",
                "movieName" : "Update Test movie 12",
                "movieFileName" : "Test12.mov",
                "moviePositionInChapter" : "1"
                },
                {
                "movieIDnum" : " 173262373",
                "movieName" : "Update Test movie 9",
                "movieFileName" : "Test9.mov",
                "moviePositionInChapter" : "2"
                },
                {
                "movieIDnum" : " 173273474",
                "movieName" : "Update Test movie 10",
                "movieFileName" : "Test10.mov",
                "moviePositionInChapter" : "3"
                }
            ]
        },

        "Chapter" : {
            "ChapterName" : "What is an Update?",
            "chapterNum" : "4",
            "movies" : [
                {
                "movieIDnum" : " 177342131",
                "chapterNum" : "4",
                "chapterName" : "What is an Update?",
                "movieName" : "Test movie again",
                "movieFileName" : "Test13.mov",
                "moviePositionInChapter" : "1"
                }
                ]
                },
        "Chapter" : {
            "ChapterName" : "Editing",
            "chapterNum" : "5",
            "movies" : [
                {
                "movieIDnum" : " 173290878",
                "movieName" : "Update Test movie 14",
                "movieFileName" : "Test14mov",
                "moviePositionInChapter" : "1"
                },
                {
                "movieIDnum" : " 177344914",
                "movieName" : " Movie 15 Test",
                "movieFileName" : "Test233.mov",
                "moviePositionInChapter" : "2"
                }
            ]
        }

    }

    var result = template(data);
    document.write(result);

</script>
</html>

我想知道为什么这不起作用,而不仅仅是“以下是如何使用完全不同的格式使用其他4种不同的东西解决问题”。我的理解是,这应该适用于我尝试使用的工具。我想更好地理解这些工具并从过程中学习,而不仅仅是获得解决方案。 (你知道,教一个人钓鱼......))

谢谢,J

json nested each handlebars.js
2个回答
29
投票

有几个变化建议,首先你不应该用几个键{ Chapter:, Chapter:, etc...}写一个对象

另一个建议是检查Handlebars的工作方式,在每种情况下都不需要。希望它澄清一下。

尝试以下更改:

<!DOCTYPE html>
<html>
<head>  <meta charset="UTF-8">
    <title>Handlebars Demo</title>
    <!-- dependant files -->
    <script src="handlebars.js"></script>
</head>

<!-- template -->
<script id="template2" type="text/x-handlebars-template">
    <div>Chapter stuff:</div>
    <ul>{{#Chapters}}
        <ol>{{@index}} {{ChapterName}}
        {{#movies}}
            <li>Movie ID:{{movieIDnum}}</li>
        {{/movies}}
        </ol>
        {{/Chapters}}
    </ul>
</script>


<body><div id="main"></div></body>

<script>
    var source = document.getElementById('template2').innerHTML;
    var template = Handlebars.compile(source);
    var data = [
        {
                "ChapterName" : "Introduction",
                "chapterNum" : "1",
                "movies" : [
                        {
                        "movieIDnum" : "16244028",
                        "movieName" : "Update Test Movie 0",
                        "movieFileName" : "Test0.mov",
                        "moviePositionInChapter" : "1"
                        }
                ]
        },
        {
            "ChapterName" : "Welcome",
            "chapterNum" : "2",
            "movies" : [
                    {
                    "movieIDnum" : " 17322365",
                    "movieName" : "Update Test movie 1",
                    "movieFileName" : "Test1.mov",
                    "moviePositionInChapter" : "1"
                    },
                    {
                    "movieIDnum" : " 17326267",
                    "movieName" : "Update Test movie 3",
                    "movieFileName" : "Test3.mov",
                    "moviePositionInChapter" : "2"
                    }
            ]
        },
        {
            "ChapterName" : "The new Interface",
            "chapterNum" : "2",
            "movies" : [
                {
                "movieIDnum" : " 1732123476",
                "movieName" : "Update Test movie 12",
                "movieFileName" : "Test12.mov",
                "moviePositionInChapter" : "1"
                },
                {
                "movieIDnum" : " 173262373",
                "movieName" : "Update Test movie 9",
                "movieFileName" : "Test9.mov",
                "moviePositionInChapter" : "2"
                },
                {
                "movieIDnum" : " 173273474",
                "movieName" : "Update Test movie 10",
                "movieFileName" : "Test10.mov",
                "moviePositionInChapter" : "3"
                }
            ]
        },
        {
            "ChapterName" : "What is an Update?",
            "chapterNum" : "4",
            "movies" : [
                {
                "movieIDnum" : " 177342131",
                "chapterNum" : "4",
                "chapterName" : "What is an Update?",
                "movieName" : "Test movie again",
                "movieFileName" : "Test13.mov",
                "moviePositionInChapter" : "1"
                }
                ]
        },
        {
            "ChapterName" : "Editing",
            "chapterNum" : "5",
            "movies" : [
                {
                "movieIDnum" : " 173290878",
                "movieName" : "Update Test movie 14",
                "movieFileName" : "Test14mov",
                "moviePositionInChapter" : "1"
                },
                {
                "movieIDnum" : " 177344914",
                "movieName" : " Movie 15 Test",
                "movieFileName" : "Test233.mov",
                "moviePositionInChapter" : "2"
                }
            ]
        }
    ];

    var result = template({Chapters: data});
    document.write(result);

</script>
</html>

11
投票

pdjota是对的。这个答案只是为了展示如何使用每个块助手。

就像明智地指出的pdjota一样,你要覆盖对象的元素,因为它们都具有相同的键,即“章节”。因此,将data转换为对象数组,而不是具有相同键的对象对象。

如果你这样做,你仍然可以将data传递给template()。您缺少的是如何引用每个块中使用的对象的属性。这是用this完成的。例如,如果您在电影迭代器中,则电影对象的属性如下所示:this.movieIDnumthis.movieName等。

<!DOCTYPE html>
<html>
<head>  
    <meta charset="UTF-8">
    <title>Handlebars Demo</title>
    <!-- dependant files -->
    <script src="Handlebars.js"></script>
</head>

<!-- template -->
<script id="template2" type="text/x-handlebars-template">
    <div>Chapter stuff:</div>
    <ul>
        {{#each this}}
            <ol>Chapter{{this.chapterNum}}: {{this.ChapterName}}
                {{#each movies}}
                    <li>Movie{{this.moviePositionInChapter}}: {{this.movieName}}</li>
                {{/each}}
            </ol>
        {{/each}}
    </ul>
</script>


<body><div id="main"></div></body>

<script>
    var source = document.getElementById('template2').innerHTML;
    var template = Handlebars.compile(source);
    var data = [
        {
                "ChapterName" : "Introduction",
                "chapterNum" : "1",
                "movies" : [
                        {
                        "movieIDnum" : "16244028",
                        "movieName" : "Update Test Movie 0",
                        "movieFileName" : "Test0.mov",
                        "moviePositionInChapter" : "1"
                        }
                ]
        },
        {
            "ChapterName" : "Welcome",
            "chapterNum" : "2",
            "movies" : [
                    {
                    "movieIDnum" : " 17322365",
                    "movieName" : "Update Test movie 1",
                    "movieFileName" : "Test1.mov",
                    "moviePositionInChapter" : "1"
                    },
                    {
                    "movieIDnum" : " 17326267",
                    "movieName" : "Update Test movie 3",
                    "movieFileName" : "Test3.mov",
                    "moviePositionInChapter" : "2"
                    }
            ]
        },
        {
            "ChapterName" : "The new Interface",
            "chapterNum" : "2",
            "movies" : [
                {
                "movieIDnum" : " 1732123476",
                "movieName" : "Update Test movie 12",
                "movieFileName" : "Test12.mov",
                "moviePositionInChapter" : "1"
                },
                {
                "movieIDnum" : " 173262373",
                "movieName" : "Update Test movie 9",
                "movieFileName" : "Test9.mov",
                "moviePositionInChapter" : "2"
                },
                {
                "movieIDnum" : " 173273474",
                "movieName" : "Update Test movie 10",
                "movieFileName" : "Test10.mov",
                "moviePositionInChapter" : "3"
                }
            ]
        },
        {
            "ChapterName" : "What is an Update?",
            "chapterNum" : "4",
            "movies" : [
                {
                "movieIDnum" : " 177342131",
                "chapterNum" : "4",
                "chapterName" : "What is an Update?",
                "movieName" : "Test movie again",
                "movieFileName" : "Test13.mov",
                "moviePositionInChapter" : "1"
                }
                ]
        },
        {
            "ChapterName" : "Editing",
            "chapterNum" : "5",
            "movies" : [
                {
                "movieIDnum" : " 173290878",
                "movieName" : "Update Test movie 14",
                "movieFileName" : "Test14mov",
                "moviePositionInChapter" : "1"
                },
                {
                "movieIDnum" : " 177344914",
                "movieName" : " Movie 15 Test",
                "movieFileName" : "Test233.mov",
                "moviePositionInChapter" : "2"
                }
            ]
        }
    ];

    var result = template(data);
    document.write(result);

</script>
</html>
© www.soinside.com 2019 - 2024. All rights reserved.