From a0029d70729f0cad0515b7e9fcb55a7527d199a1 Mon Sep 17 00:00:00 2001 From: Paul Gardiner Date: Mon, 14 Oct 2013 12:52:48 +0100 Subject: iOS: support filling in of text form fields --- platform/ios/Classes/MuDialogCreator.h | 12 + platform/ios/Classes/MuDocumentController.h | 3 +- platform/ios/Classes/MuDocumentController.m | 13 +- platform/ios/Classes/MuPageViewNormal.h | 5 +- platform/ios/Classes/MuPageViewNormal.m | 147 +++++- platform/ios/Classes/MuTapResult.h | 7 +- platform/ios/Classes/MuTapResult.m | 19 +- platform/ios/Classes/MuTextFieldController.h | 19 + platform/ios/Classes/MuTextFieldController.m | 58 +++ platform/ios/Classes/MuTextFieldController.xib | 612 +++++++++++++++++++++++++ 10 files changed, 885 insertions(+), 10 deletions(-) create mode 100644 platform/ios/Classes/MuDialogCreator.h create mode 100644 platform/ios/Classes/MuTextFieldController.h create mode 100644 platform/ios/Classes/MuTextFieldController.m create mode 100644 platform/ios/Classes/MuTextFieldController.xib (limited to 'platform/ios/Classes') diff --git a/platform/ios/Classes/MuDialogCreator.h b/platform/ios/Classes/MuDialogCreator.h new file mode 100644 index 00000000..9417facf --- /dev/null +++ b/platform/ios/Classes/MuDialogCreator.h @@ -0,0 +1,12 @@ +// +// MuDialogCreator.h +// MuPDF +// +// Copyright (c) 2013 Artifex Software, Inc. All rights reserved. +// + +#import + +@protocol MuDialogCreator +- (void) invokeTextDialog:(NSString *)aString okayAction:(void (^)(NSString *))block; +@end diff --git a/platform/ios/Classes/MuDocumentController.h b/platform/ios/Classes/MuDocumentController.h index 3ec981f8..7cf943f8 100644 --- a/platform/ios/Classes/MuDocumentController.h +++ b/platform/ios/Classes/MuDocumentController.h @@ -15,8 +15,9 @@ #import "MuOutlineController.h" #import "MuDocRef.h" +#import "MuDialogCreator.h" -@interface MuDocumentController : UIViewController +@interface MuDocumentController : UIViewController { fz_document *doc; MuDocRef *docRef; diff --git a/platform/ios/Classes/MuDocumentController.m b/platform/ios/Classes/MuDocumentController.m index 8a82fa1f..7b52f3e8 100644 --- a/platform/ios/Classes/MuDocumentController.m +++ b/platform/ios/Classes/MuDocumentController.m @@ -10,6 +10,7 @@ #import "MuPageViewNormal.h" #import "MuPageViewReflow.h" #import "MuDocumentController.h" +#import "MuTextFieldController.h" #define GAP 20 #define INDICATOR_Y -44-24 @@ -474,6 +475,8 @@ static void flattenOutline(NSMutableArray *titles, NSMutableArray *pages, fz_out // Not currently supported } caseRemote:^(MuTapResultRemoteLink *link) { // Not currently supported + } caseWidget:^(MuTapResultWidget *widget) { + tapHandled = YES; }]; if (tapHandled) break; @@ -570,7 +573,7 @@ static void flattenOutline(NSMutableArray *titles, NSMutableArray *pages, fz_out UIView *view = reflowMode ? [[MuPageViewReflow alloc] initWithFrame:CGRectMake(number * width, 0, width-GAP, height) document:docRef page:number] - : [[MuPageViewNormal alloc] initWithFrame:CGRectMake(number * width, 0, width-GAP, height) document:docRef page:number]; + : [[MuPageViewNormal alloc] initWithFrame:CGRectMake(number * width, 0, width-GAP, height) dialogCreator:self document:docRef page:number]; [view setScale:scale]; [canvas addSubview: view]; if (showLinks) @@ -618,6 +621,14 @@ static void flattenOutline(NSMutableArray *titles, NSMutableArray *pages, fz_out current = number; } +- (void) invokeTextDialog:(NSString *)aString okayAction:(void (^)(NSString *))block +{ + MuTextFieldController *tf = [[MuTextFieldController alloc] initWithText:aString okayAction:block]; + tf.modalPresentationStyle = UIModalPresentationFormSheet; + [self presentViewController:tf animated:YES completion:nil]; + [tf release]; +} + - (void) onGotoPageFinished { scroll_animating = NO; diff --git a/platform/ios/Classes/MuPageViewNormal.h b/platform/ios/Classes/MuPageViewNormal.h index 542237ec..9bbe459c 100644 --- a/platform/ios/Classes/MuPageViewNormal.h +++ b/platform/ios/Classes/MuPageViewNormal.h @@ -16,6 +16,7 @@ #import "MuHitView.h" #import "MuPageView.h" #import "MuDocRef.h" +#import "MuDialogCreator.h" @interface MuPageViewNormal : UIScrollView { @@ -30,12 +31,14 @@ UIImageView *tileView; MuHitView *hitView; MuHitView *linkView; + NSArray *widgetRects; CGSize pageSize; CGRect tileFrame; float tileScale; BOOL cancel; + id dialogCreator; } -- (id) initWithFrame: (CGRect)frame document: (MuDocRef *)aDoc page: (int)aNumber; +- (id) initWithFrame: (CGRect)frame dialogCreator:(id)dia document: (MuDocRef *)aDoc page: (int)aNumber; - (void) displayImage: (UIImage*)image; - (void) resizeImage; - (void) loadPage; diff --git a/platform/ios/Classes/MuPageViewNormal.m b/platform/ios/Classes/MuPageViewNormal.m index b34cb705..6f08424c 100644 --- a/platform/ios/Classes/MuPageViewNormal.m +++ b/platform/ios/Classes/MuPageViewNormal.m @@ -6,6 +6,8 @@ // #include "common.h" +#include "mupdf/pdf.h" +#import "MuTextFieldController.h" static void releasePixmap(void *info, const void *data, size_t size) { @@ -37,6 +39,55 @@ static UIImage *newImageWithPixmap(fz_pixmap *pix) return image; } +static NSArray *enumerateWidgetRects(fz_document *doc, fz_page *page, CGSize pageSize, CGSize screenSize) +{ + pdf_document *idoc = pdf_specifics(doc); + pdf_widget *widget; + NSMutableArray *arr = [NSMutableArray arrayWithCapacity:10]; + CGSize scale = fitPageToScreen(pageSize, screenSize); + + if (!idoc) + return nil; + + for (widget = pdf_first_widget(idoc, (pdf_page *)page); widget; widget = pdf_next_widget(widget)) + { + fz_rect rect; + + pdf_bound_widget(widget, &rect); + [arr addObject:[NSValue valueWithCGRect:CGRectMake( + rect.x0 * scale.width, + rect.y0 * scale.height, + (rect.x1-rect.x0) * scale.width, + (rect.y1-rect.y0) * scale.height)]]; + } + + return [arr retain]; +} + +static int setFocussedWidgetText(fz_document *doc, fz_page *page, const char *text) +{ + int accepted; + + fz_try(ctx) + { + pdf_document *idoc = pdf_specifics(doc); + if (idoc) + { + pdf_widget *focus = pdf_focused_widget(idoc); + if (focus) + { + accepted = pdf_text_widget_set_text(idoc, focus, (char *)text); + } + } + } + fz_catch(ctx) + { + accepted = 0; + } + + return accepted; +} + static fz_display_list *create_page_list(fz_document *doc, fz_page *page) { fz_display_list *list; @@ -70,7 +121,10 @@ static fz_display_list *create_annot_list(fz_document *doc, fz_page *page) fz_try(ctx) { fz_annot *annot; + pdf_document *idoc = pdf_specifics(doc); + if (idoc) + pdf_update_page(idoc, (pdf_page *)page); list = fz_new_display_list(ctx); dev = fz_new_list_device(ctx, list); for (annot = fz_first_annot(doc, page); annot; annot = fz_next_annot(doc, annot)) @@ -173,7 +227,7 @@ static UIImage *renderPage(fz_document *doc, fz_display_list *page_list, fz_disp annot_list = create_annot_list(doc, page); } -- (id) initWithFrame: (CGRect)frame document: (MuDocRef *)aDoc page: (int)aNumber +-(id) initWithFrame:(CGRect)frame dialogCreator:(id)dia document:(MuDocRef *)aDoc page:(int)aNumber { self = [super initWithFrame: frame]; if (self) { @@ -181,6 +235,7 @@ static UIImage *renderPage(fz_document *doc, fz_display_list *page_list, fz_disp doc = docRef->doc; number = aNumber; cancel = NO; + dialogCreator = dia; [self setShowsVerticalScrollIndicator: NO]; [self setShowsHorizontalScrollIndicator: NO]; @@ -226,6 +281,7 @@ static UIImage *renderPage(fz_document *doc, fz_display_list *page_list, fz_disp block_page = nil; }); [docRef release]; + [widgetRects release]; [linkView release]; [hitView release]; [tileView release]; @@ -325,6 +381,7 @@ static UIImage *renderPage(fz_document *doc, fz_display_list *page_list, fz_disp CGSize scale = fitPageToScreen(pageSize, self.bounds.size); CGRect rect = (CGRect){{0.0, 0.0},{pageSize.width * scale.width, pageSize.height * scale.height}}; UIImage *image = renderPage(doc, page_list, annot_list, pageSize, self.bounds.size, rect, 1.0); + widgetRects = enumerateWidgetRects(doc, page, pageSize, self.bounds.size); dispatch_async(dispatch_get_main_queue(), ^{ [self displayImage: image]; [image release]; @@ -533,8 +590,96 @@ static UIImage *renderPage(fz_document *doc, fz_display_list *page_list, fz_disp - (void) setScale:(float)scale {} +- (void) invokeTextDialog:(NSString *)text +{ + [dialogCreator invokeTextDialog:text okayAction:^(NSString *newText) { + dispatch_async(queue, ^{ + BOOL accepted = setFocussedWidgetText(doc, page, [newText UTF8String]); + fz_drop_display_list(ctx, annot_list); + annot_list = NULL; + dispatch_async(dispatch_get_main_queue(), ^{ + if (accepted) + [self loadPage]; + else + [self invokeTextDialog:newText]; + }); + }); + }]; +} + +- (void) passTapToPage:(CGPoint)pt +{ + pdf_document *idoc = pdf_specifics(doc); + CGSize scale = fitPageToScreen(pageSize, self.bounds.size); + pdf_ui_event event; + int changed = 0; + pdf_widget *focus; + + if (!idoc) + return; + + fz_try(ctx) + { + event.etype = PDF_EVENT_TYPE_POINTER; + event.event.pointer.pt.x = pt.x / scale.width; + event.event.pointer.pt.y = pt.y / scale.height; + event.event.pointer.ptype = PDF_POINTER_DOWN; + changed = pdf_pass_event(idoc, (pdf_page *)page, &event); + event.event.pointer.ptype = PDF_POINTER_UP; + changed |= pdf_pass_event(idoc, (pdf_page *)page, &event); + if (changed) + { + fz_drop_display_list(ctx, annot_list); + annot_list = NULL; + } + + focus = pdf_focused_widget(idoc); + if (focus) + { + switch (pdf_widget_get_type(focus)) + { + case PDF_WIDGET_TYPE_TEXT: + { + char *text = pdf_text_widget_text(idoc, focus); + NSString *stext = [NSString stringWithUTF8String:text?text:""]; + fz_free(ctx, text); + dispatch_async(dispatch_get_main_queue(), ^{ + [self invokeTextDialog:stext]; + }); + break; + } + + case PDF_WIDGET_TYPE_LISTBOX: + case PDF_WIDGET_TYPE_COMBOBOX: + break; + + case PDF_WIDGET_TYPE_SIGNATURE: + break; + + default: + break; + } + } + } + fz_catch(ctx) + { + } +} + - (MuTapResult *) handleTap:(CGPoint)pt { + CGPoint ipt = [self convertPoint:pt toView:imageView]; + for (int i = 0; i < widgetRects.count; i++) + { + CGRect r = [[widgetRects objectAtIndex:i] CGRectValue]; + if (CGRectContainsPoint([[widgetRects objectAtIndex:i] CGRectValue], ipt)) + { + dispatch_async(queue, ^{ + [self passTapToPage:ipt]; + }); + return [[[MuTapResultWidget alloc] init] autorelease]; + } + } CGPoint lpt = [self convertPoint:pt toView:linkView]; return linkView ? [linkView handleTap:lpt] : nil; } diff --git a/platform/ios/Classes/MuTapResult.h b/platform/ios/Classes/MuTapResult.h index c0d930c5..3271772f 100644 --- a/platform/ios/Classes/MuTapResult.h +++ b/platform/ios/Classes/MuTapResult.h @@ -10,11 +10,13 @@ @class MuTapResultInternalLink; @class MuTapResultExternalLink; @class MuTapResultRemoteLink; +@class MuTapResultWidget; @interface MuTapResult : NSObject -(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock - caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock; + caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock + caseWidget:(void (^)(MuTapResultWidget *))widgetBlock; @end @interface MuTapResultInternalLink : MuTapResult @@ -44,3 +46,6 @@ @property(readonly) BOOL newWindow; -(id)initWithFileSpec:(NSString *)aString pageNumber:(int)aNumber newWindow:(BOOL)aBool; @end + +@interface MuTapResultWidget : MuTapResult +@end diff --git a/platform/ios/Classes/MuTapResult.m b/platform/ios/Classes/MuTapResult.m index 7e3d71d1..c7f4d755 100644 --- a/platform/ios/Classes/MuTapResult.m +++ b/platform/ios/Classes/MuTapResult.m @@ -9,8 +9,7 @@ @implementation MuTapResult --(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock {} - +-(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock caseWidget:(void (^)(MuTapResultWidget *))widgetBlock {} @end @@ -28,7 +27,7 @@ return self; } --(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock +-(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock caseWidget:(void (^)(MuTapResultWidget *))widgetBlock { internalLinkBlock(self); } @@ -56,7 +55,7 @@ [super dealloc]; } --(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock +-(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock caseWidget:(void (^)(MuTapResultWidget *))widgetBlock { externalLinkBlock(self); } @@ -86,9 +85,19 @@ [super dealloc]; } --(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock +-(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock caseWidget:(void (^)(MuTapResultWidget *))widgetBlock { remoteLinkBlock(self); } +@end + + +@implementation MuTapResultWidget + +-(void) switchCaseInternal:(void (^)(MuTapResultInternalLink *))internalLinkBlock caseExternal:(void (^)(MuTapResultExternalLink *))externalLinkBlock caseRemote:(void (^)(MuTapResultRemoteLink *))remoteLinkBlock caseWidget:(void (^)(MuTapResultWidget *))widgetBlock +{ + widgetBlock(self); +} + @end \ No newline at end of file diff --git a/platform/ios/Classes/MuTextFieldController.h b/platform/ios/Classes/MuTextFieldController.h new file mode 100644 index 00000000..f74f0610 --- /dev/null +++ b/platform/ios/Classes/MuTextFieldController.h @@ -0,0 +1,19 @@ +// +// MuTextFieldController.h +// MuPDF +// +// Copyright (c) 2013 Artifex Software, Inc. All rights reserved. +// + +#import + +@interface MuTextFieldController : UIViewController +{ + void (^okayBlock)(NSString *); + NSString *initialText; +} +@property (retain, nonatomic) IBOutlet UITextView *textView; +- (id)initWithText:(NSString *)text okayAction:(void (^)(NSString *))block; +- (IBAction)okayTapped:(id)sender; +- (IBAction)cancelTapped:(id)sender; +@end diff --git a/platform/ios/Classes/MuTextFieldController.m b/platform/ios/Classes/MuTextFieldController.m new file mode 100644 index 00000000..e0864ff4 --- /dev/null +++ b/platform/ios/Classes/MuTextFieldController.m @@ -0,0 +1,58 @@ +// +// MuTextFieldController.m +// MuPDF +// +// Copyright (c) 2013 Artifex Software, Inc. All rights reserved. +// + +#import "MuTextFieldController.h" + +@interface MuTextFieldController () +@end + +@implementation MuTextFieldController + +-(id)initWithText:(NSString *)text okayAction:(void (^)(NSString *))block +{ + self = [super initWithNibName:@"MuTextFieldController" bundle:nil]; + if (self) + { + okayBlock = Block_copy(block); + initialText = [text retain]; + } + return self; +} + +- (void)viewDidLoad +{ + [super viewDidLoad]; + _textView.text = initialText; + // Do any additional setup after loading the view from its nib. +} + +- (void)didReceiveMemoryWarning +{ + [super didReceiveMemoryWarning]; + // Dispose of any resources that can be recreated. +} + +- (void)dealloc +{ + [okayBlock release]; + [initialText release]; + [_textView release]; + [super dealloc]; +} + +- (IBAction)okayTapped:(id)sender +{ + okayBlock(_textView.text); + [self dismissViewControllerAnimated:YES completion:nil]; +} + +- (IBAction)cancelTapped:(id)sender +{ + [self dismissViewControllerAnimated:YES completion:nil]; +} + +@end diff --git a/platform/ios/Classes/MuTextFieldController.xib b/platform/ios/Classes/MuTextFieldController.xib new file mode 100644 index 00000000..298e1508 --- /dev/null +++ b/platform/ios/Classes/MuTextFieldController.xib @@ -0,0 +1,612 @@ + + + + 1552 + 11G63b + 3084 + 1138.51 + 569.00 + + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + 2083 + + + IBNSLayoutConstraint + IBProxyObject + IBUIButton + IBUILabel + IBUITextView + IBUIView + + + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + + + PluginDependencyRecalculationVersion + + + + + IBFilesOwner + IBCocoaTouchFramework + + + IBFirstResponder + IBCocoaTouchFramework + + + + 274 + + + + 292 + {{20, 47}, {281, 21}} + + + _NS:9 + NO + YES + 7 + NO + IBCocoaTouchFramework + Fill in text field + + 3 + MQA + + + 0 + 1 + + 1 + 17 + + + Helvetica + 17 + 16 + + NO + + + + 292 + {{20, 89}, {281, 281}} + + + _NS:9 + + 1 + MSAxIDEAA + + YES + YES + IBCocoaTouchFramework + + + 2 + IBCocoaTouchFramework + + + Helvetica + Helvetica + 0 + 14 + + + Helvetica + 14 + 16 + + + + + 292 + {{20, 416}, {280, 44}} + + + _NS:9 + NO + IBCocoaTouchFramework + 0 + 0 + 1 + Okay + + + 1 + MC4xOTYwNzg0MzQ2IDAuMzA5ODAzOTMyOSAwLjUyMTU2ODY1NgA + + + 3 + MC41AA + + + 2 + 15 + + + Helvetica-Bold + 15 + 16 + + + + + 292 + {{20, 476}, {281, 44}} + + + _NS:9 + NO + IBCocoaTouchFramework + 0 + 0 + 1 + Cancel + + + 1 + MC4xOTYwNzg0MzQ2IDAuMzA5ODAzOTMyOSAwLjUyMTU2ODY1NgA + + + + + + + {{0, 20}, {320, 548}} + + + + 3 + MC4zMzMzMzMzMzMzAA + + + + IBUIScreenMetrics + + YES + + + + + + {320, 568} + {568, 320} + + + IBCocoaTouchFramework + Retina 4 Full Screen + 2 + + IBCocoaTouchFramework + + + + + + + view + + + + 3 + + + + textView + + + + 70 + + + + okayTapped: + + + 7 + + 71 + + + + cancelTapped: + + + 7 + + 72 + + + + + + 0 + + + + + + 1 + + + + + 5 + 0 + + 5 + 1 + + 20 + + 1000 + + 8 + 29 + 3 + + + + 4 + 0 + + 4 + 1 + + 29 + + 1000 + + 3 + 9 + 3 + + + + 4 + 0 + + 4 + 1 + + 89 + + 1000 + + 3 + 9 + 3 + + + + 9 + 0 + + 9 + 1 + + 0.0 + + 1000 + + 6 + 24 + 2 + + + + 6 + 0 + + 6 + 1 + + 20 + + 1000 + + 8 + 29 + 3 + + + + 5 + 0 + + 5 + 1 + + 20 + + 1000 + + 8 + 29 + 3 + + + + 3 + 0 + + 3 + 1 + + 89 + + 1000 + + 3 + 9 + 3 + + + + 6 + 0 + + 6 + 1 + + 0.0 + + 1000 + + 6 + 24 + 2 + + + + 6 + 0 + + 6 + 1 + + 0.0 + + 1000 + + 6 + 24 + 2 + + + + 5 + 0 + + 5 + 1 + + 20 + + 1000 + + 8 + 29 + 3 + + + + 3 + 0 + + 3 + 1 + + 47 + + 1000 + + 3 + 9 + 3 + + + + 5 + 0 + + 5 + 1 + + 20 + + 1000 + + 8 + 29 + 3 + + + + + + + + + + -1 + + + File's Owner + + + -2 + + + + + 4 + + + + + + 11 + + + + + 12 + + + + + 8 + 0 + + 0 + 1 + + 281 + + 1000 + + 3 + 9 + 1 + + + + + + 21 + + + + + 22 + + + + + + 41 + + + + + 43 + + + + + 48 + + + + + 49 + + + + + 54 + + + + + 59 + + + + + + 60 + + + + + 62 + + + + + 64 + + + + + 65 + + + + + 68 + + + + + 69 + + + + + + + MuTextFieldController + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + UIResponder + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + + + + + + + + + + + + + + + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + + + + + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + com.apple.InterfaceBuilder.IBCocoaTouchPlugin + + + + + + 72 + + + 0 + IBCocoaTouchFramework + YES + 3 + YES + 2083 + + -- cgit v1.2.3