Advertisement
Guest User

Untitled

a guest
Jan 23rd, 2020
91
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 12.30 KB | None | 0 0
  1. using System;
  2. using System.Linq;
  3. using System.Text;
  4. using System.Collections.Generic;
  5. using System.Threading.Tasks;
  6. using System.Windows;
  7. using System.Windows.Controls;
  8. using System.Windows.Data;
  9. using System.Windows.Documents;
  10. using System.Windows.Input;
  11. using System.Windows.Media;
  12. using System.Windows.Media.Imaging;
  13. using System.Windows.Navigation;
  14. using System.Windows.Shapes;
  15. using corel = Corel.Interop.VGCore;
  16. using Microsoft.VisualBasic.FileIO;
  17. using System.Text.RegularExpressions;
  18.  
  19. namespace Voyager
  20. {
  21. public struct Options
  22. {
  23. public string path { get; set; }
  24. public int start_row { get; set; }
  25. public string id_column { get; set; }
  26. public string price_column { get; set; }
  27. public bool hide_price { get; set; }
  28. public string lang_1_column { get; set; }
  29. public string lang_2_column { get; set; }
  30. }
  31.  
  32. public partial class DockerUI : UserControl
  33. {
  34. private corel.Application app;
  35. private Styles.StylesController stylesController;
  36.  
  37. public DockerUI(object _app)
  38. {
  39. InitializeComponent();
  40. try
  41. {
  42. this.app = _app as corel.Application;
  43. stylesController = new Styles.StylesController(this.Resources, this.app);
  44. }
  45. catch
  46. {
  47. global::System.Windows.MessageBox.Show("VGCore Erro");
  48. }
  49. }
  50.  
  51. private void UserControl_Loaded(object sender, RoutedEventArgs e)
  52. {
  53. stylesController.LoadThemeFromPreference();
  54. }
  55.  
  56. private Options GetOptions()
  57. {
  58. Options opts = new Options();
  59.  
  60. opts.hide_price = hidePriceBox.IsChecked.GetValueOrDefault(false);
  61. opts.lang_1_column = lang1Box.Text;
  62. opts.lang_2_column = lang2Box.Text;
  63. opts.price_column = priceBox.Text;
  64. opts.id_column = idBox.Text;
  65. opts.path = fileBox.Text;
  66.  
  67. if (opts.path.Length == 0)
  68. {
  69. throw new System.ArgumentException("Plik CSV musi byc wybrany");
  70. }
  71. if (opts.id_column.Length == 0)
  72. {
  73. throw new System.ArgumentException("Kolumna z numerem produktu musi byc podana");
  74. }
  75. try
  76. {
  77. opts.start_row = Int32.Parse(firstRowBox.Text);
  78. }
  79. catch
  80. {
  81. throw new System.ArgumentException("Pierwszy rzad musi byc liczba. Podano: " + firstRowBox.Text);
  82. }
  83. return opts;
  84. }
  85.  
  86. private void RunButton_Click(object sender, RoutedEventArgs e)
  87. {
  88. statusField.Content = "";
  89.  
  90. Options opts;
  91. try
  92. {
  93. opts = GetOptions();
  94. }
  95. catch (Exception ex)
  96. {
  97. System.Windows.MessageBox.Show(ex.ToString());
  98. return;
  99. }
  100.  
  101. /*System.Windows.MessageBox.Show(
  102. "file: " + opts.path + "\n" +
  103. "first row: " + opts.start_row + "\n" +
  104. "id: " + opts.id_column + "\n" +
  105. "price: " + opts.price_column + "\n" +
  106. "lang1: " + opts.lang_1_column + "\n" +
  107. "lang2: " + opts.lang_2_column + "\n");
  108. */
  109. Process(opts, (double status) => {
  110. statusField.Content = "Progress: " + status + "%";
  111. });
  112. statusField.Content = "Zakonczone.";
  113. }
  114.  
  115. private void FileButton_Click(object sender, RoutedEventArgs e)
  116. {
  117. var dlg = new Microsoft.Win32.OpenFileDialog();
  118. dlg.FileName = fileBox.Text; // Default file name
  119. dlg.DefaultExt = ".csv"; // Default file extension
  120. dlg.Filter = "Comma Separaated Values (.csv)|*.csv"; // Filter files by extension
  121.  
  122. Nullable<bool> result = dlg.ShowDialog();
  123. if (result == true)
  124. {
  125. fileBox.Text = dlg.FileName;
  126. }
  127. else
  128. {
  129. fileBox.Text = "";
  130. }
  131. }
  132.  
  133. // Corel macro related code:
  134.  
  135. public class Data
  136. {
  137. public struct Row
  138. {
  139. public string price { get; set; }
  140. public string lang1 { get; set; }
  141. public string lang2 { get; set; }
  142. }
  143. Dictionary<string, Row> data;
  144.  
  145.  
  146. // Returns 0-based column index in excel. Returns -1 if empty.
  147. private int ColumnNameToIndex(string name_any)
  148. {
  149. string name = name_any.ToUpper();
  150. int number = 0;
  151. int pow = 1;
  152. for (int i = name.Length - 1; i >= 0; i--)
  153. {
  154. if (name[i] < 'A' || name[i] > 'Z')
  155. throw new System.ArgumentException("Nazwa kolumny moze byc tylko literami. Znaleziono: " + name_any);
  156. number += (name[i] - 'A' + 1) * pow;
  157. pow *= 26;
  158. }
  159. return number - 1;
  160. }
  161.  
  162. private string GetField(string field_name, ref string[] fields)
  163. {
  164. int index = ColumnNameToIndex(field_name);
  165. if (index < 0 || index >= fields.Length) return "";
  166. return fields[index];
  167. }
  168.  
  169. public Data(Options opts)
  170. {
  171. data = new Dictionary<string, Row>();
  172.  
  173. using (TextFieldParser parser = new TextFieldParser(opts.path))
  174. {
  175. parser.TextFieldType = FieldType.Delimited;
  176. parser.SetDelimiters(";");
  177. int current_row = 1; // In excel rows are 1-based.
  178. while (!parser.EndOfData)
  179. {
  180. string[] fields = parser.ReadFields();
  181. if (current_row++ < opts.start_row) continue;
  182.  
  183. string long_id = GetField(opts.id_column, ref fields);
  184. string price = GetField(opts.price_column, ref fields);
  185. string lang1 = GetField(opts.lang_1_column, ref fields);
  186. string lang2 = GetField(opts.lang_2_column, ref fields);
  187. if (long_id.Length == 0) continue;
  188.  
  189. Row row = new Row { price = price, lang1 = lang1, lang2 = lang2 };
  190.  
  191. //MessageBox.Show("id: '" + short_id + "' long_id: '" + long_id + "' price: '" + price + "' lang1: '" + lang1 + "' lang2: '" + lang2);
  192. data.Add(long_id, row);
  193.  
  194.  
  195. if (IsLongId(long_id))
  196. {
  197. string short_id = ShortId(long_id);
  198. if (!data.ContainsKey(short_id)) data.Add(short_id, row);
  199. }
  200. }
  201. }
  202. }
  203.  
  204. private string ShortId(string long_id)
  205. {
  206. return long_id.Split(new char[] { '-' })[0];
  207. }
  208.  
  209. private bool IsLongId(string long_id)
  210. {
  211. return long_id.Contains("-");
  212. }
  213.  
  214. public bool HasProduct(string id)
  215. {
  216. return data.ContainsKey(id) || (IsLongId(id) && data.ContainsKey(ShortId(id)));
  217. }
  218.  
  219. public string Price(string id)
  220. {
  221. if (!data.ContainsKey(id))
  222. {
  223. if (IsLongId(id)) return Price(ShortId(id));
  224. throw new System.ArgumentException("Bad id: " + id);
  225. }
  226. return data[id].price;
  227. }
  228.  
  229. public string Lang1(string id)
  230. {
  231. if (!data.ContainsKey(id))
  232. {
  233. if (IsLongId(id)) return Price(ShortId(id));
  234. throw new System.ArgumentException("Bad id: " + id);
  235. }
  236. return data[id].lang1;
  237. }
  238. public string Lang2(string id)
  239. {
  240. if (!data.ContainsKey(id))
  241. {
  242. if (IsLongId(id)) return Price(ShortId(id));
  243. throw new System.ArgumentException("Bad id: " + id);
  244. }
  245. return data[id].lang2;
  246. }
  247. }
  248.  
  249. public class Item
  250. {
  251. private corel.Shape code;
  252. private corel.Shape description;
  253. public string id { get; set; }
  254.  
  255. public Item(corel.Shape _code, corel.Shape _description)
  256. {
  257. code = _code;
  258. description = _description;
  259. id = code.Text.Contents;
  260.  
  261. //MessageBox.Show("" + description.Text.Contents.Count(f => f == '\r'));
  262. }
  263.  
  264. public void ModifyPrice(string price)
  265. {
  266. corel.TextRange paragraph = description.Text.Frame.Range.Paragraphs[4];
  267. paragraph.Text = "Cena: " + price + " PLN";
  268. corel.Color color = new corel.Color();
  269. color.CMYKAssign(0, 0, 0, 100);
  270. paragraph.Fill.ApplyUniformFill(color);
  271. }
  272.  
  273. public void HidePrice()
  274. {
  275. corel.TextRange paragraph = description.Text.Frame.Range.Paragraphs[4];
  276. paragraph.Fill.ApplyNoFill();
  277. }
  278.  
  279. public void ModifyLang1(string content)
  280. {
  281. corel.TextRange paragraph = description.Text.Frame.Range.Paragraphs[1];
  282. paragraph.Text = content + "\r\n";
  283. }
  284.  
  285. public void ModifyLang2(string content)
  286. {
  287. corel.TextRange paragraph = description.Text.Frame.Range.Paragraphs[2];
  288. paragraph.Text = content + "\r\n";
  289. }
  290.  
  291. public void AddAlert()
  292. {
  293. corel.Color color = new corel.Color();
  294. color.CMYKAssign(0, 100, 100, 0);
  295. foreach (corel.TextRange paragraph in code.Text.Frame.Range.Paragraphs)
  296. paragraph.Fill.ApplyUniformFill(color);
  297. foreach (corel.TextRange paragraph in description.Text.Frame.Range.Paragraphs)
  298. paragraph.Fill.ApplyUniformFill(color);
  299. }
  300. }
  301.  
  302. private void Startup()
  303. {
  304. }
  305. private void Traverse(corel.Shape parent, List<corel.Shape> shapes)
  306. {
  307. shapes.Add(parent);
  308. if (parent.PowerClip != null)
  309. {
  310. foreach (corel.Shape shape in parent.PowerClip.Shapes)
  311. {
  312. Traverse(shape, shapes);
  313. }
  314. }
  315. }
  316.  
  317. private List<corel.Shape> GetShapes(corel.Page page)
  318. {
  319. List<corel.Shape> shapes = new List<corel.Shape>();
  320. foreach (corel.Layer layer in page.Layers)
  321. {
  322. if (layer.IsGuidesLayer) continue;
  323. foreach (corel.Shape shape in layer.Shapes)
  324. {
  325. Traverse(shape, shapes);
  326. }
  327. }
  328. return shapes;
  329. }
  330.  
  331. private List<corel.Shape> GetShapes(corel.Document doc)
  332. {
  333. List<corel.Shape> shapes = new List<corel.Shape>();
  334. foreach (corel.Page page in doc.Pages)
  335. {
  336. shapes.AddRange(GetShapes(page));
  337. }
  338. return shapes;
  339. }
  340.  
  341. List<Item> GetItems(corel.Page page)
  342. {
  343. List<corel.Shape> shapes = GetShapes(page);
  344. List<corel.Shape> codes = new List<corel.Shape>();
  345. List<corel.Shape> descs = new List<corel.Shape>();
  346. foreach (corel.Shape shape in shapes)
  347. {
  348. if (shape.Type != corel.cdrShapeType.cdrTextShape) continue;
  349. if (Regex.Match(shape.Text.Contents, "^[A-Z]{1,2}[0-9]{3,5}(-[0-9]{1,2}/*[A-Z]{0,5})?$").Success)
  350. {
  351. codes.Add(shape);
  352. }
  353. else if (Regex.Match(shape.Text.Contents, "Cena:").Success)
  354. {
  355. descs.Add(shape);
  356. }
  357. }
  358. if (codes.Count != descs.Count)
  359. {
  360. //System.Windows.MessageBox.Show("Znaleziono inna ilosc pol tekstowych z numerem produktu, niz pol tekstowych z cena.");
  361. //string msg = "";
  362. //foreach (corel.Shape shape in codes) msg += shape.Text.Contents + "\n\n";
  363. //System.Windows.MessageBox.Show(msg);
  364. //msg = "";
  365. //foreach (corel.Shape shape in descs) msg += shape.Text.Contents + "\n\n";
  366. //System.Windows.MessageBox.Show(msg);
  367. throw new System.ArgumentException("Did not find correct number of textboxes");
  368. }
  369.  
  370. List<Item> items = new List<Item>();
  371. HashSet<int> used = new HashSet<int>();
  372. for (int c = 0; c < codes.Count; ++c)
  373. {
  374. int best = -1;
  375. double closest = 100000000;
  376. for (int d = 0; d < descs.Count; ++d)
  377. {
  378. if (used.Contains(d)) continue;
  379. // Manhattan distance between the text fields' bottom left and upper left corner.
  380. double dist = Math.Abs(codes[c].BoundingBox.Bottom - descs[d].BoundingBox.Top) + Math.Abs(codes[c].BoundingBox.Left - descs[d].BoundingBox.Left);
  381. if (dist < closest) { closest = dist; best = d; }
  382. }
  383. if (best == -1) throw new System.ArgumentException("Did not find best match for: " + codes[c].Text.Contents);
  384. used.Add(best);
  385. items.Add(new Item(codes[c], descs[best]));
  386. }
  387. return items;
  388. }
  389.  
  390. public void Process(Options opts, Action<double> progress_func)
  391. {
  392. Data data = new Data(opts);
  393.  
  394. HashSet<string> missing_data = new HashSet<string>();
  395.  
  396. HashSet<string> bad_pages = new HashSet<string>();
  397.  
  398. app.ActiveDocument.BeginCommandGroup();
  399. int processed_pages = 0;
  400. foreach (corel.Page page in app.ActiveDocument.Pages)
  401. {
  402. List<Item> items;
  403. try
  404. {
  405. items = GetItems(page);
  406. }
  407. catch
  408. {
  409. bad_pages.Add((processed_pages + 1).ToString());
  410. continue;
  411. }
  412.  
  413. foreach (Item item in items)
  414. {
  415. if (!data.HasProduct(item.id))
  416. {
  417. missing_data.Add(item.id + "(strona " + (processed_pages + 1) + ")");
  418. item.AddAlert();
  419. continue;
  420. }
  421. if (opts.price_column.Length != 0) item.ModifyPrice(data.Price(item.id));
  422. if (opts.lang_1_column.Length != 0) item.ModifyLang1(data.Lang1(item.id));
  423. if (opts.lang_2_column.Length != 0) item.ModifyLang2(data.Lang2(item.id));
  424. if (opts.hide_price) item.HidePrice();
  425. }
  426. processed_pages++;
  427. progress_func((double)(processed_pages) / app.ActiveDocument.Pages.Count);
  428. }
  429. app.ActiveDocument.EndCommandGroup();
  430.  
  431. if (missing_data.Count > 0)
  432. {
  433. System.Windows.MessageBox.Show("Brak danych w arkuszu dla produktow: " + String.Join(", ", missing_data));
  434. }
  435. if (bad_pages.Count > 0)
  436. {
  437. System.Windows.MessageBox.Show("Ilosc numerow produktow jest inna niz ilosc cen na stronach: " + String.Join(", ", bad_pages));
  438. }
  439.  
  440. if (bad_pages.Count == 0 && missing_data.Count == 0)
  441. {
  442. System.Windows.MessageBox.Show("OK!");
  443. }
  444. }
  445. }
  446. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement