Music Player for WooCommerce - Version 1.0.104

Version Description

  • Modifies the settings page of the plugin.
  • Complete the language files.
  • Improves the errors detection by including additional error logs.
  • Includes a new option to allow playing the original audio files instead the demo versions, if the logged user has bought the product (Professional version).
Download this release

Release Info

Developer codepeople
Plugin Icon 128x128 Music Player for WooCommerce
Version 1.0.104
Comparing to
See all releases

Version 1.0.104

Files changed (42) hide show
  1. addons/dokan.addon.php +40 -0
  2. addons/dokan/player_options.php +265 -0
  3. addons/dokan/style.css +3 -0
  4. banner.php +108 -0
  5. css/style.admin.css +8 -0
  6. css/style.css +31 -0
  7. js/public.js +11 -0
  8. js/public_src.js +218 -0
  9. languages/music-player-for-woocommerce-en_US.mo +0 -0
  10. languages/music-player-for-woocommerce-en_US.po +580 -0
  11. pagebuilders/beaverbuilder/wcmp.inc.php +26 -0
  12. pagebuilders/beaverbuilder/wcmp/includes/frontend.php +10 -0
  13. pagebuilders/beaverbuilder/wcmp/wcmp.pb.php +18 -0
  14. pagebuilders/builders.php +154 -0
  15. pagebuilders/divi/divi.js +1 -0
  16. pagebuilders/divi/divi.pb.php +58 -0
  17. pagebuilders/elementor/elementor.pb.php +105 -0
  18. pagebuilders/elementor/elementor_category.pb.php +16 -0
  19. pagebuilders/gutenberg/gutenberg.css +7 -0
  20. pagebuilders/gutenberg/gutenberg.js +109 -0
  21. pagebuilders/gutenberg/wcblocks.css +1 -0
  22. pagebuilders/gutenberg/wcblocks.js +32 -0
  23. pagebuilders/siteorigin/siteorigin-wcmp/assets/banner.svg +1 -0
  24. pagebuilders/siteorigin/siteorigin-wcmp/siteorigin-wcmp.php +48 -0
  25. pagebuilders/siteorigin/siteorigin-wcmp/tpl/siteorigin-wcmp-shortcode.php +1 -0
  26. pagebuilders/visualcomposer/WCMPplaylist/WCMPplaylist/public/wcmp-preview.png +0 -0
  27. pagebuilders/visualcomposer/WCMPplaylist/WCMPplaylist/public/wcmp-thumbnail.png +0 -0
  28. pagebuilders/visualcomposer/WCMPplaylist/manifest.json +19 -0
  29. pagebuilders/visualcomposer/WCMPplaylist/public/dist/element.bundle.js +83 -0
  30. readme.txt +653 -0
  31. views/assets/skin1.png +0 -0
  32. views/assets/skin1_btn.png +0 -0
  33. views/assets/skin2.png +0 -0
  34. views/assets/skin2_btn.png +0 -0
  35. views/assets/skin3.png +0 -0
  36. views/assets/skin3_btn.png +0 -0
  37. views/global_options.php +381 -0
  38. views/player_options.php +340 -0
  39. wcmp.php +1344 -0
  40. widgets/playlist_widget.php +153 -0
  41. widgets/playlist_widget/css/style.css +29 -0
  42. widgets/playlist_widget/js/public.js +83 -0
addons/dokan.addon.php ADDED
@@ -0,0 +1,40 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ if(!class_exists('WCMP_DOKAN_ADDON'))
3
+ {
4
+ class WCMP_DOKAN_ADDON
5
+ {
6
+ private $_wcmp;
7
+
8
+ function __construct($wcmp)
9
+ {
10
+ $this->_wcmp = $wcmp;
11
+ add_action('dokan_product_edit_after_main',array($this, 'show_settings'));
12
+ add_action('dokan_process_product_meta',array($this, 'save_settings'));
13
+ add_action( 'dokan_product_deleted', array($this, 'delete_product'));
14
+ } // End __construct
15
+
16
+ public function show_settings()
17
+ {
18
+ wp_enqueue_style('wcmp-dokan', plugin_dir_url(__FILE__).'dokan/style.css');
19
+ include_once dirname(__FILE__).'/dokan/player_options.php';
20
+ /* $this->_wcmp->woocommerce_player_settings(); */
21
+ } // End show_settings
22
+
23
+ public function save_settings($post_id)
24
+ {
25
+ $post = get_post($post_id);
26
+ $this->_wcmp->save_post($post_id, $post, true);
27
+ } // End save_settings
28
+
29
+ public function delete_product($post_id)
30
+ {
31
+ $this->_wcmp->delete_post($post_id);
32
+ } // End delete_product
33
+
34
+ //******************** PRIVATE METHODS ************************
35
+
36
+
37
+ } // End WCMP_CLOUD_DRIVE_ADDON
38
+ }
39
+
40
+ new WCMP_DOKAN_ADDON($wcmp);
addons/dokan/player_options.php ADDED
@@ -0,0 +1,265 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ if( !defined( 'WCMP_PLUGIN_URL' ) ) { echo 'Direct access not allowed.'; exit; }
3
+
4
+ // include resources
5
+ wp_enqueue_style( 'wcmp-admin-style', plugin_dir_url(__FILE__).'../../css/style.admin.css', array(), '5.0.34' );
6
+ wp_enqueue_script( 'wcmp-admin-js', plugin_dir_url(__FILE__).'../../js/admin.js' );
7
+
8
+ $wcmp_js = array(
9
+ 'File Name' => __( 'File Name', 'music-player-for-woocommerce' ),
10
+ 'Choose file' => __( 'Choose file', 'music-player-for-woocommerce' ),
11
+ 'Delete' => __( 'Delete', 'music-player-for-woocommerce' ),
12
+ 'Select audio file' => __( 'Select audio file', 'music-player-for-woocommerce' ),
13
+ 'Select Item' => __( 'Select Item', 'music-player-for-woocommerce' )
14
+ );
15
+ wp_localize_script('wcmp-admin-js', 'wcmp', $wcmp_js);
16
+
17
+ global $post;
18
+ $enable_player = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_enable_player', false );
19
+ $show_in = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_show_in', 'all' );
20
+ $player_style = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_player_layout', WCMP_DEFAULT_PLAYER_LAYOUT );
21
+ $player_controls= $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_player_controls', WCMP_DEFAULT_PLAYER_CONTROLS );
22
+ $player_title = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_player_title',1 ) );
23
+ $merge_grouped = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_merge_in_grouped',0 ) );
24
+ $play_all = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
25
+ $post->ID,
26
+ '_wcmp_play_all',
27
+ // This option is only for compatibility with versions previous to 1.0.28
28
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
29
+ $post->ID,
30
+ 'play_all',
31
+ 0
32
+ )
33
+ )
34
+ );
35
+ $preload = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
36
+ $post->ID,
37
+ '_wcmp_preload',
38
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
39
+ $post->ID,
40
+ 'preload',
41
+ 'none'
42
+ )
43
+ );
44
+ $on_cover = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_on_cover', 0 ) );
45
+ ?>
46
+ <div class="dokan-edit-row wcmp-section">
47
+ <input type="hidden" name="wcmp_nonce" value="<?php echo wp_create_nonce('wcmp_updating_product'); ?>" />
48
+ <div class="dokan-section-heading"><h2><?php _e('Music Player Settings', 'music-player-for-woocommerce'); ?></h2></div>
49
+ <div class="dokan-section-content">
50
+ <div class="wcmp-highlight-box">
51
+ <?php
52
+ _e(
53
+ '<p>The player uses the audio files associated to the product.</b></p>',
54
+ 'music-player-for-woocommerce'
55
+ );
56
+ ?>
57
+ </div>
58
+ <div class="wcmp-highlight-box">
59
+ <div id="wcmp_tips_header">
60
+ <div style="margin-top:2px;margin-bottom:5px;cursor:pointer;font-weight:bold;" onclick="jQuery('#wcmp_tips_body').toggle();">
61
+ <?php _e('[+|-] Tips', 'music-player-for-woocommerce'); ?>
62
+ </div>
63
+ </div>
64
+ <div id="wcmp_tips_body">
65
+ <div class="wcmp-highlight-box">
66
+ <a class="wcmp-tip"href="javascript:void(0);" onclick="jQuery(this).next('.wcmp-tip-text').toggle();">
67
+ <?php _e('[+|-] Using the audio files stored on Google Drive', 'music-player-for-woocommerce'); ?>
68
+ </a>
69
+ <div class="wcmp-tip-text">
70
+ <ul>
71
+ <li>
72
+ <p> -
73
+ <?php
74
+ _e(
75
+ 'Go to Drive, press the right click on the file to use, and select the option: <b>"Get Shareable Link"</b>',
76
+ 'music-player-for-woocommerce'
77
+ );
78
+ ?>
79
+ </p>
80
+ <p>
81
+ <?php
82
+ _e(
83
+ 'The previous action will generate an url with the structure: <b>https://drive.google.com/open?id=FILE_ID</b>',
84
+ 'music-player-for-woocommerce'
85
+ );
86
+ ?>
87
+ </p>
88
+ </li>
89
+ <li>
90
+ <p> -
91
+ <?php
92
+ _e(
93
+ 'Knowing the FILE_ID, extracted from the previous URL, enter the URL below, into the WooCommerce product, to allow the Music Player accessing to it:',
94
+ 'music-player-for-woocommerce'
95
+ );
96
+ ?>
97
+ </p>
98
+ <p>
99
+ <b>https://drive.google.com/uc?export=download&id=FILE_ID&.mp3</b>
100
+ </p>
101
+ <p>
102
+ <?php
103
+ _e(
104
+ '<b>Note:</b> Pay attention to the use of the fake parameter: <b>&.mp3</b> as the last one in the URL',
105
+ 'music-player-for-woocommerce'
106
+ );
107
+ ?>
108
+ </p>
109
+ </li>
110
+ </div>
111
+ </div>
112
+ <div class="wcmp-highlight-box">
113
+ <a class="wcmp-tip"href="javascript:void(0);" onclick="jQuery(this).next('.wcmp-tip-text').toggle();">
114
+ <?php _e('[+|-] Using the audio files stored on DropBox', 'music-player-for-woocommerce'); ?>
115
+ </a>
116
+ <div class="wcmp-tip-text">
117
+ <ul>
118
+ <li>
119
+ <p> -
120
+ <?php
121
+ _e(
122
+ 'Sign in to <a href="https://www.dropbox.com/login" target="_blank">dropbox.com </a>',
123
+ 'music-player-for-woocommerce'
124
+ );
125
+ ?>
126
+ </p>
127
+ </li>
128
+ <li>
129
+ <p> -
130
+ <?php
131
+ _e(
132
+ "Hover your cursor over the file or folder you'd like to share and click <b>Share</b> when it appears.",
133
+ 'music-player-for-woocommerce'
134
+ );
135
+ ?>
136
+ </p>
137
+ </li>
138
+ <li>
139
+ <p> -
140
+ <?php
141
+ _e(
142
+ "If a link hasn't been created, click Create a link. (If a link was already created, click Copy link.",
143
+ 'music-player-for-woocommerce'
144
+ );
145
+ ?>
146
+ </p>
147
+ <p>
148
+ <?php
149
+ _e(
150
+ 'The link structure would be similar to:<br> https://www.dropbox.com/s/rycvgn8iokfedmo/file.mp3?dl=0',
151
+ 'music-player-for-woocommerce'
152
+ );
153
+ ?>
154
+ </p>
155
+ </li>
156
+ <li>
157
+ <p> -
158
+ <?php
159
+ _e(
160
+ 'Enter the URL into the WooCommerce product with the following structure:<br> https://www.dropbox.com/s/rycvgn8iokfedmo/file.mp3?dl=1&.mp3',
161
+ 'music-player-for-woocommerce'
162
+ );
163
+ ?>
164
+ </p>
165
+ <p>
166
+ <?php
167
+ _e(
168
+ '<b>Note:</b> Pay attention to the use of the fake parameter: <b>&.mp3</b> as the last one in the URL. Furthermore, the parameter <b>dl=0</b>, has been modified as <b>dl=1</b>',
169
+ 'music-player-for-woocommerce'
170
+ );
171
+ ?>
172
+ </p>
173
+ </li>
174
+ </div>
175
+ </div>
176
+ </div>
177
+ </div>
178
+ <div>
179
+ <div class="wcmp-dokan-attr">
180
+ <label class="wcmp-dokan-attr-label">
181
+ <input type="checkbox" name="_wcmp_enable_player" <?php echo (( $enable_player ) ? 'checked' : '' ); ?> title="<?php print esc_attr(__('The player is shown only if the product is "downloadable" with at least an audio file between the "Downloadable files", or you have selected your own audio files', 'music-player-for-woocommerce')); ?>" /> <?php _e( 'Include music player', 'music-player-for-woocommerce' ); ?>
182
+ </label>
183
+ </div>
184
+ <div class="wcmp-dokan-attr">
185
+ <label for="_wcmp_show_in" class="wcmp-dokan-attr-label"><?php _e( 'Include in', 'music-player-for-woocommerce' ); ?></label>
186
+ <div>
187
+ <label><input type="radio" name="_wcmp_show_in" value="single" <?php echo (( $show_in == 'single' ) ? 'checked' : '' ); ?> />
188
+ <?php _e('single-entry pages <i>(Product\'s page only)</i>', 'music-player-for-woocommerce'); ?></label>
189
+
190
+ <label><input type="radio" name="_wcmp_show_in" value="multiple" <?php echo (( $show_in == 'multiple' ) ? 'checked' : '' ); ?> />
191
+ <?php _e('multiple entries pages <i>(Shop pages, archive pages, but not in the product\'s page)</i>', 'music-player-for-woocommerce'); ?></label>
192
+
193
+ <label><input type="radio" name="_wcmp_show_in" value="all" <?php echo (( $show_in == 'all' ) ? 'checked' : '' ); ?> />
194
+ <?php _e('all pages <i>(with single or multiple-entries)</i>', 'music-player-for-woocommerce'); ?></label>
195
+ </div>
196
+ </div>
197
+ <div class="wcmp-dokan-attr">
198
+ <label class="wcmp-dokan-attr-label"><?php _e( 'Merge in grouped products', 'music-player-for-woocommerce' ); ?>
199
+ <input type="checkbox" name="_wcmp_merge_in_grouped" <?php echo (( $merge_grouped ) ? 'checked' : '' ); ?> /></label>
200
+ <div><em><?php _e( 'In grouped products, display the "Add to cart" buttons and quantity fields in the players rows', 'music-player-for-woocommerce' ); ?></em></div>
201
+ </div>
202
+ <div class="wcmp-dokan-attr">
203
+ <label class="wcmp-dokan-attr-label"><?php _e( 'Player layout', 'music-player-for-woocommerce' ); ?></label>
204
+ <table border="0" width="100%">
205
+ <tr>
206
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-classic" <?php echo (($player_style == 'mejs-classic') ? 'checked' : '') ;?> /></td>
207
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin1.png" /></td>
208
+ </tr>
209
+
210
+ <tr>
211
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-ted" <?php echo (($player_style == 'mejs-ted') ? 'checked' : '') ;?> /></td>
212
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin2.png" /></td>
213
+ </tr>
214
+
215
+ <tr>
216
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-wmp" <?php echo (($player_style == 'mejs-wmp') ? 'checked' : '') ;?> /></td>
217
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin3.png" /></td>
218
+ </tr>
219
+ </table>
220
+ </div>
221
+ <div class="wcmp-dokan-attr">
222
+ <label for="_wcmp_preload" class="wcmp-dokan-attr-label"><?php _e( 'Preload', 'music-player-for-woocommerce' ); ?></label>
223
+ <div>
224
+ <label><input type="radio" name="_wcmp_preload" value="none" <?php if($preload == 'none') echo 'CHECKED'; ?> /> None</label>
225
+ <label><input type="radio" name="_wcmp_preload" value="metadata" <?php if($preload == 'metadata') echo 'CHECKED'; ?> /> Metadata</label>
226
+ <label><input type="radio" name="_wcmp_preload" value="auto" <?php if($preload == 'auto') echo 'CHECKED'; ?> /> Auto</label>
227
+ </div>
228
+ </div>
229
+ <div class="wcmp-dokan-attr">
230
+ <label><?php _e( 'Play all', 'music-player-for-woocommerce' ); ?> <input type="checkbox" name="_wcmp_play_all" <?php if(!empty($play_all)) echo 'CHECKED'; ?> /></label>
231
+ </div>
232
+ <div class="wcmp-dokan-attr">
233
+ <label class="wcmp-dokan-attr-label"><?php _e( 'Player controls', 'music-player-for-woocommerce' ); ?></label>
234
+ <div>
235
+ <label><input type="radio" name="_wcmp_player_controls" value="button" <?php echo (( $player_controls == 'button' ) ? 'checked' : ''); ?> /> <?php _e( 'the play/pause button only', 'music-player-for-woocommerce' ); ?></label>
236
+ <label><input type="radio" name="_wcmp_player_controls" value="all" <?php echo (( $player_controls == 'all' ) ? 'checked' : ''); ?> /> <?php _e( 'all controls', 'music-player-for-woocommerce' ); ?></label>
237
+ <label><input type="radio" name="_wcmp_player_controls" value="default" <?php echo (( $player_controls == 'default' ) ? 'checked' : ''); ?> /> <?php _e( 'the play/pause button only, or all controls depending on context', 'music-player-for-woocommerce' ); ?></label>
238
+ <div class="wcmp-on-cover" style="margin-top:10px;">
239
+ <label><input type="checkbox" name="_wcmp_player_on_cover" value="default" <?php
240
+ echo ((!empty($on_cover) && ( $player_controls == 'button' || $player_controls == 'default')) ? 'checked' : '');
241
+ ?> /> <?php _e( 'for play/pause button players display them on cover images.', 'music-player-for-woocommerce' ); ?></label>
242
+ <div><em><?php _e('(This feature is experimental, and will depend on the theme active on the website.)', 'music-player-for-woocommerce'); ?></em></div>
243
+ </div>
244
+ </div>
245
+ </div>
246
+ <div class="wcmp-dokan-attr">
247
+ <label><?php _e( 'Display the player\'s title', 'music-player-for-woocommerce' ); ?> <input type="checkbox" name="_wcmp_player_title" <?php echo (( !empty($player_title) ) ? 'checked' : ''); ?> /></label>
248
+ </div>
249
+ </div>
250
+ </div>
251
+ </div>
252
+ <script>jQuery(window).on('load', function(){
253
+ var $ = jQuery;
254
+ function coverSection()
255
+ {
256
+ var v = $('[name="_wcmp_player_controls"]:checked').val(),
257
+ c = $('.wcmp-on-cover');
258
+ if(v == 'default' || v == 'button') c.show();
259
+ else c.hide();
260
+ };
261
+ $(document).on('change', '[name="_wcmp_player_controls"]', function(){
262
+ coverSection();
263
+ });
264
+ coverSection();
265
+ });</script>
addons/dokan/style.css ADDED
@@ -0,0 +1,3 @@
 
 
 
