~canonical-sysadmins/wordpress/4.7.2

« back to all changes in this revision

Viewing changes to wp-admin/includes/image.php

  • Committer: Jacek Nykis
  • Date: 2015-01-05 16:17:05 UTC
  • Revision ID: jacek.nykis@canonical.com-20150105161705-w544l1h5mcg7u4w9
Initial commit

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
<?php
 
2
/**
 
3
 * File contains all the administration image manipulation functions.
 
4
 *
 
5
 * @package WordPress
 
6
 * @subpackage Administration
 
7
 */
 
8
 
 
9
/**
 
10
 * Crop an Image to a given size.
 
11
 *
 
12
 * @since 2.1.0
 
13
 *
 
14
 * @param string|int $src The source file or Attachment ID.
 
15
 * @param int $src_x The start x position to crop from.
 
16
 * @param int $src_y The start y position to crop from.
 
17
 * @param int $src_w The width to crop.
 
18
 * @param int $src_h The height to crop.
 
19
 * @param int $dst_w The destination width.
 
20
 * @param int $dst_h The destination height.
 
21
 * @param int $src_abs Optional. If the source crop points are absolute.
 
22
 * @param string $dst_file Optional. The destination file to write to.
 
23
 * @return string|WP_Error New filepath on success, WP_Error on failure.
 
24
 */
 
25
function wp_crop_image( $src, $src_x, $src_y, $src_w, $src_h, $dst_w, $dst_h, $src_abs = false, $dst_file = false ) {
 
26
        $src_file = $src;
 
27
        if ( is_numeric( $src ) ) { // Handle int as attachment ID
 
28
                $src_file = get_attached_file( $src );
 
29
 
 
30
                if ( ! file_exists( $src_file ) ) {
 
31
                        // If the file doesn't exist, attempt a url fopen on the src link.
 
32
                        // This can occur with certain file replication plugins.
 
33
                        $src = _load_image_to_edit_path( $src, 'full' );
 
34
                } else {
 
35
                        $src = $src_file;
 
36
                }
 
37
        }
 
38
 
 
39
        $editor = wp_get_image_editor( $src );
 
40
        if ( is_wp_error( $editor ) )
 
41
                return $editor;
 
42
 
 
43
        $src = $editor->crop( $src_x, $src_y, $src_w, $src_h, $dst_w, $dst_h, $src_abs );
 
44
        if ( is_wp_error( $src ) )
 
45
                return $src;
 
46
 
 
47
        if ( ! $dst_file )
 
48
                $dst_file = str_replace( basename( $src_file ), 'cropped-' . basename( $src_file ), $src_file );
 
49
 
 
50
        /*
 
51
         * The directory containing the original file may no longer exist when
 
52
         * using a replication plugin.
 
53
         */
 
54
        wp_mkdir_p( dirname( $dst_file ) );
 
55
 
 
56
        $dst_file = dirname( $dst_file ) . '/' . wp_unique_filename( dirname( $dst_file ), basename( $dst_file ) );
 
57
 
 
58
        $result = $editor->save( $dst_file );
 
59
        if ( is_wp_error( $result ) )
 
60
                return $result;
 
61
 
 
62
        return $dst_file;
 
63
}
 
64
 
 
65
/**
 
66
 * Generate post thumbnail attachment meta data.
 
67
 *
 
68
 * @since 2.1.0
 
69
 *
 
70
 * @param int $attachment_id Attachment Id to process.
 
71
 * @param string $file Filepath of the Attached image.
 
72
 * @return mixed Metadata for attachment.
 
73
 */
 
