get_current_language(); // WPML will set the "Preview Language" from preview_id for Quick Edit if ( ( 'all' === $current_language ) && ( ! isset( $_GET['preview_id'] ) ) ) { if ( ! empty( $_SERVER[ 'HTTP_REFERER' ] ) ) { $default_language = $sitepress->get_default_language(); // Look for an ID from the Media/Edit Media screen $query_string = parse_url( $_SERVER[ 'HTTP_REFERER' ], PHP_URL_QUERY ); $query = array(); parse_str( strval( $query_string ), $query ); if ( isset( $query['post'] ) ) { $language_details = $sitepress->get_element_language_details( absint( $query['post'] ), 'post_attachment' ); $default_language = $language_details->language_code; } // WPML overides switch_lang() from the HTTP_REFERER $referer = remove_query_arg( 'lang', $_SERVER[ 'HTTP_REFERER' ] ); $_SERVER[ 'HTTP_REFERER' ] = add_query_arg( 'lang', $default_language, $referer ); } // HTTP_REFERER } // no ID } // ajax-tag-search } /* * Localize $mla_language_option_definitions array */ self::mla_localize_language_option_definitions(); /* * Apply the "Always Translate Media" override */ if ( ! empty( $_REQUEST['mlaAddNewBulkEditFormString'] ) && class_exists( 'WPML_Media' ) && ( 'checked' == MLACore::mla_get_option( MLACoreOptions::MLA_ADD_NEW_BULK_EDIT ) ) ) { $content_defaults = WPML_Media::get_setting( 'new_content_settings' ); $wpml_value = isset( $content_defaults['always_translate_media'] ) && $content_defaults['always_translate_media']; $args = wp_parse_args( stripslashes( urldecode( $_REQUEST['mlaAddNewBulkEditFormString'] ) ) ); if ( isset( $args['mla_always_translate_media'] ) ) { $form_value = 'true' == $args['mla_always_translate_media']; } else { $form_value = $wpml_value; } if ( $form_value !== $wpml_value ) { self::$wpml_content_defaults = $content_defaults; $content_defaults['always_translate_media'] = $form_value; WPML_Media::update_setting( 'new_content_settings', $content_defaults ); } else { self::$wpml_content_defaults = NULL; } } } /** * Adds the term-specific language code to each entry in the Media/Taxonomy "Attachments" column * * @since 2.61 * * @param NULL $filter_content NULL, indicating no changes to the current content. * @param object $tax_object Defines the current taxonomy. * @param object $term Defines the current term. * @param string $column_text MLA-computed count or "click to search". * @param boolean $count_terms True to compute counts. */ public static function mla_taxonomy_column_final( $filter_content, $tax_object, $term, $column_text, $count_terms ) { global $sitepress; $details = $sitepress->get_element_language_details( $term->term_taxonomy_id, 'tax_' . $tax_object->name ); if ( !empty( $details ) ) { $language_code = $details->language_code; } else { $language_code = 'all'; } return sprintf( '%2$s', esc_url( add_query_arg( array( 'page' => MLACore::ADMIN_PAGE_SLUG, 'mla-tax' => $tax_object->name, 'mla-term' => $term->slug, 'heading_suffix' => urlencode( $tax_object->label . ':' . $term->name ), 'lang' => $language_code ), 'upload.php' ) ), $column_text ); } /** * Captures the existing term assignments before the * Media Manager Modal Window ATTACHMENT DETAILS taxonomy meta boxes updates * * @since 2.11 * * @param object the current post */ public static function mla_media_modal_begin_update_compat_fields( $post ) { $post_id = $post->ID; MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_media_modal_begin_update_compat_fields( {$post_id} ) post = " . var_export( $post, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); // Accumulate for possible term_assignment or term_synchronization self::_build_existing_terms( $post_id ); } // mla_media_modal_begin_update_compat_fields /** * Applies Term Assignment to the terms assigned to one * Media Manager Modal Window ATTACHMENT DETAILS taxonomy * * @since 2.11 * * @param array assigned term id/name values * @param string taxonomy slug * @param object taxonomy object * @param integer current post ID */ public static function mla_media_modal_update_compat_fields_terms( $terms, $key, $value, $post_id ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_media_modal_update_compat_fields_terms( {$key}, {$post_id} ) terms = " . var_export( $terms, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); if ( 'checked' == MLACore::mla_get_option( 'term_assignment', false, false, MLA_WPML::$mla_language_option_definitions ) ) { if ( $value->hierarchical ) { $tax_inputs = array( $key => $terms ); } else { $tax_inputs = array( $key => implode( ',', $terms ) ); } self::_build_tax_input( $post_id, $tax_inputs, NULL, true ); $tax_inputs = self::_apply_tax_input( $post_id ); $terms = $tax_inputs[ $key ]; } // term_assignment return $terms; } // mla_media_modal_update_compat_fields_terms /** * Applies Term Synchronization after the * Media Manager Modal Window taxonomy updates * * @since 2.11 * * @param string HTML markup for the taxonomy meta box elements * @param array supported taxonomy objects * @param object current post object */ public static function mla_media_modal_end_update_compat_fields( $results, $taxonomies, $post ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_media_modal_end_update_compat_fields( {$post->ID} ) taxonomies = " . var_export( $taxonomies, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); /* * Synchronize the changes to all other translations */ self::_apply_term_synchronization( $post->ID ); return $results; } // mla_media_modal_end_update_compat_fields /** * Captures the Quick Edit "before update" term assignments * * @since 2.11 * * @param array $item_content NULL, to indicate no handler. * @param integer $post_id the affected attachment. * * @return object updated $item_content. NULL if no handler, otherwise * ( 'message' => error or status message(s), 'body' => '', * 'prevent_default' => true to bypass the MLA handler ) */ public static function mla_list_table_inline_action( $item_content, $post_id ) { global $sitepress; MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_list_table_inline_action( {$post_id} )", MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); // WPML does not preserve the current language for the Quick Edit Ajax action $referer = wp_get_referer(); if ( $referer ) { wp_parse_str( $referer, $args ); if ( isset( $args['lang'] ) ) { $sitepress->switch_lang( $args['lang'], true ); } } self::_build_existing_terms( $post_id ); if ( isset( $_REQUEST['action'] ) && 'mla-inline-edit-scripts' === $_REQUEST['action'] && isset( $_REQUEST['tax_input'] ) ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_list_table_inline_action( {$post_id} ) Quick Edit initial \$_REQUEST['tax_input'] = " . var_export( $_REQUEST['tax_input'], true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); if ( 'checked' == MLACore::mla_get_option( 'term_assignment', false, false, MLA_WPML::$mla_language_option_definitions ) ) { // Quick Edit calls update_single_item right after this filter self::_build_tax_input( $post_id, $_REQUEST['tax_input'], NULL, true ); $_REQUEST['tax_input'] = self::_apply_tax_input( $post_id ); } MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_list_table_inline_action( {$post_id} ) Quick Edit final \$_REQUEST['tax_input'] = " . var_export( $_REQUEST['tax_input'], true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); } return $item_content; } // mla_list_table_inline_action /** * Captures the Bulk Edit, "Upload New Media" parameters * * @since 2.11 * * @param array $request bulk action request parameters, including ['mla_bulk_action_do_cleanup']. * @param string $bulk_action the requested action. * @param array $custom_field_map [ slug => field_name ] * * @return array updated bulk action request parameters */ public static function mla_list_table_bulk_action_initial_request( $request, $bulk_action, $custom_field_map ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_list_table_bulk_action_initial_request( {$bulk_action} ) request = " . var_export( $request, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); /* * Check for Bulk Edit processing during Upload New Media */ if ( ! empty( $_REQUEST['mlaAddNewBulkEditFormString'] ) ) { /* * It is now safe to restore the WPML option settings if they have been * changed for this upload */ if ( ! empty( self::$wpml_content_defaults ) ) { WPML_Media::update_setting( 'new_content_settings', self::$wpml_content_defaults ); } /* * Suppress WPML processing in wpml-media.class.php function save_attachment_actions, * which wipes out attachment meta data. */ global $action; $action = 'upload-plugin'; } self::$bulk_edit_request = $request; self::$bulk_edit_map = $custom_field_map; return $request; } // mla_list_table_bulk_action_initial_request /** * Custom Field Map during Bulk Edit, "Upload New Media" * * @since 2.11 * * @var array [ id ] => field name */ private static $bulk_edit_map = NULL; /** * Bulk Edit parameters during "Upload New Media" * * @since 2.11 * * @var array [ field ] => new value */ private static $bulk_edit_request = NULL; /** * Converts Bulk Edit taxonomy inputs to language-specific values * * @since 2.11 * * @param array $request bulk action request parameters, including ['mla_bulk_action_do_cleanup']. * @param string $bulk_action the requested action. * @param integer $post_id the affected attachment. * @param array $custom_field_map [ slug => field_name ] * * @return array updated bulk action request parameters */ public static function mla_list_table_bulk_action_item_request( $request, $bulk_action, $post_id, $custom_field_map ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_list_table_bulk_action_item_request( {$post_id} ) request = " . var_export( $request, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); /* * Note that $request may be modified by previous items, so we must return to the initial vlues */ if ( 'edit' == $bulk_action && ( ! empty( self::$bulk_edit_request['tax_input'] ) ) && ( 'checked' == MLACore::mla_get_option( 'term_assignment', false, false, MLA_WPML::$mla_language_option_definitions ) ) ) { self::_build_existing_terms( $post_id ); self::_build_tax_input( $post_id, self::$bulk_edit_request['tax_input'], self::$bulk_edit_request['tax_action'], true ); $request['tax_input'] = self::_apply_tax_input( $post_id ); foreach( self::$bulk_edit_request['tax_action'] as $taxonomy => $action ) { // _apply_tax_input changes a remove to a replace if ( 'remove' == $action ) { $request['tax_action'][ $taxonomy ] = 'replace'; } } } if ( isset( $request['tax_input'] ) ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::bulk_action_item_request( {$bulk_action}, {$post_id} ) \$request['tax_input'] = " . var_export( $request['tax_input'], true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); } else { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::bulk_action_item_request( {$bulk_action}, {$post_id} ) \$request['tax_input'] NOT SET", MLACore::MLA_DEBUG_CATEGORY_AJAX ); } if ( isset( $request['tax_action'] ) ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::bulk_action_item_request( {$bulk_action}, {$post_id} ) \$request['tax_action'] = " . var_export( $request['tax_action'], true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); } else { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::bulk_action_item_request( {$bulk_action}, {$post_id} ) \$request['tax_action'] NOT SET", MLACore::MLA_DEBUG_CATEGORY_AJAX ); } return $request; } // mla_list_table_bulk_action_item_request /** * Add a duplicate translation for an item, then redirect to the Media/Edit Media screen * * @since 2.11 * * @param string $mla_admin_action the requested action. * @param integer $mla_item_ID zero (0), or the affected attachment. */ public static function mla_list_table_custom_admin_action( $mla_admin_action, $mla_item_ID ) { if ( 'wpml_create_translation' == $mla_admin_action ) { $new_item = WPML_Media::create_duplicate_attachment( $mla_item_ID, $_REQUEST['mla_parent_ID'], $_REQUEST['lang'] ); $view_args = isset( $_REQUEST['mla_source'] ) ? array( 'mla_source' => $_REQUEST['mla_source']) : array(); wp_redirect( add_query_arg( $view_args, admin_url( 'post.php' ) . '?action=edit&post=' . $new_item . '&message=201' ), 302 ); exit; } } // mla_list_table_custom_admin_action /** * Adds translation update message for display at the top of the Edit Media screen * * @since 2.11 * * @param array messages for the Edit screen * * @return array updated messages */ public static function post_updated_messages( $messages ) { if ( isset( $messages['attachment'] ) ) { $messages['attachment'][201] = __( 'Duplicate translation created; update as desired.', 'media-library-assistant' ); } return $messages; } // mla_post_updated_messages_filter /** * Force "All languages" mode for IPTC/EXIF mapping, which uses mla_get_shortcode_attachments * * @since 2.20 * * @param boolean true if the post_type is language-specific * @param string the post type */ public static function pre_wpml_is_translated_post_type_filter( $translated, $type ) { return $type === 'attachment' ? false : $translated; } /** * Force "All languages" mode for IPTC/EXIF mapping, which uses mla_get_shortcode_attachments * * @since 2.20 * * @param string what kind of mapping action is starting: * single_custom, single_iptc_exif, bulk_custom, bulk_iptc_exif, * create_metadata, update_metadata, custom_fields, custom_rule, * iptc_exif_standard, iptc_exif_taxonomy, iptc_exif_custom, * iptc_exif_custom_rule * @param mixed Attachment ID or NULL, depending on scope */ public static function mla_begin_mapping( $source, $post_id = NULL ) { if ( in_array( $source, array( 'create_metadata', 'single_iptc_exif', 'iptc_exif_standard', 'iptc_exif_taxonomy', 'iptc_exif_custom', 'iptc_exif_custom_rule' ) ) ) { /* * Defined in /sitepress-multilingual-cms/sitepress.class.php */ add_filter( 'pre_wpml_is_translated_post_type', 'MLA_WPML::pre_wpml_is_translated_post_type_filter', 100, 2 ); add_filter( 'mla_mapping_rule', 'MLA_WPML::mla_mapping_rule', 10, 4 ); } } // mla_begin_mapping /** * Saves the current mapping rule for term creation * * @since 2.20 * * @param array mapping rule * @param integer post ID to be evaluated * @param string category/scope to evaluate against: iptc_exif_standard_mapping, iptc_exif_taxonomy_mapping or iptc_exif_custom_mapping * @param array attachment_metadata, default NULL */ public static function mla_mapping_rule( $setting_value, $post_id, $category, $attachment_metadata ) { return self::$current_mapping_rule = $setting_value; } // mla_mapping_rule /** * Current mapping rule for term creation * * @since 2.20 * * @var array mapping rule */ private static $current_mapping_rule = array(); /** * Manages the creation of new taxonomy terms from metadata values * * @since 2.20 * * @param mixed string or array value returned by the rule * @param string field name or taxonomy name * @param integer post ID to be evaluated * @param string category/scope to evaluate against: iptc_exif_standard_mapping, iptc_exif_taxonomy_mapping or iptc_exif_custom_mapping * @param array attachment_metadata, default NULL * * @return array updated rule EXIF/Template value */ public static function mla_mapping_new_text( $new_text, $setting_key, $post_id, $category, $attachment_metadata ) { global $sitepress; static $replicate = NULL, $current_language, $taxonomies, $other_languages; if ( 'iptc_exif_taxonomy_mapping' !== $category ) { return $new_text; } if ( is_null( $replicate ) ) { $replicate = ( 'checked' == MLACore::mla_get_option( 'term_mapping_replication', false, false, MLA_WPML::$mla_language_option_definitions ) ); $current_language = $sitepress->get_current_language(); $taxonomies = $sitepress->get_translatable_taxonomies( true, 'attachment' ); $other_languages = $sitepress->get_active_languages(); unset( $other_languages[ $current_language ] ); } if ( ( ! empty( $new_text ) ) && in_array( $setting_key, $taxonomies ) ) { $language_details = $sitepress->get_element_language_details( $post_id, 'post_attachment' ); $item_language = $language_details->language_code; // Find the parent term and its translations if ( isset( self::$current_mapping_rule['parent'] ) ) { if ( $parent_term = absint( self::$current_mapping_rule['parent'] ) ) { $parent_term = self::_get_relevant_term( 'id', $parent_term, $setting_key ); } } else { $parent_term = 0; } $new_terms = array(); foreach( $new_text as $new_name ) { $relevant_term = self::_get_relevant_term( 'name', $new_name, $setting_key ); if ( $relevant_term ) { if ( isset( $relevant_term['translations'][ $item_language ] ) ) { // $new_terms[] = absint( $relevant_term['translations'][ $item_language ]->term_id ); $new_term_id = absint( $relevant_term['translations'][ $item_language ]->term_id ); $new_term = self::_get_relevant_term( 'id', $new_term_id, $setting_key ); $new_terms[] = $new_term['term']->name; } } else { // Always create the new term in the current language if ( $parent_term && isset( $parent_term['translations'][ $current_language ] ) ) { $parent = $parent_term['translations'][ $current_language ]->term_id; } else { $parent = 0; } $args = array( 'taxonomy' => $setting_key, 'lang_code' => $current_language, 'term' => $new_name, 'parent' => $parent, ); $res = WPML_Terms_Translations::create_new_term( $args ); // Add translations in the other languages? if ( $replicate ) { $trid = $sitepress->get_element_trid( $res['term_taxonomy_id'], 'tax_' . $setting_key ); $original_term = get_term( $res['term_id'], $setting_key, OBJECT, 'no' ); $args = array( 'trid' => $trid, 'source_language' => $current_language, 'term' => $new_name, 'original_id' => $res['term_id'], 'original_tax_id' => $res['term_taxonomy_id'], 'taxonomy' => $setting_key, 'update_translations' => true ); foreach( $other_languages as $language => $language_details ) { if ( $parent_term && isset( $parent_term['translations'][ $language ] ) ) { $parent = $parent_term['translations'][ $language ]->term_id; } else { $parent = 0; } $translated_slug = apply_filters( 'icl_duplicate_generic_string', $original_term->slug, $language, array( 'context' => 'taxonomy_slug', 'attribute' => $setting_key, 'key' => $original_term->term_id ) ); $translated_slug = WPML_Terms_Translations::term_unique_slug( $translated_slug, $setting_key, $language ); $args['slug'] = $translated_slug; $args['parent'] = $parent; $args['lang_code'] = $language; $res = WPML_Terms_Translations::create_new_term( $args ); } } // replicate // Reload the term with all of its new translations $relevant_term = self::_get_relevant_term( 'name', $new_name, $setting_key, NULL, false, true ); if ( isset( $relevant_term['translations'][ $item_language ] ) ) { // $new_terms[] = absint( $relevant_term['translations'][ $item_language ]->term_id ); $new_term_id = absint( $relevant_term['translations'][ $item_language ]->term_id ); $new_term = self::_get_relevant_term( 'id', $new_term_id, $setting_key ); $new_terms[] = $new_term['term']->name; } } // new term } // foreach new_name MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_mapping_new_text( {$setting_key}, {$post_id} ) \$new_terms = " . var_export( $new_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); return $new_terms; } // translated taxonomy return $new_text; } // mla_mapping_new_text /** * Remove "All languages" filter * * @since 2.20 * * @return void */ public static function mla_end_mapping() { remove_filter( 'pre_wpml_is_translated_post_type', 'MLA_WPML::pre_wpml_is_translated_post_type_filter', 100 ); } // mla_end_mapping /** * Taxonomy terms and translations * * NOTE: WPML uses term_taxonomy_id as the "element_id" in its translations; * Polylang uses term_id as the "element_id". * * @since 2.11 * * @var array [ $term_taxonomy_id ] => array( $term, $details, $translations ) */ private static $relevant_terms = array(); /** * Creates a $relevant_term given a name, taxonomy and language * * @since 2.61 * * @param string $name new term name * @param string $taxonomy slug * @param string $language code/slug */ private static function _create_relevant_term( $name, $taxonomy, $language ) { global $sitepress; $current_language = $sitepress->get_current_language(); $sitepress->switch_lang( $language, true ); $res = wp_insert_term( $name, $taxonomy, array( 'parent' => 0 ) ); // Reload the term with all of its new translations $res = self::_get_relevant_term( 'name', $name, $taxonomy ); $sitepress->switch_lang( $current_language, true ); return $res; } // _create_relevant_term /** * Creates a translation given a $relevant_term and language * * @since 2.61 * * @param string $relevant_term current term * @param string $language code/slug */ private static function _create_relevant_translation( $relevant_term, $language ) { global $sitepress; $details = $sitepress->get_element_language_details( $relevant_term['term']->term_taxonomy_id, 'tax_' . $relevant_term['term']->taxonomy ); $args = array( 'trid' => $details->trid, 'taxonomy' => $relevant_term['term']->taxonomy, 'lang_code' => $language, ); $res = WPML_Terms_Translations::create_automatic_translation( $args ); // Reload the term with its new translation return self::_get_relevant_term( 'id', $res['term_id'], $taxonomy ); } // _create_relevant_translation /** * Adds a term and its translations to $relevant_terms * * @since 2.11 * @uses MLA_WPML::$relevant_terms * * @param object WordPress term object * @param object Sitepress translations object; optional * @param boolean Ignore the Sitepress terms cache; optional */ private static function _add_relevant_term( $term, $translations = NULL, $skip_cache = false ) { global $sitepress; if ( ! is_object( $term ) ) { return false; } if ( ! array_key_exists( $term->term_taxonomy_id, self::$relevant_terms ) ) { $taxonomy_name = 'tax_' . $term->taxonomy; $details = $sitepress->get_element_language_details( $term->term_taxonomy_id, $taxonomy_name ); if ( empty( $translations ) ) { $translations = $sitepress->get_element_translations( $details->trid, $taxonomy_name, false, false, $skip_cache ); if ( empty( $translations ) ) { $language_code = $sitepress->get_default_language(); $translations[ $language_code ] = (object) array( 'element_id' => $term->term_id ); } } self::$relevant_terms[ $term->term_taxonomy_id ]['term'] = $term; self::$relevant_terms[ $term->term_taxonomy_id ]['translations'] = $translations; } return self::$relevant_terms[ $term->term_taxonomy_id ]; } // _add_relevant_term /** * Finds a $relevant_term (if defined) given a key and (optional) a language * * @since 2.11 * @uses MLA_WPML::$relevant_terms * * @param string $field to search in; 'id', 'name', or 'term_taxonomy_id' * @param mixed $value to search for; integer, string or integer * @param string $taxonomy to search in; slug * @param string $language code; string; optional * @param boolean $test_only false (default) to add missing term, true to leave term out * @param boolean Ignore the Sitepress terms cache; optional */ private static function _get_relevant_term( $field, $value, $taxonomy, $language = NULL, $test_only = false, $skip_cache = false ) { /* * WordPress encodes special characters, e.g., "&" as HTML entities in term names */ if ( 'name' == $field ) { $value = _wp_specialchars( $value ); } $relevant_term = false; foreach( self::$relevant_terms as $term_taxonomy_id => $candidate ) { if ( $taxonomy != $candidate['term']->taxonomy ) { continue; } switch ( $field ) { case 'id': if ( $value == $candidate['term']->term_id ) { $relevant_term = $candidate; } break; case 'name': if ( $value == $candidate['term']->name ) { $relevant_term = $candidate; } break; case 'term_taxonomy_id': if ( $value == $term_taxonomy_id ) { $relevant_term = $candidate; } break; } // field if ( ! empty( $relevant_term ) ) { break; } } // relevant term if ( ( false === $relevant_term ) && $test_only ) { return false; } // If no match, try to add it and its translations if ( ( false === $relevant_term ) && $candidate = get_term_by( $field, $value, $taxonomy ) ) { $relevant_term = self::_add_relevant_term( $candidate, NULL, $skip_cache ); foreach ( $relevant_term['translations'] as $translation ) { if ( array_key_exists( $translation->element_id, self::$relevant_terms ) ) { continue; } $term_object = get_term_by( 'term_taxonomy_id', $translation->element_id, $taxonomy ); self::_add_relevant_term( $term_object, $relevant_term['translations'], $skip_cache ); } // translation } // new term // Find the language-specific value, if requested if ( $relevant_term && ! empty( $language ) ) { if ( $relevant_term && array_key_exists( $language, $relevant_term['translations'] ) ) { $relevant_term = self::$relevant_terms[ $relevant_term['translations'][ $language ]->element_id ]; } else { $relevant_term = false; } } return $relevant_term; } /** * Taxonomy terms for the current item translation in the database * * @since 2.11 * * @var array ['element_id'] => $post_id; * [ 'language_code' ] => WPML item language or default language, e.g., 'en' * [ 'slug' ] => Polylang item language or default language, e.g., 'en' * [ $language ][ translation_details ] * [ $language ][ $taxonomy ][ $term_taxonomy_id ] => $term */ private static $existing_terms = array( 'element_id' => 0 ); /** * Build the $existing_terms array * * Takes each translatable taxonomy and builds an array of * language-specific term_id to term_id/term_name mappings * for terms already assigned to the item translation. * * @since 2.11 * @uses MLA_WPML::$existing_terms * @uses MLA_WPML::$relevant_terms * * @param integer $post_id ID of the current post * */ private static function _build_existing_terms( $post_id ) { global $sitepress; if ( $post_id == self::$existing_terms['element_id'] ) { return; } $language_details = (array) $sitepress->get_element_language_details( $post_id, 'post_attachment' ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_build_existing_terms( {$post_id} ) \$sitepress->get_element_language_details = " . var_export( $language_details, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); // WPML doesn't fill in $language_details if WPML Media is not installed if ( ( ! is_array( $language_details ) ) || empty( $language_details ) ) { $language_details = array( 'trid' => NULL, 'language_code' => $sitepress->get_default_language(), 'source_language_code' => NULL ); } $element_translations = $sitepress->get_element_translations( $language_details['trid'], 'post_attachment' ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_build_existing_terms( {$post_id} ) \$sitepress->get_element_translations() = " . var_export( $element_translations, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); $translations = array(); if ( $language_details['trid'] ) { foreach ( $element_translations as $language_code => $translation ) { $translations[ $language_code ] = (array) $translation; } } if ( empty( $translations ) ) { $translations[ $language_details['language_code'] ] = array( 'element_id' => $post_id ); } self::$existing_terms = array_merge( array( 'element_id' => $post_id ), $language_details, $translations ); $taxonomies = $sitepress->get_translatable_taxonomies( true, 'attachment' ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_build_existing_terms( {$post_id} ) \$sitepress->get_translatable_taxonomies() = " . var_export( $taxonomies, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); /* * Find all assigned terms and build term_master array */ $current_language = $sitepress->get_current_language(); foreach ( $translations as $language_code => $translation ) { $sitepress->switch_lang( $language_code, true ); foreach ( $taxonomies as $taxonomy_name ) { if ( $terms = get_the_terms( $translation['element_id'], $taxonomy_name ) ) { foreach ( $terms as $term ) { self::_add_relevant_term( $term ); self::$existing_terms[ $language_code ][ $taxonomy_name ][ $term->term_taxonomy_id ] = $term; } // term } else { self::$existing_terms[ $language_code ][ $taxonomy_name ] = array(); } } // taxonomy } // translation /* * Add missing translated terms to the term_master array */ foreach ( self::$relevant_terms as $term ) { foreach ( $term['translations'] as $translation ) { if ( array_key_exists( $translation->element_id, self::$relevant_terms ) ) { continue; } $sitepress->switch_lang( $translation->language_code, true ); $term_object = get_term_by( 'term_taxonomy_id', $translation->element_id, $term['term']->taxonomy ); self::_add_relevant_term( $term_object, $term['translations'] ); } // translation } // term $sitepress->switch_lang( $current_language, true ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_build_existing_terms( {$post_id} ) self::\$existing_terms = " . var_export( self::$existing_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_build_existing_terms( {$post_id} ) self::\$relevant_terms = " . var_export( self::$relevant_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); return; } /** * Update the $existing_terms array * * Takes each translatable taxonomy and rebuilds the array of * language-specific term_id to term_id/term_name mappings * for the "current translation" represented by the $post_id. * * @since 2.11 * @uses MLA_WPML::$existing_terms * @uses MLA_WPML::$relevant_terms * * @param integer $post_id ID of the current post * * @return array ( taxonomy => term assignments ) before the update */ private static function _update_existing_terms( $post_id ) { global $sitepress; MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_update_existing_terms( {$post_id} ) initial self::\$existing_terms = " . var_export( self::$existing_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_update_existing_terms( {$post_id} ) initial self::\$relevant_terms = " . var_export( self::$relevant_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); if ( $post_id != self::$existing_terms['element_id'] ) { return false; } $language_code = self::$existing_terms['language_code']; if ( isset( self::$existing_terms[ $language_code ] ) ) { $translation = self::$existing_terms[ $language_code ]; } else { $translation = array(); } $terms_before = array(); /* * Find all assigned terms and update the array */ $taxonomies = $sitepress->get_translatable_taxonomies( true, 'attachment' ); foreach ( $taxonomies as $taxonomy_name ) { $terms_before[ $taxonomy_name ] = isset( $translation[ $taxonomy_name ] ) ? $translation[ $taxonomy_name ] : array(); $translation[ $taxonomy_name ] = array(); if ( $terms = get_the_terms( $post_id, $taxonomy_name ) ) { foreach ( $terms as $term ) { self::_add_relevant_term( $term ); $translation[ $taxonomy_name ][ $term->term_taxonomy_id ] = $term; } // term } } // taxonomy self::$existing_terms[ $language_code ] = $translation; /* * Add missing translated terms to the term_master array */ foreach ( self::$relevant_terms as $term ) { foreach ( $term['translations'] as $translation ) { if ( array_key_exists( $translation->element_id, self::$relevant_terms ) ) { continue; } $term_object = get_term_by( 'term_taxonomy_id', $translation->element_id, $term['term']->taxonomy ); self::_add_relevant_term( $term_object, $term['translations'] ); } // translation } // term MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_update_existing_terms( {$post_id} ) final self::\$existing_terms = " . var_export( self::$existing_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_update_existing_terms( {$post_id} ) final self::\$relevant_terms = " . var_export( self::$relevant_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); return $terms_before; } /** * Replacement tax_input values in all languages * * @since 2.11 * * @var array ['tax_input_post_id'] => $post_id; * [ $language ][ $taxonomy ] => array of integer term_ids (hierarchical) * [ $language ][ $taxonomy ] => comma-delimited string of term names (flat) */ private static $tax_input = array( 'tax_input_post_id' => 0 ); /** * Build the $tax_input array * * Takes each term from the $tax_inputs parameter and builds an array of * language-specific term_id to term_id/term_name mappings for all languages. * * @since 2.11 * @uses MLA_WPML::$tax_input * @uses MLA_WPML::$existing_terms * * @param integer $post_id ID of the current post * @param array $tax_inputs 'tax_input' request parameter * @param array $tax_actions 'tax_action' request parameter * @param boolean $add_new_names Add term and translations for new names */ private static function _build_tax_input( $post_id, $tax_inputs = NULL, $tax_actions = NULL, $add_new_names = false ) { global $sitepress; static $new_names = array(); if ( $post_id == self::$tax_input['tax_input_post_id'] ) { return; } self::$tax_input = array( 'tax_input_post_id' => $post_id ); $active_languages = $sitepress->get_active_languages(); // See if we are cloning/"replacing" the existing assignments if ( ( NULL == $tax_inputs ) && ( NULL == $tax_actions ) && isset( self::$existing_terms['element_id'] ) && ($post_id == self::$existing_terms['element_id'] ) ) { $translation = self::$existing_terms[ self::$existing_terms['language_code'] ]; $taxonomies = $sitepress->get_translatable_taxonomies( true, 'attachment' ); $tax_inputs = array(); $no_terms = true; foreach ( $taxonomies as $taxonomy_name ) { $terms = isset( $translation[ $taxonomy_name ] ) ? $translation[ $taxonomy_name ] : array(); if ( ! empty( $terms ) ) { $no_terms = false; $input_terms = array(); foreach ( $terms as $term ) { $input_terms[] = $term->term_id; } $tax_inputs[ $taxonomy_name ] = $input_terms; } else { $tax_inputs[ $taxonomy_name ] = array(); } } // taxonomy_name if ( $no_terms ) { foreach( $active_languages as $language => $language_details ) { self::$tax_input[ $language ] = array(); } return; } } // cloning foreach ( $tax_inputs as $taxonomy => $terms ) { $tax_action = isset( $tax_actions[ $taxonomy ] ) ? $tax_actions[ $taxonomy ] : 'replace'; $input_terms = array(); // hierarchical taxonomy => array of term_id integer values; flat => comma-delimited string of names if ( $hierarchical = is_array( $terms ) ) { foreach( $terms as $term ) { if ( 0 == $term ) { continue; } $relevant_term = self::_get_relevant_term( 'term_id', $term, $taxonomy ); if ( isset( $relevant_term['translations'] ) ) { foreach ( $relevant_term['translations'] as $language => $translation ) { if ($translated_term = self::_get_relevant_term( 'term_taxonomy_id', $translation->element_id, $taxonomy ) ) { $input_terms[ $language ][ $translation->element_id ] = $translated_term['term']; } } // for each language } // translations exist } // foreach term } else { // Convert names to an array $term_names = array_map( 'trim', explode( ',', $terms ) ); foreach ( $term_names as $term_name ) { if ( ! empty( $term_name ) ) { $relevant_term = self::_get_relevant_term( 'name', $term_name, $taxonomy ); // Add new term or translation if allowed and required if ( $add_new_names ) { if ( false === $relevant_term ) { $relevant_term = self::_create_relevant_term( $term_name, $taxonomy, self::$existing_terms['language_code'] ); $new_names[ $term_name ][ self::$existing_terms['language_code'] ] = $relevant_term['term']->term_id; } else { $language = self::$existing_terms['language_code']; if ( !array_key_exists( self::$existing_terms['language_code'], $relevant_term['translations'] ) && isset( $new_names[ $term_name ] ) ) { $relevant_term = self::_create_relevant_translation( $relevant_term, self::$existing_terms['language_code'] ); $new_names[ $term_name ][ self::$existing_terms['language_code'] ] = $relevant_term['term']->term_id; } } } if ( isset( $relevant_term['translations'] ) ) { foreach ( $relevant_term['translations'] as $language => $translation ) { if ( $translated_term = self::_get_relevant_term( 'term_taxonomy_id', $translation->element_id, $taxonomy ) ) { $input_terms[ $language ][ $translation->element_id ] = $translated_term['term']; } } // for each language } // translations exist } // not empty } // foreach name } // flat taxonomy foreach( $active_languages as $language => $language_details ) { /* * Apply the tax_action to the terms_before to find the terms_after */ $term_changes = isset( $input_terms[ $language ] ) ? $input_terms[ $language ] : array(); if ( 'replace' == $tax_action ) { $terms_after = $term_changes; } else { $terms_after = isset( self::$existing_terms[ $language ][ $taxonomy ] ) ? self::$existing_terms[ $language ][ $taxonomy ] : array(); foreach( $term_changes as $term_taxonomy_id => $input_term ) { if ( 'add' == $tax_action ) { $terms_after[ $term_taxonomy_id ] = $input_term; } else { unset( $terms_after[ $term_taxonomy_id ] ); } } // input_term } /* * Convert terms_after to tax_input format */ $term_changes = array(); foreach( $terms_after as $input_term ) { $term_changes[] = $input_term->term_id; } self::$tax_input[ $language ][ $taxonomy ] = $term_changes; } // language } // foreach taxonomy MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_build_tax_input( {$post_id} ) self::\$tax_input = " . var_export( self::$tax_input, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_build_tax_input( {$post_id} ) self::\$relevant_terms = " . var_export( self::$relevant_terms, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); } // _build_tax_input /** * Filter the $tax_input array to a specific language * * @since 2.11 * @uses MLA_WPML::$tax_input * @uses MLA_WPML::$existing_terms * * @param integer $post_id ID of the post to be updated * @param string $post_language explicit language_code; optional * * @return array language-specific $tax_inputs */ private static function _apply_tax_input( $post_id, $post_language = NULL ) { global $sitepress; if ( NULL == $post_language ) { if ( isset( self::$existing_terms['element_id'] ) && $post_id == self::$existing_terms['element_id'] ) { $post_language = self::$existing_terms['language_code']; } else { $post_language = $sitepress->get_element_language_details( $post_id, 'post_attachment' ); $post_language = $post_language->language_code; } } MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_apply_tax_input( {$post_id} ) \$post_language = " . var_export( $post_language, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_apply_tax_input( {$post_id} ) self::\$tax_input[ \$post_language ] = " . var_export( self::$tax_input[ $post_language ], true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); return self::$tax_input[ $post_language ]; } // _apply_tax_input /** * Compute Term Synchronization replacement $tax_inputs * * Assumes the "current post" in $existing_terms is the source * and $existing_terms contains the target translation * * @since 2.11 * @uses MLA_WPML::$existing_terms * * @param string $language the target translation code * * @return array $tax_inputs for Term Synchronization */ private static function _apply_synch_input( $language ) { global $sitepress; // Make sure there IS a target translation if ( empty( self::$existing_terms[ $language ] ) ) { return false; } $source_language = self::$existing_terms['language_code']; $taxonomies = $sitepress->get_translatable_taxonomies( true, 'attachment' ); /* * Find all source terms with a destination equivalent, record destination equivalent */ $new_terms = array(); foreach ( $taxonomies as $taxonomy ) { $new_terms[ $taxonomy ] = array(); foreach( self::$existing_terms[ $source_language ][ $taxonomy ] as $ttid => $term ) { $source_term = self::_get_relevant_term( 'term_taxonomy_id', $ttid, $taxonomy ); if ( isset( $source_term['translations'][ $language ] ) ) { $dest_term = self::_get_relevant_term( 'id', $source_term['translations'][ $language ]->term_id, $taxonomy ); $new_terms[ $taxonomy ][ $dest_term['term']->term_taxonomy_id ] = $dest_term['term']; } } } /* * Find all destination terms with a source equivalent, record destination equivalent */ $old_terms = array(); foreach ( $taxonomies as $taxonomy ) { $old_terms[ $taxonomy ] = array(); foreach( self::$existing_terms[ $language ][ $taxonomy ] as $ttid => $term ) { $source_term = self::_get_relevant_term( 'term_taxonomy_id', $ttid, $taxonomy ); if ( isset( $source_term['translations'][ $source_language ] ) ) { $dest_term = self::_get_relevant_term( 'id', $source_term['translations'][ $source_language ]->term_id, $taxonomy ); $old_terms[ $taxonomy ][ $dest_term['term']->term_taxonomy_id ] = $dest_term['term']; } } } /* * Remove terms in common, leaving new_terms => add, old_terms => remove */ foreach ( $old_terms as $taxonomy => $terms ) { foreach ( $terms as $ttid => $term ) { if ( isset( $new_terms[ $taxonomy ][ $ttid ] ) ) { unset( $old_terms[ $taxonomy ][ $ttid ] ); unset( $new_terms[ $taxonomy ][ $ttid ] ); } } // terms } // taxonomies /* * Compute "replace" tax_inputs for the target translation */ $translation = self::$existing_terms[ $language ]; $synch_inputs = array(); foreach ( $old_terms as $taxonomy => $terms ) { $translation_terms = isset( $translation[ $taxonomy ] ) ? $translation[ $taxonomy ] : array(); $terms_changed = false; // Remove common terms foreach ( $old_terms[ $taxonomy ] as $ttid => $term ) { if ( isset( self::$relevant_terms[ $ttid ]['translations'][ $language ] ) ) { $ttid = self::$relevant_terms[ $ttid ]['translations'][ $language ]->element_id; if ( isset( $translation_terms[ $ttid ] ) ) { unset( $translation_terms[ $ttid ] ); $terms_changed = true; } } } // Add common terms foreach ( $new_terms[ $taxonomy ] as $ttid => $term ) { if ( isset( self::$relevant_terms[ $ttid ]['translations'][ $language ] ) ) { $term_translation = self::$relevant_terms[ $ttid ]['translations'][ $language ]; $ttid = $term_translation->element_id; if ( ! isset( $translation_terms[ $ttid ] ) ) { $translation_terms[ $ttid ] = (object) array( 'term_id' => absint( $term_translation->term_id ), 'name' => $term_translation->name ); $terms_changed = true; } } } if ( $terms_changed ) { $synch_inputs[ $taxonomy ] = $translation_terms; } } // taxonomies /* * Convert synch terms to $tax_inputs format */ $tax_inputs = array(); foreach ( $synch_inputs as $taxonomy_name => $terms ) { $taxonomy = get_taxonomy( $taxonomy_name ); $input_terms = array(); foreach ( $terms as $term ) { $input_terms[] = $term->term_id; } $tax_inputs[ $taxonomy_name ] = $input_terms; } // synch_inputs $post_id = self::$existing_terms[ $language ]['element_id']; MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_apply_synch_input( {$post_id} ) \$language = " . var_export( $language, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::_apply_synch_input( {$post_id} ) \$tax_inputs = " . var_export( $tax_inputs, true ), MLACore::MLA_DEBUG_CATEGORY_AJAX ); return $tax_inputs; } // _apply_synch_input /** * Apply Term Synchronization * * @since 2.15 * @uses MLA_WPML::$existing_terms * * @param integer $post_id the item we're synchronizing to * * @return array $tax_inputs for Term Synchronization */ private static function _apply_term_synchronization( $post_id ) { global $sitepress; if ( 'checked' == MLACore::mla_get_option( 'term_synchronization', false, false, MLA_WPML::$mla_language_option_definitions ) ) { /* * Update terms because they have changed */ $terms_before = self::_update_existing_terms( $post_id ); // $tax_input is a convenient source of language codes; ignore $tax_inputs $current_language = $sitepress->get_current_language(); foreach( self::$tax_input as $language => $tax_inputs ) { /* * Skip the language we've already updated */ if ( ( ! isset( self::$existing_terms[ $language ] ) ) || ( self::$existing_terms[ 'language_code' ] == $language ) ) { continue; } $sitepress->switch_lang( $language, true ); $tax_inputs = self::_apply_synch_input( $language ); if ( ! empty( $tax_inputs ) ) { $translation = self::$existing_terms[ $language ]['element_id']; MLAData::mla_update_single_item( $translation, array(), $tax_inputs ); } } // translation $sitepress->switch_lang( $current_language, true ); } // do synchronization } /** * Applies Term Synchronization after item updates * * @since 2.15 * * @param integer $post_id ID of the item that was updated. * @param integer $result Zero if the update failed else ID of the item that was updated. */ public static function mla_updated_single_item( $post_id, $result ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_updated_single_item( {$post_id}, {$result} )", MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); if ( self::$existing_terms['element_id'] == $post_id ) { /* * Synchronize the changes to all other translations */ self::_apply_term_synchronization( $post_id ); } } /** * WPML Option settings to restore when always_translate_media is changed in * Bulk Edit on Upload area * * @since 2.20 * * @var array NULL or ( always_translate_media, duplicate_media, duplicate_featured ) */ private static $wpml_content_defaults = NULL; /** * Duplicates created during media upload * * @since 2.11 * * @var array [ $post_id ] => $language; */ private static $duplicate_attachments = array(); /** * True while fixing and mapping duplicates * * @since 2.20 * * @var boolean */ private static $updating_duplicates = false; /** * Copies taxonomy terms from the source item to the new translated item * * @since 2.11 * * @param integer ID of the source item * @param integer ID of the new item */ public static function wpml_media_create_duplicate_attachment( $attachment_id, $duplicated_attachment_id ) { global $sitepress; static $already_adding = 0; MLACore::mla_debug_add( __LINE__ . " MLA_WPML::wpml_media_create_duplicate_attachment( {$attachment_id}, {$duplicated_attachment_id}, {$already_adding} )", MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); if ( $already_adding == $duplicated_attachment_id ) { return; } else { $already_adding = $duplicated_attachment_id; } $language_details = $sitepress->get_element_language_details( $duplicated_attachment_id, 'post_attachment' ); self::$duplicate_attachments [ $duplicated_attachment_id ] = $language_details->language_code; if ( isset( $_REQUEST['mla_admin_action'] ) && 'wpml_create_translation' == $_REQUEST['mla_admin_action'] ) { if ( 'checked' == MLACore::mla_get_option( 'term_synchronization', false, false, MLA_WPML::$mla_language_option_definitions ) ) { // Clone the existing common terms to the new translation self::_build_existing_terms( $attachment_id ); self::_build_tax_input( $attachment_id ); $tax_inputs = self::_apply_tax_input( 0, $language_details->language_code ); } else { $tax_inputs = NULL; } if ( !empty( $tax_inputs ) ) { MLAData::mla_update_single_item( $duplicated_attachment_id, array(), $tax_inputs ); } self::$existing_terms = array( 'element_id' => 0 ); self::$relevant_terms = array(); } // wpml_create_translation } // wpml_media_create_duplicate_attachment /** * Captures "before update" term assignments from the Media/Edit Media screen * * @since 2.13 * * @param WP_Post $post The WP_Post object. * @param array $attachment An array of attachment metadata. */ public static function attachment_fields_to_save( $post, $attachment ) { MLACore::mla_debug_add( __LINE__ . " MLA_WPML::attachment_fields_to_save post = " . var_export( $post, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); if ( 'editpost' == $post['action'] && 'attachment' == $post['post_type'] ) { self::_build_existing_terms( $post['post_ID'] ); } return $post; } /** * Copy attachment metadata to duplicated items * * This filter is called AFTER MLA mapping rules are applied during * wp_update_attachment_metadata() processing. The postfilter gives you * an opportunity to record or update the metadata after the mapping. * * @since 2.20 * * @param array attachment metadata * @param integer The Post ID of the new/updated attachment * @param array Processing options, e.g., 'is_upload' * * @return array updated attachment metadata */ public static function mla_update_attachment_metadata_postfilter( $data, $post_id, $options ) { $uploading = var_export( ! empty( $options['is_upload'] ), true ); $duplicating = var_export( self::$updating_duplicates, true ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_update_attachment_metadata_postfilter( {$post_id}, {$uploading}, {$duplicating} ) data = " . var_export( $data, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); if ( ! empty( $options['is_upload'] ) && ! self::$updating_duplicates ) { /* * If always_translate_media is set there will be translations present * that have no attachment metadata and have not been mapped. */ if ( ! empty( self::$duplicate_attachments ) ) { self::$updating_duplicates = true; foreach( self::$duplicate_attachments as $id => $language ) { $meta = get_post_meta( $id, '_wp_attachment_metadata', true ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_update_attachment_metadata_postfilter( {$id}, {$language} ) attachment_metadata = " . var_export( $meta, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); if ( is_array( $meta ) ) { continue; } /* * update_post_meta is required twice; first to set it for mapping rules, * second to repair the damage done by WPML synchronize_attachment_metadata */ update_post_meta( $id, '_wp_attachment_metadata', $data ); MLAOptions::mla_add_attachment_action( $id ); MLAOptions::mla_update_attachment_metadata_filter( $data, $id ); update_post_meta( $id, '_wp_attachment_metadata', $data ); $meta = get_post_meta( $id, '_wp_attachment_metadata', false ); MLACore::mla_debug_add( __LINE__ . " MLA_WPML::mla_update_attachment_metadata_postfilter( {$id}, {$language} ) attachment_metadata = " . var_export( $meta, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); } self::$updating_duplicates = false; } } return $data; } /** * Filters taxonomy updates by language for Bulk Edit during Add New Media * and the Media/Edit Media screen * * @since 2.11 * * @param integer ID of the current post */ public static function edit_attachment( $post_id ) { static $already_updating = 0; MLACore::mla_debug_add( __LINE__ . " MLA_WPML::edit_attachment( {$post_id} ) _REQUEST = " . var_export( $_REQUEST, true ), MLACore::MLA_DEBUG_CATEGORY_LANGUAGE ); /* * mla_update_single_item may call this action again, and * nothing should happen while updating duplicate items */ if ( ( $already_updating == $post_id ) || ( self::$updating_duplicates ) ){ return; } else { $already_updating = $post_id; } /* * Check for Bulk Edit during Add New Media */ if ( ! empty( $_REQUEST['mlaAddNewBulkEditFormString'] ) ) { if ( ! empty( self::$bulk_edit_request['tax_input'] ) ) { $tax_inputs = self::$bulk_edit_request['tax_input']; if ( 'checked' == MLACore::mla_get_option( 'term_assignment', false, false, MLA_WPML::$mla_language_option_definitions ) ) { self::_build_tax_input( $post_id, $tax_inputs, self::$bulk_edit_request['tax_action'], true ); $tax_inputs = self::_apply_tax_input( $post_id ); } } else { $tax_inputs = NULL; } $updates = MLA::mla_prepare_bulk_edits( $post_id, self::$bulk_edit_request, self::$bulk_edit_map ); unset( $updates['tax_input'] ); unset( $updates['tax_action'] ); MLAData::mla_update_single_item( $post_id, $updates, $tax_inputs ); return; } // Upload New Media Bulk Edit /* * For the Bulk Edit action on the Media/Assistant screen, only synchronization is needed */ if ( ! ( isset( $_REQUEST['bulk_action'] ) && 'bulk_edit' == $_REQUEST['bulk_action'] ) ) { /* * This is the Media/Edit Media screen. * The category taxonomy (edit screens) is a special case because * post_categories_meta_box() changes the input name */ if ( isset( $_REQUEST['tax_input'] ) ) { $tax_inputs = $_REQUEST['tax_input']; } else { $tax_inputs = array(); } if ( isset( $_REQUEST['post_category'] ) ) { $tax_inputs['category'] = $_REQUEST['post_category']; } if ( isset( $_REQUEST['tax_action'] ) ) { $tax_actions = $_REQUEST['tax_action']; } else { $tax_actions = NULL; } if ( ( ! empty( $tax_inputs ) ) && ( 'checked' == MLACore::mla_get_option( 'term_assignment', false, false, MLA_WPML::$mla_language_option_definitions ) ) ) { self::_build_tax_input( $post_id, $tax_inputs, $tax_actions ); $tax_inputs = self::_apply_tax_input( $post_id ); } if ( ! empty( $tax_inputs ) ) { MLAData::mla_update_single_item( $post_id, array(), $tax_inputs ); } } // Media/Edit Media screen, NOT Bulk Edit } // edit_attachment /** * Modify and extend the substitution values used for the Bulk Edit on Upload form. * * @since 2.20 * * @param array $page_values [ parameter_name => parameter_value ] pairs */ public static function mla_upload_bulk_edit_form_values( $page_values ) { /* * Add markup to the $page_values ['custom_fields'] element for the "Always translate" checkbox */ if ( class_exists( 'WPML_Media' ) ) { $content_defaults = WPML_Media::get_setting( 'new_content_settings' ); if ( isset( $content_defaults['always_translate_media'] ) && $content_defaults['always_translate_media'] ) { $true_selected = 'selected="selected"'; $false_selected = ''; } else { $true_selected = ''; $false_selected = 'selected="selected"'; } $page_values['custom_fields'] .= ' ' . "\n"; } return $page_values; } // mla_upload_bulk_edit_form_values /** * Adds the "Language" tab to the Settings/Media Library Assistant list * * @since 2.11 * * @param array|false The entire tablist ( $tab = NULL ), a single tab entry or false if not found/not allowed. * @param array The entire default tablist * @param string|NULL tab slug for single-element return or NULL to return entire tablist * * @return array updated tablist or single tab element */ public static function mla_get_options_tablist( $results, $mla_tablist, $tab ) { $language_key = 'language'; $language_value = array( 'title' => __( 'Language', 'media-library-assistant' ), 'render' => array( 'MLA_WPML', 'mla_render_language_tab' ) ); if ( $language_key == $tab ) { return $language_value; } return array_merge( $results, array( $language_key => $language_value ) ); } /** * $mla_language_option_definitions defines the language-specific database options and * admin page areas for setting/updating them * * The array must be populated at runtime in MLA_WPML::mla_localize_language_option_definitions(), * because localization calls cannot be placed in the "public static" array definition itself. * * Each option is defined by an array with the elements documented in class-mla-options.php */ public static $mla_language_option_definitions = array (); /** * Localize $mla_language_option_definitions array * * Localization must be done at runtime, and these calls cannot be placed * in the "public static" array definition itself. * * @since 2.11 * * @return void */ public static function mla_localize_language_option_definitions() { MLA_WPML::$mla_language_option_definitions = array ( 'media_assistant_table_header' => array('tab' => 'language', 'name' => __( 'Media/Assistant submenu table', 'media-library-assistant' ), 'type' => 'header'), 'language_column' => array('tab' => 'language', 'name' => __( 'Language Column', 'media-library-assistant' ), 'type' => 'checkbox', 'std' => 'checked', 'help' => __( 'Check this option to add a Language column to the Media/Assistant submenu table.', 'media-library-assistant' )), 'translations_column' => array('tab' => 'language', 'name' => __( 'Translations Column', 'media-library-assistant' ), 'type' => 'checkbox', 'std' => 'checked', 'help' => __( 'Check this option to add a Translation Status column to the Media/Assistant submenu table.', 'media-library-assistant' )), 'term_translation_header' => array('tab' => 'language', 'name' => __( 'Term Management', 'media-library-assistant' ), 'type' => 'header'), 'term_assignment' => array('tab' => 'language', 'name' => __( 'Term Assignment', 'media-library-assistant' ), 'type' => 'checkbox', 'std' => 'checked', 'help' => __( 'Check this option to assign language-specific terms when items are updated.'), 'media-library-assistant' ), 'term_synchronization' => array('tab' => 'language', 'name' => __( 'Term Synchronization', 'media-library-assistant' ), 'type' => 'checkbox', 'std' => 'checked', 'help' => __( 'Check this option to synchronize common terms among all item translations.'), 'media-library-assistant' ), 'term_mapping_replication' => array('tab' => 'language', 'name' => __( 'Term Mapping Replication', 'media-library-assistant' ), 'type' => 'checkbox', 'std' => 'checked', 'help' => __( 'When mapping IPTC/EXIF metadata to taxonomy terms, make them available in all languages.'), 'media-library-assistant' ), ); } /** * Renders the Settings/Media Library Assistant "Language" tab * * @since 2.11 * * @return array ( 'message' => '', 'body' => '' ) */ public static function mla_render_language_tab() { $page_content = array( 'message' => '', 'body' => '