1
+ .wcmp-section table{margin:5px 0 !important;}
2
+ .wcmp-dokan-attr{margin-top:10px;padding-top:10px;border-top: 1px solid #EBEBEB;}
3
+ .wcmp-dokan-attr-label{font-size:1.3em;}
banner.php ADDED
@@ -0,0 +1,108 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ global $codepeople_promote_banner_plugins;
3
+ if(empty($codepeople_promote_banner_plugins)) $codepeople_promote_banner_plugins = array();
4
+ if(!function_exists( 'codepeople_add_promote_banner' ))
5
+ {
6
+ function codepeople_add_promote_banner($wp_admin_bar)
7
+ {
8
+ global $codepeople_promote_banner_plugins;
9
+
10
+ if(
11
+ empty($codepeople_promote_banner_plugins) ||
12
+ !is_admin() ||
13
+ !current_user_can( 'manage_options' )
14
+ ) return;
15
+
16
+ $screen = get_current_screen();
17
+ if ( $screen->post_type == 'post' || $screen->post_type == 'page' ) return;
18
+
19
+ // Take action over the banner
20
+ if(isset($_POST['codepeople_promote_banner_nonce']) && wp_verify_nonce($_POST['codepeople_promote_banner_nonce'], __FILE__))
21
+ {
22
+ if(
23
+ !empty($_POST['codepeople_promote_banner_plugin']) &&
24
+ !empty($codepeople_promote_banner_plugins[$_POST['codepeople_promote_banner_plugin']])
25
+ )
26
+ {
27
+ set_transient( 'codepeople_promote_banner_'.sanitize_text_field($_POST['codepeople_promote_banner_plugin']), -1, 0);
28
+ if(
29
+ !empty($_POST['codepeople_promote_banner_action']) &&
30
+ $_POST['codepeople_promote_banner_action'] == 'set-review' &&
31
+ !empty($codepeople_promote_banner_plugins[$_POST['codepeople_promote_banner_plugin']]['plugin_url'])
32
+ )
33
+ {
34
+ print '<script>document.location.href="'.str_replace('&amp;', '&', esc_js($codepeople_promote_banner_plugins[$_POST['codepeople_promote_banner_plugin']]['plugin_url'])).'";</script>';
35
+ }
36
+ }
37
+ }
38
+
39
+ $minimum_days = 86400*7;
40
+ $now = time();
41
+
42
+ foreach($codepeople_promote_banner_plugins as $plugin_slug => $plugin_data )
43
+ {
44
+ $value = get_transient( 'codepeople_promote_banner_'.$plugin_slug );
45
+ if( $value === false )
46
+ {
47
+ $value = $now;
48
+ set_transient( 'codepeople_promote_banner_'.$plugin_slug, $value, 0 );
49
+ }
50
+
51
+ if($minimum_days <= abs($now-$value) && 0<$value*1)
52
+ {
53
+ ?>
54
+ <style>
55
+ #codepeople-review-banner{width:calc( 100% - 20px );width:-webkit-calc( 100% - 20px );width:-moz-calc( 100% - 20px );width:-o-calc( 100% - 20px );border:10px solid #1582AB;background:#FFF;display:table;}
56
+ #codepeople-review-banner form{float:left; padding:0 5px;}
57
+ #codepeople-review-banner .codepeople-review-banner-picture{width:120px;padding:10px 10px 10px 10px;float:left;text-align:center;}
58
+ #codepeople-review-banner .codepeople-review-banner-content{float: left;padding:10px;width: calc( 100% - 160px );width: -webkit-calc( 100% - 160px );width: -moz-calc( 100% - 160px );width: -o-calc( 100% - 160px );}
59
+ #codepeople-review-banner .codepeople-review-banner-buttons{padding-top:20px;}
60
+ #codepeople-review-banner .no-thank-button,
61
+ #codepeople-review-banner .main-button{height: 28px;border-width:1px;border-style:solid;border-radius:5px;text-decoration: none;}
62
+ #codepeople-review-banner .main-button{background: #0085ba;border-color: #0073aa #006799 #006799;-webkit-box-shadow: 0 1px 0 #006799;box-shadow: 0 1px 0 #006799;color: #fff;text-decoration: none;text-shadow: 0 -1px 1px #006799,1px 0 1px #006799,0 1px 1px #006799,-1px 0 1px #006799;}
63
+ #codepeople-review-banner .no-thank-button {color: #555;border-color: #cccccc;background: #f7f7f7;-webkit-box-shadow: 0 1px 0 #cccccc;box-shadow: 0 1px 0 #cccccc;vertical-align: top;}
64
+ #codepeople-review-banner .main-button:hover,#codepeople-review-banner .main-button:focus{background: #008ec2;border-color: #006799;color: #fff;}
65
+ #codepeople-review-banner .no-thank-button:hover,
66
+ #codepeople-review-banner .no-thank-button:focus{background: #fafafa;border-color: #999;color: #23282d;}
67
+ @media screen AND (max-width:760px)
68
+ {
69
+ #codepeople-review-banner{position:relative;top:50px;}
70
+ #codepeople-review-banner .codepeople-review-banner-picture{display:none;}
71
+ #codepeople-review-banner .codepeople-review-banner-content{width:calc( 100% - 20px );width:-webkit-calc( 100% - 20px );width:-moz-calc( 100% - 20px );width:-o-calc( 100% - 20px );}
72
+ }
73
+ </style>
74
+ <div id="codepeople-review-banner">
75
+ <div class="codepeople-review-banner-picture">
76
+ <img alt="" src="https://secure.gravatar.com/avatar/c0662edcefb5a4e2ab12803856ba2358?s=150&amp;d=mm&amp;r=g" style="width:80px;">
77
+ </div>
78
+ <div class="codepeople-review-banner-content">
79
+ <div class="codepeople-review-banner-text">
80
+ <p><strong>Want to help to the development of the "<?php print $plugin_data[ 'plugin_name' ]; ?>" plugin?</strong> The main features of this plugin are provided free of charge. We need your help to continue developing it and adding new features. If you want to help with the development please <span style="color:#1582AB;font-weight:bold;">add a review to support it</span>. Thank you!</p>
81
+ </div>
82
+ <div class="codepeople-review-banner-buttons">
83
+ <form method="post" target="_blank">
84
+ <button class="main-button" onclick="jQuery(this).closest('[id=\'codepeople-review-banner\']').hide();">Publish a Review</button>
85
+ <input type="hidden" name="codepeople_promote_banner_plugin" value="<?php echo esc_attr($plugin_slug); ?>" />
86
+ <input type="hidden" name="codepeople_promote_banner_action" value="set-review" />
87
+ <input type="hidden" name="codepeople_promote_banner_nonce" value="<?php echo wp_create_nonce(__FILE__); ?>" />
88
+ </form>
89
+ <form method="post">
90
+ <button class="no-thank-button">No Thanks</button>
91
+ <input type="hidden" name="codepeople_promote_banner_plugin" value="<?php echo esc_attr($plugin_slug); ?>" />
92
+ <input type="hidden" name="codepeople_promote_banner_action" value="not-thanks" />
93
+ <input type="hidden" name="codepeople_promote_banner_nonce" value="<?php echo wp_create_nonce(__FILE__); ?>" />
94
+ </form>
95
+ <div style="clear:both;display:block;"></div>
96
+ </div>
97
+ <div style="clear:both;"></div>
98
+ </div>
99
+ <div style="clear:both;"></div>
100
+ </div>
101
+ <?php
102
+ return;
103
+ }
104
+ }
105
+ }
106
+ add_action( 'admin_bar_menu', 'codepeople_add_promote_banner' );
107
+ } // End codepeople_promote_banner block
108
+ ?>
css/style.admin.css ADDED
@@ -0,0 +1,8 @@
 
 
 
 
 
 
 
 
1
+ .wcmp-file-name,.wcmp-file-url{width:100% !important;}
2
+ #wcmp_woocommerce_metabox .widefat{border:0;}
3
+ .wcmp-tooltip{position:relative;display:inline-block;}
4
+ .wcmp-tooltip .wcmp-tooltiptext{visibility:hidden;width:240px;background-color:#555;color:#fff;text-align:center;padding:5px;border-radius:6px;position:absolute;z-index:9999;bottom:125%;left:50%;margin-left:-120px;opacity:0;transition:opacity 1s;}
5
+ .wcmp-tooltip .wcmp-tooltiptext::after{content:"";position:absolute;top:100%;left:50%;margin-left:-10px;border-width:5px;border-style:solid;border-color:#555 transparent transparent transparent;}
6
+ .wcmp-tooltip:hover .wcmp-tooltiptext{visibility:visible;opacity:1;}
7
+ .wcmp-highlight-box{border:1px solid #E6DB55;margin-bottom:10px;padding:5px;background-color: #FFFFE0;}
8
+ #wcmp_tips_body,.wcmp-tip-text{display:none;}
css/style.css ADDED
@@ -0,0 +1,31 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ .wcmp-player{width:100% !important;}
2
+ .wcmp-player.track.mejs-wmp .mejs-controls .mejs-playpause-button button {width: 36px;height: 36px;background-position: -2px -2px;border-radius: 50%;}
3
+ .wcmp-player.track.mejs-wmp .mejs-controls .mejs-pause button{background-position:-2px -42px;}
4
+ .wcmp-player.mejs-wmp:not(.track),
5
+ .wcmp-player.mejs-ted:not(.track){min-height:65px !important;}
6
+ .wcmp-player.mejs-container{background: transparent !important;}
7
+ .wcmp-player.track{width:25px !important;height:30px !important;position:relative;float:left;margin-right:5px;overflow:hidden;}
8
+ .wcmp-player.track.mejs-ted{width:49px !important;height:28px !important;border-radius:16%;}
9
+ .wcmp-player.track.mejs-ted .mejs-controls{height:28px !important; background:transparent !important;}
10
+ .wcmp-player.track.mejs-wmp .mejs-playpause-button,
11
+ .wcmp-player.track.mejs-ted .mejs-playpause-button{top:0 !important;left:0 !important; margin: 0 !important;}
12
+
13
+ .wcmp-player.track.mejs-wmp{width:40px !important;height:40px !important;}
14
+ .wcmp-player.track.mejs-wmp .mejs-controls{height:40px !important; width:40px !important; background:transparent !important;}
15
+
16
+ .wcmp-player-list{width:100%; border:0;}
17
+ .wcmp-player-list *{word-break:normal !important;}
18
+ .wcmp-player-list td{border:0;padding:5px;}
19
+ .wcmp-player-list table{width:100%;margin:0;}
20
+ .wcmp-player-list table td{border:0;}
21
+ .wcmp-odd-row td,
22
+ .wcmp-even-row td{padding:5px;vertical-align:middle;}
23
+ .wcmp-odd-row td{background-color:#FAFAFA; border-top: 1px solid #DADADA; border-bottom: 1px solid #DADADA;}
24
+ .wcmp-column-player-title{/* width:100%; */ vertical-align:middle;}
25
+ .wcmp-column-player-mejs-classic{width:30px; min-height:30px;}
26
+ .wcmp-column-player-mejs-ted{width:54px; min-height:28px;}
27
+ .wcmp-column-player-mejs-wmp{width:45px; min-height:40px;}
28
+ .wcmp-message{font-style:italic;}
29
+ .mejs-controls{/* overflow:hidden !important; */}
30
+ .wcmp-player .mejs-controls .mejs-time-rail .mejs-time-float{border:0;}
31
+ .wcmp-player-container * {transform: none;}
js/public.js ADDED
@@ -0,0 +1,11 @@
 
 
 
 
 
 
 
 
 
 
 
1
+ var $jscomp=$jscomp||{};$jscomp.scope={};$jscomp.findInternal=function(a,c,b){a instanceof String&&(a=String(a));for(var f=a.length,g=0;g<f;g++){var d=a[g];if(c.call(b,d,g,a))return{i:g,v:d}}return{i:-1,v:void 0}};$jscomp.ASSUME_ES5=!1;$jscomp.ASSUME_NO_NATIVE_MAP=!1;$jscomp.ASSUME_NO_NATIVE_SET=!1;$jscomp.SIMPLE_FROUND_POLYFILL=!1;
2
+ $jscomp.defineProperty=$jscomp.ASSUME_ES5||"function"==typeof Object.defineProperties?Object.defineProperty:function(a,c,b){a!=Array.prototype&&a!=Object.prototype&&(a[c]=b.value)};$jscomp.getGlobal=function(a){return"undefined"!=typeof window&&window===a?a:"undefined"!=typeof global&&null!=global?global:a};$jscomp.global=$jscomp.getGlobal(this);
3
+ $jscomp.polyfill=function(a,c,b,f){if(c){b=$jscomp.global;a=a.split(".");for(f=0;f<a.length-1;f++){var g=a[f];g in b||(b[g]={});b=b[g]}a=a[a.length-1];f=b[a];c=c(f);c!=f&&null!=c&&$jscomp.defineProperty(b,a,{configurable:!0,writable:!0,value:c})}};$jscomp.polyfill("Array.prototype.find",function(a){return a?a:function(a,b){return $jscomp.findInternal(this,a,b).v}},"es6","es3");
4
+ (function(){var a=[],c=0;window.generate_the_wcmp=function(b){function f(e){if(e+1<c){var h=e+1;a[h]instanceof d&&a[h].is("a")?a[h].is(":visible")?a[h].click():f(e+1):d(a[h].container).is(":visible")?a[h].play():f(e+1)}}function g(a){var e=a.data("product"),b=d("img.product-"+e);b.length&&1==d('[data-product="'+e+'"]').length&&(e=b.offset(),a=a.closest("div.wcmp-player"),a.css({position:"absolute","z-index":999999}).offset({left:e.left+(b.width()-a.width())/2,top:e.top+(b.height()-a.height())/2}))}
5
+ if(!("boolean"!==typeof b&&"undefined"!=typeof wcmp_global_settings&&1*wcmp_global_settings.onload)&&"undefined"===typeof generated_the_wcmp){generated_the_wcmp=!0;var d=jQuery;d(document).on("click",".wcmp-player-container",function(a){a.preventDefault();a.stopPropagation()});d.expr[":"].regex=function(a,b,c){b=c[3].split(",");var e=/^(data|css):/;c=b[0].match(e)?b[0].split(":")[0]:"attr";e=b.shift().replace(e,"");return(new RegExp(b.join("").replace(/^\s+|\s+$/g,""),"ig")).test(d(a)[c](e))};var m=
6
+ "undefined"!=typeof wcmp_global_settings?wcmp_global_settings.play_all:!0;b=d("audio.wcmp-player:not(.track):not([playernumber])");var n=d("audio.wcmp-player.track:not([playernumber])"),k={iPadUseNativeControls:!1,iPhoneUseNativeControls:!1,success:function(a,b){var e=function(a){a=d(a.target);var b=a.data("duration");"undefined"!=typeof b&&a.closest(".wcmp-player-container").find(".mejs-duration").html(b)};a.addEventListener("timeupdate",function(a){e(a);isNaN(this.currentTime)||isNaN(this.duration)||
7
+ -1==this.src.indexOf("ms-action=secure")||(4>this.duration-this.currentTime?this.setVolume(this.volume-this.volume/3):("undefined"==typeof this.bkVolume&&(this.bkVolume=this.volume),this.setVolume(this.bkVolume)))});a.addEventListener("volumechange",function(a){!isNaN(this.currentTime)&&!isNaN(this.duration)&&-1!=this.src.indexOf("ms-action=secure")&&4<this.duration-this.currentTime&&this.currentTime&&(this.bkVolume=this.volume)});a.addEventListener("ended",function(a){1*m&&(a=1*d(this).attr("playernumber"),
8
+ f(a))});a.addEventListener("loadedmetadata",function(a){e(a)})}},l=".product-type-grouped :regex(name,quantity\\[\\d+\\])";b.each(function(){var b=d(this);b.find("source").attr("src");k.audioVolume="vertical";try{a[c]=new MediaElementPlayer(b,k)}catch(h){a[c]=new MediaElementPlayer(b[0],k)}b.attr("playernumber",c);c++});n.each(function(){var b=d(this);b.find("source").attr("src");k.features=["playpause"];try{a[c]=new MediaElementPlayer(b,k)}catch(h){a[c]=new MediaElementPlayer(b[0],k)}b.attr("playernumber",
9
+ c);c++;g(b);d(window).resize(function(){g(b)})});d(l).length||(l=".product-type-grouped [data-product_id]");d(l).each(function(){var a=d(this),b=a.data("product_id")||a.attr("name").replace(/[^\d]/g,"");b=d(".wcmp-player-list.merge_in_grouped_products .product-"+b+":first .wcmp-player-title");var c=d("<table></table>");b.length&&(b.closest("tr").addClass("wcmp-first-in-product"),0==b.closest("form").length&&b.closest(".wcmp-player-list").prependTo(a.closest("form")),c.append(a.closest("tr").prepend("<td>"+
10
+ b.html()+"</td>")),b.html("").append(c))})}};window.wcmp_force_init=function(){delete window.generated_the_wcmp;generate_the_wcmp(!0)};jQuery(generate_the_wcmp);jQuery(window).on("load",function(){generate_the_wcmp(!0);var a=jQuery,c=window.navigator.userAgent;a("[data-lazyloading]").each(function(){var b=a(this);b.attr("preload",b.data("lazyloading"))});if(c.match(/iPad/i)||c.match(/iPhone/i))if("undefined"!=typeof wcmp_global_settings?wcmp_global_settings.play_all:1)a(".wcmp-player .mejs-play button").one("click",
11
+ function(){if("undefined"==typeof wcmp_preprocessed_players){wcmp_preprocessed_players=!0;var b=a(this);a(".wcmp-player audio").each(function(){this.play();this.pause()});setTimeout(function(){b.click()},500)}})}).on("popstate",function(){jQuery("audio[data-product]:not([playernumber])").length&&wcmp_force_init()})})();
js/public_src.js ADDED
@@ -0,0 +1,218 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ (function(){
2
+ var wcmp_players = [],
3
+ wcmp_player_counter = 0;
4
+
5
+ window['generate_the_wcmp'] = function(isOnLoadEvent)
6
+ {
7
+ if(
8
+ typeof isOnLoadEvent !== 'boolean' &&
9
+ typeof wcmp_global_settings != 'undefined' &&
10
+ wcmp_global_settings['onload']*1
11
+ ) return;
12
+
13
+ if('undefined' !== typeof generated_the_wcmp) return;
14
+ generated_the_wcmp = true;
15
+
16
+ var $ = jQuery;
17
+ $(document).on('click', '.wcmp-player-container', function(evt){evt.preventDefault();evt.stopPropagation();});
18
+
19
+ /**
20
+ * Play next player
21
+ */
22
+ function _playNext( playernumber )
23
+ {
24
+ if( playernumber+1 < wcmp_player_counter )
25
+ {
26
+ var toPlay = playernumber+1;
27
+ if( wcmp_players[ toPlay ] instanceof $ && wcmp_players[ toPlay ].is( 'a' ) ){
28
+ if(wcmp_players[ toPlay ].is(':visible')) wcmp_players[ toPlay ].click();
29
+ else _playNext(playernumber+1);
30
+ }
31
+ else
32
+ {
33
+ if($(wcmp_players[ toPlay ].container).is(':visible')) wcmp_players[ toPlay ].play();
34
+ else _playNext(playernumber+1);
35
+ }
36
+ }
37
+ };
38
+
39
+ function _setOverImage(p)
40
+ {
41
+ var i = p.data('product'),
42
+ t = $('img.product-'+i);
43
+
44
+ if(t.length && $('[data-product="'+i+'"]').length == 1)
45
+ {
46
+ var o = t.offset(),
47
+ c = p.closest('div.wcmp-player');
48
+
49
+ c.css({'position': 'absolute', 'z-index': 999999})
50
+ .offset({'left': o.left+(t.width()-c.width())/2, 'top': o.top+(t.height()-c.height())/2});
51
+ }
52
+ };
53
+
54
+ $.expr[':'].regex = function(elem, index, match) {
55
+ var matchParams = match[3].split(','),
56
+ validLabels = /^(data|css):/,
57
+ attr = {
58
+ method: matchParams[0].match(validLabels) ?
59
+ matchParams[0].split(':')[0] : 'attr',
60
+ property: matchParams.shift().replace(validLabels,'')
61
+ },
62
+ regexFlags = 'ig',
63
+ regex = new RegExp(matchParams.join('').replace(/^\s+|\s+$/g,''), regexFlags);
64
+ return regex.test($(elem)[attr.method](attr.property));
65
+ }
66
+
67
+ //------------------------ MAIN CODE ------------------------
68
+ var play_all = (typeof wcmp_global_settings != 'undefined') ? wcmp_global_settings[ 'play_all' ] : true, // Play all songs on page
69
+ s = $('audio.wcmp-player:not(.track):not([playernumber])'),
70
+ m = $('audio.wcmp-player.track:not([playernumber])'),
71
+ c = {
72
+ iPadUseNativeControls: false,
73
+ iPhoneUseNativeControls: false,
74
+ success: function( media, dom ){
75
+ var update_duration = function(e){
76
+ var t = $(e.target),
77
+ duration = t.data('duration');
78
+ if(typeof duration != 'undefined')
79
+ {
80
+ t.closest('.wcmp-player-container')
81
+ .find('.mejs-duration')
82
+ .html(duration);
83
+ }
84
+ };
85
+
86
+ media.addEventListener( 'timeupdate', function( e ){
87
+ update_duration(e);
88
+ if( !isNaN( this.currentTime ) && !isNaN( this.duration ) && this.src.indexOf( 'ms-action=secure' ) != -1 )
89
+ {
90
+ if( this.duration - this.currentTime < 4 )
91
+ {
92
+ this.setVolume( this.volume - this.volume / 3 );
93
+ }
94
+ else
95
+ {
96
+ if( typeof this[ 'bkVolume' ] == 'undefined' ) this[ 'bkVolume' ] = this.volume;
97
+ this.setVolume( this.bkVolume );
98
+ }
99
+
100
+ }
101
+ });
102
+
103
+ media.addEventListener( 'volumechange', function( e ){
104
+ if( !isNaN( this.currentTime ) && !isNaN( this.duration ) && this.src.indexOf( 'ms-action=secure' ) != -1 )
105
+ {
106
+ if( ( this.duration - this.currentTime > 4 ) && this.currentTime ) this[ 'bkVolume' ] = this.volume;
107
+ }
108
+ });
109
+
110
+ media.addEventListener( 'ended', function( e ){
111
+ if( play_all*1 )
112
+ {
113
+ var playernumber = $(this).attr('playernumber')*1;
114
+ _playNext( playernumber );
115
+ }
116
+ });
117
+
118
+ media.addEventListener('loadedmetadata', function( e ){
119
+ update_duration(e);
120
+ });
121
+ }
122
+ },
123
+ selector = '.product-type-grouped :regex(name,quantity\\[\\d+\\])';
124
+ s.each(function(){
125
+ var e = $(this),
126
+ src = e.find( 'source' ).attr( 'src' );
127
+
128
+ c['audioVolume'] = 'vertical';
129
+ try{
130
+ wcmp_players[ wcmp_player_counter ] = new MediaElementPlayer(e, c);
131
+ }
132
+ catch(err)
133
+ {
134
+ wcmp_players[ wcmp_player_counter ] = new MediaElementPlayer(e[0], c);
135
+ }
136
+ e.attr('playernumber', wcmp_player_counter);
137
+ wcmp_player_counter++;
138
+
139
+ /* _setOverImage(e); */
140
+ });
141
+
142
+
143
+ m.each(function(){
144
+ var e = $(this),
145
+ src = e.find( 'source' ).attr( 'src' );
146
+
147
+ c['features'] = ['playpause'];
148
+ try{
149
+ wcmp_players[ wcmp_player_counter ] = new MediaElementPlayer(e, c);
150
+ }
151
+ catch(err)
152
+ {
153
+ wcmp_players[ wcmp_player_counter ] = new MediaElementPlayer(e[0], c);
154
+ }
155
+ e.attr('playernumber', wcmp_player_counter);
156
+ wcmp_player_counter++;
157
+
158
+ _setOverImage(e);
159
+ $(window).resize(function(){_setOverImage(e);});
160
+ });
161
+
162
+ if(!$(selector).length) selector = '.product-type-grouped [data-product_id]';
163
+ $(selector).each(function(){
164
+ var e = $(this),
165
+ i = e.data( 'product_id' )||e.attr('name').replace(/[^\d]/g,''),
166
+ c = $( '.wcmp-player-list.merge_in_grouped_products .product-'+i+':first .wcmp-player-title' ), /* Replaced :last with :first 2018.06.12 */
167
+ t = $('<table></table>');
168
+
169
+ if(c.length)
170
+ {
171
+ c.closest('tr').addClass('wcmp-first-in-product'); /* To identify the firs element in the product */
172
+ if(c.closest('form').length == 0)
173
+ {
174
+ c.closest('.wcmp-player-list').prependTo(e.closest('form'));
175
+ }
176
+ t.append(e.closest('tr').prepend('<td>'+c.html()+'</td>'));
177
+ c.html('').append(t);
178
+ }
179
+ });
180
+ }
181
+
182
+ window['wcmp_force_init'] = function()
183
+ {
184
+ delete window.generated_the_wcmp;
185
+ generate_the_wcmp(true);
186
+ }
187
+
188
+ jQuery(generate_the_wcmp);
189
+ jQuery(window).on('load', function(){
190
+ generate_the_wcmp(true);
191
+ var $ = jQuery,
192
+ ua = window.navigator.userAgent;
193
+
194
+ $('[data-lazyloading]').each(function(){ var e = $(this); e.attr('preload', e.data('lazyloading'));});
195
+ if(ua.match(/iPad/i) || ua.match(/iPhone/i))
196
+ {
197
+ var p = (typeof wcmp_global_settings != 'undefined') ? wcmp_global_settings[ 'play_all' ] : true;
198
+ if(p) // Solution to the play all in Safari iOS
199
+ {
200
+ $('.wcmp-player .mejs-play button').one('click', function(){
201
+
202
+ if('undefined' != typeof wcmp_preprocessed_players) return;
203
+ wcmp_preprocessed_players = true;
204
+
205
+ var e = $(this);
206
+ $('.wcmp-player audio').each(function(){
207
+ this.play();
208
+ this.pause();
209
+ });
210
+ setTimeout(function(){e.click();}, 500);
211
+ });
212
+ }
213
+ }
214
+ }).on('popstate', function(){
215
+ if(jQuery('audio[data-product]:not([playernumber])').length) wcmp_force_init();
216
+ });
217
+
218
+ })()
languages/music-player-for-woocommerce-en_US.mo ADDED
Binary file
languages/music-player-for-woocommerce-en_US.po ADDED
@@ -0,0 +1,580 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ msgid ""
2
+ msgstr ""
3
+ "Project-Id-Version: music-player-for-woocommerce\n"
4
+ "POT-Creation-Date: 2020-06-04 02:57+0200\n"
5
+ "PO-Revision-Date: 2020-06-04 02:57+0200\n"
6
+ "Last-Translator: CodePeople\n"
7
+ "Language-Team: CodePeople\n"
8
+ "Language: en_US\n"
9
+ "MIME-Version: 1.0\n"
10
+ "Content-Type: text/plain; charset=UTF-8\n"
11
+ "Content-Transfer-Encoding: 8bit\n"
12
+ "X-Generator: Poedit 2.3.1\n"
13
+ "X-Poedit-Basepath: ..\n"
14
+ "Plural-Forms: nplurals=2; plural=(n != 1);\n"
15
+ "X-Poedit-KeywordsList: __;_e;esc_attr__;esc_attr_e\n"
16
+ "X-Poedit-SearchPath-0: .\n"
17
+
18
+ #: addons/dokan/player_options.php:9 views/player_options.php:299
19
+ msgid "File Name"
20
+ msgstr ""
21
+
22
+ #: addons/dokan/player_options.php:10 views/player_options.php:305
23
+ msgid "Choose file"
24
+ msgstr ""
25
+
26
+ #: addons/dokan/player_options.php:11 views/player_options.php:308
27
+ msgid "Delete"
28
+ msgstr ""
29
+
30
+ #: addons/dokan/player_options.php:12
31
+ msgid "Select audio file"
32
+ msgstr ""
33
+
34
+ #: addons/dokan/player_options.php:13
35
+ msgid "Select Item"
36
+ msgstr ""
37
+
38
+ #: addons/dokan/player_options.php:48
39
+ msgid "Music Player Settings"
40
+ msgstr ""
41
+
42
+ #: addons/dokan/player_options.php:53
43
+ msgid "<p>The player uses the audio files associated to the product.</b></p>"
44
+ msgstr ""
45
+
46
+ #: addons/dokan/player_options.php:61 views/player_options.php:53
47
+ msgid "[+|-] Tips"
48
+ msgstr ""
49
+
50
+ #: addons/dokan/player_options.php:67 views/player_options.php:59
51
+ msgid "[+|-] Using the audio files stored on Google Drive"
52
+ msgstr ""
53
+
54
+ #: addons/dokan/player_options.php:75 views/player_options.php:67
55
+ msgid ""
56
+ "Go to Drive, press the right click on the file to use, and select the "
57
+ "option: <b>\"Get Shareable Link\"</b>"
58
+ msgstr ""
59
+
60
+ #: addons/dokan/player_options.php:83 views/player_options.php:75
61
+ msgid ""
62
+ "The previous action will generate an url with the structure: <b>https://"
63
+ "drive.google.com/open?id=FILE_ID</b>"
64
+ msgstr ""
65
+
66
+ #: addons/dokan/player_options.php:93 views/player_options.php:85
67
+ msgid ""
68
+ "Knowing the FILE_ID, extracted from the previous URL, enter the URL below, "
69
+ "into the WooCommerce product, to allow the Music Player accessing to it:"
70
+ msgstr ""
71
+
72
+ #: addons/dokan/player_options.php:104 views/player_options.php:96
73
+ msgid ""
74
+ "<b>Note:</b> Pay attention to the use of the fake parameter: <b>&.mp3</b> as "
75
+ "the last one in the URL"
76
+ msgstr ""
77
+
78
+ #: addons/dokan/player_options.php:114 views/player_options.php:106
79
+ msgid "[+|-] Using the audio files stored on DropBox"
80
+ msgstr ""
81
+
82
+ #: addons/dokan/player_options.php:122 views/player_options.php:114
83
+ msgid ""
84
+ "Sign in to <a href=\"https://www.dropbox.com/login\" target=\"_blank"
85
+ "\">dropbox.com </a>"
86
+ msgstr ""
87
+
88
+ #: addons/dokan/player_options.php:132 views/player_options.php:124
89
+ msgid ""
90
+ "Hover your cursor over the file or folder you'd like to share and click "
91
+ "<b>Share</b> when it appears."
92
+ msgstr ""
93
+
94
+ #: addons/dokan/player_options.php:142 views/player_options.php:134
95
+ msgid ""
96
+ "If a link hasn't been created, click Create a link. (If a link was already "
97
+ "created, click Copy link."
98
+ msgstr ""
99
+
100
+ #: addons/dokan/player_options.php:150 views/player_options.php:142
101
+ msgid ""
102
+ "The link structure would be similar to:<br> https://www.dropbox.com/s/"
103
+ "rycvgn8iokfedmo/file.mp3?dl=0"
104
+ msgstr ""
105
+
106
+ #: addons/dokan/player_options.php:160 views/player_options.php:152
107
+ msgid ""
108
+ "Enter the URL into the WooCommerce product with the following structure:<br> "
109
+ "https://www.dropbox.com/s/rycvgn8iokfedmo/file.mp3?dl=1&.mp3"
110
+ msgstr ""
111
+
112
+ #: addons/dokan/player_options.php:168 views/player_options.php:160
113
+ msgid ""
114
+ "<b>Note:</b> Pay attention to the use of the fake parameter: <b>&.mp3</b> as "
115
+ "the last one in the URL. Furthermore, the parameter <b>dl=0</b>, has been "
116
+ "modified as <b>dl=1</b>"
117
+ msgstr ""
118
+
119
+ #: addons/dokan/player_options.php:181 views/global_options.php:213
120
+ msgid ""
121
+ "The player is shown only if the product is \"downloadable\" with at least an "
122
+ "audio file between the \"Downloadable files\", or you have selected your own "
123
+ "audio files"
124
+ msgstr ""
125
+
126
+ #: addons/dokan/player_options.php:181 views/player_options.php:176
127
+ msgid "Include music player"
128
+ msgstr ""
129
+
130
+ #: addons/dokan/player_options.php:185 views/global_options.php:216
131
+ #: views/player_options.php:180
132
+ msgid "Include in"
133
+ msgstr ""
134
+
135
+ #: addons/dokan/player_options.php:188 views/global_options.php:219
136
+ #: views/player_options.php:183
137
+ msgid "single-entry pages <i>(Product's page only)</i>"
138
+ msgstr ""
139
+
140
+ #: addons/dokan/player_options.php:191 views/global_options.php:222
141
+ #: views/player_options.php:186
142
+ msgid ""
143
+ "multiple entries pages <i>(Shop pages, archive pages, but not in the "
144
+ "product's page)</i>"
145
+ msgstr ""
146
+
147
+ #: addons/dokan/player_options.php:194 views/global_options.php:225
148
+ #: views/player_options.php:189
149
+ msgid "all pages <i>(with single or multiple-entries)</i>"
150
+ msgstr ""
151
+
152
+ #: addons/dokan/player_options.php:198 views/global_options.php:235
153
+ #: views/player_options.php:193
154
+ msgid "Merge in grouped products"
155
+ msgstr ""
156
+
157
+ #: addons/dokan/player_options.php:200 views/global_options.php:236
158
+ #: views/player_options.php:194
159
+ msgid ""
160
+ "In grouped products, display the \"Add to cart\" buttons and quantity fields "
161
+ "in the players rows"
162
+ msgstr ""
163
+
164
+ #: addons/dokan/player_options.php:203 views/global_options.php:239
165
+ #: views/player_options.php:197 widgets/playlist_widget.php:71
166
+ msgid "Player layout"
167
+ msgstr ""
168
+
169
+ #: addons/dokan/player_options.php:222 views/global_options.php:261
170
+ #: views/player_options.php:219 widgets/playlist_widget.php:87
171
+ msgid "Preload"
172
+ msgstr ""
173
+
174
+ #: addons/dokan/player_options.php:230 views/global_options.php:271
175
+ #: views/player_options.php:229 widgets/playlist_widget.php:83
176
+ msgid "Play all"
177
+ msgstr ""
178
+
179
+ #: addons/dokan/player_options.php:233 views/global_options.php:278
180
+ #: views/player_options.php:236
181
+ msgid "Player controls"
182
+ msgstr ""
183
+
184
+ #: addons/dokan/player_options.php:235 views/global_options.php:280
185
+ #: views/player_options.php:238
186
+ msgid "the play/pause button only"
187
+ msgstr ""
188
+
189
+ #: addons/dokan/player_options.php:236 views/global_options.php:281
190
+ #: views/player_options.php:239
191
+ msgid "all controls"
192
+ msgstr ""
193
+
194
+ #: addons/dokan/player_options.php:237 views/global_options.php:282
195
+ #: views/player_options.php:240
196
+ msgid "the play/pause button only, or all controls depending on context"
197
+ msgstr ""
198
+
199
+ #: addons/dokan/player_options.php:241 views/global_options.php:287
200
+ #: views/player_options.php:245
201
+ msgid "for play/pause button players display them on cover images."
202
+ msgstr ""
203
+
204
+ #: addons/dokan/player_options.php:242 views/global_options.php:290
205
+ #: views/player_options.php:248
206
+ msgid ""
207
+ "(This feature is experimental, and will depend on the theme active on the "
208
+ "website.)"
209
+ msgstr ""
210
+
211
+ #: addons/dokan/player_options.php:247 views/global_options.php:297
212
+ #: views/player_options.php:255
213
+ msgid "Display the player's title"
214
+ msgstr ""
215
+
216
+ #: pagebuilders/beaverbuilder/wcmp.inc.php:8
217
+ msgid "Enter the products ids and the rest of shortcode attributes"
218
+ msgstr ""
219
+
220
+ #: pagebuilders/beaverbuilder/wcmp.inc.php:11
221
+ msgid "Playlist Shortcode"
222
+ msgstr ""
223
+
224
+ #: pagebuilders/beaverbuilder/wcmp.inc.php:15
225
+ msgid "Products ids separated by comma (* represents all products)"
226
+ msgstr ""
227
+
228
+ #: pagebuilders/beaverbuilder/wcmp.inc.php:19
229
+ msgid "Additional attributes"
230
+ msgstr ""
231
+
232
+ #: pagebuilders/beaverbuilder/wcmp/wcmp.pb.php:9
233
+ #: pagebuilders/beaverbuilder/wcmp/wcmp.pb.php:11
234
+ #: pagebuilders/beaverbuilder/wcmp/wcmp.pb.php:12 pagebuilders/builders.php:130
235
+ #: pagebuilders/siteorigin/siteorigin-wcmp/siteorigin-wcmp.php:17 wcmp.php:214
236
+ msgid "Music Player for WooCommerce"
237
+ msgstr ""
238
+
239
+ #: pagebuilders/beaverbuilder/wcmp/wcmp.pb.php:10
240
+ msgid "Insert the playlist shortcode"
241
+ msgstr ""
242
+
243
+ #: pagebuilders/elementor/elementor.pb.php:42
244
+ #: pagebuilders/elementor/elementor.pb.php:49
245
+ msgid "Music Player For WooCommerce"
246
+ msgstr ""
247
+
248
+ #: pagebuilders/elementor/elementor.pb.php:52
249
+ #: pagebuilders/siteorigin/siteorigin-wcmp/siteorigin-wcmp.php:27
250
+ msgid ""
251
+ "To include specific products in the playlist enter their IDs in the "
252
+ "products_ids attributes, separated by comma symbols (,)"
253
+ msgstr ""
254
+
255
+ #: pagebuilders/elementor/elementor.pb.php:52
256
+ msgid "More information visiting the follwing link: "
257
+ msgstr ""
258
+
259
+ #: pagebuilders/elementor/elementor.pb.php:52
260
+ msgid "CLICK HERE"
261
+ msgstr ""
262
+
263
+ #: pagebuilders/siteorigin/siteorigin-wcmp/siteorigin-wcmp.php:19
264
+ msgid "Insert a playlist with the products players"
265
+ msgstr ""
266
+
267
+ #: views/global_options.php:34
268
+ msgid "Music Player for WooCommerce - Global Settings"
269
+ msgstr ""
270
+
271
+ #: views/global_options.php:38
272
+ msgid ""
273
+ "For reporting any issue or to request a customization, <a href=\"https://"
274
+ "wordpress.dwbooster.com/contact-us\" target=\"_blank\">CLICK HERE</a><br />\n"
275
+ "\tFor testing the premium version of the plugin, visit the online demo:<br/> "
276
+ "<a href=\"https://demos.dwbooster.com/music-player-for-woocommerce/wp-login."
277
+ "php\" target=\"_blank\">Administration area: Click to access the "
278
+ "administration area demo</a><br/>\n"
279
+ "\t<a href=\"https://demos.dwbooster.com/music-player-for-woocommerce/\" "
280
+ "target=\"_blank\">Public page: Click to visit the WooCommerce Store</a>"
281
+ msgstr ""
282
+
283
+ #: views/global_options.php:47
284
+ msgid "Registering of Plugin"
285
+ msgstr ""
286
+
287
+ #: views/global_options.php:49
288
+ msgid "Enter the email address of buyer"
289
+ msgstr ""
290
+
291
+ #: views/global_options.php:50
292
+ msgid "Register"
293
+ msgstr ""
294
+
295
+ #: views/global_options.php:62 views/player_options.php:43
296
+ msgid ""
297
+ "<p>The player uses the audio files associated to the product. If you want "
298
+ "protecting the audio files for selling, tick the checkbox: <b>\"Protect the "
299
+ "file\"</b>, in whose case the plugin will create a truncated version of the "
300
+ "audio files for selling to be used for demo. The size of audio files for "
301
+ "demo is based on the number entered through the attribute: <b>\"Percent of "
302
+ "audio used for protected playbacks\"</b>.</p><p><b>Protecting the files "
303
+ "prevents that malicious users can access to the original audio files without "
304
+ "pay for them.</b></p>"
305
+ msgstr ""
306
+
307
+ #: views/global_options.php:73
308
+ msgid "General Settings"
309
+ msgstr ""
310
+
311
+ #: views/global_options.php:76
312
+ msgid "Include the players only for registered users"
313
+ msgstr ""
314
+
315
+ #: views/global_options.php:80
316
+ msgid "The general settings affect only the PRO version of the plugin"
317
+ msgstr ""
318
+
319
+ #: views/global_options.php:80 views/global_options.php:303
320
+ #: views/player_options.php:47 views/player_options.php:261
321
+ msgid "CLICK HERE TO GET THE PRO VERSION OF THE PLUGIN"
322
+ msgstr ""
323
+
324
+ #: views/global_options.php:83
325
+ msgid ""
326
+ "For buyers, play the purchased audio files instead the truncated files for "
327
+ "demo"
328
+ msgstr ""
329
+
330
+ #: views/global_options.php:90
331
+ msgid "Truncate the audio files for demo with ffmpeg"
332
+ msgstr ""
333
+
334
+ #: views/global_options.php:94
335
+ msgid "ffmpeg path"
336
+ msgstr ""
337
+
338
+ #: views/global_options.php:101
339
+ msgid "Delete the demo files generated previously"
340
+ msgstr ""
341
+
342
+ #: views/global_options.php:108
343
+ msgid "Store demo files on Google Drive"
344
+ msgstr ""
345
+
346
+ #: views/global_options.php:112
347
+ msgid "Import a JSON Key file"
348
+ msgstr ""
349
+
350
+ #: views/global_options.php:158
351
+ msgid "Troubleshoot Area"
352
+ msgstr ""
353
+
354
+ #: views/global_options.php:162
355
+ msgid "Loading players in the onload event"
356
+ msgstr ""
357
+
358
+ #: views/global_options.php:166
359
+ msgid "tick the checkbox if the players are not being loaded properly"
360
+ msgstr ""
361
+
362
+ #: views/global_options.php:171
363
+ msgid "For files whose extensions cannot be determined"
364
+ msgstr ""
365
+
366
+ #: views/global_options.php:175
367
+ msgid "handle them as mp3 files"
368
+ msgstr ""
369
+
370
+ #: views/global_options.php:180
371
+ msgid ""
372
+ "For the WooCommerce Gutenberg Blocks, include the main player in the "
373
+ "products titles"
374
+ msgstr ""
375
+
376
+ #: views/global_options.php:184
377
+ msgid "Includes the main player in front of products titles"
378
+ msgstr ""
379
+
380
+ #: views/global_options.php:189
381
+ msgid "WooCommerce hook used to display the players in the shop pages"
382
+ msgstr ""
383
+
384
+ #: views/global_options.php:193
385
+ msgid ""
386
+ "The plugin uses by default the <b>woocommerce_shop_loop_item_title</b> hook. "
387
+ "If the player is not being displayed, enter the hook used by the theme "
388
+ "active on your website."
389
+ msgstr ""
390
+
391
+ #: views/global_options.php:198
392
+ msgid "WooCommerce hook used to display the players in the products pages"
393
+ msgstr ""
394
+
395
+ #: views/global_options.php:202
396
+ msgid ""
397
+ "The plugin uses by default the <b>woocommerce_single_product_summary</b> "
398
+ "hook. If the player is not being displayed, enter the hook used by the theme "
399
+ "active on your website."
400
+ msgstr ""
401
+
402
+ #: views/global_options.php:207
403
+ msgid ""
404
+ "Click on the <a href=\"https://docs.woocommerce.com/wc-apidocs/hook-docs.html"
405
+ "\" target=\"_blank\">THIS LINK</a> for the list of available <a href="
406
+ "\"https://docs.woocommerce.com/wc-apidocs/hook-docs.html\" target=\"_blank\" "
407
+ "style=\"font-weight:bold;font-size:1.3em;\">WooCommerce Hooks</a>"
408
+ msgstr ""
409
+
410
+ #: views/global_options.php:212
411
+ msgid "Include music player in all products"
412
+ msgstr ""
413
+
414
+ #: views/global_options.php:229
415
+ msgid "Include players in cart"
416
+ msgstr ""
417
+
418
+ #: views/global_options.php:303 views/player_options.php:261
419
+ msgid "The security feature is only available in the PRO version of the plugin"
420
+ msgstr ""
421
+
422
+ #: views/global_options.php:306 views/player_options.php:264
423
+ msgid "Protect the file"
424
+ msgstr ""
425
+
426
+ #: views/global_options.php:310 views/player_options.php:268
427
+ msgid "Percent of audio used for protected playbacks"
428
+ msgstr ""
429
+
430
+ #: views/global_options.php:313 views/player_options.php:271
431
+ msgid ""
432
+ "To prevent unauthorized copying of audio files, the files will be partially "
433
+ "accessible"
434
+ msgstr ""
435
+
436
+ #: views/global_options.php:318
437
+ msgid ""
438
+ "Text to display beside the player explaining that demos are partial versions "
439
+ "of the original files"
440
+ msgstr ""
441
+
442
+ #: views/global_options.php:334
443
+ msgid "Scope"
444
+ msgstr ""
445
+
446
+ #: views/global_options.php:335
447
+ msgid ""
448
+ "Ticking the checkbox the previous settings are applied to all products, even "
449
+ "if they have a player enabled."
450
+ msgstr ""
451
+
452
+ #: views/global_options.php:335
453
+ msgid "Apply the previous settings to all products pages in the website."
454
+ msgstr ""
455
+
456
+ #: views/global_options.php:347
457
+ msgid "Analytics"
458
+ msgstr ""
459
+
460
+ #: views/global_options.php:351
461
+ msgid ""
462
+ "Allows the integration with Google Analytics for registering new events when "
463
+ "the songs are played. The event information would include: the URL to the "
464
+ "audio file as the event label and the product's id as its value."
465
+ msgstr ""
466
+
467
+ #: views/global_options.php:352
468
+ msgid "Note"
469
+ msgstr ""
470
+
471
+ #: views/global_options.php:352
472
+ msgid ""
473
+ "If the preload option is configured as Metadata or Auto in the players "
474
+ "settings, the event would be registered when the audio file is loaded by the "
475
+ "player and not exactly when they are playing."
476
+ msgstr ""
477
+
478
+ #: views/global_options.php:357
479
+ msgid "Tracking Id"
480
+ msgstr ""
481
+
482
+ #: views/global_options.php:365
483
+ msgid "Save settings"
484
+ msgstr ""
485
+
486
+ #: views/player_options.php:47
487
+ msgid ""
488
+ "The security feature and particular files for demo are only available in the "
489
+ "PRO version of the plugin"
490
+ msgstr ""
491
+
492
+ #: views/player_options.php:48
493
+ msgid ""
494
+ "For testing the premium version of the plugin, visit the online demo:<br/> "
495
+ "<a href=\"https://demos.dwbooster.com/music-player-for-woocommerce/wp-login."
496
+ "php\" target=\"_blank\">Administration area: Click to access the "
497
+ "administration area demo</a><br/><a href=\"https://demos.dwbooster.com/music-"
498
+ "player-for-woocommerce/\" target=\"_blank\">Public page: Click to visit the "
499
+ "WooCommerce Store</a>"
500
+ msgstr ""
501
+
502
+ #: views/player_options.php:177
503
+ msgid ""
504
+ "The player is shown only if the product is \"downloadable\", and there is at "
505
+ "least an audio file between the \"Downloadable files\""
506
+ msgstr ""
507
+
508
+ #: views/player_options.php:283
509
+ msgid "Select my own demo files"
510
+ msgstr ""
511
+
512
+ #: views/player_options.php:287
513
+ msgid "Demo files"
514
+ msgstr ""
515
+
516
+ #: views/player_options.php:291
517
+ msgid "Name"
518
+ msgstr ""
519
+
520
+ #: views/player_options.php:292
521
+ msgid "File URL"
522
+ msgstr ""
523
+
524
+ #: views/player_options.php:315
525
+ msgid "Add File"
526
+ msgstr ""
527
+
528
+ #: wcmp.php:224
529
+ msgid "Help"
530
+ msgstr ""
531
+
532
+ #: wcmp.php:931
533
+ msgid "There are no products that satisfy the block's settings"
534
+ msgstr ""
535
+
536
+ #: widgets/playlist_widget.php:51
537
+ msgid "Title"
538
+ msgstr ""
539
+
540
+ #: widgets/playlist_widget.php:54
541
+ msgid "Products IDs"
542
+ msgstr ""
543
+
544
+ #: widgets/playlist_widget.php:54
545
+ msgid "Products IDs separated by comma, or a * for all"
546
+ msgstr ""
547
+
548
+ #: widgets/playlist_widget.php:58
549
+ msgid ""
550
+ "Enter the ID of products separated by comma, or a * symbol to includes all "
551
+ "products in the playlist."
552
+ msgstr ""
553
+
554
+ #: widgets/playlist_widget.php:62
555
+ msgid "Playlist layout"
556
+ msgstr ""
557
+
558
+ #: widgets/playlist_widget.php:65
559
+ msgid "New layout"
560
+ msgstr ""
561
+
562
+ #: widgets/playlist_widget.php:68
563
+ msgid "Original layout"
564
+ msgstr ""
565
+
566
+ #: widgets/playlist_widget.php:93
567
+ msgid "Highlight the current product"
568
+ msgstr ""
569
+
570
+ #: widgets/playlist_widget.php:96
571
+ msgid "Continue playing after navigate"
572
+ msgstr ""
573
+
574
+ #: widgets/playlist_widget.php:100
575
+ msgid ""
576
+ "Continue playing the same song at same position after navigate. You can "
577
+ "experiment some delay because the music player should to load the audio file "
578
+ "again, and in some mobiles devices, where the action of the user is "
579
+ "required, the player cannot starting playing automatically."
580
+ msgstr ""
pagebuilders/beaverbuilder/wcmp.inc.php ADDED
@@ -0,0 +1,26 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ require_once dirname(__FILE__).'/wcmp/wcmp.pb.php';
3
+
4
+ FLBuilder::register_module(
5
+ 'WCMPBeaver',
6
+ array(
7
+ 'wcmp-tab' => array(
8
+ 'title' => __('Enter the products ids and the rest of shortcode attributes', 'music-player-for-woocommerce'),
9
+ 'sections' => array(
10
+ 'wcmp-section' => array(
11
+ 'title' => __('Playlist Shortcode', 'music-player-for-woocommerce'),
12
+ 'fields' => array(
13
+ 'products_ids' => array(
14
+ 'type' => 'text',
15
+ 'label' => __('Products ids separated by comma (* represents all products)', 'music-player-for-woocommerce')
16
+ ),
17
+ 'attributes' => array(
18
+ 'type' => 'text',
19
+ 'label' => __('Additional attributes', 'music-player-for-woocommerce')
20
+ ),
21
+ )
22
+ )
23
+ )
24
+ )
25
+ )
26
+ );
pagebuilders/beaverbuilder/wcmp/includes/frontend.php ADDED
@@ -0,0 +1,10 @@
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ if(!empty($settings->products_ids)) $products_ids = preg_replace('/[^\d\,]/', '', $settings->products_ids);
3
+ if(empty($products_ids)) $products_ids = '*';
4
+
5
+ $output = '[wcmp-playlist products_ids="'.sanitize_text_field($products_ids).'"';
6
+
7
+ if(!empty($settings->attributes)) $output .= ' '.sanitize_text_field($settings->attributes);
8
+
9
+ $output .= ']';
10
+ echo $output;
pagebuilders/beaverbuilder/wcmp/wcmp.pb.php ADDED
@@ -0,0 +1,18 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ class WCMPBeaver extends FLBuilderModule {
3
+ public function __construct()
4
+ {
5
+ $modules_dir = dirname(__FILE__).'/';
6
+ $modules_url = plugins_url( '/', __FILE__ ).'/';
7
+
8
+ parent::__construct(array(
9
+ 'name' => __( 'Music Player for WooCommerce', 'music-player-for-woocommerce' ),
10
+ 'description' => __( 'Insert the playlist shortcode', 'music-player-for-woocommerce' ),
11
+ 'group' => __( 'Music Player for WooCommerce', 'music-player-for-woocommerce' ),
12
+ 'category' => __( 'Music Player for WooCommerce', 'music-player-for-woocommerce' ),
13
+ 'dir' => $modules_dir,
14
+ 'url' => $modules_url,
15
+ 'partial_refresh' => true,
16
+ ));
17
+ }
18
+ }
pagebuilders/builders.php ADDED
@@ -0,0 +1,154 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /**
3
+ * Main class to interace with the different Content Editors: WCMP_BUILDERS class
4
+ *
5
+ */
6
+ if(!class_exists('WCMP_BUILDERS'))
7
+ {
8
+ class WCMP_BUILDERS
9
+ {
10
+ private static $_instance;
11
+
12
+ private function __construct(){}
13
+ private static function instance()
14
+ {
15
+ if(!isset(self::$_instance)) self::$_instance = new self();
16
+ return self::$_instance;
17
+ } // End instance
18
+
19
+ public static function run()
20
+ {
21
+ $instance = self::instance();
22
+ add_action('init', array($instance, 'init'));
23
+ add_action('after_setup_theme', array($instance, 'after_setup_theme'));
24
+ }
25
+
26
+ public function init()
27
+ {
28
+ $instance = self::instance();
29
+
30
+ // Gutenberg
31
+ add_action( 'enqueue_block_editor_assets', array($instance,'gutenberg_editor' ) );
32
+ add_filter( 'pre_render_block', array($instance, 'gutenberg_pre_render_block'), 10, 2);
33
+
34
+ // Elementor
35
+ add_action( 'elementor/widgets/widgets_registered', array($instance, 'elementor_editor') );
36
+ add_action( 'elementor/elements/categories_registered', array($instance, 'elementor_editor_category') );
37
+
38
+ // Beaver builder
39
+ if(class_exists('FLBuilder'))
40
+ {
41
+ include_once dirname(__FILE__).'/beaverbuilder/wcmp.inc.php';
42
+ }
43
+
44
+ // DIVI
45
+ add_action( 'et_builder_ready', array($instance, 'divi_editor') );
46
+
47
+ } // End init
48
+
49
+ public function after_setup_theme()
50
+ {
51
+ $instance = $instance = self::instance();
52
+
53
+ // SiteOrigin
54
+ add_filter('siteorigin_widgets_widget_folders', array($instance, 'siteorigin_widgets_collection'));
55
+ add_filter('siteorigin_panels_widget_dialog_tabs', array($instance, 'siteorigin_panels_widget_dialog_tabs'));
56
+
57
+ // Visual Composer
58
+ add_action('vcv:api', array($instance, 'visualcomposer_editor'));
59
+ } // End after_setup_theme
60
+
61
+ /**************************** DIVI ****************************/
62
+
63
+ public function divi_editor()
64
+ {
65
+ if(class_exists('ET_Builder_Module'))
66
+ {
67
+ if(isset($_GET['et_fb']))
68
+ {
69
+ wp_enqueue_script('wcmp-admin-gutenberg-editor', plugin_dir_url(__FILE__).'divi/divi.js', array('react'), null, true);
70
+ }
71
+ require_once dirname(__FILE__).'/divi/divi.pb.php';
72
+ }
73
+ } // End divi_editor
74
+
75
+ /**************************** GUTENBERG ****************************/
76
+
77
+ /**
78
+ * Loads the javascript resources to integrate the plugin with the Gutenberg editor
79
+ */
80
+ public function gutenberg_editor()
81
+ {
82
+ wp_enqueue_style('wcmp-gutenberg-editor-css', plugin_dir_url(__FILE__).'gutenberg/gutenberg.css');
83
+
84
+ $url = WCMP_WEBSITE_URL;
85
+ $url .= ((strpos($url, '?') === false) ? '?' : '&').'wcmp-preview=';
86
+
87
+ wp_enqueue_script('wcmp-admin-gutenberg-editor', plugin_dir_url(__FILE__).'gutenberg/gutenberg.js', array( 'wp-blocks', 'wp-element' ), null, true);
88
+
89
+ wp_localize_script('wcmp-admin-gutenberg-editor', 'wcmp_gutenberg_editor_config', array('url' => $url));
90
+ } // End gutenberg_editor
91
+
92
+ public function gutenberg_pre_render_block($content, $block)
93
+ {
94
+ if(
95
+ stripos($block['blockName'], 'woocommerce/') !== false &&
96
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_force_main_player_in_title', 1 )
97
+ )
98
+ {
99
+ add_filter( 'woocommerce_product_title', array($GLOBALS[ 'WooCommerceMusicPlayer' ], 'woocommerce_product_title'), 10, 2);
100
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->enqueue_resources();
101
+ wp_enqueue_script('wcmp-wcblocks-js', plugin_dir_url(__FILE__).'gutenberg/wcblocks.js', array('jquery'));
102
+ wp_enqueue_style('wcmp-wcblocks-css', plugin_dir_url(__FILE__).'gutenberg/wcblocks.css');
103
+ }
104
+ return $content;
105
+ } // End gutenberg_pre_render_block
106
+
107
+ /**************************** ELEMENTOR ****************************/
108
+
109
+ public function elementor_editor_category()
110
+ {
111
+ require_once dirname(__FILE__).'/elementor/elementor_category.pb.php';
112
+ } // End elementor_editor
113
+
114
+ public function elementor_editor()
115
+ {
116
+ require_once dirname(__FILE__).'/elementor/elementor.pb.php';
117
+ } // End elementor_editor
118
+
119
+ /**************************** SITEORIGIN ****************************/
120
+
121
+ public function siteorigin_widgets_collection($folders)
122
+ {
123
+ $folders[] = dirname(__FILE__).'/siteorigin/';
124
+ return $folders;
125
+ } // End siteorigin_widgets_collection
126
+
127
+ public function siteorigin_panels_widget_dialog_tabs($tabs)
128
+ {
129
+ $tabs[] = array(
130
+ 'title' => __('Music Player for WooCommerce', 'music-player-for-woocommerce'),
131
+ 'filter' => array(
132
+ 'groups' => array('music-player-for-woocommerce')
133
+ )
134
+ );
135
+
136
+ return $tabs;
137
+ } // End siteorigin_panels_widget_dialog_tabs
138
+
139
+ /**************************** VISUAL COMPOSER ****************************/
140
+
141
+ public function visualcomposer_editor($api)
142
+ {
143
+ $elementsToRegister = ['WCMPplaylist'];
144
+ $pluginBaseUrl = rtrim(plugins_url('visualcomposer/', __FILE__), '\\/');
145
+ $elementsApi = $api->elements;
146
+ foreach ($elementsToRegister as $tag)
147
+ {
148
+ $manifestPath = dirname(__FILE__) . '/visualcomposer/' . $tag . '/manifest.json';
149
+ $elementBaseUrl = $pluginBaseUrl . '/' . $tag;
150
+ $elementsApi->add($manifestPath, $elementBaseUrl);
151
+ }
152
+ } // End visualcomposer_editor
153
+ } // End WCMP_BUILDERS
154
+ }
pagebuilders/divi/divi.js ADDED
@@ -0,0 +1 @@
 
1
+ !function(e){var t={};function r(n){if(t[n])return t[n].exports;var o=t[n]={i:n,l:!1,exports:{}};return e[n].call(o.exports,o,o.exports,r),o.l=!0,o.exports}r.m=e,r.c=t,r.d=function(e,t,n){r.o(e,t)||Object.defineProperty(e,t,{configurable:!1,enumerable:!0,get:n})},r.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return r.d(t,"a",t),t},r.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},r.p="/",r(r.s=0)}([function(e,t,r){r(1),e.exports=r(2)},function(e,t,r){"use strict"},function(e,t,r){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var n=r(3),o=r.n(n),i=r(4);o()(window).on("et_builder_api_ready",function(e,t){t.registerModules(i.a)})},function(e,t){e.exports=jQuery},function(e,t,r){"use strict";var n=r(5);t.a=[n.a]},function(e,t,r){"use strict";var n=r(6),o=r.n(n);function i(e){return(i="function"===typeof Symbol&&"symbol"===typeof Symbol.iterator?function(e){return typeof e}:function(e){return e&&"function"===typeof Symbol&&e.constructor===Symbol&&e!==Symbol.prototype?"symbol":typeof e})(e)}function u(e,t){for(var r=0;r<t.length;r++){var n=t[r];n.enumerable=n.enumerable||!1,n.configurable=!0,"value"in n&&(n.writable=!0),Object.defineProperty(e,n.key,n)}}function c(e,t){return!t||"object"!==i(t)&&"function"!==typeof t?function(e){if(void 0===e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return e}(e):t}var s=function(e){function t(){return function(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}(this,t),c(this,(t.__proto__||Object.getPrototypeOf(t)).apply(this,arguments))}var r,i,s;return function(e,t){if("function"!==typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function");e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}(t,n["Component"]),r=t,(i=[{key:"render",value:function(){var e="",t="",r="";return"wcmp_products_ids"in this.props&&(t=this.props.wcmp_products_ids.replace(/[^\d\,\*]/g,"")),/^\s*$/.test(t)&&(t="*"),e='[wcmp-playlist products_ids="'+t+'"',"wcmp_attributes"in this.props&&(r=this.props.wcmp_attributes.replace(/^\s+/,"").replace(/\s+$/,"")),/^\s*$/.test(r)||(e+=" "+r),e+="]",o.a.createElement("div",{className:"wcmp-iframe-overlay"},e)}}])&&u(r.prototype,i),s&&u(r,s),t}();Object.defineProperty(s,"slug",{configurable:!0,enumerable:!0,writable:!0,value:"et_pb_wcmp_divi_module"}),t.a=s},function(e,t){e.exports=React}]);
pagebuilders/divi/divi.pb.php ADDED
@@ -0,0 +1,58 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ class WCMP_DIVI extends ET_Builder_Module
3
+ {
4
+
5
+ public $slug = 'et_pb_wcmp_divi_module';
6
+ public $vb_support = 'on';
7
+
8
+ public function init()
9
+ {
10
+ $this->name = esc_html__('Music Player for WooCommerce', 'music-player-for-woocommerce');
11
+ $this->settings_modal_toggles = array(
12
+ 'general' => array(
13
+ 'toggles' => array(
14
+ 'main_content' => esc_html__( 'Playlist', 'music-player-for-woocommerce' ),
15
+ ),
16
+ ),
17
+ );
18
+ }
19
+
20
+ public function get_fields()
21
+ {
22
+ global $wpdb;
23
+ return array(
24
+ 'wcmp_products_ids' => array(
25
+ 'label' => esc_html__( 'Products ids', 'music-player-for-woocommerce' ),
26
+ 'type' => 'text',
27
+ 'default' => '*',
28
+ 'option_category' => 'basic_option',
29
+ 'description' => esc_html__( 'Enter the products ids separated by comma, or the * sign to include all products.', 'music-player-for-woocommerce' ),
30
+ 'toggle_slug' => 'main_content',
31
+ ),
32
+ 'wcmp_attributes' => array(
33
+ 'label' => esc_html__( 'Additional attributes', 'music-player-for-woocommerce' ),
34
+ 'type' => 'text',
35
+ 'option_category' => 'basic_option',
36
+ 'description' => 'controls="track" layout="new"',
37
+ 'toggle_slug' => 'main_content',
38
+ ),
39
+ );
40
+ }
41
+
42
+ public function render($unprocessed_props, $content = null, $render_slug)
43
+ {
44
+ $output = '';
45
+ $products = sanitize_text_field($this->props['wcmp_products_ids']);
46
+ if(empty($products)) $products = '*';
47
+
48
+ $output = '[wcmp-playlist products_ids="'.esc_attr($products).'"';
49
+
50
+ $attributes = sanitize_text_field($this->props['wcmp_attributes']);
51
+ if(!empty($attributes)) $output .= ' '.$attributes;
52
+
53
+ $output .= ']';
54
+ return do_shortcode($output);
55
+ }
56
+ }
57
+
58
+ new WCMP_DIVI;
pagebuilders/elementor/elementor.pb.php ADDED
@@ -0,0 +1,105 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ namespace Elementor;
3
+
4
+ if ( ! defined( 'ABSPATH' ) ) {
5
+ exit; // Exit if accessed directly.
6
+ }
7
+
8
+ class Elementor_WCMP_Widget extends Widget_Base
9
+ {
10
+ public function get_name()
11
+ {
12
+ return 'music-player-for-woocommerce';
13
+ } // End get_name
14
+
15
+ public function get_title()
16
+ {
17
+ return 'Playlist';
18
+ } // End get_title
19
+
20
+ public function get_icon()
21
+ {
22
+ return 'fa fa-play';
23
+ } // End get_icon
24
+
25
+ public function get_categories()
26
+ {
27
+ return array( 'music-player-for-woocommerce-cat' );
28
+ } // End get_categories
29
+
30
+ public function is_reload_preview_required()
31
+ {
32
+ return true;
33
+ } // End is_reload_preview_required
34
+
35
+ protected function _register_controls()
36
+ {
37
+ global $wpdb;
38
+
39
+ $this->start_controls_section(
40
+ 'wcmp_section',
41
+ array(
42
+ 'label' => __( 'Music Player For WooCommerce', 'music-player-for-woocommerce' )
43
+ )
44
+ );
45
+
46
+ $this->add_control(
47
+ 'shortcode',
48
+ array(
49
+ 'label' => __('Music Player For WooCommerce', 'music-player-for-woocommerce'),
50
+ 'type' => Controls_Manager::TEXTAREA,
51
+ 'default' => '[wcmp-playlist products_ids="*" controls="track"]',
52
+ 'description' => '<p>'.__('To include specific products in the playlist enter their IDs in the products_ids attributes, separated by comma symbols (,)', 'music-player-for-woocommerce').'</p><p>'.__('More information visiting the follwing link: ', 'music-player-for-woocommerce').'<br><a href="https://wcmp.dwbooster.com/documentation#playlist-shortcode" target="_blank">'.__('CLICK HERE', 'music-player-for-woocommerce').'</a></p>'
53
+ )
54
+ );
55
+
56
+ $this->end_controls_section();
57
+ } // End _register_controls
58
+
59
+ private function _get_shortcode()
60
+ {
61
+ $settings = $this->get_settings_for_display();
62
+ $shortcode = $settings['shortcode'];
63
+ $shortcode = preg_replace('/[\r\n]/', ' ', $shortcode);
64
+ return trim($shortcode);
65
+ } // End _get_shortcode
66
+
67
+ protected function render()
68
+ {
69
+ $shortcode = sanitize_text_field($this->_get_shortcode());
70
+ if(
71
+ isset($_REQUEST['action']) &&
72
+ (
73
+ $_REQUEST['action'] == 'elementor' ||
74
+ $_REQUEST['action'] == 'elementor_ajax'
75
+ )
76
+ )
77
+ {
78
+
79
+ $url = WCMP_WEBSITE_URL;
80
+ $url .= ((strpos($url, '?') === false) ? '?' : '&').'wcmp-preview='.urlencode($shortcode);
81
+ ?>
82
+ <div class="wcmp-iframe-container" style="position:relative;">
83
+ <div class="wcmp-iframe-overlay" style="position:absolute;top:0;right:0;bottom:0;left:0;"></div>
84
+ <iframe height="0" width="100%" src="<?php print $url; ?>" scrolling="no">
85
+ </div>
86
+ <?php
87
+ }
88
+ else
89
+ {
90
+ print do_shortcode(shortcode_unautop($shortcode));
91
+ }
92
+
93
+ } // End render
94
+
95
+ public function render_plain_content()
96
+ {
97
+ echo $this->_get_shortcode();
98
+ } // End render_plain_content
99
+
100
+ protected function _content_template() {} // End _content_template
101
+ } // End Elementor_WCMP_Widget
102
+
103
+
104
+ // Register the widgets
105
+ Plugin::instance()->widgets_manager->register_widget_type( new Elementor_WCMP_Widget );
pagebuilders/elementor/elementor_category.pb.php ADDED
@@ -0,0 +1,16 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ namespace Elementor;
3
+
4
+ if ( ! defined( 'ABSPATH' ) ) {
5
+ exit; // Exit if accessed directly.
6
+ }
7
+
8
+ // Register the categories
9
+ Plugin::$instance->elements_manager->add_category(
10
+ 'music-player-for-woocommerce-cat',
11
+ array(
12
+ 'title'=>'Music Player For WooCommerce',
13
+ 'icon' => 'fa fa-plug'
14
+ ),
15
+ 2 // position
16
+ );
pagebuilders/gutenberg/gutenberg.css ADDED
@@ -0,0 +1,7 @@
 
 
 
 
 
 
 
1
+ .wcmp-iframe-container {
2
+ position: relative;
3
+ }
4
+ .wcmp-iframe-overlay {
5
+ position: absolute;
6
+ top: 0; right: 0; bottom: 0; left: 0;
7
+ }
pagebuilders/gutenberg/gutenberg.js ADDED
@@ -0,0 +1,109 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ( function( blocks, element ) {
2
+ var el = element.createElement,
3
+ InspectorControls = ('blockEditor' in wp) ? wp.blockEditor.InspectorControls : wp.editor.InspectorControls;
4
+
5
+ /* Plugin Category */
6
+ blocks.getCategories().push({slug: 'wcmp', title: 'WooCommerce Music Player'});
7
+
8
+ /* ICONS */
9
+ const iconWCMPP = el('img', { width: 20, height: 20, src: "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAUCAYAAACNiR0NAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAABx0RVh0U29mdHdhcmUAQWRvYmUgRmlyZXdvcmtzIENTNui8sowAAAChSURBVDiNY/z//z8DNQETVU0bEgaywBhLU2eQFJgxczIZYWzkeKC6CxlhpjMyMhJQihvQ1IXwMFySMp3sMEQGo2GIG8DCbEnK9C0MDAw5MXMyH2BTR44LvRkYGK4vSZnesCRlOju6JMlhiOaTBwwMDBnRszN2UuJCdMCKzCHXwB8MDAyNDAwMGjFzMrcgS7BgV48X7GRgYMjAFSmMg77EBgAc+TshcDQUDgAAAABJRU5ErkJggg==" } );
10
+
11
+ /* Sell Downloads Shortcode */
12
+ blocks.registerBlockType( 'wcmp/woocommerce-music-player-playlist', {
13
+ title: 'WooCommerce Music Player Playlist',
14
+ icon: iconWCMPP,
15
+ category: 'wcmp',
16
+ customClassName: false,
17
+ supports:{
18
+ customClassName: false,
19
+ className: false
20
+ },
21
+ attributes: {
22
+ shortcode : {
23
+ type : 'string',
24
+ source : 'text',
25
+ default: '[wcmp-playlist products_ids="*" controls="track"]'
26
+ }
27
+ },
28
+
29
+ edit: function( props ) {
30
+ var children = [], focus = props.isSelected;
31
+
32
+ children.push(
33
+ el('textarea',
34
+ {
35
+ key : 'wcmp_playlist_shortcode',
36
+ value: props.attributes.shortcode,
37
+ onChange: function(evt){
38
+ props.setAttributes({shortcode: evt.target.value});
39
+ },
40
+ style: {width:"100%", resize: "vertical"}
41
+ }
42
+ )
43
+ );
44
+
45
+ children.push(
46
+ el(
47
+ 'div', {className: 'wcmp-iframe-container', key:'wcmp_iframe_container'},
48
+ el('div', {className: 'wcmp-iframe-overlay', key:'wcmp_iframe_overlay'}),
49
+ el('iframe',
50
+ {
51
+ key: 'wcmp_iframe',
52
+ src: wcmp_gutenberg_editor_config.url+encodeURIComponent(props.attributes.shortcode),
53
+ height: 0,
54
+ width: 500,
55
+ scrolling: 'no'
56
+ }
57
+ )
58
+ )
59
+ );
60
+
61
+ if(!!focus)
62
+ {
63
+ children.push(
64
+ el(
65
+ InspectorControls,
66
+ {
67
+ key : 'wcmp_playlist'
68
+ },
69
+ [
70
+ el(
71
+ 'p',
72
+ {
73
+ key: 'wcmp_inspector_help'
74
+
75
+ },
76
+ 'To include specific products in the playlist enter their IDs in the products_ids attributes, separated by comma symbols (,)'
77
+ ),
78
+ el(
79
+ 'p',
80
+ {
81
+ key : 'wcmp_inspector_more_help',
82
+ style : {fontWeight: 'bold'}
83
+ },
84
+ 'More information visiting the follwing link:'
85
+ ),
86
+ el(
87
+ 'a',
88
+ {
89
+ key : 'wcmp_inspector_help_link',
90
+ href : 'https://wcmp.dwbooster.com/documentation#playlist-shortcode',
91
+ target : '_blank'
92
+ },
93
+ 'CLICK HERE'
94
+ ),
95
+ ]
96
+ )
97
+ );
98
+ }
99
+ return children;
100
+ },
101
+
102
+ save: function( props ) {
103
+ return props.attributes.shortcode;
104
+ }
105
+ });
106
+ } )(
107
+ window.wp.blocks,
108
+ window.wp.element
109
+ );
pagebuilders/gutenberg/wcblocks.css ADDED
@@ -0,0 +1 @@
 
1
+ .wc-block-all-products .wc-block-grid__product-title{display:none;}
pagebuilders/gutenberg/wcblocks.js ADDED
@@ -0,0 +1,32 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ jQuery(function(){
2
+ jQuery('.wc-block-all-products').each(
3
+ function()
4
+ {
5
+ (new MutationObserver(
6
+ function(mutationsList, observer)
7
+ {
8
+ for(let mutation of mutationsList)
9
+ {
10
+ if (mutation.type === 'childList')
11
+ {
12
+ if(mutation.addedNodes.length)
13
+ {
14
+ try{
15
+ var l = jQuery('.wc-block-grid__product-title:hidden', '.wc-block-all-products');
16
+ if(l.length)
17
+ {
18
+ l.each(function(){
19
+ var e = jQuery('a',this);
20
+ if(e.length) e.html(e.text()).parent().show();
21
+ });
22
+ wcmp_force_init();
23
+ }
24
+ }catch(err){}
25
+ }
26
+ }
27
+ }
28
+ }
29
+ )).observe(this, { childList: true, subtree: true });
30
+ }
31
+ );
32
+ });
pagebuilders/siteorigin/siteorigin-wcmp/assets/banner.svg ADDED
@@ -0,0 +1 @@
 
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24"><path d="M0 0h24v24H0z" fill="none"/><path d="M15 6H3v2h12V6zm0 4H3v2h12v-2zM3 16h8v-2H3v2zM17 6v8.18c-.31-.11-.65-.18-1-.18-1.66 0-3 1.34-3 3s1.34 3 3 3 3-1.34 3-3V8h3V6h-5z"/></svg>
pagebuilders/siteorigin/siteorigin-wcmp/siteorigin-wcmp.php ADDED
@@ -0,0 +1,48 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /*
3
+ Widget Name: Music Player for WooCommerce
4
+ Description: Insert a playlist with the products players.
5
+ Documentation: https://wcmp.dwbooster.com/documentation#playlist-shortcode
6
+ */
7
+
8
+ class SiteOrigin_WCMP_Shortcode extends SiteOrigin_Widget
9
+ {
10
+ function __construct()
11
+ {
12
+ global $wpdb;
13
+ $options = array();
14
+ $default = '';
15
+ parent::__construct(
16
+ 'siteorigin-wcmp-shortcode',
17
+ __('Music Player for WooCommerce', 'music-player-for-woocommerce'),
18
+ array(
19
+ 'description' => __('Insert a playlist with the products players', 'music-player-for-woocommerce'),
20
+ 'panels_groups' => array('music-player-for-woocommerce'),
21
+ 'help' => 'https://wcmp.dwbooster.com/documentation#playlist-shortcode',
22
+ ),
23
+ array(),
24
+ array(
25
+ 'shortcode' => array(
26
+ 'type' => 'text',
27
+ 'label' => __('To include specific products in the playlist enter their IDs in the products_ids attributes, separated by comma symbols (,)', 'music-player-for-woocommerce'),
28
+ 'default' => '[wcmp-playlist products_ids="*" controls="track"]'
29
+ ),
30
+ ),
31
+ plugin_dir_path(__FILE__)
32
+ );
33
+ } // End __construct
34
+
35
+ function get_template_name($instance)
36
+ {
37
+ return 'siteorigin-wcmp-shortcode';
38
+ } // End get_template_name
39
+
40
+ function get_style_name($instance)
41
+ {
42
+ return '';
43
+ } // End get_style_name
44
+
45
+ } // End Class SiteOrigin_WCMP_Shortcode
46
+
47
+ // Registering the widget
48
+ siteorigin_widget_register('siteorigin-wcmp-shortcode', __FILE__, 'SiteOrigin_WCMP_Shortcode');
pagebuilders/siteorigin/siteorigin-wcmp/tpl/siteorigin-wcmp-shortcode.php ADDED
@@ -0,0 +1 @@
 
1
+ <?php print !empty($instance['shortcode']) ? sanitize_text_field($instance['shortcode']) : '';
pagebuilders/visualcomposer/WCMPplaylist/WCMPplaylist/public/wcmp-preview.png ADDED
Binary file
pagebuilders/visualcomposer/WCMPplaylist/WCMPplaylist/public/wcmp-thumbnail.png ADDED
Binary file
pagebuilders/visualcomposer/WCMPplaylist/manifest.json ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "elements": {
3
+ "WCMPplaylist": {
4
+ "settings": {
5
+ "name": "Music Player for WooCommerce Playlist",
6
+ "metaThumbnailUrl": "[publicPath]/wcmp-thumbnail.png",
7
+ "metaPreviewUrl": "[publicPath]/wcmp-preview.png",
8
+ "metaDescription": "Add a playlist."
9
+ }
10
+ }
11
+ },
12
+ "categories": {
13
+ "Misc": {
14
+ "elements": [
15
+ "WCMPplaylist"
16
+ ]
17
+ }
18
+ }
19
+ }
pagebuilders/visualcomposer/WCMPplaylist/public/dist/element.bundle.js ADDED
@@ -0,0 +1,83 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ (window["vcvWebpackJsonp4x"] = window["vcvWebpackJsonp4x"] || []).push([["element"],{
2
+
3
+ /***/ "./WCMPplaylist/component.js":
4
+ /*!***********************************!*\
5
+ !*** ./WCMPplaylist/component.js ***!
6
+ \***********************************/
7
+ /*! no static exports found */
8
+ /***/ (function(module, exports, __webpack_require__) {
9
+
10
+ "use strict";
11
+ eval("\n\nObject.defineProperty(exports, \"__esModule\", {\n\tvalue: true\n});\n\nvar _extends2 = __webpack_require__(/*! babel-runtime/helpers/extends */ \"./node_modules/babel-runtime/helpers/extends.js\");\n\nvar _extends3 = _interopRequireDefault(_extends2);\n\nvar _getPrototypeOf = __webpack_require__(/*! babel-runtime/core-js/object/get-prototype-of */ \"./node_modules/babel-runtime/core-js/object/get-prototype-of.js\");\n\nvar _getPrototypeOf2 = _interopRequireDefault(_getPrototypeOf);\n\nvar _classCallCheck2 = __webpack_require__(/*! babel-runtime/helpers/classCallCheck */ \"./node_modules/babel-runtime/helpers/classCallCheck.js\");\n\nvar _classCallCheck3 = _interopRequireDefault(_classCallCheck2);\n\nvar _createClass2 = __webpack_require__(/*! babel-runtime/helpers/createClass */ \"./node_modules/babel-runtime/helpers/createClass.js\");\n\nvar _createClass3 = _interopRequireDefault(_createClass2);\n\nvar _possibleConstructorReturn2 = __webpack_require__(/*! babel-runtime/helpers/possibleConstructorReturn */ \"./node_modules/babel-runtime/helpers/possibleConstructorReturn.js\");\n\nvar _possibleConstructorReturn3 = _interopRequireDefault(_possibleConstructorReturn2);\n\nvar _get2 = __webpack_require__(/*! babel-runtime/helpers/get */ \"./node_modules/babel-runtime/helpers/get.js\");\n\nvar _get3 = _interopRequireDefault(_get2);\n\nvar _inherits2 = __webpack_require__(/*! babel-runtime/helpers/inherits */ \"./node_modules/babel-runtime/helpers/inherits.js\");\n\nvar _inherits3 = _interopRequireDefault(_inherits2);\n\nvar _react = __webpack_require__(/*! react */ \"./node_modules/react/index.js\");\n\nvar _react2 = _interopRequireDefault(_react);\n\nvar _vcCake = __webpack_require__(/*! vc-cake */ \"./node_modules/vc-cake/index.js\");\n\nvar _vcCake2 = _interopRequireDefault(_vcCake);\n\nfunction _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }\n\nvar vcvAPI = _vcCake2.default.getService('api');\n\nvar WCMPplaylistElement = function (_vcvAPI$elementCompon) {\n\t(0, _inherits3.default)(WCMPplaylistElement, _vcvAPI$elementCompon);\n\n\tfunction WCMPplaylistElement() {\n\t\t(0, _classCallCheck3.default)(this, WCMPplaylistElement);\n\t\treturn (0, _possibleConstructorReturn3.default)(this, (WCMPplaylistElement.__proto__ || (0, _getPrototypeOf2.default)(WCMPplaylistElement)).apply(this, arguments));\n\t}\n\n\t(0, _createClass3.default)(WCMPplaylistElement, [{\n\t\tkey: 'sanitize',\n\t\tvalue: function sanitize(str, args) {\n\t\t\tif (typeof args == 'undefined') args = {};\n\t\t\tif (!('quotes' in args)) args['quotes'] = false;\n\t\t\tif (!('spaces' in args)) args['spaces'] = false;\n\n\t\t\tstr = str.replace(/[^a-zA-Z0-9\\.\\-*_\\s\"'=]/g, '');\n\t\t\tif (!args.quotes) str = str.replace(/'\"/g, '');\n\t\t\tif (!args.spaces) str = str.replace(/\\s/g, '');\n\n\t\t\treturn str;\n\t\t}\n\t}, {\n\t\tkey: 'getTheShortcode',\n\t\tvalue: function getTheShortcode(atts) {\n\t\t\t// Generates the form's shortcode\n\t\t\tvar _atts$products_ids = atts.products_ids,\n\t\t\t products_ids = _atts$products_ids === undefined ? \"\" : _atts$products_ids,\n\t\t\t _atts$attrs = atts.attrs,\n\t\t\t attrs = _atts$attrs === undefined ? \"\" : _atts$attrs;\n\n\t\t\tif (products_ids == '') products_ids = '*';\n\t\t\tvar shortcode = '[wcmp-playlist products_ids=\"' + this.sanitize(products_ids, { spaces: true }) + '\"';\n\t\t\tif (attrs != '') shortcode += ' ' + this.sanitize(attrs, { quotes: true, spaces: true });\n\t\t\tshortcode += ']';\n\n\t\t\treturn shortcode;\n\t\t}\n\t}, {\n\t\tkey: 'addFormGeneratorForVSEditor',\n\t\tvalue: function addFormGeneratorForVSEditor(base) {\n\t\t\treturn base != '' ? base + '<script>delete generated_the_wcmp; generate_the_wcmp();</script>' : base;\n\t\t}\n\t}, {\n\t\tkey: 'componentDidMount',\n\t\tvalue: function componentDidMount() {\n\n\t\t\tvar shortcode = this.addFormGeneratorForVSEditor(this.getTheShortcode(this.props.atts));\n\t\t\t(0, _get3.default)(WCMPplaylistElement.prototype.__proto__ || (0, _getPrototypeOf2.default)(WCMPplaylistElement.prototype), 'updateShortcodeToHtml', this).call(this, shortcode, this.refs.vcvhelper);\n\t\t\tif (!window.wp || !window.wp.shortcode || !window.VCV_API_WPBAKERY_WPB_MAP) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tthis.multipleShortcodesRegex = window.wp.shortcode.regexp(window.VCV_API_WPBAKERY_WPB_MAP().join('|'));\n\t\t\tthis.localShortcodesRegex = new RegExp(this.multipleShortcodesRegex.source);\n\t\t}\n\t}, {\n\t\tkey: 'componentDidUpdate',\n\t\tvalue: function componentDidUpdate(props) {\n\n\t\t\tvar shortcode = this.addFormGeneratorForVSEditor(this.getTheShortcode(this.props.atts));\n\t\t\tvar shortcodeCmp = this.getTheShortcode(props.atts);\n\t\t\t// update only if shortcode changed\n\t\t\tif (shortcode !== shortcodeCmp) {\n\t\t\t\t(0, _get3.default)(WCMPplaylistElement.prototype.__proto__ || (0, _getPrototypeOf2.default)(WCMPplaylistElement.prototype), 'updateShortcodeToHtml', this).call(this, shortcode, this.refs.vcvhelper);\n\t\t\t}\n\t\t}\n\t}, {\n\t\tkey: 'render',\n\t\tvalue: function render() {\n\t\t\tvar _props = this.props,\n\t\t\t id = _props.id,\n\t\t\t atts = _props.atts,\n\t\t\t editor = _props.editor;\n\n\n\t\t\tvar shortcode = this.getTheShortcode(atts);\n\t\t\tvar elementClasses = 'vce-wcmp-playlist';\n\t\t\tvar wrapperClasses = 'vce-wcmp-playlist-wrapper vce';\n\t\t\tvar customProps = {};\n\n\t\t\tvar doAll = this.applyDO('all');\n\n\t\t\treturn _react2.default.createElement(\n\t\t\t\t'div',\n\t\t\t\t(0, _extends3.default)({ className: elementClasses }, editor, customProps),\n\t\t\t\t_react2.default.createElement(\n\t\t\t\t\t'div',\n\t\t\t\t\t(0, _extends3.default)({ className: wrapperClasses, id: 'el-' + id }, doAll),\n\t\t\t\t\t_react2.default.createElement('style', { className: 'vcvhelper', ref: 'style' }),\n\t\t\t\t\t_react2.default.createElement('div', { className: 'vcvhelper', ref: 'vcvhelper', 'data-vcvs-html': shortcode })\n\t\t\t\t)\n\t\t\t);\n\t\t}\n\t}]);\n\treturn WCMPplaylistElement;\n}(vcvAPI.elementComponent);\n\nexports.default = WCMPplaylistElement;\n\n//# sourceURL=webpack:///./WCMPplaylist/component.js?");
12
+
13
+ /***/ }),
14
+
15
+ /***/ "./WCMPplaylist/index.js":
16
+ /*!*******************************!*\
17
+ !*** ./WCMPplaylist/index.js ***!
18
+ \*******************************/
19
+ /*! no static exports found */
20
+ /***/ (function(module, exports, __webpack_require__) {
21
+
22
+ "use strict";
23
+ eval("\n\nvar _vcCake = __webpack_require__(/*! vc-cake */ \"./node_modules/vc-cake/index.js\");\n\nvar _vcCake2 = _interopRequireDefault(_vcCake);\n\nvar _component = __webpack_require__(/*! ./component */ \"./WCMPplaylist/component.js\");\n\nvar _component2 = _interopRequireDefault(_component);\n\nfunction _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }\n\nvar vcvAddElement = _vcCake2.default.getService('cook').add;\n\nvcvAddElement(__webpack_require__(/*! ./settings.json */ \"./WCMPplaylist/settings.json\"),\n// Component callback\nfunction (component) {\n component.add(_component2.default);\n}, {\n css: false,\n editorCss: __webpack_require__(/*! raw-loader!./editor.css */ \"./node_modules/raw-loader/index.js!./WCMPplaylist/editor.css\")\n});\n\n//# sourceURL=webpack:///./WCMPplaylist/index.js?");
24
+
25
+ /***/ }),
26
+
27
+ /***/ "./WCMPplaylist/settings.json":
28
+ /*!************************************!*\
29
+ !*** ./WCMPplaylist/settings.json ***!
30
+ \************************************/
31
+ /*! exports provided: products_ids, attrs, designOptions, editFormTab1, metaEditFormTabs, relatedTo, tag, default */
32
+ /***/ (function(module) {
33
+
34
+ eval("module.exports = {\"products_ids\":{\"type\":\"string\",\"access\":\"public\",\"options\":{\"label\":\"Enter the products ids (Required)\",\"description\":\"Enter the products ids separated by comma, or the * symbol for including all products\"}},\"attrs\":{\"type\":\"string\",\"access\":\"public\",\"options\":{\"label\":\"Additional attributes (Optional)\",\"description\":\"Enter the additional parameters to include in the playlist's shortcode. Ex. layout=\\\"new\\\" highlight_current_product=\\\"1\\\"\"}},\"designOptions\":{\"type\":\"designOptions\",\"access\":\"public\",\"value\":{},\"options\":{\"label\":\"Design Options\"}},\"editFormTab1\":{\"type\":\"group\",\"access\":\"protected\",\"value\":[\"products_ids\",\"attrs\"],\"options\":{\"label\":\"General\"}},\"metaEditFormTabs\":{\"type\":\"group\",\"access\":\"protected\",\"value\":[\"editFormTab1\",\"designOptions\"]},\"relatedTo\":{\"type\":\"group\",\"access\":\"protected\",\"value\":[\"General\"]},\"tag\":{\"access\":\"protected\",\"type\":\"string\",\"value\":\"WCMPplaylist\"}};\n\n//# sourceURL=webpack:///./WCMPplaylist/settings.json?");
35
+
36
+ /***/ }),
37
+
38
+ /***/ "./node_modules/babel-runtime/core-js/object/get-own-property-descriptor.js":
39
+ /*!**********************************************************************************!*\
40
+ !*** ./node_modules/babel-runtime/core-js/object/get-own-property-descriptor.js ***!
41
+ \**********************************************************************************/
42
+ /*! no static exports found */
43
+ /***/ (function(module, exports, __webpack_require__) {
44
+
45
+ eval("module.exports = { \"default\": __webpack_require__(/*! core-js/library/fn/object/get-own-property-descriptor */ \"./node_modules/core-js/library/fn/object/get-own-property-descriptor.js\"), __esModule: true };\n\n//# sourceURL=webpack:///./node_modules/babel-runtime/core-js/object/get-own-property-descriptor.js?");
46
+
47
+ /***/ }),
48
+
49
+ /***/ "./node_modules/babel-runtime/helpers/get.js":
50
+ /*!***************************************************!*\
51
+ !*** ./node_modules/babel-runtime/helpers/get.js ***!
52
+ \***************************************************/
53
+ /*! no static exports found */
54
+ /***/ (function(module, exports, __webpack_require__) {
55
+
56
+ "use strict";
57
+ eval("\n\nexports.__esModule = true;\n\nvar _getPrototypeOf = __webpack_require__(/*! ../core-js/object/get-prototype-of */ \"./node_modules/babel-runtime/core-js/object/get-prototype-of.js\");\n\nvar _getPrototypeOf2 = _interopRequireDefault(_getPrototypeOf);\n\nvar _getOwnPropertyDescriptor = __webpack_require__(/*! ../core-js/object/get-own-property-descriptor */ \"./node_modules/babel-runtime/core-js/object/get-own-property-descriptor.js\");\n\nvar _getOwnPropertyDescriptor2 = _interopRequireDefault(_getOwnPropertyDescriptor);\n\nfunction _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }\n\nexports.default = function get(object, property, receiver) {\n if (object === null) object = Function.prototype;\n var desc = (0, _getOwnPropertyDescriptor2.default)(object, property);\n\n if (desc === undefined) {\n var parent = (0, _getPrototypeOf2.default)(object);\n\n if (parent === null) {\n return undefined;\n } else {\n return get(parent, property, receiver);\n }\n } else if (\"value\" in desc) {\n return desc.value;\n } else {\n var getter = desc.get;\n\n if (getter === undefined) {\n return undefined;\n }\n\n return getter.call(receiver);\n }\n};\n\n//# sourceURL=webpack:///./node_modules/babel-runtime/helpers/get.js?");
58
+
59
+ /***/ }),
60
+
61
+ /***/ "./node_modules/core-js/library/fn/object/get-own-property-descriptor.js":
62
+ /*!*******************************************************************************!*\
63
+ !*** ./node_modules/core-js/library/fn/object/get-own-property-descriptor.js ***!
64
+ \*******************************************************************************/
65
+ /*! no static exports found */
66
+ /***/ (function(module, exports, __webpack_require__) {
67
+
68
+ eval("__webpack_require__(/*! ../../modules/es6.object.get-own-property-descriptor */ \"./node_modules/core-js/library/modules/es6.object.get-own-property-descriptor.js\");\nvar $Object = __webpack_require__(/*! ../../modules/_core */ \"./node_modules/core-js/library/modules/_core.js\").Object;\nmodule.exports = function getOwnPropertyDescriptor(it, key) {\n return $Object.getOwnPropertyDescriptor(it, key);\n};\n\n\n//# sourceURL=webpack:///./node_modules/core-js/library/fn/object/get-own-property-descriptor.js?");
69
+
70
+ /***/ }),
71
+
72
+ /***/ "./node_modules/raw-loader/index.js!./WCMPplaylist/editor.css":
73
+ /*!***********************************************************!*\
74
+ !*** ./node_modules/raw-loader!./WCMPplaylist/editor.css ***!
75
+ \***********************************************************/
76
+ /*! no static exports found */
77
+ /***/ (function(module, exports) {
78
+
79
+ eval("module.exports = \".vce-wcmp-playlist {\\n min-height: 1em;\\n}\\n.vce-wcmp-playlist .vcvhelper:empty{min-height:1em; background:#DEDEDE;}\\n.vce-wcmp-playlist .vcvhelper *{pointer-events: none;}\"\n\n//# sourceURL=webpack:///./WCMPplaylist/editor.css?./node_modules/raw-loader");
80
+
81
+ /***/ })
82
+
83
+ },[['./WCMPplaylist/index.js']]]);
readme.txt ADDED
@@ -0,0 +1,653 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ === Music Player for WooCommerce ===
2
+ Contributors: codepeople
3
+ Donate link: https://wcmp.dwbooster.com
4
+ Tags:WooCommerce,music player,audio,music,song,player,audio player,media player,mp3,wav,oga,ogg,dokan
5
+ Requires at least: 3.5.0
6
+ Tested up to: 5.4
7
+ Stable tag: trunk
8
+ License: GPLv2 or later
9
+ License URI: http://www.gnu.org/licenses/gpl-2.0.html
10
+
11
+ Music Player for WooCommerce includes the MediaElement.js music player in the pages of the products with audio files associated.
12
+
13
+ == Description ==
14
+
15
+ Features of the Music Player for WooCommerce and Dokan:
16
+
17
+ ♪ Integrate a music player into the WooCommerce products and Dokan
18
+ ♪ Includes an audio player that supports formats: OGA, MP3, WAV, WMA
19
+ ♪ Includes multiple skins for the Music Player
20
+ ♪ Supports all most popular web browsers and mobile devices
21
+ ♪ Includes a widget to insert a playlist on sidebars
22
+ ♪ Includes a block to insert the playlists on pages using Gutenberg
23
+ ♪ Includes a widget to insert the playlists on pages using Elementor
24
+ ♪ Includes a widget for inserting the playlists on pages with Page Builder by SiteOrigin
25
+ ♪ Includes a control for inserting the playlists on pages with BeaverBuilder
26
+ ♪ Includes an element for inserting the playlists on pages with Visual Composer
27
+ ♪ Includes a module for inserting the playlists on pages with DIVI
28
+
29
+ Note: for the other editors, insert directly the playlists' shortcodes.
30
+
31
+ Music Player for WooCommerce includes the MediaElement.js music player in the pages of the products with audio files associated, and in the store's pages. It allows the integration with Dokan multivendor store. Furthermore, the plugin allows selecting between multiple skins.
32
+
33
+ MediaElement.js is an music player compatible with all major browsers: Internet Explorer, Firefox, Opera, Safari, Chrome and mobile devices: iPhone, iPad, Android. The music player is developed following the html5 standard. The music player supports the following file formats: MP3, WAV, WMA and OGA.
34
+
35
+ The basic version of the plugin, available for free from the WordPress Directory, has the features needed to include a music player in the pages of the products and the store.
36
+
37
+ **Premium Features**
38
+
39
+ * Allows playing the audio files in secure mode to prevent unauthorized downloading of the audio files.
40
+ * Allows to define the percent of the audio file's size to be played in secure mode.
41
+
42
+ == Installation ==
43
+
44
+ **To install Music Player for WooCommerce, follow these steps:**
45
+
46
+ 1. Download and unzip the plugin
47
+ 2. Upload the entire "woocommerce_music_player" directory to the "/wp-content/plugins/" directory
48
+ 3. Activate the plugin through the "Plugins" menu in "WordPress"
49
+ 4. Go to the products pages to configure the players.
50
+
51
+ == Interface ==
52
+
53
+ **Global Settings of Music Players**
54
+
55
+ The global settings are accessible through the menu option: "Settings/Music Player for WooCommerce".
56
+
57
+ * Include music player in all all products: checkbox to include the music player in all products.
58
+ * Include in: radio button to decide where to display the music player, in pages with a single entry, multiple entries, or both (both cases by default).
59
+ * Include players in cart: checkbox to include the music players on the cart page or not.
60
+ * Merge in grouped products: in grouped products, display the "Add to cart" buttons and quantity fields in the players rows.
61
+ * Player layout: list of available skins for the music player.
62
+ * Preload: to decide if preload the audio files, their metadata, or don't preload nothing at all.
63
+ * Play all: play all players in the page (one after the other).
64
+ * Player controls: determines the controls to include in the music player.
65
+ * Display the player's title: show/hide the name associated to the downloadable file.
66
+ * Protect the file: checkbox to playback the songs in secure mode (only available in the pro version of the plugin).
67
+ * Percent of audio used for protected playbacks: integer number from 0 to 100, that represents the percent of the size of the original audio file that will be used in the audio file for demo (only available in the pro version of the plugin).
68
+ * Apply the previous settings to all products pages in the website: tick the checkbox to apply the previous settings to all products overwriting the products' settings.
69
+
70
+ **Google Analytics Integration**
71
+
72
+ * Tracking id: Enter the tracking id in the property settings of Google Analytics account.
73
+
74
+ **Setting up the Music Players through the products' pages**
75
+
76
+ The Music Players are configured from the products pages and Dokan interface.
77
+
78
+ **Settings Interface**
79
+
80
+ * Include music player: checkbox to include the music player in the product's page, or not.
81
+ * Include in: radio button to decide where to display the music player, in pages with a single entry, multiple entries, or both (both cases by default).
82
+ * Merge in grouped products: in grouped products, display the "Add to cart" buttons and quantity fields in the players rows.
83
+ * Player layout: list of available skins for the music player.
84
+ * Preload: to decide if preload the audio files, their metadata, or don't preload nothing at all.
85
+ * Play all: play all players in the page (one after the other).
86
+ * Player controls: determines the controls to include in the music player.
87
+ * Display the player's title: show/hide the name associated to the downloadable file.
88
+ * Protect the file: checkbox to playback the songs in secure mode (only available in the pro version of the plugin).
89
+ * Percent of audio used for protected playbacks: integer number from 0 to 100, that represents the percent of the size of the original audio file that will be used in the audio file for demo (only available in the pro version of the plugin).
90
+ * Select my own demo files: checkbox to use different audio files for demo, than the audio files for selling (only available in the pro version of the plugin).
91
+ * Demo files: section similar to the audio files for selling, but in this case it allows to select different audio files for demo, and their names (only available in the pro version of the plugin).
92
+
93
+ **How the Pro version of the Music Player for WooCommerce protect the audio files?**
94
+
95
+ If the "Protect the file" checkbox was ticked in the product's page, and was entered an integer number through the attribute: "Percent of audio used for protected playbacks", the plugin will create a truncated copy of the audio files for selling (or the audio files for demo) into the "/wp-content/plugins/wcmp" directory, to be used as demo. The sizes of the audio files for demo are a percentage of the sizes of the original files (the integer number entered in the player's settings). So, the users cannot access to the original audio files, from the public pages of the products.
96
+
97
+ **Music Player for WooCommerce - Playlist Widget**
98
+
99
+ The widget allows to include a playlist on sidebars, with the downloadable files associated to all products with the music player enabled, or for only some of the products.
100
+
101
+ The widget settings:
102
+
103
+ * Title: the title of the widget on sidebar.
104
+ * Products IDs: enter the ids of products to include in the playlist, separated by comma, or the * symbol to include all products.
105
+ * Playlist layout: select between the new playlist layout and the original one.
106
+ * Player layout: select the layout of music players (the widget uses only the play/pause control)
107
+ * Preload: to decide if preload the audio files, their metadata, or don't preload nothing at all. This attribute has a global scope, and will modify the default settings.
108
+ * Play all: play all players in the page (one after the other). This attribute has a global scope, and will modify the default settings.
109
+ * Highlight the current product: if the checkbox is ticked, and the user is in the page of a product, and it is included in the playlist, the corresponding item would be highlighted in the playlist.
110
+ * Continue playing after navigate: if the checkbox is ticked, and there is a song playing when navigates, the player will continue playing after loading the webpage, in the same position.
111
+
112
+ Note: In mobiles devices where the direct action of user is required for playing audios and videos, the plugin cannot start playing dynamically.
113
+
114
+
115
+ **Music Player for WooCommerce - [wcmp-playlist] shortcode**
116
+
117
+ The `[wcmp-playlist]` shortcode allows to include a playlist on the pages' contents, with all products, or for some of them.
118
+
119
+ The shortcode attributes are:
120
+
121
+ * products_ids: define the ids of products to include in the playlist, separated by comma, or the * symbol to include all products:
122
+
123
+ `[wcmp-playlist products_ids="*"]`
124
+
125
+ * player_style: select the layout of music players (the playlist displays only the play/pause control):
126
+
127
+ `[wcmp-playlist products_ids="*" player_style="mejs-classic"]`
128
+
129
+ * highlight_current_product: if the playlist is included in a product's page, the corresponding item would be highlighted in the playlist:
130
+
131
+ `[wcmp-playlist products_ids="*" highlight_current_product="1"]`
132
+
133
+ * cover: allows to include the featured images in the playlist. The possible values are: 0 or 1, 0 is the value by default
134
+
135
+ `[wcmp-playlist products_ids="*" cover="1"]`
136
+
137
+ * continue_playing: if there is a song playing when navigates, the player will continue playing after loading the webpage in the same position:
138
+
139
+ `[wcmp-playlist products_ids="*" continue_playing="1"]`
140
+
141
+ * controls: allows to define the controls to be used with the players on playlist. The possible values are: track or all, to include only a play/pause button or all player's controls respectively.
142
+ * layout: allows to select the new or original layouts with the values: new or classic ("new" is the value by default):
143
+
144
+ `[wcmp-playlist products_ids="*" layout="classic"]`
145
+
146
+
147
+ Note: In mobiles devices where the direct action of user is required for playing audios and videos, the plugin cannot start playing dynamically.
148
+
149
+
150
+ **Hooks (actions and filters)**
151
+
152
+ * wcmp_before_player_shop_page: action called before the players containers in the shop pages.
153
+ * wcmp_after_player_shop_page: action called after the players containers in the shop pages.
154
+ * wcmp_before_players_product_page: action called before the players containers in the products pages.
155
+ * wcmp_after_players_product_page: action called after the players containers in the products pages.
156
+
157
+ * wcmp_audio_tag: filter called when the audio tag is generated. The callback function receives three parameters: the audio tag, the product's id, and the file's id;
158
+ * wcmp_file_name: filter called when the file's name is included with the player. The callback function receives three parameters: the file's name, the product's id, and the file's id;
159
+
160
+ * wcmp_widget_audio_tag: filter called when the audio tag is generated as a widget on sidebars. The callback function receives three parameters: the audio tag, the product's id, and the file's id;
161
+ * wcmp_widget_file_name: filter called when the file's name is included with the player as a widget on sidebars. The callback function receives three parameters: the file's name, the product's id, and the file's id;
162
+
163
+ **Other recommended plugins**
164
+
165
+ * If your project is a music store, and WooCommerce is more than you need it is possible to use [Music Store plugin](https://wordpress.org/plugins/music-store/ "Music Store")
166
+ * Or if you need a general purpose music and video player, not especific for WooCommerce, [CP Media Player - Audio Player and Video Player plugin](https://wordpress.org/plugins/audio-and-video-player/ "CP Media Player - Audio Player and Video Player")
167
+
168
+ == Frequently Asked Questions ==
169
+
170
+ = Q: Why the audio file is played partially? =
171
+
172
+ A: If you decide to protect the audio files, the plugin creates a truncated version of the file to be used as demo and prevent that the original file be copied by unauthorized users.
173
+
174
+ = Q: Why the music player is not loading on page? =
175
+
176
+ A: Verify that the theme used in your website, includes the function wp_footer(); in the template file "footer.php" or the template file "index.php"
177
+
178
+ = Q: What can I do if the woocommerce_music_player directory exists and the premium version of plugin cannot be installed? =
179
+
180
+ A: Go to the plugins section in WordPress, deactivate the free version of Music Player for WooCommerce, and delete it ( Don't worry, this process don't modify players configured with the free version of the plugin), and finally install and activate the premium version of plugin.
181
+
182
+ = Q: Can be modified the size of audio files played in secure mode? =
183
+
184
+ A: In the pro version of the plugin the files for demo are generated dynamically to prevent the access to the original files.
185
+
186
+ Each time save the data of a product, the files for demo are deleted and generated again, so, you simply should modify the percentage of the audio file to be used for demo in the product's page.
187
+
188
+ == Screenshots ==
189
+ 01. Music players in the store's pages
190
+ 02. Music player in the products pages
191
+ 03. Music player skins
192
+ 04. Music player settings
193
+ 05. Playlist widget
194
+ 06. Inserting the playlist in Gutenberg
195
+ 07. Inserting the playlist in Elementor
196
+ 08. Inserting the playlist with Page Builder by SiteOrigin
197
+ 09. Inserting the playlist BeaverBuilder
198
+ 10. Inserting the playlist Visual Composer
199
+
200
+ == Changelog ==
201
+
202
+ = 1.0.104 =
203
+
204
+ * Modifies the settings page of the plugin.
205
+ * Complete the language files.
206
+ * Improves the errors detection by including additional error logs.
207
+ * Includes a new option to allow playing the original audio files instead the demo versions, if the logged user has bought the product (Professional version).
208
+
209
+ = 1.0.103 =
210
+
211
+ * Fixes a notice.
212
+ * Improves the plugin registration process (Professional version).
213
+
214
+ = 1.0.102 =
215
+
216
+ * Modifies the integration of player with the new WooCommerce blocks for Gutenberg.
217
+ * Fixes a conflict with some theme styles.
218
+
219
+ = 1.0.101 =
220
+
221
+ * Fixes a conflict with Firefox.
222
+ * Includes the integration of player with the new WooCommerce blocks for Gutenberg.
223
+
224
+ = 1.0.100 =
225
+
226
+ * Increase the timeout while reads the audio files when they are hosted in external domains.
227
+
228
+ = 1.0.99 =
229
+
230
+ * Modifies the playlist widget.
231
+
232
+ = 1.0.98 =
233
+
234
+ * Includes the integration with Dokan multivendor store.
235
+
236
+ = 1.0.97 =
237
+
238
+ * Modifies the script that generates the players for those pages whose contents are loaded with AJAX, and don't trigger document onready or window onload events.
239
+
240
+ = 1.0.96 =
241
+
242
+ * Fixes an issue re-positioning the player over covers when the browser is resize.
243
+ * If the playlist shortcode is inserted into a WooCommerce product without the products_ids attribute, the playlist will be generated with only the current product.
244
+
245
+ = 1.0.95 =
246
+
247
+ * Fixes some conflicts with third party plugins.
248
+
249
+ = 1.0.94 =
250
+
251
+ * Adapts the plugin's blocks to the new version of the Gutenberg editor.
252
+
253
+ = 1.0.93 =
254
+
255
+ * Includes two new actions: wcmp_main_player and wcmp_all_players to allow the themes' developers insert the players in the preferred places of the products' pages and the stores' items.
256
+
257
+ = 1.0.92 =
258
+
259
+ * Includes a new feature, to allow insert the music players only for registered users.
260
+
261
+ = 1.0.91 =
262
+
263
+ * Fixes some conflict with the styles.
264
+
265
+ = 1.0.90 =
266
+
267
+ * Modifies the access to the website and documentation.
268
+
269
+ = 1.0.89 =
270
+
271
+ * Makes easier the access to the WooCommerce hooks.
272
+
273
+ = 1.0.88 =
274
+
275
+ * Modifies the player's styles.
276
+
277
+ = 1.0.87 =
278
+
279
+ * Includes a new option in the troubleshooting section to generate the music players in the page onload event.
280
+
281
+ = 1.0.86 =
282
+
283
+ * Includes the access to the online demo from the plugin's interface.
284
+
285
+ = 1.0.85 =
286
+
287
+ * Includes additional validations to verify that WooCommerce is installed and active.
288
+
289
+ = 1.0.84 =
290
+ = 1.0.83 =
291
+
292
+ * Modifies the code that generates the files for demo.
293
+
294
+ = 1.0.82 =
295
+
296
+ * Modifies the language files.
297
+ * Improves the javascript performance.
298
+
299
+ = 1.0.81 =
300
+
301
+ * Reduces the server workload and the number of redirections required.
302
+
303
+ = 1.0.80 =
304
+
305
+ * Fixes a conflict between the DIVI module and the Classic WordPress Editor.
306
+
307
+ = 1.0.79 =
308
+
309
+ * New section for tracking Google Analytics events when the demos are playing.
310
+
311
+ = 1.0.78 =
312
+
313
+ * Fixes a conflict with third party plugins.
314
+
315
+ = 1.0.77 =
316
+
317
+ * Implements a basic module to allow the insertion of the playlist module from DIVI.
318
+
319
+ = 1.0.76 =
320
+
321
+ * Fixes a conflict with third-party plugins.
322
+
323
+ = 1.0.75 =
324
+
325
+ * Includes new tips about playing files stored in DropBox.
326
+
327
+ = 1.0.74 =
328
+
329
+ * Includes a Tips section in the player's interface to help the users configure them properly.
330
+
331
+ = 1.0.73 =
332
+
333
+ * Implements a specific element to insert the forms using Visual Composer.
334
+
335
+ = 1.0.72 =
336
+
337
+ * Fixes a minor issue in the playlist shortcode.
338
+
339
+ = 1.0.71 =
340
+
341
+ * Improves the security sanitizing every parameter used by the plugin.
342
+
343
+ = 1.0.70 =
344
+
345
+ * Includes the integration with BeaverBuilder.
346
+
347
+ = 1.0.69 =
348
+
349
+ * Fixes some notices.
350
+
351
+ = 1.0.68 =
352
+
353
+ * Improves the integration with third-party plugins, and the cloud.
354
+
355
+ = 1.0.67 =
356
+
357
+ * Includes the cover attribute in the playlist shortcode `[wcmp-playlist]` for including the products' featured images in the playlist.
358
+
359
+ = 1.0.66 =
360
+
361
+ * Fixes an issue displaying the add to cart icon, in the playlist when the product's price is less than 1.
362
+
363
+ = 1.0.65 =
364
+
365
+ * Modifies the plugin to allow the play all feature in iOS.
366
+
367
+ = 1.0.64 =
368
+
369
+ * Improves the loading of the audio files without affecting the page load.
370
+ * Fixes an issue with the play/pause button of one of player's layout.
371
+ * Fixes an issue with the preload attribute of products' settings.
372
+ * Includes new attributes in the troubleshoot section to decide the WooCommerce hooks to use in the pages of the shop and products, in case the theme active on the website does not use the usual WooCommerce hooks.
373
+
374
+ = 1.0.63 =
375
+
376
+ * Includes the integration with the WooCommerce Product Table plugin by Barn2 Media, including the player in the column for the products' names.
377
+
378
+ = 1.0.62 =
379
+
380
+ * Selects the none option as the default value for the Preload attribute in the players settings to prevent errors in web servers with limited resources.
381
+
382
+ = 1.0.61 =
383
+
384
+ * Improves the module that manages the players in the shopping cart.
385
+
386
+ = 1.0.60 =
387
+
388
+ * Fixes an issue cause by the previous updates.
389
+
390
+ = 1.0.59 =
391
+
392
+ * Allows to include the music players in the shopping cart, from a checkbox in the settings page of the plugin.
393
+
394
+ = 1.0.58 =
395
+
396
+ * Implements a Widget to allow the specific integration with the Page Builder by SiteOrigin.
397
+
398
+ = 1.0.57 =
399
+
400
+ * Modifies the blocks for the Gutenberg editor, preparing the plugin for WordPress 5.1
401
+
402
+ = 1.0.56 =
403
+
404
+ * Improves the design of the playlist and players.
405
+ * Includes a new attribute in the widget to select the playlist layout.
406
+ * Display the products in the playlist following the same order than their ids were entered into the playlist shortcode, or widget.
407
+
408
+ = 1.0.55 =
409
+
410
+ * Implements a new layout for the playlists inserted with the playlists' shortcodes, and accepts a new attribute in the shortcode for selecting the previous layout: layout="old"
411
+ * Fixes some CSS conflicts.
412
+ * Removes some unneeded attributes from the Widget settings.
413
+
414
+ = 1.0.54 =
415
+
416
+ * Modifies the language files and plugin headers.
417
+
418
+ = 1.0.53 =
419
+
420
+ * Implements the specific integration with the Elementor page builder.
421
+
422
+ = 1.0.52 =
423
+
424
+ * Fixes an issue in the preload attribute in the form's settings.
425
+ * Creates a preview of music players when the playlist shortcode is inserted in the Gutenberg editor.
426
+
427
+ = 1.0.51 =
428
+
429
+ * Fixes an issue generating the URLs of demo files.
430
+
431
+ = 1.0.50 =
432
+
433
+ * Fixes an issue determining the files' types in variable and grouped products.
434
+ * Fixes an issue with the CSS rules.
435
+
436
+ = 1.0.49 =
437
+
438
+ * Fixes an issue between the Promote Banner and the official distribution of WP5.0
439
+
440
+ = 1.0.48 =
441
+
442
+ * Includes some modifications in the settings.
443
+
444
+ = 1.0.47 =
445
+
446
+ * Fixes an issue when the URLs of audio files in the products' settings are relative URLs.
447
+
448
+ = 1.0.46 =
449
+
450
+ * Fixes a conflict with the "Speed Booster Pack" plugin.
451
+
452
+ = 1.0.45 =
453
+
454
+ * Includes a troubleshoot area in the settings page of the plugin, to improves the integration with audio files that are stored in the cloud and their types (extensions) are unclear.
455
+
456
+ = 1.0.44 =
457
+
458
+ * Improves the module that determines the duration of audio files.
459
+ * With this update the plugin is able to understand the URLs to the audio files without the schema component.
460
+
461
+ = 1.0.43 =
462
+
463
+ * Hides the promotion banner for the majority of roles and fixes a conflict between the promotion banner and the Gutenberg editor.
464
+
465
+ = 1.0.42 =
466
+
467
+ * Implements the integration with the Gutenberg editor.
468
+
469
+ = 1.0.41 =
470
+
471
+ * Fixes an ambiguity between the "Play All" attribute in the settings page of the plugin and products' settings.
472
+
473
+ = 1.0.40 =
474
+
475
+ * Includes a new and experimental feature. In music players defined as play/pause buttons, displays them on the products' covers.
476
+
477
+ = 1.0.39 =
478
+
479
+ * Fixes some possible conflicts with other plugins and themes that include to medialementjs player.
480
+
481
+ = 1.0.38 =
482
+
483
+ * Removes functions that were deprecated in PHP 7.2
484
+
485
+ = 1.0.37 =
486
+
487
+ * Improves the appearance and behavior of plugin in grouped products.
488
+
489
+ = 1.0.36 =
490
+
491
+ * Modifies the way the music players are generated.
492
+ * Replaces some deprecated functions in WooCommerce.
493
+ * The Professional version allows the integration with Google Drive to store the demo files in the cloud.
494
+
495
+ = 1.0.35 =
496
+
497
+ * Includes some modifications in the grouped products.
498
+
499
+ = 1.0.34 =
500
+
501
+ * Fixes an issue when the WordPress and the public website include different schemes in their URLs.
502
+
503
+ = 1.0.33 =
504
+
505
+ * Includes the crossOrigin attribute in the audio tags for playing files in external domains.
506
+
507
+ = 1.0.32 =
508
+
509
+ * Includes the controls attribute in the `[wcmp-playlist]` shortcode, with the possible values: track and all for displaying only the play/pause button or all player's controls.
510
+ * The professional version of the plugin allows to define a message to be shown beside the music players with a message describing the use of partial versions of the audio files for selling as demo.
511
+
512
+ = 1.0.31 =
513
+
514
+ * Includes the music player with a different WooCommerce action to display it even if the product is not for selling (does not includes an "Add to cart" button).
515
+
516
+ = 1.0.30 =
517
+
518
+ * Modifies the settings page of the plugin.
519
+ * The professional version allows to use the FFMpeg application in the server to generate the demo files.
520
+
521
+ = 1.0.29 =
522
+
523
+ * Fixes an issue with the play all feature.
524
+
525
+ = 1.0.28 =
526
+
527
+ * Adds the settings page to define the default players' settings. From the settings page it is possible activate and configure the player in all existent and future products.
528
+
529
+ = 1.0.27 =
530
+
531
+ * Improved the process that determines the duration of the original audio files.
532
+
533
+ = 1.0.26 =
534
+
535
+ * For the audio files published in the website, the plugin displays the duration of the original file, even if player was configured to protect the original files creating truncated versions for demo.
536
+
537
+ = 1.0.25 =
538
+
539
+ * Loads a specific version of the MediaElementJS library to prevent an issue with the next version of WordPress 4.9
540
+
541
+ = 1.0.24 =
542
+
543
+ * Improves the players' settings.
544
+
545
+ = 1.0.23 =
546
+
547
+ * Allows configure all products in the website at the same time.
548
+
549
+ = 1.0.22 =
550
+
551
+ * Includes a new option to decide the pages where showing the music players: pages with a single entry, with multiple-entries, or both.
552
+
553
+ = 1.0.21 =
554
+
555
+ * Allows controlling the "preload" attribute of audio tags through the player's settings.
556
+
557
+ = 1.0.20 =
558
+
559
+ * Modifies the widget.
560
+ * Adds the `[wcmp-playlist]` shortcode to include a playlist in the website's pages.
561
+
562
+ = 1.0.19 =
563
+
564
+ * Fixes the order of players in grouped and variable products.
565
+
566
+ = 1.0.18 =
567
+
568
+ * Fixes an issue in the promote banner.
569
+
570
+ = 1.0.17 =
571
+
572
+ * Modifies the module for accessing the WordPress reviews section.
573
+
574
+ = 1.0.16 =
575
+
576
+ * Modifies the module that merges the music players with the products titles and the "add to cart" buttons of grouped products.
577
+
578
+ = 1.0.15 =
579
+
580
+ * Improves the access to the plugin documentation.
581
+ * Modifies the module that delete the copies of files used by the player.
582
+
583
+ = 1.0.14 =
584
+
585
+ * Modifies the plugin to be compatible with the new version of WooCommerce 3.x
586
+
587
+ = 1.0.13 =
588
+
589
+ * Includes the "Play all" option in the settings, for playing all audio files in the same page, one after the other.
590
+
591
+ = 1.0.12 =
592
+
593
+ * Fixes an issue accessing to outer-domain audio files.
594
+ * Includes a new option in the player's settings to display the "Add to Cart" buttons, beside each player in the Grouped Products.
595
+ * Adds a list of Hooks (actions and filters) to allow developers and designers modify the players section.
596
+
597
+ = 1.0.11 =
598
+
599
+ * Fixes a conflict with the links to the products pages in the shop's pages.
600
+
601
+ = 1.0.10 =
602
+
603
+ * Move the Music Player settings to its own metabox.
604
+ * Allows to integrate the players with "Simple", "Variable", and "Grouped" products (the previous version was compatible only with "Simple" products).
605
+
606
+ = 1.0.9 =
607
+
608
+ * Modifies the plugin's interface.
609
+ * Fixes some tags in the music players.
610
+ * Clears the generated audio files when the plugin is deactivated.
611
+
612
+ = 1.0.8 =
613
+
614
+ * Fixes an issue with the products' ids in the playlist widget.
615
+
616
+ = 1.0.7 =
617
+
618
+ * Includes some changes in the plugin's interface.
619
+
620
+ = 1.0.6 =
621
+
622
+ * Allows show/hide the name of downloadable files beside the player.
623
+ * Includes the widget "Music Player for WooCommerce - Playlist"
624
+
625
+ = 1.0.5 =
626
+
627
+ * Adds a new feature to specify the controls in the music player.
628
+
629
+ = 1.0.4 =
630
+
631
+ * Modifies the module to determine if the audio file is local to the website or not.
632
+
633
+ = 1.0.3 =
634
+
635
+ * Allows to play m4a files.
636
+
637
+ = 1.0.2 =
638
+
639
+ * Fixed some conflicts with styles of the active themes.
640
+
641
+ = 1.0.1 =
642
+
643
+ * Fixed an issue in the URL of the audio files.
644
+
645
+ = 1.0.0 =
646
+
647
+ * First version released.
648
+
649
+ == Upgrade Notice ==
650
+
651
+ = 1.0.104 =
652
+
653
+ Important note: If you are using the Professional version don't update via the WP dashboard but using your personal update link. Contact us if you need further information: http://wordpress.dwbooster.com/support
views/assets/skin1.png ADDED
Binary file
views/assets/skin1_btn.png ADDED
Binary file
views/assets/skin2.png ADDED
Binary file
views/assets/skin2_btn.png ADDED
Binary file
views/assets/skin3.png ADDED
Binary file
views/assets/skin3_btn.png ADDED
Binary file
views/global_options.php ADDED
@@ -0,0 +1,381 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ if( !defined( 'WCMP_PLUGIN_URL' ) ) { echo 'Direct access not allowed.'; exit; }
3
+
4
+ // include resources
5
+ wp_enqueue_style( 'wcmp-admin-style', plugin_dir_url(__FILE__).'../css/style.admin.css', array(), '5.0.23' );
6
+
7
+ $troubleshoot_default_extension = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_default_extension', false );
8
+ $force_main_player_in_title = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_force_main_player_in_title', 1 );
9
+ $troubleshoot_onload = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_onload', false );
10
+ $include_main_player_hook = trim($GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr('_wcmp_main_player_hook', ''));
11
+ $include_all_players_hook = trim($GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr('_wcmp_all_players_hook', ''));
12
+
13
+ $enable_player = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_enable_player', false );
14
+ $show_in = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_show_in', 'all' );
15
+ $players_in_cart = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_players_in_cart', false );
16
+ $player_style = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_player_layout', WCMP_DEFAULT_PLAYER_LAYOUT );
17
+ $player_controls= $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_player_controls', WCMP_DEFAULT_PLAYER_CONTROLS );
18
+ $player_title = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_player_title',1 ) );
19
+ $merge_grouped = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_merge_in_grouped',0 ) );
20
+ $preload = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr(
21
+ '_wcmp_preload',
22
+ // This option is only for compatibility with versions previous to 1.0.28
23
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( 'preload', 'none' )
24
+ );
25
+ $play_all = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr(
26
+ '_wcmp_play_all',
27
+ // This option is only for compatibility with versions previous to 1.0.28
28
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( 'play_all', 0 )
29
+ );
30
+ $on_cover = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_on_cover', 0 ) );
31
+ $analytics_property = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_analytics_property', '' );
32
+ $registered_only = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( '_wcmp_registered_only', 0 );
33
+ ?>
34
+ <h1><?php _e('Music Player for WooCommerce - Global Settings', 'music-player-for-woocommerce'); ?></h1>
35
+ <div style="border:1px solid #E6DB55;margin-bottom:10px;padding:5px;background-color: #FFFFE0;">
36
+ <?php
37
+ _e(
38
+ 'For reporting any issue or to request a customization, <a href="https://wordpress.dwbooster.com/contact-us" target="_blank">CLICK HERE</a><br />
39
+ For testing the premium version of the plugin, visit the online demo:<br/> <a href="https://demos.dwbooster.com/music-player-for-woocommerce/wp-login.php" target="_blank">Administration area: Click to access the administration area demo</a><br/>
40
+ <a href="https://demos.dwbooster.com/music-player-for-woocommerce/" target="_blank">Public page: Click to visit the WooCommerce Store</a>',
41
+ 'music-player-for-woocommerce'
42
+ );
43
+ ?>
44
+ </div>
45
+ <form method="post">
46
+ <div class="postbox">
47
+ <h3 class="hndle" style="padding:5px;color:#DDDDDD;"><?php _e('Registering of Plugin', 'music-player-for-woocommerce'); ?></h3>
48
+ <div class="inside">
49
+ <label style="color:#DDDDDD;"><?php _e('Enter the email address of buyer', 'music-player-for-woocommerce'); ?>:</label>
50
+ <br><input type="text" disabled> <input value="<?php esc_attr_e(__('Register', 'music-player-for-woocommerce')); ?>" disabled class="button-primary">
51
+ </div>
52
+ </div>
53
+ </form>
54
+ <form method="post">
55
+ <input type="hidden" name="wcmp_nonce" value="<?php echo wp_create_nonce( 'wcmp_updating_plugin_settings' ); ?>" />
56
+ <table class="widefat" style="border-left:0;border-right:0;border-bottom:0;padding-bottom:0;">
57
+ <tr>
58
+ <td>
59
+ <div style="border:1px solid #E6DB55;margin-bottom:10px;padding:5px;background-color: #FFFFE0;">
60
+ <?php
61
+ _e(
62
+ '<p>The player uses the audio files associated to the product. If you want protecting the audio files for selling, tick the checkbox: <b>"Protect the file"</b>, in whose case the plugin will create a truncated version of the audio files for selling to be used for demo. The size of audio files for demo is based on the number entered through the attribute: <b>"Percent of audio used for protected playbacks"</b>.</p><p><b>Protecting the files prevents that malicious users can access to the original audio files without pay for them.</b></p>',
63
+ 'music-player-for-woocommerce'
64
+ );
65
+ ?>
66
+ </div>
67
+ </td>
68
+ </tr>
69
+ <tr>
70
+ <td>
71
+ <table class="widefat" style="border:1px solid #e1e1e1;margin-bottom:20px;">
72
+ <tr>
73
+ <td colspan="2"><h2><?php _e( 'General Settings', 'music-player-for-woocommerce' ); ?></h2></td>
74
+ </tr>
75
+ <tr>
76
+ <td width="30%"><?php _e( 'Include the players only for registered users', 'music-player-for-woocommerce' ); ?></td>
77
+ <td><input type="checkbox" name="_wcmp_registered_only" <?php print(($registered_only) ? 'CHECKED' : '' ); ?> /></td>
78
+ </tr>
79
+ <tr>
80
+ <td colspan="2" style="color:red;"><?php _e( 'The general settings affect only the PRO version of the plugin', 'music-player-for-woocommerce'); ?>. <a target="_blank" href="https://wcmp.dwbooster.com"><?php _e('CLICK HERE TO GET THE PRO VERSION OF THE PLUGIN', 'music-player-for-woocommerce'); ?></a></td>
81
+ </tr>
82
+ <tr>
83
+ <td width="30%" style="color:#DDDDDD;"><?php _e( 'For buyers, play the purchased audio files instead the truncated files for demo', 'music-player-for-woocommerce' ); ?></td>
84
+ <td><input type="checkbox" DISABLED /></td>
85
+ </tr>
86
+ <tr>
87
+ <td colspan="2"><hr /></td>
88
+ </tr>
89
+ <tr>
90
+ <td width="30%" style="color:#DDDDDD;"><?php _e( 'Truncate the audio files for demo with ffmpeg', 'music-player-for-woocommerce' ); ?></td>
91
+ <td><input type="checkbox" DISABLED /></td>
92
+ </tr>
93
+ <tr>
94
+ <td width="30%" style="color:#DDDDDD;"><?php _e( 'ffmpeg path', 'music-player-for-woocommerce' ); ?></td>
95
+ <td><input type="text" DISABLED /></td>
96
+ </tr>
97
+ <tr>
98
+ <td colspan="2"><hr /></td>
99
+ </tr>
100
+ <tr>
101
+ <td width="30%" style="color:#DDDDDD;"><?php _e( 'Delete the demo files generated previously', 'music-player-for-woocommerce' ); ?></td>
102
+ <td><input type="checkbox" DISABLED /></td>
103
+ </tr>
104
+ <tr>
105
+ <td colspan="2"><hr /></td>
106
+ </tr>
107
+ <tr>
108
+ <td width="30%" style="color:#DDDDDD;"><?php _e( 'Store demo files on Google Drive', 'music-player-for-woocommerce' ); ?></td>
109
+ <td><input type="checkbox" disabled /></td>
110
+ </tr>
111
+ <tr>
112
+ <td width="30%" style="color:#DDDDDD;"><?php _e( 'Import a JSON Key file', 'music-player-for-woocommerce' ); ?></td>
113
+ <td>
114
+ <input type="file" disabled />
115
+ <br /><br />
116
+ <div style="border:1px solid #E6DB55;margin-bottom:10px;padding:5px;background-color: #FFFFE0;">
117
+ <h3>Turn on the Drive API</h3>
118
+ <p>
119
+ <ol>
120
+ <li>
121
+ Use <a href="javascript:void(0);" target="_blank" class="gc-analytics-event" data-category="Quickstart" data-action="Enable" data-label="Drive API, PHP">this wizard</a> to create or select a project in the Google Developers Console and automatically turn on the API. Click <strong>Continue</strong>, then <strong>Go to credentials</strong>.
122
+ </li>
123
+ <li>
124
+ On the <strong>Add credentials to your project</strong> page, click the <strong>Cancel</strong> button.
125
+ </li>
126
+ <li>
127
+ At the top of the page, select the <strong>OAuth consent screen</strong> tab. Select an
128
+ <strong>Email address</strong>, enter a <strong>Product name</strong> if not already set, and click the <strong>Save</strong> button.
129
+ </li>
130
+ <li>
131
+ Select the <strong>Credentials</strong> tab, click the <strong>Create credentials</strong> button and select <strong>OAuth client ID</strong>.
132
+ </li>
133
+ <li>Press the <strong>Configure consent screen</strong> button, enter the name <strong>WooCommerce Music Player</strong> in the attribute: <strong>Product name shown to users</strong>, and click the <strong>Save</strong> button.</li>
134
+ <li>
135
+ Select the application type <strong>Web application</strong>, enter the URL below as the <strong>Authorized redirect URIs</strong>:<br><br>
136
+ .........
137
+ <br><br>
138
+ and click the <strong>Create</strong> button.
139
+ </li>
140
+ <li>
141
+ Click <strong>OK</strong> to dismiss the resulting dialog.
142
+ </li>
143
+ <li>
144
+ Click the <span style="display:inline-block;width:14px;height:14px;"><svg viewBox="0 0 14 14"><g><rect x="1" y="11" width="12" height="2"></rect><polygon points="7 5 12 10 2 10 " transform="translate(7.000000, 7.500000) scale(1, -1) translate(-7.000000, -7.500000) "></polygon><rect x="5" y="1" width="4" height="4"></rect></g></svg></span> (Download JSON) button to the right of the client ID.
145
+ </li>
146
+ <li>
147
+ Select the file through the <strong>"Import a JSON Key file"</strong> attribute.
148
+ </li>
149
+ </ol>
150
+ </p>
151
+ </div>
152
+ </td>
153
+ </tr>
154
+ <tr>
155
+ <td colspan="2"><hr /></td>
156
+ </tr>
157
+ <tr>
158
+ <td colspan="2"><h2><?php _e('Troubleshoot Area', 'music-player-for-woocommerce'); ?></h2></td>
159
+ </tr>
160
+ <tr>
161
+ <td width="30%">
162
+ <?php _e( 'Loading players in the onload event', 'music-player-for-woocommerce' ); ?>
163
+ </td>
164
+ <td>
165
+ <input type="checkbox" name="_wcmp_onload" <?php if($troubleshoot_onload) print 'CHECKED'; ?>/>
166
+ <?php _e( 'tick the checkbox if the players are not being loaded properly', 'music-player-for-woocommerce' ); ?>
167
+ </td>
168
+ </tr>
169
+ <tr>
170
+ <td width="30%">
171
+ <?php _e( 'For files whose extensions cannot be determined', 'music-player-for-woocommerce' ); ?>
172
+ </td>
173
+ <td>
174
+ <input type="checkbox" name="_wcmp_default_extension" <?php if($troubleshoot_default_extension) print 'CHECKED'; ?>/>
175
+ <?php _e( 'handle them as mp3 files', 'music-player-for-woocommerce' ); ?>
176
+ </td>
177
+ </tr>
178
+ <tr>
179
+ <td width="30%">
180
+ <?php _e( 'For the WooCommerce Gutenberg Blocks, include the main player in the products titles', 'music-player-for-woocommerce' ); ?>
181
+ </td>
182
+ <td>
183
+ <input type="checkbox" name="_wcmp_force_main_player_in_title" <?php if($force_main_player_in_title) print 'CHECKED'; ?>/>
184
+ <?php _e( 'Includes the main player in front of products titles', 'music-player-for-woocommerce' ); ?>
185
+ </td>
186
+ </tr>
187
+ <tr>
188
+ <td width="30%">
189
+ <?php _e( 'WooCommerce hook used to display the players in the shop pages', 'music-player-for-woocommerce' ); ?>
190
+ </td>
191
+ <td>
192
+ <input type="text" name="_wcmp_main_player_hook" value="<?php esc_attr_e($include_main_player_hook); ?>" style="width:100%" /><br />
193
+ <?php _e( 'The plugin uses by default the <b>woocommerce_shop_loop_item_title</b> hook. If the player is not being displayed, enter the hook used by the theme active on your website.', 'music-player-for-woocommerce' ); ?>
194
+ </td>
195
+ </tr>
196
+ <tr>
197
+ <td width="30%">
198
+ <?php _e( 'WooCommerce hook used to display the players in the products pages', 'music-player-for-woocommerce' ); ?>
199
+ </td>
200
+ <td>
201
+ <input type="text" name="_wcmp_all_players_hook" value="<?php esc_attr_e($include_all_players_hook); ?>" style="width:100%" /><br />
202
+ <?php _e( 'The plugin uses by default the <b>woocommerce_single_product_summary</b> hook. If the player is not being displayed, enter the hook used by the theme active on your website.', 'music-player-for-woocommerce' ); ?>
203
+ </td>
204
+ </tr>
205
+ <tr>
206
+ <td></td>
207
+ <td><?php _e('Click on the <a href="https://docs.woocommerce.com/wc-apidocs/hook-docs.html" target="_blank">THIS LINK</a> for the list of available <a href="https://docs.woocommerce.com/wc-apidocs/hook-docs.html" target="_blank" style="font-weight:bold;font-size:1.3em;">WooCommerce Hooks</a>', 'music-player-for-woocommerce'); ?></td>
208
+ </tr>
209
+ </table>
210
+ <table class="widefat wcmp-player-settings" style="border:1px solid #e1e1e1;">
211
+ <tr>
212
+ <td width="30%"><?php _e( 'Include music player in all products', 'music-player-for-woocommerce' ); ?></td>
213
+ <td><div class="wcmp-tooltip"><span class="wcmp-tooltiptext"><?php _e('The player is shown only if the product is "downloadable" with at least an audio file between the "Downloadable files", or you have selected your own audio files', 'music-player-for-woocommerce'); ?></span><input type="checkbox" name="_wcmp_enable_player" <?php echo (( $enable_player ) ? 'checked' : '' ); ?> /></div></td>
214
+ </tr>
215
+ <tr>
216
+ <td width="30%"><?php _e( 'Include in', 'music-player-for-woocommerce' ); ?></td>
217
+ <td>
218
+ <input type="radio" name="_wcmp_show_in" value="single" <?php echo (( $show_in == 'single' ) ? 'checked' : '' ); ?> />
219
+ <?php _e('single-entry pages <i>(Product\'s page only)</i>', 'music-player-for-woocommerce'); ?><br />
220
+
221
+ <input type="radio" name="_wcmp_show_in" value="multiple" <?php echo (( $show_in == 'multiple' ) ? 'checked' : '' ); ?> />
222
+ <?php _e('multiple entries pages <i>(Shop pages, archive pages, but not in the product\'s page)</i>', 'music-player-for-woocommerce'); ?><br />
223
+
224
+ <input type="radio" name="_wcmp_show_in" value="all" <?php echo (( $show_in == 'all' ) ? 'checked' : '' ); ?> />
225
+ <?php _e('all pages <i>(with single or multiple-entries)</i>', 'music-player-for-woocommerce'); ?>
226
+ </td>
227
+ </tr>
228
+ <tr>
229
+ <td width="30%"><?php _e( 'Include players in cart', 'music-player-for-woocommerce' ); ?></td>
230
+ <td>
231
+ <input type="checkbox" name="_wcmp_players_in_cart" <?php echo (( $players_in_cart ) ? 'checked' : '' ); ?> />
232
+ </td>
233
+ </tr>
234
+ <tr>
235
+ <td width="30%"><?php _e( 'Merge in grouped products', 'music-player-for-woocommerce' ); ?></td>
236
+ <td><input type="checkbox" name="_wcmp_merge_in_grouped" <?php echo (( $merge_grouped ) ? 'checked' : '' ); ?> /><br /><em><?php _e( 'In grouped products, display the "Add to cart" buttons and quantity fields in the players rows', 'music-player-for-woocommerce' ); ?></em></td>
237
+ </tr>
238
+ <tr>
239
+ <td valign="top" width="30%"><?php _e( 'Player layout', 'music-player-for-woocommerce' ); ?></td>
240
+ <td>
241
+ <table>
242
+ <tr>
243
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-classic" <?php echo (($player_style == 'mejs-classic') ? 'checked' : '') ;?> /></td>
244
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin1.png" /></td>
245
+ </tr>
246
+
247
+ <tr>
248
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-ted" <?php echo (($player_style == 'mejs-ted') ? 'checked' : '') ;?> /></td>
249
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin2.png" /></td>
250
+ </tr>
251
+
252
+ <tr>
253
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-wmp" <?php echo (($player_style == 'mejs-wmp') ? 'checked' : '') ;?> /></td>
254
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin3.png" /></td>
255
+ </tr>
256
+ </table>
257
+ </td>
258
+ </tr>
259
+ <tr>
260
+ <td width="30%">
261
+ <?php _e( 'Preload', 'music-player-for-woocommerce' ); ?>
262
+ </td>
263
+ <td>
264
+ <label><input type="radio" name="_wcmp_preload" value="none" <?php if($preload == 'none') echo 'CHECKED'; ?> /> None</label><br />
265
+ <label><input type="radio" name="_wcmp_preload" value="metadata" <?php if($preload == 'metadata') echo 'CHECKED'; ?> /> Metadata</label><br />
266
+ <label><input type="radio" name="_wcmp_preload" value="auto" <?php if($preload == 'auto') echo 'CHECKED'; ?> /> Auto</label><br />
267
+ </td>
268
+ </tr>
269
+ <tr>
270
+ <td width="30%">
271
+ <?php _e( 'Play all', 'music-player-for-woocommerce' ); ?>
272
+ </td>
273
+ <td>
274
+ <input type="checkbox" name="_wcmp_play_all" <?php if($play_all) echo 'CHECKED'; ?> />
275
+ </td>
276
+ </tr>
277
+ <tr>
278
+ <td width="30%"><?php _e( 'Player controls', 'music-player-for-woocommerce' ); ?></td>
279
+ <td>
280
+ <input type="radio" name="_wcmp_player_controls" value="button" <?php echo (( $player_controls == 'button' ) ? 'checked' : ''); ?> /> <?php _e( 'the play/pause button only', 'music-player-for-woocommerce' ); ?><br />
281
+ <input type="radio" name="_wcmp_player_controls" value="all" <?php echo (( $player_controls == 'all' ) ? 'checked' : ''); ?> /> <?php _e( 'all controls', 'music-player-for-woocommerce' ); ?><br />
282
+ <input type="radio" name="_wcmp_player_controls" value="default" <?php echo (( $player_controls == 'default' ) ? 'checked' : ''); ?> /> <?php _e( 'the play/pause button only, or all controls depending on context', 'music-player-for-woocommerce' ); ?>
283
+ <div class="wcmp-on-cover" style="margin-top:10px;">
284
+ <input type="checkbox" name="_wcmp_player_on_cover" value="default" <?php
285
+ echo ((!empty($on_cover) && ( $player_controls == 'button' || $player_controls == 'default')) ? 'checked' : '');
286
+ ?> />
287
+ <?php _e( 'for play/pause button players display them on cover images.', 'music-player-for-woocommerce' ); ?>
288
+ <i>
289
+ <?php
290
+ _e('(This feature is experimental, and will depend on the theme active on the website.)', 'music-player-for-woocommerce');
291
+ ?>
292
+ </i>
293
+ </div>
294
+ </td>
295
+ </tr>
296
+ <tr>
297
+ <td width="30%"><?php _e( 'Display the player\'s title', 'music-player-for-woocommerce' ); ?></td>
298
+ <td>
299
+ <input type="checkbox" name="_wcmp_player_title" <?php echo (( !empty($player_title) ) ? 'checked' : ''); ?> />
300
+ </td>
301
+ </tr>
302
+ <tr>
303
+ <td colspan="2" style="color:red;"><?php _e( 'The security feature is only available in the PRO version of the plugin', 'music-player-for-woocommerce'); ?>. <a target="_blank" href="https://wcmp.dwbooster.com"><?php _e('CLICK HERE TO GET THE PRO VERSION OF THE PLUGIN', 'music-player-for-woocommerce'); ?></a></td>
304
+ </tr>
305
+ <tr>
306
+ <td style="color:#DDDDDD;" width="30%"><?php _e( 'Protect the file', 'music-player-for-woocommerce' ); ?></td>
307
+ <td><input type="checkbox" DISABLED /></td>
308
+ </tr>
309
+ <tr valign="top">
310
+ <td style="color:#DDDDDD;" width="30%"><?php _e('Percent of audio used for protected playbacks', 'music-player-for-woocommerce'); ?></td>
311
+ <td style="color:#DDDDDD;">
312
+ <input type="number" DISABLED /> % <br />
313
+ <em><?php _e('To prevent unauthorized copying of audio files, the files will be partially accessible', 'music-player-for-woocommerce'); ?></em>
314
+ </td>
315
+ </tr>
316
+ <tr valign="top">
317
+ <td style="color:#DDDDDD;" width="30%">
318
+ <?php _e('Text to display beside the player explaining that demos are partial versions of the original files', 'music-player-for-woocommerce'); ?>
319
+ <td style="color:#DDDDDD;">
320
+ <textarea style="width:100%;" rows="4" disabled></textarea>
321
+ </td>
322
+ </tr>
323
+
324
+ </table>
325
+ </td>
326
+ </tr>
327
+ </table>
328
+ <table class="widefat" style="border:0;">
329
+ <tr>
330
+ <td>
331
+ <table class="widefat" style="border:1px solid #e1e1e1;">
332
+ <tr>
333
+ <td>
334
+ <div><?php _e('Scope', 'music-player-for-woocommerce'); ?></div>
335
+ <div><div class="wcmp-tooltip"><span class="wcmp-tooltiptext"><?php _e('Ticking the checkbox the previous settings are applied to all products, even if they have a player enabled.', 'music-player-for-woocommerce');?></span><input type="checkbox" name="_wcmp_apply_to_all_players" /></div> <?php _e('Apply the previous settings to all products pages in the website.', 'music-player-for-woocommerce'); ?></div>
336
+ </td>
337
+ </tr>
338
+ </table>
339
+ </td>
340
+ </tr>
341
+ </table>
342
+ <table class="widefat" style="border:0;">
343
+ <tr>
344
+ <td>
345
+ <table class="widefat" style="border:1px solid #e1e1e1;">
346
+ <tr>
347
+ <td><h2><?php _e('Analytics', 'music-player-for-woocommerce'); ?></h2></td>
348
+ </tr>
349
+ <tr>
350
+ <td>
351
+ <p><?php _e('Allows the integration with Google Analytics for registering new events when the songs are played. The event information would include: the URL to the audio file as the event label and the product\'s id as its value.', 'music-player-for-woocommerce'); ?></p>
352
+ <p style="border:1px solid #E6DB55;margin-bottom:10px;padding:5px;background-color: #FFFFE0;"><b><?php _e('Note', 'music-player-for-woocommerce')?></b>: <?php _e('If the preload option is configured as Metadata or Auto in the players settings, the event would be registered when the audio file is loaded by the player and not exactly when they are playing.', 'music-player-for-woocommerce');?></p>
353
+ </td>
354
+ </tr>
355
+ <tr>
356
+ <td>
357
+ <div><?php _e('Tracking Id', 'music-player-for-woocommerce'); ?></div>
358
+ <div><input type="text" name="_wcmp_analytics_property" value="<?php print esc_attr($analytics_property); ?>" style="width:100%;" placeholder="UA-XXXXX-Y"></div>
359
+ </td>
360
+ </tr>
361
+ </table>
362
+ </td>
363
+ </tr>
364
+ </table>
365
+ <div style="margin-top:20px;"><input type="submit" value="<?php _e('Save settings', 'music-player-for-woocommerce'); ?>" class="button-primary" /></div>
366
+ </form>
367
+ <script>jQuery(window).on('load', function(){
368
+ var $ = jQuery;
369
+ function coverSection()
370
+ {
371
+ var v = $('[name="_wcmp_player_controls"]:checked').val(),
372
+ c = $('.wcmp-on-cover');
373
+ if(v == 'default' || v == 'button') c.show();
374
+ else c.hide();
375
+ };
376
+ $(document).on('change', '[name="_wcmp_player_controls"]', function(){
377
+ coverSection();
378
+ });
379
+ coverSection();
380
+ });</script>
381
+ <style>.wcmp-player-settings tr td:first-child{width:225px;}</style>
views/player_options.php ADDED
@@ -0,0 +1,340 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ if( !defined( 'WCMP_PLUGIN_URL' ) ) { echo 'Direct access not allowed.'; exit; }
3
+
4
+ // include resources
5
+ wp_enqueue_style( 'wcmp-admin-style', plugin_dir_url(__FILE__).'../css/style.admin.css', array(), '1.0.24' );
6
+
7
+ global $post;
8
+ $enable_player = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_enable_player', false );
9
+ $show_in = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_show_in', 'all' );
10
+ $player_style = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_player_layout', WCMP_DEFAULT_PLAYER_LAYOUT );
11
+ $player_controls= $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_player_controls', WCMP_DEFAULT_PLAYER_CONTROLS );
12
+ $player_title= intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_player_title', 1 ) );
13
+ $merge_grouped = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_merge_in_grouped',0 ) );
14
+ $play_all = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
15
+ $post->ID,
16
+ '_wcmp_play_all',
17
+ // This option is only for compatibility with versions previous to 1.0.28
18
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
19
+ $post->ID,
20
+ 'play_all',
21
+ 0
22
+ )
23
+ )
24
+ );
25
+ $preload = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
26
+ $post->ID,
27
+ '_wcmp_preload',
28
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
29
+ $post->ID,
30
+ 'preload',
31
+ 'none'
32
+ )
33
+ );
34
+ $on_cover = intval( $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr( $post->ID, '_wcmp_on_cover', 0 ) );
35
+ ?>
36
+ <input type="hidden" name="wcmp_nonce" value="<?php echo wp_create_nonce('wcmp_updating_product'); ?>" />
37
+ <table class="widefat" style="border-left:0;border-right:0;border-bottom:0;padding-bottom:0;">
38
+ <tr>
39
+ <td>
40
+ <div class="wcmp-highlight-box">
41
+ <?php
42
+ _e(
43
+ '<p>The player uses the audio files associated to the product. If you want protecting the audio files for selling, tick the checkbox: <b>"Protect the file"</b>, in whose case the plugin will create a truncated version of the audio files for selling to be used for demo. The size of audio files for demo is based on the number entered through the attribute: <b>"Percent of audio used for protected playbacks"</b>.</p><p><b>Protecting the files prevents that malicious users can access to the original audio files without pay for them.</b></p>',
44
+ 'music-player-for-woocommerce'
45
+ );
46
+ ?>
47
+ <p><?php _e( 'The security feature and particular files for demo are only available in the PRO version of the plugin', 'music-player-for-woocommerce'); ?>. <a target="_blank" href="https://wcmp.dwbooster.com"><?php _e('CLICK HERE TO GET THE PRO VERSION OF THE PLUGIN', 'music-player-for-woocommerce'); ?></a></p>
48
+ <p><?php _e( 'For testing the premium version of the plugin, visit the online demo:<br/> <a href="https://demos.dwbooster.com/music-player-for-woocommerce/wp-login.php" target="_blank">Administration area: Click to access the administration area demo</a><br/><a href="https://demos.dwbooster.com/music-player-for-woocommerce/" target="_blank">Public page: Click to visit the WooCommerce Store</a>', 'music-player-for-woocommerce'); ?></p>
49
+ </div>
50
+ <div class="wcmp-highlight-box">
51
+ <div id="wcmp_tips_header">
52
+ <h3 style="margin-top:2px;margin-bottom:5px;cursor:pointer;" onclick="jQuery('#wcmp_tips_body').toggle();">
53
+ <?php _e('[+|-] Tips', 'music-player-for-woocommerce'); ?>
54
+ </h3>
55
+ </div>
56
+ <div id="wcmp_tips_body">
57
+ <div class="wcmp-highlight-box">
58
+ <a class="wcmp-tip"href="javascript:void(0);" onclick="jQuery(this).next('.wcmp-tip-text').toggle();">
59
+ <?php _e('[+|-] Using the audio files stored on Google Drive', 'music-player-for-woocommerce'); ?>
60
+ </a>
61
+ <div class="wcmp-tip-text">
62
+ <ul>
63
+ <li>
64
+ <p> -
65
+ <?php
66
+ _e(
67
+ 'Go to Drive, press the right click on the file to use, and select the option: <b>"Get Shareable Link"</b>',
68
+ 'music-player-for-woocommerce'
69
+ );
70
+ ?>
71
+ </p>
72
+ <p>
73
+ <?php
74
+ _e(
75
+ 'The previous action will generate an url with the structure: <b>https://drive.google.com/open?id=FILE_ID</b>',
76
+ 'music-player-for-woocommerce'
77
+ );
78
+ ?>
79
+ </p>
80
+ </li>
81
+ <li>
82
+ <p> -
83
+ <?php
84
+ _e(
85
+ 'Knowing the FILE_ID, extracted from the previous URL, enter the URL below, into the WooCommerce product, to allow the Music Player accessing to it:',
86
+ 'music-player-for-woocommerce'
87
+ );
88
+ ?>
89
+ </p>
90
+ <p>
91
+ <b>https://drive.google.com/uc?export=download&id=FILE_ID&.mp3</b>
92
+ </p>
93
+ <p>
94
+ <?php
95
+ _e(
96
+ '<b>Note:</b> Pay attention to the use of the fake parameter: <b>&.mp3</b> as the last one in the URL',
97
+ 'music-player-for-woocommerce'
98
+ );
99
+ ?>
100
+ </p>
101
+ </li>
102
+ </div>
103
+ </div>
104
+ <div class="wcmp-highlight-box">
105
+ <a class="wcmp-tip"href="javascript:void(0);" onclick="jQuery(this).next('.wcmp-tip-text').toggle();">
106
+ <?php _e('[+|-] Using the audio files stored on DropBox', 'music-player-for-woocommerce'); ?>
107
+ </a>
108
+ <div class="wcmp-tip-text">
109
+ <ul>
110
+ <li>
111
+ <p> -
112
+ <?php
113
+ _e(
114
+ 'Sign in to <a href="https://www.dropbox.com/login" target="_blank">dropbox.com </a>',
115
+ 'music-player-for-woocommerce'
116
+ );
117
+ ?>
118
+ </p>
119
+ </li>
120
+ <li>
121
+ <p> -
122
+ <?php
123
+ _e(
124
+ "Hover your cursor over the file or folder you'd like to share and click <b>Share</b> when it appears.",
125
+ 'music-player-for-woocommerce'
126
+ );
127
+ ?>
128
+ </p>
129
+ </li>
130
+ <li>
131
+ <p> -
132
+ <?php
133
+ _e(
134
+ "If a link hasn't been created, click Create a link. (If a link was already created, click Copy link.",
135
+ 'music-player-for-woocommerce'
136
+ );
137
+ ?>
138
+ </p>
139
+ <p>
140
+ <?php
141
+ _e(
142
+ 'The link structure would be similar to:<br> https://www.dropbox.com/s/rycvgn8iokfedmo/file.mp3?dl=0',
143
+ 'music-player-for-woocommerce'
144
+ );
145
+ ?>
146
+ </p>
147
+ </li>
148
+ <li>
149
+ <p> -
150
+ <?php
151
+ _e(
152
+ 'Enter the URL into the WooCommerce product with the following structure:<br> https://www.dropbox.com/s/rycvgn8iokfedmo/file.mp3?dl=1&.mp3',
153
+ 'music-player-for-woocommerce'
154
+ );
155
+ ?>
156
+ </p>
157
+ <p>
158
+ <?php
159
+ _e(
160
+ '<b>Note:</b> Pay attention to the use of the fake parameter: <b>&.mp3</b> as the last one in the URL. Furthermore, the parameter <b>dl=0</b>, has been modified as <b>dl=1</b>',
161
+ 'music-player-for-woocommerce'
162
+ );
163
+ ?>
164
+ </p>
165
+ </li>
166
+ </div>
167
+ </div>
168
+ </div>
169
+ </div>
170
+ </td>
171
+ </tr>
172
+ <tr>
173
+ <td>
174
+ <table class="widefat wcmp-player-settings" style="border:1px solid #e1e1e1;">
175
+ <tr>
176
+ <td><?php _e( 'Include music player', 'music-player-for-woocommerce' ); ?></td>
177
+ <td><div class="wcmp-tooltip"><span class="wcmp-tooltiptext"><?php _e('The player is shown only if the product is "downloadable", and there is at least an audio file between the "Downloadable files"', 'music-player-for-woocommerce'); ?></span><input type="checkbox" name="_wcmp_enable_player" <?php echo (( $enable_player ) ? 'checked' : '' ); ?> /></div></td>
178
+ </tr>
179
+ <tr>
180
+ <td><?php _e( 'Include in', 'music-player-for-woocommerce' ); ?></td>
181
+ <td>
182
+ <input type="radio" name="_wcmp_show_in" value="single" <?php echo (( $show_in == 'single' ) ? 'checked' : '' ); ?> />
183
+ <?php _e('single-entry pages <i>(Product\'s page only)</i>', 'music-player-for-woocommerce'); ?><br />
184
+
185
+ <input type="radio" name="_wcmp_show_in" value="multiple" <?php echo (( $show_in == 'multiple' ) ? 'checked' : '' ); ?> />
186
+ <?php _e('multiple entries pages <i>(Shop pages, archive pages, but not in the product\'s page)</i>', 'music-player-for-woocommerce'); ?><br />
187
+
188
+ <input type="radio" name="_wcmp_show_in" value="all" <?php echo (( $show_in == 'all' ) ? 'checked' : '' ); ?> />
189
+ <?php _e('all pages <i>(with single or multiple-entries)</i>', 'music-player-for-woocommerce'); ?>
190
+ </td>
191
+ </tr>
192
+ <tr>
193
+ <td><?php _e( 'Merge in grouped products', 'music-player-for-woocommerce' ); ?></td>
194
+ <td><input type="checkbox" name="_wcmp_merge_in_grouped" <?php echo (( $merge_grouped ) ? 'checked' : '' ); ?> /><br /><em><?php _e( 'In grouped products, display the "Add to cart" buttons and quantity fields in the players rows', 'music-player-for-woocommerce' ); ?></em></td>
195
+ </tr>
196
+ <tr>
197
+ <td valign="top"><?php _e( 'Player layout', 'music-player-for-woocommerce' ); ?></td>
198
+ <td>
199
+ <table>
200
+ <tr>
201
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-classic" <?php echo (($player_style == 'mejs-classic') ? 'checked' : '') ;?> /></td>
202
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin1.png" /></td>
203
+ </tr>
204
+
205
+ <tr>
206
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-ted" <?php echo (($player_style == 'mejs-ted') ? 'checked' : '') ;?> /></td>
207
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin2.png" /></td>
208
+ </tr>
209
+
210
+ <tr>
211
+ <td><input name="_wcmp_player_layout" type="radio" value="mejs-wmp" <?php echo (($player_style == 'mejs-wmp') ? 'checked' : '') ;?> /></td>
212
+ <td><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin3.png" /></td>
213
+ </tr>
214
+ </table>
215
+ </td>
216
+ </tr>
217
+ <tr>
218
+ <td>
219
+ <?php _e( 'Preload', 'music-player-for-woocommerce' ); ?>
220
+ </td>
221
+ <td>
222
+ <label><input type="radio" name="_wcmp_preload" value="none" <?php if($preload == 'none') echo 'CHECKED'; ?> /> None</label><br />
223
+ <label><input type="radio" name="_wcmp_preload" value="metadata" <?php if($preload == 'metadata') echo 'CHECKED'; ?> /> Metadata</label><br />
224
+ <label><input type="radio" name="_wcmp_preload" value="auto" <?php if($preload == 'auto') echo 'CHECKED'; ?> /> Auto</label><br />
225
+ </td>
226
+ </tr>
227
+ <tr>
228
+ <td>
229
+ <?php _e( 'Play all', 'music-player-for-woocommerce' ); ?>
230
+ </td>
231
+ <td>
232
+ <input type="checkbox" name="_wcmp_play_all" <?php if(!empty($play_all)) echo 'CHECKED'; ?> />
233
+ </td>
234
+ </tr>
235
+ <tr>
236
+ <td><?php _e( 'Player controls', 'music-player-for-woocommerce' ); ?></td>
237
+ <td>
238
+ <input type="radio" name="_wcmp_player_controls" value="button" <?php echo (( $player_controls == 'button' ) ? 'checked' : ''); ?> /> <?php _e( 'the play/pause button only', 'music-player-for-woocommerce' ); ?><br />
239
+ <input type="radio" name="_wcmp_player_controls" value="all" <?php echo (( $player_controls == 'all' ) ? 'checked' : ''); ?> /> <?php _e( 'all controls', 'music-player-for-woocommerce' ); ?><br />
240
+ <input type="radio" name="_wcmp_player_controls" value="default" <?php echo (( $player_controls == 'default' ) ? 'checked' : ''); ?> /> <?php _e( 'the play/pause button only, or all controls depending on context', 'music-player-for-woocommerce' ); ?>
241
+ <div class="wcmp-on-cover" style="margin-top:10px;">
242
+ <input type="checkbox" name="_wcmp_player_on_cover" value="default" <?php
243
+ echo ((!empty($on_cover) && ( $player_controls == 'button' || $player_controls == 'default')) ? 'checked' : '');
244
+ ?> />
245
+ <?php _e( 'for play/pause button players display them on cover images.', 'music-player-for-woocommerce' ); ?>
246
+ <i>
247
+ <?php
248
+ _e('(This feature is experimental, and will depend on the theme active on the website.)', 'music-player-for-woocommerce');
249
+ ?>
250
+ </i>
251
+ </div>
252
+ </td>
253
+ </tr>
254
+ <tr>
255
+ <td><?php _e( 'Display the player\'s title', 'music-player-for-woocommerce' ); ?></td>
256
+ <td>
257
+ <input type="checkbox" name="_wcmp_player_title" <?php echo (( !empty($player_title) ) ? 'checked' : ''); ?> />
258
+ </td>
259
+ </tr>
260
+ <tr>
261
+ <td colspan="2" style="color:red;"><?php _e( 'The security feature is only available in the PRO version of the plugin', 'music-player-for-woocommerce'); ?>. <a target="_blank" href="https://wcmp.dwbooster.com"><?php _e('CLICK HERE TO GET THE PRO VERSION OF THE PLUGIN', 'music-player-for-woocommerce'); ?></a></td>
262
+ </tr>
263
+ <tr>
264
+ <td style="color:#DDDDDD;"><?php _e( 'Protect the file', 'music-player-for-woocommerce' ); ?></td>
265
+ <td><input type="checkbox" DISABLED /></td>
266
+ </tr>
267
+ <tr valign="top">
268
+ <td style="color:#DDDDDD;"><?php _e('Percent of audio used for protected playbacks', 'music-player-for-woocommerce'); ?></td>
269
+ <td style="color:#DDDDDD;">
270
+ <input type="number" DISABLED /> % <br /><br />
271
+ <em><?php _e('To prevent unauthorized copying of audio files, the files will be partially accessible', 'music-player-for-woocommerce'); ?></em>
272
+ </td>
273
+ </tr>
274
+ </table>
275
+ </td>
276
+ </tr>
277
+ </table>
278
+ <table class="widefat" style="border:0;padding-bottom:20px;">
279
+ <tr valign="top">
280
+ <td style="color:#DDDDDD;">
281
+ <table class="widefat" style="border:1px solid #e1e1e1;">
282
+ <tr valign="top">
283
+ <td style="color:#DDDDDD;"><input type="checkbox" disabled /> <?php _e('Select my own demo files', 'music-player-for-woocommerce'); ?></td>
284
+ </tr>
285
+ <tr valign="top" class="wcmp-demo-files">
286
+ <td>
287
+ <div style="color:#DDDDDD;"><?php _e('Demo files', 'music-player-for-woocommerce'); ?></div>
288
+ <table class="widefat">
289
+ <thead>
290
+ <tr>
291
+ <th style="color:#DDDDDD;"><?php _e('Name', 'music-player-for-woocommerce'); ?></th>
292
+ <th colspan="2" style="color:#DDDDDD;"><?php _e('File URL', 'music-player-for-woocommerce'); ?></th>
293
+ <th>&nbsp;</th>
294
+ </tr>
295
+ </thead>
296
+ <tbody>
297
+ <tr>
298
+ <td>
299
+ <input type="text" class="wcmp-file-name" placeholder="<?php _e('File Name', 'music-player-for-woocommerce'); ?>" disabled style="color:#DDDDDD;" />
300
+ </td>
301
+ <td>
302
+ <input type="text" class="wcmp-file-url" placeholder="http://" disabled style="color:#DDDDDD;" />
303
+ </td>
304
+ <td width="1%" style="color:#DDDDDD;">
305
+ <a href="javascript:void(0);" class="button wcmp-select-file" style="color:#DDDDDD;"><?php _e('Choose file', 'music-player-for-woocommerce'); ?></a>
306
+ </td>
307
+ <td width="1%" style="color:#DDDDDD;">
308
+ <a href="javascript:void(0);" class="wcmp-delete" style="color:#DDDDDD;"><?php _e('Delete', 'music-player-for-woocommerce');?></a>
309
+ </td>
310
+ </tr>
311
+ </tbody>
312
+ <tfoot>
313
+ <tr>
314
+ <th colspan="4" style="color:#DDDDDD;">
315
+ <a href="javascript:void(0);" class="button wcmp-add" style="color:#DDDDDD;"><?php _e('Add File', 'music-player-for-woocommerce'); ?></a>
316
+ </th>
317
+ </tr>
318
+ </tfoot>
319
+ </table>
320
+ </td>
321
+ </tr>
322
+ </table>
323
+ </td>
324
+ </tr>
325
+ </table>
326
+ <script>jQuery(window).on('load', function(){
327
+ var $ = jQuery;
328
+ function coverSection()
329
+ {
330
+ var v = $('[name="_wcmp_player_controls"]:checked').val(),
331
+ c = $('.wcmp-on-cover');
332
+ if(v == 'default' || v == 'button') c.show();
333
+ else c.hide();
334
+ };
335
+ $(document).on('change', '[name="_wcmp_player_controls"]', function(){
336
+ coverSection();
337
+ });
338
+ coverSection();
339
+ });</script>
340
+ <style>.wcmp-player-settings tr td:first-child{width:225px;}</style>
wcmp.php ADDED
@@ -0,0 +1,1344 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ /*
3
+ Plugin Name: Music Player for WooCommerce
4
+ Plugin URI: https://wcmp.dwbooster.com
5
+ Version: 1.0.104
6
+ Text Domain: music-player-for-woocommerce
7
+ Author: CodePeople
8
+ Author URI: https://wcmp.dwbooster.com
9
+ Description: Music Player for WooCommerce includes the MediaElement.js music player in the pages of the products with audio files associated, and in the store's pages, furthermore, the plugin allows selecting between multiple skins.
10
+ License: GPLv2 or later
11
+ License URI: http://www.gnu.org/licenses/gpl-2.0.html
12
+ */
13
+
14
+ require_once 'banner.php';
15
+ $codepeople_promote_banner_plugins[ 'codepeople-music-player-for-woocommerce' ] = array(
16
+ 'plugin_name' => 'Music Player for WooCommerce',
17
+ 'plugin_url' => 'https://wordpress.org/support/plugin/music-player-for-woocommerce/reviews/#new-post'
18
+ );
19
+
20
+ // CONSTANTS
21
+
22
+ define( 'WCMP_WEBSITE_URL', get_home_url(get_current_blog_id(), '', is_ssl() ? 'https' : 'http') );
23
+ define( 'WCMP_PLUGIN_URL', plugins_url( '', __FILE__ ) );
24
+ define( 'WCMP_DEFAULT_PLAYER_LAYOUT', 'mejs-classic' );
25
+ define( 'WCMP_DEFAULT_PLAYER_CONTROLS', 'default' );
26
+ define( 'WCMP_DEFAULT_PlAYER_TITLE', 1 );
27
+ define( 'WCMP_REMOTE_TIMEOUT', 120);
28
+
29
+ // Load widgets
30
+ require_once 'widgets/playlist_widget.php';
31
+
32
+ add_filter('option_sbp_settings', array('WooCommerceMusicPlayer', 'troubleshoot'));
33
+ if ( !class_exists( 'WooCommerceMusicPlayer' ) ) {
34
+ class WooCommerceMusicPlayer
35
+ {
36
+ //******************** ATTRIBUTES ************************
37
+
38
+ private $_products_attrs = array();
39
+ private $_global_attrs = array();
40
+ private $_player_layouts = array( 'mejs-classic', 'mejs-ted', 'mejs-wmp' );
41
+ private $_player_controls= array( 'button', 'all', 'default' );
42
+ private $_files_directory_path;
43
+ private $_files_directory_url;
44
+ private $_enqueued_resources = false;
45
+ private $_insert_player = true;
46
+
47
+ /**
48
+ * WCMP constructor
49
+ *
50
+ * @access public
51
+ * @return void
52
+ */
53
+ public function __construct()
54
+ {
55
+ $this->_createDir();
56
+ register_activation_hook( __FILE__, array( &$this, 'activation' ) );
57
+ register_deactivation_hook( __FILE__, array( &$this, 'deactivation' ) );
58
+ add_action( 'plugins_loaded', array(&$this, 'load_textdomain') );
59
+ add_action('init', array(&$this, 'init'));
60
+ add_action('admin_init', array(&$this, 'admin_init'), 99);
61
+
62
+ $this->_load_addons();
63
+
64
+ // Integration with the content editors
65
+ require_once dirname(__FILE__).'/pagebuilders/builders.php';
66
+ WCMP_BUILDERS::run();
67
+ } // End __constructor
68
+
69
+ public function activation()
70
+ {
71
+ $this->_deleteDir( $this->_files_directory_path );
72
+ $this->_createDir();
73
+ }
74
+
75
+ public function deactivation()
76
+ {
77
+ $this->_deleteDir( $this->_files_directory_path );
78
+ }
79
+
80
+ public function load_textdomain()
81
+ {
82
+ load_plugin_textdomain( 'music-player-for-woocommerce', FALSE, basename( dirname( __FILE__ ) ) . '/languages/' );
83
+ }
84
+
85
+ public function get_product_attr( $product_id, $attr, $default = false )
86
+ {
87
+ if( !isset( $this->_products_attrs[ $product_id ] ) ) $this->_products_attrs[ $product_id ] = array();
88
+ if( !isset( $this->_products_attrs[ $product_id ][ $attr ] ) )
89
+ {
90
+ if( metadata_exists( 'post', $product_id, $attr ) )
91
+ {
92
+ $this->_products_attrs[ $product_id ][ $attr ] = get_post_meta( $product_id, $attr, true );
93
+ }
94
+ else
95
+ {
96
+ $this->_products_attrs[ $product_id ][ $attr ] = $this->get_global_attr($attr, $default);
97
+ }
98
+ }
99
+ return $this->_products_attrs[ $product_id ][ $attr ];
100
+
101
+ } // End get_product_attr
102
+
103
+ public function get_global_attr( $attr, $default = false )
104
+ {
105
+ if(empty($this->_global_attrs)) $this->_global_attrs = get_option('wcmp_global_settings',array());
106
+ if( !isset( $this->_global_attrs[ $attr ] ) ) $this->_global_attrs[ $attr ] = $default;
107
+ return $this->_global_attrs[ $attr ];
108
+
109
+ } // End get_global_attr
110
+
111
+ //******************** WORDPRESS ACTIONS **************************
112
+
113
+ public function init()
114
+ {
115
+ // Check if WooCommerce is installed or not
116
+ if(!class_exists('woocommerce')) return;
117
+ $_current_user_id = get_current_user_id();
118
+ if(
119
+ $this->get_global_attr( '_wcmp_registered_only', 0 ) &&
120
+ $_current_user_id == 0
121
+ ) $this->_insert_player = false;
122
+
123
+ if( !is_admin() )
124
+ {
125
+ // Define the shortcode for the playlist_widget
126
+ add_shortcode('wcmp-playlist', array(&$this, 'replace_playlist_shortcode' ));
127
+ $this->_preview();
128
+ if( isset( $_REQUEST[ 'wcmp-action' ] ) && $_REQUEST[ 'wcmp-action' ] == 'play' )
129
+ {
130
+ if( isset( $_REQUEST[ 'wcmp-product' ] ) )
131
+ {
132
+ $product_id = @intval( $_REQUEST[ 'wcmp-product' ] );
133
+ if( !empty( $product_id ) )
134
+ {
135
+ $product = wc_get_product( $product_id );
136
+ if( $product !== false && isset( $_REQUEST[ 'wcmp-file' ] ) )
137
+ {
138
+ $files = $this->_get_product_files(
139
+ array(
140
+ 'product' => $product,
141
+ 'file_id' => sanitize_key($_REQUEST[ 'wcmp-file' ])
142
+ )
143
+ );
144
+
145
+ if( !empty( $files ) )
146
+ {
147
+ $file_url = $files[ sanitize_key($_REQUEST[ 'wcmp-file' ]) ][ 'file' ];
148
+ $this->_tracking_play_event($product_id, $file_url);
149
+ $this->_output_file( array( 'url' => $file_url ) );
150
+ }
151
+ }
152
+ }
153
+ }
154
+ exit;
155
+ }
156
+ else
157
+ {
158
+ // To allow customize the hooks
159
+ $include_main_player_hook = trim($this->get_global_attr('_wcmp_main_player_hook', ''));
160
+ $include_all_players_hook = trim($this->get_global_attr('_wcmp_all_players_hook', ''));
161
+
162
+ if(empty($include_main_player_hook)) $include_main_player_hook = 'woocommerce_shop_loop_item_title';
163
+ if(empty($include_all_players_hook)) $include_all_players_hook = 'woocommerce_single_product_summary';
164
+
165
+ add_action( $include_main_player_hook, array( &$this, 'include_main_player' ), 11 );
166
+ add_action( $include_all_players_hook, array( &$this, 'include_all_players' ), 11 );
167
+
168
+ // Allows to call the players directly by themes
169
+ add_action( 'wcmp_main_player', array( &$this, 'include_main_player' ), 11 );
170
+ add_action( 'wcmp_all_players', array( &$this, 'include_all_players' ), 11 );
171
+
172
+ // Integration with woocommerce-product-table by barn2media
173
+ add_filter( 'wc_product_table_data_name', array(&$this, 'product_table_data_name'), 11, 2);
174
+
175
+ $players_in_cart = $this->get_global_attr('_wcmp_players_in_cart', false);
176
+ if($players_in_cart)
177
+ {
178
+ add_action( 'woocommerce_after_cart_item_name', array( &$this, 'player_in_cart' ), 11, 2 );
179
+ }
180
+
181
+ // Add product id to audio tag
182
+ add_filter('wcmp_audio_tag', array(&$this, 'add_data_product'), 99, 3);
183
+
184
+ // Add class name to the feature image of product
185
+ add_filter('woocommerce_product_get_image', array(&$this, 'add_class_attachment'),99,6);
186
+ add_filter('woocommerce_single_product_image_thumbnail_html', array(&$this, 'add_class_single_product_image'), 99, 2);
187
+
188
+ // Include players with the titles
189
+ if(
190
+ $this->get_global_attr( '_wcmp_force_main_player_in_title', 1 ) &&
191
+ !empty($_SERVER['REQUEST_URI']) &&
192
+ stripos($_SERVER['REQUEST_URI'], 'wc/store') !== false
193
+ )
194
+ {
195
+ add_filter( 'woocommerce_product_title', array(&$this, 'woocommerce_product_title'), 10, 2);
196
+ }
197
+
198
+ // For accepting the <source> tags
199
+ add_filter( 'wp_kses_allowed_html', array(&$this, 'allowed_html_tags'), 10, 2);
200
+ }
201
+ }
202
+ else
203
+ {
204
+ add_action('admin_menu', array(&$this, 'menu_links'), 10);
205
+ }
206
+
207
+ } // End init
208
+
209
+ public function admin_init()
210
+ {
211
+ // Check if WooCommerce is installed or not
212
+ if(!class_exists('woocommerce')) return;
213
+
214
+ add_meta_box('wcmp_woocommerce_metabox', __("Music Player for WooCommerce", 'music-player-for-woocommerce'), array(&$this, 'woocommerce_player_settings'), 'product', 'normal');
215
+ add_action('save_post', array(&$this, 'save_post'), 10, 3);
216
+ add_action('delete_post', array(&$this, 'delete_post'));
217
+ add_filter("plugin_action_links_".plugin_basename(__FILE__), array(&$this, 'help_link'));
218
+ } // End admin_init
219
+
220
+ public function help_link($links)
221
+ {
222
+ array_unshift(
223
+ $links,
224
+ '<a href="https://wordpress.org/support/plugin/music-player-for-woocommerce/#new-post" target="_blank">'.__('Help').'</a>'
225
+ );
226
+ return $links;
227
+ } // End help_link
228
+
229
+ public function menu_links()
230
+ {
231
+ add_options_page('Music Player for WooCommerce', 'Music Player for WooCommerce', 'manage_options', 'music-player-for-woocommerce-settings', array(&$this, 'settings_page'));
232
+ } // End menu_links
233
+
234
+ public function settings_page()
235
+ {
236
+ if (
237
+ isset( $_POST['wcmp_nonce'] ) &&
238
+ wp_verify_nonce( $_POST['wcmp_nonce'], 'wcmp_updating_plugin_settings' )
239
+ )
240
+ {
241
+ $_REQUEST = stripslashes_deep($_REQUEST);
242
+ // Save the player settings
243
+ $registered_only = (isset($_REQUEST['_wcmp_registered_only'])) ? 1 : 0;
244
+ $troubleshoot_default_extension = (isset($_REQUEST['_wcmp_default_extension'])) ? true : false;
245
+ $force_main_player_in_title = (isset($_REQUEST['_wcmp_force_main_player_in_title'])) ? 1 : 0;
246
+ $troubleshoot_onload = (isset($_REQUEST['_wcmp_onload'])) ? true : false;
247
+ $include_main_player_hook = (isset($_REQUEST['_wcmp_main_player_hook'])) ? sanitize_text_field($_REQUEST['_wcmp_main_player_hook']) : '';
248
+ $include_all_players_hook = (isset($_REQUEST['_wcmp_all_players_hook'])) ? sanitize_text_field($_REQUEST['_wcmp_all_players_hook']) : '';
249
+
250
+ $enable_player = (isset($_REQUEST['_wcmp_enable_player'])) ? 1 : 0;
251
+ $show_in = (isset($_REQUEST['_wcmp_show_in']) && in_array($_REQUEST['_wcmp_show_in'], array('single', 'multiple'))) ? $_REQUEST['_wcmp_show_in'] : 'all';
252
+ $players_in_cart = (isset($_REQUEST['_wcmp_players_in_cart'])) ? true : false;
253
+ $player_style = (
254
+ isset($_REQUEST['_wcmp_player_layout']) &&
255
+ in_array($_REQUEST['_wcmp_player_layout'], $this->_player_layouts)
256
+ ) ? $_REQUEST['_wcmp_player_layout'] : WCMP_DEFAULT_PLAYER_LAYOUT;
257
+ $player_controls = (
258
+ isset( $_REQUEST[ '_wcmp_player_controls' ] ) &&
259
+ in_array( $_REQUEST[ '_wcmp_player_controls' ], $this->_player_controls )
260
+ ) ? $_REQUEST[ '_wcmp_player_controls' ] : WCMP_DEFAULT_PLAYER_CONTROLS;
261
+
262
+ $on_cover = (($player_controls == 'button' || $player_controls == 'default') && isset($_REQUEST['_wcmp_player_on_cover'])) ? 1 : 0;
263
+
264
+ $player_title = ( isset( $_REQUEST[ '_wcmp_player_title' ] ) ) ? 1 : 0;
265
+ $merge_grouped = ( isset( $_REQUEST[ '_wcmp_merge_in_grouped' ] ) ) ? 1 : 0;
266
+ $play_all = (isset($_REQUEST['_wcmp_play_all'])) ? 1 : 0;
267
+ $preload = (
268
+ isset($_REQUEST['_wcmp_preload']) &&
269
+ in_array($_REQUEST['_wcmp_preload'], array('none', 'metadata', 'auto'))
270
+ ) ? $_REQUEST['_wcmp_preload'] : 'none';
271
+
272
+ $global_settings = array(
273
+ '_wcmp_registered_only' => $registered_only,
274
+ '_wcmp_enable_player' => $enable_player,
275
+ '_wcmp_show_in' => $show_in,
276
+ '_wcmp_players_in_cart' => $players_in_cart,
277
+ '_wcmp_player_layout' => $player_style,
278
+ '_wcmp_player_controls' => $player_controls,
279
+ '_wcmp_player_title'=> $player_title,
280
+ '_wcmp_merge_in_grouped' => $merge_grouped,
281
+ '_wcmp_play_all' => $play_all,
282
+ '_wcmp_preload' => $preload,
283
+ '_wcmp_on_cover' => $on_cover,
284
+ '_wcmp_default_extension' => $troubleshoot_default_extension,
285
+ '_wcmp_force_main_player_in_title' => $force_main_player_in_title,
286
+ '_wcmp_onload' => $troubleshoot_onload,
287
+ '_wcmp_main_player_hook' => $include_main_player_hook,
288
+ '_wcmp_all_players_hook' => $include_all_players_hook,
289
+ '_wcmp_analytics_property' => (isset($_REQUEST['_wcmp_analytics_property'])) ? sanitize_text_field($_REQUEST['_wcmp_analytics_property']) : ''
290
+ );
291
+
292
+ $apply_to_all_players = ( isset( $_REQUEST[ '_wcmp_apply_to_all_players' ] ) ) ? 1 : 0;
293
+ if($apply_to_all_players)
294
+ {
295
+ $this->_deleteDir( $this->_files_directory_path );
296
+
297
+ $products_ids = array(
298
+ 'post_type' => 'product',
299
+ 'numberposts' => -1,
300
+ 'post_status' => array('publish', 'pending', 'draft', 'future'),
301
+ 'fields' => 'ids',
302
+ 'cache_results' => false
303
+ );
304
+
305
+ $products = get_posts($products_ids);
306
+ foreach($products as $product_id)
307
+ {
308
+ update_post_meta( $product_id, '_wcmp_enable_player', $enable_player);
309
+ update_post_meta($product_id, '_wcmp_show_in', $show_in);
310
+ update_post_meta($product_id, '_wcmp_player_layout', $player_style);
311
+ update_post_meta($product_id, '_wcmp_player_controls', $player_controls);
312
+ update_post_meta($product_id, '_wcmp_player_title', $player_title);
313
+ update_post_meta($product_id, '_wcmp_merge_in_grouped', $merge_grouped);
314
+ update_post_meta($product_id, '_wcmp_play_all', $play_all);
315
+ update_post_meta($product_id, '_wcmp_preload', $preload);
316
+ update_post_meta($product_id, '_wcmp_on_cover', $on_cover);
317
+ }
318
+ }
319
+
320
+ update_option('wcmp_global_settings', $global_settings);
321
+ $this->_global_attrs = $global_settings;
322
+ } // Save settings
323
+
324
+ print '<div class="wrap">'; // Open Wrap
325
+ include_once dirname(__FILE__).'/views/global_options.php';
326
+ print '</div>'; // Close Wrap
327
+ } // End settings_page
328
+
329
+ public function save_post($post_id, $post, $update)
330
+ {
331
+ if ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) return;
332
+ if ( empty( $_POST['wcmp_nonce'] ) || !wp_verify_nonce( $_POST['wcmp_nonce'], 'wcmp_updating_product' ) ) return;
333
+ if ( !isset($post) || 'product' !== $post->post_type || !current_user_can( 'edit_post', $post_id ) ) return;
334
+
335
+ $this->delete_post($post_id);
336
+
337
+ // Save the player options
338
+ $enable_player = ( isset( $_REQUEST[ '_wcmp_enable_player' ] ) ) ? 1 : 0;
339
+ $show_in = (isset($_REQUEST[ '_wcmp_show_in' ]) && in_array($_REQUEST[ '_wcmp_show_in' ], array('single', 'multiple'))) ? $_REQUEST[ '_wcmp_show_in' ] : 'all';
340
+ $player_style = (
341
+ isset( $_REQUEST[ '_wcmp_player_layout' ] ) &&
342
+ in_array( $_REQUEST[ '_wcmp_player_layout' ], $this->_player_layouts )
343
+ ) ? $_REQUEST[ '_wcmp_player_layout' ] : WCMP_DEFAULT_PLAYER_LAYOUT;
344
+
345
+ $player_controls = (
346
+ isset( $_REQUEST[ '_wcmp_player_controls' ] ) &&
347
+ in_array( $_REQUEST[ '_wcmp_player_controls' ], $this->_player_controls )
348
+ ) ? $_REQUEST[ '_wcmp_player_controls' ] : WCMP_DEFAULT_PLAYER_CONTROLS;
349
+
350
+ $player_title = ( isset( $_REQUEST[ '_wcmp_player_title' ] ) ) ? 1 : 0;
351
+ $merge_grouped = ( isset( $_REQUEST[ '_wcmp_merge_in_grouped' ] ) ) ? 1 : 0;
352
+ $play_all = (isset($_REQUEST['_wcmp_play_all'])) ? 1 : 0;
353
+ $preload = (
354
+ isset($_REQUEST['_wcmp_preload']) &&
355
+ in_array($_REQUEST['_wcmp_preload'], array('none', 'metadata', 'auto'))
356
+ ) ? $_REQUEST['_wcmp_preload'] : 'none';
357
+
358
+ $on_cover = (($player_controls == 'button' || $player_controls == 'default') && isset($_REQUEST['_wcmp_player_on_cover'])) ? 1 : 0;
359
+
360
+ add_post_meta( $post_id, '_wcmp_enable_player', $enable_player, true );
361
+ add_post_meta( $post_id, '_wcmp_show_in', $show_in, true );
362
+ add_post_meta( $post_id, '_wcmp_player_layout', $player_style, true );
363
+ add_post_meta( $post_id, '_wcmp_player_controls', $player_controls, true );
364
+ add_post_meta( $post_id, '_wcmp_player_title', $player_title, true );
365
+ add_post_meta( $post_id, '_wcmp_merge_in_grouped', $merge_grouped, true );
366
+ add_post_meta( $post_id, '_wcmp_preload', $preload, true );
367
+ add_post_meta( $post_id, '_wcmp_play_all', $play_all, true );
368
+ add_post_meta( $post_id, '_wcmp_on_cover', $on_cover, true );
369
+ } // End save_post
370
+
371
+ public function delete_post($post_id)
372
+ {
373
+ $post = get_post($post_id);
374
+ if ( !isset($post) || 'product' !== $post->post_type || !current_user_can( 'edit_post', $post_id ) ) return;
375
+
376
+ // Delete truncated version of the audio file
377
+ $this->_delete_truncated_files( $post_id );
378
+
379
+ delete_post_meta( $post_id, '_wcmp_enable_player' );
380
+ delete_post_meta( $post_id, '_wcmp_show_in' );
381
+ delete_post_meta( $post_id, '_wcmp_merge_in_grouped' );
382
+ delete_post_meta( $post_id, '_wcmp_player_layout' );
383
+ delete_post_meta( $post_id, '_wcmp_player_controls' );
384
+ delete_post_meta( $post_id, '_wcmp_player_title' );
385
+ delete_post_meta( $post_id, '_wcmp_preload' );
386
+ delete_post_meta( $post_id, '_wcmp_play_all' );
387
+ delete_post_meta( $post_id, '_wcmp_on_cover' );
388
+ } // End delete_post
389
+
390
+ public function enqueue_resources()
391
+ {
392
+ if( $this->_enqueued_resources ) return;
393
+ $this->_enqueued_resources = true;
394
+
395
+ if(function_exists('wp_add_inline_script'))
396
+ {
397
+ wp_add_inline_script('wp-mediaelement','try{if(mejs && mejs.i18n && "undefined" == typeof mejs.i18n.locale) mejs.i18n.locale={};}catch(mejs_err){if(console) console.log(mejs_err);};');
398
+ }
399
+
400
+ // Registering resources
401
+ wp_register_style(
402
+ 'wp-mediaelement_22212',
403
+ 'https://cdnjs.cloudflare.com/ajax/libs/mediaelement/2.21.2/mediaelementplayer.min.css'
404
+ );
405
+ wp_register_script(
406
+ 'wp-mediaelement_22212',
407
+ 'https://cdnjs.cloudflare.com/ajax/libs/mediaelement/2.21.2/mediaelement-and-player.min.js'
408
+ );
409
+
410
+ wp_enqueue_style( 'wp-mediaelement_22212' );
411
+ wp_enqueue_style( 'wp-mediaelement-skins', 'https://cdnjs.cloudflare.com/ajax/libs/mediaelement/2.21.2/mejs-skins.min.css' );
412
+ wp_enqueue_style( 'wcmp-style', plugin_dir_url(__FILE__).'css/style.css' );
413
+ wp_enqueue_script('jquery');
414
+ wp_enqueue_script('wp-mediaelement_22212');
415
+ wp_enqueue_script('wcmp-script', plugin_dir_url(__FILE__).'js/public.js', array('jquery', 'wp-mediaelement_22212'),'1.0.104');
416
+
417
+ $play_all = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr(
418
+ '_wcmp_play_all',
419
+ // This option is only for compatibility with versions previous to 1.0.28
420
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( 'play_all', 0 )
421
+ );
422
+
423
+ if(is_product())
424
+ {
425
+ global $post;
426
+ if(!empty($post) && $post->post_type == 'product')
427
+ {
428
+ $play_all = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
429
+ $post->ID,
430
+ '_wcmp_play_all',
431
+ // This option is only for compatibility with versions previous to 1.0.28
432
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_product_attr(
433
+ $post->ID,
434
+ 'play_all',
435
+ $play_all
436
+ )
437
+ );
438
+ }
439
+ }
440
+ wp_localize_script(
441
+ 'wcmp-script',
442
+ 'wcmp_global_settings',
443
+ array(
444
+ 'play_all'=>intval($play_all),
445
+ 'onload' => $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr('_wcmp_onload', false)
446
+ )
447
+ );
448
+ } // End enqueue_resources
449
+
450
+ /**
451
+ * Replace the shortcode to display a playlist with all songs.
452
+ */
453
+ public function replace_playlist_shortcode($atts)
454
+ {
455
+ global $post;
456
+
457
+ $output = '';
458
+ if(!$this->_insert_player) return $output;
459
+
460
+ if(!is_array($atts)) $atts = array();
461
+ if(empty($atts['products_ids']) && !empty($post) && $post->post_type == 'product')
462
+ $atts['products_ids'] = $post->ID;
463
+
464
+ extract(
465
+ shortcode_atts(
466
+ array(
467
+ 'products_ids' => '*',
468
+ 'highlight_current_product' => 0,
469
+ 'continue_playing' => 0,
470
+ 'player_style' => WCMP_DEFAULT_PLAYER_LAYOUT,
471
+ 'controls' => 'track',
472
+ 'layout' => 'new',
473
+ 'cover' => 0
474
+ ),
475
+ $atts
476
+ )
477
+ );
478
+
479
+ // Typecasting variables.
480
+ $cover = @intval($cover);
481
+
482
+ // get the produts ids
483
+ $products_ids = preg_replace( '/[^\d\,\*]/', '', $products_ids);
484
+ $products_ids = preg_replace( '/(\,\,)+/', '', $products_ids);
485
+ $products_ids = trim($products_ids, ',');
486
+
487
+ if( strlen( $products_ids ) == 0 ) return $output;
488
+
489
+ // MAIN CODE GOES HERE
490
+ global $wpdb, $post;
491
+
492
+ $current_post_id = !empty( $post ) ? (is_int($post) ? $post : $post->ID) : -1;
493
+
494
+ $query = 'SELECT posts.ID FROM '.$wpdb->posts.' AS posts, '.$wpdb->postmeta.' as postmeta WHERE posts.post_status="publish" AND posts.post_type="product" AND posts.ID = postmeta.post_id AND postmeta.meta_key="_wcmp_enable_player" AND (postmeta.meta_value="yes" OR postmeta.meta_value="1")';
495
+
496
+ if( strpos( '*', $products_ids ) === false )
497
+ {
498
+ $query .= ' AND posts.ID IN ('.$products_ids.')';
499
+ $query .= ' ORDER BY FIELD(posts.ID,'.$products_ids.')';
500
+ }
501
+ else
502
+ {
503
+ $query .= ' ORDER BY posts.post_title ASC';
504
+ }
505
+
506
+ $products = $wpdb->get_results( $query );
507
+ if( !empty( $products ) )
508
+ {
509
+ // Enqueue resources
510
+
511
+ $this->enqueue_resources();
512
+ wp_enqueue_style( 'wcmp-playlist-widget-style', plugin_dir_url(__FILE__).'widgets/playlist_widget/css/style.css' );
513
+ wp_enqueue_script( 'wcmp-playlist-widget-script', plugin_dir_url(__FILE__).'widgets/playlist_widget/js/public.js' );
514
+ wp_localize_script(
515
+ 'wcmp-playlist-widget-script',
516
+ 'wcmp_widget_settings',
517
+ array('continue_playing' => $continue_playing)
518
+ );
519
+ $counter = 0;
520
+ foreach( $products as $product )
521
+ {
522
+ $product_obj = wc_get_product( $product->ID );
523
+ $counter++;
524
+ $preload = $this->get_product_attr($product->ID, '_wcmp_preload', '');
525
+ $class = 'wcmp-even-product';
526
+ if( $counter%2 == 1) $class = 'wcmp-odd-product';
527
+
528
+ $audio_files = $this->get_product_files( $product->ID );
529
+ if(!is_array($audio_files)) continue;
530
+
531
+ if($cover)
532
+ {
533
+ $featured_image = get_the_post_thumbnail_url($product->ID);
534
+ }
535
+
536
+ if($layout == 'new')
537
+ {
538
+ $price = $product_obj->get_price();
539
+ $output .= '
540
+ <div class="wcmp-widget-product controls-'.esc_attr($controls).' '.esc_attr( $class ).' '.esc_attr( ( $product->ID == $current_post_id && $highlight_current_product) ? 'wcmp-current-product' : '' ).'">
541
+ <div class="wcmp-widget-product-header">
542
+ <div class="wcmp-widget-product-title">
543
+ <a href="'.esc_url( get_permalink( $product->ID ) ).'">'.$product_obj->get_name().'</a>
544
+ </div><!-- product title -->
545
+ ';
546
+ if(@floatval($price) != 0)
547
+ {
548
+ $output .= '<div class="wcmp-widget-product-purchase">
549
+ '.wc_price($product_obj->get_price(), '').' <a href="?add-to-cart='.$product->ID.'"></a>
550
+ </div><!-- product purchase -->
551
+ ';
552
+ }
553
+ $output .= '</div>
554
+ <div class="wcmp-widget-product-files">
555
+ ';
556
+
557
+ if(!empty($featured_image))
558
+ $output .= '<img src="'.esc_attr($featured_image).'" class="wcmp-widget-feature-image" /><div class="wcmp-widget-product-files-list">';
559
+
560
+ foreach( $audio_files as $index => $file )
561
+ {
562
+ $audio_url = $this->generate_audio_url( $product->ID, $index, $file );
563
+ $duration = $this->_get_duration_by_url($file['file']);
564
+ $audio_tag = apply_filters(
565
+ 'wcmp_widget_audio_tag',
566
+ $this->get_player(
567
+ $audio_url,
568
+ array(
569
+ 'player_controls' => $controls,
570
+ 'player_style' => $player_style,
571
+ 'media_type' => $file[ 'media_type' ],
572
+ 'id' => $index,
573
+ 'duration' => $duration,
574
+ 'preload' => $preload
575
+ )
576
+ ),
577
+ $product->ID,
578
+ $index
579
+ );
580
+ $file_title = esc_html(apply_filters('wcmp_widget_file_name', $file[ 'name' ], $product->ID, $index));
581
+ $output .= '
582
+ <div class="wcmp-widget-product-file">
583
+ '.$audio_tag.''.$file_title.'<div style="clear:both;"></div>
584
+ </div><!--product file -->
585
+ ';
586
+ }
587
+
588
+ if(!empty($featured_image))
589
+ {
590
+ $output .= '</div>';
591
+ }
592
+
593
+ $output .= '
594
+ </div><!-- product-files -->
595
+ </div><!-- product -->
596
+ ';
597
+ }
598
+ else // Load the previous playlist layout
599
+ {
600
+ $output .= '<ul class="wcmp-widget-playlist controls-'.esc_attr($controls).' '.esc_attr( $class ).' '.esc_attr( ( $product->ID == $current_post_id && $highlight_current_product) ? 'wcmp-current-product' : '' ).'">';
601
+
602
+ if(!empty($featured_image))
603
+ $output .= '<li style="display:table-row;"><img src="'.esc_attr($featured_image).'" class="wcmp-widget-feature-image" /><div class="wcmp-widget-product-files-list"><ul>';
604
+
605
+ foreach( $audio_files as $index => $file )
606
+ {
607
+ $audio_url = $this->generate_audio_url( $product->ID, $index, $file );
608
+ $duration = $this->_get_duration_by_url($file['file']);
609
+ $audio_tag = apply_filters(
610
+ 'wcmp_widget_audio_tag',
611
+ $this->get_player(
612
+ $audio_url,
613
+ array(
614
+ 'player_controls' => $controls,
615
+ 'player_style' => $player_style,
616
+ 'media_type' => $file[ 'media_type' ],
617
+ 'id' => $index,
618
+ 'duration' => $duration,
619
+ 'preload' => $preload
620
+ )
621
+ ),
622
+ $product->ID,
623
+ $index
624
+ );
625
+ $file_title = esc_html(apply_filters('wcmp_widget_file_name', ( ( !empty( $file[ 'name' ] ) ) ? $file[ 'name' ] : $product->post_title ),$product->ID, $index));
626
+
627
+ $output .= '<li class="wcmp-widget-playlist-item">'.$audio_tag.'<a href="'.esc_url( get_permalink( $product->ID ) ).'">'.$file_title.'</a><div style="clear:both;"/></li>';
628
+ }
629
+ if(!empty($featured_image))
630
+ {
631
+ $output .= '</ul></div></li>';
632
+ }
633
+ $output .= '</ul>';
634
+ }
635
+ }
636
+ }
637
+ return $output;
638
+ } // End replace_playlist_shortcode
639
+
640
+ /**
641
+ * Used for accepting the <source> tags
642
+ */
643
+ function allowed_html_tags( $allowedposttags, $context )
644
+ {
645
+ if(!in_array('source', $allowedposttags))
646
+ {
647
+ $allowedposttags['source'] = array('src'=>true, 'type'=>true);
648
+ }
649
+ return $allowedposttags;
650
+ } // End allowed_html_tags
651
+
652
+ //******************** WOOCOMMERCE ACTIONS ************************
653
+
654
+ public function woocommerce_product_title($title, $product)
655
+ {
656
+ $player = '';
657
+ ob_start();
658
+ $this->include_main_player($product);
659
+ $player .= ob_get_contents();
660
+ ob_end_clean();
661
+ return $player.$title;
662
+ } // End woocommerce_product_title
663
+
664
+ /**
665
+ * Load the additional attributes to select the player layout
666
+ */
667
+ public function woocommerce_player_settings()
668
+ {
669
+ include_once 'views/player_options.php';
670
+ } // End woocommerce_player_settings
671
+
672
+ public function get_player(
673
+ $audio_url,
674
+ $args = array()
675
+ )
676
+ {
677
+
678
+ $default_args = array(
679
+ 'media_type' => 'mp3',
680
+ 'player_style' => WCMP_DEFAULT_PLAYER_LAYOUT,
681
+ 'player_controls' => WCMP_DEFAULT_PLAYER_CONTROLS,
682
+ 'duration' => false
683
+ );
684
+
685
+ $args = array_merge( $default_args, $args );
686
+ $id = ( !empty( $args[ 'id' ] ) ) ? 'id="'.esc_attr( $args[ 'id' ] ).'"' : '';
687
+
688
+ $preload = (!empty($args['preload'])) ? $args['preload'] : $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr(
689
+ '_wcmp_preload',
690
+ // This option is only for compatibility with versions previous to 1.0.28
691
+ $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr( 'preload', 'none' )
692
+ );
693
+
694
+ return '<audio '.$id.' preload="none" data-lazyloading="'.esc_attr($preload).'" class="wcmp-player '.esc_attr($args[ 'player_controls' ]).' '.esc_attr($args[ 'player_style' ]).'" '.((!empty($args['duration']))? 'data-duration="'.esc_attr($args['duration']).'"': '').'><source src="'.esc_url($audio_url).'" type="audio/'.esc_attr($args['media_type']).'" /></audio>';
695
+
696
+ } // End get_player
697
+
698
+ public function get_product_files( $id )
699
+ {
700
+ $product = wc_get_product( $id );
701
+ if( !empty($product) )
702
+ return $this->_get_product_files( array( 'product' => $product, 'all' => 1 ) );
703
+ return array();
704
+ }
705
+
706
+ public function generate_audio_url( $product_id, $file_id, $file_data = array())
707
+ {
708
+ return $this->_generate_audio_url( $product_id, $file_id, $file_data);
709
+ }
710
+
711
+ public function include_main_player($product = '')
712
+ {
713
+ if(!$this->_insert_player) return;
714
+ if(!is_object($product)) $product = wc_get_product();
715
+ $files = $this->_get_product_files( array( 'product' => $product, 'first' => true ) );
716
+ if( !empty( $files ) )
717
+ {
718
+ $id = $product->get_id();
719
+
720
+ $show_in = $this->get_product_attr( $id, '_wcmp_show_in', 'all' );
721
+ if(
722
+ ($show_in == 'single' && !is_product()) ||
723
+ ($show_in == 'multiple' && is_product())
724
+ ) return;
725
+ $preload = $this->get_product_attr($id, '_wcmp_preload', '');
726
+ $this->enqueue_resources();
727
+
728
+ $player_style = $this->get_product_attr( $id, '_wcmp_player_layout', WCMP_DEFAULT_PLAYER_LAYOUT );
729
+ $player_controls = ( $this->get_product_attr( $id, '_wcmp_player_controls', WCMP_DEFAULT_PLAYER_CONTROLS ) != 'all' ) ? 'track' : '';
730
+
731
+ $file = reset($files);
732
+ $index = key($files);
733
+ $audio_url = $this->_generate_audio_url( $id, $index, $file);
734
+ $duration = $this->_get_duration_by_url($file['file']);
735
+ $audio_tag = apply_filters(
736
+ 'wcmp_audio_tag',
737
+ $this->get_player(
738
+ $audio_url,
739
+ array(
740
+ 'player_controls' => $player_controls,
741
+ 'player_style' => $player_style,
742
+ 'media_type' => $file[ 'media_type' ],
743
+ 'duration' => $duration,
744
+ 'preload' => $preload
745
+ )
746
+ ),
747
+ $id,
748
+ $index
749
+ );
750
+
751
+ do_action('wcmp_before_player_shop_page',$id);
752
+ print '<div class="wcmp-player-container product-'.$file['product'].'">'.$audio_tag.'</div>';
753
+ do_action('wcmp_after_player_shop_page',$id);
754
+ }
755
+ } // End include_main_player
756
+
757
+ public function include_all_players($product = '')
758
+ {
759
+ if(!$this->_insert_player) return;
760
+ if(!is_object($product)) $product = wc_get_product();
761
+ $files = $this->_get_product_files( array( 'product' => $product, 'all' => true ) );
762
+ if( !empty( $files ) )
763
+ {
764
+ $id = $product->get_id();
765
+
766
+ $show_in = $this->get_product_attr( $id, '_wcmp_show_in', 'all' );
767
+ if(
768
+ ($show_in == 'single' && !is_singular()) ||
769
+ ($show_in == 'multiple' && is_singular())
770
+ ) return;
771
+ $preload = $this->get_product_attr($id, '_wcmp_preload', '');
772
+ $this->enqueue_resources();
773
+ $player_style = $this->get_product_attr( $id, '_wcmp_player_layout', WCMP_DEFAULT_PLAYER_LAYOUT );
774
+ $player_controls = $this->get_product_attr( $id, '_wcmp_player_controls', WCMP_DEFAULT_PLAYER_CONTROLS );
775
+ $player_title = intval( $this->get_product_attr( $id, '_wcmp_player_title', WCMP_DEFAULT_PlAYER_TITLE ) );
776
+ $merge_grouped = intval( $this->get_product_attr( $id, '_wcmp_merge_in_grouped', 0 ) );
777
+ $merge_grouped_clss = ($merge_grouped) ? 'merge_in_grouped_products' : '';
778
+
779
+ $counter = count( $files );
780
+ do_action('wcmp_before_players_product_page',$id);
781
+ if( $counter == 1 )
782
+ {
783
+ $player_controls = ($player_controls == 'button') ? 'track' : '';
784
+ $file = reset($files);
785
+ $index = key($files);
786
+ $audio_url = $this->_generate_audio_url( $id, $index, $file );
787
+ $duration = $this->_get_duration_by_url($file['file']);
788
+ $audio_tag = apply_filters(
789
+ 'wcmp_audio_tag',
790
+ $this->get_player(
791
+ $audio_url,
792
+ array(
793
+ 'player_controls' => $player_controls,
794
+ 'player_style' => $player_style,
795
+ 'media_type' => $file[ 'media_type' ],
796
+ 'duration' => $duration,
797
+ 'preload' => $preload
798
+ )
799
+ ),
800
+ $id,
801
+ $index
802
+ );
803
+ $title = esc_html(($player_title)?apply_filters('wcmp_file_name',$file['name'],$id,$index):'');
804
+ print '<div class="wcmp-player-container '.$merge_grouped_clss.' product-'.$file['product'].'">'.$audio_tag.'</div><div class="wcmp-player-title">'.$title.'</div><div style="clear:both;"></div>';
805
+ }
806
+ elseif( $counter > 1 )
807
+ {
808
+ $before = '<table class="wcmp-player-list '.$merge_grouped_clss.'">';
809
+ $after = '';
810
+ foreach( $files as $index => $file )
811
+ {
812
+ $evenOdd = ( $counter % 2 == 1 ) ? 'wcmp-odd-row' : 'wcmp-even-row';
813
+ $counter--;
814
+ $audio_url = $this->_generate_audio_url( $id, $index, $file );
815
+ $duration = $this->_get_duration_by_url($file['file']);
816
+ $audio_tag = apply_filters(
817
+ 'wcmp_audio_tag',
818
+ $this->get_player(
819
+ $audio_url,
820
+ array(
821
+ 'player_style' => $player_style,
822
+ 'player_controls' => ($player_controls != 'all' ) ? 'track' : '',
823
+ 'media_type' => $file[ 'media_type' ],
824
+ 'duration' => $duration,
825
+ 'preload' => $preload
826
+ )
827
+ ),
828
+ $id,
829
+ $index
830
+ );
831
+ $title = esc_html(($player_title)?apply_filters('wcmp_file_name',$file['name'],$id,$index):'');
832
+
833
+ print $before;
834
+ $before = '';
835
+ $after = '</table>';
836
+ if($player_controls != 'all' )
837
+ {
838
+ print '<tr class="'.esc_attr( $evenOdd ).' product-'.$file['product'].'"><td class="wcmp-player-container wcmp-column-player-'.esc_attr($player_style).'">'.$audio_tag.'</td><td class="wcmp-player-title wcmp-column-player-title">'.$title.'</td></tr>';
839
+ }
840
+ else
841
+ {
842
+ print '<tr class="'.esc_attr( $evenOdd ).' product-'.$file['product'].'"><td><div class="wcmp-player-container">'.$audio_tag.'</div><div class="wcmp-player-title wcmp-column-player-title">'.$title.'</div></td></tr>';
843
+ }
844
+ }
845
+ print $after;
846
+ }
847
+ do_action('wcmp_after_players_product_page',$id);
848
+ }
849
+ } // End include_all_players
850
+
851
+ public function player_in_cart($cart_item, $cart_item_key)
852
+ {
853
+ $product = wc_get_product( $cart_item['product_id'] );
854
+ $this->include_all_players($product);
855
+ } // player_in_cart
856
+
857
+ // Integration with woocommerce-product-table by barn2media
858
+ public function product_table_data_name( $name, $product )
859
+ {
860
+ ob_start();
861
+ $this->include_main_player($product);
862
+ $player = ob_get_contents();
863
+ ob_end_clean();
864
+ $player = str_replace('<div ', '<div style="display:inline-block" ', $player);
865
+ return $player.$name;
866
+ } // product_table_data_name
867
+
868
+ public function add_data_product($player, $product_id, $index)
869
+ {
870
+ $player = preg_replace('/<audio\b/i', '<audio data-product="'.esc_attr($product_id).'" ',$player);
871
+ return $player;
872
+ } // End add_data_product
873
+
874
+ public function add_class_attachment($html, $product, $size, $attr, $placeholder, $image )
875
+ {
876
+ $id = $product->get_id();
877
+ $html = $this->_add_class($html, $product);
878
+ return $html;
879
+ } // End add_class_attachment
880
+
881
+ public function add_class_single_product_image($html, $post_thumbnail_id)
882
+ {
883
+ global $product;
884
+
885
+ if(!empty($product))
886
+ {
887
+ $html = $this->_add_class($html,$product);
888
+ }
889
+ return $html;
890
+ } // add_class_single_product_image
891
+
892
+ //******************** PRIVATE METHODS ************************
893
+ private function _load_addons()
894
+ {
895
+ $path = __DIR__.'/addons';
896
+ $wcmp = $this;
897
+
898
+ if( file_exists( $path ) )
899
+ {
900
+ $addons = dir( $path );
901
+ while( false !== ( $entry = $addons->read() ) )
902
+ {
903
+ if( strlen( $entry ) > 3 && strtolower( pathinfo( $entry, PATHINFO_EXTENSION) ) == 'php' )
904
+ {
905
+ include_once $addons->path.'/'.$entry;
906
+ }
907
+ }
908
+ }
909
+ } // End _load_addons
910
+
911
+ private function _preview()
912
+ {
913
+ $user = wp_get_current_user();
914
+ $allowed_roles = array('editor', 'administrator', 'author');
915
+
916
+ if(array_intersect($allowed_roles, $user->roles ))
917
+ {
918
+ if(!empty($_REQUEST['wcmp-preview']))
919
+ {
920
+ // Sanitizing variable
921
+ $preview = stripcslashes($_REQUEST['wcmp-preview']);
922
+ $preview = strip_tags($preview);
923
+
924
+ // Remove every shortcode that is not in the plugin
925
+ remove_all_shortcodes();
926
+ add_shortcode('wcmp-playlist', array(&$this, 'replace_playlist_shortcode' ));
927
+
928
+ if(has_shortcode($preview, 'wcmp-playlist'))
929
+ {
930
+ print '<!DOCTYPE html>';
931
+ $if_empty = __('There are no products that satisfy the block\'s settings', 'music-player-for-woocommerce');
932
+ wp_enqueue_script('jquery');
933
+ $output = do_shortcode($preview);
934
+ if(preg_match('/^\s*$/', $output))
935
+ {
936
+ $output = '<div>'.$if_empty.'</div>';
937
+ }
938
+
939
+ // Deregister all scripts and styles for loading only the plugin styles.
940
+ global $wp_styles, $wp_scripts;
941
+ if(!empty($wp_scripts)) $wp_scripts->reset();
942
+ $this->enqueue_resources();
943
+ if(!empty($wp_styles)) $wp_styles->do_items();
944
+ if(!empty($wp_scripts)) $wp_scripts->do_items();
945
+
946
+ print '<div class="wcmp-preview-container">'.$output.'</div>';
947
+ print'<script type="text/javascript">jQuery(window).on("load", function(){ var frameEl = window.frameElement; if(frameEl) frameEl.height = jQuery(".wcmp-preview-container").outerHeight(true)+25; });</script>';
948
+ exit;
949
+ }
950
+
951
+ }
952
+ }
953
+ } // End _preview
954
+
955
+ private function _createDir()
956
+ {
957
+ // Generate upload dir
958
+ $_files_directory = wp_upload_dir();
959
+ $this->_files_directory_path = rtrim( $_files_directory[ 'basedir' ], '/' ).'/wcmp/';
960
+ $this->_files_directory_url = rtrim( $_files_directory[ 'baseurl' ], '/' ).'/wcmp/';
961
+ $this->_files_directory_url = preg_replace('/^http(s)?:\/\//', '//', $this->_files_directory_url);
962
+ if( !file_exists( $this->_files_directory_path ) ) @mkdir( $this->_files_directory_path, 0755 );
963
+ } // End _createDir
964
+
965
+ private function _deleteDir( $dirPath )
966
+ {
967
+ try
968
+ {
969
+ if (!is_dir($dirPath)) return;
970
+ if (substr($dirPath, strlen($dirPath) - 1, 1) != '/') $dirPath .= '/';
971
+ $files = glob($dirPath . '*', GLOB_MARK);
972
+ foreach ($files as $file)
973
+ {
974
+ if (is_dir($file)) $this->_deleteDir($file);
975
+ else unlink($file);
976
+ }
977
+ rmdir($dirPath);
978
+ }
979
+ catch( Exception $err )
980
+ {
981
+ return;
982
+ }
983
+ } // End _deleteDir
984
+
985
+ private function _get_duration_by_url( $url )
986
+ {
987
+ global $wpdb;
988
+ try
989
+ {
990
+ $attachment = $wpdb->get_col($wpdb->prepare("SELECT ID FROM $wpdb->posts WHERE guid RLIKE %s;", $url ));
991
+ if(empty($attachment))
992
+ {
993
+ $uploads_dir = wp_upload_dir();
994
+ $uploads_url = $uploads_dir['baseurl'];
995
+ $parsed_url = explode( parse_url( $uploads_url, PHP_URL_PATH ), $url );
996
+ $this_host = str_ireplace( 'www.', '', parse_url( home_url(), PHP_URL_HOST ) );
997
+ $file_host = str_ireplace( 'www.', '', parse_url( $url, PHP_URL_HOST ) );
998
+ if (!isset($parsed_url[1]) || empty($parsed_url[1]) || ($this_host != $file_host)) return false;
999
+ $file = trim($parsed_url[1], '/');
1000
+ $attachment = $wpdb->get_col($wpdb->prepare("SELECT post_id FROM $wpdb->postmeta WHERE meta_key='_wp_attached_file' AND meta_value RLIKE %s;", $file));
1001
+ }
1002
+ if(!empty($attachment))
1003
+ {
1004
+ $metadata = wp_get_attachment_metadata( $attachment[ 0 ] );
1005
+ if( $metadata !== false && !empty($metadata['length_formatted']) )
1006
+ {
1007
+ return $metadata['length_formatted'];
1008
+ }
1009
+ }
1010
+ }
1011
+ catch(Exception $err)
1012
+ {}
1013
+ return false;
1014
+ } // End _get_duration_by_url
1015
+
1016
+ private function _generate_audio_url( $product_id, $file_index, $file_data = array() )
1017
+ {
1018
+ if(!empty($file_data['file']))
1019
+ {
1020
+ $file_url = $file_data['file'];
1021
+ if(!empty($file_data['play_src'])) return $file_url; // Play src audio file, without copying or truncate it.
1022
+
1023
+ // If the playback of music are tracked with Google Analytics, should not be loaded directly the audio files.
1024
+ $_wcmp_analytics_property = trim($this->get_global_attr('_wcmp_analytics_property', ''));
1025
+ if($_wcmp_analytics_property == '')
1026
+ {
1027
+ $file_name = $this->_demo_file_name($file_url);
1028
+
1029
+ $file_path = $this->_files_directory_path.$file_name;
1030
+
1031
+ if(file_exists($file_path))
1032
+ {
1033
+ return 'http'.((is_ssl()) ? 's:' : ':').$this->_files_directory_url.$file_name;
1034
+ }
1035
+ }
1036
+ }
1037
+ $url = esc_url_raw($_SERVER['REQUEST_URI']);
1038
+ $url .= ( (strpos( $url, '?' ) === false) ? '?' : '&' ).'wcmp-action=play&wcmp-product='.$product_id.'&wcmp-file='.$file_index;
1039
+ return $url;
1040
+ } // End _generate_audio_url
1041
+
1042
+ private function _delete_truncated_files( $product_id )
1043
+ {
1044
+ $files_arr = get_post_meta( $product_id, '_downloadable_files', true );
1045
+ if( !empty( $files_arr ) && is_array( $files_arr ) )
1046
+ {
1047
+ foreach( $files_arr as $file )
1048
+ {
1049
+ if( is_array( $file ) && !empty( $file[ 'file' ] ) )
1050
+ {
1051
+ $ext = pathinfo( $file[ 'file' ], PATHINFO_EXTENSION );
1052
+ $file_name = md5( $file[ 'file' ] ).( (!empty($ext) ) ? '.'.$ext : '' );
1053
+ @unlink( $this->_files_directory_path.$file_name );
1054
+ }
1055
+ }
1056
+ }
1057
+
1058
+ } // End _delete_truncated_files
1059
+
1060
+ /**
1061
+ * Check if the file is an audio file and return its type or false
1062
+ */
1063
+ private function _is_audio( $file_path )
1064
+ {
1065
+ if( preg_match( '/\.(mp3|ogg|oga|wav|wma|mp4|m4a)$/i', $file_path, $match ) )
1066
+ return $match[ 1 ];
1067
+
1068
+ // From troubleshoot
1069
+ $extension = pathinfo($file_path,PATHINFO_EXTENSION);
1070
+ $troubleshoot_default_extension = $GLOBALS[ 'WooCommerceMusicPlayer' ]->get_global_attr('_wcmp_default_extension', false);
1071
+ if((empty($extension) || !preg_match('/^[a-z\d]{3,4}$/i', $extension)) && $troubleshoot_default_extension) return 'mp3';
1072
+
1073
+ return false;
1074
+ } // End _is_audio
1075
+
1076
+ private function _sort_list($product_a, $product_b)
1077
+ {
1078
+ $menu_order_a = $product_a->get_menu_order();
1079
+ $menu_order_b = $product_b->get_menu_order();
1080
+ if ($menu_order_a == $menu_order_b)
1081
+ {
1082
+ $name_a = $product_a->get_name();
1083
+ $name_b = $product_b->get_name();
1084
+ if($name_a == $name_b) return 0;
1085
+ return ($name_a < $name_b) ? -1 : 1;
1086
+ }
1087
+ return ($menu_order_a < $menu_order_b) ? -1 : 1;
1088
+ } // End _sort_list
1089
+
1090
+ private function _edit_files_array($product_id, $files, $play_src = 0)
1091
+ {
1092
+ $p_files = array();
1093
+ foreach($files as $key => $file)
1094
+ {
1095
+ $p_key = $key.'_'.$product_id;
1096
+ if(gettype($file) == "object") $file = (array)$file->get_data();
1097
+ $file['product']=$product_id;
1098
+ $file['play_src'] = $play_src;
1099
+ $p_files[$p_key] = $file;
1100
+ }
1101
+ return $p_files;
1102
+ } // end _edit_files_array
1103
+
1104
+ private function _get_recursive_product_files($product, $files_arr )
1105
+ {
1106
+ $id = $product->get_id();
1107
+ $product_type = $product->get_type();
1108
+
1109
+ if( $product_type == 'variation' )
1110
+ {
1111
+ // $_files = $product->get_files();
1112
+ $_files = $product->get_downloads();
1113
+ $_files = $this->_edit_files_array($id, $_files);
1114
+ $files_arr = array_merge( $files_arr, $_files );
1115
+ }
1116
+ else
1117
+ {
1118
+
1119
+ if( !$this->get_product_attr( $id, '_wcmp_enable_player', false ) ) return $files_arr;
1120
+
1121
+ switch( $product_type )
1122
+ {
1123
+ case 'simple':
1124
+ // $_files = $product->get_files();
1125
+ $_files = $product->get_downloads();
1126
+ $_files = $this->_edit_files_array($id, $_files );
1127
+ $files_arr = array_merge( $files_arr, $_files );
1128
+ break;
1129
+ case 'variable':
1130
+ case 'grouped':
1131
+ $children = $product->get_children();
1132
+
1133
+ foreach( $children as $key => $child_id )
1134
+ $children[$key] = wc_get_product($child_id);
1135
+
1136
+ uasort($children, array(&$this,'_sort_list'));
1137
+
1138
+ foreach( $children as $child_obj )
1139
+ $files_arr = $this->_get_recursive_product_files( $child_obj, $files_arr );
1140
+
1141
+ break;
1142
+ }
1143
+ }
1144
+ return $files_arr;
1145
+ } // End _get_recursive_product_files
1146
+
1147
+ private function _get_product_files( $args )
1148
+ {
1149
+ if( empty( $args[ 'product' ] ) ) return false;
1150
+
1151
+ $product = $args[ 'product' ];
1152
+ $files = $this->_get_recursive_product_files( $product, array() );
1153
+
1154
+ if( empty( $files ) ) return false;
1155
+
1156
+ $audio_files = array();
1157
+ foreach( $files as $index => $file )
1158
+ {
1159
+ if( !empty( $file[ 'file' ] ) && ($media_type = $this->_is_audio( $file[ 'file' ] )) !== false )
1160
+ {
1161
+ $file[ 'media_type' ] = $media_type;
1162
+
1163
+ if( !empty( $args[ 'file_id' ] ) )
1164
+ {
1165
+ if( $args[ 'file_id' ] == $index )
1166
+ {
1167
+ $audio_files[ $index ] = $file;
1168
+ return $audio_files;
1169
+ }
1170
+ }
1171
+ elseif( !empty( $args[ 'first' ] ) )
1172
+ {
1173
+ $audio_files[ $index ] = $file;
1174
+ return $audio_files;
1175
+ }
1176
+ elseif( !empty( $args[ 'all' ] ) )
1177
+ {
1178
+ $audio_files[ $index ] = $file;
1179
+ }
1180
+ }
1181
+ }
1182
+
1183
+ return $audio_files;
1184
+ } // End _get_product_files
1185
+
1186
+ private function _demo_file_name($url)
1187
+ {
1188
+ $file_extension = pathinfo($url, PATHINFO_EXTENSION);
1189
+ $file_name = md5( $url ).( ( !empty( $file_extension ) && preg_match('/^[a-z\d]{3,4}$/i', $file_extension) ) ? '.'.$file_extension : '.mp3' );
1190
+ return $file_name;
1191
+ } // End _demo_file_name
1192
+
1193
+ /**
1194
+ * Create a temporal file and redirect to the new file
1195
+ */
1196
+ private function _output_file( $args )
1197
+ {
1198
+ if( empty( $args[ 'url' ] ) ) return;
1199
+ $url = $args[ 'url' ];
1200
+ $url = do_shortcode($url);
1201
+
1202
+ if(strpos($url, '//') === 0) $url_fixed = 'http'.(is_ssl() ? 's:' : ':').$url;
1203
+ elseif(strpos($url, '/') === 0) $url_fixed = rtrim(WCMP_WEBSITE_URL, '/').$url;
1204
+ else $url_fixed = $url;
1205
+
1206
+ $file_name = $this->_demo_file_name($url);
1207
+ $text = 'The requested URL was not found on this server';
1208
+ $file_path = $this->_files_directory_path.$file_name;
1209
+
1210
+ if(file_exists($file_path)){
1211
+ header('location: http'.((is_ssl()) ? 's:' : ':').$this->_files_directory_url.$file_name);
1212
+ exit;
1213
+ }else{
1214
+ try{
1215
+ $c = false;
1216
+ if( ( $path = $this->_is_local( $url_fixed ) ) !== false ){
1217
+ $c = copy( $path, $file_path);
1218
+ }else{
1219
+ $response = wp_remote_get($url_fixed, array( 'timeout' => WCMP_REMOTE_TIMEOUT, 'stream' => true, 'filename' => $file_path ) );
1220
+ if( !is_wp_error( $response ) && $response['response']['code'] == 200 ) $c = true;
1221
+ }
1222
+
1223
+ if( $c === true ){
1224
+ header('location: http'.((is_ssl()) ? 's:' : ':').$this->_files_directory_url.$file_name);
1225
+ exit;
1226
+ }
1227
+ }
1228
+ catch(Exception $err)
1229
+ {
1230
+ error_log($err->getMessage());
1231
+ }
1232
+ $text = 'It is not possible to generate the file for demo. Possible causes are: - the amount of memory allocated to the php script on the web server is not enough, - the execution time is too short, - or the "uploads/wcmp" directory does not have write permissions.';
1233
+ }
1234
+ $this->_print_page_not_found( $text );
1235
+ } // End _output_file
1236
+
1237
+ /**
1238
+ * Add the class name: product-<product id> to cover images associated to the products.
1239
+ *
1240
+ * @param $html, a html piece of code that includes the <img> tag.
1241
+ * @param $product, the product object.
1242
+ */
1243
+ private function _add_class($html, $product)
1244
+ {
1245
+ if(preg_match('/<img\b[^>]*>/i',$html, $image))
1246
+ {
1247
+ $id = $product->get_id();
1248
+ if($GLOBALS['WooCommerceMusicPlayer']->get_product_attr($id, '_wcmp_on_cover', 0))
1249
+ {
1250
+ if(preg_match('/\bclass\s*=/i', $image[0]))
1251
+ $tmp_image = preg_replace('/\bclass\s*=\s*[\'"]/i', "$0product-$id ", $image[0]);
1252
+ else
1253
+ $tmp_image = preg_replace('/<img\b/i', "<img $0 class=\"product-$id\" ", $image[0]);
1254
+
1255
+ $html = str_replace($image[0], $tmp_image, $html);
1256
+ }
1257
+ }
1258
+
1259
+ return $html;
1260
+ } // End _add_class
1261
+
1262
+ /**
1263
+ * Print not found page if file it is not accessible
1264
+ */
1265
+ private function _print_page_not_found( $text = 'The requested URL was not found on this server' ){
1266
+ header("Status: 404 Not Found");
1267
+ echo '<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
1268
+ <HTML><HEAD>
1269
+ <TITLE>404 Not Found</TITLE>
1270
+ </HEAD><BODY>
1271
+ <H1>Not Found</H1>
1272
+ <P>'.$text.'</P>
1273
+ </BODY></HTML>
1274
+ ';
1275
+ } // End _print_page_not_found
1276
+
1277
+ private function _is_local( $url )
1278
+ {
1279
+ $attachment_id = attachment_url_to_postid( $url );
1280
+ if( $attachment_id )
1281
+ {
1282
+ $file_path = get_attached_file( $attachment_id );
1283
+ if( file_exists( $file_path ) ) return $file_path;
1284
+ }
1285
+ return false;
1286
+ } // End _is_local
1287
+
1288
+ private function _tracking_play_event($product_id, $file_url)
1289
+ {
1290
+ $_wcmp_analytics_property = trim($this->get_global_attr('_wcmp_analytics_property', ''));
1291
+ if($_wcmp_analytics_property != '')
1292
+ {
1293
+ $cid = 555;
1294
+ try
1295
+ {
1296
+ if(isset($_COOKIE['_ga']))
1297
+ {
1298
+ $cid_parts = explode('.', $_COOKIE['_ga'], 3);
1299
+ $cid = $cid_parts[2];
1300
+ error_log('CID_Pure: '.$_COOKIE['_ga']);
1301
+ error_log('CID: '.$cid);
1302
+ }
1303
+ }
1304
+ catch(Exception $err)
1305
+ {
1306
+
1307
+ }
1308
+
1309
+ $_response = wp_remote_post(
1310
+ 'http://www.google-analytics.com/collect',
1311
+ array(
1312
+ 'body' => array(
1313
+ 'v' => 1,
1314
+ 'tid' => $_wcmp_analytics_property,
1315
+ 'cid' => $cid,
1316
+ 't' => 'event',
1317
+ 'ec' => 'Music Player for WooCommerce',
1318
+ 'ea' => 'play',
1319
+ 'el' => $file_url,
1320
+ 'ev' => $product_id
1321
+ )
1322
+ )
1323
+ );
1324
+
1325
+ if(is_wp_error($_response))
1326
+ {
1327
+ error_log($_response->get_error_message());
1328
+ }
1329
+ }
1330
+ } // _tracking_play_event
1331
+
1332
+ public static function troubleshoot($option)
1333
+ {
1334
+ if(!is_admin())
1335
+ {
1336
+ // Solves a conflict caused by the "Speed Booster Pack" plugin
1337
+ if(is_array($option) && isset($option['jquery_to_footer'])) unset($option['jquery_to_footer']);
1338
+ }
1339
+ return $option;
1340
+ } // End troubleshoot
1341
+ } // End Class WooCommerceMusicPlayer
1342
+
1343
+ $GLOBALS[ 'WooCommerceMusicPlayer' ] = new WooCommerceMusicPlayer;
1344
+ }
widgets/playlist_widget.php ADDED
@@ -0,0 +1,153 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <?php
2
+ if(!function_exists('wcmp_register_playlist_widget'))
3
+ {
4
+ function wcmp_register_playlist_widget()
5
+ {
6
+ return register_widget("WCMP_PLAYLIST_WIDGET");
7
+ }
8
+ }
9
+ add_action( 'widgets_init', 'wcmp_register_playlist_widget' );
10
+
11
+ if( !class_exists( 'WCMP_PLAYLIST_WIDGET' ) )
12
+ {
13
+ class WCMP_PLAYLIST_WIDGET extends WP_Widget
14
+ {
15
+ function __construct()
16
+ {
17
+ $widget_ops = array('classname' => 'WCMP_PLAYLIST_WIDGET', 'description' => 'Includes a playlist with the audio files of products selected' );
18
+
19
+ parent::__construct('WCMP_PLAYLIST_WIDGET', 'Music Player for WooCommerce - Playlist', $widget_ops);
20
+ }
21
+
22
+ function form($instance)
23
+ {
24
+ $instance = wp_parse_args( (array) $instance, array( 'title' => '', 'products_ids' => '', 'highlight_current_product' => 0, 'continue_playing' => 0, 'player_style' => WCMP_DEFAULT_PLAYER_LAYOUT ) );
25
+
26
+ $title = sanitize_text_field($instance['title']);
27
+ $products_ids = sanitize_text_field($instance['products_ids']);
28
+ $highlight_current_product = sanitize_text_field($instance['highlight_current_product']);
29
+ $continue_playing = sanitize_text_field($instance['continue_playing']);
30
+ $player_style = sanitize_text_field($instance['player_style']);
31
+ $playlist_layout = sanitize_text_field((!empty($instance['playlist_layout'])) ? $instance['playlist_layout'] : 'new');
32
+
33
+ $play_all = sanitize_text_field($GLOBALS['WooCommerceMusicPlayer']->get_global_attr(
34
+ '_wcmp_play_all',
35
+ // This option is only for compatibility with versions previous to 1.0.28
36
+ $GLOBALS['WooCommerceMusicPlayer']->get_global_attr(
37
+ 'play_all',
38
+ 0
39
+ )
40
+ ));
41
+ $preload = sanitize_text_field($GLOBALS['WooCommerceMusicPlayer']->get_global_attr(
42
+ '_wcmp_preload',
43
+ // This option is only for compatibility with versions previous to 1.0.28
44
+ $GLOBALS['WooCommerceMusicPlayer']->get_global_attr(
45
+ 'preload',
46
+ 'metadata'
47
+ )
48
+ ));
49
+ ?>
50
+ <p>
51
+ <label for="<?php echo $this->get_field_id('title'); ?>"><?php _e( 'Title', 'music-player-for-woocommerce' ); ?>: <input class="widefat" id="<?php echo $this->get_field_id('title'); ?>" name="<?php echo $this->get_field_name('title'); ?>" type="text" value="<?php echo esc_attr($title); ?>" /></label>
52
+ </p>
53
+ <p>
54
+ <label for="<?php echo $this->get_field_id('products_ids'); ?>"><?php _e( 'Products IDs', 'music-player-for-woocommerce' ); ?>: <input class="widefat" id="<?php echo $this->get_field_id('products_ids'); ?>" name="<?php echo $this->get_field_name('products_ids'); ?>" type="text" value="<?php echo esc_attr($products_ids); ?>" placeholder="<?php _e( 'Products IDs separated by comma, or a * for all', 'music-player-for-woocommerce' ); ?>" /></label>
55
+ </p>
56
+ <p>
57
+ <?php
58
+ _e( 'Enter the ID of products separated by comma, or a * symbol to includes all products in the playlist.', 'music-player-for-woocommerce' );
59
+ ?>
60
+ </p>
61
+ <p>
62
+ <label for="<?php echo $this->get_field_id('playlist_layout'); ?>"><?php _e( 'Playlist layout', 'music-player-for-woocommerce' ); ?>: </label>
63
+ </p>
64
+ <p>
65
+ <label><input name="<?php echo $this->get_field_name('playlist_layout'); ?>" type="radio" value="new" <?php echo (($playlist_layout == 'new') ? 'checked' : '') ;?> style="float:left; margin-top:8px;" /><?php _e('New layout', 'music-player-for-woocommerce'); ?></label>
66
+ </p>
67
+ <p>
68
+ <label><input name="<?php echo $this->get_field_name('playlist_layout'); ?>" type="radio" value="old" <?php echo (($playlist_layout == 'old') ? 'checked' : '') ;?> style="float:left; margin-top:8px;" /><?php _e('Original layout', 'music-player-for-woocommerce'); ?></label>
69
+ </p>
70
+ <p>
71
+ <label for="<?php echo $this->get_field_id('player_style'); ?>"><?php _e( 'Player layout', 'music-player-for-woocommerce' ); ?>: </label>
72
+ </p>
73
+ <p>
74
+ <label><input name="<?php echo $this->get_field_name('player_style'); ?>" type="radio" value="mejs-classic" <?php echo (($player_style == 'mejs-classic') ? 'checked' : '') ;?> style="float:left; margin-top:8px;" /><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin1_btn.png" /></label>
75
+ </p>
76
+ <p>
77
+ <label><input name="<?php echo $this->get_field_name('player_style'); ?>" type="radio" value="mejs-ted" <?php echo (($player_style == 'mejs-ted') ? 'checked' : '') ;?> style="float:left; margin-top:8px;" /><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin2_btn.png" /></label>
78
+ </p>
79
+ <p>
80
+ <label><input name="<?php echo $this->get_field_name('player_style'); ?>" type="radio" value="mejs-wmp" <?php echo (($player_style == 'mejs-wmp') ? 'checked' : '') ;?> style="float:left; margin-top:16px;" /><img src="<?php print esc_url(WCMP_PLUGIN_URL); ?>/views/assets/skin3_btn.png" /></label>
81
+ </p>
82
+ <p>
83
+ <label for="<?php echo $this->get_field_id('play_all'); ?>"><?php _e( 'Play all', 'music-player-for-woocommerce' ); ?>: <input id="<?php echo $this->get_field_id('play_all'); ?>" name="<?php echo $this->get_field_name('play_all'); ?>" type="checkbox" <?php echo ( ( $play_all ) ? 'CHECKED' : '' );
84
+ ?> /></label>
85
+ </p>
86
+ <p>
87
+ <label for="<?php echo $this->get_field_id('preload'); ?>"><?php _e( 'Preload', 'music-player-for-woocommerce' ); ?>:</label><br />
88
+ <label><input name="<?php echo $this->get_field_name('preload'); ?>" type="radio" value="none" <?php echo ( ( $preload == 'none' ) ? 'CHECKED' : '' ); ?> /> None</label>
89
+ <label><input name="<?php echo $this->get_field_name('preload'); ?>" type="radio" value="metadata" <?php echo ( ( $preload == 'metadata' ) ? 'CHECKED' : '' ); ?> /> Metadata</label>
90
+ <label><input name="<?php echo $this->get_field_name('preload'); ?>" type="radio" value="auto" <?php echo ( ( $preload == 'auto' ) ? 'CHECKED' : '' ); ?> /> Auto</label>
91
+ </p>
92
+ <p>
93
+ <label for="<?php echo $this->get_field_id('highlight_current_product'); ?>"><?php _e( 'Highlight the current product', 'music-player-for-woocommerce' ); ?>: <input id="<?php echo $this->get_field_id('highlight_current_product'); ?>" name="<?php echo $this->get_field_name('highlight_current_product'); ?>" type="checkbox" <?php echo ( ( $highlight_current_product ) ? 'CHECKED' : '' ); ?> /></label>
94
+ </p>
95
+ <p>
96
+ <label for="<?php echo $this->get_field_id('continue_playing'); ?>"><?php _e( 'Continue playing after navigate', 'music-player-for-woocommerce' ); ?>: <input id="<?php echo $this->get_field_id('continue_playing'); ?>" name="<?php echo $this->get_field_name('continue_playing'); ?>" type="checkbox" <?php echo ( ( $continue_playing ) ? 'CHECKED' : '' ); ?> value="1" /></label>
97
+ </p>
98
+ <p>
99
+ <?php
100
+ _e( 'Continue playing the same song at same position after navigate. You can experiment some delay because the music player should to load the audio file again, and in some mobiles devices, where the action of the user is required, the player cannot starting playing automatically.', 'music-player-for-woocommerce' );
101
+ ?>
102
+ </p>
103
+ <?php
104
+ }
105
+
106
+ function update($new_instance, $old_instance)
107
+ {
108
+ $instance = $old_instance;
109
+ $instance['title'] = sanitize_text_field($new_instance['title']);
110
+ $instance['products_ids'] = sanitize_text_field($new_instance['products_ids']);
111
+ $instance['highlight_current_product'] = sanitize_text_field($new_instance['highlight_current_product']);
112
+ $instance['continue_playing'] = sanitize_text_field($new_instance['continue_playing']);
113
+ $instance['player_style'] = sanitize_text_field($new_instance['player_style']);
114
+ $instance['playlist_layout'] = sanitize_text_field((!empty($new_instance['playlist_layout'])) ? $new_instance['playlist_layout'] : 'new');
115
+
116
+ $global_settings = get_option('wcmp_global_settings', array());
117
+ $global_settings['_wcmp_play_all'] = (!empty($new_instance['play_all'])) ? 1 : 0;
118
+ $global_settings['_wcmp_preload'] = (
119
+ !empty($new_instance['preload']) &&
120
+ in_array($new_instance['preload'], array('none','metadata','auto'))
121
+ ) ? $new_instance['preload'] : 'metadata';
122
+
123
+ update_option( 'wcmp_global_settings', $global_settings );
124
+
125
+ return $instance;
126
+ }
127
+
128
+ function widget($args, $instance)
129
+ {
130
+ if(!is_array($args)) $args = array();
131
+ extract($args, EXTR_SKIP);
132
+
133
+ $title = empty($instance['title']) ? ' ' : apply_filters('widget_title', $instance['title']);
134
+
135
+ $output = $GLOBALS[ 'WooCommerceMusicPlayer' ]->replace_playlist_shortcode(
136
+ array(
137
+ 'products_ids' => $instance['products_ids'],
138
+ 'highlight_current_product' => $instance['highlight_current_product'],
139
+ 'continue_playing' => $instance['continue_playing'],
140
+ 'player_style' => $instance['player_style'],
141
+ 'layout' => (!empty($instance['playlist_layout'])) ? $instance['playlist_layout'] : 'new'
142
+ )
143
+ );
144
+
145
+ if( strlen( $output ) == 0 ) return;
146
+
147
+ print $before_widget;
148
+ if (!empty($title)) print $before_title . $title . $after_title;
149
+ print $output;
150
+ print $after_widget;
151
+ }
152
+ } // End Class WCMP_PLAYLIST_WIDGET
153
+ }
widgets/playlist_widget/css/style.css ADDED
@@ -0,0 +1,29 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ .wcmp-widget-playlist{list-style: none; margin:0 !important; padding:0 !important;}
2
+ .wcmp-widget-playlist ul{margin: 0; padding: 0;}
3
+ .wcmp-widget-playlist *{word-break:normal !important;}
4
+ .controls-track .wcmp-widget-playlist-item{display: block; line-height:normal;padding: 5px 0 !important;clear:both;}
5
+ .wcmp-widget-playlist-item .mejs-controls{top: 0;}
6
+ .wcmp-odd-product{background-color:#FAFAFA; border-top: 1px solid #DADADA; border-bottom: 1px solid #DADADA;}
7
+ .wcmp-current-product{background-color:#FFFFD7;}
8
+
9
+ /* New playlist layout */
10
+ .wcmp-widget-product{padding:10px;margin:0 !important;}
11
+ .wcmp-widget-product *{font-family: Arial, Helvetica, sans-serif !important;word-break:normal !important;color:#111;}
12
+ .wcmp-widget-product.wcmp-odd-product{background-color:rgba(250, 250, 250, 0.9); border: 0 !important;}
13
+ .wcmp-widget-product.wcmp-even-product{background-color: rgba(255,255,255,0.8);}
14
+ .wcmp-widget-product:hover,
15
+ .wcmp-widget-product.wcmp-current-product{background-color:#FFEDD8;}
16
+ .wcmp-widget-product-header{display:flex; flex-wrap:wrap; border-bottom:1px solid #DADADA; margin-bottom:15px;}
17
+ .wcmp-widget-product:hover .wcmp-widget-product-header,
18
+ .wcmp-widget-product.wcmp-current-product .wcmp-widget-product-header{border-color:white;}
19
+ .wcmp-widget-product-title a{text-decoration: none !important; font-size: 1.3em;}
20
+ .wcmp-widget-product-purchase{margin-left: auto;}
21
+ .wcmp-widget-product-purchase a{background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='24' height='24' viewBox='0 0 24 24'><path d='M7 18c-1.1 0-1.99.9-1.99 2S5.9 22 7 22s2-.9 2-2-.9-2-2-2zM1 2v2h2l3.6 7.59-1.35 2.45c-.16.28-.25.61-.25.96 0 1.1.9 2 2 2h12v-2H7.42c-.14 0-.25-.11-.25-.25l.03-.12.9-1.63h7.45c.75 0 1.41-.41 1.75-1.03l3.58-6.49c.08-.14.12-.31.12-.48 0-.55-.45-1-1-1H5.21l-.94-2H1zm16 16c-1.1 0-1.99.9-1.99 2s.89 2 1.99 2 2-.9 2-2-.9-2-2-2z'/><path d='M0 0h24v24H0z' fill='none'/></svg>");
22
+ display:inline-block; width:24px; height:24px;
23
+ }
24
+ .wcmp-widget-product .wcmp-widget-product-file{display:block;margin-bottom:5px;}
25
+
26
+ .wcmp-widget-product-files{display: table-row;}
27
+ .wcmp-widget-feature-image{display:table-cell;max-width:80px;margin-right:10px;}
28
+ .wcmp-widget-playlist .wcmp-widget-feature-image{margin-top:5px; margin-bottom: 5px;}
29
+ .wcmp-widget-product-files-list{display:table-cell;vertical-align: top;}
widgets/playlist_widget/js/public.js ADDED
@@ -0,0 +1,83 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ jQuery( window ).on(
2
+ 'load',
3
+ function()
4
+ {
5
+ function setCookie( value )
6
+ {
7
+ var expires = "expires="+ctime;
8
+ document.cookie = cname + "=" + value + "; " + expires;
9
+ }
10
+
11
+ function deleteCookie()
12
+ {
13
+ document.cookie = cname+"=; expires=Thu, 01 Jan 1970 00:00:00 UTC";
14
+ }
15
+
16
+ function getCookie()
17
+ {
18
+ var name = cname + "=";
19
+ var ca = document.cookie.split(';');
20
+ for(var i = 0; i < ca.length; i++) {
21
+ var c = ca[i];
22
+ while (c.charAt(0) == ' ') {
23
+ c = c.substring(1);
24
+ }
25
+ if (c.indexOf(name) == 0) {
26
+ return c.substring(name.length, c.length);
27
+ }
28
+ }
29
+ return "";
30
+ }
31
+
32
+ // Get history
33
+ var $ = jQuery,
34
+ cname = 'wcmp_playing',
35
+ ctime = 0,
36
+ continue_playing = false,
37
+ cookie = getCookie(),
38
+ parts,
39
+ player;
40
+
41
+ if(typeof wcmp_widget_settings != 'undefined')
42
+ if('continue_playing' in wcmp_widget_settings)
43
+ continue_playing = wcmp_widget_settings['continue_playing'];
44
+
45
+ if(continue_playing)
46
+ {
47
+ if( !/^\s*$/.test( cookie ) )
48
+ {
49
+ parts = cookie.split( '||' );
50
+ if( parts.length == 2 )
51
+ {
52
+ player = $( '#'+parts[ 0 ] );
53
+ if( player.length )
54
+ {
55
+ player[0].currentTime = parts[1];
56
+ player[0].play();
57
+ }
58
+ }
59
+ }
60
+
61
+ // Set events
62
+ $( '.wcmp-player audio' )
63
+ .on(
64
+ 'timeupdate',
65
+ function()
66
+ {
67
+ if(!isNaN( this.currentTime ) && this.currentTime)
68
+ {
69
+ var id = $( this ).attr( 'id' );
70
+ setCookie( id+'||'+this.currentTime );
71
+ }
72
+ }
73
+ )
74
+ .on(
75
+ 'ended pause',
76
+ function()
77
+ {
78
+ deleteCookie();
79
+ }
80
+ );
81
+ }
82
+ }
83
+ );