74
function wp_generate_attachment_metadata( $attachment_id, $file ) {
 
75
        $attachment = get_post( $attachment_id );
 
76
 
 
77
        $metadata = array();
 
78
        $support = false;
 
79
        if ( preg_match('!^image/!', get_post_mime_type( $attachment )) && file_is_displayable_image($file) ) {
 
80
                $imagesize = getimagesize( $file );
 
81
                $metadata['width'] = $imagesize[0];
 
82
                $metadata['height'] = $imagesize[1];
 
83
 
 
84
                // Make the file path relative to the upload dir.
 
85
                $metadata['file'] = _wp_relative_upload_path($file);
 
86
 
 
87
                // Make thumbnails and other intermediate sizes.
 
88
                global $_wp_additional_image_sizes;
 
89
 
 
90
                $sizes = array();
 
91
                foreach ( get_intermediate_image_sizes() as $s ) {
 
92
                        $sizes[$s] = array( 'width' => '', 'height' => '', 'crop' => false );
 
93
                        if ( isset( $_wp_additional_image_sizes[$s]['width'] ) )
 
94
                                $sizes[$s]['width'] = intval( $_wp_additional_image_sizes[$s]['width'] ); // For theme-added sizes
 
95
                        else
 
96
                                $sizes[$s]['width'] = get_option( "{$s}_size_w" ); // For default sizes set in options
 
97
                        if ( isset( $_wp_additional_image_sizes[$s]['height'] ) )
 
98
                                $sizes[$s]['height'] = intval( $_wp_additional_image_sizes[$s]['height'] ); // For theme-added sizes
 
99
                        else
 
100
                                $sizes[$s]['height'] = get_option( "{$s}_size_h" ); // For default sizes set in options
 
101
                        if ( isset( $_wp_additional_image_sizes[$s]['crop'] ) )
 
102
                                $sizes[$s]['crop'] = $_wp_additional_image_sizes[$s]['crop']; // For theme-added sizes
 
103
                        else
 
104
                                $sizes[$s]['crop'] = get_option( "{$s}_crop" ); // For default sizes set in options
 
105
                }
 
106
 
 
107
                /**
 
108
                 * Filter the image sizes automatically generated when uploading an image.
 
109
                 *
 
110
                 * @since 2.9.0
 
111
                 *
 
112
                 * @param array $sizes An associative array of image sizes.
 
113
                 */
 
114
                $sizes = apply_filters( 'intermediate_image_sizes_advanced', $sizes );
 
115
 
 
116
                if ( $sizes ) {
 
117
                        $editor = wp_get_image_editor( $file );
 
118
 
 
119
                        if ( ! is_wp_error( $editor ) )
 
120
                                $metadata['sizes'] = $editor->multi_resize( $sizes );
 
121
                } else {
 
122
                        $metadata['sizes'] = array();
 
123
                }
 
124
 
 
125
                // Fetch additional metadata from EXIF/IPTC.
 
126
                $image_meta = wp_read_image_metadata( $file );
 
127
                if ( $image_meta )
 
128
                        $metadata['image_meta'] = $image_meta;
 
129
 
 
130
        } elseif ( preg_match( '#^video/#', get_post_mime_type( $attachment ) ) ) {
 
131
                $metadata = wp_read_video_metadata( $file );
 
132
                $support = current_theme_supports( 'post-thumbnails', 'attachment:video' ) || post_type_supports( 'attachment:video', 'thumbnail' );
 
133
        } elseif ( preg_match( '#^audio/#', get_post_mime_type( $attachment ) ) ) {
 
134
                $metadata = wp_read_audio_metadata( $file );
 
135
                $support = current_theme_supports( 'post-thumbnails', 'attachment:audio' ) || post_type_supports( 'attachment:audio', 'thumbnail' );
 
136
        }
 
137
 
 
138
        if ( $support && ! empty( $metadata['image']['data'] ) ) {
 
139
                // Check for existing cover.
 
140
                $hash = md5( $metadata['image']['data'] );
 
141
                $posts = get_posts( array(
 
142
                        'fields' => 'ids',
 
143
                        'post_type' => 'attachment',
 
144
                        'post_mime_type' => $metadata['image']['mime'],
 
145
                        'post_status' => 'inherit',
 
146
                        'posts_per_page' => 1,
 
147
                        'meta_key' => '_cover_hash',
 
148
                        'meta_value' => $hash
 
149
                ) );
 
150
                $exists = reset( $posts );
 
151
 
 
152
                if ( ! empty( $exists ) ) {
 
153
                        update_post_meta( $attachment_id, '_thumbnail_id', $exists );
 
154
                } else {
 
155
                        $ext = '.jpg';
 
156
                        switch ( $metadata['image']['mime'] ) {
 
157
                        case 'image/gif':
 
158
                                $ext = '.gif';
 
159
                                break;
 
160
                        case 'image/png':
 
161
                                $ext = '.png';
 
162
                                break;
 
163
                        }
 
164
                        $basename = str_replace( '.', '-', basename( $file ) ) . '-image' . $ext;
 
165
                        $uploaded = wp_upload_bits( $basename, '', $metadata['image']['data'] );
 
166
                        if ( false === $uploaded['error'] ) {
 
167
                                $image_attachment = array(
 
168
                                        'post_mime_type' => $metadata['image']['mime'],
 
169
                                        'post_type' => 'attachment',
 
170
                                        'post_content' => '',
 
171
                                );
 
172
                                /**
 
173
                                 * Filter the parameters for the attachment thumbnail creation.
 
174
                                 *
 
175
                                 * @since 3.9.0
 
176
                                 *
 
177
                                 * @param array $image_attachment An array of parameters to create the thumbnail.
 
178
                                 * @param array $metadata         Current attachment metadata.
 
179
                                 * @param array $uploaded         An array containing the thumbnail path and url.
 
180
                                 */
 
181
                                $image_attachment = apply_filters( 'attachment_thumbnail_args', $image_attachment, $metadata, $uploaded );
 
182
 
 
183
                                $sub_attachment_id = wp_insert_attachment( $image_attachment, $uploaded['file'] );
 
184
                                add_post_meta( $sub_attachment_id, '_cover_hash', $hash );
 
185
                                $attach_data = wp_generate_attachment_metadata( $sub_attachment_id, $uploaded['file'] );
 
186
                                wp_update_attachment_metadata( $sub_attachment_id, $attach_data );
 
187
                                update_post_meta( $attachment_id, '_thumbnail_id', $sub_attachment_id );
 
188
                        }
 
189
                }
 
190
        }
 
191
 
 
192
        // Remove the blob of binary data from the array.
 
193
        if ( isset( $metadata['image']['data'] ) )
 
194
                unset( $metadata['image']['data'] );
 
195
 
 
196
        /**
 
197
         * Filter the generated attachment meta data.
 
198
         *
 
199
         * @since 2.1.0
 
200
         *
 
201
         * @param array $metadata      An array of attachment meta data.
 
202
         * @param int   $attachment_id Current attachment ID.
 
203
         */
 
204
        return apply_filters( 'wp_generate_attachment_metadata', $metadata, $attachment_id );
 
205
}
 
