All you have to do is to load a couple of scripts, four, to be precise.
- Register your widget class first
- Load the media library
- Pass some variables to translate things properly (please see translation standards of WordPress for more info about this.)
- Add your own script on top to trigger the modal window and handle the file upload
First register your widget as a class, then drop in the scripts:
<?php
// We register our widget
function wpse_register_my_custom_widget(){
register_widget('The_Custom_Image_Upload_Widget');
}
add_action('widgets_init', 'wpse_register_my_custom_widget');
// in your plugin main file or functions.php when in a theme ..
function wpse_load_media_library(){
// Set $pagenow to global to check, where to load the scripts..
global $pagenow;
// make a variable for the path in case you don't have it
$dir = plugins_url('/my-plugin-folder');
// register your own script first
wp_register_script(
// WP internal name (so called "handle") this is important as you need to relate to this name later on
'my-js-file-with-code',
$dir . '/components/js/the-custom-image-upload-actions.js',
array('jquery'),
false,
true
);
// Now let's kick in our scripts
if($pagenow === 'widgets.php'){
// Load/enqueue the media library, this is what you didn't find and struggled with..
wp_enqueue_media();
// load your own script with the trigger of the modal
wp_enqueue_script('my-js-file-with-code');
// Then pass some variables to wordpress in order to translate things in Javascript
wp_localize_script(
// WP Handle/ID of the script to translate
'my-js-file-with-code',
// random varname (array) which holds the strings
'scripttext',
array( // array with strings
'title' => __('Logo upload', 'textdomain'),
'button' => __('use this logo', 'textdomain'),
'multiple' => __('use these images', 'textdomain')
)
);
}
add_action('admin_enqueque_scripts', 'wpse_load_media_library');
?>
// My JS file with code
<script>
// image Upload
$('#trigger_to_open_the_modal').click(function(e){
var single_image_frame;
e.preventDefault();
if ( single_image_frame ) {
single_image_frame.open();
return;
}
single_image_frame = wp.media.frames.single_image_frame = wp.media({
title: scripttext.title,
button: { text: scripttext.button },
library: { type: 'image' }
});
single_image_frame.on('select', function(){
var media_attachment = single_image_frame.state().get('selection').first().toJSON();
// Adjust this to your needs, pops in the url to the img tag
$('#custom-upload-logo').attr('src', media_attachment.url);
$('#logo_url').val(media_attachment.url);
});
single_image_frame.open();
});
</script>
Since I don't know your markup, I did not write any example HTML of your widget. This took me about an hour to write so I hope you don't mind.