Is there a way to hide assets from users within my Mac App? - objective-c

I have developed a simple app for Mac which uses a browser window to display some content. Now the assets (images etc.) are visible to anyone who receives the app and discloses the content in finder using 'show package content'.
Is there a way to prevent this? Can I hide it or encapsulate it somehow using code or some XCode function?

A trivial way would be to change the extension on your files so the system doesn't recognize them as images. You'd then have to load the images as data and convert them to images in code, which would be a bit of a pain.
A more rigorous solution would be to encrypt the images in your app bundle, then write a utility function that loads and decrypts images.

Here's another option.
You can zip all the assets. Use whatever is easiest e.g. pkzip or gzip or even just tar it all. Then you hide a lot of info and, if you want to go the extra step, it is easy to encrypt the zipped file and there are lots of libraries around to include in your project and use to unzip it with.
It should be easy to read assets directly from the zipped file, but if you need them individually you could e.g. put a single file / resource inside a zip or you could unzip it. You could even unzip to temporary space and remove it all when the app quits if you have really sensitive stuff that is too big to fit in memory.
** EDIT **
Java works this way right. A jar file is just a renamed zip and it often contains all of the resources the app needs, and it seems to be working there. So if that is a guide performance should not be too bad.

Related

How do I disable PNG file "optimization" when building in MonoTouch?

I am making an application which uses a large amount of PNG file resources. In order to minimize the size of my binary, I have manually optimized all of my files, and was able to reduce the resources folder size to almost 20% of the original non-optimized size.
However, when building my application for device (not simulator) testing, the build process attempts to "optimize" my PNG files by running what seems to be a modified version of pngcrush, which not only makes the build process almost five minutes longer, and makes most of my files larger, but also makes some files unusable by doing alpha premultiplication, which I don't need, since I'm using the alpha values for purposes different than transparency.
I found that it is possible to disable this step in xcode, were I making an objective-c project, by changing "Compress PNG Files" to "No" in the Build Settings as described in this webpage.
However, I have not been able to find how to modify this setting in the MonoDevelop project.
How do I disable this PNG "optimization" step when building from MonoDevelop?
This feature is being worked on (in MonoDevelop). However the iPhone addin (for MonoDevelop) is not open source so hacking it yourself won't work.
Right now you have two options.
Moving the image directly to the device during development so they won't be deployed each time (along with the application). You can see how to implement this hack from this article.
Hack your iphone-optimize script (that's what MonoDevelop calls). The script tis located in your Xcode directory (if you have several version then the one specified in MonoDevelop's SDK locations is being used).
For this you need to:
Backup your existing (original) PNG;
Copy the optimized PNG as your 'new' originals;
Backup the iphoneos-optimize script;
Edit that script to ignore the PNG files (i.e. not execute pngcrush)
Keep in mind that updating Xcode will replace the script - so you'll need to re-edit it after updates.
Half year ago it was not possible.
Yet, since MonoDevelop sources are open, it is possible to patch it and compile from sources.

What does iOS do when an app is "Installing" and is it possible to programmatically control it?

I understand it may be unpacking some sort of compressed package into the file system (and due to the mobile nature I suppose it may be quite aggressive compression to reduce download time). But does it run any sort of preflight scripts? I suppose it does stuff like register the info.plist, add a pane in Settings.app if you've specified one, and the app's global URL and file type reception registration.
The reason why I'm interested is twofold: curiosity (would there be a way of seeing precisely what's going on? Has anyone investigated this?) and making an installation script. I'm constructing a dictionary app using Core Data (I've thought about this a lot, trust me, I want to use Core Data) and I'd like to have a way of nicely generating the Core Data store from the original XML without degrading the user experience by having some kind of "initializing app". Furthermore I'd like to deploy the dictionary compressed and then uncompress it on the device, to keep it under the 20 mb over the air download limit.
I suppose I could generate the Core Data store on my simulator or dev phone and then add it to the bundle, though that way still seems less than neat. Hence why it would be nice for iOS to handle it for me
Anyway, thoughts?
Whatever the OS does during install, you can be certain that Apple does not offer developers any hook into the operation. There is no way to run any code of your own (install script etc.) until the user first launches your app manually. So do whatever initialization needs to be done on first launch.
The .ipa packages you submit to Apple are already compressed (they are just ZIP files with another file extension) so it should not be necessary to compress a text file yourself to stay under the 20 MB limit. Compressing it twice probably won't help much in terms of file size.

Providing an embedded webkit with resources from memory

I'm working on an application that embeds WebKit (via the Gtk bindings). I'm trying to add support for viewing CHM documents (Microsoft's bundled HTML format).
HTML files in such documents have links to images, CSS etc. of the form "/blah.gif" or "/layout.css" and I need to catch these to provide the actual data. I understand how to hook into the "resource-request-starting" signal and one option would be to unpack parts of the document to temporary files and change the uri at this point to point at these files.
What I'd like to do, however, is provide WebKit with the relevant chunk of memory. As far as I can see, you can't do this by catching resource-request-starting, but maybe there's another way to hook in?
An alternative is to base64-encode the image into a data: URI. It's not exactly better than using a temporary file, but it may be simpler to code.

Flash Builder asset files

Where is the best place to store your dependent files like xml, css and assets? I have been storing them in the src folder which works ok as they get moved to the debug folder when I build.
I can't find any info on this but I'm thinking that src is not really the place for these.
For what it's worth, here is the way Flash Catalyst CS5 (1.0.0) organizes its packages and assets when it generates a FXP:
src(default package)assetsgraphicsimagescom.adobe.flashcatalyst.componentscomponentsskins
Where graphics contains any .fxg files, and images holds all other image files. An auto-generated .css file (in my case, for embedding a font), was placed inside the (default package).
I would assume that this is how the Adobe team would expect things to be organized. However, you may also want to check out how they do it in Flash Catalyst "Panini", since the big thing with that release is the two-way workflow with Flash Builder "Burrito".

Writing to files in bundle?

If you scroll down to the section 'Writing to Files and URLs' at this link, would the path varaible have to be a file on disk? Is it possible to write to a file in the bundle or must it always be deployed first?
You can write files to the application bundle as much as you'd like. Just get the path of the file through NSBundle's pathForResource:ofType: method and you can write to that file. If you want just the directory of the bundle, use resourcePath.
You don't want to do this, though. There are various reasons, but you'll break code signing, which is a big one. You should use the established conventions instead (such as writing to Library:Application Support:Your App).
EDIT: For a (possibly) more convincing reason of not to do this... When I was first learning Cocoa programming, I saved to the bundle because I didn't want to bother with the Library. It got really annoying, though, because every time you make a change to your program, you lose all of your saved data/settings for that program (assuming you're not using NSUserDefaults for preferences). I kept having to move it over from the old version to the new one. By using the Library, you don't have to worry about this.
The bundle is on disk; it's just the ".app" directory. You should not write to files in this directory, however. While currently possible on Mac, it will break code signing. On iPhone, you already can't write into your own bundle, and we should expect to see this limitation in the future on Mac. You should write your application files into various directories under ~/Library or ~/Documents as appropriate. See the File System Programming Guide for guidance.