206
 
 
207
/**
 
208
 * Convert a fraction string to a decimal.
 
209
 *
 
210
 * @since 2.5.0
 
211
 *
 
212
 * @param string $str
 
213
 * @return int|float
 
214
 */
 
215
function wp_exif_frac2dec($str) {
 
216
        @list( $n, $d ) = explode( '/', $str );
 
217
        if ( !empty($d) )
 
218
                return $n / $d;
 
219
        return $str;
 
220
}
 
221
 
 
222
/**
 
223
 * Convert the exif date format to a unix timestamp.
 
224
 *
 
225
 * @since 2.5.0
 
226
 *
 
227
 * @param string $str
 
228
 * @return int
 
229
 */
 
230
function wp_exif_date2ts($str) {
 
231
        @list( $date, $time ) = explode( ' ', trim($str) );
 
232
        @list( $y, $m, $d ) = explode( ':', $date );
 
233
 
 
234
        return strtotime( "{$y}-{$m}-{$d} {$time}" );
 
235
}
 
236
 
 
237
/**
 
238
 * Get extended image metadata, exif or iptc as available.
 
239
 *
 
240
 * Retrieves the EXIF metadata aperture, credit, camera, caption, copyright, iso
 
241
 * created_timestamp, focal_length, shutter_speed, and title.
 
242
 *
 
243
 * The IPTC metadata that is retrieved is APP13, credit, byline, created date
 
244
 * and time, caption, copyright, and title. Also includes FNumber, Model,
 
245
 * DateTimeDigitized, FocalLength, ISOSpeedRatings, and ExposureTime.
 
246
 *
 
247
 * @todo Try other exif libraries if available.
 
248
 * @since 2.5.0
 
249
 *
 
250
 * @param string $file
 
251
 * @return bool|array False on failure. Image metadata array on success.
 
252
 */
 
