I am creating one application using airdrop feature, I want to pass one message(NSString) from one device to other device. I had completed that part, but I want restrict this feature for my application only. Currently what happen, when I am sending NSString via airdrop (let say Device A) in near by device, the other Device B can receive this string even if my application is not installed in it.
My requirement is to share one message from one device to other device only and this thing happen via airdrop for my application only. Please give suggestion. Thanks..!!
To ensure that only your app can open this "payload" you must register a new UTI with the system, and supply that same UTI when providing the item to share to UIActivityViewcontroller (using the UIActivityItemSource protocol). The AirDrop sample code has an example of registering a new UTI and using it (see the "Sending/receiving an instance of a custom class as data via AirDrop" parts of the sample)
Related
I'm building a sandboxed macOS app with Swift, which contains a child app inside.
What I want to implement is:
Parent can launch multiple child apps
Parent send different content to each child app to show
Both parent and child app have their own UIs.
Implementation way I've been thinking about:
Distributed Notification
Distributed notification with user info objects are denied by sandbox.
CFMessagePort
It requires both parent and child app are in the same app group, and signed with proper provision profiles. But on Xcode it is always None required on the provision profile settings so nowhere to change the settings.
Besides, there is no documents or posts explaining how to use CFMessagePort in Swift. I tried the code below but it crashes everytime as it's denied by sandbox.
let portName = "{team_identifier}.{app_group_identifier}.{port_name}"
let remote = CFMessagePortCreateRemote(nil, portName as CFString)
var returnData: Unmanaged<CFData>? = nil
if kCFMessagePortSuccess == CFMessagePortSendRequest(remote, 0, data as CFData, 1, 1, CFRunLoopMode.defaultMode.rawValue, &returnData) && nil != returnData {
}
NSXPCConnection
I don`t think XPC works for this situation, as XPC is designed to communicate between a service running invisible and a client app, while the service is bundled into the app. I doubt it would work for the parent-child model.
So, is there any better way to achieve my target? I feel I should go with CFMessagePort but I also need some more help on how to use it with Swift. Thanks!
I think your best bet would be to use Apple Events, as I do. Sandboxed apps can receive and send Apple Events to themselves by default, but they cannot send Apple Events to other applications. However, they can send Apple Events if
"you request a scripting-targets entitlement or an apple-events
temporary exception entitlement. In the same way, regardless of
whether your app is sandboxed, any external sandboxed app that
attempts to interact with your app must also request the appropriate
entitlements to do so."
You can read all about it on the Technical Q&A note QA1888.
I would also recommend that you check this tutorial to handle Apple Events in a sandboxed app and this tutorial (part 1 and part 2) how to handle the foundation classes you can use to build Apple Events in Swift.
If you want a more in-depth explanation and including sample code (however, it is mostly in C), you can refer to Apple's references pages, namely:
Apple Event Manager
AppleScript Overview (explains in
detail macOS scripting architecture)
Apple Events Programming
Guide (full reference for building, sending and receiving Apple
Events)
If you run into trouble, let us know as I use this old but proven technology to handle most IPC between my main app and its helpers.
I have an app that I have been working on and I am now at the point that I want to integrate some interaction with an external device via the dock connector. The device that I am using (the iDive 300) conforms to the Made For iPod program. I have written a separate simple app based on the EADemo code to gather information about the device. However, when I run this app the iDive reports nothing for the Name, Serial Number, Firmware, etc and also says that no protocols were found. I know this simple app is working correctly because I have connected to several other external devices and the Name, serial number, etc is populated for each device.
The other odd thing is that the iDive seems to work properly when plugged into my iPhone 4 (i.e. it will increase the volume and play songs and videos found on my iPhone via the buttons on the device). Shouldn't this mean that some protocol is in place for this device to communicate with the iPhone? Is it all possible for me to read data from this device (e.g. capture when the 'play','menu', or other buttons are pressed) if I don't know the protocol?
I am completely new to the External Accessories framework and any help is appreciated!
You should autopsy the app that is associated with iDive. In its info.plist, there should be a key:
UISupportedExternalAccessoryProtocols
whose value is an array(See this for the formal definition), and within it lies a string whose value looks like a reversed domain name, as the device protocol.
You should edit your Info.plist, add the key('Supported external accessory protocols' in plain English) for an array, put in the protocol as its item.
There's no guarantee that an accessory actually uses EA. It may communicate using the protocols defined by Apple.
EA is only necessary if you want to communicate using your own proprietary protocol.
Check the EADemo example from Apple... If it doesn't show up in the demo app, it's not EA.
Lets say I have a pdf file on an iOS device that I want to transmit wirelessly to another iOS device.
Is there a way to simply get an NSURL from the file on device A so that device B can directly access it?
I'd like to skip the step of having to post it to a server first.
Yes, this is possible by making device A into an ad hoc HTTP server. You can find implementation help here:
http://code.google.com/p/cocoahttpserver/
It works quite well, but needs some fiddling.
I built an app which I can add images and texts, what I would like to do is to pack a data from this app (which I can do that by serializing an object to a file) and send it non-synchronically to another app in another IPhone and open it there (without using the mail nor the internet).
for example if I had MMS on IPhone I could do that by sending the file as MMS and set my app to open files with specific post-fix I choose.
Please help, Thanks.
What do you mean by "without using the internet"? You could use NSNetServices to establish connections between devices, and send whatever you want between them. This relies on the TCP/IP protocol though, but does not use HTTP. So if you mean "without going via HTTP", this should be an alternative:
http://developer.apple.com/library/ios/#documentation/Networking/Conceptual/NSNetServiceProgGuide/Articles/ResolvingServices.html#//apple_ref/doc/uid/20001078-SW1
you use an url scheme for small data, or the new UIDocumentInteractionController
While working on iphone security architecture, i came to know that i can run applications from other applications in iphone. referring to the following url http://iosdevelopertips.com/cocoa/launching-other-apps-within-an-iphone-application.html
for example, i can put a link in a website with following hyperlink
skype://
will result skype to run and call at particular number. Now i have few concerns here.
is there a shell running in background in iphone, so that it allows other application to run basic app commands.
if the above statement is true then how can i enable or run commands directly into iphone shell?
if above statements are false, then could you please explain how these commands are being executed?
is this part of iPhone SDK? or this funcationality is iPhone OS
This is functionality of the iPhone OS. Applications register themselves as URL Handlers for particular protocols. In this case the Skype app is registered to handle skype:// URL protocols.
An Application registers itself as a protocol handler via the CFBundleURLTypes key in it's Info.plist. See here.
The OS reads this key when your application is installed.
Whenever a URL for that protocol is encountered and tapped on, the OS will launch your App and your Application Delegate will be sent the application:handleOpenURL: message.
It is then up to your Application to correctly decode the URL and perform the correct action.
PS. There is virtually identical functionality available in Mac OS X, with the additional possiblity for URLs to be sent to already running applications.
A shell can be spawned with system or popen etc. Of course, because the apps are sandboxed, fork() is denied so the shell won't be accessible from any AppStore apps.
However, there are lots of stuff running in background on the iPhoneOS. One of them is SpringBoard.app, which is the "home screen" you see on start up. Actually SpringBoard.app is responsible for much more stuff than just displaying the home screen, one of them is to receive and deliver URL requests.
The registration process has been described by #Alan. But under hood, when a URL request is issued by an app, the following will happen:
The app, knowing itself cannot handle a particular URL, calls -[UIKit openURL:] to delegate the open request to others.
UIKit will package the URL request into a GSEvent (an IPC mechanism), and then dispatch it to SpringBoard.
SpringBoard, receiving this GSEvent, calls -[SpringBoard applicationOpenURL:].
This method will check if the URL is well-form and safe (stuff like tel://*5005*78283# will be rejected, for example). If it is valid, the action will be performed (dial a number, subscribe to a calendar, open an app, etc.)
what alee is asking about, I guess, is the "mailto://". when you put this in the browser address bar it does not do anything, but if you put it as a link and click on it, it lunches the mail app. why does the mail app have this behavior?