Key: Special character/phrase * > Value: Placeholder for special character * @var array */ public $special_chars = null; public $special_chars_default = array( '{' => '%SQB_L%', '}' => '%SQB_R%', ); /** * Reference to parent object that current instance inherits from * @var object */ public $parent = null; /** * Title * @var string */ public $title = ''; /** * @var string Short description */ public $description = ''; /** * @var array Object Properties */ public $properties = array(); /** * Initialization properties * @var array */ protected $properties_init = null; /** * Structure: Property names stored as keys in group * Root * -> Group Name * -> Property Name => Null * Reason: Faster searching over large arrays * @var array Groupings of Properties */ public $property_groups = array(); /** * Keys to filter out of properties array before setting properties * @var array */ public $property_filter = array( 'group' ); /** * Define order of properties * Useful when processing order is important (e.g. one property depends on another) * @var array */ public $property_priority = array(); /** * Data for object * May also contain data for nested objects * @var mixed */ public $data = null; /** * Whether data has been fetched or not * @var bool */ protected $data_loaded = false; /** * @var array Script resources to include for object */ public $scripts = array(); /** * @var array CSS style resources to include for object */ public $styles = array(); /** * Hooks (Filters/Actions) for object * @var array */ public $hooks = array(); /** * Mapping of child properties to parent members * Allows more flexibility when creating new instances of child objects using property arrays * Associative array structure: * > Key: Child property to map FROM * > Val: Parent property to map TO * @var array */ public $map = null; /** * Options used when building collection (callbacks, etc.) * Associative array * > Key: Option name * > Value: Option value * @var array */ public $build_vars = array(); public $build_vars_default = array(); /** * Constructor */ function __construct( $id = '', $properties = null ) { parent::__construct(); // Normalize Properties $args = func_get_args(); $defaults = $this->integrate_id( $id ); $properties = $this->make_properties( $args, $defaults ); // Save init properties $this->properties_init = $properties; // Set Properties $this->set_properties( $properties ); } /* Getters/Setters */ /** * Checks if the specified path exists in the object * @param array $path Path to check for * @return bool TRUE if path exists in object, FALSE otherwise */ function path_isset( $path = '' ) { // Stop execution if no path is supplied if ( empty( $path ) ) { return false; } $args = func_get_args(); $path = $this->util->build_path( $args ); $item =& $this; // Iterate over path and check if each level exists before moving on to the next $path_size = count( $path ); for ( $x = 0; $x < $path_size; $x++ ) { if ( $this->util->property_exists( $item, $path[ $x ] ) ) { // Set $item as reference to next level in path for next iteration $item =& $this->util->get_property( $item, $path[ $x ] ); } else { return false; } } return true; } /** * Retrieves a value from object using a specified path * Checks to make sure path exists in object before retrieving value * @param array $path Path to retrieve value from. Each item in array is a deeper dimension * @return mixed Value at specified path */ function &get_path_value( $path = '' ) { $ret = ''; $path = $this->util->build_path( func_get_args() ); if ( $this->path_isset( $path ) ) { $ret =& $this; $path_size = count( $path ); for ( $x = 0; $x < $path_size; $x++ ) { if ( 0 === $x ) { $ret =& $ret->{ $path[ $x ] }; } else { $ret =& $ret[ $path[ $x ] ]; } } } return $ret; } /** * Search for specified member value in field type ancestors * @param string $member Name of object member to search (e.g. properties, layout, etc.) * @param string $name Value to retrieve from member * @return mixed Member value if found (Default: empty string) */ function get_parent_value( $member, $name = '', $default = '' ) { $parent = $this->get_parent(); return $this->get_object_value( $parent, $member, $name, $default, 'parent' ); } /** * Retrieves specified member value. * * Handles inherited values and merges corresponding parents * if value is an array (e.g. for property groups). * * @param string|array $member Member to get value from. * @param string|array $name Optional. Element/Path to Element to retrieve from member. Default none. * @param mixed $default Optional. Default value to return if no data retrieved. Default empty string. * @param string $dir Optional. Direction to move through hierarchy to find value. * Possible Values: * * parent (default) - Search through field parents. * * current - Do not search through connected objects. * * container - Search through field containers. * * caller - Search through field callers. * @return mixed Specified member value. * @todo Return reference. */ function &get_member_value( $member, $name = '', $default = '', $dir = 'parent' ) { // Check if path to member is supplied $path = array(); if ( is_array( $member ) && isset( $member['tag'] ) ) { if ( isset( $member['attributes']['ref_base'] ) ) { if ( 'root' !== $member['attributes']['ref_base'] ) { $path[] = $member['attributes']['ref_base']; } } else { $path[] = 'properties'; } $path[] = $member['tag']; } else { $path = $member; } // Prep name. if ( is_string( $name ) ) { $name = trim( $name ); } $path = $this->util->build_path( $path, $name ); // Set defaults and prepare data $val = $default; $inherit = false; $inherit_tag = '{inherit}'; /** * Determines whether the value must be retrieved from a parent/container object. * * Conditions: * * 1. Path does not exist in current field. * 2. Path exists and is not an object, but at least one of the following is true: * * Value at path is an array (e.g. properties, elements, etc. array): * * - Parent/container values should be merged with retrieved array. * * Value at path is a string that inherits from another field: * * - Value from other field will be retrieved and will replace * inheritance placeholder in retrieved value * @var bool */ $deeper = false; if ( ! $this->path_isset( $path ) ) { $deeper = true; } else { $val = $this->get_path_value( $path ); if ( is_array( $val ) ) { $deeper = true; } elseif ( is_string( $val ) && false !== strpos( $val, $inherit_tag ) ) { $deeper = true; // Value inherits from another field. $inherit = true; } } if ( $deeper && 'current' !== $dir ) { $ex_val = ''; // Get Parent value (recursive) if ( 'parent' === $dir ) { $ex_val = $this->get_parent_value( $member, $name, $default ); } elseif ( method_exists( $this, 'get_container_value' ) ) { $ex_val = $this->get_container_value( $member, $name, $default ); } // Handle inheritance if ( is_array( $val ) ) { // Combine Arrays if ( is_array( $ex_val ) ) { $val = array_merge( $ex_val, $val ); } } elseif ( false !== $inherit ) { // Replace placeholder with inherited string $val = str_replace( $inherit_tag, $ex_val, $val ); } else { // Default: Set parent value as value $val = $ex_val; } } return $val; } /** * Search for specified member value in an object * @param object $object Reference to object to retrieve value from * @param string $member Name of object member to search (e.g. properties, layout, etc.) * @param string $name (optional) Value to retrieve from member * @param mixed $default (optional) Default value to use if no value found (Default: empty string) * @param string $dir Direction to move through hierarchy to find value @see SLB_Field_Type::get_member_value() for possible values * @return mixed Member value if found (Default: $default) */ function get_object_value( &$object, $member, $name = '', $default = '', $dir = 'parent' ) { $ret = $default; if ( is_object( $object ) && method_exists( $object, 'get_member_value' ) ) { $ret = $object->get_member_value( $member, $name, $default, $dir ); } return $ret; } /** * Set item ID * @param string $id Unique item ID */ function set_id( $id ) { if ( empty( $id ) || ! is_string( $id ) ) { return false; } $this->id = trim( $id ); } /** * Retrieves field ID * @param array|string $options (optional) Options or ID of format to use * @return string item ID */ function get_id( $options = array() ) { $item_id = trim( $this->id ); $formats = $this->get_id_formats(); // Setup options $wrap_default = array( 'open' => '', 'close' => '', 'segment_open' => '', 'segment_close' => '', ); $options_default = array( 'format' => null, 'wrap' => array(), 'segments_pre' => null, 'prefix' => '', 'recursive' => false, ); // Load options based on format if ( ! is_array( $options ) ) { $options = array( 'format' => $options ); } if ( isset( $options['format'] ) && is_string( $options['format'] ) && isset( $formats[ $options['format'] ] ) ) { $options_default = wp_parse_args( $formats[ $options['format'] ], $options_default ); } else { unset( $options['format'] ); } $options = wp_parse_args( $options, $options_default ); // Import options into function extract( $options ); // Validate options $wrap = wp_parse_args( $wrap, $wrap_default ); if ( ! is_array( $segments_pre ) ) { $segments_pre = array( $segments_pre ); } $segments_pre = array_reverse( $segments_pre ); // Format ID based on options $item_id = array( $item_id ); // Add parent objects to ID if ( ! ! $recursive ) { // Create array of ID components $m = 'get_caller'; $c = ( method_exists( $this, $m ) ) ? $this->{$m}() : null; while ( ! ! $c ) { // Add ID of current caller to array if ( method_exists( $c, 'get_id' ) && ! strlen( $c->get_id() ) > 0 ) { $item_id = $c->get_id(); } // Get parent object $c = ( method_exists( $c, $m ) ) ? $c->{$m}() : null; } unset( $c ); } // Additional segments (Pre) foreach ( $segments_pre as $seg ) { if ( is_null( $seg ) ) { continue; } if ( is_object( $seg ) ) { $seg = (array) $seg; } if ( is_array( $seg ) ) { $item_id = array_merge( $item_id, array_reverse( $seg ) ); } elseif ( '' !== strval( $seg ) ) { $item_id[] = strval( $seg ); } } // Prefix if ( is_array( $prefix ) ) { // Array is sequence of instance methods to call on object // Last array member can be an array of parameters to pass to methods $count = count( $prefix ); $args = ( $count > 1 && is_array( $prefix[ $count - 1 ] ) ) ? array_pop( $prefix ) : array(); $p = $this; $val = ''; // Iterate through methods foreach ( $prefix as $m ) { if ( ! method_exists( $p, $m ) ) { continue; } // Build callback $m = $this->util->m( $p, $m ); // Call callback $val = call_user_func_array( $m, $args ); // Returned value may be an instance object if ( is_object( $val ) ) { $p = $val; // Use returned object in next round } else { array_unshift( $args, $val ); // Pass returned value as parameter to next method on using current object } } $prefix = $val; unset( $p, $val ); } if ( is_numeric( $prefix ) ) { $prefix = strval( $prefix ); } if ( empty( $prefix ) || ! is_string( $prefix ) ) { $prefix = ''; } // Convert array to string $item_id = $prefix . $wrap['open'] . implode( $wrap['segment_close'] . $wrap['segment_open'], array_reverse( $item_id ) ) . $wrap['close']; return $item_id; } /** * Retrieves ID formats. * * @return array ID formats. */ private function &get_id_formats() { $this->init_id_formats(); return $this->id_formats; } /** * Initializes default ID formats. * * @since 2.8.0 * * @return void */ private function init_id_formats() { if ( ! $this->id_formats_init ) { $this->id_formats_init = true; // Initilize default formats. $this->add_id_format( 'attr_id', [ 'wrap' => [ 'open' => '_', 'segment_open' => '_', ], 'prefix' => [ 'get_container', 'get_id', 'add_prefix' ], 'recursive' => true, ], true ); $this->add_id_format( 'attr_name', [ 'wrap' => [ 'open' => '[', 'close' => ']', 'segment_open' => '[', 'segment_close' => ']', ], 'prefix' => [ 'get_container', 'get_id', 'add_prefix' ], 'recursive' => true, ], true ); } } /** * Adds custom ID format. * * @since 2.8.0 * * @param string $name Format name. * @param array $wrap * @param array $prefix * @param bool $recursive Optional. * @param bool $overwrite Optional. Overwrite existing format. Default false. * @return void */ protected function add_id_format( $name, array $options, $overwrite = false ) { // Init ID formats before adding new ones. $this->init_id_formats(); // Validate args. $name = trim( $name ); // Stop if name invalid. if ( empty( $name ) ) { return; } $overwrite = (bool) $overwrite; // Do not add format if name matches existing format (when overwriting not allowed). if ( ! $overwrite && in_array( $name, array_keys( $this->id_formats ), true ) ) { return; } // Normlize options. $options = wp_parse_args( $options, [ 'wrap' => [], 'prefix' => [], 'recursive' => false, ] ); // Add format. $this->id_formats[ $name ] = $options; } /** * Retrieve value from data member * @param string $context Context to format data for * @param bool $top (optional) Whether to traverse through the field hierarchy to get data for field (Default: TRUE) * @return mixed Value at specified path */ function get_data( $context = '', $top = true ) { $opt_d = array( 'context' => '', 'top' => true, ); $args = func_get_args(); $a = false; if ( count( $args ) === 1 && is_array( $args[0] ) && ! empty( $args[0] ) ) { $a = true; $args = wp_parse_args( $args[0], $opt_d ); extract( $args ); } if ( is_string( $top ) ) { if ( 'false' === $top ) { $top = false; } elseif ( 'true' === $top ) { $top = true; } elseif ( is_numeric( $top ) ) { $top = intval( $top ); } } $top = ! ! $top; $obj =& $this; $obj_path = array( $this ); $path = array(); if ( $top ) { // Iterate through hiearchy to get top-most object while ( ! empty( $obj ) ) { $new = null; // Try to get caller first if ( method_exists( $obj, 'get_caller' ) ) { $checked = true; $new =& $obj->get_caller(); } // Try to get container if no caller found if ( empty( $new ) && method_exists( $obj, 'get_container' ) ) { $checked = true; $new =& $obj->get_container(); // Load data if ( method_exists( $new, 'load_data' ) ) { $new->load_data(); } } $obj =& $new; unset( $new ); // Stop iteration if ( ! empty( $obj ) ) { // Add object to path if it is valid $obj_path[] =& $obj; } } unset( $obj ); } // Check each object (starting with top-most) for matching data for current field // Reverse array $obj_path = array_reverse( $obj_path ); // Build path for data location foreach ( $obj_path as $obj ) { if ( method_exists( $obj, 'get_id' ) ) { $path[] = $obj->get_id(); } } // Iterate through objects while ( ! empty( $obj_path ) ) { // Get next object $obj = array_shift( $obj_path ); // Shorten path array_shift( $path ); // Check for value in object and stop iteration if matching data found $val = $this->get_object_value( $obj, 'data', $path, null, 'current' ); if ( ! is_null( $val ) ) { break; } } return $this->format( $val, $context ); } /** * Sets value in data member * Sets value to data member itself by default * @param mixed $value Value to set * @param string|array $name Name of value to set (Can also be path to value) */ function set_data( $value, $name = '' ) { $ref =& $this->get_path_value( 'data', $name ); $ref = $value; } /** * Sets parent object of current instance * Parent objects must be the same object type as current instance * @uses SLB to get field type definition * @uses SLB_Fields::has() to check if field type exists * @uses SLB_Fields::get() to retrieve field type object reference * @param string|object $parent Parent ID or reference */ function set_parent( $parent = null ) { // Stop processing if parent empty if ( empty( $parent ) && ! is_string( $this->parent ) ) { return false; } // Parent passed as object reference wrapped in array if ( is_array( $parent ) && isset( $parent[0] ) && is_object( $parent[0] ) ) { $parent = $parent[0]; } // No parent set but parent ID (previously) set in object if ( empty( $parent ) && is_string( $this->parent ) ) { $parent = $this->parent; } // Retrieve reference object if ID was supplied if ( is_string( $parent ) ) { $parent = trim( $parent ); // Get parent object reference /** * @var SLB */ $b = $this->get_base(); if ( ! ! $b && isset( $b->fields ) && $b->fields->has( $parent ) ) { $parent = $b->fields->get( $parent ); } } // Set parent value on object if ( is_string( $parent ) || is_object( $parent ) ) { $this->parent = $parent; } } /** * Retrieve field type parent * @return SLB_Field_Type Parent field */ function get_parent() { return $this->parent; } /** * Set object title * @param string $title Title for object * @param string $plural Plural form of title */ function set_title( $title = '' ) { if ( is_scalar( $title ) ) { $this->title = wp_strip_all_tags( trim( $title ) ); } } /** * Retrieve object title */ function get_title() { return $this->get_member_value( 'title', '', '', 'current' ); } /** * Set object description * @param string $description Description for object */ function set_description( $description = '' ) { $this->description = wp_strip_all_tags( trim( $description ) ); } /** * Retrieve object description * @return string Object description */ function get_description() { $dir = 'current'; return $this->get_member_value( 'description', '', '', $dir ); } /** * Sets multiple properties on field type at once. * * @param array $properties Properties to set - each element is an * array containing the arguments to set a * new property. * @return void * @todo Test refactored code. */ function set_properties( $properties ) { if ( ! is_array( $properties ) ) { return; } // Normalize properties $properties = $this->remap_properties( $properties ); $properties = $this->sort_properties( $properties ); // Set Member properties. foreach ( $properties as $prop => $val ) { $m = 'set_' . $prop; if ( method_exists( $this, $m ) ) { $this->{$m}( $val ); // Remove member property from array unset( $properties[ $prop ] ); } unset( $m ); } // Filter properties $properties = $this->filter_properties( $properties ); // Set additional instance properties foreach ( $properties as $name => $val ) { $this->set_property( $name, $val ); } } /** * Remap properties based on $map * @uses $map For determine how child properties should map to parent properties * @uses SLB_Utlities::array_remap() to perform array remapping * @param array $properties Associative array of properties * @return array Remapped properties */ function remap_properties( $properties ) { // Return remapped properties return $this->util->array_remap( $properties, $this->map ); } /** * Sort properties based on priority * @uses this::property_priority * @return array Sorted priorities */ function sort_properties( $properties ) { // Stop if sorting not necessary if ( empty( $properties ) || ! is_array( $properties ) || empty( $this->property_priority ) || ! is_array( $this->property_priority ) ) { return $properties; } $props = array(); foreach ( $this->property_priority as $prop ) { if ( ! array_key_exists( $prop, $properties ) ) { continue; } // Add to new array $props[ $prop ] = $properties[ $prop ]; // Remove from old array unset( $properties[ $prop ] ); } // Append any remaining properties $props = array_merge( $props, $properties ); return $props; } /** * Build properties array * @param array $props Instance properties * @param array $signature (optional) Default properties * @return array Normalized properties */ function make_properties( $props, $signature = array() ) { $p = array(); if ( is_array( $props ) ) { foreach ( $props as $prop ) { if ( is_array( $prop ) ) { $p = array_merge( $prop, $p ); } } } $props = $p; if ( is_array( $signature ) ) { $props = array_merge( $signature, $props ); } return $props; } function validate_id( $id ) { return ( is_scalar( $id ) && ! empty( $id ) ) ? true : false; } function integrate_id( $id ) { return ( $this->validate_id( $id ) ) ? array( 'id' => $id ) : array(); } /** * Filter property members * @uses $property_filter to remove define members to remove from $properties * @param array $props Properties * @return array Filtered properties */ function filter_properties( $props = array() ) { return $this->util->array_filter_keys( $props, $this->property_filter ); } /** * Add/Set a property on the field definition * @param string $name Name of property * @param mixed $value Default value for property * @param string|array $group Group(s) property belongs to * @return boolean TRUE if property is successfully added to field type, FALSE otherwise */ function set_property( $name, $value = '', $group = null ) { // Do not add if property name is not a string if ( ! is_string( $name ) ) { return false; } // Create property array $prop_arr = array(); $prop_arr['value'] = $value; // Add to properties array $this->properties[ $name ] = $value; // Add property to specified groups if ( ! empty( $group ) ) { $this->set_group_property( $group, $name ); } return true; } /** * Retreives property from field type * @param string $name Name of property to retrieve * @return mixed Specified Property if exists (Default: Empty string) */ function get_property( $name ) { $val = $this->get_member_value( 'properties', $name ); return $val; } /** * Removes a property from item * @param string $name Property ID */ function remove_property( $name ) { // Remove property if ( isset( $this->properties[ $name ] ) ) { unset( $this->properties[ $name ] ); } // Remove from group foreach ( array_keys( $this->property_groups ) as $g ) { if ( isset( $this->property_groups[ $g ][ $name ] ) ) { unset( $this->property_groups[ $g ][ $name ] ); break; } } } /** * Adds Specified Property to a Group * @param string|array $group Group(s) to add property to * @param string $property Property to add to group */ function set_group_property( $group, $property ) { if ( is_string( $group ) && isset( $this->property_groups[ $group ][ $property ] ) ) { return; } if ( ! is_array( $group ) ) { $group = array( $group ); } foreach ( $group as $g ) { $g = trim( $g ); // Initialize group if it doesn't already exist if ( ! isset( $this->property_groups[ $g ] ) ) { $this->property_groups[ $g ] = array(); } // Add property to group $this->property_groups[ $g ][ $property ] = null; } } /** * Retrieve property group * @param string $group Group to retrieve * @return array Array of properties in specified group */ function get_group( $group ) { return $this->get_member_value( 'property_groups', $group, array() ); } /** * Save field data * Child classes will define their own * functionality for this method * @return bool TRUE if save was successful (FALSE otherwise) */ function save() { return true; } /*-** Hooks **-*/ /** * Retrieve hooks added to object * @return array Hooks */ function get_hooks() { return $this->get_member_value( 'hooks', '', array() ); } /** * Add hook for object * @see add_filter() for parameter defaults * @param $tag * @param $function_to_add * @param $priority * @param $accepted_args */ function add_hook( $tag, $function_to_add, $priority = 10, $accepted_args = 1 ) { // Create new array for tag (if not already set) if ( ! isset( $this->hooks[ $tag ] ) ) { $this->hooks[ $tag ] = array(); } // Build Unique ID if ( is_string( $function_to_add ) ) { $id = $function_to_add; } elseif ( is_array( $function_to_add ) && ! empty( $function_to_add ) ) { $id = strval( $function_to_add[ count( $function_to_add ) - 1 ] ); } else { $id = 'function_' . ( count( $this->hooks[ $tag ] ) + 1 ); } // Add hook $this->hooks[ $tag ][ $id ] = func_get_args(); } /** * Convenience method for adding an action for object * @see add_filter() for parameter defaults * @param $tag * @param $function_to_add * @param $priority * @param $accepted_args */ function add_action( $tag, $function_to_add, $priority = 10, $accepted_args = 1 ) { $this->add_hook( $tag, $function_to_add, $priority, $accepted_args ); } /** * Convenience method for adding a filter for object * @see add_filter() for parameter defaults * @param $tag * @param $function_to_add * @param $priority * @param $accepted_args */ function add_filter( $tag, $function_to_add, $priority = 10, $accepted_args = 1 ) { $this->add_hook( $tag, $function_to_add, $priority, $accepted_args ); } /*-** Dependencies **-*/ /** * Adds dependency to object * @param string $type Type of dependency to add (script, style) * @param array|string $context When dependency will be added (@see SLB_Utilities::get_action() for possible contexts) * @see wp_enqueue_script for the following of the parameters * @param $handle * @param $src * @param $deps * @param $ver * @param $ex */ function add_dependency( $type, $context, $handle, $src = false, $deps = array(), $ver = false, $ex = false ) { $args = func_get_args(); // Remove type/context from arguments $args = array_slice( $args, 2 ); // Set context if ( ! is_array( $context ) ) { // Wrap single contexts in an array if ( is_string( $context ) ) { $context = array( $context ); } else { $context = array(); } } // Add file to instance property if ( isset( $this->{$type} ) && is_array( $this->{$type} ) ) { $this->{$type}[ $handle ] = array( 'context' => $context, 'params' => $args, ); } } /** * Add script to object to be added in specified contexts * @param array|string $context Array of contexts to add script to page * @see wp_enqueue_script for the following of the parameters * @param $handle * @param $src * @param $deps * @param $ver * @param $in_footer */ function add_script( $context, $handle, $src = false, $deps = array(), $ver = false, $in_footer = false ) { $args = func_get_args(); // Add file type to front of arguments array array_unshift( $args, 'scripts' ); call_user_func_array( $this->m( 'add_dependency' ), $args ); } /** * Retrieve script dependencies for object * @return array Script dependencies */ function get_scripts() { return $this->get_member_value( 'scripts', '', array() ); } /** * Add style to object to be added in specified contexts * @param array|string $context Array of contexts to add style to page * @see wp_enqueue_style for the following of the parameters * @param $handle * @param $src * @param $deps * @param $ver * @param $in_footer */ function add_style( $handle, $src = false, $deps = array(), $ver = false, $media = false ) { $args = func_get_args(); array_unshift( $args, 'styles' ); call_user_func_array( $this->m( 'add_dependency' ), $args ); } /** * Retrieve Style dependencies for object * @return array Style dependencies */ function get_styles() { return $this->get_member_value( 'styles', '', array() ); } /* Helpers */ /** * Format value based on specified context * @param mixed $value Value to format * @param string $context Current context * @return mixed Formatted value */ function format( $value, $context = '' ) { if ( is_scalar( $context ) && ! empty( $context ) ) { $handler = 'format_' . trim( strval( $context ) ); // Only process if context is valid and has a handler if ( ! empty( $context ) && method_exists( $this, $handler ) ) { // Pass value to handler $value = $this->{$handler}( $value, $context ); } } // Return formatted value return $value; } /** * Format value for output as an attribute. * * Only strings are formatted. * * @since 2.8.0 * * @param mixed $value Value to format. * @return mixed Formatted value. */ function format_attr( $value ) { if ( is_string( $value ) ) { $value = esc_attr( $value ); } return $value; } /** * Formats value for output as plain text. * * Escapes HTML, etc. * Only strings are formatted. * * @since 2.8.0 * * @param mixed $value Value to format. * @return mixed Formatted value. */ function format_text( $value ) { if ( is_string( $value ) ) { $value = esc_html( $value ); } return $value; } /** * Final formatting before output * Restores special characters, etc. * @uses $special_chars * @uses $special_chars_default * @param mixed $value Pre-final field output * @param string $context (Optional) Formatting context * @return mixed Formatted value */ function format_final( $value, $context = '' ) { if ( ! is_string( $value ) ) { return $value; } // Restore special chars return $this->restore_special_chars( $value, $context ); } function preserve_special_chars( $value, $context = '' ) { if ( ! is_string( $value ) ) { return $value; } $specials = $this->get_special_chars(); return str_replace( array_keys( $specials ), $specials, $value ); } function restore_special_chars( $value, $context = '' ) { if ( ! is_string( $value ) ) { return $value; } $specials = $this->get_special_chars(); return str_replace( $specials, array_keys( $specials ), $value ); } /** * Retrieve special characters/placeholders * Merges defaults with class-specific characters * @uses $special_chars * @uses $special_chars_default * @return array Special characters/placeholders */ function get_special_chars() { return wp_parse_args( $this->special_chars, $this->special_chars_default ); } }