function ubik_photo_meta_template($class = 'ubik-photo-meta', $mode = 'table') { // Get photo metadata and exit early if there's nothing to work with $photo_meta = ubik_photo_meta(); if (empty($photo_meta)) { return; } // Initialize $output = array(); // Microdata handling $microdata_id = ubik_photo_meta_microdata_id(); // Class is required for output if (empty($class)) { $class = 'ubik-photo-meta'; } // Table output if ($mode == 'table') { // Loop through the array and format name and data foreach ($photo_meta as $key => $value) { if (!empty($microdata_id) && ubik_photo_meta_set('microdata', $value)) { $output[] = '<tr' . $value['microdata']['container'] . '><td class="' . esc_attr($class) . '-name"' . $value['microdata']['name'] . '>' . $value['name'] . '</td><td class="' . esc_attr($class) . '-data"' . $value['microdata']['value'] . '>' . $value['data'] . '</td></tr>'; } else { $output[] = '<tr><td class="ubik-photo-meta-name">' . $value['name'] . '</td><td class="ubik-photo-meta-value">' . $value['data'] . '</td></tr>'; } } // Return what we got if (!empty($output) && is_array($output)) { return '<table class="' . esc_attr($class) . '"' . $microdata_id . '>' . implode('', $output) . '</table>'; } } elseif ($mode == 'list') { // Loop through the array and format name and data foreach ($photo_meta as $key => $value) { if (!empty($microdata_id) && ubik_photo_meta_set('microdata', $value)) { $output[] = '<li' . $value['microdata']['container'] . '><span' . $value['microdata']['name'] . '>' . $value['name'] . '</span>: <span' . $value['microdata']['value'] . '>' . $value['data'] . '</span></li>'; } else { $output[] = '<li>' . $value['name'] . ': ' . $value['data'] . '</li>'; } } // Return generated markup or null if nothing remains if (!empty($output) && is_array($output)) { return '<ul class="' . esc_attr($class) . '"' . $microdata_id . '><li>' . implode('', $output) . '</ul>'; } } return; }
function ubik_photo_meta_location_data($m = '') { // Exit early if necessary if (!is_array($m) || empty($m)) { return; } // Initialize $d = array('latitude_raw' => '', 'latitude_string' => '', 'latitude_numeric' => '', 'latitude_ref' => '', 'latitude_sign' => 1, 'longitude_raw' => '', 'longitude_string' => '', 'longitude_numeric' => '', 'longitude_ref' => '', 'longitude_sign' => 1, 'string' => '', 'string_linked' => '', 'string_microdata' => '', 'string_microdata_linked' => '', 'numeric' => '', 'google_url' => '', 'google_img' => '', 'sublocation' => '', 'city' => '', 'province' => '', 'country' => ''); // Extended IPTC metadata (warning: these properties are deprecated but still in use, for example by Adobe Lightroom) if (ubik_photo_meta_set('sublocation', $m)) { $d['sublocation'] = $m['sublocation']; } if (ubik_photo_meta_set('city', $m)) { $d['city'] = $m['city']; } if (ubik_photo_meta_set('province', $m)) { $d['province'] = $m['province']; } if (ubik_photo_meta_set('country', $m)) { $d['country'] = $m['country']; } // Populate the array with latitude and longitude data if (ubik_photo_meta_set('latitude', $m)) { $d['latitude_raw'] = $m['latitude']; $d['latitude_string'] = ubik_photo_meta_location_convert($m['latitude'], 'string'); $d['latitude_numeric'] = ubik_photo_meta_location_convert($m['latitude']); if (ubik_photo_meta_set('latitude_ref', $m)) { $d['latitude_ref'] = $m['latitude_ref']; if ($d['latitude_ref'] == 'S') { $d['latitude_sign'] = -1; } } } if (ubik_photo_meta_set('longitude', $m)) { $d['longitude_raw'] = $m['longitude']; $d['longitude_string'] = ubik_photo_meta_location_convert($m['longitude'], 'string'); $d['longitude_numeric'] = ubik_photo_meta_location_convert($m['longitude']); if (ubik_photo_meta_set('longitude_ref', $m)) { $d['longitude_ref'] = $m['longitude_ref']; if ($d['longitude_ref'] == 'W') { $d['longitude_sign'] = -1; } } } // Derived formatting if (!empty($d['latitude_string']) && !empty($d['longitude_string'])) { $d['string'] = $d['latitude_string'] . ' ' . $d['latitude_ref'] . ', ' . $d['longitude_string'] . ' ' . $d['longitude_ref']; $d['string_microdata'] = '<span itemscope itemprop="geo" itemtype="http://schema.org/GeoCoordinates"><span itemprop="latitude">' . $d['latitude_string'] . ' ' . $d['latitude_ref'] . '</span>, <span itemprop="longitude">' . $d['longitude_string'] . ' ' . $d['longitude_ref'] . '</span></span>'; } if (!empty($d['latitude_numeric']) && !empty($d['longitude_numeric'])) { $d['numeric'] = $d['latitude_sign'] * number_format($d['latitude_numeric'], 6) . ',' . $d['longitude_sign'] * number_format($d['longitude_numeric'], 6); } if (!empty($d['numeric'])) { $d['google_url'] = esc_url('//maps.google.com/maps?q=' . $d['numeric'] . '&ll=' . $d['numeric'] . '&z=15&t=h'); // Some help with Google Maps stuff: https://moz.com/ugc/everything-you-never-wanted-to-know-about-google-maps-parameters $d['google_img'] = esc_url('//maps.googleapis.com/maps/api/staticmap?zoom=12&size=500x500&maptype=roadmap&markers=color:blue%7Clabel:S%7C' . $d['numeric'] . '&sensor=false'); } if (!empty($d['google_url'])) { $d['string_linked'] = '<a href="' . $d['google_url'] . '">' . $d['string'] . '</a>'; $d['string_microdata_linked'] = '<a href="' . $d['google_url'] . '" itemprop="hasMap">' . $d['string_microdata'] . '</a>'; } return apply_filters('ubik_photo_meta_location_data', $d, $m); }
function ubik_photo_meta_read_image($meta, $file, $sourceImageType) { // Exit early if we have no file to act upon if (empty($file)) { return $meta; } // Initialize $meta_extra = array(); // Parse IPTC metadata; mapping codes courtesy of https://github.com/peterhudec/image-metadata-cruncher if (is_callable('iptcparse')) { getimagesize($file, $iptc); if (!empty($iptc['APP13'])) { $iptc = iptcparse($iptc['APP13']); if (!empty($iptc['2#090'])) { $meta_extra['city'] = $iptc['2#090'][0]; } if (!empty($iptc['2#092'])) { $meta_extra['sublocation'] = $iptc['2#092'][0]; } if (!empty($iptc['2#095'])) { $meta_extra['province'] = $iptc['2#095'][0]; } if (!empty($iptc['2#101'])) { $meta_extra['country'] = $iptc['2#101'][0]; } if (!empty($iptc['2#025']) && is_array($iptc['2#025'])) { $meta_extra['keywords'] = implode(', ', $iptc['2#025']); } // Store keywords as a comma-delimited string for easy manipulation and re-use } } // Parse EXIF metadata if (is_callable('exif_read_data') && in_array($sourceImageType, apply_filters('wp_read_image_metadata_types', array(IMAGETYPE_JPEG, IMAGETYPE_TIFF_II, IMAGETYPE_TIFF_MM)))) { $exif = @exif_read_data($file); // GPS data if (!empty($exif['GPSLatitude'])) { $meta_extra['latitude'] = $exif['GPSLatitude']; } if (!empty($exif['GPSLatitudeRef'])) { $meta_extra['latitude_ref'] = trim($exif['GPSLatitudeRef']); } if (!empty($exif['GPSLongitude'])) { $meta_extra['longitude'] = $exif['GPSLongitude']; } if (!empty($exif['GPSLongitudeRef'])) { $meta_extra['longitude_ref'] = trim($exif['GPSLongitudeRef']); } // Additional photographic metadata if (!empty($exif['ExposureBiasValue'])) { $meta_extra['exposure'] = trim($exif['ExposureBiasValue']); } if (!empty($exif['Flash'])) { $meta_extra['flash'] = trim($exif['Flash']); } } // Sanitize extra metadata keys; 'latitude', 'latitude_ref', 'longitude', 'longitude_ref' aren't necessarily strings so let's not run those through foreach (array('exposure', 'flash') as $key) { if (ubik_photo_meta_set($key, $meta_extra) && !seems_utf8($meta_extra[$key])) { $meta_extra[$key] = utf8_encode($meta_extra[$key]); } } // Add metadata to the existing metadata object foreach ($meta_extra as $field => $extra) { if (is_string($extra)) { $extra = wp_kses_post($extra); } if (is_array($extra)) { $extra = array_map('esc_attr', $extra); } $meta[$field] = $extra; } // Return and filter the results return apply_filters('ubik_photo_meta_read_image', $meta, $file, $sourceImageType); }
function ubik_photo_meta_data($id, $fields = array()) { // Exit early if necessary if (empty($id)) { return; } // Fetch metadata if (!empty($id)) { $meta_raw = wp_get_attachment_metadata($id); } // Fill the photo metadata array with whatever we have available if (!empty($meta_raw) && ubik_photo_meta_set('image_meta', $meta_raw)) { // Setup $m = $meta_raw['image_meta']; // Raw source material $d = array(); // Processed output // Populate the array with formatted metadata; there is also an orientation property in vanilla WordPress to consider if (ubik_photo_meta_set('aperture', $m) && in_array('aperture', $fields)) { $d['aperture'] = array('name' => __('Aperture', 'ubik'), 'data' => apply_filters('ubik_photo_meta_f_symbol', '<em>ƒ</em>') . '/' . $m['aperture'], 'microdata' => ubik_photo_meta_microdata('exif')); } if (ubik_photo_meta_set('camera', $m) && in_array('camera', $fields)) { $d['camera'] = array('name' => __('Camera', 'ubik'), 'data' => $m['camera'], 'microdata' => ubik_photo_meta_microdata('exif')); } if (ubik_photo_meta_set('caption', $m) && in_array('caption', $fields)) { $d['caption'] = array('name' => __('Caption', 'ubik'), 'data' => $m['caption']); } if (ubik_photo_meta_set('created_timestamp', $m) && in_array('created_timestamp', $fields)) { $d['created_timestamp'] = array('name' => __('Date taken', 'ubik'), 'data' => ubik_photo_meta_date($m['created_timestamp']), 'microdata' => ubik_photo_meta_microdata('created')); } if (ubik_photo_meta_set('credit', $m) && in_array('credit', $fields)) { $d['credit'] = array('name' => __('Credit', 'ubik'), 'data' => $m['credit'], 'microdata' => ubik_photo_meta_microdata('credit')); } if (ubik_photo_meta_set('copyright', $m) && in_array('copyright', $fields)) { $d['copyright'] = array('name' => __('Copyright', 'ubik'), 'data' => $m['copyright']); } if (ubik_photo_meta_set('focal_length', $m) && in_array('focal_length', $fields)) { $d['focal_length'] = array('name' => __('Focal length', 'ubik'), 'data' => ubik_photo_meta_focal_length($m['focal_length']), 'microdata' => ubik_photo_meta_microdata('exif')); } if (ubik_photo_meta_set('iso', $m) && in_array('iso', $fields)) { $d['iso'] = array('name' => __('ISO', 'ubik'), 'data' => $m['iso'], 'microdata' => ubik_photo_meta_microdata('exif')); } if (ubik_photo_meta_set('shutter_speed', $m) && in_array('shutter_speed', $fields)) { $d['shutter_speed'] = array('name' => __('Shutter speed', 'ubik'), 'data' => ubik_photo_meta_shutter_speed($m['shutter_speed']), 'microdata' => ubik_photo_meta_microdata('exif')); } if (ubik_photo_meta_set('title', $m) && in_array('title', $fields)) { $d['title'] = array('name' => __('Title', 'ubik'), 'data' => $m['title']); } // Extended EXIF metadata if (ubik_photo_meta_set('exposure', $m) && in_array('exposure', $fields)) { $d['exposure'] = array('name' => __('Exposure', 'ubik'), 'data' => ubik_photo_meta_exposure($m['exposure']), 'microdata' => ubik_photo_meta_microdata('exif')); } if (ubik_photo_meta_set('flash', $m) && in_array('flash', $fields)) { $d['flash'] = array('name' => __('Flash', 'ubik'), 'data' => ubik_photo_meta_binary($m['flash']), 'microdata' => ubik_photo_meta_microdata('exif')); } // Keywords; by default these are filtered to associate with tags in the database if (ubik_photo_meta_set('keywords', $m) && in_array('keywords', $fields)) { $keywords = ubik_photo_meta_keywords($m['keywords']); if (!empty($keywords)) { $d['keywords'] = array('name' => __('Keywords', 'ubik'), 'data' => $keywords, 'microdata' => ubik_photo_meta_microdata('keywords')); } } // Location data; this is a special case: 1) there are many kinds of location metadat, and 2) users may wish to display this in any number of ways if (in_array('location', $fields)) { $location = ubik_photo_meta_location($m); if (!empty($location) && is_array($location)) { $d['location'] = $location; } } } return apply_filters('ubik_photo_meta_data', $d); }