Completed
Push — master ( ab284c...4fdc7c )
by Justin
07:07
created

display-items-functions.php ➔ wpsc_stock_control_forms()   F

Complexity

Conditions 17
Paths 5376

Size

Total Lines 116
Code Lines 73

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 17
eloc 73
c 1
b 0
f 0
nc 5376
nop 0
dl 0
loc 116
rs 2

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
/**
3
 * WPSC Product form generation functions
4
 *
5
 * @package wp-e-commerce
6
 * @since 3.7
7
 */
8
9
global $wpsc_product_defaults;
10
11
$wpsc_product_defaults = array(
12
	'id' => '0',
13
	'name' => '',
14
	'description' => '',
15
	'additional_description' => '',
16
	'price' => '0.00',
17
	'weight' => '0',
18
	'weight_unit' => 'pound',
19
	'pnp' => '0.00',
20
	'international_pnp' => '0.00',
21
	'file' => '0',
22
	'image' => '',
23
	'category' => '0',
24
	'brand' => '0',
25
	'quantity_limited' => '0',
26
	'quantity' => '0',
27
	'special' => '0',
28
	'special_price' => 0.00,
29
	'display_frontpage' => '0',
30
	'notax' => '0',
31
	'publish' => '1',
32
	'active' => '1',
33
	'donation' => '0',
34
	'no_shipping' => '0',
35
	'thumbnail_image' => '',
36
	'thumbnail_state' => '1',
37
	'meta' => array(
38
		'external_link' => NULL,
0 ignored issues
show
Coding Style introduced by
TRUE, FALSE and NULL must be lowercase; expected null, but found NULL.
Loading history...
39
		'external_link_text' => NULL,
0 ignored issues
show
Coding Style introduced by
TRUE, FALSE and NULL must be lowercase; expected null, but found NULL.
Loading history...
40
		'external_link_target' => NULL,
0 ignored issues
show
Coding Style introduced by
TRUE, FALSE and NULL must be lowercase; expected null, but found NULL.
Loading history...
41
		'merchant_notes' => NULL,
0 ignored issues
show
Coding Style introduced by
TRUE, FALSE and NULL must be lowercase; expected null, but found NULL.
Loading history...
42
		'sku' => NULL,
0 ignored issues
show
Coding Style introduced by
TRUE, FALSE and NULL must be lowercase; expected null, but found NULL.
Loading history...
43
		'engraved' => '0',
44
		'can_have_uploaded_image' => '0',
45
		'table_rate_price' => array(
46
			'quantity' => array(
47
				0 => '',
48
			),
49
			'table_price' => array(
50
				0 => '',
51
			),
52
		),
53
	),
54
);
55
56
function wpsc_redirect_variation_update( $location, $post_id ) {
0 ignored issues
show
Unused Code introduced by
The parameter $post_id is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
57
	global $post;
58
59
	if ( $post->post_parent > 0 && 'wpsc-product' == $post->post_type )
60
		wp_redirect( admin_url( 'post.php?post='.$post->post_parent.'&action=edit' ) );
61
	else
62
		return $location;
63
64
}
65
66
add_filter( 'redirect_post_location', 'wpsc_redirect_variation_update', 10, 2 );
67
68
function wpsc_price_control_forms() {
69
	global $post, $wpdb, $variations_processor, $wpsc_product_defaults;
70
71
	$product_data         = get_post_custom( $post->ID );
72
	$product_data['meta'] = maybe_unserialize( $product_data );
73
74
	foreach ( $product_data['meta'] as $meta_key => $meta_value ) {
75
		$product_data['meta'][$meta_key] = $meta_value[0];
76
	}
77
78
	$product_meta = array();
79
80
	if ( ! empty( $product_data['_wpsc_product_metadata'] ) ) {
81
		$product_meta = maybe_unserialize( $product_data['_wpsc_product_metadata'][0] );
82
	}
83
84
	if ( isset( $product_data['meta']['_wpsc_currency'] ) ) {
85
		$product_alt_currency = maybe_unserialize( $product_data['meta']['_wpsc_currency'] );
86
	}
87
88
	if ( ! isset( $product_data['meta']['_wpsc_table_rate_price'] ) ) {
89
		$product_data['meta']['_wpsc_table_rate_price'] = $wpsc_product_defaults['meta']['table_rate_price'];
90
	}
91
92
	if ( isset( $product_meta['_wpsc_table_rate_price'] ) ) {
93
		$product_meta['table_rate_price']['state']      = 1;
94
		$product_meta['table_rate_price']              += $product_meta['_wpsc_table_rate_price'];
95
		$product_data['meta']['_wpsc_table_rate_price'] = $product_meta['_wpsc_table_rate_price'];
96
	}
97
0 ignored issues
show
Coding Style introduced by
Functions must not contain multiple empty lines in a row; found 2 empty lines
Loading history...
98
99
	if ( ! isset( $product_data['meta']['_wpsc_is_donation'] ) ) {
100
		$product_data['meta']['_wpsc_is_donation'] = $wpsc_product_defaults['donation'];
101
	}
102
103
	if ( ! isset( $product_meta['table_rate_price']['state'] ) ) {
104
		$product_meta['table_rate_price']['state'] = null;
105
	}
106
107
	if ( ! isset( $product_meta['table_rate_price']['quantity'] ) ) {
108
		$product_meta['table_rate_price']['quantity'] = $wpsc_product_defaults['meta']['table_rate_price']['quantity'][0];
109
	}
110
111
	if ( ! isset( $product_data['meta']['_wpsc_price'] ) ) {
112
		$product_data['meta']['_wpsc_price'] = $wpsc_product_defaults['price'];
113
	}
114
115
	if ( ! isset( $product_data['special'] ) ) {
116
		$product_data['special'] = $wpsc_product_defaults['special'];
117
	}
118
119
	if ( ! isset( $product_data['meta']['_wpsc_special_price'] ) ) {
120
		$product_data['meta']['_wpsc_special_price'] = $wpsc_product_defaults['special_price'];
121
	}
122
123
	$product_data['meta']['_wpsc_special_price'] = wpsc_format_number( $product_data['meta']['_wpsc_special_price'] );
124
125
	if ( ! isset( $product_data['meta']['_wpsc_price'] ) ) {
126
		$product_data['meta']['_wpsc_price'] = 0;
127
	}
128
129
	$product_data['meta']['_wpsc_price'] = wpsc_format_number( $product_data['meta']['_wpsc_price'] );
130
131
	$currency_data = $wpdb->get_results( "SELECT * FROM `" . WPSC_TABLE_CURRENCY_LIST . "` ORDER BY `country` ASC", ARRAY_A );
132
133
	/* Get country name and symbol */
134
	$currency_type = get_option( 'currency_type' );
135
	$country       = new WPSC_Country( $currency_type );
136
137
	$ct_code = $country->get_currency_code();   // Country currency code
138
	$ct_symb = $country->get_currency_symbol(); // Country symbol
139
140
	$price      = $product_data['meta']['_wpsc_price'];
141
	$sale_price = $product_data['meta']['_wpsc_special_price'];
142
143
	$wp_38 = version_compare( $GLOBALS['wp_version'], '3.8', '>=' );
144
145
	$currency_delete_class = $wp_38 ? ' dashicons dashicons-dismiss' : '';
146
	$currency_delete_text  = $wp_38 ? '' : 'x';
147
?>
148
		<em id="wpsc_product_price_metabox_live_title" class="wpsc_metabox_live_title">
149
			<p>&nbsp;<?php echo esc_html( $ct_symb ); ?><span><?php echo esc_html( $sale_price ); ?></span></p>
150
			<del><?php echo esc_html( $ct_symb ); ?><span><?php echo esc_html( $price ) ?></span></del>
151
		</em>
152
		<input type="hidden" id="parent_post" name="parent_post" value="<?php echo $post->post_parent; ?>" />
153
		<?php /* Lots of tedious work is avoided with this little line. */ ?>
154
		<input type="hidden" id="product_id" name="product_id" value="<?php echo $post->ID; ?>" />
155
156
		<?php /* Check product if a product has variations */ ?>
157
		<?php if ( wpsc_product_has_children( $post->ID ) ) : ?>
158
			<?php $price = wpsc_product_variation_price_from( $post->ID ); ?>
159
			<p style="margin-top: 6px;"><?php echo sprintf( __( 'This product has variations. To edit the price, please use the <a href="%s">Variation Controls</a>.' , 'wp-e-commerce'  ), '#wpsc_product_variation_forms' ); ?></p>
160
			<p><?php printf( __( 'Price: %s and above.' , 'wp-e-commerce' ), $price ); ?></p>
161
		<?php else: ?>
162
163
		<div class='wpsc_floatleft' style="width:100px;">
164
			<label for="wpsc_price"><?php _e( 'Price', 'wp-e-commerce' ); ?></label>
165
			<?php echo esc_html( $ct_symb ); ?> <input id="wpsc_price"
166
					type="text"
167
					style="width: 70px;"
168
					name="meta[_wpsc_price]"
169
					value="<?php echo esc_attr( $price );  ?>" />
170
		</div>
171
172
		<div class='wpsc_floatleft' style='width:95px; margin-left:30px;'>
173
			<label for='wpsc_sale_price'><?php _e( 'Sale Price', 'wp-e-commerce' ); ?></label>
174
			<?php echo esc_html( $ct_symb ); ?> <input id = "wpsc_sale_price"
175
					type="text"
176
					style="width: 70px;"
177
					value="<?php echo esc_attr( $sale_price ); ?>"
178
					name='meta[_wpsc_special_price]' />
179
		</div>
180
181
		<div class="wpsc-currency-layers">
182
			<table>
183
				<thead>
184
					<tr>
185
						<th class="type" colspan="2"><?php esc_html_e( 'Alternative Currencies:', 'wp-e-commerce' ); ?></th>
186
						<th class="price"><?php esc_html_e( 'Price:', 'wp-e-commerce' ); ?></th>
187
					<tr>
188
				</thead>
189
				<tbody>
190
					<?php
191
					if ( isset( $product_alt_currency ) && is_array( $product_alt_currency ) ) :
192
						$i = 0;
193
						foreach ( $product_alt_currency as $iso => $alt_price ) :
194
							$i++;
195
							?>
196
							<tr class="wpsc_additional_currency">
197
								<td class="remove"><a href="#" class="wpsc_delete_currency_layer<?php echo $currency_delete_class; ?>" rel="<?php echo $iso; ?>"><?php echo $currency_delete_text; ?></a></td>
198
								<td>
199
									<select name="newCurrency[]" class="newCurrency">
200
										<?php foreach ( $currency_data as $currency ) : ?>
201
											<option value="<?php echo absint( $currency['id'] ); ?>" <?php selected( $iso, $currency['isocode'] ); ?>>
202
												<?php echo esc_html( $currency['country'] ); ?> (<?php echo esc_html( $currency['currency'] ); ?>)
203
											</option>
204
										<?php endforeach; ?>
205
									</select>
206
								</td>
207
								<td><input class="newCurrPrice text" size="8" name="newCurrPrice[]" value="<?php echo esc_attr( $alt_price ); ?>" /></td>
208
							</tr>
209
							<?php
210
						endforeach;
211
					endif;
212
					?>
213
					<tr id="wpsc_currency_row_template" class="template hidden">
214
						<td class="remove"><a href="#" class="wpsc_delete_currency_layer<?php echo $currency_delete_class; ?>"><?php echo $currency_delete_text; ?></a></td>
215
						<td>
216
							<select name="newCurrency[]" class="newCurrency">
217
								<?php foreach ( (array) $currency_data as $currency ) { ?>
218
									<option value="<?php echo absint( $currency['id'] ); ?>">
219
										<?php echo esc_html( $currency['country'] ); ?>
220
									</option>
221
								<?php } ?>
222
							</select>
223
						</td>
224
						<td><input class="newCurrPrice text" size="8" name="newCurrPrice[]" value="0.00" /></td>
225
					</tr>
226
				</tbody>
227
			</table>
228
			<a href="#wpsc_currency_row_template" class="button button-small wpsc_add_new_currency"><?php esc_html_e( 'Add a Currency Option', 'wp-e-commerce' ); ?></a>
229
			<?php wp_nonce_field( 'update-options', 'wpsc-update-currency-layers', false ); ?>
230
		</div>
231
232
		<div class="wpsc-quantity-discounts">
233
			<table>
234
				<thead>
235
					<tr>
236
						<th class="qty" colspan="2"><?php esc_html_e( 'Quantity:', 'wp-e-commerce' ); ?></th>
237
						<th class="curr"><span class="hidden"><?php esc_html_e( 'Currency:', 'wp-e-commerce' ); ?><span></th>
238
						<th class="price"><?php esc_html_e( 'Price:', 'wp-e-commerce' ); ?></th>
239
					</tr>
240
				</thead>
241
				<tbody>
242
					<?php
243
					if ( count( $product_meta['table_rate_price']['quantity'] ) > 0 ) {
244
						foreach ( (array) $product_meta['table_rate_price']['quantity'] as $key => $quantity ) {
245
							if ( $quantity != '' ) {
246
								$table_price = number_format( $product_meta['table_rate_price']['table_price'][ $key ], 2, '.', '' );
247
								?>
248
								<tr>
249
									<td class="remove"><a href="#" class="remove_line<?php echo $currency_delete_class; ?>"><?php echo $currency_delete_text; ?></a></td>
250
									<td class="qty">
251
										<input type="text" size="5" value="<?php echo absint( $quantity ); ?>" name="table_rate_price[quantity][]" />
252
										<?php esc_html_e( '+', 'wp-e-commerce' ); ?>
253
									</td>
254
									<td class="curr"><?php echo $ct_code . ' ' . $ct_symb; ?></td>
255
									<td><input class="newCurrPrice text" value="<?php echo $table_price; ?>" name="table_rate_price[table_price][]" /></td>
256
								</tr>
257
								<?php
258
							}
259
						}
260
					}
261
					?>
262
					<tr id="wpsc_quantity_discount_row_template" class="template hidden">
263
						<td class="remove"><a href="#" class="remove_line<?php echo $currency_delete_class; ?>"><?php echo $currency_delete_text; ?></a></td>
264
						<td class="qty">
265
							<input size="5" value="0" name="table_rate_price[quantity][]" />
266
							<?php esc_html_e( '+', 'wp-e-commerce' ); ?>
267
						</td>
268
						<td class="curr"><?php echo $ct_code . ' ' . $ct_symb; ?></td>
269
						<td><input size="10"class="newCurrPrice text" value="0" name="table_rate_price[table_price][]" /></td>
270
					</tr>
271
				</tbody>
272
			</table>
273
			<a href="#wpsc_quantity_discount_row_template" class="add_level button button-small"><?php esc_html_e( 'Add a Quantity Discount', 'wp-e-commerce' ); ?></a>
274
			<?php wp_nonce_field( 'update-options', 'wpsc-update-quantity-discounts', false ); ?>
275
		</div>
276
277
		<input id="add_form_donation" type="checkbox" name="meta[_wpsc_is_donation]" value="yes" <?php checked( $product_data['meta']['_wpsc_is_donation'], 1 ); ?> />
278
		<label for="add_form_donation"><?php _e( 'Purchase is a donation.', 'wp-e-commerce' ) ?></label>
279
		<?php wp_nonce_field( 'update', 'wpsc_product_pricing_nonce' ); ?>
280
281
<?php endif;
282
283
}
284
function wpsc_stock_control_forms() {
285
	global $post, $wpdb, $variations_processor, $wpsc_product_defaults;
286
287
	$product_data         = get_post_custom( $post->ID );
288
	$product_data['meta'] = maybe_unserialize( $product_data );
289
290
	foreach ( $product_data['meta'] as $meta_key => $meta_value ) {
291
		$product_data['meta'][$meta_key] = $meta_value[0];
292
	}
293
294
	$product_meta = array();
295
296
	if ( ! empty( $product_data['_wpsc_product_metadata'] ) ) {
297
		$product_meta = maybe_unserialize( $product_data["_wpsc_product_metadata"][0] );
298
	}
299
300
	// this is to make sure after upgrading to 3.8.9, products will have
301
	// "notify_when_none_left" enabled by default if "unpublish_when_none_left"
302
	// is enabled.
303
	if ( ! isset( $product_meta['notify_when_none_left'] ) ) {
304
		$product_meta['notify_when_none_left'] = 0;
305
306
		if ( ! empty( $product_meta['unpublish_when_none_left'] ) ) {
307
			$product_meta['notify_when_none_left'] = 1;
308
		}
309
	}
310
311
	if ( ! isset( $product_meta['unpublish_when_none_left'] ) ) {
312
		$product_meta['unpublish_when_none_left'] = '';
313
	}
314
315
	// Display live title if stock is set
316
	if ( isset( $product_data['meta']['_wpsc_stock'] ) && is_numeric( $product_data['meta']['_wpsc_stock'] ) ) {
317
		$live_title = '<em id="wpsc_product_stock_metabox_live_title" class="wpsc_metabox_live_title">';
318
		$live_title .= sprintf( '<p><span>%s</span> %s</p>', wpsc_format_number( $product_data['meta']['_wpsc_stock'], 0 ), _x( 'left in stock', 'live preview of stock remaining in admin', 'wp-e-commerce' ) );
319
		$live_title .= '</em>';
320
321
		echo $live_title;
322
	}
323
324
	if ( ! empty( $product_meta['unpublish_when_none_left'] ) && ! isset( $product_meta['notify_when_none_left'] ) )
325
?>
326
		<label for="wpsc_sku"><abbr title="<?php esc_attr_e( 'Stock Keeping Unit', 'wp-e-commerce' ); ?>"><?php esc_html_e( 'SKU:', 'wp-e-commerce' ); ?></abbr></label>
327
<?php
328
	if ( !isset( $product_data['meta']['_wpsc_sku'] ) )
329
		$product_data['meta']['_wpsc_sku'] = $wpsc_product_defaults['meta']['sku']; ?><br />
330
			<input size='32' type='text' class='text' id="wpsc_sku" name='meta[_wpsc_sku]' value='<?php echo esc_html( $product_data['meta']['_wpsc_sku'] ); ?>' />
331
			<br style="clear:both" />
332
			<?php
333
	if ( !isset( $product_data['meta']['_wpsc_stock'] ) )
334
		$product_data['meta']['_wpsc_stock'] = ''; ?>
335
			<br /><input class='limited_stock_checkbox' id='add_form_quantity_limited' type='checkbox' value='yes' <?php if ( is_numeric( $product_data['meta']['_wpsc_stock'] ) ) echo 'checked="checked"'; else echo ''; ?> name='meta[_wpsc_limited_stock]' />
336
			<label for='add_form_quantity_limited' class='small'><?php esc_html_e( 'Product has limited stock', 'wp-e-commerce' ); ?></label>
337
			<?php
338
	if ( $post->ID > 0 ) {
339
		if ( is_numeric( $product_data['meta']['_wpsc_stock'] ) ) {?>
340
					<div class='edit_stock' style='display: block;'> <?php
341
		} else { ?>
342
					<div class='edit_stock' style='display: none;'><?php
343
		} ?>
344
					<?php if ( wpsc_product_has_children( $post->ID ) ) : ?>
345
						<?php $stock = wpsc_variations_stock_remaining( $post->ID ); ?>
346
						<p><?php echo sprintf( __( 'This product has variations. To edit the quantity, please use the <a href="%s">Variation Controls</a> below.' , 'wp-e-commerce' ), '#wpsc_product_variation_forms' ); ?></p>
347
						<p><?php printf( _n( "%s variant item in stock.", "%s variant items in stock.", $stock, 'wp-e-commerce' ), $stock ); ?></p>
348
					<?php else: ?>
349
						<div style="margin-bottom:20px;">
350
							<label for="stock_limit_quantity"><?php esc_html_e( 'Quantity in stock', 'wp-e-commerce' ); ?></label>
351
							<input type='number' min="0" step="1" style="width:80px; margin-left:50px;"
352
									id="stock_limit_quantity" name='meta[_wpsc_stock]'
353
									size='3' value='<?php echo absint( $product_data['meta']['_wpsc_stock'] ); ?>'
354
									class='stock_limit_quantity' />
355
						</div>
356
357
						<?php
358
							$remaining_quantity = wpsc_get_remaining_quantity( $post->ID );
359
							$reserved_quantity  = $product_data['meta']['_wpsc_stock'] - $remaining_quantity;
360
							if ( $reserved_quantity ) {
361
								echo '<p><em>';
362
								printf( _n('%s of them is reserved for pending or recently completed orders.',
363
										  '%s of them are reserved for pending or recently completed orders.',
364
										  $reserved_quantity, 'wp-e-commerce'), $reserved_quantity );
365
366
								echo '</em></p>';
367
							}
368
						?>
369
					<?php endif; ?>
370
371
						<p><?php esc_html_e( 'When stock reduces to zero:', 'wp-e-commerce' ); ?></p>
372
						<div class='notify_when_none_left'>
373
							<input  type='checkbox' id="notify_when_oos"
374
									name='meta[_wpsc_product_metadata][notify_when_none_left]'
375
									class='notify_when_oos'<?php checked( $product_meta['notify_when_none_left'] ); ?> />
376
							<label for="notify_when_oos"><?php esc_html_e( 'Notify site owner via email', 'wp-e-commerce' ); ?></label>
377
						</div>
378
						<div class='unpublish_when_none_left'>
379
							<input  type='checkbox' id="unpublish_when_oos"
380
									name='meta[_wpsc_product_metadata][unpublish_when_none_left]'
381
									class='unpublish_when_oos'<?php checked( $product_meta['unpublish_when_none_left'] ); ?> />
382
							<label for="unpublish_when_oos"><?php esc_html_e( 'Unpublish product from website', 'wp-e-commerce' ); ?></label>
383
384
						</div>
385
				</div> <?php
386
	} else { ?>
387
				<div style='display: none;' class='edit_stock'>
388
					 <?php esc_html_e( 'Stock Qty', 'wp-e-commerce' ); ?><input type='text' name='meta[_wpsc_stock]' value='0' size='10' />
389
					<div style='font-size:9px; padding:5px;'>
390
						<input type='checkbox' class='notify_when_oos' name='meta[_wpsc_product_metadata][notify_when_none_left]' /> <?php esc_html_e( 'Email site owner if this Product runs out of stock', 'wp-e-commerce' ); ?>
391
						<input type='checkbox' class='unpublish_when_oos' name='meta[_wpsc_product_metadata][unpublish_when_none_left]' /> <?php esc_html_e( 'Set status to Unpublished if this Product runs out of stock', 'wp-e-commerce' ); ?>
392
					</div>
393
				</div>
394
		<?php
395
	}
396
397
	wp_nonce_field( 'update', 'wpsc_product_stock_nonce' );
398
399
}
400
401
function wpsc_product_taxes_forms() {
402
	global $post, $wpdb, $wpsc_product_defaults;
403
	$product_data = get_post_custom( $post->ID );
404
405
	$product_data['meta'] = $product_meta = array();
406
	if ( !empty( $product_data['_wpsc_product_metadata'] ) )
407
		$product_data['meta'] = $product_meta = maybe_unserialize( $product_data['_wpsc_product_metadata'][0] );
408
409
	if ( !isset( $product_data['meta']['_wpsc_custom_tax'] ) )
410
		$product_data['meta']['_wpsc_custom_tax'] = '';
411
	$custom_tax = $product_data['meta']['_wpsc_custom_tax'];
412
0 ignored issues
show
Coding Style introduced by
Functions must not contain multiple empty lines in a row; found 2 empty lines
Loading history...
413
414
	if ( !isset( $product_meta['custom_tax'] ) ) {
415
		$product_meta['custom_tax'] = 0.00;
416
	}
417
418
	//Add New WPEC-Taxes Bands Here
419
	$wpec_taxes_controller = new wpec_taxes_controller();
420
421
	//display tax bands
422
	$band_select_settings = array(
423
		'id' => 'wpec_taxes_band',
424
		'name' => 'meta[_wpsc_product_metadata][wpec_taxes_band]',
425
		'label' => __( 'Custom Tax Band', 'wp-e-commerce' )
426
	);
427
	$wpec_taxes_band = '';
428
	if ( isset( $product_meta['wpec_taxes_band'] ) ) {
429
		$band = $wpec_taxes_controller->wpec_taxes->wpec_taxes_get_band_from_index( $product_meta['wpec_taxes_band'] );
0 ignored issues
show
Bug introduced by
The property wpec_taxes does not seem to exist in wpec_taxes_controller.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
430
		$wpec_taxes_band = array( 'index'=>$band['index'], 'name'=>$band['name'] );
431
	}
432
433
	$taxable_checkbox_settings = array(
434
		'type' => 'checkbox',
435
		'id' => 'wpec_taxes_taxable',
436
		'name' => 'meta[_wpsc_product_metadata][wpec_taxes_taxable]',
437
		'label' => __( 'Product is exempt from taxation.', 'wp-e-commerce' )
438
	);
439
440
	if ( isset( $product_meta['wpec_taxes_taxable'] ) && 'on' == $product_meta['wpec_taxes_taxable'] ) {
441
		$taxable_checkbox_settings['checked'] = 'checked';
442
	}
443
444
	//add taxable amount only for exclusive tax
445
	if ( !$wpec_taxes_controller->wpec_taxes_isincluded() ) {
446
		$taxable_amount_input_settings = array(
447
			'id'          =>  'wpec_taxes_taxable_amount',
0 ignored issues
show
introduced by
Expected 1 space after "=>"; 2 found
Loading history...
448
			'name'        => 'meta[_wpsc_product_metadata][wpec_taxes_taxable_amount]',
449
			'label'       => __( 'Taxable Amount', 'wp-e-commerce' ),
450
			'description' => __( 'Taxable amount in your currency, not percentage of price.', 'wp-e-commerce' ),
451
		);
452
453
		if ( isset( $product_meta['wpec_taxes_taxable_amount'] ) ) {
454
			$taxable_amount_input_settings['value'] = $product_meta['wpec_taxes_taxable_amount'];
455
456
			if ( ! empty( $product_meta['wpec_taxes_taxable_amount'] ) )
457
				$taxable_amount_input_settings['value'] = wpsc_format_number(
458
					$taxable_amount_input_settings['value']
459
				);
460
		}
461
	}// if
462
463
	$output = '<a name="wpsc_tax"></a>';
464
	$output .= '<p>'.$wpec_taxes_controller->wpec_taxes_build_input( $taxable_checkbox_settings ).'</p>';
465
	$output .= '<p>'.$wpec_taxes_controller->wpec_taxes_display_tax_bands( $band_select_settings, $wpec_taxes_band ).'</p>';
466
	$output .= '<p>';
467
		$output .=  ( !$wpec_taxes_controller->wpec_taxes_isincluded() ) ? $wpec_taxes_controller->wpec_taxes_build_input( $taxable_amount_input_settings ) : '';
0 ignored issues
show
Bug introduced by
The variable $taxable_amount_input_settings does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
introduced by
Expected 1 space after ".="; 2 found
Loading history...
468
	$output .= '</p>';
469
470
	if ( ! $wpec_taxes_controller->wpec_taxes->wpec_taxes_get_enabled() ) {
471
		$output = '<p>' . sprintf( __( 'Taxes are not enabled. See <a href="%s">Settings &gt; Taxes</a>', 'wp-e-commerce' ), admin_url( 'options-general.php?page=wpsc-settings&tab=taxes' ) ) . '</p>';
472
	}
473
474
	echo $output;
475
476
	wp_nonce_field( 'update', 'wpsc_product_tax_nonce' );
477
478
}
479
480
function wpsc_product_variation_forms() {
481
	?>
482
	<iframe src="<?php echo _wpsc_get_product_variation_form_url(); ?>"></iframe>
483
	<?php
484
}
485
486
function _wpsc_get_product_variation_form_url( $id = false ) {
487
	if ( ! $id ) {
488
		$id = get_the_ID();
489
	}
490
491
	return admin_url( 'admin-ajax.php?action=wpsc_product_variations_table&product_id=' . $id . '&_wpnonce=' . wp_create_nonce( 'wpsc_product_variations_table' ) );
492
}
493
494
function wpsc_product_shipping_forms_metabox() {
495
	wpsc_product_shipping_forms();
496
}
497
498
/**
499
 * Dimension Units
500
 *
501
 * @since   3.8.13
502
 *
503
 * @return  array  List of valid dimension units.
504
 */
