RedactionContentViewModel.cs 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552
  1. using ComPDFKit.Import;
  2. using ComPDFKit.PDFAnnotation;
  3. using ComPDFKit.PDFPage;
  4. using ComPDFKitViewer;
  5. using ComPDFKitViewer.AnnotEvent;
  6. using ComPDFKitViewer.PdfViewer;
  7. using PDF_Office.CustomControl;
  8. using PDF_Office.EventAggregators;
  9. using PDF_Office.Model;
  10. using PDF_Office.Properties;
  11. using Prism.Commands;
  12. using Prism.Events;
  13. using Prism.Mvvm;
  14. using Prism.Regions;
  15. using Prism.Services.Dialogs;
  16. using System;
  17. using System.Collections.Generic;
  18. using System.Linq;
  19. using System.Windows;
  20. using System.Windows.Controls;
  21. using System.Windows.Input;
  22. using System.Windows.Media;
  23. namespace PDF_Office.ViewModels.EditTools.Redaction
  24. {
  25. public class RedactionContentViewModel : BindableBase, INavigationAware
  26. {
  27. public IEventAggregator eventAggregator;
  28. public IRegionManager redactionRegion;
  29. public IDialogService dialogs;
  30. private CPDFViewer PDFViewer;
  31. private ViewContentViewModel viewContentViewModel;
  32. private RedactionAnnotArgs redactionArgs = new RedactionAnnotArgs();
  33. public string RedactionDocumentRegionName { get; set; }
  34. public string RedactionBottomBarRegionName { get; set; }
  35. public string RedactionDocumentName = "RedactionDocumentContent";
  36. public string Unicode = null;
  37. public DelegateCommand CloseEditToolCommand { get; set; }
  38. public DelegateCommand<string> ApplyCommmand { get; set; }
  39. public DelegateCommand PageRedactionCommand { get; set; }
  40. public DelegateCommand<string> EraseCommand { get; set; }
  41. public RedactionCommandEventArgs TempArgs { get; set; }
  42. private int currentPage = 0;
  43. /// <summary>
  44. /// 是否因为本身传递值 防止循环调用
  45. /// </summary>
  46. private bool isFromSelf = false;
  47. public int CurrentPage
  48. {
  49. get { return currentPage; }
  50. set
  51. {
  52. SetProperty(ref currentPage, value);
  53. if (value >= 1 && value <= PDFViewer.Document.PageCount && !isFromSelf)
  54. {
  55. PDFViewer.GoToPage(value - 1);
  56. }
  57. }
  58. }
  59. private int pageCount = 0;
  60. public int PageCount
  61. {
  62. get { return pageCount; }
  63. set
  64. {
  65. SetProperty(ref pageCount, value);
  66. }
  67. }
  68. private bool isEnable = false;
  69. /// <summary>
  70. /// 按钮是否启用
  71. /// </summary>
  72. public bool IsEnable
  73. {
  74. get { return isEnable; }
  75. set
  76. {
  77. SetProperty(ref isEnable, value);
  78. }
  79. }
  80. public RedactionContentViewModel(IRegionManager regionManager, IEventAggregator eventAggregator, IDialogService dialogService)
  81. {
  82. this.redactionRegion = regionManager;
  83. this.eventAggregator = eventAggregator;
  84. this.dialogs = dialogService;
  85. RedactionDocumentRegionName = Guid.NewGuid().ToString();
  86. Unicode = App.mainWindowViewModel.SelectedItem.Unicode;
  87. CloseEditToolCommand = new DelegateCommand(CloseEditTool);
  88. ApplyCommmand = new DelegateCommand<string>(apply,CanExcute).ObservesProperty(() => IsEnable);
  89. EraseCommand = new DelegateCommand<string>(erase, CanExcute).ObservesProperty(() => IsEnable);
  90. PageRedactionCommand = new DelegateCommand(pageMark);
  91. eventAggregator.GetEvent<RedactionCommandEvent>().Subscribe(SetContextMenu, e => e.UniCode == Unicode);
  92. }
  93. private void SetContextMenu(RedactionCommandEventArgs obj)
  94. {
  95. var contextmenu = App.Current.FindResource("RedactionContextMenu") as ContextMenu;
  96. obj.args.PopupMenu = contextmenu;
  97. TempArgs = obj;
  98. for(int i=0;i<contextmenu.Items.Count;i++)
  99. {
  100. if(contextmenu.Items[i] is MenuItem)
  101. {
  102. var item = contextmenu.Items[i] as MenuItem;
  103. switch (item.Name)
  104. {
  105. case "MenuDelete":
  106. item.Command = ApplicationCommands.Delete;
  107. item.CommandParameter = (UIElement)obj.Sender;
  108. break;
  109. case "MenuSetDeufalt":
  110. item.Command = new DelegateCommand<RedactionCommandEventArgs>(SetDefualtProperty);
  111. item.CommandParameter = obj;
  112. break;
  113. case "MenuProperties":
  114. item.Command = new DelegateCommand<RedactionCommandEventArgs>(ShowProperty);
  115. item.CommandParameter = obj;
  116. break;
  117. case "MenuRepeat":
  118. item.Command = new DelegateCommand<RedactionCommandEventArgs>(RepreatMark);
  119. item.CommandParameter = obj;
  120. break;
  121. case "MenuApply":
  122. item.Command = this.ApplyCommmand;
  123. item.CommandParameter = "Single";
  124. break;
  125. case "MenuErase":
  126. item.Command = this.EraseCommand;
  127. item.CommandParameter = "Single";
  128. break;
  129. default:
  130. break;
  131. }
  132. }
  133. }
  134. }
  135. /// <summary>
  136. /// 设置当前为默认属性
  137. /// </summary>
  138. /// <param name="args"></param>
  139. private void SetDefualtProperty(RedactionCommandEventArgs args)
  140. {
  141. var annoteargs = args.args.AnnotEventArgsList[0] as RedactionAnnotArgs;
  142. DialogParameters keyValues = new DialogParameters();
  143. keyValues.Add(ParameterNames.DataModel,args.args.AnnotEventArgsList[0] as RedactionAnnotArgs);
  144. Settings.Default.RedactionsSettings.SetDefualtValue(annoteargs.Content, annoteargs.LineColor,annoteargs.BgColor,annoteargs.FontColor, (int)annoteargs.FontSize,string.IsNullOrEmpty(annoteargs.Content) ? false : true, annoteargs.Align, annoteargs.FontFamily.ToString(),annoteargs.FontWeight);
  145. PDFViewer.SetMouseMode(MouseModes.AnnotCreate);
  146. PDFViewer.SetToolParam(annoteargs);
  147. }
  148. /// <summary>
  149. /// 显示属性弹窗
  150. /// </summary>
  151. /// <param name="args"></param>
  152. private void ShowProperty(RedactionCommandEventArgs args)
  153. {
  154. DialogParameters keyValues = new DialogParameters();
  155. keyValues.Add(ParameterNames.DataModel, args.args.AnnotEventArgsList[0] as RedactionAnnotArgs);
  156. dialogs.ShowDialog(DialogNames.MarkSettingDialog,keyValues,null);
  157. }
  158. /// <summary>
  159. /// 显示跨页标记弹窗
  160. /// </summary>
  161. /// <param name="args"></param>
  162. private void RepreatMark(RedactionCommandEventArgs args)
  163. {
  164. DialogParameters keyValues = new DialogParameters();
  165. keyValues.Add(ParameterNames.PageCount,PDFViewer.Document.PageCount);
  166. dialogs.ShowDialog(DialogNames.RepeatMarkDialog, keyValues, e=> {
  167. if (e.Result == ButtonResult.OK)
  168. {
  169. PDFViewer.AddRedaction(e.Parameters.GetValue<List<int>>(ParameterNames.PageList), args.args);
  170. }
  171. });
  172. }
  173. /// <summary>
  174. /// 应用
  175. /// </summary>
  176. private void apply(string type)
  177. {
  178. AlertsMessage alertsMessage = new AlertsMessage();
  179. alertsMessage.ShowDialog("Apply Redactions", "Use blank blocks to remove selected sensitive content." +
  180. "This action will permanently delete the marked ciphertext information from this document and you will not be able to retrieve the marked ciphertext information.", "Cancel", "Apply & Save As");
  181. if (alertsMessage.result == ContentResult.Ok)
  182. {
  183. if (!string.IsNullOrEmpty(type) && type == "All")
  184. {
  185. viewContentViewModel.saveAsFile(applyAll);
  186. }
  187. else
  188. {
  189. viewContentViewModel.saveAsFile(applySingle);
  190. }
  191. }
  192. }
  193. /// <summary>
  194. /// 擦除
  195. /// </summary>
  196. private void erase(string type)
  197. {
  198. AlertsMessage alertsMessage = new AlertsMessage();
  199. alertsMessage.ShowDialog("","Replace selected sensitive content with color blocks."+
  200. "This action will permanently delete the marked ciphertext information from this document and you will not be able to retrieve the marked ciphertext information.", "Cancel", "Apply & Save As");
  201. if (alertsMessage.result == ContentResult.Ok)
  202. {
  203. if (!string.IsNullOrEmpty(type) && type == "All")
  204. {
  205. viewContentViewModel.saveAsFile(eraseAll);
  206. }
  207. else
  208. {
  209. viewContentViewModel.saveAsFile(eraseSingle);
  210. }
  211. }
  212. }
  213. /// <summary>
  214. /// 应用所有密文块
  215. /// </summary>
  216. private void applyAll()
  217. {
  218. PDFViewer.Document.ApplyRedaction();
  219. PDFViewer.Document.ReleasePages();
  220. PDFViewer.ReloadDocument();
  221. }
  222. /// <summary>
  223. /// 擦除所有密文块
  224. /// </summary>
  225. private void eraseAll()
  226. {
  227. for (int i = 0; i < PDFViewer.Document.PageCount; i++)
  228. {
  229. //获取页面Page对象
  230. var page = PDFViewer.Document.PageAtIndex(i);
  231. var annots = PDFViewer.GetAnnotCommentList(i, PDFViewer.Document);
  232. //循环擦除当前页的标记密文
  233. for (int j = 0; j < annots.Count; j++)
  234. {
  235. if (annots[j].EventType == AnnotArgsType.AnnotRedaction)
  236. {
  237. foreach (var rect in (annots[j] as RedactionAnnotArgs).QuardRects)
  238. {
  239. page.ErasureRedaction(rect);
  240. }
  241. }
  242. }
  243. }
  244. }
  245. /// <summary>
  246. /// 应用选中的密文块
  247. /// </summary>
  248. private void applySingle()
  249. {
  250. AnnotCommandArgs annotCommand =TempArgs.args;
  251. if (annotCommand != null)
  252. {
  253. List<RedactionAnnotArgs> redactionList = new List<RedactionAnnotArgs>();
  254. foreach (AnnotHandlerEventArgs annotArgs in annotCommand.AnnotEventArgsList)
  255. {
  256. if (annotArgs.EventType == AnnotArgsType.AnnotRedaction)
  257. {
  258. redactionList.Add((RedactionAnnotArgs)annotArgs);
  259. }
  260. }
  261. PDFViewer.ApplyRedaction(redactionList);
  262. }
  263. }
  264. /// <summary>
  265. /// 擦除选中的密文块
  266. /// </summary>
  267. private void eraseSingle()
  268. {
  269. AnnotCommandArgs annotCommand = TempArgs.args;
  270. if (annotCommand != null)
  271. {
  272. List<RedactionAnnotArgs> redactionList = new List<RedactionAnnotArgs>();
  273. foreach (AnnotHandlerEventArgs annotArgs in annotCommand.AnnotEventArgsList)
  274. {
  275. if (annotArgs.EventType == AnnotArgsType.AnnotRedaction)
  276. {
  277. foreach (var rect in (annotArgs as RedactionAnnotArgs).QuardRects)
  278. {
  279. var page = PDFViewer.Document.PageAtIndex((annotArgs as RedactionAnnotArgs).PageIndex);
  280. page.ErasureRedaction(rect);
  281. }
  282. }
  283. }
  284. }
  285. }
  286. private bool CanExcute(string type)
  287. {
  288. return IsEnable;
  289. }
  290. private void pageMark()
  291. {
  292. DialogParameters valuePairs = new DialogParameters();
  293. valuePairs.Add(ParameterNames.PageCount,PDFViewer.Document.PageCount);
  294. valuePairs.Add(ParameterNames.CurrentPageIndex,PDFViewer.CurrentIndex);
  295. dialogs.ShowDialog(DialogNames.PageMarkDialog,valuePairs,e=> {
  296. if(e.Result == ButtonResult.OK)
  297. {
  298. var pagelist = e.Parameters.GetValue<List<int>>(ParameterNames.PageList);
  299. addMarkToPages(pagelist);
  300. }
  301. });
  302. }
  303. private void addMarkToPages(List<int> list)
  304. {
  305. foreach (var page in list)
  306. {
  307. //根据页面大小,创建标记密文注释
  308. CPDFPage docPage = PDFViewer.Document.PageAtIndex(page);
  309. CPDFRedactAnnotation redactionAnnot = docPage.CreateAnnot(C_ANNOTATION_TYPE.C_ANNOTATION_REDACT) as CPDFRedactAnnotation;
  310. if (redactionAnnot == null)
  311. {
  312. //TODO 操作失败
  313. return;
  314. }
  315. redactionAnnot.SetQuardRects(new List<CRect>() { new CRect(0, (float)docPage.PageSize.Height, (float)docPage.PageSize.Width,0)});
  316. if (redactionArgs == null)
  317. return;
  318. byte[] lineColor = { redactionArgs.LineColor.R, redactionArgs.LineColor.G, redactionArgs.LineColor.B };
  319. redactionAnnot.SetOutlineColor(lineColor);
  320. if (redactionArgs.BgColor != Colors.Transparent)
  321. {
  322. byte[] bgColor = { redactionArgs.BgColor.R, redactionArgs.BgColor.G, redactionArgs.BgColor.B };
  323. redactionAnnot.SetFillColor(bgColor);
  324. }
  325. else
  326. {
  327. // redactionAnnot.ClearBgColor();
  328. }
  329. CTextAttribute textAttr = new CTextAttribute();
  330. byte[] fontColor = { redactionArgs.FontColor.R, redactionArgs.FontColor.G, redactionArgs.FontColor.B };
  331. textAttr.FontColor = fontColor;
  332. textAttr.FontSize = (float)redactionArgs.FontSize;
  333. redactionAnnot.SetTextAttribute(textAttr);
  334. switch (redactionArgs.Align)
  335. {
  336. case TextAlignment.Left:
  337. redactionAnnot.SetTextAlignment(C_TEXT_ALIGNMENT.ALIGNMENT_LEFT);
  338. break;
  339. case TextAlignment.Center:
  340. redactionAnnot.SetTextAlignment(C_TEXT_ALIGNMENT.ALIGNMENT_CENTER);
  341. break;
  342. case TextAlignment.Right:
  343. redactionAnnot.SetTextAlignment(C_TEXT_ALIGNMENT.ALIGNMENT_RIGHT);
  344. break;
  345. default:
  346. redactionAnnot.SetTextAlignment(C_TEXT_ALIGNMENT.ALIGNMENT_LEFT);
  347. break;
  348. }
  349. //byte transparency = (byte)Math.Round(redactionArgs.Transparency * 255);
  350. //redactionAnnot.SetTransparency(transparency);
  351. redactionAnnot.SetBorderWidth(1);
  352. //redactionAnnot.SetRect(new CRect(Left, Bottom, Right, Top));
  353. //redactionAnnot.SetCreationDate(Helpers.GetCurrentPdfTime());
  354. if (string.IsNullOrEmpty(Settings.Default.AppProperties.Description.Author))
  355. {
  356. redactionAnnot.SetAuthor(Settings.Default.AppProperties.Description.Author);
  357. }
  358. if (redactionArgs.Content != null && redactionArgs.Content != string.Empty)
  359. {
  360. redactionAnnot.SetOverlayText(redactionArgs.Content);
  361. }
  362. if (redactionAnnot.GetIsLocked() != redactionArgs.Locked)
  363. {
  364. redactionAnnot.SetIsLocked(redactionArgs.Locked);
  365. }
  366. redactionAnnot.UpdateAp();
  367. redactionAnnot.ReleaseAnnot();
  368. }
  369. }
  370. public void CloseEditTool()
  371. {
  372. bool isClose = true;
  373. if (CheckHasRedactionAnnote())
  374. {
  375. AlertsMessage alertsMessage = new AlertsMessage();
  376. alertsMessage.ShowDialog("", "There are unapplied redactions in this file. Exit will not save redaction.", "Cancel", "Exit");
  377. if (alertsMessage.result != ContentResult.Ok)
  378. {
  379. isClose = false;
  380. }
  381. }
  382. if(isClose)
  383. {
  384. PDFViewer.SetMouseMode(MouseModes.Default);
  385. redactionRegion.Regions[RegionNames.ViwerRegionName].Remove(PDFViewer);
  386. redactionRegion.Regions[RedactionDocumentRegionName].Remove(PDFViewer);
  387. this.eventAggregator.GetEvent<CloseEditToolEvent>().Publish(new EnumCloseModeUnicode { Unicode = this.Unicode, Status = EnumCloseMode.StatusCancel });
  388. App.mainWindowViewModel.SelectedItem.IsInReadctonMode = false;
  389. }
  390. }
  391. /// <summary>
  392. /// 检查是否有未应用的标记密文
  393. /// </summary>
  394. private bool CheckHasRedactionAnnote()
  395. {
  396. for (int i = 0; i < PDFViewer.Document.PageCount; i++)
  397. {
  398. var items = PDFViewer.GetAnnotCommentList(i, PDFViewer.Document);
  399. for (int j = 0; j < items.Count; j++)
  400. {
  401. if (items[j].EventType == AnnotArgsType.AnnotRedaction)
  402. {
  403. return true;
  404. }
  405. }
  406. }
  407. return false;
  408. }
  409. #region Navigation
  410. public bool IsNavigationTarget(NavigationContext navigationContext)
  411. {
  412. return true;
  413. }
  414. public void OnNavigatedFrom(NavigationContext navigationContext)
  415. {
  416. }
  417. public void OnNavigatedTo(NavigationContext navigationContext)
  418. {
  419. App.mainWindowViewModel.SelectedItem.IsInReadctonMode = true;
  420. navigationContext.Parameters.TryGetValue<CPDFViewer>(ParameterNames.PDFViewer, out PDFViewer);
  421. navigationContext.Parameters.TryGetValue<ViewContentViewModel>(ParameterNames.ViewContentViewModel, out viewContentViewModel);
  422. PDFViewer.InfoChanged -= PDFViewer_InfoChanged;
  423. PDFViewer.InfoChanged += PDFViewer_InfoChanged;
  424. PDFViewer.AnnotEditHandler -= PDFViewer_AnnotEditHandler;
  425. PDFViewer.AnnotEditHandler += PDFViewer_AnnotEditHandler;
  426. CurrentPage = PDFViewer.CurrentIndex + 1;
  427. PageCount = PDFViewer.Document.PageCount;
  428. if (!redactionRegion.Regions[RedactionDocumentRegionName].Views.Contains(PDFViewer))
  429. {
  430. redactionArgs = new RedactionAnnotArgs();
  431. AnnotHandlerEventArgs annotArgs = null;
  432. redactionArgs.LineColor = Settings.Default.RedactionsSettings.LineColor;
  433. redactionArgs.BgColor = Settings.Default.RedactionsSettings.BgColor;
  434. redactionArgs.FontColor = Settings.Default.RedactionsSettings.FontColor;
  435. redactionArgs.Align = Settings.Default.RedactionsSettings.Align;
  436. redactionArgs.FontSize = Settings.Default.RedactionsSettings.FontSize;
  437. redactionArgs.Content = Settings.Default.RedactionsSettings.Content;
  438. if (!Settings.Default.RedactionsSettings.isUseText)
  439. {
  440. redactionArgs.Content = "";
  441. }
  442. annotArgs = redactionArgs;
  443. if (annotArgs != null)
  444. {
  445. //设置注释作者
  446. annotArgs.Author = Settings.Default.AppProperties.Description.Author;
  447. PDFViewer.SetMouseMode(MouseModes.AnnotCreate);
  448. PDFViewer.SetToolParam(annotArgs);
  449. }
  450. redactionRegion.AddToRegion(RedactionDocumentRegionName, PDFViewer);
  451. }
  452. }
  453. private void PDFViewer_AnnotEditHandler(object sender, List<AnnotEditEvent> e)
  454. {
  455. //添加注释后检测是否有未应用的标记密文注释
  456. IsEnable = false;
  457. for(int i=0;i<PDFViewer.Document.PageCount;i++)
  458. {
  459. var annotes = PDFViewer.GetAnnotCommentList(i,PDFViewer.Document);
  460. for(int j=0;j<annotes.Count;j++)
  461. {
  462. if(annotes[j].EventType == AnnotArgsType.AnnotRedaction)
  463. {
  464. IsEnable = true;
  465. return;
  466. }
  467. }
  468. }
  469. }
  470. private void PDFViewer_InfoChanged(object sender, KeyValuePair<string, object> e)
  471. {
  472. isFromSelf = true;
  473. if(e.Key=="PageNum")
  474. {
  475. var data = e.Value as RenderData;
  476. CurrentPage = data.PageIndex;
  477. }
  478. isFromSelf = false;
  479. }
  480. #endregion
  481. }
  482. }