Essentials
Essentials copied to clipboard
Collection of categories, functions, macros and classes that are essential part of my projects.
Essentials
This is a collection of categories, functions, macros and classes that are essential part of my projects.
Prefix
ESSis typically used, but we had no shame for usingNS,UIorCGprefixes for relevant functions.
Highlights
Type Inferrence Macros
Macros let and var that infer types of declated variables, just like in that other language. Uses clang __auto_type feature.
var string = @"Hello";
let answer = 42;
Macro foreach that improves for-in loop with type inferrence of emunerated collections. All is just compiler magic.
NSArray<NSString *> *titles = @[ @"Mr", @"Mrs", @"Ms", @"Mx" ];
foreach (title, titles) {
// title is NSString
}
ESSAssert
Assertion macro with optional message. It’ active also on Release and provides fallback handling using else clause. Works perfectly with compiler static analysis.
ESSAssert(condition); // Prints default message.
ESSDebugAssert(condition); // Active only on Debug.
ESSAssert(condition, @"Must be %@", requirement); // Prints custom message.
ESSAssert(condition) else return nil; // Fallback handler for Release.
int* pointer = NULL;
*pointer = 5; // Compiler warning for NULL dereference !!!
ESSAssert(pointer) else return;
*pointer = 5; // Compiler is ok, because we returned above.
ESSLazyMake
Macro for convenient lazy getters.
ESSLazyMake(NSData *, fileContents) {
// Invoked only once, returned value is stored in _fileContents ivar.
return [NSData stringWithContentsOfURL:self.fileURL];
}
NSEqual
Function for nil-safe object comparison. Calling -isEqual: on nil with nil argument returns wrong answer.
NSEqual(nil, nil); // YES
NSEqual(nil, @"A"); // NO
NSEqual(@"A", nil); // NO
NSEqual(@"A", @"A"); // YES
ESSDebug / ESSNotice / ESSWarning / ESSError
Logging functions with better format than NSLog(). I don’t need to see year, process name or thread ID. Also allows filtering logs to arbitrary level (e.g. ignore ESSDebug).
2016-02-13 10:16:17.838 ProcessName[76035:16575258] Using NSLog
Feb 13 10:16:17: Using ESSDebug
Feb 13 10:16:17: ╸Using ESSNotice╺
Feb 13 10:16:17: ◆ Warning: Using ESSWarning ◆
Feb 13 10:16:17: >> Error: Using ESSError <<
Feb 13 10:20:28: BACKGROUND ╸Using ESSNotice from non-main thread╺
+cast:
Type-checked method for safe casting of object pointers. Returns instance of the receiving class or nil.
[NSString cast:@"A"]; // @"A"
[NSString cast:@42]; // nil
NSString
- Enumerating occurences of string.
- Collecting indexes of characters from set.
- Stripping diacritics and normalizing for search.
- Trimming whitespace and deleting HTML tags.
- Splitting to letters, words, sentences, and lines.
NSOperationQueue
- Shared instances for all Quality of Service modes:
+interactiveQueue,+userQueue,+utilityQueue,+backgroundQueue. - Methods for executing blocks synchronously, asynchronously, after delay, in parallel.
NSTimer
- Block-based constructor.
- Convenience scheduling in
UITrackingRunLoopMode. - Methods for postpone and hold.
NSDate
- Convenient comparison methods (no more
-compare:or-earlierDate:). - Rounding dates to calendar components (to day, to hour, …).
- Checking whether two days are within the same calendar component.
NSLocale
- Accessors for language, country, currency (no more
-objectForKey:). - Shared POSIX locale accessor.
NSURLSession
Completely custom interface for making requests and handling responses.
- Accessor for shared session on Main Queue.
- Convenient downloading using
-download:completion:and-downloadFile:completion:. - Convenient uploading using
-uploadTo:payload:completion:, where paylod may beNSData,NSStringorNSURL. - Easy to start request using explicit HTTP methods: GET, HEAD, DELETE, POST, PUT, PATCH.
- Unique response handling, see below.
ESSURLResponse
Custom class that encapsulates interaction with HTTP responses, returned by NSURLSession category above.
- Access to metadata, like status code, headers, content length, MIME type, last modified date.
- Automatic status code propagation as
NSError(e.g. 408 Request Timeout →NSURLErrorTimedOut). - Access to data as
NSDataorNSString(of any encoding) and automatic JSON decoding. - Access to URL of downloaded file and manipulation with it.
- Single error covering all domains (URL loading, status code errors, file error, JSON error).
- Convenient retry mechanism using
-shouldRetryand-retryAfter:.
[[NSURLSession mainQueueSession] download:URL
completion:^(ESSURLResponse *response) {
if (response.shouldRetry) {
[response retryIfNeededAfter:5 count:3]; // Limit number of retries.
}
else {
NSString *title = response.JSON[@"title"];
// ...
}
}];
ESSEncode / ESSDecode
Single pair of macros to encode and decode values of any type using NSCoder. It uses KVC and requires the coder to be stored in decoder and encoder variables.
@property NSString *title;
@property NSUInteger count;
@property (weak) id owner;
- (void)encodeWithCoder:(NSCoder *)encoder {
ESSEncode(title);
ESSEncode(count);
ESSEncodeConditional(owner);
}
- (instancetype)initWithCoder:(NSCoder *)decoder {
self = [self init];
if (self) {
ESSDecode(title);
ESSDecode(count);
ESSDecode(owner);
}
return self;
}
CGGeometry
- Rounding numbers, points, sizes and rects to screen scale.
- Fitting rects, getting rect center, and point arithmetics.
UIColor
- Creating random colors and rendomizing shades of existing colors.
- Access to components and blending colors
- Access to luminance and deriving color with desired luminance.
- Getting natural names of colors (e.g. red, light blue, teal, dark purple).
- Creating autoreleased
CGGradients(no moreCGGradientReffunctions).
UIDevice Hardware
- Access to hardware identifier: iPhone8,2, iPad5,2
- Getting hardware name: iPhone 6S Plus, iPad Mini 4
- Getting hardware line: iPhone Plus, iPad Mini
- Getting hardware family: iPhone, iPad
UIImage
- Creating images of solid color.
- Creating from drawing code.
- Getting photo orientation and equivalent
CFAffineTransform. - Cropping and resizing.
- Creating color histograms.
- Bitmap and per-pixel processing.
UIImage *inverted = [image imageByEnumeratingPixels:^GLKVector4(GLKVector4 color) {
return GLKVector4Make(1 - color.r,
1 - color.g,
1 - color.b,
color.a);
}];
UIView
- Snapshotting.
- Corner radius, rasterization, anchor point, border (no more
.layer). - Shadow using
NSShadowand shadow path asUIBezierPath. - Access to transform components: scale, rotation, translation.
UIScrollView
- Getting and setting page for paged scroll views.
- Access to content scroll progress, a value in 0…1 range.
- Stop scrolling programatically.
- Enabling Natural Touch Handling™ so
UIButtonis not delayed, just likeUITableViewCell. Uses swizzling.
[UIScrollView enableNaturalButtonHandling]; // Done!
Attributed String
Category for setting attributes as properties.
NSMutableAttribtedString *string = [NSMutableAttribtedString new];
[string append:@"ABCD"];
string.font = [UIFont boldSystemFontOfSize: 20];
string.color = [UIColor redColor];
string.alignment = NSTextAlignmentCenter;
string.kerning = 10;
string.hasUnderline = YES;
// Set attributes on subrange:
[string subrange:NSRangeMake(1, 2)].color = [UIColor blackColor];
CoreImage
- Convenient
UIImageprocessing. - Filter constructors for every
CIFiltertype (e.g. blur, hue, saturation, contrast, invert, grayscale, …).
UIImage *processed = [CIContext imageFromImage:image filters:@[
[CIFilter blurWithRadius:7],
[CIFilter adjustSaturation:1.3],
[CIFilter invertColors],
[CIFilter photoEffectTonal],
]];