505
function wpsc_dimension_units() {
506
	return array(
507
		'in'    => __( 'inches', 'wp-e-commerce' ),
508
		'cm'    => __( 'cm', 'wp-e-commerce' ),
509
		'meter' => __( 'meters', 'wp-e-commerce' )
510
	);
511
}
512
513
/**
514
 * Weight Units
515
 *
516
 * @since   3.8.13
517
 *
518
 * @return  array  List of valid weight units.
519
 */
520
function wpsc_weight_units() {
521
	return array(
522
		'pound'    => __( 'pounds', 'wp-e-commerce' ),
523
		'ounce'    => __( 'ounces', 'wp-e-commerce' ),
524
		'gram'     => __( 'grams', 'wp-e-commerce' ),
525
		'kilogram' => __( 'kilograms', 'wp-e-commerce' )
526
	);
527
}
528
529
/**
530
 * Weight Unit Display
531
 *
532
 * Returns a weight unit abbreviation for display.
533
 *
534
 * @since   3.8.13
535
 *
536
 * @param   string  $unit  Weight unit.
537
 * @return  string         Weight unit string.
538
 */
539
function wpsc_weight_unit_display( $unit ) {
540
	switch ( $unit ) {
541
		case 'pound' :
542
			return __( ' lbs.', 'wp-e-commerce' );
543
		case 'ounce' :
544
			return __( ' oz.', 'wp-e-commerce' );
545
		case 'gram' :
546
			return __( ' g', 'wp-e-commerce' );
547
		case 'kilograms' :
548
		case 'kilogram' :
549
			return __( ' kgs.', 'wp-e-commerce' );
550
	}
551
	return '';
552
}
553
554
/**
555
 * Validate Dimension Unit
556
 *
557
 * Returns a valid dimensions unit.
558
 * If the unit is not set or invalid it will be filtered using 'wpsc_default_dimension_unit'
559
 * so that an alternative default unit can be set.
560
 *
561
 * @since   3.8.13
562
 *
563
 * @param   string  $unit  Dimension unit.
564
 * @return  string         Dimension unit string.
565
 *
566
 * @uses    wpsc_default_dimension_unit
567
 */
