Metadata from Media is null, JavaFX

Tags: ,



I’m trying to get artist’s name from a song in my listview on click of a button but i’m getting this

null
null
null
null
XXXTENTACION
XXXTENTACION
XXXTENTACION
XXXTENTACION
XXXTENTACION
XXXTENTACION

And here is my code

btnPlay.setOnAction(event -> {
            try {
                File selectedItem = listView.getSelectionModel().getSelectedItem();
                Media media = new Media(selectedItem.toURI().toString());
                mediaPlayer = new MediaPlayer(media);
                mediaPlayer.play();
                System.out.println(media);


                media.getMetadata().addListener((MapChangeListener<String, Object>) change -> {
                    String artist = (String)media.getMetadata().get("artist");
                    System.out.println(artist);
                });
            }
            catch (Exception e){
                System.out.println("Please choose the song...");
            }

How do i print it normally, only once?

Answer

Your listener will be invoked when any of the metadata change. Since you’re only interested in when the artist changes, and is changed to a non-null value, you can do:

media.getMetadata().addListener((MapChangeListener<String, Object>) change -> {
    if (change.getKey().equals("artist")) {
        String artist = (String)media.getMetadata().get("artist");
        if (artist != null) {
            System.out.println(artist);
        }
    }
});

It’s also pretty safe to assume here that the only change that ever happens to the artist is that a value is added (i.e. goes from null to non-null); making this assumption you could also do

media.getMetadata().addListener((MapChangeListener<String, Object>) change -> {
    if (change.getKey().equals("artist") && change.wasAdded()) {
        String artist = (String)change.getValueAdded();
        System.out.println(artist);
    }
});

Note that typically in the UI you don’t want to display the value in the console, but in a label (or something similar). In this case, there’s really no need to check for the correct change – you can use a binding instead:

Label artistLabel = new Label();
// ...

Media media = new Media(selectedItem.toURI().toString());
artistLabel.textProperty().bind(
    Bindings.valueAt(media.getMetadata(), "artist")
            .asString("Artist: %s"));


Source: stackoverflow