253
function wp_read_image_metadata( $file ) {
 
254
        if ( ! file_exists( $file ) )
 
255
                return false;
 
256
 
 
257
        list( , , $sourceImageType ) = getimagesize( $file );
 
258
 
 
259
        /*
 
260
         * EXIF contains a bunch of data we'll probably never need formatted in ways
 
261
         * that are difficult to use. We'll normalize it and just extract the fields
 
262
         * that are likely to be useful. Fractions and numbers are converted to
 
263
         * floats, dates to unix timestamps, and everything else to strings.
 
264
         */
 
265
        $meta = array(
 
266
                'aperture' => 0,
 
267
                'credit' => '',
 
268
                'camera' => '',
 
269
                'caption' => '',
 
270
                'created_timestamp' => 0,
 
271
                'copyright' => '',
 
272
                'focal_length' => 0,
 
273
                'iso' => 0,
 
274
                'shutter_speed' => 0,
 
275
                'title' => '',
 
276
                'orientation' => 0,
 
277
        );
 
278
 
 
279
        /*
 
280
         * Read IPTC first, since it might contain data not available in exif such
 
281
         * as caption, description etc.
 
282
         */
 
283
        if ( is_callable( 'iptcparse' ) ) {
 
284
                getimagesize( $file, $info );
 
285
 
 
286
                if ( ! empty( $info['APP13'] ) ) {
 
287
                        $iptc = iptcparse( $info['APP13'] );
 
288
 
 
289
                        // Headline, "A brief synopsis of the caption."
 
290
                        if ( ! empty( $iptc['2#105'][0] ) ) {
 
291
                                $meta['title'] = trim( $iptc['2#105'][0] );
 
292
                        /*
 
293
                         * Title, "Many use the Title field to store the filename of the image,
 
294
                         * though the field may be used in many ways."
 
295
                         */
 
296
                        } elseif ( ! empty( $iptc['2#005'][0] ) ) {
 
297
                                $meta['title'] = trim( $iptc['2#005'][0] );
 
298
                        }
 
299
 
 
300
                        if ( ! empty( $iptc['2#120'][0] ) ) { // description / legacy caption
 
301
                                $caption = trim( $iptc['2#120'][0] );
 
302
                                if ( empty( $meta['title'] ) ) {
 
303
                                        mbstring_binary_safe_encoding();
 
304
                                        $caption_length = strlen( $caption );
 
305
                                        reset_mbstring_encoding();
 
306
 
 
307
                                        // Assume the title is stored in 2:120 if it's short.
 
308
                                        if ( $caption_length < 80 ) {
 
309
                                                $meta['title'] = $caption;
 
310
                                        } else {
 
311
                                                $meta['caption'] = $caption;
 
312
                                        }
 
313
                                } elseif ( $caption != $meta['title'] ) {
 
314
                                        $meta['caption'] = $caption;
 
315
                                }
 
316
                        }
 
317
 
 
318
                        if ( ! empty( $iptc['2#110'][0] ) ) // credit
 
319
                                $meta['credit'] = trim( $iptc['2#110'][0] );
 
320
                        elseif ( ! empty( $iptc['2#080'][0] ) ) // creator / legacy byline
 
321
                                $meta['credit'] = trim( $iptc['2#080'][0] );
 
322
 
 
323
                        if ( ! empty( $iptc['2#055'][0] ) and ! empty( $iptc['2#060'][0] ) ) // created date and time
 
324
                                $meta['created_timestamp'] = strtotime( $iptc['2#055'][0] . ' ' . $iptc['2#060'][0] );
 
325
 
 
326
                        if ( ! empty( $iptc['2#116'][0] ) ) // copyright
 
327
                                $meta['copyright'] = trim( $iptc['2#116'][0] );
 
328
                 }
 
329
        }
 
330
 
 
331
        /**
 
332
         * Filter the image types to check for exif data.
 
333
         *
 
334
         * @since 2.5.0
 
335
         *
 
336
         * @param array $image_types Image types to check for exif data.
 
337
         */
 
338
        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 ) ) ) ) {
 
339
                $exif = @exif_read_data( $file );
 
340
 
 
341
                if ( empty( $meta['title'] ) && ! empty( $exif['Title'] ) ) {
 
342
                        $meta['title'] = trim( $exif['Title'] );
 
343
                }
 
344
 
 
345
                if ( ! empty( $exif['ImageDescription'] ) ) {
 
346
                        mbstring_binary_safe_encoding();
 
347
                        $description_length = strlen( $exif['ImageDescription'] );
 
348
                        reset_mbstring_encoding();
 
349
 
 
350
                        if ( empty( $meta['title'] ) && $description_length < 80 ) {
 
351
                                // Assume the title is stored in ImageDescription
 
352
                                $meta['title'] = trim( $exif['ImageDescription'] );
 
353
                                if ( empty( $meta['caption'] ) && ! empty( $exif['COMPUTED']['UserComment'] ) && trim( $exif['COMPUTED']['UserComment'] ) != $meta['title'] ) {
 
354
                                        $meta['caption'] = trim( $exif['COMPUTED']['UserComment'] );
 
355
                                }
 
356
                        } elseif ( empty( $meta['caption'] ) && trim( $exif['ImageDescription'] ) != $meta['title'] ) {
 
357
                                $meta['caption'] = trim( $exif['ImageDescription'] );
 
358
                        }
 
359
                } elseif ( empty( $meta['caption'] ) && ! empty( $exif['Comments'] ) && trim( $exif['Comments'] ) != $meta['title'] ) {
 
360
                        $meta['caption'] = trim( $exif['Comments'] );
 
361
                }
 
362
 
 
363
                if ( empty( $meta['credit'] ) ) {
 
364
                        if ( ! empty( $exif['Artist'] ) ) {
 
365
                                $meta['credit'] = trim( $exif['Artist'] );
 
366
                        } elseif ( ! empty($exif['Author'] ) ) {
 
367
                                $meta['credit'] = trim( $exif['Author'] );
 
368
                        }
 
369
                }
 
370
 
 
371
                if ( empty( $meta['copyright'] ) && ! empty( $exif['Copyright'] ) ) {
 
372
                        $meta['copyright'] = trim( $exif['Copyright'] );
 
373
                }
 
374
                if ( ! empty( $exif['FNumber'] ) ) {
 
375
                        $meta['aperture'] = round( wp_exif_frac2dec( $exif['FNumber'] ), 2 );
 
376
                }
 
377
                if ( ! empty( $exif['Model'] ) ) {
 
378
                        $meta['camera'] = trim( $exif['Model'] );
 
379
                }
 
380
                if ( empty( $meta['created_timestamp'] ) && ! empty( $exif['DateTimeDigitized'] ) ) {
 
381
                        $meta['created_timestamp'] = wp_exif_date2ts( $exif['DateTimeDigitized'] );
 
382
                }
 
383
                if ( ! empty( $exif['FocalLength'] ) ) {
 
384
                        $meta['focal_length'] = (string) wp_exif_frac2dec( $exif['FocalLength'] );
 
385
                }
 
386
                if ( ! empty( $exif['ISOSpeedRatings'] ) ) {
 
387
                        $meta['iso'] = is_array( $exif['ISOSpeedRatings'] ) ? reset( $exif['ISOSpeedRatings'] ) : $exif['ISOSpeedRatings'];
 
388
                        $meta['iso'] = trim( $meta['iso'] );
 
389
                }
 
390
                if ( ! empty( $exif['ExposureTime'] ) ) {
 
391
                        $meta['shutter_speed'] = (string) wp_exif_frac2dec( $exif['ExposureTime'] );
 
392
                }
 
393
                if ( ! empty( $exif['Orientation'] ) ) {
 
394
                        $meta['orientation'] = $exif['Orientation'];
 
395
                }
 
396
        }
 
