I used AVFoundation framework delegate methods to read QR Code.It is reading almost all QR codes & giving resulted data for them. But when I try with some QR code(eg. below QR image) , it is predicting that it is QR code but does not give any data for it.
Your sample is triggering an internal (C++) exception.. it seems to be getting caught around [AVAssetCache setMaxSize:] which suggests either the data in this particular sample is corrupt, or it's just to large for AVFoundation to handle.
As it's an internal exception it is (mostly) failing silently. The exception occurs when you try to extract the stringValue from your AVMetadataMachineReadableCodeObject.
So if you test for the existence of your AVMetadataMachineReadableCodeObject, you will get YES, whereas if you test for stringValue you will get NO.
AVMetadataMachineReadableCodeObject *readableObject =
(AVMetadataMachineReadableCodeObject *)[self.previewLayer
transformedMetadataObjectForMetadataObject:metadataObject];
BOOL foundObject = readableObject != nil;
//returns YES
BOOL foundString = readableObject.stringValue != nil;
//returns NO + triggers internal exception
It's probably best to test for the string, rather than the object, and ignore any result that returns NO.
update
In your comment you ask about native framework solution that will read this barcode. AVFoundation is the native framework for barcode reading, so if it fails on your sample, you will have to look for third-party solutions.
zxing offers an iOS port but it looks to be old and unsupported.
zbarSDK used to be a good solution but also seems to be unsupported past ios4. As AVFoundation now has built-in barcode reading, this is unsurprising.
This solution by Accusoft does read the sample but is proprietary and really pricey.
I do wonder about the content of you sample though - it looks either corrupt or some kind of exotic encoding...
Related
I'm writing an iOS Swift app to fetch metadata from DJI drone images. I'm trying to access the Xmp.drone-dji.X metadata. The iOS/Swift CGImageSource and CGImageMetadata libraries/classes get almost all of the metadata out of the image but not the Xmp.drone-dji. When I get a list of tags, those tag/values are not listed. I know the tags/data are in the images because I've examined the images using exif, exiv2, etc.
Any suggestions?
Here is the code I'm using so far:
result.itemProvider.loadDataRepresentation(forTypeIdentifier: UTType.image.identifier)
{ data, err in
if let data = data {
let src = CGImageSourceCreateWithData(data as CFData,nil)!
let md = CGImageSourceCopyPropertiesAtIndex(src,0,nil) as! NSDictionary
let md2 = CGImageSourceCopyMetadataAtIndex(src,0,nil)
}
Thanks,
Bobby
So, after a lot of searching, trial and error, I have found an answer.
I was not able to get any of the CGImage swift libraries to extract this info for me.
Adobe has a c++ library that parses xmp/xml data out of images and it purports to support iOS. I didnt want the hassle of building c++ on iOS, importing that into Xcode and then dealing with the fact that thrown errors do not propagate well from c++/objectiveC to Swift.
So, at a high level, I did the following:
get the bytes of the raw image as CFData or Data then cast to a String
then use String.range() to find beginning of XML/XMP data in image
searching for substring <?xpacket begin
use String.range() to find end of XML/XMP data in image
using substring <?xpacket end.*?>
Extract the XML document out of image data String
Use Swift XMLParser class to parse the XML and then copying attributes and
elements as necessary. I just simply added what I wanted to already
existing Exif NSdictionary returned by CGImage classes.
Happy to answer questions on this approach. My code will eventually be uploaded to GitHub under OpenAthenaIOS project.
Bobby
Does someone know how to change WebRTC (https://cocoapods.org/pods/libjingle_peerconnection) video source?
I am working on an screen sharing app.
At the moment, I retrieve the rendered frames in real-time in CVPixelBuffer. Does someone know how I could add my frames as video source please?
Is it possible to set an other video source instead of camera device source ? Is yes, which format the video has to be and how to do it ?
Thanks.
var connectionFactory : RTCPeerConnectionFactory = RTCPeerConnectionFactory()
let videoSource : RTCVideoSource = factory.videoSource()
videoSource.capturer(videoCapturer, didCapture: videoFrame!)
Mounis answer is wrong. This leads to nothing. At least not at the time of this writing. There is simply nothing happening.
In fact, you would need to satisfy this delegate
- (void)capturer:(RTCVideoCapturer *)capturer didCaptureVideoFrame:(RTCVideoFrame *)frame;
(Note the difference to the Swift version: didCapture vs. didCaptureVideoFrame)
Since this delegate is for unclear reasons not available at Swift level (the compiler says you have to use didCapture, since it has been renamed from didCaptureVideoFrame with Swift3) you have to put the code int an ObjC class. I did copy this and this (which is a part of this sample project)into my project, made my videoCapturer an instance of ARDBroadcastSampleHandler
self.videoCapturer = ARDExternalSampleCapturer(delegate: videoSource)
and within the capture callback I'm calling it
let capturer = self.videoCapturer as? ARDExternalSampleCapturer
capturer?.didCapture(sampleBuffer)
To start, here is my code:
var buffer = malloc(interop.sizeof(interop.types.UTF8CString));
var fillBuffer = mac.getBytes(buffer);
var bytes = new interop.Reference(interop.types.UTF8CString, buffer);
var hexMac = bytes[0];
The variable 'Mac' is an NSData objected retrieved from CoreBluetooth. It is the scan response from a BLE device, which contains the peripheral's MAC address (00:0b:57:a2:fb:a0).
This problem is linked to THIS question I had posted earlier.
The solution provided is great; however, I cannot seem to implement this in nativescript :
(instancetype)stringWithFormat:(NSString *)format, ...;
Intellisense tells me the method doesnt exist on type NSString.
Due to that issue, I decided to go another route (as you can tell). I am filling a buffer with the bytes of the MAC address. In the code above, bytes[0] equates to 0xb57a2fba0.
I am now trying to convert that (which is an interop.Reference) into a string that I can store on the back-end (preferably in the xx:xx:xx:xx:xx format).
I have been at this all weekend, and cannot seem to find a solution. I even broke down objc!foundation.d.ts to figure out if stringWithFormat was supported, to no avail.
The nativescript community slack was unable to provide a resolution as well.
Please help if you can!
I don't know anything about NativeScript at all, but given the other code you wrote, I assume you're calling +alloc first, and so mean to use -initWithFormat: (an instance method that initializes) rather than +stringWithFormat: (a class method which handles allocation and initialization).
I would like to be able to redirect my logging statements to a file so that I can retrieve them when my app runs standalone (i.e. is not attached to Xcode). I have discovered (thank you Stackoverflow) that freopen can be used to accomplish this.
If I create a new Xcode project and add the code to redirect stderr then everything works as expected.
However, when I add the redirection code to my existing, bluetooth project I am having trouble. The file is being created and I can retrieve it using iTunes or Xcode's Devices window, but it is of size 0. If I explicitly close the file then the text that I wrote actually makes it into the file. It is as though iOS is not flushing the file when the app is terminated. I suspect that the trouble stems from the fact that I have enabled background processing. Can anyone help me to understand this?
Here is my code:
let pathes = NSSearchPathForDirectoriesInDomains(.DocumentDirectory, .UserDomainMask, true);
let filePath = NSURL(fileURLWithPath: pathes[0]).URLByAppendingPathComponent("Test.log")
freopen(filePath.path!, "a", stderr);
fputs("Hello, Samantha!\r\n", stderr);
struct StderrOutputStream: OutputStreamType {
static let stream = StderrOutputStream()
func write(string: String) {fputs(string, stderr)}
}
var errStream = StderrOutputStream.stream
print("Hello, Robert", toStream: &errStream)
fclose(stderr) // Without this the text does not make it into the file.
I'd leave this as a comment, but have you looked into NSFileHandle? It sounds like you just need a way to append data to the end of a text file, correct?
Once you have a handle with something like NSFileHandle(forWritingToURL:), you can use .seekToEndOfFile() and .writeData(_:). As a side note, you'll need to convert your String to Data before writing it.
Admittedly, this will probably end up being more lines of code, and you'll almost certainly need to take threading into consideration.
Is it possible to create a single QR code that contains the url, vcard and geo location all in one?
QR Codes can contain anything you want, they are just data.
There are no norms for the data inside QR Codes, but there are good practice such as MeCARD, Wireless network, Geolocation. It's hard to predict whether the phone/OS/QR Code reader
will read it correctly or not.
Here is a great list maintained by ZXing: https://code.google.com/p/zxing/wiki/BarcodeContents.
Anyway, the best is to create a QR Code with a web link, and do your thing in a web page or with a file to download. You can create editable web links for QR Code at http://www.unitag.fr, they are called QR Code Live.
There are lots of QR code generators.
Here is one:
http://www.qrstuff.com/
Click on "text" and you can put in all kinds of stuff - up to 1000 characters.
Here is the first line of the Gettysburg Address:
One QR code generator is also at zxing QR code generator. I used it and generated a QR code and scanned that code with QR code reader app on my Windows 8 phone. Works great. Many thanks to those guys at zxing. Moreover, you can generate QR code in any app (Windows Phone/Android/iPhone/WinForms/Windows 8 desktop app) using the libraries for respective platform.
An example in .NET 4.0 follows. This code doesn't use any obsolete classes/methods.
string contact = File.ReadAllText(#"C:\Users\****\Documents\****.vcf");
BarcodeWriter bcWriter = new BarcodeWriter();
ZXing.Rendering.BitmapRenderer renderer = new ZXing.Rendering.BitmapRenderer();
bcWriter.Renderer = renderer;
bcWriter.Format = BarcodeFormat.QR_CODE;
Bitmap bm = bcWriter.Write(contact);
pictureBoxQrCode.Image = bm;
bm.Save(#"C:\Users\****\Documents\****.png");