4

I'd like to add a download button to the core wp audio player (mediaelement.js).

How can I do that simply? Any suggestions?

  • I'm waiting for the solution . – mahdiar Apr 27 '14 at 14:41
  • I assume you mean the audio playlist, because of your other question on how to use a playlist with external audio files. – birgire Apr 30 '14 at 23:39
  • "I'm waiting for the solution" Don't be rude. Your question as it stands should get now response. This is not a do-my-work-for-me-website. You need to at least show effort from your site, some research, some code. – Pieter Goosen May 1 '14 at 7:12
  • I don't like to be rude but I should recheck my answer . Really sorry .You are compeltely right. – mahdiar May 2 '14 at 12:17
9

How to use a custom playlist template:

You can overwrite the playlist template with your own template:

/**
 * Remove the native playlist template and load our custom template
 * @link http://wordpress.stackexchange.com/q/141767/26350
 */

add_action( 'wp_playlist_scripts', 'wpse_141767_wp_playlist_scripts' );

function wpse_141767_wp_playlist_scripts()
{
    remove_action( 'wp_footer', 'wp_underscore_playlist_templates', 0 );
    add_action( 'wp_footer', 'wpse_141767_wp_underscore_playlist_templates', 0 );
}

where our modified template is defined as:

/**
 * Our custom playlist template.
 */

function wpse_141767_wp_underscore_playlist_templates() {
?>
<script type="text/html" id="tmpl-wp-playlist-current-item">
        <# if ( data.image ) { #>
        <img src="{{ data.thumb.src }}"/>
        <# } #>
        <div class="wp-playlist-caption">
                <span class="wp-playlist-item-meta wp-playlist-item-title">&#8220;{{ data.title }}&#8221;</span>
                <# if ( data.meta.album ) { #><span class="wp-playlist-item-meta wp-playlist-item-album">{{ data.meta.album }}</span><# } #>
                <# if ( data.meta.artist ) { #><span class="wp-playlist-item-meta wp-playlist-item-artist">{{ data.meta.artist }}</span><# } #>
        </div>
</script>
<script type="text/html" id="tmpl-wp-playlist-item">
        <div class="wp-playlist-item">
                <a class="wp-playlist-caption" href="{{ data.src }}">
                        {{ data.index ? ( data.index + '. ' ) : '' }}
                        <# if ( data.caption ) { #>
                                {{ data.caption }}
                        <# } else { #>
                                <span class="wp-playlist-item-title">&#8220;{{{ data.title }}}&#8221;</span>
                                <# if ( data.artists && data.meta.artist ) { #>
                                <span class="wp-playlist-item-artist"> &mdash; {{ data.meta.artist }}</span>
                                <# } #>
                        <# } #>
                </a>
                <# if ( data.meta.length_formatted ) { #>
                <div class="wp-playlist-item-length">{{ data.meta.length_formatted }}</div>
                <# } #>             
        </div>

        <!-- BEGIN CHANGES -->
           <a href="{{ data.src }}" class="wpse-download" download="">download</a>
        <!-- END CHANGES -->

</script>
<?php
}

where we added this part at the end:

<!-- BEGIN CHANGES -->
   (<a href="{{ data.src }}" class="wpse-download" download="">download</a>)
<!-- END CHANGES -->

You might also need to add a special url to download the files.

The reason why I didn't add it within the div.wp-playlist-item selector, is because everything that's clicked on inside it, will start the player. The reason is this part of the /wp-includes/js/mediaelement/wp-playlist.js file:

events : {
    'click .wp-playlist-item' : 'clickTrack',
    'click .wp-playlist-next' : 'next',
    'click .wp-playlist-prev' : 'prev'
},

clickTrack : function (e) {
    e.preventDefault();

    this.index = this.$( '.wp-playlist-item' ).index( e.currentTarget );
    this.setCurrent();
},

Here's the screenshot of our modified playlist template in action:

Modified playlist template

You could try some custom CSS to modify this to your needs.

Here's one kind of hack, that might need adjustments depending on the current theme:

<style>
    .wpse-download {
        margin-top: -22px;
        margin-left: -16px;
        position: absolute;
    }
    .wp-playlist {
        padding: 25px;
    }
</style>

with:

<!-- BEGIN CHANGES -->
    <a href="{{ data.src }}" class="wpse-download" download="">
        <i class="fa fa-download" aria-hidden="true"></i>
    </a>
<!-- END CHANGES -->

in the presence of Font Awesome.

Custom CSS download button

Further customization:

You might also consider enqueuing your own version of the wp-playlist.js file where you replace:

'click .wp-playlist-item' : 'clickTrack',

with for example:

'click a.wp-playlist-item-caption' : 'clickTrack',

to be able to have the download link in the same row as the song title.

Update:

Updated the screenshots and added another example.

To make sure the file is downloaded and not displayed in the browser, we can use the download link attribute. I've updated the above with:

(<a href="{{ data.src }}" download="">download</a>)

It seems that the empty value will download it as current file name.

0
<script>
/**
 * Our custom playlist template for mp3 download`.
 */
function wpse_141767_wp_underscore_playlist_templates() {
?>
<script type="text/html" id="tmpl-wp-playlist-current-item">
        <# if ( data.image ) { #>
        <img src="{{ data.thumb.src }}"/>
        <# } #>
        <div class="wp-playlist-caption">
                <span class="wp-playlist-item-meta wp-playlist-item-title">&#8220;{{ data.title }}&#8221;</span>
                <# if ( data.meta.album ) { #><span class="wp-playlist-item-meta wp-playlist-item-album">{{ data.meta.album }}</span><# } #>
                <# if ( data.meta.artist ) { #><span class="wp-playlist-item-meta wp-playlist-item-artist">{{ data.meta.artist }}</span><# } #>
        </div>
</script>
<script type="text/html" id="tmpl-wp-playlist-item">
        <div class="wp-playlist-item">
                <a class="wp-playlist-caption" href="{{ data.src }}">
                        {{ data.index ? ( data.index + '. ' ) : '' }}
                        <# if ( data.caption ) { #>
                                {{ data.caption }}
                        <# } else { #>
                                <span class="wp-playlist-item-title">&#8220;{{{ data.title }}}&#8221;</span>
                                <# if ( data.artists && data.meta.artist ) { #>
                                <span class="wp-playlist-item-artist"> &mdash; {{ data.meta.artist }}</span>
                                <# } #>
                        <# } #>
                </a>
                <# if ( data.meta.length_formatted ) { #>
<div class="wp-playlist-item-length">
<span>
            (<a href="{{ data.src }}"><i class="fa fa-download" title="Download" aria-hidden="true"></i></a>)
        </span>{{ data.meta.length_formatted }}</div>
                <# } #>             
        </div>
</script>
<?php
}
</script>

protected by Community Apr 13 '18 at 15:31

Thank you for your interest in this question. Because it has attracted low-quality or spam answers that had to be removed, posting an answer now requires 10 reputation on this site (the association bonus does not count).

Would you like to answer one of these unanswered questions instead?

Not the answer you're looking for? Browse other questions tagged or ask your own question.