397
 
 
398
        foreach ( array( 'title', 'caption', 'credit', 'copyright', 'camera', 'iso' ) as $key ) {
 
399
                if ( $meta[ $key ] && ! seems_utf8( $meta[ $key ] ) ) {
 
400
                        $meta[ $key ] = utf8_encode( $meta[ $key ] );
 
401
                }
 
402
        }
 
403
 
 
404
        foreach ( $meta as &$value ) {
 
405
                if ( is_string( $value ) ) {
 
406
                        $value = wp_kses_post( $value );
 
407
                }
 
408
        }
 
409
 
 
410
        /**
 
411
         * Filter the array of meta data read from an image's exif data.
 
412
         *
 
413
         * @since 2.5.0
 
414
         *
 
415
         * @param array  $meta            Image meta data.
 
416
         * @param string $file            Path to image file.
 
417
         * @param int    $sourceImageType Type of image.
 
418
         */
 
419
        return apply_filters( 'wp_read_image_metadata', $meta, $file, $sourceImageType );
 
420
 
 
421
}
 
422
 
 
423
/**
 
424
 * Validate that file is an image.
 
425
 *
 
426
 * @since 2.5.0
 
427
 *
 
428
 * @param string $path File path to test if valid image.
 
429
 * @return bool True if valid image, false if not valid image.
 
430
 */
 
