CPDFViewController.m 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441
  1. //
  2. // CPDFViewController.m
  3. // viewer-ctrl-demo
  4. //
  5. // Copyright © 2014-2023 PDF Technologies, Inc. All Rights Reserved.
  6. //
  7. // THIS SOURCE CODE AND ANY ACCOMPANYING DOCUMENTATION ARE PROTECTED BY INTERNATIONAL COPYRIGHT LAW
  8. // AND MAY NOT BE RESOLD OR REDISTRIBUTED. USAGE IS BOUND TO THE ComPDFKit LICENSE AGREEMENT.
  9. // UNAUTHORIZED REPRODUCTION OR DISTRIBUTION IS SUBJECT TO CIVIL AND CRIMINAL PENALTIES.
  10. // This notice may not be removed from this file.
  11. //
  12. #import "CPDFViewController.h"
  13. #import <ComPDFKit/ComPDFKit.h>
  14. #import <compdfkit_tools/compdfkit_tools.h>
  15. @interface CPDFViewController ()<UISearchBarDelegate,CPDFViewDelegate,CPDFListViewDelegate, CPDFMoreListViewDelegate, CSearchToolbarDelegate, CPDFDisplayViewDelegate, CPDFBOTAViewControllerDelegate,CPDFSearchResultsDelegate, CPDFThumbnailViewControllerDelegate,CPDFPopMenuViewDelegate,UIDocumentPickerDelegate>
  16. @property(nonatomic, strong) NSString *filePath;
  17. @property(nonatomic, strong) CPDFListView *pdfListView;
  18. @property(nonatomic, strong) CNavigationRightView *rightView;
  19. @property(nonatomic, strong) CSearchToolbar *searchToolbar;
  20. @property(nonatomic, strong) CActivityIndicatorView *loadingView;
  21. @property(nonatomic, strong) NSString *navigationTitle;
  22. @property(nonatomic, strong) CNavigationBarTitleButton * titleButton;
  23. @property(nonatomic, strong) CPDFPopMenu *popMenu;
  24. @end
  25. @implementation CPDFViewController
  26. #pragma mark - Initializers
  27. - (instancetype)initWithFilePath:(NSString *)filePath {
  28. if(self = [super init]) {
  29. self.filePath = filePath;
  30. }
  31. return self;
  32. }
  33. - (void)viewDidLoad {
  34. [super viewDidLoad];
  35. self.view.backgroundColor = [CPDFColorUtils CPDFViewControllerBackgroundColor];
  36. self.pdfListView = [[CPDFListView alloc] initWithFrame:self.view.bounds];
  37. self.pdfListView.performDelegate = self;
  38. self.pdfListView.delegate = self;
  39. self.pdfListView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
  40. [self.view addSubview:self.pdfListView];
  41. UIBarButtonItem *leftItem = [[UIBarButtonItem alloc] initWithImage:[UIImage imageNamed:@"CPDFThunbnailImageEnter" inBundle:[NSBundle bundleForClass:self.class] compatibleWithTraitCollection:nil] style:UIBarButtonItemStylePlain target:self action:@selector(buttonItemClicked_thumbnail:)];
  42. self.navigationItem.leftBarButtonItem = leftItem;
  43. __block typeof(self) blockSelf = self;
  44. self.rightView = [[CNavigationRightView alloc] initWithDefaultItemsClickBack:^(NSUInteger tag) {
  45. switch (tag) {
  46. case CNavigationRightTypeSearch:
  47. [blockSelf navigationRightItemSearch];
  48. break;
  49. case CNavigationRightTypeBota:
  50. [blockSelf navigationRightItemBota];
  51. break;
  52. default:
  53. case CNavigationRightTypeMore:
  54. [blockSelf navigationRightItemMore];
  55. break;
  56. }
  57. }];
  58. //titleButton
  59. CNavigationBarTitleButton * navTitleButton = [[CNavigationBarTitleButton alloc] init];
  60. CGRect frame = navTitleButton.frame;
  61. frame.size.width = 35;
  62. navTitleButton.frame = frame;
  63. self.titleButton = navTitleButton;
  64. self.navigationItem.titleView = navTitleButton;
  65. [navTitleButton setImage:[UIImage imageNamed:@"syasarrow"] forState:UIControlStateNormal];
  66. [navTitleButton addTarget:self action:@selector(titleButtonClickd:) forControlEvents:UIControlEventTouchUpInside];
  67. self.searchToolbar = [[CSearchToolbar alloc] initWithPDFView:self.pdfListView];
  68. self.searchToolbar.delegate = self;
  69. [self reloadDocumentWithFilePath:self.filePath completion:^(BOOL result) {
  70. }];
  71. }
  72. - (void) titleButtonClickd:(UIButton *) button {
  73. }
  74. - (void)viewWillLayoutSubviews {
  75. [super viewWillLayoutSubviews];
  76. if (@available(iOS 11.0, *)) {
  77. [self.popMenu showMenuInRect:CGRectMake(self.view.frame.size.width - self.view.safeAreaInsets.right - 250, self.view.safeAreaInsets.top - 10, 250, 200)];
  78. } else {
  79. // Fallback on earlier versions
  80. [self.popMenu showMenuInRect:CGRectMake(self.view.frame.size.width - 250, -10, 250, 200)];
  81. }
  82. if (@available(iOS 11.0, *)) {
  83. self.pdfListView.frame = CGRectMake(self.view.safeAreaInsets.left, self.view.safeAreaInsets.top, self.view.frame.size.width - self.view.safeAreaInsets.left - self.view.safeAreaInsets.right, self.view.frame.size.height - self.view.safeAreaInsets.bottom- self.view.safeAreaInsets.top);
  84. } else {
  85. self.pdfListView.frame = self.view.bounds;
  86. }
  87. }
  88. #pragma mark - Accessors
  89. #pragma mark - Public method
  90. - (void)reloadDocumentWithFilePath:(NSString *)filePath completion:(void (^)(BOOL result))completion {
  91. self.title = [[filePath lastPathComponent] stringByDeletingPathExtension];
  92. _navigationTitle = self.title;
  93. //
  94. [self.titleButton setTitle:self.title forState:UIControlStateNormal];
  95. [self.navigationController.view setUserInteractionEnabled:NO];
  96. if (![self.loadingView superview]) {
  97. [self.view addSubview:self.loadingView];
  98. }
  99. [self.loadingView startAnimating];
  100. dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
  101. NSURL *url = [NSURL fileURLWithPath:filePath];
  102. CPDFDocument *document = [[CPDFDocument alloc] initWithURL:url];
  103. dispatch_async(dispatch_get_main_queue(), ^{
  104. [self.navigationController.view setUserInteractionEnabled:YES];
  105. [self.loadingView stopAnimating];
  106. [self.loadingView removeFromSuperview];
  107. if (document.error && document.error.code != CPDFDocumentPasswordError) {
  108. UIAlertAction *okAction = [UIAlertAction actionWithTitle:NSLocalizedString(@"OK", nil) style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
  109. [self.navigationController popViewControllerAnimated:YES];
  110. }];
  111. UIAlertController *alert = [UIAlertController alertControllerWithTitle:@""
  112. message:NSLocalizedString(@"Sorry PDF Reader Can't open this pdf file!", nil)
  113. preferredStyle:UIAlertControllerStyleAlert];
  114. [alert addAction:okAction];
  115. if (completion) {
  116. completion(NO);
  117. }
  118. } else {
  119. self.pdfListView.document = document;
  120. if (completion) {
  121. completion(YES);
  122. }
  123. }
  124. });
  125. });
  126. }
  127. #pragma mark - Action
  128. - (void)navigationRightItemSearch {
  129. [self.searchToolbar showInView:self.navigationController.navigationBar];
  130. self.title = nil;
  131. self.navigationItem.rightBarButtonItem = nil;
  132. }
  133. - (void)navigationRightItemBota {
  134. CPDFBOTAViewController *botaViewController = [[CPDFBOTAViewController alloc] initWithPDFView:self.pdfListView];
  135. botaViewController.delegate = self;
  136. AAPLCustomPresentationController *presentationController NS_VALID_UNTIL_END_OF_SCOPE;
  137. presentationController = [[AAPLCustomPresentationController alloc] initWithPresentedViewController:botaViewController presentingViewController:self];
  138. botaViewController.transitioningDelegate = presentationController;
  139. [self presentViewController:botaViewController animated:YES completion:nil];
  140. }
  141. - (void)navigationRightItemMore {
  142. CPDFPopMenuView * menuView = [[CPDFPopMenuView alloc] initWithFrame:CGRectMake(0, 0, 200, 200)];
  143. menuView.delegate = self;
  144. self.popMenu = [CPDFPopMenu popMenuWithContentView:menuView];
  145. self.popMenu.dimCoverLayer = YES;
  146. if (@available(iOS 11.0, *)) {
  147. [self.popMenu showMenuInRect:CGRectMake(self.view.frame.size.width - self.view.safeAreaInsets.right - 250, self.view.safeAreaInsets.top - 10, 250, 200)];
  148. } else {
  149. // Fallback on earlier versions
  150. [self.popMenu showMenuInRect:CGRectMake(self.view.frame.size.width - 250, -10, 250, 200)];
  151. }
  152. }
  153. - (void)buttonItemClicked_thumbnail:(id)sender {
  154. CPDFThumbnailViewController *thumbnailViewController = [[CPDFThumbnailViewController alloc] initWithPDFView:self.pdfListView];
  155. thumbnailViewController.delegate = self;
  156. [self.navigationController pushViewController:thumbnailViewController animated:NO];
  157. }
  158. - (void)menuItemClick_CopyAction:(id)sender {
  159. if (self.pdfListView.currentSelection.string)
  160. [[UIPasteboard generalPasteboard] setString:self.pdfListView.currentSelection.string];
  161. [self.pdfListView clearSelection];
  162. }
  163. #pragma mark - CPDFViewDelegate
  164. - (void)PDFViewDocumentDidLoaded:(CPDFView *)pdfView {
  165. UIBarButtonItem* rightItem = [[UIBarButtonItem alloc] initWithCustomView:self.rightView];
  166. self.navigationItem.rightBarButtonItem = rightItem;
  167. }
  168. - (void)PDFViewCurrentPageDidChanged:(CPDFView *)pdfView {
  169. }
  170. #pragma mark - CPDFListViewDelegate
  171. - (void)PDFListViewPerformTouchEnded:(CPDFListView *)pdfView {
  172. if (CPDFViewAnnotationModeNone != self.pdfListView.annotationMode) {
  173. self.pdfListView.annotationMode = CPDFViewAnnotationModeNone;
  174. return;
  175. }
  176. if (UIUserInterfaceIdiomPhone == UI_USER_INTERFACE_IDIOM()) {
  177. if (self.navigationController.navigationBarHidden) {
  178. [self.navigationController setNavigationBarHidden:NO animated:YES];
  179. [UIView animateWithDuration:0.3 animations:^{
  180. self.pdfListView.pageSliderView.alpha = 1.0;
  181. }];
  182. } else {
  183. [self.navigationController setNavigationBarHidden:YES animated:YES];
  184. [UIView animateWithDuration:0.3 animations:^{
  185. self.pdfListView.pageSliderView.alpha = 0.0;
  186. }];
  187. }
  188. } else {
  189. if (self.navigationController.navigationBarHidden) {
  190. [self.navigationController setNavigationBarHidden:NO animated:YES];
  191. [UIView animateWithDuration:0.3 animations:^{
  192. self.pdfListView.pageSliderView.alpha = 1.0;
  193. }];
  194. } else {
  195. [self.navigationController setNavigationBarHidden:YES animated:YES];
  196. [UIView animateWithDuration:0.3 animations:^{
  197. self.pdfListView.pageSliderView.alpha = 0.0;
  198. }];
  199. }
  200. }
  201. }
  202. #pragma mark - CPDFMorelistViewDelegate
  203. - (void)PDFMoreListViewController:(CPDFMoreListViewController *)moreVC didSelectRow:(CPDFMoreListViewType)row {
  204. if(CPDFMoreListViewTypeInfo == row){
  205. //File Info
  206. CPDFInfoViewController * infoVc = [[CPDFInfoViewController alloc] initWithPDFView:self.pdfListView];
  207. [self.navigationController pushViewController:infoVc animated:YES];
  208. } else {
  209. CPDFDisplayViewController *displayVc = [[CPDFDisplayViewController alloc] initWithPDFView:self.pdfListView];
  210. displayVc.delegate = self;
  211. [self.navigationController pushViewController:displayVc animated:NO];
  212. }
  213. }
  214. #pragma mark - CSearchToolbarDelegate
  215. - (void)searchToolbar:(CSearchToolbar *)searchToolbar onSearchQueryResults:(NSArray *)results {
  216. if ([results count] < 1) {
  217. UIAlertAction *cancelAction = [UIAlertAction actionWithTitle:NSLocalizedString(@"OK", nil)
  218. style:UIAlertActionStyleCancel
  219. handler:nil];
  220. UIAlertController *alert = [UIAlertController alertControllerWithTitle:nil
  221. message:NSLocalizedString(@"your have‘t search result", nil)
  222. preferredStyle:UIAlertControllerStyleAlert];
  223. [alert addAction:cancelAction];
  224. [self presentViewController:alert animated:YES completion:nil];
  225. return;
  226. }
  227. [self searchToolbarOnExitSearch:searchToolbar];
  228. CPDFSearchResultsViewController* searchResultController = [[CPDFSearchResultsViewController alloc] initWithResultArray:results keyword:searchToolbar.searchKeyString document:self.pdfListView.document];
  229. searchResultController.delegate = self;
  230. [self.navigationController pushViewController:searchResultController animated:YES];
  231. }
  232. - (void)searchToolbarOnExitSearch:(CSearchToolbar *)searchToolbar {
  233. if([searchToolbar superview]) {
  234. [searchToolbar removeFromSuperview];
  235. UIBarButtonItem *rightItem = [[UIBarButtonItem alloc] initWithCustomView:self.rightView];
  236. self.navigationItem.rightBarButtonItem = rightItem;
  237. self.title = self.navigationTitle;
  238. }
  239. }
  240. #pragma mark - CPDFDisplayViewDelegate
  241. - (void)displayViewControllerDismiss:(CPDFDisplayViewController *)displayViewController {
  242. [self.navigationController popToRootViewControllerAnimated:YES];
  243. }
  244. #pragma mark - CPDFBOTAViewControllerDelegate
  245. - (void)botaViewControllerDismiss:(CPDFBOTAViewController *)botaViewController {
  246. [self.navigationController popViewControllerAnimated:YES];
  247. }
  248. #pragma mark - CPDFSearchResultsDelegate
  249. - (void)searchResultsView:(CPDFSearchResultsViewController *)resultVC forSelection:(CPDFSelection *)selection indexPath:(NSIndexPath *)indexPath {
  250. [self.navigationController popViewControllerAnimated:YES];
  251. NSInteger pageIndex = [self.pdfListView.document indexForPage:selection.page];
  252. [self.pdfListView goToPageIndex:pageIndex animated:NO];
  253. [self.pdfListView setHighlightedSelection:selection animated:YES];
  254. }
  255. -(void)searchResultsViewControllerDismiss:(CPDFSearchResultsViewController *)searchResultsViewController {
  256. [self.navigationController popViewControllerAnimated:YES];
  257. }
  258. #pragma mark - CPDFThumbnailViewControllerDelegate
  259. - (void)thumbnailViewController:(CPDFThumbnailViewController *)thumbnailViewController pageIndex:(NSInteger)pageIndex {
  260. [self.pdfListView goToPageIndex:pageIndex animated:NO];
  261. [self.navigationController popViewControllerAnimated:YES];
  262. }
  263. #pragma mark - CPDFMenuViewdelegate
  264. - (void)menuDidClickAtView:(CPDFPopMenuView *)view clickType:(CPDFPopMenuViewType)viewType {
  265. switch (viewType) {
  266. case CPDFPopMenuViewTypeSetting:
  267. //display controller
  268. {
  269. [self.popMenu hideMenu];
  270. CPDFDisplayViewController *displayVc = [[CPDFDisplayViewController alloc] initWithPDFView:self.pdfListView];
  271. displayVc.delegate = self;
  272. AAPLCustomPresentationController *presentationController NS_VALID_UNTIL_END_OF_SCOPE;
  273. presentationController = [[AAPLCustomPresentationController alloc] initWithPresentedViewController:displayVc presentingViewController:self];
  274. displayVc.transitioningDelegate = presentationController;
  275. [self presentViewController:displayVc animated:YES completion:nil];
  276. }
  277. break;
  278. case CPDFPopMenuViewTypeInfo:
  279. {
  280. [self.popMenu hideMenu];
  281. CPDFInfoViewController * infoVc = [[CPDFInfoViewController alloc] initWithPDFView:self.pdfListView];
  282. AAPLCustomPresentationController *presentationController NS_VALID_UNTIL_END_OF_SCOPE;
  283. presentationController = [[AAPLCustomPresentationController alloc] initWithPresentedViewController:infoVc presentingViewController:self];
  284. infoVc.transitioningDelegate = presentationController;
  285. [self presentViewController:infoVc animated:YES completion:nil];
  286. }
  287. break;
  288. case CPDFPopMenuViewTypeShare:
  289. {
  290. [self.popMenu hideMenu];
  291. if (self.pdfListView.isEdited) {
  292. dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
  293. [self.pdfListView commitEditing];
  294. dispatch_async(dispatch_get_main_queue(), ^{
  295. [self.pdfListView endOfEditing];
  296. [self shareAction];
  297. });
  298. });
  299. } else {
  300. [self.pdfListView endOfEditing];
  301. [self shareAction];
  302. }
  303. }
  304. break;
  305. case CPDFPopMenuViewTypeAddFile:
  306. {
  307. [self.popMenu hideMenu];
  308. NSArray *documentTypes = @[@"com.adobe.pdf"];
  309. UIDocumentPickerViewController *documentPickerViewController = [[UIDocumentPickerViewController alloc] initWithDocumentTypes:documentTypes inMode:UIDocumentPickerModeOpen];
  310. documentPickerViewController.delegate = self;
  311. [self presentViewController:documentPickerViewController animated:YES completion:nil];
  312. }
  313. default:
  314. break;
  315. }
  316. }
  317. - (void)shareAction {
  318. UIActivityViewController *activityVC = [[UIActivityViewController alloc]initWithActivityItems:@[self.pdfListView.document.documentURL] applicationActivities:nil];
  319. activityVC.definesPresentationContext = YES;
  320. [self presentViewController:activityVC animated:YES completion:nil];
  321. activityVC.completionWithItemsHandler = ^(UIActivityType _Nullable activityType, BOOL completed, NSArray * _Nullable returnedItems, NSError * _Nullable activityError) {
  322. if (completed) {
  323. NSLog(@"Success!");
  324. } else {
  325. NSLog(@"Failed Or Canceled!");
  326. }
  327. };
  328. }
  329. #pragma mark - UIDocument Picker
  330. - (void)documentPicker:(UIDocumentPickerViewController *)controller didPickDocumentAtURL:(NSURL *)url {
  331. __weak typeof(self) weakSelf = self;
  332. BOOL canAccessingResource = [url startAccessingSecurityScopedResource];
  333. if(canAccessingResource) {
  334. NSFileCoordinator *fileCoordinator = [[NSFileCoordinator alloc] init];
  335. NSError *error;
  336. [fileCoordinator coordinateReadingItemAtURL:url options:0 error:&error byAccessor:^(NSURL *newURL) {
  337. [weakSelf reloadDocumentWithFilePath:newURL.path completion:^(BOOL result) {
  338. }];
  339. }];
  340. if (error) {
  341. }
  342. } else {
  343. // startAccessingSecurityScopedResource fail
  344. }
  345. [url stopAccessingSecurityScopedResource];
  346. }
  347. @end