568
function wpsc_validate_dimension_unit( $unit = '' ) {
569
570
	$default_unit = apply_filters( 'wpsc_default_dimension_unit', $unit );
571
572
	if ( empty( $unit ) && array_key_exists( $default_unit, wpsc_dimension_units() ) ) {
573
		$unit = $default_unit;
574
	}
575
576
	return $unit;
577
}
578
579
/**
580
 * Validate Weight Unit
581
 *
582
 * Returns a valid weight unit.
583
 * If the unit is not set or invalid it will be filtered using 'wpsc_default_weight_unit'
584
 * so that an alternative default unit can be set.
585
 *
586
 * @since   3.8.13
587
 *
588
 * @param   string  $unit  Weight unit.
589
 * @return  string         Weight unit string.
590
 *
591
 * @uses    wpsc_default_weight_unit
592
 */
593
function wpsc_validate_weight_unit( $unit = '' ) {
594
595
	$default_unit = apply_filters( 'wpsc_default_weight_unit', $unit );
596
597
	if ( empty( $unit ) && array_key_exists( $default_unit, wpsc_weight_units() ) ) {
598
		$unit = $default_unit;
599
	}
600
601
	return $unit;
602
}
603
604
/**
605
 * Product Shipping Forms
606
 *
607
 * @uses  wpsc_validate_weight_unit()
608
 * @uses  wpsc_validate_dimension_unit()
609
 */