431
function file_is_valid_image($path) {
 
432
        $size = @getimagesize($path);
 
433
        return !empty($size);
 
434
}
 
435
 
 
436
/**
 
437
 * Validate that file is suitable for displaying within a web page.
 
438
 *
 
439
 * @since 2.5.0
 
440
 *
 
441
 * @param string $path File path to test.
 
442
 * @return bool True if suitable, false if not suitable.
 
443
 */
 
444
function file_is_displayable_image($path) {
 
445
        $displayable_image_types = array( IMAGETYPE_GIF, IMAGETYPE_JPEG, IMAGETYPE_PNG, IMAGETYPE_BMP );
 
446
 
 
447
        $info = @getimagesize( $path );
 
448
        if ( empty( $info ) ) {
 
449
                $result = false;
 
450
        } elseif ( ! in_array( $info[2], $displayable_image_types ) ) {
 
451
                $result = false;
 
452
        } else {
 
453
                $result = true;
 
454
        }
 
455
 
 
456
        /**
 
457
         * Filter whether the current image is displayable in the browser.
 
458
         *
 
459
         * @since 2.5.0
 
460
         *
 
461
         * @param bool   $result Whether the image can be displayed. Default true.
 
462
         * @param string $path   Path to the image.
 
463
         */
 
464
        return apply_filters( 'file_is_displayable_image', $result, $path );
 
465
}
 
466
 
 
467
/**
 
468
 * Load an image resource for editing.
 
469
 *
 
470
 * @since 2.9.0
 
471
 *
 
472
 * @param string $attachment_id Attachment ID.
 
473
 * @param string $mime_type Image mime type.
 
474
 * @param string $size Optional. Image size, defaults to 'full'.
 
475
 * @return resource|false The resulting image resource on success, false on failure.
 
476
 */
 
477
function load_image_to_edit( $attachment_id, $mime_type, $size = 'full' ) {
 
478
        $filepath = _load_image_to_edit_path( $attachment_id, $size );
 
479
        if ( empty( $filepath ) )
 
480
                return false;
 
481
 
 
482
        switch ( $mime_type ) {
 
483
                case 'image/jpeg':
 
484
                        $image = imagecreatefromjpeg($filepath);
 
485
                        break;
 
486
                case 'image/png':
 
487
                        $image = imagecreatefrompng($filepath);
 
488
                        break;
 
489
                case 'image/gif':
 
490
                        $image = imagecreatefromgif($filepath);
 
491
                        break;
 
492
                default:
 
493
                        $image = false;
 
494
                        break;
 
495
        }
 
496
        if ( is_resource($image) ) {
 
497
                /**
 
498
                 * Filter the current image being loaded for editing.
 
499
                 *
 
500
                 * @since 2.9.0
 
501
                 *
 
502
                 * @param resource $image         Current image.
 
503
                 * @param string   $attachment_id Attachment ID.
 
504
                 * @param string   $size          Image size.
 
505
                 */
 
506
                $image = apply_filters( 'load_image_to_edit', $image, $attachment_id, $size );
 
507
                if ( function_exists('imagealphablending') && function_exists('imagesavealpha') ) {
 
508
                        imagealphablending($image, false);
 
509
                        imagesavealpha($image, true);
 
510
                }
 
511
        }
 
512
        return $image;
 
513
}
 
