0

I am currently trying to sort all my game objects alphabetically by title. I have gotten my onclick to register but it does not execute my JS function below is the HTML and JS snippets. The sortAlpha is a method within the Games class.

*edit 1: Adjusted function to attach a event listener

*edit 2: I have opted to create a variable to store and call the function. My next question is am I not correctly displaying the newly alphabetized contents with my function ? I get no errors and my log shows that clicks are being registered.

<div id="filter">
    <div id="buttons">
        <button onclick="let the_game = new Games(); the_game.sortAlpha()">Sort Games Alphabetically</button>
    </div>
</div>

class Games {
    constructor() {
        this.games = []
        this.adapter = new GamesAdapter()
        this.initBindingsAndEventListeners()
        this.fetchAndLoadGames()
    }
    initBindingsAndEventListeners() {
        this.newGameForm = document.getElementById('new-game-form')
        this.newGameTitle = document.getElementById('new-game-title')
        this.newGameDeveloper = document.getElementById('new-game-developer')
        this.newGameCover = document.getElementById('new-game-cover')
        this.newGameForm.addEventListener('submit', this.createGame.bind(this))
    }

    createGame(g) {
        g.preventDefault();
        const titleValue = this.newGameTitle.value;
        const developerValue = this.newGameDeveloper.value;
        const coverValue = this.newGameCover.value;

        this.adapter.createGame(titleValue, developerValue, coverValue)
            .then(game => {
            const newGame = new Game(game)
            this.games.push(newGame)
            this.newGameTitle.value = ' '
            this.newGameDeveloper.value = ' '
            this.newGameCover.value = ' '
            newGame.renderGameBlock()
        })
    }
    fetchAndLoadGames() {
        this.adapter
        .getGames()
        .then(games => {
        games.forEach(game => this.games.push(new Game(game)))
        })
        .then(() => {
        this.renderGames()
        })
    }

    renderGames() {
        this.games.map(game => game.renderGameBlock())
    }

  sortAlpha() {
    console.log('test');
    this.games.sort(function(gameA, gameB){
        if (gameA.title < gameB.title) {
            return -1;

        }
        if (gameA.title > gameB.title){
            return 1;
        }

        return 0;
       });
        window.onload = function() {
        document.getElementById("filter").onclick = sortAlpha;
       }
    }
}
steveks17
  • 73
  • 9
  • That's not a stand-alone function definition. Is that part of a class? You probably need to call this on an object, like `x.sortAlpha()` where `x` is an instance of this class. – tadman Apr 29 '20 at 22:32
  • 1
    @tadman It's unlikely that `x` would be declared in the global scope as the DOM is being parsed, so using `onclick` probably won't work at all. The OP should use `addEventListener` during `DOMContentLoaded` (and also re-bind `this`). – Dai Apr 29 '20 at 22:34
  • 1
    @Dai Completely agree. I'm just starting with the first problem of the function being not-found. – tadman Apr 29 '20 at 22:35
  • Hmm I think I am understanding this correctly so what I've done is make a new function. going to edit my post to show changes. – steveks17 Apr 29 '20 at 22:44

1 Answers1

1

The sortAlpha is a method within the Games class.

That's your answer right there. sortAlpha is not a free-function, but your onclick="" attribute references sortAlpha() as though it were a free-function.

(A "free function" is a function that is not a member of a class/type)

You need to move your sortAlpha function to the global scope, or attach it to the button using addEventListener. You cannot use class method functions in onclick="" without fully qualifying them.

Dai
  • 141,631
  • 28
  • 261
  • 374
  • Since it uses `this` it can't be moved global. – tadman Apr 29 '20 at 22:34
  • 2
    @tadman Then you should use `addEventListener` inside `DOMContentLoaded` (or whenever your `Games` class initializes itself). – Dai Apr 29 '20 at 22:35
  • Can you please elaborate on this I believe you mean I should add this new event listener to my initBindingsAndEventListeners() in game.js – steveks17 Apr 29 '20 at 22:56