610
function wpsc_product_shipping_forms( $product = false, $field_name_prefix = 'meta[_wpsc_product_metadata]', $bulk = false ) {
611
	if ( ! $product )
612
		$product_id = get_the_ID();
613
	else
614
		$product_id = $product->ID;
615
616
	$meta = get_post_meta( $product_id, '_wpsc_product_metadata', true );
617
	if ( ! is_array( $meta ) )
618
		$meta = array();
619
620
	$defaults = array(
621
		'weight'            => '',
622
		'weight_unit'       => wpsc_validate_weight_unit(),
623
		'demension_unit'    => wpsc_validate_dimension_unit(),
624
		'dimensions'        => array(),
625
		'shipping'          => array(),
626
		'no_shipping'       => '',
627
		'display_weight_as' => '',
628
	);
629
	$dimensions_defaults = array(
630
		'height' => 0,
631
		'width'  => 0,
632
		'length' => 0,
633
	);
634
	$shipping_defaults = array(
635
		'local'         => '',
636
		'international' => '',
637
	);
638
	$meta = array_merge( $defaults, $meta );
639
	$meta['dimensions'] = array_merge( $dimensions_defaults, $meta['dimensions'] );
640
	$meta['shipping'] = array_merge( $shipping_defaults, $meta['shipping'] );
641
642
	extract( $meta, EXTR_SKIP );
0 ignored issues
show
introduced by
extract() usage is highly discouraged, due to the complexity and unintended issues it might cause.
Loading history...
643
644
	foreach ( $shipping as $key => &$val ) {
645
		$val = wpsc_format_number( $val );
646
	}
647
648
	$weight = wpsc_convert_weight( $weight, 'pound', $weight_unit );
649
650
	$dimension_units = wpsc_dimension_units();
651
	$weight_units = wpsc_weight_units();
652
653
	// Why we need this????
654
	$measurements = $dimensions;
655
	$measurements['weight'] = $weight;
656
	$measurements['weight_unit'] = $weight_unit;
657
	// End why
658
659
?>
660
	<div class="wpsc-stock-editor<?php if ( $bulk ) echo ' wpsc-bulk-edit' ?>">
661
		<p class="wpsc-form-field">
662
			<input type="checkbox" id="wpsc-product-no-shipping" name="<?php echo esc_attr( $field_name_prefix ); ?>[no_shipping]" value="1" <?php checked( $no_shipping && ! $bulk ); ?>>
663
			<label for="wpsc-product-no-shipping"><?php _e( 'Product will <em>not</em> be shipped to customer', 'wp-e-commerce' ); ?></label>
664
		</p>
665
666
		<div class="wpsc-product-shipping-section wpsc-product-shipping-weight-dimensions">
667
			<p><strong><?php esc_html_e( 'Calculate Shipping Costs based on measurements', 'wp-e-commerce' ); ?></strong></p>
668
669
			<!-- WEIGHT INPUT -->
670
			<p class="wpsc-form-field">
671
				<?php if ( $bulk ) : ?>
672
					<input class="wpsc-bulk-edit-fields" type="checkbox" name="wpsc_bulk_edit[fields][measurements][weight]" value="1" />
673
				<?php endif; ?>
674
				<label for="wpsc-product-shipping-weight"><?php echo esc_html_e( 'Weight', 'wp-e-commerce' ); ?></label>
675
				<span class="wpsc-product-shipping-input">
676
					<input type="text" id="wpsc-product-shipping-weight" name="<?php echo esc_attr( $field_name_prefix ); ?>[weight]" value="<?php if ( ! $bulk ) echo esc_attr( wpsc_format_number( $weight ) ); ?>" />
677
					<select id="wpsc-product-shipping-weight-unit" name="<?php echo $field_name_prefix; ?>[weight_unit]">
678
							<?php foreach ( $weight_units as $unit => $unit_label ): ?>
679
								<option value="<?php echo esc_attr( $unit ); ?>" <?php if ( ! $bulk ) selected( $unit, $measurements['weight_unit'] ); ?>><?php echo esc_html( $unit_label ); ?></option>
680
							<?php endforeach; ?>
681
						</select>
682
				</span>
683
			</p>
684
			<!-- END WEIGHT INPUT -->
685
686
			<!-- DIMENSIONS INPUT -->
687
			<p class="wpsc-form-field">
688
				<?php if ( $bulk ) : ?>
689
					<input class="wpsc-bulk-edit-fields" type="checkbox" name="wpsc_bulk_edit[fields][measurements][dimensions]" value="1" />
690
				<?php endif; ?>
691
				<label for="wpsc-product-shipping-weight"><?php echo esc_html_e( 'Dimensions', 'wp-e-commerce' ); ?></label>
692
				<span class="wpsc-product-shipping-input">
693
					<input placeholder="L" type="text" id="wpsc-product-shipping-length" name="<?php echo esc_attr( $field_name_prefix ); ?>[dimensions][length]" value="<?php if ( !$bulk && $dimensions['length']>0 ) echo esc_attr( wpsc_format_number( $dimensions['length'] ) ); ?>" />&nbsp;&times;&nbsp;
694
					<input placeholder="W" type="text" id="wpsc-product-shipping-width" name="<?php echo esc_attr( $field_name_prefix ); ?>[dimensions][width]" value="<?php if ( !$bulk && $dimensions['width']>0 ) echo esc_attr( wpsc_format_number( $dimensions['width'] ) ); ?>" />&nbsp;&times;&nbsp;
695
					<input placeholder="H" type="text" id="wpsc-product-shipping-height" name="<?php echo esc_attr( $field_name_prefix ); ?>[dimensions][height]" value="<?php if ( !$bulk && $dimensions['height']>0 ) echo esc_attr( wpsc_format_number( $dimensions['height'] ) ); ?>" />
696
					<select id="wpsc-product-shipping-dimensions-unit" name="<?php echo $field_name_prefix; ?>[dimension_unit]">
697
						<?php foreach ( $dimension_units as $unit => $unit_label ): ?>
698
							<option value="<?php echo esc_attr( $unit ); ?>" <?php if ( ! $bulk && isset( $meta['dimension_unit'] ) ) selected( $unit, $meta['dimension_unit'] ); // Dirty code ?>><?php echo esc_html( $unit_label ); ?></option>
699
						<?php endforeach; ?>
700
					</select>
701
				</span>
702
			</p>
703
			<!-- END DEMENSION INPUT -->
704
705
		</div>
706
707
		<?php
708
			$currency_type = get_option( 'currency_type' );
709
			$country = new WPSC_Country( $currency_type );
710
711
			$ct_symb = $country->get_currency_symbol_html();
712
		?>
713
714
		<div class="wpsc-product-shipping-section wpsc-product-shipping-flat-rate">
715
			<p><strong><?php esc_html_e( 'Flat Rate Settings', 'wp-e-commerce' ); ?></strong></p>
716
			<p class="wpsc-form-field">
717
				<?php if ( $bulk ): ?>
718
					<input class="wpsc-bulk-edit-fields" type="checkbox" name="wpsc_bulk_edit[fields][shipping][local]" value="1" />
719
				<?php endif; ?>
720
				<label for="wpsc-product-shipping-flatrate-local"><?php esc_html_e( 'Local Shipping Fee', 'wp-e-commerce' ); ?></label>
721
				<span>
722
					<?php echo esc_html( $ct_symb ); ?>
723
					<input type="text" id="wpsc-product-shipping-flatrate-local" name="<?php echo esc_html( $field_name_prefix ); ?>[shipping][local]" value="<?php if ( ! $bulk ) echo $shipping['local']; ?>"  />
724
				</span>
725
			</p>
726
			<p class="wpsc-form-field">
727
				<?php if ( $bulk ): ?>
728
					<input class="wpsc-bulk-edit-fields" type="checkbox" name="wpsc_bulk_edit[fields][shipping][international]" value="1" />
729
				<?php endif; ?>
730
				<label for="wpsc-product-shipping-flatrate-international"><?php esc_html_e( 'International Shipping Fee', 'wp-e-commerce' ); ?></label>
731
				<span>
732
					<?php echo esc_html( $ct_symb ); ?>
733
					<input type="text" id="wpsc-product-shipping-flatrate-international" name="<?php echo esc_html( $field_name_prefix ); ?>[shipping][international]" value="<?php if ( ! $bulk ) echo $shipping['international']; ?>"  />
734
				</span>
735
			</p>
736
		</div>
737
	</div>
738
	<?php
739
740
	wp_nonce_field( 'update', 'wpsc_product_shipping_nonce' );
741
742
}
743
744
/**
745
 * Product Custom Metadata Form
746
 *
747
 * @global  $post  Instance of WP_Post.
748
 * @global  $wpdb  Instance of wpdb.
749
 */
750
function wpsc_product_advanced_forms() {
751
752
	global $post, $wpdb;
753
754
	$delete_nonce = _wpsc_create_ajax_nonce( 'remove_product_meta' );
755
756
	$custom_fields = $wpdb->get_results( "
757
		SELECT
758
			`meta_id`, `meta_key`, `meta_value`
759
		FROM
760
			`{$wpdb->postmeta}`
761
		WHERE
762
			`post_id` = {$post->ID}
763
		AND
764
			`meta_key` NOT LIKE '\_%'
765
		ORDER BY
766
			LOWER(meta_key)", ARRAY_A
767
	);
768
769
	$output = '<table id="wpsc_product_meta_table" class="wp-list-table widefat posts">';
770
		$output .= '<thead>';
771
			$output .= '<tr>';
772
				$output .= '<th id="wpsc_custom_meta_name_th">' . _x( 'Name', 'Product meta UI', 'wp-e-commerce' ) . '</th>';
773
				$output .= '<th id="wpsc_custom_meta_value_th">' . _x( 'Value', 'Product meta UI', 'wp-e-commerce' ) . '</th>';
774
				$output .= '<th id="wpsc_custom_meta_action_th">' . _x( 'Action', 'Product meta UI', 'wp-e-commerce' ) . '</th>';
775
			$output .= '</tr>';
776
		$output .= '</thead>';
777
		$output .= '<tfoot>';
778
			$output .= '<tr>';
779
				$output .= '<th>' . _x( 'Name', 'Product meta UI', 'wp-e-commerce' ) . '</th>';
780
				$output .= '<th>' . _x( 'Value', 'Product meta UI', 'wp-e-commerce' ) . '</th>';
781
				$output .= '<th>' . _x( 'Action', 'Product meta UI', 'wp-e-commerce' ) . '</th>';
782
			$output .= '</tr>';
783
		$output .= '</tfood>';
784
785
		$output .= '<tbody>';
786
787
		if ( empty( $custom_fields ) ) {
788
			$output .= '<tr class="no-meta"><td colspan="3"><p>' . sprintf( __( 'You have no custom metadata. You can set any arbitrary meta you like and access it programatically via the <a href="">Post Meta API</a>.', 'wp-e-commerce' ), esc_url( 'https://codex.wordpress.org/Function_Reference/get_post_meta' ) ) . '</p></td></tr>';
789
		} else {
790
			// Display all available metadata
791
			$alternate = false;
792
			foreach ( (array) $custom_fields as $custom_field ) {
793
				$i = $custom_field['meta_id'];
794
				$alternate = ! $alternate;
795
796
				$output .= '<tr'. ($alternate ? ' class="alternate"' : '') .'>';
797
					$output .= '<td><input type="text" value="'.esc_attr( $custom_field['meta_key'] ).'" name="custom_meta['.$i.'][name]" id="custom_meta_name_'.$i.'"></input></td>';
798
					$output .= '<td><input type="text" value="'.esc_attr( $custom_field['meta_value'] ).'" name="custom_meta['.$i.'][value]" id="custom_meta_value_'.$i.'"></input></td>';
799
					$output .= '<td><a href="#" data-nonce="'.esc_attr( $delete_nonce ).'" class="wpsc_remove_meta" onclick="wpsc_remove_custom_meta(this,'.$i.')">'.esc_html( 'Delete', 'wp-e-commerce' ).'</a></td>';
800
				$output .= '</tr>';
801
			}
802
		}
803
804
			// Template for new metadata input
805
			$output .= '<tr id="wpsc_new_meta_template">';
806
				$output .= '<td><input type="text" name="new_custom_meta[name][]"  value=""></input></td>';
807
				$output .= '<td><input type="text" name="new_custom_meta[value][]" value=""></input></td>';
808
				$output .= '<td><a href="#" class="wpsc_remove_meta" onclick="wpsc_remove_empty_meta(this)">'.esc_html( 'Delete', 'wp-e-commerce' ).'</a></td>';
809
			$output .= '</tr>';
810
811
		$output .= '</tbody>';
812
	$output .= '</table>';
813
814
	$output .= '<a href="#" class="add_more_meta  button button-small" id="wpsc_add_custom_meta">'.esc_html( '+ Add Custom Meta', 'wp-e-commerce' ).'</a>';
815
816
	echo $output;
817
818
}
819
820
/**
821
 * Display Product External Link Meta Box Form Fields.
822
 *
823
 * @global  $post  Instance of WP_Post.
824
 */
