im facing this issue , i email textfiled the app crash
+(BOOL)isCorrectEmail:(NSString *)email{
BOOL strictFilter = NO;
NSString *strictFilterString = #"[A-Z0-9a-z\\._%+-]+#([A-Az-z0-9-]+\\.)+[A-Za-z]{2,4})";
NSString *lastString = #".+#([A-Za-z0-9-]+\\.)+[A-Za-z]{2}[A-Za-z]+";
NSString *emailRegex = strictFilter ? strictFilterString : lastString;
NSPredicate *emailPred = [NSPredicate predicateWithFormat:#"SELF MATCHES NO",emailRegex];
return [emailPred evaluateWithObject:email];
}
Related
Before explaining I need to say EVERYTHING is working perfect on Android and the problem is on IOS devices I am using react-native-signature-capture , I have two signature field at the same page, I solve the problem of not getting saved but when I save one of the field both of them get the same value for the signature .
How can I handle it?
codes for signature component here
This is the extraInputsList logs in the codes
and this is my RSSSignatureViewManager.m file
#import "RSSignatureViewManager.h"
#import <React/RCTBridgeModule.h>
#import <React/RCTBridge.h>
#import <React/RCTEventDispatcher.h>
#import <React/RCTUIManager.h>
#implementation RSSignatureViewManager
#synthesize bridge = _bridge;
#synthesize signView;
RCT_EXPORT_MODULE()
RCT_EXPORT_VIEW_PROPERTY(rotateClockwise, BOOL)
RCT_EXPORT_VIEW_PROPERTY(square, BOOL)
RCT_EXPORT_VIEW_PROPERTY(showBorder, BOOL)
RCT_EXPORT_VIEW_PROPERTY(showNativeButtons, BOOL)
RCT_EXPORT_VIEW_PROPERTY(showTitleLabel, BOOL)
-(dispatch_queue_t) methodQueue
{
return dispatch_get_main_queue();
}
-(UIView *) view
{
self.signView = [[RSSignatureView alloc] init];
self.signView.manager = self;
return signView;
}
// Both of these methods needs to be called from the main thread so the
// UI can clear out the signature.
RCT_EXPORT_METHOD(saveImage:(nonnull NSNumber *)reactTag) {
[self.bridge.uiManager addUIBlock:^(RCTUIManager *uiManager, NSDictionary<NSNumber *,UIView *> *viewRegistry) {
RSSignatureView *view = viewRegistry[reactTag];
if (!view || ![view isKindOfClass:[RSSignatureView class]]) {
RCTLogError(#"Cannot find NativeView ", reactTag);
return;
}
[view saveImage];
}];
}
RCT_EXPORT_METHOD(resetImage:(nonnull NSNumber *)reactTag) {
[self.bridge.uiManager addUIBlock:^(RCTUIManager *uiManager, NSDictionary<NSNumber *,UIView *> *viewRegistry) {
RSSignatureView *view = viewRegistry[reactTag];
if (!view || ![view isKindOfClass:[RSSignatureView class]]) {
RCTLogError(#"Cannot find NativeView with tag", reactTag);
return;
}
[view erase];
}];
}
-(void) publishSaveImageEvent:(NSString *) aTempPath withEncoded: (NSString *) aEncoded {
[self.bridge.eventDispatcher
sendDeviceEventWithName:#"onSaveEvent"
body:#{
#"pathName": aTempPath,
#"encoded": aEncoded
}];
}
-(void) publishDraggedEvent {
[self.bridge.eventDispatcher
sendDeviceEventWithName:#"onDragEvent"
body:#{#"dragged": #YES}];
}
#end
Solution
just install this package from this git
you can edit package.json like this
"react-native-signature-capture": "git+https://github.com/nomi9995/react-native-signature-capture.git",
Then do yarn install, react-native link react-native-signature-capture, and finally, it works great when I have multiple signature-pads!
UPDATE:
Both the Android and iOS versions save images from any signature box to the same path/filename. To support multiple boxes, you'll need to deal with the encoding/file sequentially. Or you can overload/change the saveImage method to take a filename.
Looks every time you save an image, this library will actively delete the previous image.
Android version from RSSignatureCaptureMainView.java:140
final void saveImage() {
String root = Environment.getExternalStorageDirectory().toString();
// the directory where the signature will be saved
File myDir = new File(root + "/saved_signature");
// make the directory if it does not exist yet
if (!myDir.exists()) {
myDir.mkdirs();
}
// set the file name of your choice
String fname = "signature.png";
// in our case, we delete the previous file, you can remove this
File file = new File(myDir, fname);
if (file.exists()) {
file.delete();
}
.
.
.
iOS version from RSSignatureView.m:186
-(void) saveImage {
saveButton.hidden = YES;
clearButton.hidden = YES;
UIImage *signImage = [self.sign signatureImage: _rotateClockwise withSquare:_square];
saveButton.hidden = NO;
clearButton.hidden = NO;
NSError *error;
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths firstObject];
NSString *tempPath = [documentsDirectory stringByAppendingFormat:#"/signature.png"];
//remove if file already exists
if ([[NSFileManager defaultManager] fileExistsAtPath:tempPath]) {
[[NSFileManager defaultManager] removeItemAtPath:tempPath error:&error];
if (error) {
NSLog(#"Error: %#", error.debugDescription);
}
}
.
.
.
Previous answer:
This looks to be a known issue.
In RSSignatureViewManager.m, add #import <React/RCTUIManager.h>
and change the method RCT_EXPORT_METHOD to the following
RCT_EXPORT_METHOD(saveImage:(nonnull NSNumber *)reactTag) {
[self.bridge.uiManager addUIBlock:^(RCTUIManager *uiManager, NSDictionary<NSNumber *,UIView *> *viewRegistry) {
RSSignatureView *view = viewRegistry[reactTag];
if (!view || ![view isKindOfClass:[RSSignatureView class]]) {
RCTLogError(#"Cannot find NativeView with tag #%#", reactTag);
return;
}
[view saveImage];
}];
}
I'm developing a OS X app with sqlite3 and I want to copy the database from the application's bundle to Library/Application support/ directory because I need read/write on the db, however, the sql is copied to my documents folder and I don't want that location. My code:
- (NSString *)filePath {
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
return [[paths objectAtIndex:0] stringByAppendingPathComponent:#"myDB.sql"];
}
- (void)openDB {
NSString *destinationPath = [self filePath];
if (![[NSFileManager defaultManager] fileExistsAtPath:destinationPath]) {
NSString *sourcePath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:#"myDB.sql"];
NSError *error;
[[NSFileManager defaultManager] copyItemAtPath:sourcePath toPath:destinationPath error:&error];
if (error != nil) {
//Error
}
}
A file like this belongs in the Application Support folder of the Library. So, instead of NSDocumentDirectory, use NSApplicationSupportDirectory. Also, as the File System Basics documentation says, "All content in this directory should be placed in a custom subdirectory whose name is that of your app’s bundle identifier or your company."
For example:
- (NSString *)filePath {
NSString *applicationSupport = NSSearchPathForDirectoriesInDomains(NSApplicationSupportDirectory, NSUserDomainMask, YES)[0];
NSString *applicationFolder = [applicationSupport stringByAppendingPathComponent:[[NSBundle mainBundle] bundleIdentifier]];
return [applicationFolder stringByAppendingPathComponent:#"myDB.sql"];
}
By the way, when creating this file, remember to create the folder:
- (void)openDB {
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *destinationPath = [self filePath];
if (![fileManager fileExistsAtPath:destinationPath]) {
NSError *error;
if (![fileManager createDirectoryAtPath:[destinationPath stringByDeletingLastPathComponent] withIntermediateDirectories:TRUE attributes:nil error:&error]) {
NSLog(#"%s: createDirectoryAtPath error: %#", __FUNCTION__, error);
}
NSString *sourcePath = [[NSBundle mainBundle] pathForResource:#"myDB" ofType:#"sql"];
if (![fileManager copyItemAtPath:sourcePath toPath:destinationPath error:&error]) {
NSLog(#"%s: copyItemAtPath error: %#", __FUNCTION__, error);
}
}
}
I develop an application and I need to display the content using an UITextView which must have set the height dynamically and it must recognize a link.
I used code above:
self.textView.text = [NSString stringWithFormat:#"%# \n %#", self.offersObjects.body, self.offersObjects.url];
self.textView.dataDetectorTypes = UIDataDetectorTypeLink;
if (([[[UIDevice currentDevice] systemVersion] integerValue] < 7)){
CGRect frame = self.textView.frame;
frame.size.height = self.textView.contentSize.height;contentSize.height;
self.textView.frame = frame;
}else{
[self.textView sizeToFit];
[self.textView layoutIfNeeded];
}
My problem is that it doesn't recognize the link .
try with below code :
-(IBAction)txtStustes:(id)sender
{
NSError *error = nil;
NSDataDetector *detector = [NSDataDetector dataDetectorWithTypes:NSTextCheckingTypeLink
| NSTextCheckingTypePhoneNumber error:&error];
NSString *string = self.textView.text;
NSArray *matches = [detector matchesInString:string options:0 range:NSMakeRange(0, [string length])];
for (NSTextCheckingResult *match in matches) {
if ([match resultType] == NSTextCheckingTypeLink) {
NSURL *url = [match URL];
[[UIApplication sharedApplication] openURL:url];
}
}
}
Also add below code in your viewDidLoad method
UITapGestureRecognizer *LblProfileNameTouch=[[UITapGestureRecognizer alloc]initWithTarget:self action:#selector(txtStustes:)];
[LblProfileNameTouch setNumberOfTouchesRequired:1];
[self.textView addGestureRecognizer:LblProfileNameTouch];
I am trying to save NSMutableDictionary in iOS keychain using KeychainItemWrapper classes. But I am not able to save it. I am getting error
Terminating app due to uncaught exception 'NSInternalInconsistencyException', reason: 'Couldn't add the Keychain Item.'
Here is my data to be saved
{
country = USA;
id = 3;
name = "Test User";
photo = "http://www.mydomain.com/images/user1.jpg";
result = true;
"country" = 1;
}
Here is my code
// Call to save
[self storeLoggedInUserInfoInKeychainWithDictionary:dict];
-(void)storeLoggedInUserInfoInKeychainWithDictionary:(NSMutableDictionary*)dict
{
// Save Login Credentials
KeychainItemWrapper* loginUserkeychain = [[KeychainItemWrapper alloc] initWithIdentifier:LOGIN_USER_SERVICE accessGroup:nil];
NSString *error;
[loginUserkeychain setObject:(__bridge id)(kSecAttrAccessibleWhenUnlocked) forKey:(__bridge id)(kSecAttrAccessible)];
NSData *dictionaryRep = [NSPropertyListSerialization dataFromPropertyList:dict format:NSPropertyListXMLFormat_v1_0 errorDescription:&error];
[loginUserkeychain setObject:dictionaryRep forKey:(__bridge id)(kSecValueData)];
}
-(NSMutableDictionary*)fetchLoggedInUserInfoFromKeychain
{
KeychainItemWrapper* loginUserkeychain = [[KeychainItemWrapper alloc] initWithIdentifier:LOGIN_USER_SERVICE accessGroup:nil];
NSString *error;
//When the NSData object object is retrieved from the Keychain, you convert it back to NSDictionary type
NSData *dictionaryRep = [loginUserkeychain objectForKey:(__bridge id)(kSecValueData)];
NSDictionary *dictionary = [NSPropertyListSerialization propertyListFromData:dictionaryRep mutabilityOption:NSPropertyListImmutable format:nil errorDescription:&error];
if (error) {
NSLog(#"%#", error);
}
return [NSMutableDictionary dictionaryWithDictionary:dictionary];
}
-(void)resetLoggedInUserInfoFromKeychain
{
KeychainItemWrapper* loginUserkeychain = [[KeychainItemWrapper alloc] initWithIdentifier:LOGIN_USER_SERVICE accessGroup:nil];
[loginUserkeychain resetKeychainItem];
}
Can anybody tell me whats wrong in above code ?
Thanks in advance.
After few attempts & research using below code I am able to save the data in keychain. If any one is interested can have a look at below code
-(void)storeLoggedInUserInfoInKeychainWithDictionary:(NSMutableDictionary*)dict
{
// Create encoded data
NSData *encodedData= [NSKeyedArchiver archivedDataWithRootObject:dict];
// Create encoded string from data
NSString *encodedString= [encodedData base64EncodedString];
// Save Login Credentials
KeychainItemWrapper* tranxkeychain = [[KeychainItemWrapper alloc] initWithIdentifier:LOGIN_USER_KEYCHAIN accessGroup:nil];
[tranxkeychain setObject:(__bridge id)(kSecAttrAccessibleWhenUnlocked) forKey:(__bridge id)(kSecAttrAccessible)];
[tranxkeychain setObject:LOGIN_USER_SERVICE forKey: (__bridge id)kSecAttrService];
[tranxkeychain setObject:LOGIN_USER_INFO forKey:(__bridge id)(kSecAttrAccount)];
[tranxkeychain setObject:encodedString forKey:(__bridge id)(kSecValueData)];
}
-(NSDictionary*)fetchLoggedInUserInfoFromKeychain
{
KeychainItemWrapper* tranxkeychain = [[KeychainItemWrapper alloc] initWithIdentifier:LOGIN_USER_KEYCHAIN accessGroup:nil];
[tranxkeychain setObject:(__bridge id)(kSecAttrAccessibleWhenUnlocked) forKey:(__bridge id)(kSecAttrAccessible)];
[tranxkeychain setObject:LOGIN_USER_SERVICE forKey: (__bridge id)kSecAttrService];
// Get decoded string
NSString *decodedString=[tranxkeychain objectForKey:(__bridge id)(kSecValueData)];
// Get decoded data
NSData *decodedData= [NSData dataFromBase64String:decodedString];
NSDictionary *dict =[NSKeyedUnarchiver unarchiveObjectWithData:decodedData];
return dict;
}
-(void)resetLoggedInUserInfoFromKeychain
{
KeychainItemWrapper* tranxkeychain = [[KeychainItemWrapper alloc] initWithIdentifier:LOGIN_USER_KEYCHAIN accessGroup:nil];
[tranxkeychain resetKeychainItem];
}
Unsure how to use an image loaded from the web as an asset in a GLKit skybox (like the old apple/google maps streetview) There are 2 methods for loading cubemaps with GLKTextureLoader: cubeMapWithContentsOfFile and cubeMapWithContentsOfUrl
If I grab the image locally it works fine:
NSString *path = [[NSBundle mainBundle] pathForResource:#"pano" ofType:#"jpg"];
GLKTextureInfo *skyboxCubemap = [GLKTextureLoader cubeMapWithContentsOfFile:imgPath options:options error:&error];
So is there a way to get a path from an image loaded from the web and use it here?
I ended up loading the image from the web like so:
- (void) cacheImage: (NSURL *) ImageURL : (NSString *)imageName
{
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *dir = [paths objectAtIndex: 0];
NSString *file = [docDir stringByAppendingPathComponent: imageName];
if(![[NSFileManager defaultManager] fileExistsAtPath: file])
{
NSData *data = [[NSData alloc] initWithContentsOfURL: ImageURL];
UIImage *image = [[UIImage alloc] initWithData: data];
[UIImageJPEGRepresentation(image, 100) writeToFile: docFile atomically: YES];
}
}
caching and returning the file url via :
- (NSString *) getCachedImage : (NSString *)imageName
{
NSArray *paths = NSSearchPathForDirectoriesInDomains
(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString* cachedPath = [documentsDirectory stringByAppendingPathComponent:imageName];
NSString *path;
if([[NSFileManager defaultManager] fileExistsAtPath: cachedPath])
{
path = cachedPath;
}
return path;
}
and loading the file via
NSString *cached = [self getCachedImage:#"cacheKey"];
self.skyboxCubemap = [GLKTextureLoader cubeMapWithContentsOfFile:cached options:options error:&error];