' . __( 'Language', 'media-library-assistant' ) . '

' ); /* * Check for submit buttons to change or reset settings. * Initialize page messages and content. */ if ( !empty( $_REQUEST['mla-language-options-save'] ) ) { check_admin_referer( MLACore::MLA_ADMIN_NONCE_ACTION, MLACore::MLA_ADMIN_NONCE_NAME ); $page_content = self::_save_language_settings( ); } elseif ( !empty( $_REQUEST['mla-language-options-reset'] ) ) { check_admin_referer( MLACore::MLA_ADMIN_NONCE_ACTION, MLACore::MLA_ADMIN_NONCE_NAME ); $page_content = self::_reset_language_settings( ); } else { $page_content = array( 'message' => '', 'body' => '' ); } if ( !empty( $page_content['body'] ) ) { return $page_content; } /* * Find WPML Media plugin status */ $installed = false; $active = false; $wpml_media = SitePress::get_installed_plugins(); if ( isset( $wpml_media['WPML Media'] ) ) { $wpml_media = $wpml_media['WPML Media']; if ( ! empty( $wpml_media['plugin'] ) ) { $installed = true; $active = isset( $wpml_media['file'] ) && is_plugin_active( $wpml_media['file'] ); } } $wpml_media = ''; if ( ! $installed ) { $wpml_media = '