825
function wpsc_product_external_link_forms() {
826
827
	global $post;
828
829
	// Get External Link Values
830
	$product_meta = get_post_meta( $post->ID, '_wpsc_product_metadata', true );
831
	$product_meta = wp_parse_args( $product_meta, array(
832
		'external_link'        => '',
833
		'external_link_text'   => '',
834
		'external_link_target' => ''
835
	) );
836
837
	?>
838
	<table class="form-table" style="width: 100%;" cellspacing="2" cellpadding="5">
839
		<tbody>
840
			<tr class="form-field">
841
				<th valign="top" scope="row"><label for="external_link"><?php esc_html_e( 'URL', 'wp-e-commerce' ); ?></label></th>
842
				<td><input type="text" name="meta[_wpsc_product_metadata][external_link]" id="external_link" value="<?php echo esc_url( $product_meta['external_link'] ); ?>" size="50" style="width: 95%" placeholder="http://" /></td>
843
			</tr>
844
			<tr class="form-field">
845
				<th valign="top" scope="row"><label for="external_link_text"><?php esc_html_e( 'Label', 'wp-e-commerce' ); ?></label></th>
846
				<td><input type="text" name="meta[_wpsc_product_metadata][external_link_text]" id="external_link_text" value="<?php echo esc_attr( $product_meta['external_link_text'] ); ?>" size="50" style="width: 95%" placeholder="<?php _e( 'Buy Now', 'wp-e-commerce' ); ?>" /></td>
847
			</tr>
848
			<tr class="form-field">
849
				<th valign="top" scope="row"><label for="external_link_target"><?php esc_html_e( 'Target', 'wp-e-commerce' ); ?></label></th>
850
				<td id="external_link_target">
851
852
					<label>
853
						<input type="radio" name="meta[_wpsc_product_metadata][external_link_target]" value=""<?php checked( '', $product_meta['external_link_target'] ); ?> />
854
						<?php _ex( 'Default (set by theme)', 'External product link target', 'wp-e-commerce' ); ?>
855
					</label>
856
857
					<label>
858
						<input type="radio" name="meta[_wpsc_product_metadata][external_link_target]" value="_self"<?php checked( '_self', $product_meta['external_link_target'] ); ?> />
859
						<?php esc_html_e( 'Force open in same window', 'wp-e-commerce' ); ?>
860
					</label>
861
862
					<label>
863
						<input type="radio" name="meta[_wpsc_product_metadata][external_link_target]" value="_blank"<?php checked( '_blank', $product_meta['external_link_target'] ); ?> />
864
						<?php esc_html_e( 'Force open in new window', 'wp-e-commerce' ); ?>
865
					</label>
866
867
				</td>
868
			</tr>
869
		</tbody>
870
	</table>
871
	<em><?php esc_html_e( 'This option overrides the "Buy Now" and "Add to Cart" buttons, replacing them with the link you describe here.', 'wp-e-commerce' ); ?></em>
872
	<?php
873
874
	wp_nonce_field( 'update', 'wpsc_product_external_link_nonce' );
875
876
}
877
878
function wpsc_additional_desc() {
879
?>
880
	<textarea name='additional_description' id='additional_description' cols='40' rows='5' ><?php echo esc_textarea( get_post_field( 'post_excerpt', get_the_ID() ) ); ?></textarea>
881
	<em><?php _e( 'Short Descriptions are optional hand-crafted summaries of your content that can be used in your theme.', 'wp-e-commerce' ); ?></em>
882
<?php
883
884
}
885
886
/**
887
 * We really need to either bake this functionality in for 3.9.0 or rip it out into Gold Cart or something else.
888
 * So not awesome to have this exposed and unusable.
889
 *
890
 * @param  WP_Post $post Product
891
 * @return void
892
 */
893
function wpsc_product_gallery( $post ) {
894
	// pull the old iframe source for non JS users
895
	$upload_iframe_src = esc_url( get_upload_iframe_src( 'image', $post->ID ) );
896
	// get our gallery image IDs if present
897
	$images = wpsc_get_admin_product_gallery( $post->ID );
898
	// begin HTML output
899
	$output = '<div id="wpsc_product_gallery">';
900
		$output .= '<ul>';
901
		// check for images before beginngin loop
902
		if ( $images ) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $images of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
903
			// now loop images
904
			foreach ( $images as $image_id ) {
905
				// get the thumbnail URL
906
				$thumb_url  = wp_get_attachment_thumb_url( absint( $image_id ) );
907
				// output each item
908
				$output .= '<li><div class="list_gallery_image">';
909
						$output .= '<img src="' . esc_url( $thumb_url ) . '">';
910
						$output .= '<input type="hidden" name="wpsc-product-gallery-imgs[]" value="' . absint( $image_id ) . '">';
911
912
						$output .= '<span class="product_gallery_image_delete_button dashicons dashicons-no-alt"></span></div>';
913
						$output .= '<input type="hidden" class="product_gallery_image_id" value="'.$image_id.'">';
914
						$output .= '<input type="hidden" class="product_gallery_post_id" value="'.$post->ID.'">';
915
				$output .= '</li>';
916
			}
917
		}
918
		$output .= '</ul>';
919
		$output .= '<div class="clear"></div>';
920
	$output .= '</div>';
921
	$nonce_var = wp_create_nonce( 'wpsc_gallery_nonce' );
922
  ?>
923
  <input type="hidden" class="nonce_class" value="<?php echo $nonce_var; ?>">
924
  <?php
925
	// button for old iframe for non JS people
926
	$output .= '<p class="hide-if-no-js">';
927
		$output .= '<a class="button button-small thickbox" title="' . esc_attr__( 'Manage Product Image Gallery...', 'wp-e-commerce' ).'" href="' . $upload_iframe_src . '" id="wpsc-manage-product-gallery">';
928
			$output .= esc_html__( 'Manage Product Image Gallery...', 'wp-e-commerce' );
929
		$output .= '</a>';
930
	$output .= '</p>';
931
932
	// include a nonce for verification
933
	$output .= wp_nonce_field( 'wpec_product_gallery_nonce', 'wpec_product_gallery_nonce', false, false );
934
935
	// echo the gallery output
936
	echo $output;
937
}
938
939
940
function wpsc_product_download_forms() {
941
	global $post, $wpdb, $wpsc_product_defaults;
942
	$product_data = get_post_custom( $post->ID );
943
	$output = '';
944
	$product_data['meta'] = array();
945
946
	if ( !empty( $product_data['_wpsc_product_metadata'] ) )
947
		$product_data['meta'] = maybe_unserialize( $product_data['_wpsc_product_metadata'][0] );
948
949
	$upload_max = wpsc_get_max_upload_size();
950
?>
951
	<?php echo wpsc_select_product_file( $post->ID ); ?>
952
953
	<a href="admin.php?wpsc_admin_action=product_files_existing&amp;product_id=<?php echo absint( $post->ID ); ?>" class="thickbox button button-small" title="<?php echo esc_attr( sprintf( __( 'Select all downloadable files for %s', 'wp-e-commerce' ), $post->post_title ) ); ?>"><?php esc_html_e( 'Add existing files...', 'wp-e-commerce' ); ?></a>
954
955
	<div class="wpsc_fileUpload button button-small">
956
		<span><?php esc_html_e('Upload new file...','wp-e-commerce'); ?></span>
957
		<input type='file' name='file' class="button button-small" value='' onchange="wpsc_push_v2t(this, '#wpsc_fileupload_path')" />
958
	</div>
959
	<em id="wpsc_fileupload_path"></em>
960
961
<?php
962
	if ( function_exists( "make_mp3_preview" ) || function_exists( "wpsc_media_player" ) ) {
963
?>
964
			<br />
965
			<h4><?php esc_html_e( 'Select an MP3 file to upload as a preview', 'wp-e-commerce' ) ?></h4>
966
			<input type='file' name='preview_file' value='' /><br />
967
968
			<h4><?php esc_html_e( 'Your preview for this product', 'wp-e-commerce' ) ?>:</h4>
969
970
			 <?php
971
				$args = array(
972
					'post_type'   => 'wpsc-preview-file',
973
					'post_parent' => $post->ID,
974
					'numberposts' => -1,
0 ignored issues
show
introduced by
Disabling pagination is prohibited in VIP context, do not set numberposts to -1 ever.
Loading history...
975
					'post_status' => 'all'
976
				);
977
978
			$preview_files = (array) get_posts( $args );
979
980
			foreach ( $preview_files as $preview ) {
981
				echo $preview->post_title . '<br />';
982
			}
983
984
			?>
985
			<br />
986
		<?php
987
	}
988
989
	$output = apply_filters( 'wpsc_downloads_metabox', $output );
990
}
991
992
/**
993
 * Product Personalization Form
994
 *
995
 * @global  $post  Instance of WP_Post.
996
 */
