未捕获的TypeError:无法读取未定义的属性'getAttribute'

时间:2018-09-29 23:14:04

标签: javascript dom uncaught-typeerror getattribute

首先,我查看了其他具有相同错误的帖子,而他们对我的 specific 问题没有答案,即为什么 me < / em> ???

该代码应实例化用于记忆游戏的一堆纸牌。当您单击卡片时,它们应该通过从一张图像变为另一张图像来“翻转”。我可以使用'createBoard();'实例化卡片但是除此之外,什么都没有发生,除了在控制台中显示“ Uncaught TypeError:无法读取未定义的属性'getAttribute'”。我该如何解决?我已经检查了这么长时间,我完全被困住了。

// stores cards available for memory game
let cards = [
{
    rank: 'queen',
    suit: 'hearts',
    cardImage: 'images/queen-of-hearts.png'
},
{
    rank: 'queen',
    suit: 'diamonds',
    cardImage: 'images/queen-of-diamonds.png'
},
{
    rank: 'king',
    suit: 'hearts',
    cardImage: 'images/king-of-hearts.png'
},
{
    rank: 'king',
    suit: 'diamonds',
    cardImage: 'images/king-of-diamonds.png'
}
];
// stores flipped cards
let cardsInPlay = [];

/*
if two cards have been flipped
checks for match, alerts to success/failure
*/
let checkForMatch = () => {
    if (cardsInPlay.length === 2) {
        alert((cardsInPlay[0] === cardsInPlay[1]) ? 
            'You found a match!' : 
            'Sorry, try again.');
    }
}

/*
retrieves the card id from the element that was clicked
adds the card to cardsInPlay
changes the imagesrc of the element
calls checkForMatch()
*/
let flipCard = () => {
    let cardId = document.this.getAttribute('data-id');
    cardsInPlay.push(cards[cardId].rank);
    document.this.setAttribute('src', cards[cardId].cardImage);
    checkForMatch();
}

/*
appends 4 imgs with sequential IDs
to the div with id='game-board'
each img listens for click, which calls flipCard()
*/
let createBoard = () => {
    for (let i = 0; i < cards.length; i++) {
        var cardElement = document.createElement('img');
        cardElement.setAttribute('src', 'images/back.png');
        cardElement.setAttribute('data-id', i);
        cardElement.addEventListener('click', flipCard);
        document.getElementById('game-board').appendChild(cardElement);
    }
}

// instantiate gameboard
createBoard();

以下是随附的HTML:

<!DOCTYPE html>
<html>
<head>
    <title>Memory Card Game</title>
    <link href="https://fonts.googleapis.com/css?family=Droid+Serif|Raleway:400,500,600,700" rel="stylesheet">
    <link href="css/reset.css" rel="stylesheet" type="text/css">
    <link href="css/style.css" rel="stylesheet" type="text/css">
</head>
<body>
    <header>
        <h1>MEMORY GAME</h1>
    </header>
    <nav>
        <a class="nav" href="#">RULES</a> |
        <a class="nav" href="#">GAME</a>
    </nav>
    <main>
        <h2>RULES</h2>
        <p>Concentration, also known as Match Match, Memory, Pelmanism, Shinkei-suijaku, Pexeso, or simply Pairs, is a card game in which all of the cards are laid face down on a surface and two cards are flipped up over each turn. The object of the game is to turn over pairs of matching cards</p>
        <div id="game-board" class="board clearfix"></div>
    </main>
    <footer class="clearfix">
        <p class="copyright">Copyright 2017</p>
    </footer>
    <script src="js/main.js"></script>
</body> 
</html>

请,老师,请教我。

更新:为回答有关我的意图的任何问题,我添加了评论和html

1 个答案:

答案 0 :(得分:0)

您的事件处理程序flipCard将收到一个Event对象,如果发生点击事件,则将收到一个MouseEvent对象。 MouseEvent对象将包含属性currentTarget,该属性将引用事件处理程序附加到的元素。

尝试一下...

let flipcard = (event) => {
    let card = event.currentTarget;
    let cardId = card.getAttribute('data-id');
    cardsInPlay.push(cards[cardId].rank);
    card.setAttribute('src', cards[cardId].cardImage);
    checkForMatch();
}

您还将在target对象上拥有一个Event属性,该属性指的是触发事件并考虑到事件冒泡的元素(https://developer.mozilla.org/en-US/docs/Web/API/Event/target)。

注意正如@RobG所指出的,您应该真正考虑何时使用箭头功能。