diff --git a/ModelTraining/.gitignore b/ModelTraining/.gitignore index dba9a4f..ac9438d 100755 --- a/ModelTraining/.gitignore +++ b/ModelTraining/.gitignore @@ -8,6 +8,12 @@ __pycache__/ # C extensions *.so + +data/ +downloads/ +fortt/ +logs/ + # Distribution / packaging .Python build/ diff --git a/android-tflite/.gitignore b/android-tflite/.gitignore index 2c17da7..c29df47 100755 --- a/android-tflite/.gitignore +++ b/android-tflite/.gitignore @@ -17,6 +17,7 @@ out/ # Gradle files .gradle/ build/ +.idea/ # Local configuration file (sdk path, etc) local.properties diff --git a/android-tflite/gradle/wrapper/gradle-wrapper.jar b/android-tflite/gradle/wrapper/gradle-wrapper.jar index f6b961f..13372ae 100755 Binary files a/android-tflite/gradle/wrapper/gradle-wrapper.jar and b/android-tflite/gradle/wrapper/gradle-wrapper.jar differ diff --git a/android-tflite/gradle/wrapper/gradle-wrapper.properties b/android-tflite/gradle/wrapper/gradle-wrapper.properties index 073a420..4d87136 100755 --- a/android-tflite/gradle/wrapper/gradle-wrapper.properties +++ b/android-tflite/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ -#Sun Apr 14 18:43:29 CDT 2019 +#Tue Nov 14 09:09:45 PST 2017 distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-4.10.1-all.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-4.1-all.zip diff --git a/android-tflite/gradlew b/android-tflite/gradlew index cccdd3d..9d82f78 100755 --- a/android-tflite/gradlew +++ b/android-tflite/gradlew @@ -1,4 +1,4 @@ -#!/usr/bin/env sh +#!/usr/bin/env bash ############################################################################## ## @@ -6,6 +6,42 @@ ## ############################################################################## +# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +DEFAULT_JVM_OPTS="" + +APP_NAME="Gradle" +APP_BASE_NAME=`basename "$0"` + +# Use the maximum available, or set MAX_FD != -1 to use that value. +MAX_FD="maximum" + +warn ( ) { + echo "$*" +} + +die ( ) { + echo + echo "$*" + echo + exit 1 +} + +# OS specific support (must be 'true' or 'false'). +cygwin=false +msys=false +darwin=false +case "`uname`" in + CYGWIN* ) + cygwin=true + ;; + Darwin* ) + darwin=true + ;; + MINGW* ) + msys=true + ;; +esac + # Attempt to set APP_HOME # Resolve links: $0 may be a link PRG="$0" @@ -24,46 +60,6 @@ cd "`dirname \"$PRG\"`/" >/dev/null APP_HOME="`pwd -P`" cd "$SAVED" >/dev/null -APP_NAME="Gradle" -APP_BASE_NAME=`basename "$0"` - -# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. -DEFAULT_JVM_OPTS="" - -# Use the maximum available, or set MAX_FD != -1 to use that value. -MAX_FD="maximum" - -warn () { - echo "$*" -} - -die () { - echo - echo "$*" - echo - exit 1 -} - -# OS specific support (must be 'true' or 'false'). -cygwin=false -msys=false -darwin=false -nonstop=false -case "`uname`" in - CYGWIN* ) - cygwin=true - ;; - Darwin* ) - darwin=true - ;; - MINGW* ) - msys=true - ;; - NONSTOP* ) - nonstop=true - ;; -esac - CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar # Determine the Java command to use to start the JVM. @@ -89,7 +85,7 @@ location of your Java installation." fi # Increase the maximum file descriptors if we can. -if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then +if [ "$cygwin" = "false" -a "$darwin" = "false" ] ; then MAX_FD_LIMIT=`ulimit -H -n` if [ $? -eq 0 ] ; then if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then @@ -154,19 +150,11 @@ if $cygwin ; then esac fi -# Escape application args -save () { - for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done - echo " " +# Split up the JVM_OPTS And GRADLE_OPTS values into an array, following the shell quoting and substitution rules +function splitJvmOpts() { + JVM_OPTS=("$@") } -APP_ARGS=$(save "$@") +eval splitJvmOpts $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS +JVM_OPTS[${#JVM_OPTS[*]}]="-Dorg.gradle.appname=$APP_BASE_NAME" -# Collect all arguments for the java command, following the shell quoting and substitution rules -eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" - -# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong -if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then - cd "$(dirname "$0")" -fi - -exec "$JAVACMD" "$@" +exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@" diff --git a/android-tflite/gradlew.bat b/android-tflite/gradlew.bat index f955316..8a0b282 100755 --- a/android-tflite/gradlew.bat +++ b/android-tflite/gradlew.bat @@ -8,14 +8,14 @@ @rem Set local scope for the variables with windows NT shell if "%OS%"=="Windows_NT" setlocal +@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. +set DEFAULT_JVM_OPTS= + set DIRNAME=%~dp0 if "%DIRNAME%" == "" set DIRNAME=. set APP_BASE_NAME=%~n0 set APP_HOME=%DIRNAME% -@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. -set DEFAULT_JVM_OPTS= - @rem Find java.exe if defined JAVA_HOME goto findJavaFromJavaHome @@ -46,9 +46,10 @@ echo location of your Java installation. goto fail :init -@rem Get command-line arguments, handling Windows variants +@rem Get command-line arguments, handling Windowz variants if not "%OS%" == "Windows_NT" goto win9xME_args +if "%@eval[2+2]" == "4" goto 4NT_args :win9xME_args @rem Slurp the command line arguments. @@ -59,6 +60,11 @@ set _SKIP=2 if "x%~1" == "x" goto execute set CMD_LINE_ARGS=%* +goto execute + +:4NT_args +@rem Get arguments from the 4NT Shell from JP Software +set CMD_LINE_ARGS=%$ :execute @rem Setup the command line diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/Contents.json b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/Contents.json new file mode 100755 index 0000000..1c25084 --- /dev/null +++ b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/Contents.json @@ -0,0 +1,116 @@ +{ + "images": [ + { + "size": "20x20", + "idiom": "iphone", + "filename": "logo-2.png", + "scale": "2x" + }, + { + "size": "20x20", + "idiom": "iphone", + "filename": "logo-3.png", + "scale": "3x" + }, + { + "size": "29x29", + "idiom": "iphone", + "filename": "logo-4.png", + "scale": "2x" + }, + { + "size": "29x29", + "idiom": "iphone", + "filename": "logo-5.png", + "scale": "3x" + }, + { + "size": "40x40", + "idiom": "iphone", + "filename": "logo-6.png", + "scale": "2x" + }, + { + "size": "40x40", + "idiom": "iphone", + "filename": "logo-7.png", + "scale": "3x" + }, + { + "size": "60x60", + "idiom": "iphone", + "filename": "logo-1.png", + "scale": "2x" + }, + { + "size": "60x60", + "idiom": "iphone", + "filename": "logo.png", + "scale": "3x" + }, + { + "size": "20x20", + "idiom": "ipad", + "filename": "logo-8.png", + "scale": "1x" + }, + { + "size": "20x20", + "idiom": "ipad", + "filename": "logo-9.png", + "scale": "2x" + }, + { + "size": "29x29", + "idiom": "ipad", + "filename": "logo-10.png", + "scale": "1x" + }, + { + "size": "29x29", + "idiom": "ipad", + "filename": "logo-11.png", + "scale": "2x" + }, + { + "size": "40x40", + "idiom": "ipad", + "filename": "logo-12.png", + "scale": "1x" + }, + { + "size": "40x40", + "idiom": "ipad", + "filename": "logo-13.png", + "scale": "2x" + }, + { + "size": "76x76", + "idiom": "ipad", + "filename": "logo-14.png", + "scale": "1x" + }, + { + "size": "76x76", + "idiom": "ipad", + "filename": "logo-15.png", + "scale": "2x" + }, + { + "size": "83.5x83.5", + "idiom": "ipad", + "filename": "logo-16.png", + "scale": "2x" + }, + { + "size": "1024x1024", + "idiom": "ios-marketing", + "filename": "logo-17.png", + "scale": "1x" + } + ], + "info": { + "version": 1, + "author": "xcode" + } +} \ No newline at end of file diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-1.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-1.png new file mode 100755 index 0000000..7eee5db Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-1.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-10.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-10.png new file mode 100755 index 0000000..26e797d Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-10.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-11.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-11.png new file mode 100755 index 0000000..10b514b Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-11.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-12.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-12.png new file mode 100755 index 0000000..a533018 Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-12.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-13.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-13.png new file mode 100755 index 0000000..9f1e45e Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-13.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-14.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-14.png new file mode 100755 index 0000000..3db1736 Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-14.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-15.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-15.png new file mode 100755 index 0000000..5a8e969 Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-15.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-16.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-16.png new file mode 100755 index 0000000..4354bf8 Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-16.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-17.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-17.png new file mode 100755 index 0000000..34cdf5d Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-17.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-2.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-2.png new file mode 100755 index 0000000..a533018 Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-2.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-3.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-3.png new file mode 100755 index 0000000..985cbcc Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-3.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-4.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-4.png new file mode 100755 index 0000000..10b514b Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-4.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-5.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-5.png new file mode 100755 index 0000000..65aa946 Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-5.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-6.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-6.png new file mode 100755 index 0000000..9f1e45e Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-6.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-7.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-7.png new file mode 100755 index 0000000..7eee5db Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-7.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-8.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-8.png new file mode 100755 index 0000000..b73b2bc Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-8.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-9.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-9.png new file mode 100755 index 0000000..a533018 Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo-9.png differ diff --git a/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo.png b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo.png new file mode 100755 index 0000000..13a71eb Binary files /dev/null and b/iOS-tflite/AppIcon.xcassets/AppIcon.appiconset/logo.png differ diff --git a/iOS-tflite/AppIcon.xcassets/Contents.json b/iOS-tflite/AppIcon.xcassets/Contents.json new file mode 100755 index 0000000..121dee6 --- /dev/null +++ b/iOS-tflite/AppIcon.xcassets/Contents.json @@ -0,0 +1,6 @@ +{ + "info": { + "version": 1, + "author": "xcode" + } +} \ No newline at end of file diff --git a/iOS-tflite/CameraExampleAppDelegate.h b/iOS-tflite/CameraExampleAppDelegate.h new file mode 100755 index 0000000..55891c3 --- /dev/null +++ b/iOS-tflite/CameraExampleAppDelegate.h @@ -0,0 +1,21 @@ +// Copyright 2017 The TensorFlow Authors. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#import + +@interface CameraExampleAppDelegate : UIResponder + +@property(strong, nonatomic) UIWindow* window; + +@end diff --git a/iOS-tflite/CameraExampleAppDelegate.m b/iOS-tflite/CameraExampleAppDelegate.m new file mode 100755 index 0000000..128266d --- /dev/null +++ b/iOS-tflite/CameraExampleAppDelegate.m @@ -0,0 +1,44 @@ +// Copyright 2017 The TensorFlow Authors. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#import "CameraExampleAppDelegate.h" + +@implementation CameraExampleAppDelegate + +@synthesize window = _window; + +- (BOOL)application:(UIApplication *)application + didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { + [self.window makeKeyAndVisible]; + return YES; +} + +- (void)applicationWillResignActive:(UIApplication *)application { + [[UIApplication sharedApplication] setIdleTimerDisabled:NO]; +} + +- (void)applicationDidEnterBackground:(UIApplication *)application { +} + +- (void)applicationWillEnterForeground:(UIApplication *)application { +} + +- (void)applicationDidBecomeActive:(UIApplication *)application { + [[UIApplication sharedApplication] setIdleTimerDisabled:YES]; +} + +- (void)applicationWillTerminate:(UIApplication *)application { +} + +@end diff --git a/iOS-tflite/CameraExampleViewController.h b/iOS-tflite/CameraExampleViewController.h new file mode 100755 index 0000000..a195d46 --- /dev/null +++ b/iOS-tflite/CameraExampleViewController.h @@ -0,0 +1,58 @@ +// Copyright 2017 The TensorFlow Authors. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#import +#import +#import + +#include + +#include "tensorflow/contrib/lite/kernels/register.h" +#include "tensorflow/contrib/lite/model.h" + +typedef struct { + int width; + int height; + int channels; + std::vector data; +} image_data; + + +@interface CameraExampleViewController + : UIViewController { + IBOutlet UIView* previewView; + CALayer* previewLayer; + UIView* flashView; + NSMutableArray* labelLayers; + + + std::vector labels; + std::unique_ptr model; + tflite::ops::builtin::BuiltinOpResolver resolver; + std::unique_ptr interpreter; + + double total_latency; + int total_count; + + int photos_index; + PHFetchResult *photos; + + UIImage* input_image; + UIImage* display_image; +} +@property(strong, nonatomic) CATextLayer* predictionTextLayer; + +- (IBAction)takePicture:(id)sender; +@end + diff --git a/iOS-tflite/CameraExampleViewController.mm b/iOS-tflite/CameraExampleViewController.mm new file mode 100755 index 0000000..3d3e17f --- /dev/null +++ b/iOS-tflite/CameraExampleViewController.mm @@ -0,0 +1,467 @@ +// Copyright 2017 The TensorFlow Authors. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#import "CameraExampleViewController.h" +#import +#import +#import +#import + +#include +#include +#include +#include + +#include "tensorflow/contrib/lite/kernels/register.h" +#include "tensorflow/contrib/lite/model.h" +#include "tensorflow/contrib/lite/string_util.h" +#include "tensorflow/contrib/lite/mutable_op_resolver.h" + +#define LOG(x) std::cerr + +// If you have your own model, modify this to the file name, and make sure +// you've added the file to your app resources too. +static NSString* model_file_name = @"graph"; +static NSString* model_file_type = @"lite"; + +// If you have your own model, point this to the labels file. +static NSString* labels_file_name = @"labels"; +static NSString* labels_file_type = @"txt"; + +// These dimensions need to match those the model was trained with. +static const int wanted_input_width = 224; +static const int wanted_input_height = 224; +static const int wanted_input_channels = 3; + +static NSString* FilePathForResourceName(NSString* name, NSString* extension) { + NSString* file_path = [[NSBundle mainBundle] pathForResource:name ofType:extension]; + if (file_path == NULL) { + LOG(FATAL) << "Couldn't find '" << [name UTF8String] << "." << [extension UTF8String] + << "' in bundle."; + } + return file_path; +} + +static void LoadLabels(NSString* file_name, NSString* file_type, + std::vector* label_strings) { + NSString* labels_path = FilePathForResourceName(file_name, file_type); + if (!labels_path) { + LOG(ERROR) << "Failed to find model proto at" << [file_name UTF8String] + << [file_type UTF8String]; + } + std::ifstream t; + t.open([labels_path UTF8String]); + std::string line; + while (t) { + std::getline(t, line); + if (line.length()){ + label_strings->push_back(line); + } + } + t.close(); +} + +// Returns the top N confidence values over threshold in the provided vector, +// sorted by confidence in descending order. +static void GetTopN(const float* prediction, const int prediction_size, const int num_results, + const float threshold, std::vector>* top_results) { + // Will contain top N results in ascending order. + std::priority_queue, std::vector>, + std::greater>> + top_result_pq; + + const long count = prediction_size; + for (int i = 0; i < count; ++i) { + const float value = prediction[i]; + // Only add it if it beats the threshold and has a chance at being in + // the top N. + if (value < threshold) { + continue; + } + + top_result_pq.push(std::pair(value, i)); + + // If at capacity, kick the smallest value out. + if (top_result_pq.size() > num_results) { + top_result_pq.pop(); + } + } + + // Copy to output vector and reverse into descending order. + while (!top_result_pq.empty()) { + top_results->push_back(top_result_pq.top()); + top_result_pq.pop(); + } + std::reverse(top_results->begin(), top_results->end()); +} + +@interface CameraExampleViewController (InternalMethods) +- (void)teardownAVCapture; +@end + +@implementation CameraExampleViewController + +- (void) attachPreviewLayer{ + photos_index = 0; + photos = nil; + previewLayer = [[CALayer alloc] init]; + + [previewLayer setBackgroundColor:[[UIColor blackColor] CGColor]]; + CALayer* rootLayer = [previewView layer]; + [rootLayer setMasksToBounds:YES]; + [previewLayer setFrame:[rootLayer bounds]]; + [rootLayer addSublayer:previewLayer]; + + [self UpdatePhoto]; +} + +- (void)UpdatePhoto{ + PHAsset* asset; + if (photos==nil || photos_index >= photos.count){ + [self updatePhotosLibrary]; + photos_index=0; + } + if (photos.count){ + asset = photos[photos_index]; + photos_index += 1; + input_image = [self convertImageFromAsset:asset + targetSize:CGSizeMake(wanted_input_width, wanted_input_height) + mode:PHImageContentModeAspectFill]; + display_image = [self convertImageFromAsset:asset + targetSize:CGSizeMake(asset.pixelWidth,asset.pixelHeight) + mode:PHImageContentModeAspectFit]; + [self DrawImage]; + } + + if (input_image != nil){ + image_data image = [self CGImageToPixels:input_image.CGImage]; + [self inputImageToModel:image]; + [self runModel]; + } +} + +- (void)DrawImage{ + CGFloat view_height = 800; + CGFloat view_width = 600; + + UIGraphicsBeginImageContextWithOptions(CGSizeMake(view_width, view_height), NO, 0.0); + CGContextRef context = UIGraphicsGetCurrentContext(); + UIGraphicsPushContext(context); + + float scale = view_width/display_image.size.width; + + if (display_image.size.height*scale > view_height){ + scale = view_height/display_image.size.height; + } + + CGPoint origin = CGPointMake((view_width - display_image.size.width*scale) / 2.0f, + (view_height - display_image.size.height*scale) / 2.0f); + [display_image drawInRect:CGRectMake(origin.x, origin.y, + display_image.size.width*scale, + display_image.size.height*scale)]; + UIGraphicsPopContext(); + display_image = UIGraphicsGetImageFromCurrentImageContext(); + UIGraphicsEndImageContext(); + previewLayer.contents = (id) display_image.CGImage; +} + +- (void)teardownAVCapture { + [previewLayer removeFromSuperlayer]; +} + +- (void) updatePhotosLibrary{ + PHFetchOptions *fetchOptions = [[PHFetchOptions alloc] init]; + fetchOptions.sortDescriptors = @[[NSSortDescriptor sortDescriptorWithKey:@"creationDate" ascending:YES]]; + photos = [PHAsset fetchAssetsWithMediaType:PHAssetMediaTypeImage options:fetchOptions]; +} + +- (UIImage *) convertImageFromAsset:(PHAsset *)asset + targetSize:(CGSize) targetSize + mode:(PHImageContentMode) mode{ + PHImageManager * manager = [[PHImageManager alloc] init]; + PHImageRequestOptions * options = [[PHImageRequestOptions alloc] init]; + NSMutableArray * images = [[NSMutableArray alloc] init]; + NSMutableArray * infos = [[NSMutableArray alloc] init]; + + options.synchronous = TRUE; + + [manager requestImageForAsset:asset + targetSize:targetSize + contentMode:mode + options:options + resultHandler:^(UIImage *image, NSDictionary *info){ + [images addObject:image]; + [infos addObject:info]; + } + ]; + + UIImage *result = images[0]; + + return result; +} + +- (AVCaptureVideoOrientation)avOrientationForDeviceOrientation: + (UIDeviceOrientation)deviceOrientation { + AVCaptureVideoOrientation result = (AVCaptureVideoOrientation)(deviceOrientation); + if (deviceOrientation == UIDeviceOrientationLandscapeLeft) + result = AVCaptureVideoOrientationLandscapeRight; + else if (deviceOrientation == UIDeviceOrientationLandscapeRight) + result = AVCaptureVideoOrientationLandscapeLeft; + return result; +} + +- (image_data)CGImageToPixels:(CGImage *)image { + image_data result; + result.width = (int)CGImageGetWidth(image); + result.height = (int)CGImageGetHeight(image); + result.channels = 4; + + CGColorSpaceRef color_space = CGColorSpaceCreateDeviceRGB(); + const int bytes_per_row = (result.width * result.channels); + const int bytes_in_image = (bytes_per_row * result.height); + result.data = std::vector(bytes_in_image); + const int bits_per_component = 8; + + CGContextRef context = + CGBitmapContextCreate(result.data.data(), result.width, result.height, bits_per_component, bytes_per_row, + color_space, kCGImageAlphaPremultipliedLast | kCGBitmapByteOrder32Big); + CGColorSpaceRelease(color_space); + CGContextDrawImage(context, CGRectMake(0, 0, result.width, result.height), image); + CGContextRelease(context); + + return result; +} + + + +- (IBAction)takePicture:(id)sender { + [self UpdatePhoto]; +} + +- (void)inputImageToModel:(image_data)image{ + float* out = interpreter->typed_input_tensor(0); + + const float input_mean = 127.5f; + const float input_std = 127.5f; + assert(image.channels >= wanted_input_channels); + uint8_t* in = image.data.data(); + + for (int y = 0; y < wanted_input_height; ++y) { + const int in_y = (y * image.height) / wanted_input_height; + uint8_t* in_row = in + (in_y * image.width * image.channels); + float* out_row = out + (y * wanted_input_width * wanted_input_channels); + for (int x = 0; x < wanted_input_width; ++x) { + const int in_x = (x * image.width) / wanted_input_width; + uint8_t* in_pixel = in_row + (in_x * image.channels); + float* out_pixel = out_row + (x * wanted_input_channels); + for (int c = 0; c < wanted_input_channels; ++c) { + out_pixel[c] = (in_pixel[c] - input_mean) / input_std; + } + } + } +} + +- (void)runModel { + double startTimestamp = [[NSDate new] timeIntervalSince1970]; + if (interpreter->Invoke() != kTfLiteOk) { + LOG(FATAL) << "Failed to invoke!"; + } + double endTimestamp = [[NSDate new] timeIntervalSince1970]; + total_latency += (endTimestamp - startTimestamp); + total_count += 1; + NSLog(@"Time: %.4lf, avg: %.4lf, count: %d", endTimestamp - startTimestamp, + total_latency / total_count, total_count); + + const int output_size = (int)labels.size(); + const int kNumResults = 5; + const float kThreshold = 0.1f; + + std::vector> top_results; + + float* output = interpreter->typed_output_tensor(0); + GetTopN(output, output_size, kNumResults, kThreshold, &top_results); + + std::vector> newValues; + for (const auto& result : top_results) { + std::pair item; + item.first = result.first; + item.second = labels[result.second]; + + newValues.push_back(item); + } + dispatch_async(dispatch_get_main_queue(), ^(void) { + [self setPredictionValues:newValues]; + }); +} + +- (void)dealloc { + [self teardownAVCapture]; +} + +- (void)didReceiveMemoryWarning { + [super didReceiveMemoryWarning]; +} + +- (void)viewDidLoad { + [super viewDidLoad]; + labelLayers = [[NSMutableArray alloc] init]; + + NSString* graph_path = FilePathForResourceName(model_file_name, model_file_type); + model = tflite::FlatBufferModel::BuildFromFile([graph_path UTF8String]); + if (!model) { + LOG(FATAL) << "Failed to mmap model " << graph_path; + } + LOG(INFO) << "Loaded model " << graph_path; + model->error_reporter(); + LOG(INFO) << "resolved reporter"; + + tflite::ops::builtin::BuiltinOpResolver resolver; + LoadLabels(labels_file_name, labels_file_type, &labels); + + tflite::InterpreterBuilder(*model, resolver)(&interpreter); + if (!interpreter) { + LOG(FATAL) << "Failed to construct interpreter"; + } + if (interpreter->AllocateTensors() != kTfLiteOk) { + LOG(FATAL) << "Failed to allocate tensors!"; + } + + [self attachPreviewLayer]; +} + +- (void)viewDidUnload { + [super viewDidUnload]; +} + +- (void)viewWillAppear:(BOOL)animated { + [super viewWillAppear:animated]; +} + +- (void)viewDidAppear:(BOOL)animated { + [super viewDidAppear:animated]; +} + +- (void)viewWillDisappear:(BOOL)animated { + [super viewWillDisappear:animated]; +} + +- (void)viewDidDisappear:(BOOL)animated { + [super viewDidDisappear:animated]; +} + +- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation { + return (interfaceOrientation == UIInterfaceOrientationPortrait); +} + +- (BOOL)prefersStatusBarHidden { + return YES; +} + +- (void)setPredictionValues:(std::vector>)newValues { + + const float leftMargin = 10.0f; + const float topMargin = 10.0f; + + const float valueWidth = 48.0f; + const float valueHeight = 18.0f; + + const float labelWidth = 246.0f; + const float labelHeight = 18.0f; + + const float labelMarginX = 5.0f; + const float labelMarginY = 5.0f; + + [self removeAllLabelLayers]; + + int labelCount = 0; + for (const auto& item : newValues) { + std::string label = item.second; + const float value = item.first; + const float originY = topMargin + ((labelHeight + labelMarginY) * labelCount); + const int valuePercentage = (int)roundf(value * 100.0f); + + const float valueOriginX = leftMargin; + NSString* valueText = [NSString stringWithFormat:@"%d%%", valuePercentage]; + + [self addLabelLayerWithText:valueText + originX:valueOriginX + originY:originY + width:valueWidth + height:valueHeight + alignment:kCAAlignmentRight]; + + const float labelOriginX = (leftMargin + valueWidth + labelMarginX); + + NSString *nsLabel = [NSString stringWithCString:label.c_str() + encoding:[NSString defaultCStringEncoding]]; + [self addLabelLayerWithText:[nsLabel capitalizedString] + originX:labelOriginX + originY:originY + width:labelWidth + height:labelHeight + alignment:kCAAlignmentLeft]; + + labelCount += 1; + if (labelCount > 4) { + break; + } + } +} + +- (void)removeAllLabelLayers { + for (CATextLayer* layer in labelLayers) { + [layer removeFromSuperlayer]; + } + [labelLayers removeAllObjects]; +} + +- (void)addLabelLayerWithText:(NSString*)text + originX:(float)originX + originY:(float)originY + width:(float)width + height:(float)height + alignment:(NSString*)alignment { + CFTypeRef font = (CFTypeRef) @"Menlo-Regular"; + const float fontSize = 12.0; + const float marginSizeX = 5.0f; + const float marginSizeY = 2.0f; + + const CGRect backgroundBounds = CGRectMake(originX, originY, width, height); + const CGRect textBounds = CGRectMake((originX + marginSizeX), (originY + marginSizeY), + (width - (marginSizeX * 2)), (height - (marginSizeY * 2))); + + CATextLayer* background = [CATextLayer layer]; + [background setBackgroundColor:[UIColor blackColor].CGColor]; + [background setOpacity:0.5f]; + [background setFrame:backgroundBounds]; + background.cornerRadius = 5.0f; + + [[self.view layer] addSublayer:background]; + [labelLayers addObject:background]; + + CATextLayer* layer = [CATextLayer layer]; + [layer setForegroundColor:[UIColor whiteColor].CGColor]; + [layer setFrame:textBounds]; + [layer setAlignmentMode:alignment]; + [layer setWrapped:YES]; + [layer setFont:font]; + [layer setFontSize:fontSize]; + layer.contentsScale = [[UIScreen mainScreen] scale]; + [layer setString:text]; + + [[self.view layer] addSublayer:layer]; + [labelLayers addObject:layer]; +} + +@end diff --git a/iOS-tflite/Info.plist b/iOS-tflite/Info.plist new file mode 100755 index 0000000..068487f --- /dev/null +++ b/iOS-tflite/Info.plist @@ -0,0 +1,48 @@ + + + + + CFBundleDevelopmentRegion + en + CFBundleDisplayName + tflite_photos_example + CFBundleExecutable + ${EXECUTABLE_NAME} + CFBundleIdentifier + $(PRODUCT_BUNDLE_IDENTIFIER) + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + ${PRODUCT_NAME} + CFBundlePackageType + APPL + CFBundleShortVersionString + 1.0 + CFBundleSignature + ???? + CFBundleVersion + 1.0 + LSRequiresIPhoneOS + + NSCameraUsageDescription + Capture images to detect object + NSPhotoLibraryAddUsageDescription + This app requires access to the photo library. + NSPhotoLibraryUsageDescription + This App classifies images from your photos library. + UIMainStoryboardFile + MainStoryboard_iPhone + UIRequiresFullScreen + + UIStatusBarHidden + + UISupportedInterfaceOrientations + + UIInterfaceOrientationPortrait + + UISupportedInterfaceOrientations~ipad + + UIInterfaceOrientationPortrait + + + diff --git a/iOS-tflite/MainStoryboard_iPhone.storyboard b/iOS-tflite/MainStoryboard_iPhone.storyboard new file mode 100755 index 0000000..1c829e6 --- /dev/null +++ b/iOS-tflite/MainStoryboard_iPhone.storyboard @@ -0,0 +1,56 @@ + + + + + + + + + + + + + Menlo-Regular + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/iOS-tflite/Podfile b/iOS-tflite/Podfile new file mode 100755 index 0000000..75323f3 --- /dev/null +++ b/iOS-tflite/Podfile @@ -0,0 +1,5 @@ +platform :ios, '8.0' +inhibit_all_warnings! + +target 'tflite_photos_example' + pod 'TensorFlowLite' diff --git a/iOS-tflite/main.mm b/iOS-tflite/main.mm new file mode 100755 index 0000000..1a9e542 --- /dev/null +++ b/iOS-tflite/main.mm @@ -0,0 +1,28 @@ +// Copyright 2017 The TensorFlow Authors. All Rights Reserved. + +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#import + +#import "CameraExampleAppDelegate.h" + +int main(int argc, char* argv[]) { + int retVal = 0; + + @autoreleasepool { + retVal = + UIApplicationMain(argc, argv, nil, NSStringFromClass([CameraExampleAppDelegate class])); + } + return retVal; +} diff --git a/iOS-tflite/tflite_photos_example.xcodeproj/project.pbxproj b/iOS-tflite/tflite_photos_example.xcodeproj/project.pbxproj new file mode 100755 index 0000000..b122682 --- /dev/null +++ b/iOS-tflite/tflite_photos_example.xcodeproj/project.pbxproj @@ -0,0 +1,395 @@ +// !$*UTF8*$! +{ + archiveVersion = 1; + classes = { + }; + objectVersion = 46; + objects = { + +/* Begin PBXBuildFile section */ + 1C3C9DCC1ED3AB4200B8B5FA /* main.mm in Sources */ = {isa = PBXBuildFile; fileRef = 1C3C9DCA1ED3AB4200B8B5FA /* main.mm */; }; + 1C99111C1ED3B0E600A6BFB9 /* MainStoryboard_iPhone.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 1C99111B1ED3B0E600A6BFB9 /* MainStoryboard_iPhone.storyboard */; }; + 1CA5EB931ED3ABFB00247A34 /* CoreMedia.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 1CA5EB921ED3ABFB00247A34 /* CoreMedia.framework */; }; + 1CB47D491ED3AD1700DF7666 /* AVFoundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 1CB47D481ED3AD1700DF7666 /* AVFoundation.framework */; }; + 1CDB2D491ED3A9CD007929E9 /* CameraExampleAppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 1CDB2D431ED3A9CD007929E9 /* CameraExampleAppDelegate.m */; }; + 1CDB2D4A1ED3A9CD007929E9 /* CameraExampleViewController.mm in Sources */ = {isa = PBXBuildFile; fileRef = 1CDB2D451ED3A9CD007929E9 /* CameraExampleViewController.mm */; }; + 1CDB2D4E1ED3AA35007929E9 /* Info.plist in Resources */ = {isa = PBXBuildFile; fileRef = 1CDB2D4D1ED3AA35007929E9 /* Info.plist */; }; + 2E12E3C82087CB8600FD9D4A /* graph.lite in Resources */ = {isa = PBXBuildFile; fileRef = 2E12E3C72087CB8600FD9D4A /* graph.lite */; }; + 2E92D8912088011F005F343A /* AppIcon.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 2E92D8902088011F005F343A /* AppIcon.xcassets */; }; + 2ED6BE3A207C23E000D3BF6F /* Photos.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 2ED6BE39207C23E000D3BF6F /* Photos.framework */; }; + AB30E2C6AA6147C90F25FFD2 /* libPods-tflite_photos_example.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 2FF33ED907C01C2D2EA78BBB /* libPods-tflite_photos_example.a */; }; + AC1F82661FBA3CBD0052BA77 /* labels.txt in Resources */ = {isa = PBXBuildFile; fileRef = AC1F82641FBA3CBD0052BA77 /* labels.txt */; }; +/* End PBXBuildFile section */ + +/* Begin PBXFileReference section */ + 1C0D73481ECCC41B008C1DAB /* CoreImage.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreImage.framework; path = System/Library/Frameworks/CoreImage.framework; sourceTree = SDKROOT; }; + 1C0D734A1ECCC460008C1DAB /* CoreGraphics.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreGraphics.framework; path = System/Library/Frameworks/CoreGraphics.framework; sourceTree = SDKROOT; }; + 1C3C9DCA1ED3AB4200B8B5FA /* main.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = main.mm; sourceTree = ""; }; + 1C564C0D1ED3A92E00087306 /* tflite_photos_example.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = tflite_photos_example.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 1C99111B1ED3B0E600A6BFB9 /* MainStoryboard_iPhone.storyboard */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.storyboard; path = MainStoryboard_iPhone.storyboard; sourceTree = ""; }; + 1CA45FFE1ECCC356002FA6A4 /* UIKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = UIKit.framework; path = System/Library/Frameworks/UIKit.framework; sourceTree = SDKROOT; }; + 1CA5EB921ED3ABFB00247A34 /* CoreMedia.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreMedia.framework; path = System/Library/Frameworks/CoreMedia.framework; sourceTree = SDKROOT; }; + 1CB47D481ED3AD1700DF7666 /* AVFoundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AVFoundation.framework; path = System/Library/Frameworks/AVFoundation.framework; sourceTree = SDKROOT; }; + 1CDB2D421ED3A9CD007929E9 /* CameraExampleAppDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CameraExampleAppDelegate.h; sourceTree = ""; }; + 1CDB2D431ED3A9CD007929E9 /* CameraExampleAppDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CameraExampleAppDelegate.m; sourceTree = ""; }; + 1CDB2D441ED3A9CD007929E9 /* CameraExampleViewController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CameraExampleViewController.h; sourceTree = ""; }; + 1CDB2D451ED3A9CD007929E9 /* CameraExampleViewController.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = CameraExampleViewController.mm; sourceTree = ""; }; + 1CDB2D4D1ED3AA35007929E9 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; + 2E12E3C72087CB8600FD9D4A /* graph.lite */ = {isa = PBXFileReference; lastKnownFileType = file; path = graph.lite; sourceTree = ""; }; + 2E92D8902088011F005F343A /* AppIcon.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = AppIcon.xcassets; sourceTree = ""; }; + 2ED6BE39207C23E000D3BF6F /* Photos.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Photos.framework; path = System/Library/Frameworks/Photos.framework; sourceTree = SDKROOT; }; + 2FF33ED907C01C2D2EA78BBB /* libPods-tflite_photos_example.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-tflite_photos_example.a"; sourceTree = BUILT_PRODUCTS_DIR; }; + 3BA8BF92C84895BFE59D8236 /* libPods-tflite_camera_example.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-tflite_camera_example.a"; sourceTree = BUILT_PRODUCTS_DIR; }; + 3BC5BE4BBD09374D3E98F082 /* Pods-tflite_camera_example.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-tflite_camera_example.debug.xcconfig"; path = "Pods/Target Support Files/Pods-tflite_camera_example/Pods-tflite_camera_example.debug.xcconfig"; sourceTree = ""; }; + 55ED318E8D29C8AFEF03DF1E /* Pods-tflite_camera_example.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-tflite_camera_example.release.xcconfig"; path = "Pods/Target Support Files/Pods-tflite_camera_example/Pods-tflite_camera_example.release.xcconfig"; sourceTree = ""; }; + 7B75D9AAB5B7890D81174E26 /* Pods-tflite_photos_example.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-tflite_photos_example.release.xcconfig"; path = "Pods/Target Support Files/Pods-tflite_photos_example/Pods-tflite_photos_example.release.xcconfig"; sourceTree = ""; }; + 92A36BF8A50AF5A52BB51EA5 /* Pods-tflite_photos_example.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-tflite_photos_example.debug.xcconfig"; path = "Pods/Target Support Files/Pods-tflite_photos_example/Pods-tflite_photos_example.debug.xcconfig"; sourceTree = ""; }; + AC1F82641FBA3CBD0052BA77 /* labels.txt */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = labels.txt; sourceTree = ""; }; +/* End PBXFileReference section */ + +/* Begin PBXFrameworksBuildPhase section */ + 1C564C0A1ED3A92E00087306 /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + 2ED6BE3A207C23E000D3BF6F /* Photos.framework in Frameworks */, + 1CB47D491ED3AD1700DF7666 /* AVFoundation.framework in Frameworks */, + 1CA5EB931ED3ABFB00247A34 /* CoreMedia.framework in Frameworks */, + AB30E2C6AA6147C90F25FFD2 /* libPods-tflite_photos_example.a in Frameworks */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXFrameworksBuildPhase section */ + +/* Begin PBXGroup section */ + 24D7686C331131624F4454A0 /* Frameworks */ = { + isa = PBXGroup; + children = ( + 2ED6BE39207C23E000D3BF6F /* Photos.framework */, + 1CB47D481ED3AD1700DF7666 /* AVFoundation.framework */, + 1CA5EB921ED3ABFB00247A34 /* CoreMedia.framework */, + 1C0D734A1ECCC460008C1DAB /* CoreGraphics.framework */, + 1C0D73481ECCC41B008C1DAB /* CoreImage.framework */, + 1CA45FFE1ECCC356002FA6A4 /* UIKit.framework */, + 3BA8BF92C84895BFE59D8236 /* libPods-tflite_camera_example.a */, + 2FF33ED907C01C2D2EA78BBB /* libPods-tflite_photos_example.a */, + ); + name = Frameworks; + sourceTree = ""; + }; + 3E9FC355632FB928EA23BEED /* Pods */ = { + isa = PBXGroup; + children = ( + 3BC5BE4BBD09374D3E98F082 /* Pods-tflite_camera_example.debug.xcconfig */, + 55ED318E8D29C8AFEF03DF1E /* Pods-tflite_camera_example.release.xcconfig */, + 92A36BF8A50AF5A52BB51EA5 /* Pods-tflite_photos_example.debug.xcconfig */, + 7B75D9AAB5B7890D81174E26 /* Pods-tflite_photos_example.release.xcconfig */, + ); + name = Pods; + sourceTree = ""; + }; + 591157921CF4011C00C31E3A = { + isa = PBXGroup; + children = ( + 2E92D8902088011F005F343A /* AppIcon.xcassets */, + 1C99111B1ED3B0E600A6BFB9 /* MainStoryboard_iPhone.storyboard */, + 1C3C9DCA1ED3AB4200B8B5FA /* main.mm */, + 1CDB2D4D1ED3AA35007929E9 /* Info.plist */, + 1CDB2D421ED3A9CD007929E9 /* CameraExampleAppDelegate.h */, + 1CDB2D431ED3A9CD007929E9 /* CameraExampleAppDelegate.m */, + 1CDB2D441ED3A9CD007929E9 /* CameraExampleViewController.h */, + 1CDB2D451ED3A9CD007929E9 /* CameraExampleViewController.mm */, + 59A3CFF31CF4E68100C4259F /* data */, + 5911579C1CF4011C00C31E3A /* Products */, + 3E9FC355632FB928EA23BEED /* Pods */, + 24D7686C331131624F4454A0 /* Frameworks */, + ); + sourceTree = ""; + }; + 5911579C1CF4011C00C31E3A /* Products */ = { + isa = PBXGroup; + children = ( + 1C564C0D1ED3A92E00087306 /* tflite_photos_example.app */, + ); + name = Products; + sourceTree = ""; + }; + 59A3CFF31CF4E68100C4259F /* data */ = { + isa = PBXGroup; + children = ( + 2E12E3C72087CB8600FD9D4A /* graph.lite */, + AC1F82641FBA3CBD0052BA77 /* labels.txt */, + ); + path = data; + sourceTree = ""; + }; +/* End PBXGroup section */ + +/* Begin PBXNativeTarget section */ + 1C564C0C1ED3A92E00087306 /* tflite_photos_example */ = { + isa = PBXNativeTarget; + buildConfigurationList = 1C564C351ED3A92E00087306 /* Build configuration list for PBXNativeTarget "tflite_photos_example" */; + buildPhases = ( + 66DAEAAEE9EF6550C3A061E0 /* [CP] Check Pods Manifest.lock */, + 1C564C091ED3A92E00087306 /* Sources */, + 1C564C0A1ED3A92E00087306 /* Frameworks */, + 1C564C0B1ED3A92E00087306 /* Resources */, + ); + buildRules = ( + ); + dependencies = ( + ); + name = tflite_photos_example; + productName = tflite_camera_example; + productReference = 1C564C0D1ED3A92E00087306 /* tflite_photos_example.app */; + productType = "com.apple.product-type.application"; + }; +/* End PBXNativeTarget section */ + +/* Begin PBXProject section */ + 591157931CF4011C00C31E3A /* Project object */ = { + isa = PBXProject; + attributes = { + LastSwiftUpdateCheck = 0830; + LastUpgradeCheck = 0830; + ORGANIZATIONNAME = Google; + TargetAttributes = { + 1C564C0C1ED3A92E00087306 = { + CreatedOnToolsVersion = 8.3.2; + DevelopmentTeam = EQHXZ8M8AV; + ProvisioningStyle = Manual; + }; + }; + }; + buildConfigurationList = 591157961CF4011C00C31E3A /* Build configuration list for PBXProject "tflite_photos_example" */; + compatibilityVersion = "Xcode 3.2"; + developmentRegion = English; + hasScannedForEncodings = 0; + knownRegions = ( + en, + Base, + ); + mainGroup = 591157921CF4011C00C31E3A; + productRefGroup = 5911579C1CF4011C00C31E3A /* Products */; + projectDirPath = ""; + projectRoot = ""; + targets = ( + 1C564C0C1ED3A92E00087306 /* tflite_photos_example */, + ); + }; +/* End PBXProject section */ + +/* Begin PBXResourcesBuildPhase section */ + 1C564C0B1ED3A92E00087306 /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 2E92D8912088011F005F343A /* AppIcon.xcassets in Resources */, + 2E12E3C82087CB8600FD9D4A /* graph.lite in Resources */, + 1C99111C1ED3B0E600A6BFB9 /* MainStoryboard_iPhone.storyboard in Resources */, + 1CDB2D4E1ED3AA35007929E9 /* Info.plist in Resources */, + AC1F82661FBA3CBD0052BA77 /* labels.txt in Resources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXResourcesBuildPhase section */ + +/* Begin PBXShellScriptBuildPhase section */ + 66DAEAAEE9EF6550C3A061E0 /* [CP] Check Pods Manifest.lock */ = { + isa = PBXShellScriptBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + inputPaths = ( + "${PODS_PODFILE_DIR_PATH}/Podfile.lock", + "${PODS_ROOT}/Manifest.lock", + ); + name = "[CP] Check Pods Manifest.lock"; + outputPaths = ( + "$(DERIVED_FILE_DIR)/Pods-tflite_photos_example-checkManifestLockResult.txt", + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n"; + showEnvVarsInLog = 0; + }; +/* End PBXShellScriptBuildPhase section */ + +/* Begin PBXSourcesBuildPhase section */ + 1C564C091ED3A92E00087306 /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 1CDB2D4A1ED3A9CD007929E9 /* CameraExampleViewController.mm in Sources */, + 1CDB2D491ED3A9CD007929E9 /* CameraExampleAppDelegate.m in Sources */, + 1C3C9DCC1ED3AB4200B8B5FA /* main.mm in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXSourcesBuildPhase section */ + +/* Begin XCBuildConfiguration section */ + 1C564C361ED3A92E00087306 /* Debug */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 92A36BF8A50AF5A52BB51EA5 /* Pods-tflite_photos_example.debug.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ANALYZER_NONNULL = YES; + CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; + DEVELOPMENT_TEAM = EQHXZ8M8AV; + INFOPLIST_FILE = Info.plist; + IPHONEOS_DEPLOYMENT_TARGET = 10.3; + LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; + PRODUCT_BUNDLE_IDENTIFIER = "com.pf.tf-photos-example"; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; + SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + SWIFT_VERSION = 3.0; + }; + name = Debug; + }; + 1C564C371ED3A92E00087306 /* Release */ = { + isa = XCBuildConfiguration; + baseConfigurationReference = 7B75D9AAB5B7890D81174E26 /* Pods-tflite_photos_example.release.xcconfig */; + buildSettings = { + ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; + CLANG_ANALYZER_NONNULL = YES; + CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; + DEVELOPMENT_TEAM = EQHXZ8M8AV; + INFOPLIST_FILE = Info.plist; + IPHONEOS_DEPLOYMENT_TARGET = 10.3; + LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks"; + PRODUCT_BUNDLE_IDENTIFIER = "com.pf.tf-photos-example"; + PRODUCT_NAME = "$(TARGET_NAME)"; + SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule"; + SWIFT_VERSION = 3.0; + }; + name = Release; + }; + 591157B01CF4011D00C31E3A /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CLANG_WARN_UNREACHABLE_CODE = YES; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; + COPY_PHASE_STRIP = NO; + DEBUG_INFORMATION_FORMAT = dwarf; + ENABLE_STRICT_OBJC_MSGSEND = YES; + ENABLE_TESTABILITY = YES; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_DYNAMIC_NO_PIC = NO; + GCC_NO_COMMON_BLOCKS = YES; + GCC_OPTIMIZATION_LEVEL = 0; + GCC_PREPROCESSOR_DEFINITIONS = ( + "DEBUG=1", + "$(inherited)", + ); + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + HEADER_SEARCH_PATHS = ( + "$(inherited)", + ../../../../../../, + ../../../downloads/flatbuffers/include/, + ../../../downloads/eigen/, + ../../../downloads/, + ); + IPHONEOS_DEPLOYMENT_TARGET = 8.0; + MTL_ENABLE_DEBUG_INFO = YES; + ONLY_ACTIVE_ARCH = YES; + SDKROOT = iphoneos; + TARGETED_DEVICE_FAMILY = "1,2"; + }; + name = Debug; + }; + 591157B11CF4011D00C31E3A /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_ENABLE_OBJC_ARC = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INFINITE_RECURSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN_SUSPICIOUS_MOVE = YES; + CLANG_WARN_UNREACHABLE_CODE = YES; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; + COPY_PHASE_STRIP = NO; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + ENABLE_NS_ASSERTIONS = NO; + ENABLE_STRICT_OBJC_MSGSEND = YES; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_NO_COMMON_BLOCKS = YES; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + GCC_WARN_UNUSED_VARIABLE = YES; + HEADER_SEARCH_PATHS = ( + "$(inherited)", + ../../../../../../, + ../../../downloads/flatbuffers/include/, + ../../../downloads/eigen/, + ../../../downloads/, + ); + IPHONEOS_DEPLOYMENT_TARGET = 8.0; + MTL_ENABLE_DEBUG_INFO = NO; + SDKROOT = iphoneos; + TARGETED_DEVICE_FAMILY = "1,2"; + VALIDATE_PRODUCT = YES; + }; + name = Release; + }; +/* End XCBuildConfiguration section */ + +/* Begin XCConfigurationList section */ + 1C564C351ED3A92E00087306 /* Build configuration list for PBXNativeTarget "tflite_photos_example" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 1C564C361ED3A92E00087306 /* Debug */, + 1C564C371ED3A92E00087306 /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; + 591157961CF4011C00C31E3A /* Build configuration list for PBXProject "tflite_photos_example" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 591157B01CF4011D00C31E3A /* Debug */, + 591157B11CF4011D00C31E3A /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; +/* End XCConfigurationList section */ + }; + rootObject = 591157931CF4011C00C31E3A /* Project object */; +}