997
function wpsc_product_personalization_forms() {
998
999
	global $post;
1000
1001
	$product_meta = get_post_meta( $post->ID, '_wpsc_product_metadata', true );
1002
	$product_meta = wp_parse_args( $product_meta, array(
1003
		'engraved'                => 0,
1004
		'can_have_uploaded_image' => 0
1005
	) );
1006
1007
	?>
1008
	<ul id="wpsc_product_personalization_option">
1009
		<li>
1010
			<input type="checkbox" name="meta[_wpsc_product_metadata][engraved]" <?php checked( $product_meta['engraved'], '1' ); ?> id="add_engrave_text" />
1011
			<label for="add_engrave_text"><?php esc_html_e( 'Users can personalize this product by leaving a message on single product page', 'wp-e-commerce' ); ?></label>
1012
		</li>
1013
		<li>
1014
			<input type="checkbox" name="meta[_wpsc_product_metadata][can_have_uploaded_image]" <?php checked( $product_meta['can_have_uploaded_image'], '1' ); ?> id="can_have_uploaded_image" />
1015
			<label for="can_have_uploaded_image"> <?php esc_html_e( 'Users can upload images on single product page to purchase logs.', 'wp-e-commerce' ); ?></label>
1016
		</li>
1017
		<?php do_action( 'wpsc_add_advanced_options', $post->ID ); ?>
1018
	</ul>
1019
	<em><?php _e( "Form fields for the customer to personalize this product will be shown on it's single product page.", 'wp-e-commerce' ); ?></em>
1020
	<?php
1021
1022
	wp_nonce_field( 'update', 'wpsc_product_personalization_nonce' );
1023
1024
}
1025
1026
function wpsc_product_delivery_forms(){
1027
	$has_variations    = wpsc_product_has_variations( get_post()->ID );
1028
1029
	$show_if_variation = $has_variations ? 'display: block;' : 'display:none;';
1030
?>
1031
	<em id="wpsc_product_delivery_metabox_live_title" class="wpsc_metabox_live_title">
1032
		<p></p>
1033
	</em>
1034
1035
	<div id="wpsc_product_delivery_forms" class="categorydiv wpsc-categorydiv">
1036
		<ul id="wpsc_product_delivery_tabs" class="category-tabs">
1037
			<li class="tabs"><a href="#wpsc_product_delivery-shipping"><?php _e( 'Shipping', 'wp-e-commerce' ); ?></a></li>
1038
			<li><a href="#wpsc_product_delivery-download"><?php _e( 'Download', 'wp-e-commerce' ); ?></a></li>
1039
			<li><a href="#wpsc_product_delivery-external_link"><?php _e( 'External Link', 'wp-e-commerce' ); ?></a></li>
1040
		</ul>
1041
1042
		<div id="wpsc_product_delivery-shipping" class="tabs-panel" style="display:block;">
1043
			<?php
1044
				if ( ! $has_variations ) {
1045
					wpsc_product_shipping_forms();
1046
				} else {
1047
					echo '<p>' . sprintf( __( 'This product has variations. To edit the shipping, please use the <a href="%s">Variation Controls</a>.', 'wp-e-commerce'  ), '#wpsc_product_variation_forms' ) . '</p>';
1048
				}
1049
			?>
1050
		</div>
1051
1052
		<div id="wpsc_product_delivery-download" class="tabs-panel" style="display:none;">
1053
			<?php wpsc_product_download_forms(); ?>
1054
		</div>
1055
1056
		<div id="wpsc_product_delivery-external_link" class="tabs-panel" style="display: none;">
1057
			<?php wpsc_product_external_link_forms(); ?>
1058
		</div>
1059
	</div>
1060
<?php
1061
}
1062
1063
function wpsc_product_details_forms(){
1064
?>
1065
	<em id="wpsc_product_details_metabox_live_title" class="wpsc_metabox_live_title">
1066
		<p></p>
1067
	</em>
1068
1069
	<div id="wpsc_product_details_forms" class="categorydiv wpsc-categorydiv">
1070
		<ul id="wpsc_product_details_tabs"  class="category-tabs">
1071
			<li class="tabs"><a href="#wpsc_product_details-image"><?php _e( 'Image Gallery', 'wp-e-commerce' ); ?></a></li>
1072
			<li><a href="#wpsc_product_details-desc"><?php _e( 'Short Description', 'wp-e-commerce' ); ?></a></li>
1073
			<li><a href="#wpsc_product_details-personalization"><?php _e( 'Personalization', 'wp-e-commerce' ); ?></a></li>
1074
			<li><a href="#wpsc_product_details-meta"><?php _e( 'Metadata', 'wp-e-commerce' ); ?></a></li>
1075
		</ul>
1076
1077
		<div id="wpsc_product_details-image" class="tabs-panel" style="display: block;">
1078
			<?php wpsc_product_gallery( get_post() ); ?>
1079
		</div>
1080
1081
		<div id="wpsc_product_details-desc" class="tabs-panel" style="display: none;">
1082
			<?php wpsc_additional_desc(); ?>
1083
		</div>
1084
1085
		<div id="wpsc_product_details-personalization" class="tabs-panel" style="display: none;">
1086
			<?php wpsc_product_personalization_forms(); ?>
1087
		</div>
1088
1089
		<div id="wpsc_product_details-meta" class="tabs-panel" style="display: none;">
1090
			<?php wpsc_product_advanced_forms(); ?>
1091
		</div>
1092
	</div>
1093
<?php
1094
}
1095
1096
function wpsc_form_multipart_encoding() {
1097
	echo ' enctype="multipart/form-data"';
1098
}
1099
1100
add_action( 'post_edit_form_tag', 'wpsc_form_multipart_encoding' );
1101
1102
/*
1103
* Modifications to Media Gallery
1104
*/
1105
1106
add_filter( 'attachment_fields_to_edit', 'wpsc_attachment_fields', 11, 2 );
1107
add_filter( 'attachment_fields_to_save', 'wpsc_save_attachment_fields', 9, 2 );
1108
add_filter( 'gettext_with_context', 'wpsc_filter_gettex_with_context', 12, 4);
1109
1110
/*
1111
 * This filter overrides string with context translations
1112
 *
1113
 * @param $translation The current translation
1114
 * @param $text The text being translated
1115
 * @param $context The domain for the translation
1116
 * @param $domain The domain for the translation
1117
 * @return string The translated / filtered text.
1118
 */
1119
function wpsc_filter_gettex_with_context( $translation, $text, $context, $domain ) {
1120
1121
	if ( 'Taxonomy Parent' == $context && 'Parent' == $text && isset($_GET['taxonomy']) && 'wpsc-variation' == $_GET['taxonomy'] ) {
1122
		$translations = get_translations_for_domain( $domain );
1123
		return $translations->translate( 'Variation Set', 'wp-e-commerce' );
1124
		//this will never happen, this is here only for gettext to pick up the translation
1125
		return __( 'Variation Set', 'wp-e-commerce' );
0 ignored issues
show
Unused Code introduced by
//this will never happen...Set', 'wp-e-commerce'); does not seem to be reachable.

This check looks for unreachable code. It uses sophisticated control flow analysis techniques to find statements which will never be executed.

Unreachable code is most often the result of return, die or exit statements that have been added for debug purposes.

function fx() {
    try {
        doSomething();
        return true;
    }
    catch (\Exception $e) {
        return false;
    }

    return false;
}

In the above example, the last return false will never be executed, because a return statement has already been met in every possible execution path.

Loading history...
1126
	}
1127
	return $translation;
1128
}
1129
1130
function wpsc_attachment_fields( $form_fields, $post ) {
1131
	$out = '';
1132
1133
	if( isset( $_REQUEST["post_id"] ) )
1134
		$parent_post = get_post( absint( $_REQUEST["post_id"] ) );
1135
	else
1136
		$parent_post = get_post( $post->post_parent );
1137
1138
	// check if post is set before accessing
1139
	if ( isset( $parent_post ) && $parent_post->post_type == "wpsc-product" ) {
1140
1141
		//Unfortunate hack, as I'm not sure why the From Computer tab doesn't process filters the same way the Gallery does
1142
		ob_start();
1143
		echo '
1144
<script type="text/javascript">
1145
1146
	jQuery(function(){
1147
1148
		jQuery("a.wp-post-thumbnail").each(function(){
1149
			var product_image = jQuery(this).text();
1150
			if (product_image == "' . esc_js( __( 'Use as featured image', 'wp-e-commerce' ) ) . '") {
1151
				jQuery(this).text("' . esc_js( __('Use as Product Thumbnail', 'wp-e-commerce' ) ) . '");
1152
			}
1153
		});
1154
1155
		var trash = jQuery("#media-upload a.del-link").text();
1156
1157
		if (trash == "' . esc_js( __( 'Delete', 'wp-e-commerce' ) ) . '") {
1158
			jQuery("#media-upload a.del-link").text("' . esc_js( __( 'Trash', 'wp-e-commerce' ) ) . '");
1159
		}
1160
1161
1162
		});
1163
1164
</script>';
1165
		$out .= ob_get_clean();
1166
1167
		$size_names = array( 'small-product-thumbnail' => __( 'Default Product Thumbnail Size', 'wp-e-commerce' ), 'medium-single-product' => __( 'Single Product Image Size', 'wp-e-commerce' ), 'full' => __( 'Full Size', 'wp-e-commerce' ) );
1168
1169
		$check = get_post_meta( $post->ID, '_wpsc_selected_image_size', true );
1170
		if ( !$check )
1171
			$check = 'medium-single-product';
1172
1173
		$current_size = image_get_intermediate_size( $post->ID, $check );
1174
		$settings_width = get_option( 'single_view_image_width' );
1175
		$settings_height = get_option( 'single_view_image_height' );
1176
1177
		// regenerate size metadata in case it's missing
1178
		if ( ! $check || ( $current_size['width'] != $settings_width && $current_size['height'] != $settings_height ) ) {
1179
			_wpsc_regenerate_thumbnail_size( $post->ID, $check );
1180
		}
1181
1182
		//This loop attaches the custom thumbnail/single image sizes to this page
1183
		foreach ( $size_names as $size => $name ) {
1184
			$downsize = image_downsize( $post->ID, $size );
1185
			// is this size selectable?
1186
			$enabled = ( $downsize[3] || 'full' == $size );
1187
			$css_id = "image-size-{$size}-{$post->ID}";
1188
			// if this size is the default but that's not available, don't select it
1189
1190
			$html = "<div class='image-size-item'><input type='radio' " . disabled( $enabled, false, false ) . "name='attachments[$post->ID][wpsc_image_size]' id='{$css_id}' value='{$size}' " . checked( $size, $check, false ) . " />";
1191
1192
			$html .= "<label for='{$css_id}'>$name</label>";
1193
			// only show the dimensions if that choice is available
1194
			if ( $enabled )
1195
				$html .= " <label for='{$css_id}' class='help'>" . sprintf( __( "(%d&nbsp;&times;&nbsp;%d)", 'wp-e-commerce' ), $downsize[1], $downsize[2] ). "</label>";
1196
1197
			$html .= '</div>';
1198
1199
			$out .= $html;
1200
		}
1201
1202
		unset( $form_fields['post_excerpt'], $form_fields['image_url'], $form_fields['post_content'], $form_fields['post_title'], $form_fields['url'], $form_fields['align'], $form_fields['image_alt']['helps'], $form_fields["image-size"] );
1203
		$form_fields['image_alt']['helps'] =  __( 'Alt text for the product image, e.g. &#8220;Rockstar T-Shirt&#8221;', 'wp-e-commerce' );
0 ignored issues
show
introduced by
Expected 1 space after "="; 2 found
Loading history...
1204
1205
		$form_fields["wpsc_image_size"] = array(
1206
			'label' => __( 'Single Product Page Thumbnail:', 'wp-e-commerce' ),
1207
			'input' => 'html',
1208
			'html'  => $out,
1209
			'helps' => "<span style='text-align:left; clear:both; display:block; padding-top:3px;'>" . __( 'This is the Thumbnail size that will be displayed on the Single Product page. You can change the default sizes under your store settings', 'wp-e-commerce' ) . "</span>"
1210
		);
1211
1212
		//This is for the custom thumbnail size.
1213
1214
		$custom_thumb_size_w = get_post_meta( $post->ID, "_wpsc_custom_thumb_w", true );
1215
		$custom_thumb_size_h = get_post_meta( $post->ID, "_wpsc_custom_thumb_h", true );
1216
		$custom_thumb_html = "
1217
1218
			<input style='width:50px; text-align:center' type='text' name='attachments[{$post->ID}][wpsc_custom_thumb_w]' value='{$custom_thumb_size_w}' /> X <input style='width:50px; text-align:center' type='text' name='attachments[{$post->ID}][wpsc_custom_thumb_h]' value='{$custom_thumb_size_h}' />
1219
1220
		";
1221
		$form_fields["wpsc_custom_thumb"] = array(
1222
			"label" => __( 'Products Page Thumbnail Size:', 'wp-e-commerce' ),
1223
			"input" => "html", // this is default if "input" is omitted
1224
			"helps" => "<span style='text-align:left; clear:both; display:block; padding-top:3px;'>" . __( 'Custom thumbnail size for this image on the main Product Page', 'wp-e-commerce') . "</span>",
1225
			"html" => $custom_thumb_html
1226
		);
1227
	}
1228
	return $form_fields;
1229
1230
}
1231
function wpsc_save_attachment_fields( $post, $attachment ) {
1232
1233
	if ( isset( $attachment['wpsc_custom_thumb_w'] ) ) {
1234
		update_post_meta( $post['ID'], '_wpsc_custom_thumb_w', $attachment['wpsc_custom_thumb_w'] );
1235
	}
1236
1237
	if ( isset( $attachment['wpsc_custom_thumb_h'] ) ) {
1238
		update_post_meta( $post['ID'], '_wpsc_custom_thumb_h', $attachment['wpsc_custom_thumb_h'] );
1239
	}
1240
1241
	if ( isset( $attachment['wpsc_image_size'] ) ) {
1242
		update_post_meta( $post['ID'], '_wpsc_selected_image_size', $attachment['wpsc_image_size'] );
1243
	}
1244
1245
	return $post;
1246
}
1247
1248
/**
1249
 * Save Product Quick Edit Box
1250
 *
1251
 * Saves input for the various meta in the quick edit boxes.
1252
 *
1253
 * @todo  UI.
1254
 * @todo  Data validation / sanitization / security.
1255
 * @todo  AJAX should probably return weight unit.
1256
 *
1257
 * @return  int  $post_id  Post ID.
1258
 */
