1 /* xscreensaver, Copyright (c) 1992-2016 Jamie Zawinski <jwz@jwz.org>
3 * Permission to use, copy, modify, distribute, and sell this software and its
4 * documentation for any purpose is hereby granted without fee, provided that
5 * the above copyright notice appear in all copies and that both that
6 * copyright notice and this permission notice appear in supporting
7 * documentation. No representations are made about the suitability of this
8 * software for any purpose. It is provided "as is" without express or
12 /* This iOS code to choose and return a random image from the user's
15 * Much of the following written by:
17 * Created by David Oster on 6/23/12.
18 * Copyright (c) 2012 Google. All rights reserved.
19 * Licensed under the Apache License, Version 2.0 (the "License");
20 * you may not use this file except in compliance with the License.
21 * You may obtain a copy of the License at
23 * http://www.apache.org/licenses/LICENSE-2.0
25 * Unless required by applicable law or agreed to in writing, software
26 * distributed under the License is distributed on an "AS IS" BASIS,
27 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
28 * See the License for the specific language governing permissions and
29 * limitations under the License.
32 #ifdef USE_IPHONE // whole file
34 #import <AssetsLibrary/AssetsLibrary.h>
35 #import "grabscreen.h"
38 /* ALAssetsLibrary is an async API, so we need to fire it off and then
39 call a callback when it's done. Fortunately, this fits the same
40 interaction model already used in xscreensaver by load_image_async(),
41 so it works out nicely.
45 void (*callback) (void *uiimage, const char *fn, int width, int height,
49 ALAssetsLibrary *library;
50 NSMutableArray *assets;
56 ios_random_image_done (ios_loader_data *d, BOOL ok)
60 NSUInteger n = ok ? [d->assets count] : 0;
62 ALAsset *asset = [d->assets objectAtIndex: random() % n];
63 ALAssetRepresentation *rep = [asset defaultRepresentation];
65 // "fullScreenImage" returns a smaller image than "fullResolutionImage",
66 // but this function still takes a significant fraction of a second,
67 // causing a visible glitch in e.g. "glslideshow".
68 CGImageRef cgi = [rep fullScreenImage];
70 UIImageOrientation orient = (UIImageOrientation)
71 [[asset valueForProperty:ALAssetPropertyOrientation] intValue];
72 img = [UIImage imageWithCGImage: cgi
76 fn = [[[rep filename] stringByDeletingPathExtension]
77 cStringUsingEncoding:NSUTF8StringEncoding];
84 d->callback (img, fn, [img size].width, [img size].height, d->closure);
90 ios_load_random_image (void (*callback) (void *uiimage, const char *fn,
91 int width, int height,
95 ios_loader_data *d = (ios_loader_data *) calloc (1, sizeof(*d));
96 d->callback = callback;
99 d->library = [[[ALAssetsLibrary alloc] init] retain];
100 d->assets = [[NSMutableArray array] retain];
102 // The closures passed in here are called later, after we have returned.
104 [d->library enumerateGroupsWithTypes: ALAssetsGroupAll
105 usingBlock: ^(ALAssetsGroup *group, BOOL *stop) {
106 NSString *name = [group valueForProperty:ALAssetsGroupPropertyName];
108 [group enumerateAssetsUsingBlock: ^(ALAsset *asset, NSUInteger index,
110 if ([[asset valueForProperty: ALAssetPropertyType]
111 isEqual: ALAssetTypePhoto]) {
112 [d->assets addObject:asset];
117 if (! group) { // done
118 ios_random_image_done (d, YES);
120 } failureBlock:^(NSError *error) {
121 // E.g., ALAssetsLibraryErrorDomain: "The user has denied the
122 // application access to their media."
123 NSLog(@"reading Photo Library: %@", error);
124 ios_random_image_done (d, NO);
128 #endif // USE_IPHONE - whole file