Custom post preview without saving

I found a nice way to do this using the preview_post_link filter, which allows you to rewrite the URL used by the preview operation. In my case I did something like:

add_filter( 'preview_post_link', function ( $link ) {
    return 'http://domain.com/mobile-preview/?src="https://wordpress.stackexchange.com/questions/191918/. urlencode($link) ."%26admin_bar=false';
} );

When I click my preview button WordPress opens up my custom URL. Easy, and no need for JavaScript – WordPress being brilliant again!

In case anyone does need to do it with JS, though, you can try this:

(function ($) {

    $(document).ready(function () {

        // Create URL for post preview
        var previewUrl = $('#preview-action').find('.preview').attr('href');
        var parser = document.createElement('a');
        parser.href = previewUrl;
        var postId = $('#post_ID').val();
        mobilePreviewUrl = parser.protocol + '//' + parser.host + '?p=' + postId;

        var href = mobilePreviewUrl ? 'http://domain.com/mobile-preview/?src="https://wordpress.stackexchange.com/questions/191918/+ encodeURIComponent(mobilePreviewUrl) +"%26preview=true' : '';

        // Preview buttons
        var mobilePreviewBtn = $('<a/>').addClass('preview button').attr({
            'id'    : 'mobile-preview',
            'href'  : href,
            'target': '_new'
        }).text('Preview Mobile');
        $('#preview-action').prepend(mobilePreviewBtn);
        $('#post-preview').hide();
        mobilePreviewBtn.on('click', function(e){
            e.preventDefault();
            $(window).off( 'beforeunload.edit-post' );
            wp.autosave.server.tempBlockSave();
            $('form#post').submit();
            window.open(href, 'mobilePreview');
        });

    }); // end document ready

})(jQuery);

This grabs the URL from the default preview button’s href attribute, and uses it as the href of a new custom mobile preview button. My mobile preview page is hosted offsite – when the user clicks on the custom preview button we’re going to pass the default preview URL to this special page as a parameter called src. The preview page displays the URL in a mobile-sized iframe.

The click handler for the custom preview button turns off the beforeunload.edit-post event handler to stop the default “are you sure you want to leave this page?” confirm that pops up when you submit the post edit form. The next line calls the autosave JS method WordPress normally uses when you click the preview button. This saves the draft currently in the post editor. The next line submits the post saved in the editor, and the final line opens a new window with our custom preview URL.