1259
function wpsc_save_quickedit_box( $post_id ) {
1260
1261
	global $doaction;
1262
1263
	// Only save product if saving (not autosaving) via AJAX.
1264
	if ( ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) || ! defined( 'DOING_AJAX' ) || ! DOING_AJAX || get_post_type( $post_id ) != 'wpsc-product' ) {
1265
		return;
1266
	}
1267
1268
	$bulk = isset( $doaction ) && $doaction == 'edit';
1269
1270
	// Map post field to meta key.
1271
	$custom_fields = array(
1272
		'weight'     => 'product_metadata',
1273
		'stock'      => 'stock',
1274
		'price'      => 'price',
1275
		'sale_price' => 'special_price',
1276
		'sku'        => 'sku'
1277
	);
1278
1279
	// Get product variations (if any).
1280
	$children = get_children( array(
1281
		'post_parent' => $post_id,
1282
		'post_type'   => 'wpsc-product',
1283
		'post_status' => 'inherit'
1284
	) );
1285
	$is_parent = (bool) $children;
1286
1287
	foreach ( $custom_fields as $post_key => $meta_key ) {
1288
1289
		// Don't update if field is not set or we're bulk updating and the field is left blank.
1290
		if ( ! isset( $_REQUEST[ $post_key ] ) || ( $bulk && empty( $_REQUEST[ $post_key ] ) ) ) {
1291
			continue;
1292
		}
1293
1294
		// Don't update if the product has variations and the field is one of the defined custom fields (unless overridden).
1295
		$override_variant = isset( $_REQUEST[ $post_key . '_variant' ] ) && $_REQUEST[ $post_key . '_variant' ] == 'on';
1296
		if ( $is_parent && ! $override_variant && in_array( $post_key, array_keys( $custom_fields ) ) ) {
1297
			continue;
1298
		}
1299
1300
		// Select single product or variation IDs.
1301
		if ( $is_parent && count( $children ) > 0 ) {
1302
			$products = wp_list_pluck( $children, 'ID' );
1303
		} else {
1304
			$products = array( $post_id );
1305
		}
1306
1307
		foreach ( $products as $post_id ) {
1308
			$value = $_REQUEST[ $post_key ];
1309
1310
			// Validate custom field values
1311
			switch ( $post_key ) {
1312
1313
				case 'weight':
1314
					$product_meta = get_post_meta( $post_id, '_wpsc_product_metadata', true );
1315
					if ( ! is_array( $product_meta ) ) {
1316
						$product_meta = array();
1317
					}
1318
1319
					// Draft products don't have product metadata set yet
1320
					$weight_unit = isset( $product_meta['weight_unit'] ) ? $product_meta['weight_unit'] : 'pound';
1321
					$weight = wpsc_convert_weight( $value, $weight_unit, 'pound', true );
1322
1323
					if ( isset( $product_meta['weight'] ) ) {
1324
						unset( $product_meta['weight'] );
1325
					}
1326
1327
					$product_meta['weight'] = $weight;
1328
1329
					$value = $product_meta;
1330
					break;
1331
1332
				case 'stock':
1333
					if ( ! is_numeric( $value ) ) {
1334
						$value = '';
1335
					}
1336
					break;
1337
1338
				case 'sku':
1339
					if ( $value == __( 'N/A', 'wp-e-commerce' ) ) {
1340
						$value = '';
1341
					} else {
1342
						$value = sanitize_text_field( $value );
1343
					}
1344
					break;
1345
				default :
1346
					$value = sanitize_text_field( $value );
1347
1348
			}
1349
1350
			update_post_meta( $post_id, "_wpsc_{$meta_key}", $value );
1351
		}
1352
	}
1353
1354
	return $post_id;
1355
1356
}
1357
1358
/**
1359
 * wpsc_quick_edit_boxes function
1360
 * Creates inputs for the various meta in the quick edit boxes.
1361
 *
1362
 * @todo UI
1363
 * @internal The post_id cannot be accessed here because this gets output at the very end
1364
 *           of the editor form, and injected within relevant rows using javascript.
1365
 */
1366
1367
function wpsc_quick_edit_boxes( $col_name, $_screen_post_type = null ) {
1368
	// Avoid outputting this on term edit screens.
1369
	// See http://core.trac.wordpress.org/ticket/16392#comment:9
1370
	if ( current_filter() == 'quick_edit_custom_box' && $_screen_post_type == 'edit-tags' )
1371
		return;
1372
?>
1373
1374
<fieldset class="inline-edit-col-left wpsc-cols">
1375
	<div class="inline-edit-col">
1376
		<div class="inline-edit-group">
1377
<?php
1378
	switch ( $col_name ) :
1379
	case 'SKU' :
1380
?>
1381
			<label style="max-width: 85%" class="alignleft">
1382
				<span class="checkbox-title wpsc-quick-edit"><?php esc_html_e( 'SKU:', 'wp-e-commerce' ); ?> </span>
1383
				<input type="text" name="sku" class="wpsc_ie_sku" />
1384
				<input type="checkbox" name="sku_variant"> <span><?php esc_html_e( 'Update Variants', 'wp-e-commerce');?></span>
1385
1386
			</label>
1387
			<?php
1388
	break;
1389
case 'weight' :
1390
?>
1391
			<label style="max-width: 85%" class="alignleft">
1392
				<span class="checkbox-title wpsc-quick-edit"><?php esc_html_e( 'Weight:', 'wp-e-commerce' ); ?> </span>
1393
				<input type="text" name="weight" class="wpsc_ie_weight" />
1394
				<input type="checkbox" name="weight_variant"> <span><?php esc_html_e( 'Update Variants', 'wp-e-commerce');?></span>
1395
			</label>
1396
			<?php
1397
	break;
1398
case 'stock' :
1399
?>
1400
			<label style="max-width: 85%" class="alignleft">
1401
				<span class="checkbox-title wpsc-quick-edit"><?php esc_html_e( 'Stock:', 'wp-e-commerce' ); ?> </span>
1402
				<input type="text" name="stock" class="wpsc_ie_stock" />
1403
				<input type="checkbox" name="stock_variant"> <span><?php esc_html_e( 'Update Variants', 'wp-e-commerce');?></span>
1404
			</label>
1405
			<?php
1406
	break;
1407
case 'price' :
1408
?>
1409
			<label style="max-width: 85%" class="alignleft">
1410
				<span class="checkbox-title wpsc-quick-edit"><?php esc_html_e( 'Price:', 'wp-e-commerce' ); ?> </span>
1411
				<input type="text" name="price" class="wpsc_ie_price" />
1412
				<input type="checkbox" name="price_variant"> <span><?php esc_html_e( 'Update Variants', 'wp-e-commerce');?></span>
1413
			</label>
1414
			<?php
1415
	break;
1416
case 'sale_price' :
1417
?>
1418
			<label style="max-width: 85%" class="alignleft">
1419
				<span class="checkbox-title wpsc-quick-edit"><?php esc_html_e( 'Sale Price:', 'wp-e-commerce' ); ?> </span>
1420
				<input type="text" name="sale_price" class="wpsc_ie_sale_price" />
1421
				<input type="checkbox" name="sale_price_variant"> <span><?php esc_html_e( 'Update Variants', 'wp-e-commerce');?></span>
1422
			</label>
1423
			<?php
1424
	break;
1425
	endswitch;
1426
?>
1427
		 </div>
1428
	</div>
1429
</fieldset>
1430
<?php
1431
}
1432
1433
add_action( 'quick_edit_custom_box', 'wpsc_quick_edit_boxes', 10, 2 );
1434
add_action( 'bulk_edit_custom_box', 'wpsc_quick_edit_boxes', 10, 2 );
1435
add_action( 'save_post', 'wpsc_save_quickedit_box' );
1436
1437
/**
1438
 * If it doesn't exist, let's create a multi-dimensional associative array
1439
 * that will contain all of the term/price associations
1440
 *
1441
 * @param <type> $variation
0 ignored issues
show
Documentation introduced by
The doc-type <type> could not be parsed: Unknown type name "<" at position 0. (view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
1442
 */