' . __( 'WARNING:', 'media-library-assistant' ) . __( ' WPML Media is not installed.', 'media-library-assistant' ) . '

'; } elseif ( ! $active ) { $wpml_media = '

' . __( 'WARNING:', 'media-library-assistant' ) . __( ' WPML Media is not active.', 'media-library-assistant' ) . '

'; } $page_values = array( 'Language Options' => __( 'Language Options', 'media-library-assistant' ), /* translators: 1: - 4: page subheader values */ 'In this tab' => sprintf( __( 'In this tab you can find a number of options for controlling WPML-specific operations. Scroll down to find options for %1$s and %2$s. Be sure to click "Save Changes" at the bottom of the tab to save any changes you make.', 'media-library-assistant' ), '' . __( 'Media/Assistant submenu table', 'media-library-assistant' ) . '', '' . __( 'Term Management', 'media-library-assistant' ) . '' ), /* translators: 1: Documentation hyperlink */ 'You can find' => sprintf( __( 'You can find more information about multilingual features in the %1$s section of the Documentation.', 'media-library-assistant' ), '' . __( 'WPML & Polylang Multilingual Support; the MLA Language Tab', 'media-library-assistant' ) . '' ), 'WPML Status' => $wpml_media, 'settingsURL' => admin_url('options-general.php'), 'Save Changes' => __( 'Save Changes', 'media-library-assistant' ), 'Delete Language options' => __( 'Delete Language options and restore default settings', 'media-library-assistant' ), '_wpnonce' => wp_nonce_field( MLACore::MLA_ADMIN_NONCE_ACTION, MLACore::MLA_ADMIN_NONCE_NAME, true, false ), '_wp_http_referer' => wp_referer_field( false ), 'Go to Top' => __( 'Go to Top', 'media-library-assistant' ), 'form_url' => admin_url( 'options-general.php' ) . '?page=mla-settings-menu-language&mla_tab=language', 'options_list' => '', ); $options_list = ''; foreach ( MLA_WPML::$mla_language_option_definitions as $key => $value ) { if ( 'language' == $value['tab'] ) { $options_list .= MLASettings::mla_compose_option_row( $key, $value, MLA_WPML::$mla_language_option_definitions ); } } $page_values['options_list'] = $options_list; $page_template = MLACore::mla_load_template( 'admin-display-language-tab.tpl' ); $page_content['body'] = MLAData::mla_parse_template( $page_template, $page_values ); return $page_content; } /** * Save Language settings to the options table * * @since 2.11 * * @uses $_REQUEST * * @return array Message(s) reflecting the results of the operation */ private static function _save_language_settings( ) { $message_list = ''; foreach ( MLA_WPML::$mla_language_option_definitions as $key => $value ) { if ( 'language' == $value['tab'] ) { $message_list .= MLASettings::mla_update_option_row( $key, $value, MLA_WPML::$mla_language_option_definitions ); } // language option } // foreach mla_options $page_content = array( 'message' => __( 'Language settings saved.', 'media-library-assistant' ) . "\n", 'body' => '' ); /* * Uncomment this for debugging. */ //$page_content['message'] .= $message_list; return $page_content; } // _save_language_settings /** * Delete saved settings, restoring default values * * @since 2.11 * * @return array Message(s) reflecting the results of the operation */ private static function _reset_language_settings( ) { $message_list = ''; foreach ( MLA_WPML::$mla_language_option_definitions as $key => $value ) { if ( 'language' == $value['tab'] ) { if ( 'custom' == $value['type'] && isset( $value['reset'] ) ) { $message = call_user_func( array( 'MLA_WPML', $value['reset'] ), 'reset', $key, $value, $_REQUEST ); } elseif ( ('header' == $value['type']) || ('hidden' == $value['type']) ) { $message = ''; } else { MLACore::mla_delete_option( $key, MLA_WPML::$mla_language_option_definitions ); /* translators: 1: option name */ $message = '
' . sprintf( _x( 'delete_option "%1$s"', 'message_list', 'media-library-assistant'), $key ); } $message_list .= $message; } } $page_content = array( 'message' => __( 'Language settings reset to default values.', 'media-library-assistant' ) . "\n", 'body' => '' ); /* * Uncomment this for debugging. */ //$page_content['message'] .= $message_list; return $page_content; } // _reset_language_settings } // Class MLA_WPML /** * Class MLA (Media Library Assistant) WPML List Table adds a reference to an MLA_WPML object * * Extends the MLA_List_Table class. * * @package Media Library Assistant * @since 2.11 */ class MLA_WPML_List_Table extends MLA_List_Table { /** * The MLA_WPML_Table support object * * @since 2.11 * * @var object */ protected $mla_wpml_table = NULL; } /** * Class MLA (Media Library Assistant) WPML Table provides support for the WPML Multilingual CMS * family of plugins, including WPML Media, for an MLA_List_Table object. * * An instance of this class is created in the class MLA_List_Table constructor (class-mla-list-table.php). * * @package Media Library Assistant * @since 2.11 */ class MLA_WPML_Table { /** * Reference to the MLA_List_Table object this object supports * * @since 2.11 * * @var object */ protected $mla_list_table = NULL; /** * The constructor contains add_action and add_filter calls. * * @since 2.11 * * @param object $table The MLA_List_Table object this object supports * * @return void */ function __construct( $table ) { /* * Save a reference to the parent MLA_List_Table object */ $this->mla_list_table = $table; /* * Defined in /wp-admin/includes/class-wp-list-table.php */ // filter "views_{$this->screen->id}" add_filter( 'views_media_page_mla-menu', 'MLA_WPML_Table::mla_views_media_page_mla_menu_filter', 10, 1 ); /* * Defined in /media-library-assistant/includes/class-mla-list-table.php */ add_filter( 'mla_list_table_submenu_arguments', array( $this, 'mla_list_table_submenu_arguments' ), 10, 2 ); add_filter( 'mla_list_table_get_columns', array( $this, 'mla_list_table_get_columns' ), 10, 1 ); add_filter( 'mla_list_table_column_default', array( $this, 'mla_list_table_column_default' ), 10, 3 ); //add_filter( 'mla_list_table_build_inline_data', array( $this, 'mla_list_table_build_inline_data' ), 10, 2 ); /* * Defined in /plugins/wpml-media/inc/wpml-media.class.php */ add_filter( 'wpml-media_view-upload-sql', array( $this, 'mla_wpml_media_view_upload_sql_filter' ), 10, 2 ); add_filter( 'wpml-media_view-upload-count', array( $this, 'mla_wpml_media_view_upload_count_filter' ), 10, 4 ); add_filter( 'wpml-media_view-upload-page-sql', array( $this, 'mla_wpml_media_view_upload_page_sql_filter' ), 10, 2 ); add_filter( 'wpml-media_view-upload-page-count', array( $this, 'mla_wpml_media_view_upload_page_count_filter' ), 10, 2 ); } /** * Handler for filter "views_{$this->screen->id}" in * /wp-admin/includes/class-wp-list-table.php * * Filter the list of available list table views, calling the WPML filter that adds language-specific views. * * @since 2.11 * * @param array A list of available list table views * * @return array Updated list of available list table views */ public static function mla_views_media_page_mla_menu_filter( $views ) { // hooked by WPML Media in wpml-media.class.php $views = apply_filters( 'views_upload', $views ); // Fix WPML bug for view = all if ( false === strpos( $views['all'], 'page=mla-menu' ) ) { $views['all'] = str_replace( 'upload.php?', 'upload.php?page=mla-menu&', $views['all'] ); } return $views; } /** * Extend the MLA_List_Table class * * Adds a protected variable holding a reference to the WPML_List_Table object, * then creates the WPML_List_Table passing it a reference to the new "parent" object. * * @since 2.11 * * @param object $mla_list_table NULL, to indicate no extension/use the base class. * * @return object updated mla_list_table object. */ public static function mla_list_table_new_instance( $mla_list_table ) { $mla_list_table = new MLA_WPML_List_Table; $mla_list_table->mla_wpml_table = new MLA_WPML_Table( $mla_list_table ); return $mla_list_table; } /** * Handler for filter "wpml-media_view-upload-sql" in /plugins/wpml-media/inc/wpml-media.class.php * * Computes the number of language-specific attachments that satisfy a meta_query specification. * The count is made language-specific by WPML filters when the current_language is set. * * @since 2.11 * * @param string SQL query string * @param string language code, e.g., 'en', 'es' * * @return mixed updated SQL query string */ public function mla_wpml_media_view_upload_sql_filter( $sql, $lang ) { if ( isset( $_GET['detached'] ) && ( '0' == $_GET['detached'] ) ) { $sql = str_replace( "post_mime_type LIKE 'attached%'", 'post_parent > 0', $sql ); } return $sql; } /** * Handler for filter "wpml-media_view-upload-count" in * /plugins/wpml-media/inc/wpml-media.class.php * * Computes the number of attachments that satisfy a meta_query specification. * The count is automatically made language-specific by WPML filters. * * @since 2.11 * * @param NULL default return value if not replacing count * @param string key/slug value for the selected view * @param string HTML tag for the link to the selected view * @param string language code, e.g., 'en', 'es' * * @return mixed NULL to allow SQL query or replacement count value */ public function mla_wpml_media_view_upload_count_filter( $count, $key, $view, $lang ) { // extract the base URL and query parameters $href_count = preg_match( '/(href=["\'])([\s\S]+?)\?([\s\S]+?)(["\'])/', $view, $href_matches ); if ( $href_count ) { wp_parse_str( $href_matches[3], $href_args ); // esc_url() converts & to #038;, which wp_parse_str does not strip if ( isset( $href_args['meta_query'] ) || isset( $href_args['#038;meta_query'] ) ) { $meta_view = $this->mla_list_table->mla_get_view( $key, '' ); // extract the count value $href_count = preg_match( '/class="count">\(([^\)]*)\)/', $meta_view, $href_matches ); if ( $href_count ) { $count = array( $href_matches[1] ); } } } return $count; } /** * Handler for filter "wpml-media_view-upload-page-sql" in /plugins/wpml-media/inc/wpml-media.class.php * * Computes the number of language-specific attachments that satisfy a meta_query specification. * The count is made language-specific by WPML filters when the current_language is set. * * @since 2.11 * * @param string SQL query string * @param string language code, e.g., 'en', 'es' * * @return mixed updated SQL query string */ public function mla_wpml_media_view_upload_page_sql_filter( $sql, $lang ) { if ( isset( $_GET['detached'] ) && ( '0' == $_GET['detached'] ) ) { $sql = str_replace( 'post_parent = 0', 'post_parent > 0', $sql ); } return $sql; } /** * Handler for filter "wpml-media_view-upload-page-count" in /plugins/wpml-media/inc/wpml-media.class.php * * Computes the number of language-specific attachments that satisfy a meta_query specification. * The count is made language-specific by WPML filters when the current_language is set. * * @since 2.11 * * @param NULL default return value if not replacing count * @param string language code, e.g., 'en', 'es' * * @return mixed NULL to allow SQL query or replacement count value */ public function mla_wpml_media_view_upload_page_count_filter( $count, $lang ) { global $sitepress; if ( isset( $_GET['meta_slug'] ) ) { $save_lang = $sitepress->get_current_language(); $sitepress->switch_lang( $lang['code'] ); $meta_view = $this->mla_list_table->mla_get_view( $_GET['meta_slug'], '' ); $sitepress->switch_lang( $save_lang ); if ( false !== $meta_view ) { // extract the count value $href_count = preg_match( '/class="count">\(([^\)]*)\)/', $meta_view, $href_matches ); if ( $href_count ) { $count = array( $href_matches[1] ); } } else { $count = '0'; } } return $count; } /** * Table language column definitions * * Defined as static because it is used before the List_Table object is created. * * @since 2.11 * * @var array */ protected static $language_columns = NULL; /** * Filter the "sticky" submenu URL parameters * * Adds a language ('lang') parameter to the URL parameters that will be * retained when the submenu page refreshes. * * @since 2.11 * * @param array $submenu_arguments An array of query arguments. * format: attribute => value * @param boolean Include the "click filter" values in the results * * @return array updated array of query arguments. */ public static function mla_list_table_submenu_arguments( $submenu_arguments, $include_filters ) { global $sitepress; if ( isset( $_REQUEST['lang'] ) ) { $submenu_arguments['lang'] = $_REQUEST['lang']; } else { $submenu_arguments['lang'] = self::mla_get_table_language(); } return $submenu_arguments; } /** * Get the table-level language code * * This function is used for column-level operations, because * $sitepress->get_current_language() is item-specific. * * @since 2.71 * * @return string table-level language code */ private static function mla_get_table_language() { global $sitepress; if ( !empty( $_REQUEST['lang'] ) ) { $table_language = $_REQUEST['lang']; } else { if ( empty( $table_language ) && ( ! empty( $_SERVER[ 'HTTP_REFERER' ] ) ) ) { $query_string = parse_url( $_SERVER[ 'HTTP_REFERER' ], PHP_URL_QUERY ); $query = array(); parse_str( strval( $query_string ), $query ); if ( !empty( $query['lang'] ) ) { $table_language = $query['lang']; } } if ( empty( $table_language ) && method_exists( $sitepress, 'get_admin_language_cookie' ) ) { $table_language = $sitepress->get_admin_language_cookie(); } if ( empty( $table_language ) ) { $table_language = $sitepress->get_default_language(); } } return $table_language; } /** * Filter the MLA_List_Table columns * * Inserts the language columns just after the item thumbnail column. * Defined as static because it is called before the List_Table object is created. * Added as a filter when the file is loaded. * * @since 2.11 * * @param array $columns An array of columns. * format: column_slug => Column Label * * @return array updated array of columns. */ public static function mla_list_table_get_columns( $columns ) { global $sitepress, $wpdb; if ( is_null( self::$language_columns ) && $sitepress->is_translated_post_type( 'attachment' ) ) { // Build language management columns $show_language = 'checked' == MLACore::mla_get_option( 'language_column', false, false, MLA_WPML::$mla_language_option_definitions ); $table_language = self::mla_get_table_language(); $languages = $sitepress->get_active_languages(); $view_status = isset( $_REQUEST['status'] ) ? $_REQUEST['status'] : ''; if ( 1 < count( $languages ) && $view_status != 'trash' ) { $show_translations = 'checked' == MLACore::mla_get_option( 'translations_column', false, false, MLA_WPML::$mla_language_option_definitions ); } else { $show_translations = false; } self::$language_columns = array(); if ( $show_language && 'all' == $table_language ) { self::$language_columns['language'] = __( 'Language', 'wpml-media' ); } if ( $show_translations ) { $language_codes = array(); foreach ( $languages as $language ) { if ( $table_language != $language['code'] ) { $language_codes[] = $language['code']; } } $results = $wpdb->get_results( $wpdb->prepare(" SELECT f.lang_code, f.flag, f.from_template, l.name FROM {$wpdb->prefix}icl_flags f JOIN {$wpdb->prefix}icl_languages_translations l ON f.lang_code = l.language_code WHERE l.display_language_code = %s AND f.lang_code IN(" . wpml_prepare_in( $language_codes ) . ")", $sitepress->get_admin_language() ) ); $wp_upload_dir = wp_upload_dir(); foreach ( $results as $result ) { if ( $result->from_template ) { $flag_path = $wp_upload_dir['baseurl'] . '/flags/'; } else { $flag_path = ICL_PLUGIN_URL . '/res/flags/'; } $flags[ $result->lang_code ] = '' . $result->name . ''; } $flags_column = ''; foreach ( $languages as $language ) { if ( isset( $flags[ $language['code'] ] ) ) { $flags_column .= $flags[ $language['code'] ]; } } self::$language_columns['icl_translations'] = $flags_column; } // multi-language not trash } // add columns if ( ! empty( self::$language_columns ) ) { $end = array_slice( $columns, 2) ; $columns = array_slice( $columns, 0, 2 ); $columns = array_merge( $columns, self::$language_columns, $end ); } return $columns; } // mla_list_table_get_columns_filter /** * Add styles for the icl_translations table column * * @since 2.11 * * @return void echoes CSS styles before returning */ public static function mla_list_table_add_icl_styles() { global $sitepress; $current_language = self::mla_get_table_language(); $languages = count( $sitepress->get_active_languages() ); $view_status = isset( $_REQUEST['status'] ) ? $_REQUEST['status'] : ''; if ( 1 < $languages && $view_status != 'trash' ) { $w = 22 * ( 'all' == $current_language ? $languages : $languages - 1 ); echo ''; } } /** * Supply a column value if no column-specific function has been defined * * Fills in the Language columns with the item's translation status values. * * @since 2.11 * * @param string NULL, indicating no default content * @param array A singular item (one full row's worth of data) * @param array The name/slug of the column to be processed * * @return string Text or HTML to be placed inside the column */ public function mla_list_table_column_default( $content, $item, $column_name ) { global $sitepress; static $languages = NULL, $default_language, $current_language, $table_language; if ( 'language' == $column_name ) { $item_language = $sitepress->get_language_for_element( $item->ID, 'post_attachment' ); $display_language = $sitepress->get_admin_language(); if ( 'all' === $display_language ) { $display_language = $sitepress->get_default_language(); } $content = $sitepress->get_display_language_name( $item_language, $display_language ); } elseif ('icl_translations' == $column_name ) { if ( is_null( $languages ) ) { $languages = $sitepress->get_active_languages(); $default_language = $sitepress->get_default_language(); $current_language = $sitepress->get_current_language(); // $current_language is item-specific, $table_language is for the entire table $table_language = self::mla_get_table_language(); } $trid = $sitepress->get_element_trid( $item->ID, 'post_attachment' ); $translations = $sitepress->get_element_translations( $trid, 'post_attachment' ); $content = ''; foreach( $languages as $language ) { if ( $language['code'] == $table_language ) { continue; } if ( isset( $translations[ $language['code'] ] ) && $translations[ $language['code'] ]->element_id == $item->ID ) { // The item's own language $img = 'yes.png'; $alt = sprintf( __( 'Edit the %s translation', 'sitepress' ), $language['display_name'] ); $link = 'post.php?action=edit&mla_source=edit&post=' . $translations[ $language['code'] ]->element_id . '&lang=' . $language['code']; } elseif ( isset( $translations[ $language['code'] ] ) && $translations[ $language['code'] ]->element_id ) { // Translation exists $img = 'edit_translation.png'; $alt = sprintf( __( 'Edit the %s translation', 'sitepress' ), $language['display_name'] ); $link = 'post.php?action=edit&mla_source=edit&post=' . $translations[ $language['code'] ]->element_id . '&lang=' . $language['code']; } else { // Translation does not exist $img = 'add_translation.png'; $alt = sprintf( __( 'Add translation to %s', 'sitepress' ), $language['display_name'] ); $src_lang = $current_language; if ( 'all' == $src_lang ) { foreach( $translations as $translation ) { if ( $translation->original ) { $src_lang = $translation->language_code; break; } } } $args = array ( 'page' => MLACore::ADMIN_PAGE_SLUG, 'mla_admin_action' => 'wpml_create_translation', 'mla_item_ID' => $item->ID, 'mla_parent_ID' => $item->post_parent, 'lang' => $language['code'] ); $link = add_query_arg( $args, MLACore::mla_nonce_url( 'upload.php', MLACore::MLA_ADMIN_NONCE_ACTION, MLACore::MLA_ADMIN_NONCE_NAME ) ); } $link = apply_filters( 'wpml_link_to_translation', $link, false, $language['code'], $trid ); $content .= ''; $content .= '' . $alt . ''; $content .= ''; } // foreach language // Is this the original item or a translation? if ( false && isset( $item->mla_item_wpml_media_processed ) && ( '1' == $item->mla_item_wpml_media_processed ) ) { $content .= 'T'; } } return $content; } // mla_list_table_column_default_filter /** * Filter the data for inline (Quick and Bulk) editing * * Adds a 'lang' value for the JS Quick Edit function. * * @since 2.15 * * @param string $inline_data The HTML markup for inline data. * @param object $item The current Media Library item. * * @return string updated HTML markup for inline data. */ public static function mla_list_table_build_inline_data( $inline_data, $item ) { global $sitepress; $language_details = $sitepress->get_element_language_details( $item->ID, 'post_attachment' ); if ( isset( $language_details->language_code ) ) { $inline_data .= "\n\t
{$language_details->language_code}
"; } return $inline_data; } // mla_list_table_build_inline_data } // Class MLA_WPML_Table /* * Some actions and filters are added here, when the source file is loaded, because the * MLA_List_Table object is created too late to be useful. */ /* * Defined in /media-library-assistant/includes/class-mla-list-table.php */ add_filter( 'mla_list_table_get_columns', 'MLA_WPML_Table::mla_list_table_get_columns', 10, 1 ); ?>