Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Newer
Older
100644 449 lines (406 sloc) 14.334 kb
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
1 <?php
2 /*
6046a9a Brian Zoetewey Updated to work as a WordPress plugin.
Omicron7 authored
3 * Plugin Name: Advanced Custom Fields - Taxonomy Field add-on
4 * Plugin URI: https://github.com/GCX/acf-taxonomy-field
5 * Description: This plugin is an add-on for Advanced Custom Fields. It provides a dropdown of taxonomy terms and the ability to map the selected terms to the post.
6 * Author: Brian Zoetewey
7 * Author URI: https://github.com/GCX
d10d349 Brian Zoetewey Updated meta for version 1.1 release
Omicron7 authored
8 * Version: 1.1
6046a9a Brian Zoetewey Updated to work as a WordPress plugin.
Omicron7 authored
9 * Text Domain: acf-taxonomy-field
10 * Domain Path: /languages/
11 * License: Modified BSD
12 */
13 ?>
14 <?php
15 /*
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
16 * Copyright (c) 2012, CAMPUS CRUSADE FOR CHRIST
17 * All rights reserved.
18 *
19 * Redistribution and use in source and binary forms, with or without modification,
20 * are permitted provided that the following conditions are met:
21 *
22 * Redistributions of source code must retain the above copyright notice, this
23 * list of conditions and the following disclaimer.
24 * Redistributions in binary form must reproduce the above copyright notice,
25 * this list of conditions and the following disclaimer in the documentation
26 * and/or other materials provided with the distribution.
27 * Neither the name of CAMPUS CRUSADE FOR CHRIST nor the names of its
28 * contributors may be used to endorse or promote products derived from this
29 * software without specific prior written permission.
30 *
31 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
32 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
33 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
34 * IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
35 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
36 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
37 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
38 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
39 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
40 * OF THE POSSIBILITY OF SUCH DAMAGE.
41 */
42 ?>
43 <?php
44
45 if( !class_exists( 'ACF_Taxonomy_Field' ) && class_exists( 'acf_Field' ) ) :
46
47 /**
48 * Advanced Custom Fields - Taxonomy Field add-on
49 *
50 * @author Brian Zoetewey <brian.zoetewey@ccci.org>
51 * @version 1.0
52 */
53 class ACF_Taxonomy_Field extends acf_Field {
54 /**
55 * Base directory
56 * @var string
57 */
58 private $base_dir;
59
60 /**
61 * Relative Uri from the WordPress ABSPATH constant
62 * @var string
63 */
64 private $base_uri_rel;
65
66 /**
67 * Absolute Uri
68 *
69 * This is used to create urls to CSS and JavaScript files.
70 * @var string
71 */
72 private $base_uri_abs;
73
74 /**
75 * WordPress Localization Text Domain
76 *
77 * The textdomain for the field is controlled by the helper class.
78 * @var string
79 */
80 private $l10n_domain;
81
82 /**
83 * Class Constructor - Instantiates a new Taxonomy Field
84 * @param Acf $parent Parent Acf class
85 */
86 public function __construct( $parent ) {
87 //Call parent constructor
88 parent::__construct( $parent );
89
90 //Get the textdomain from the Helper class
91 $this->l10n_domain = ACF_Taxonomy_Field_Helper::L10N_DOMAIN;
92
93 //Base directory of this field
94 $this->base_dir = rtrim( dirname( realpath( __FILE__ ) ), '/' );
95
96 //Build the base relative uri by searching backwards until we encounter the wordpress ABSPATH
97 $root = array_pop( explode( '/', rtrim( ABSPATH, '/' ) ) );
98 $path_parts = explode( '/', $this->base_dir );
99 $parts = array();
100 while( $part = array_pop( $path_parts ) ) {
101 if( $part == $root )
102 break;
103 array_unshift( $parts, $part );
104 }
105 $this->base_uri_rel = '/' . implode( '/', $parts );
106 $this->base_uri_abs = get_site_url( null, $this->base_uri_rel );
107
108 $this->name = 'taxonomy-field';
7b2144d Brian Zoetewey Fixed variable name typo
Omicron7 authored
109 $this->title = __( 'Taxonomy', $this->l10n_domain );
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
110
111 add_action( 'admin_print_scripts', array( &$this, 'admin_print_scripts' ), 12, 0 );
112 add_action( 'admin_print_styles', array( &$this, 'admin_print_styles' ), 12, 0 );
113 }
114
115 /**
116 * Registers and enqueues necessary CSS
117 *
118 * This method is called by ACF when rendering a post add or edit screen.
119 * We also call this method on the Acf Field Options screen as well in order
120 * to style our Field options
121 *
122 * @see acf_Field::admin_print_styles()
123 */
124 public function admin_print_styles() {
125 global $pagenow;
126 // wp_register_style( 'acf-taxonomy-field', $this->base_uri_abs . '/taxonomy-field.css' );
127
128 if( in_array( $pagenow, array( 'post.php', 'post-new.php' ) ) ) {
129 // wp_enqueue_style( 'acf-taxonomy-field' );
130 }
131 }
132
133 /**
134 * Registers and enqueues necessary JavaScript
135 *
136 * This method is called by ACF when rendering a post add or edit screen.
137 * We also call this method on the Acf Field Options screen as well in order
138 * to add the necessary JavaScript for taxonomy selection.
139 *
140 * @see acf_Field::admin_print_scripts()
141 */
142 public function admin_print_scripts() {
143 global $pagenow;
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
144 // wp_register_script( 'acf-taxonomy-field', $this->base_uri_abs . '/taxonomy-field.js', array( 'jquery' ) );
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
145
146 if( in_array( $pagenow, array( 'post.php', 'post-new.php' ) ) ) {
147 // wp_enqueue_script( 'acf-taxonomy-field' );
148 }
149 }
150
151 /**
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
152 * Populates the fields array with defaults for this field type
153 *
154 * @param array $field
155 * @return array
156 */
157 private function set_field_defaults( &$field ) {
158 $field[ 'taxonomy' ] = ( array_key_exists( 'taxonomy', $field ) && isset( $field[ 'taxonomy' ] ) ) ? $field[ 'taxonomy' ] : 'category';
159 $field[ 'input_type' ] = ( array_key_exists( 'input_type', $field ) && isset( $field[ 'input_type' ] ) ) ? $field[ 'input_type' ] : 'select';
160 $field[ 'input_size' ] = ( array_key_exists( 'input_size', $field ) && isset( $field[ 'input_size' ] ) ) ? (int) $field[ 'input_size' ] : 5;
161 // $field[ 'allow_new_terms' ] = ( array_key_exists( 'allow_new_terms', $field ) && isset( $field[ 'allow_new_terms' ] ) ) ? (int) $field[ 'allow_new_terms' ] : 0; //false
162 $field[ 'set_post_terms' ] = ( array_key_exists( 'set_post_terms', $field ) && isset( $field[ 'set_post_terms' ] ) ) ? (int) $field[ 'set_post_terms' ] : 1; //true
163 return $field;
164 }
165
166 /**
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
167 * Creates the taxonomy field for inside post metaboxes
168 *
169 * @see acf_Field::create_field()
170 */
171 public function create_field( $field ) {
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
172 $this->set_field_defaults( $field );
173
174 $terms = get_terms( $field['taxonomy'], array( 'hide_empty' => false ) );
175 $value = $field[ 'value' ];
7029c69 Brian Zoetewey Removed strict equality and force type to integer when comparing selecte...
Omicron7 authored
176
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
177 if( in_array( $field[ 'input_type' ], array( 'select', 'multiselect' ) ) ) :
178 ?>
179 <select name="<?php echo $field[ 'name' ]; ?>[]" id="<?php echo $field[ 'name' ]; ?>" class="<?php echo $field[ 'class' ]; ?>" <?php echo ( $field[ 'input_type' ] == 'multiselect' ) ? 'multiple="multiple" size="' . $field[ 'input_size' ] . '"' : ''; ?>>
180 <?php foreach( $terms as $term ) : ?>
77bd773 Brian Zoetewey value should not be typecast to int as it is an array.
Omicron7 authored
181 <option value="<?php echo $term->term_id; ?>" <?php selected( in_array( (int) $term->term_taxonomy_id, $value ) ); ?>><?php echo $term->name; ?></option>
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
182 <?php endforeach; ?>
183 </select>
184 <?php
185 endif;
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
186 }
187
188 /**
189 * Builds the field options
190 *
191 * @see acf_Field::create_options()
192 * @param string $key
193 * @param array $field
194 */
195 public function create_options( $key, $field ) {
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
196 $this->set_field_defaults( $field );
197
198 $taxonomies = get_taxonomies( array(), 'objects' );
199 ksort( $taxonomies );
200 $tax_choices = array();
201 foreach( $taxonomies as $tax )
202 $tax_choices[ $tax->name ] = $tax->label;
203
204 ?>
205 <tr class="field_option field_option_<?php echo $this->name; ?>">
206 <td class="label">
207 <label><?php _e( 'Taxonomy' , $this->l10n_domain ); ?></label>
208 <p class="description"><?php _e( 'Select the taxonomy to display.', $this->l10n_domain ); ?></p>
209 </td>
210 <td>
211 <?php
212 $this->parent->create_field( array(
213 'type' => 'select',
214 'name' => "fields[{$key}][taxonomy]",
215 'value' => $field[ 'taxonomy' ],
216 'choices' => $tax_choices,
217 ) );
218 ?>
219 </td>
220 </tr>
221 <tr class="field_option field_option_<?php echo $this->name; ?>">
222 <td class="label">
223 <label><?php _e( 'Input Method' , $this->l10n_domain ); ?></label>
224 <p class="description"><?php _e( '', $this->l10n_domain ); ?></p>
225 </td>
226 <td>
227 <?php
228 $this->parent->create_field( array(
229 'type' => 'select',
230 'name' => "fields[{$key}][input_type]",
231 'value' => $field[ 'input_type' ],
232 'class' => 'taxonomy_input_type',
233 'choices' => array(
234 'select' => 'Select',
235 'multiselect' => 'Multi-Select',
236 //'token' => 'Input Tokenizer',
237 ),
238 ) );
239 ?>
240 </td>
241 </tr>
242 <tr class="field_option field_option_<?php echo $this->name; ?>">
243 <td class="label">
244 <label><?php _e( 'Set Post Terms' , $this->l10n_domain ); ?></label>
245 <p class="description"><?php _e( 'Add the selected term(s) to the post. The current post must support the selected taxonomy for this to work.', $this->l10n_domain ); ?></p>
246 </td>
247 <td>
248 <?php
249 $this->parent->create_field( array(
250 'type' => 'true_false',
251 'name' => "fields[{$key}][set_post_terms]",
252 'value' => $field[ 'set_post_terms' ],
253 ) );
254 ?>
255 </td>
256 </tr>
257 <!--
258 <tr class="field_option field_option_<?php echo $this->name; ?> taxonomy_add_terms">
259 <td class="label">
260 <label><?php _e( 'Add New Terms' , $this->l10n_domain ); ?></label>
261 <p class="description"><?php _e( 'Add any new terms to the selected taxonomy.', $this->l10n_domain ); ?></p>
262 </td>
263 <td>
264 <?php
265 $this->parent->create_field( array(
266 'type' => 'true_false',
267 'name' => "fields[{$key}][allow_new_terms]",
268 'value' => $field[ 'allow_new_terms' ],
269 ) );
270 ?>
271 </td>
272 </tr>
273 -->
274 <tr class="field_option field_option_<?php echo $this->name; ?> taxonomy_input_size">
275 <td class="label">
276 <label><?php _e( 'Multi-Select Size' , $this->l10n_domain ); ?></label>
277 <p class="description"><?php _e( 'The number of terms to show at once in a multi-select.', $this->l10n_domain ); ?></p>
278 </td>
279 <td>
280 <?php
281 $this->parent->create_field( array(
282 'type' => 'select',
283 'name' => "fields[{$key}][input_size]",
284 'value' => $field[ 'input_size' ],
285 'choices' => array_combine( range( 3, 15, 2 ), range( 3, 15, 2 ) ),
286 ) );
287 ?>
288 </td>
289 </tr>
290 <?php
291 }
292
6046a9a Brian Zoetewey Updated to work as a WordPress plugin.
Omicron7 authored
293 /**
294 * (non-PHPdoc)
295 * @see acf_Field::update_value()
296 */
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
297 public function update_value( $post_id, $field, $value ) {
298 $this->set_field_defaults( $field );
299
300 if( $field[ 'set_post_terms' ] ) {
301 $terms = array();
302 foreach( (array) $value as $item ) {
303 if( intval( $item ) > 0 )
304 $terms[] = intval( $item );
305 else
306 $terms[] = strval( $item );
307 }
308 $value = wp_set_object_terms( $post_id, $terms, $field[ 'taxonomy' ], false );
309 }
310
6046a9a Brian Zoetewey Updated to work as a WordPress plugin.
Omicron7 authored
311 parent::update_value( $post_id, $field, $value );
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
312 }
313
314 /**
315 * Returns the values of the field
316 *
317 * @see acf_Field::get_value()
318 * @param int $post_id
319 * @param array $field
320 * @return mixed
321 */
322 public function get_value( $post_id, $field ) {
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
323 $value = (array) parent::get_value( $post_id, $field );
324 return $value;
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
325 }
326
327 /**
328 * Returns the value of the field for the advanced custom fields API
329 *
330 * @see acf_Field::get_value_for_api()
331 * @param int $post_id
332 * @param array $field
333 * @return string
334 */
335 public function get_value_for_api( $post_id, $field ) {
3f7bf56 Brian Zoetewey Use get_the_term_list to output links to the terms for the api call.
Omicron7 authored
336 $this->set_field_defaults( $field );
6e479f2 Brian Zoetewey Updated get_value API to work for posts with or without set_post_terms e...
Omicron7 authored
337 //If terms are set on the post, we can let WordPress create the list
338 if( $field[ 'set_post_terms' ] ) {
339 return get_the_term_list( $post_id, $field[ 'taxonomy' ] );
340 }
341
342 //Otherwise, loop through the terms
3f7bf56 Brian Zoetewey Use get_the_term_list to output links to the terms for the api call.
Omicron7 authored
343 $value = parent::get_value_for_api($post_id, $field);
6e479f2 Brian Zoetewey Updated get_value API to work for posts with or without set_post_terms e...
Omicron7 authored
344 if( empty( $value ) )
345 return false;
346
347 $term_links = array();
348 foreach( $value as $term_id ) {
349 $term_id = intval( $term_id );
350 $term = get_term( $term_id );
351 $link = get_term_link( $term, $taxonomy );
352 if( !is_wp_error( $link ) )
353 $term_links[] = '<a href="' . $link . '" rel="tag">' . $term->name . '</a>';
354 }
355 if( empty( $term_links ) )
356 return false;
357
358 //Allow plugins to modify
359 $term_links = apply_filters( "term_links-{$field[ 'taxonomy' ]}", $term_links );
360
361 return join( '', $term_links );
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
362 }
363 }
364
365 endif; //class_exists 'ACF_Taxonomy_Field'
366
367 if( !class_exists( 'ACF_Taxonomy_Field_Helper' ) ) :
368
369 /**
370 * Advanced Custom Fields - Taxonomy Field Helper
371 *
372 * @author Brian Zoetewey <brian.zoetewey@ccci.org>
373 */
374 class ACF_Taxonomy_Field_Helper {
375 /**
376 * Singleton instance
377 * @var ACF_Taxonomy_Field_Helper
378 */
379 private static $instance;
380
381 /**
382 * Returns the ACF_Taxonomy_Field_Helper singleton
383 *
384 * <code>$obj = ACF_Taxonomy_Field_Helper::singleton();</code>
385 * @return ACF_Taxonomy_Field_Helper
386 */
387 public static function singleton() {
388 if( !isset( self::$instance ) ) {
389 $class = __CLASS__;
390 self::$instance = new $class();
391 }
392 return self::$instance;
393 }
394
395 /**
396 * Prevent cloning of the ACF_Taxonomy_Field_Helper object
397 * @internal
398 */
399 private function __clone() {
400 }
401
402 /**
403 * WordPress Localization Text Domain
404 *
405 * Used in wordpress localization and translation methods.
406 * @var string
407 */
408 const L10N_DOMAIN = 'acf-taxonomy-field';
409
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
410 /**
411 * Language directory path
412 *
413 * Used to build the path for WordPress localization files.
414 * @var string
415 */
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
416 private $lang_dir;
417
418 /**
419 * Constructor
420 */
421 private function __construct() {
422 $this->lang_dir = rtrim( dirname( realpath( __FILE__ ) ), '/' ) . '/languages';
423
6046a9a Brian Zoetewey Updated to work as a WordPress plugin.
Omicron7 authored
424 add_action( 'init', array( &$this, 'register_field' ), 5, 0 );
425 add_action( 'init', array( &$this, 'load_textdomain' ), 2, 0 );
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
426 }
427
428 /**
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
429 * Registers the Field with Advanced Custom Fields
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
430 */
8230f7e Brian Zoetewey Taxonomy field working as select or multi-select.
Omicron7 authored
431 public function register_field() {
fa7b180 Brian Zoetewey Taxonomy field skeleton. WIP
Omicron7 authored
432 if( function_exists( 'register_field' ) ) {
433 register_field( 'ACF_Taxonomy_Field', __FILE__ );
434 }
435 }
436
437 /**
438 * Loads the textdomain for the current locale if it exists
439 */
440 public function load_textdomain() {
441 $locale = get_locale();
442 $mofile = $this->lang_dir . '/' . self::L10N_DOMAIN . '-' . $locale . '.mo';
443 load_textdomain( self::L10N_DOMAIN, $mofile );
444 }
445 }
446 endif; //class_exists 'ACF_Taxonomy_Field_Helper'
447
448 //Instantiate the Addon Helper class
449 ACF_Taxonomy_Field_Helper::singleton();
Something went wrong with that request. Please try again.