1443
function variation_price_field( $variation ) {
1444
	$term_prices = get_option( 'term_prices' );
1445
1446
	if ( is_object( $variation ) )
1447
		$term_id = $variation->term_id;
1448
1449
	if ( empty( $term_prices ) || !is_array( $term_prices ) ) {
1450
1451
		$term_prices = array( );
0 ignored issues
show
introduced by
Empty array declaration must have no space between the parentheses
Loading history...
1452
		if ( isset( $term_id ) ) {
1453
			$term_prices[$term_id] = array( );
0 ignored issues
show
introduced by
Empty array declaration must have no space between the parentheses
Loading history...
1454
			$term_prices[$term_id]["price"] = '';
1455
			$term_prices[$term_id]["checked"] = '';
1456
		}
1457
		add_option( 'term_prices', $term_prices );
1458
	}
1459
1460
	if ( isset( $term_id ) && is_array( $term_prices ) && array_key_exists( $term_id, $term_prices ) )
1461
		$price = esc_attr( $term_prices[$term_id]["price"] );
1462
	else
1463
		$price = '';
1464
1465
	if( !isset( $_GET['action'] ) ) {
1466
	?>
1467
	<div class="form-field">
1468
		<label for="variation_price"><?php esc_html_e( 'Variation Price', 'wp-e-commerce' ); ?></label>
1469
		<input type="text" name="variation_price" id="variation_price" style="width:50px;" value="<?php echo $price; ?>"><br />
1470
		<span class="description"><?php esc_html_e( 'You can list a default price here for this variation.  You can list a regular price (18.99), differential price (+1.99 / -2) or even a percentage-based price (+50% / -25%).', 'wp-e-commerce' ); ?></span>
1471
	</div>
1472
	<script type="text/javascript">
1473
		jQuery('#parent option:contains("   ")').remove();
1474
		jQuery('#parent').mousedown(function(){
1475
			jQuery('#parent option:contains("   ")').remove();
1476
		});
1477
	</script>
1478
	<?php
1479
	} else{
1480
	?>
1481
	<tr class="form-field">
1482
			<th scope="row" valign="top">
1483
		<label for="variation_price"><?php esc_html_e( 'Variation Price', 'wp-e-commerce' ); ?></label>
1484
			</th>
1485
			<td>
1486
		<input type="text" name="variation_price" id="variation_price" style="width:50px;" value="<?php echo $price; ?>"><br />
1487
		<span class="description"><?php esc_html_e( 'You can list a default price here for this variation.  You can list a regular price (18.99), differential price (+1.99 / -2) or even a percentage-based price (+50% / -25%).', 'wp-e-commerce' ); ?></span>
1488
			</td>
1489
	</tr>
1490
	<?php
1491
	}
1492
}
1493
add_action( 'wpsc-variation_edit_form_fields', 'variation_price_field' );
1494
add_action( 'wpsc-variation_add_form_fields', 'variation_price_field' );
1495
1496
/*
1497
WordPress doesnt let you change the custom post type taxonomy form very easily
1498
Use Jquery to move the set variation (parent) field to the top and add a description
1499
*/
1500
function variation_set_field(){
1501
?>
1502
	<script>
1503
		/* change the text on the variation set from (none) to new variation set*/
1504
		jQuery("#parent option[value='-1']").text("New Variation Set");
1505
		/* Move to the top of the form and add a description */
1506
		jQuery("#tag-name").parent().before( jQuery("#parent").parent().append('<p>Choose the Variation Set you want to add variants to. If your\'e creating a new variation set then select "New Variation Set"</p>') );
1507
		/*
1508
		create a small description about variations below the add variation / set title
1509
		we can then get rid of the big red danger warning
1510
		*/
1511
		( jQuery("div#ajax-response").after('<p>Variations allow you to create options for your products, for example if you\'re selling T-Shirts they will have a size option you can create this as a variation. Size will be the Variation Set name, and it will be a "New Variant Set". You will then create variants (small, medium, large) which will have the "Variation Set" of Size. Once you have made your set you can use the table on the right to manage them (edit, delete). You will be able to order your variants by draging and droping them within their Variation Set.</p>') );
1512
	</script>
1513
<?php
1514
}
1515
add_action( 'wpsc-variation_edit_form_fields', 'variation_set_field' );
1516
add_action( 'wpsc-variation_add_form_fields', 'variation_set_field' );
1517
1518
1519
function category_edit_form(){
1520
?>
1521
	<script type="text/javascript">
1522
1523
	</script>
1524
<?php
1525
}
1526
1527
function variation_price_field_check( $variation ) {
1528
1529
	$term_prices = get_option( 'term_prices' );
1530
1531
	if ( is_array( $term_prices ) && array_key_exists( $variation->term_id, $term_prices ) )
1532
		$checked = ($term_prices[$variation->term_id]["checked"] == 'checked') ? 'checked' : '';
1533
	else
1534
		$checked = ''; ?>
1535
1536
	<tr class="form-field">
1537
		<th scope="row" valign="top"><label for="apply_to_current"><?php esc_html_e( 'Apply to current variations?', 'wp-e-commerce' ) ?></label></th>
1538
		<td>
1539
			<span class="description"><input type="checkbox" name="apply_to_current" id="apply_to_current" style="width:2%;" <?php echo $checked; ?> /><?php _e( 'By checking this box, the price rule you implement above will be applied to all variations that currently exist.  If you leave it unchecked, it will only apply to products that use this variation created or edited from now on.  Take note, this will apply this rule to <strong>every</strong> product using this variation.  If you need to override it for any reason on a specific product, simply go to that product and change the price.', 'wp-e-commerce' ); ?></span>
1540
		</td>
1541
	</tr>
1542
<?php
1543
}
1544
add_action( 'wpsc-variation_edit_form_fields', 'variation_price_field_check' );
1545
1546
1547
1548
/**
1549
 * @todo - Should probably refactor this at some point - very procedural,
1550
 *         WAY too many foreach loops for my liking :)  But it does the trick
1551
 *
1552
 * @param <type> $term_id
0 ignored issues
show
Documentation introduced by
The doc-type <type> could not be parsed: Unknown type name "<" at position 0. (view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
1553
 */
1554
function save_term_prices( $term_id ) {
1555
	// First - Saves options from input
1556
	if ( isset( $_POST['variation_price'] ) || isset( $_POST["apply_to_current"] ) ) {
1557
1558
		$term_prices = get_option( 'term_prices' );
1559
1560
		$term_prices[$term_id]["price"] = sanitize_text_field( $_POST["variation_price"] );
1561
		$term_prices[$term_id]["checked"] = (isset( $_POST["apply_to_current"] )) ? "checked" : "unchecked";
1562
1563
		update_option( 'term_prices', $term_prices );
1564
	}
1565
1566
	// Second - If box was checked, let's then check whether or not it was flat, differential, or percentile, then let's apply the pricing to every product appropriately
1567
	if ( isset( $_POST["apply_to_current"] ) ) {
1568
1569
		//Now, find all products with this term_id, update their pricing structure (terms returned include only parents at this point, we'll grab relevent children soon)
1570
		$products_to_mod = get_objects_in_term( $term_id, "wpsc-variation" );
1571
		$product_parents = array( );
0 ignored issues
show
introduced by
Empty array declaration must have no space between the parentheses
Loading history...
1572
1573
		foreach ( (array)$products_to_mod as $get_parent ) {
1574
1575
			$post = get_post( $get_parent );
0 ignored issues
show
introduced by
Overridding WordPress globals is prohibited
Loading history...
1576
1577
			if ( !$post->post_parent )
1578
				$product_parents[] = $post->ID;
1579
		}
1580
1581
		//Now that we have all parent IDs with this term, we can get the children (only the ones that are also in $products_to_mod, we don't want to apply pricing to ALL kids)
1582
1583
		foreach ( $product_parents as $parent ) {
1584
			$args = array(
1585
				'post_parent' => $parent,
1586
				'post_type' => 'wpsc-product'
1587
			);
1588
			$children = get_children( $args, ARRAY_A );
1589
1590
			foreach ( $children as $childrens ) {
1591
				$parent = $childrens["post_parent"];
1592
				$children_ids[$parent][] = $childrens["ID"];
0 ignored issues
show
Coding Style Comprehensibility introduced by
$children_ids was never initialized. Although not strictly required by PHP, it is generally a good practice to add $children_ids = array(); before regardless.

Adding an explicit array definition is generally preferable to implicit array definition as it guarantees a stable state of the code.

Let’s take a look at an example:

foreach ($collection as $item) {
    $myArray['foo'] = $item->getFoo();

    if ($item->hasBar()) {
        $myArray['bar'] = $item->getBar();
    }

    // do something with $myArray
}

As you can see in this example, the array $myArray is initialized the first time when the foreach loop is entered. You can also see that the value of the bar key is only written conditionally; thus, its value might result from a previous iteration.

This might or might not be intended. To make your intention clear, your code more readible and to avoid accidental bugs, we recommend to add an explicit initialization $myArray = array() either outside or inside the foreach loop.

Loading history...
1593
				$children_ids[$parent] = array_intersect( $children_ids[$parent], $products_to_mod );
1594
			}
1595
		}
1596
1597
		//Got the right kids, let's grab their parent pricing and modify their pricing based on var_price_type
1598
1599
		foreach ( (array)$children_ids as $parents => $kids ) {
0 ignored issues
show
Bug introduced by
The variable $children_ids does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
1600
1601
			$kids = array_values( $kids );
1602
1603
			foreach ( $kids as $kiddos ) {
1604
				$price = wpsc_determine_variation_price( $kiddos );
1605
				update_product_meta( $kiddos, 'price', $price );
1606
			}
1607
		}
1608
	}
1609
}
1610
add_action( 'edited_wpsc-variation', 'save_term_prices' );
1611
add_action( 'created_wpsc-variation', 'save_term_prices' );
1612
1613
function wpsc_delete_variations( $postid ) {
1614
	$post = get_post( $postid );
0 ignored issues
show
introduced by
Overridding WordPress globals is prohibited
Loading history...
1615
	if ( $post->post_type != 'wpsc-product' || $post->post_parent != 0 )
1616
		return;
1617
	$variations = get_posts( array(
1618
		'post_type' => 'wpsc-product',
1619
		'post_parent' => $postid,
1620
		'post_status' => 'any',
1621
		'numberposts' => -1,
0 ignored issues
show
introduced by
Disabling pagination is prohibited in VIP context, do not set numberposts to -1 ever.
Loading history...
1622
	) );
1623
1624
	if ( ! empty( $variations ) )
1625
		foreach ( $variations as $variation ) {
1626
			wp_delete_post( $variation->ID, true );
1627
		}
1628
}
1629
add_action( 'before_delete_post', 'wpsc_delete_variations' );
1630
1631
1632
/**
1633
 * fetch the items for display inside the admin product gallery
1634
 * differs from the original `wpsc_get_product_gallery` in that
1635
 * it only checks the postmeta for an actual gallery generated by
1636
 * the user instead of pulling all attachments
1637
 *
1638
 * @since   3.8.14.2
1639
 *
1640
 * @param   integer     $product_id         the product ID of the product
1641
 * @return  array       $gallery            the attachment IDs of the gallery if present
1642
 */
1643
function wpsc_get_admin_product_gallery( $product_id = 0 ) {
1644
1645
	// grab our meta from the DB
1646
	$gallery = get_post_meta( $product_id, '_wpsc_product_gallery', true );
1647
1648
	// no custom gallery was created, so return nothing
1649
	if ( ! $gallery ) {
1650
		return;
1651
	}
1652
1653
	// now make sure the IDs present are actual attachments
1654
	// by looping and unsetting them
1655
	//
1656
	// may want to add a MIME type check here, but not sure
1657
	// if that would cause issues if people use non-images
1658
	// in their galleries
1659
	foreach( $gallery as $key => $image_id ) {
1660
		if ( get_post_type( $image_id ) !== 'attachment' ) {
1661
			unset( $gallery[ $key ] );
1662
		}
1663
	}
1664
1665
	// somehow everything in the gallery
1666
	// was not an attachment, so bail
1667
	if ( empty( $gallery ) ) {
1668
		return;
1669
	}
1670
1671
	// send it back
1672
	return $gallery;
1673
1674
}
1675
1676
/**
1677
 * save our gallery IDs on post save
1678
 *
1679
 * @since   3.8.14.2
1680
 * @param   integer     $product_id     the post ID being passed
1681
 * @return  void
1682
 */
1683
function wpsc_new_gallery_save( $product_id = 0 ) {
1684
1685
	// do our nonce check. ALWAYS A NONCE CHECK
1686
	if ( ! isset( $_POST['wpsc_product_gallery_nonce'] ) || ! wp_verify_nonce( $_POST['wpsc_product_gallery_nonce'], 'wpsc_product_gallery_nonce' ) ) {
1687
		return $product_id;
1688
	}
1689
1690
	// set an empty array for the image IDs
1691
	$image_ids  = array();
1692
1693
	// ok. we have image IDs to work with. do some filtering
1694
	if ( ! empty( $_POST['wpsc-product-gallery-imgs'] ) ) {
1695
		// make sure our IDs are set to an array
1696
		$image_ids  = (array) $_POST['wpsc-product-gallery-imgs'];
1697
		// ensure nothing non-numeric got added in
1698
		$image_ids  = wp_parse_id_list( $image_ids );
1699
		// filter out any empty items
1700
		$image_ids  = array_filter( $image_ids );
1701
	}
1702
1703
	// now if we have image IDs left after filtering, save them
1704
	// if not, delete the meta key
1705
	if ( ! empty( $image_ids ) ) {
1706
		update_post_meta( $product_id, '_wpsc_product_gallery', $image_ids );
1707
	} else {
1708
		delete_post_meta( $product_id, '_wpsc_product_gallery' );
1709
	}
1710
1711
	// add an action for after the gallery being saved
1712
	// passing the post ID and the image IDs
1713
	do_action( 'wpsc_after_gallery_save', $product_id, $image_ids );
1714
1715
}
1716
1717
add_action( 'wpsc_edit_product', 'wpsc_new_gallery_save' );