514
 
 
515
/**
 
516
 * Retrieve the path or url of an attachment's attached file.
 
517
 *
 
518
 * If the attached file is not present on the local filesystem (usually due to replication plugins),
 
519
 * then the url of the file is returned if url fopen is supported.
 
520
 *
 
521
 * @since 3.4.0
 
522
 * @access private
 
523
 *
 
524
 * @param string $attachment_id Attachment ID.
 
525
 * @param string $size Optional. Image size, defaults to 'full'.
 
526
 * @return string|false File path or url on success, false on failure.
 
527
 */
 
528
function _load_image_to_edit_path( $attachment_id, $size = 'full' ) {
 
529
        $filepath = get_attached_file( $attachment_id );
 
530
 
 
531
        if ( $filepath && file_exists( $filepath ) ) {
 
532
                if ( 'full' != $size && ( $data = image_get_intermediate_size( $attachment_id, $size ) ) ) {
 
533
                        /**
 
534
                         * Filter the path to the current image.
 
535
                         *
 
536
                         * The filter is evaluated for all image sizes except 'full'.
 
537
                         *
 
538
                         * @since 3.1.0
 
539
                         *
 
540
                         * @param string $path          Path to the current image.
 
541
                         * @param string $attachment_id Attachment ID.
 
542
                         * @param string $size          Size of the image.
 
543
                         */
 
544
                        $filepath = apply_filters( 'load_image_to_edit_filesystempath', path_join( dirname( $filepath ), $data['file'] ), $attachment_id, $size );
 
545
                }
 
546
        } elseif ( function_exists( 'fopen' ) && function_exists( 'ini_get' ) && true == ini_get( 'allow_url_fopen' ) ) {
 
547
                /**
 
548
                 * Filter the image URL if not in the local filesystem.
 
549
                 *
 
550
                 * The filter is only evaluated if fopen is enabled on the server.
 
551
                 *
 
552
                 * @since 3.1.0
 
553
                 *
 
554
                 * @param string $image_url     Current image URL.
 
555
                 * @param string $attachment_id Attachment ID.
 
556
                 * @param string $size          Size of the image.
 
557
                 */
 
558
                $filepath = apply_filters( 'load_image_to_edit_attachmenturl', wp_get_attachment_url( $attachment_id ), $attachment_id, $size );
 
559
        }
 
560
 
 
561
        /**
 
562
         * Filter the returned path or URL of the current image.
 
563
         *
 
564
         * @since 2.9.0
 
565
         *
 
566
         * @param string|bool $filepath      File path or URL to current image, or false.
 
567
         * @param string      $attachment_id Attachment ID.
 
568
         * @param string      $size          Size of the image.
 
569
         */
 
570
        return apply_filters( 'load_image_to_edit_path', $filepath, $attachment_id, $size );
 
571
}
 
572
 
 
573
/**
 
574
 * Copy an existing image file.
 
575
 *
 
576
 * @since 3.4.0
 
577
 * @access private
 
578
 *
 
579
 * @param string $attachment_id Attachment ID.
 
580
 * @return string|false New file path on success, false on failure.
 
581
 */
 
582
function _copy_image_file( $attachment_id ) {
 
583
        $dst_file = $src_file = get_attached_file( $attachment_id );
 
584
        if ( ! file_exists( $src_file ) )
 
585
                $src_file = _load_image_to_edit_path( $attachment_id );
 
586
 
 
587
        if ( $src_file ) {
 
588
                $dst_file = str_replace( basename( $dst_file ), 'copy-' . basename( $dst_file ), $dst_file );
 
589
                $dst_file = dirname( $dst_file ) . '/' . wp_unique_filename( dirname( $dst_file ), basename( $dst_file ) );
 
590
 
 
591
                /*
 
592
                 * The directory containing the original file may no longer
 
593
                 * exist when using a replication plugin.
 
594
                 */
 
595
                wp_mkdir_p( dirname( $dst_file ) );
 
596
 
 
597
                if ( ! @copy( $src_file, $dst_file ) )
 
598
                        $dst_file = false;
 
599
        } else {
 
600
                $dst_file = false;
 
601
        }
 
602
 
 
603
        return $dst_file;
 
604
}