WmfParser.cs 40 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using System.Threading.Tasks;
  6. namespace WMFConverter.Wmf
  7. {
  8. /// <summary>
  9. /// Windows Metafile - Parse WMF to SVG
  10. /// </summary>
  11. public class WmfParser
  12. {
  13. #region Constructors
  14. /// <summary>
  15. /// Default constructor.
  16. /// </summary>
  17. public WmfParser()
  18. {
  19. }
  20. #endregion
  21. #region Public Methods
  22. /// <summary>
  23. /// Parse WMF file to SVG file.
  24. /// </summary>
  25. /// <param name="stream"></param>
  26. /// <param name="gdi"></param>
  27. public void Parse(System.IO.Stream stream, Gdi.IGdi gdi)
  28. {
  29. WMFConverter.IO.DataInput binReader = null;
  30. bool isEmpty = true;
  31. try
  32. {
  33. binReader = new WMFConverter.IO.DataInput(stream, true);
  34. int mtType = 0;
  35. int mtHeaderSize = 0;
  36. long key = binReader.ReadUint32();
  37. isEmpty = false;
  38. if (key == -1698247209)//0x9AC6CDD7)
  39. {
  40. int hmf = binReader.ReadInt16();
  41. int vsx = binReader.ReadInt16();
  42. int vsy = binReader.ReadInt16();
  43. int vex = binReader.ReadInt16();
  44. int vey = binReader.ReadInt16();
  45. int dpi = binReader.ReadUint16();
  46. long reserved = binReader.ReadUint32();
  47. int checksum = binReader.ReadUint16();
  48. gdi.PlaceableHeader(vsx, vsy, vex, vey, dpi);
  49. mtType = binReader.ReadUint16();
  50. mtHeaderSize = binReader.ReadUint16();
  51. }
  52. else
  53. {
  54. mtType = (int)(key & 0x0000FFFF);
  55. mtHeaderSize = (int)((key & 0xFFFF0000) >> 16);
  56. }
  57. int mtVersion = binReader.ReadUint16();
  58. long mtSize = binReader.ReadUint32();
  59. int mtNoObjects = binReader.ReadUint16();
  60. long mtMaxRecord = binReader.ReadUint32();
  61. int mtNoParameters = binReader.ReadUint16();
  62. if (mtType != 1 || mtHeaderSize != 9)
  63. {
  64. throw new WmfParseException("invalid file format.");
  65. }
  66. gdi.Header();
  67. WMFConverter.Gdi.IGdiObject[] objs = new WMFConverter.Gdi.IGdiObject[mtNoObjects];
  68. while (true)
  69. {
  70. int size = (int)binReader.ReadUint32() - 3;
  71. int id = binReader.ReadUint16();
  72. if (id == (int)WmfConstants.RECORD_EOF)
  73. break; // Last record
  74. binReader.Count = 0;
  75. switch (id)
  76. {
  77. case (int)WmfConstants.RECORD_REALIZE_PALETTE:
  78. gdi.RealizePalette();
  79. break;
  80. case (int)WmfConstants.RECORD_SET_PALETTE_ENTRIES:
  81. {
  82. int[] entries = new int[binReader.ReadUint16()];
  83. int startIndex = binReader.ReadUint16();
  84. int objID = binReader.ReadUint16();
  85. for (int i = 0; i < entries.Length; i++)
  86. entries[i] = binReader.ReadInt32();
  87. gdi.SetPaletteEntries((Gdi.IGdiPalette)objs[objID], startIndex, entries);
  88. break;
  89. }
  90. case (int)WmfConstants.RECORD_SET_BK_MODE:
  91. {
  92. int mode = binReader.ReadInt16();
  93. gdi.SetBkMode(mode);
  94. break;
  95. }
  96. case (int)WmfConstants.RECORD_SET_MAP_MODE:
  97. {
  98. int mode = binReader.ReadInt16();
  99. gdi.SetMapMode(mode);
  100. break;
  101. }
  102. case (int)WmfConstants.RECORD_SET_ROP2:
  103. {
  104. int mode = binReader.ReadInt16();
  105. gdi.SetROP2(mode);
  106. break;
  107. }
  108. case (int)WmfConstants.RECORD_SET_REL_ABS:
  109. {
  110. int mode = binReader.ReadInt16();
  111. gdi.SetRelAbs(mode);
  112. break;
  113. }
  114. case (int)WmfConstants.RECORD_SET_POLY_FILL_MODE:
  115. {
  116. int mode = binReader.ReadInt16();
  117. gdi.SetPolyFillMode(mode);
  118. break;
  119. }
  120. case (int)WmfConstants.RECORD_SET_STRETCH_BLT_MODE:
  121. {
  122. int mode = binReader.ReadInt16();
  123. gdi.SetStretchBltMode(mode);
  124. break;
  125. }
  126. case (int)WmfConstants.RECORD_SET_TEXT_CHARACTER_EXTRA:
  127. {
  128. int extra = binReader.ReadInt16();
  129. gdi.SetTextCharacterExtra(extra);
  130. break;
  131. }
  132. case (int)WmfConstants.RECORD_RESTORE_DC:
  133. {
  134. int dc = binReader.ReadInt16();
  135. gdi.RestoreDC(dc);
  136. break;
  137. }
  138. case (int)WmfConstants.RECORD_RESIZE_PALETTE:
  139. {
  140. int objID = binReader.ReadUint16();
  141. gdi.ResizePalette((Gdi.IGdiPalette)objs[objID]);
  142. break;
  143. }
  144. case (int)WmfConstants.RECORD_DIB_CREATE_PATTERN_BRUSH:
  145. {
  146. int usage = binReader.ReadInt32();
  147. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  148. for (int i = 0; i < objs.Length; i++)
  149. {
  150. if (objs[i] == null)
  151. {
  152. objs[i] = gdi.DibCreatePatternBrush(image, usage);
  153. break;
  154. }
  155. }
  156. break;
  157. }
  158. case (int)WmfConstants.RECORD_SET_LAYOUT:
  159. {
  160. long layout = binReader.ReadUint32();
  161. gdi.SetLayout(layout);
  162. break;
  163. }
  164. case (int)WmfConstants.RECORD_SET_BK_COLOR:
  165. {
  166. int color = binReader.ReadInt32();
  167. gdi.SetBkColor(color);
  168. break;
  169. }
  170. case (int)WmfConstants.RECORD_SET_TEXT_COLOR:
  171. {
  172. int color = binReader.ReadInt32();
  173. gdi.SetTextColor(color);
  174. break;
  175. }
  176. case (int)WmfConstants.RECORD_OFFSET_VIEWPORT_ORG_EX:
  177. {
  178. int y = binReader.ReadInt16();
  179. int x = binReader.ReadInt16();
  180. gdi.OffsetViewportOrgEx(x, y, null);
  181. break;
  182. }
  183. case (int)WmfConstants.RECORD_LINE_TO:
  184. {
  185. int ey = binReader.ReadInt16();
  186. int ex = binReader.ReadInt16();
  187. gdi.LineTo(ex, ey);
  188. break;
  189. }
  190. case (int)WmfConstants.RECORD_MOVE_TO_EX:
  191. {
  192. int y = binReader.ReadInt16();
  193. int x = binReader.ReadInt16();
  194. gdi.MoveToEx(x, y, null);
  195. break;
  196. }
  197. case (int)WmfConstants.RECORD_OFFSET_CLIP_RGN:
  198. {
  199. int y = binReader.ReadInt16();
  200. int x = binReader.ReadInt16();
  201. gdi.OffsetClipRgn(x, y);
  202. break;
  203. }
  204. case (int)WmfConstants.RECORD_FILL_RGN:
  205. {
  206. int brushID = binReader.ReadUint16();
  207. int rgnID = binReader.ReadUint16();
  208. gdi.FillRgn((Gdi.IGdiRegion)objs[rgnID], (Gdi.IGdiBrush)objs[brushID]);
  209. break;
  210. }
  211. case (int)WmfConstants.RECORD_SET_MAPPER_FLAGS:
  212. {
  213. long flag = binReader.ReadUint32();
  214. gdi.SetMapperFlags(flag);
  215. break;
  216. }
  217. case (int)WmfConstants.RECORD_SELECT_PALETTE:
  218. {
  219. bool mode = (binReader.ReadInt16() != 0);
  220. if ((size * 2 - binReader.Count) > 0)
  221. {
  222. int objID = binReader.ReadUint16();
  223. gdi.SelectPalette((Gdi.IGdiPalette)objs[objID], mode);
  224. }
  225. break;
  226. }
  227. case (int)WmfConstants.RECORD_POLYGON:
  228. {
  229. WMFConverter.Gdi.Point[] points = new WMFConverter.Gdi.Point[binReader.ReadInt16()];
  230. for (int i = 0; i < points.Length; i++)
  231. points[i] = new WMFConverter.Gdi.Point(binReader.ReadInt16(), binReader.ReadInt16());
  232. gdi.Polygon(points);
  233. break;
  234. }
  235. case (int)WmfConstants.RECORD_POLYLINE:
  236. {
  237. WMFConverter.Gdi.Point[] points = new WMFConverter.Gdi.Point[binReader.ReadInt16()];
  238. for (int i = 0; i < points.Length; i++)
  239. points[i] = new WMFConverter.Gdi.Point(binReader.ReadInt16(), binReader.ReadInt16());
  240. gdi.Polyline(points);
  241. break;
  242. }
  243. case (int)WmfConstants.RECORD_SET_TEXT_JUSTIFICATION:
  244. {
  245. int breakCount = binReader.ReadInt16();
  246. int breakExtra = binReader.ReadInt16();
  247. gdi.SetTextJustification(breakExtra, breakCount);
  248. break;
  249. }
  250. case (int)WmfConstants.RECORD_SET_WINDOW_ORG_EX:
  251. {
  252. int y = binReader.ReadInt16();
  253. int x = binReader.ReadInt16();
  254. gdi.SetWindowOrgEx(x, y, null);
  255. break;
  256. }
  257. case (int)WmfConstants.RECORD_SET_WINDOW_EXT_EX:
  258. {
  259. int height = binReader.ReadInt16();
  260. int width = binReader.ReadInt16();
  261. gdi.SetWindowExtEx(width, height, null);
  262. break;
  263. }
  264. case (int)WmfConstants.RECORD_SET_VIEWPORT_ORG_EX:
  265. {
  266. int y = binReader.ReadInt16();
  267. int x = binReader.ReadInt16();
  268. gdi.SetViewportOrgEx(x, y, null);
  269. break;
  270. }
  271. case (int)WmfConstants.RECORD_SET_VIEWPORT_EXT_EX:
  272. {
  273. int y = binReader.ReadInt16();
  274. int x = binReader.ReadInt16();
  275. gdi.SetViewportExtEx(x, y, null);
  276. break;
  277. }
  278. case (int)WmfConstants.RECORD_OFFSET_WINDOW_ORG_EX:
  279. {
  280. int y = binReader.ReadInt16();
  281. int x = binReader.ReadInt16();
  282. gdi.OffsetWindowOrgEx(x, y, null);
  283. break;
  284. }
  285. case (int)WmfConstants.RECORD_SCALE_WINDOW_EXT_EX:
  286. {
  287. int yd = binReader.ReadInt16();
  288. int y = binReader.ReadInt16();
  289. int xd = binReader.ReadInt16();
  290. int x = binReader.ReadInt16();
  291. gdi.ScaleWindowExtEx(x, xd, y, yd, null);
  292. break;
  293. }
  294. case (int)WmfConstants.RECORD_SCALE_VIEWPORT_EXT_EX:
  295. {
  296. int yd = binReader.ReadInt16();
  297. int y = binReader.ReadInt16();
  298. int xd = binReader.ReadInt16();
  299. int x = binReader.ReadInt16();
  300. gdi.ScaleViewportExtEx(x, xd, y, yd, null);
  301. break;
  302. }
  303. case (int)WmfConstants.RECORD_EXCLUDE_CLIP_RECT:
  304. {
  305. int ey = binReader.ReadInt16();
  306. int ex = binReader.ReadInt16();
  307. int sy = binReader.ReadInt16();
  308. int sx = binReader.ReadInt16();
  309. gdi.ExcludeClipRect(sx, sy, ex, ey);
  310. break;
  311. }
  312. case (int)WmfConstants.RECORD_INTERSECT_CLIP_RECT:
  313. {
  314. int ey = binReader.ReadInt16();
  315. int ex = binReader.ReadInt16();
  316. int sy = binReader.ReadInt16();
  317. int sx = binReader.ReadInt16();
  318. gdi.IntersectClipRect(sx, sy, ex, ey);
  319. break;
  320. }
  321. case (int)WmfConstants.RECORD_ELLIPSE:
  322. {
  323. int ey = binReader.ReadInt16();
  324. int ex = binReader.ReadInt16();
  325. int sy = binReader.ReadInt16();
  326. int sx = binReader.ReadInt16();
  327. gdi.Ellipse(sx, sy, ex, ey);
  328. break;
  329. }
  330. case (int)WmfConstants.RECORD_FLOOD_FILL:
  331. {
  332. int color = binReader.ReadInt32();
  333. int y = binReader.ReadInt16();
  334. int x = binReader.ReadInt16();
  335. gdi.FloodFill(x, y, color);
  336. break;
  337. }
  338. case (int)WmfConstants.RECORD_FRAME_RGN:
  339. {
  340. int height = binReader.ReadInt16();
  341. int width = binReader.ReadInt16();
  342. int brushID = binReader.ReadUint16();
  343. int rgnID = binReader.ReadUint16();
  344. gdi.FrameRgn((Gdi.IGdiRegion)objs[rgnID], (Gdi.IGdiBrush)objs[brushID], width, height);
  345. break;
  346. }
  347. case (int)WmfConstants.RECORD_ANIMATE_PALETTE:
  348. {
  349. int[] entries = new int[binReader.ReadUint16()];
  350. int startIndex = binReader.ReadUint16();
  351. int objID = binReader.ReadUint16();
  352. for (int i = 0; i < entries.Length; i++)
  353. entries[i] = binReader.ReadInt32();
  354. gdi.AnimatePalette((Gdi.IGdiPalette)objs[objID], startIndex, entries);
  355. break;
  356. }
  357. case (int)WmfConstants.RECORD_TEXT_OUT:
  358. {
  359. int count = binReader.ReadInt16();
  360. byte[] text = binReader.ReadBytes(count);
  361. if (count % 2 == 1)
  362. {
  363. binReader.ReadByte();
  364. }
  365. int y = binReader.ReadInt16();
  366. int x = binReader.ReadInt16();
  367. gdi.TextOut(x, y, text);
  368. break;
  369. }
  370. case (int)WmfConstants.RECORD_POLY_POLYGON:
  371. {
  372. WMFConverter.Gdi.Point[][] points = new WMFConverter.Gdi.Point[binReader.ReadInt16()][];
  373. for (int i = 0; i < points.Length; i++)
  374. points[i] = new WMFConverter.Gdi.Point[binReader.ReadInt16()];
  375. for (int i = 0; i < points.Length; i++)
  376. for (int j = 0; j < points[i].Length; j++)
  377. points[i][j] = new WMFConverter.Gdi.Point(binReader.ReadInt16(), binReader.ReadInt16());
  378. gdi.PolyPolygon(points);
  379. break;
  380. }
  381. case (int)WmfConstants.RECORD_EXT_FLOOD_FILL:
  382. {
  383. int type = binReader.ReadUint16();
  384. int color = binReader.ReadInt32();
  385. int y = binReader.ReadInt16();
  386. int x = binReader.ReadInt16();
  387. gdi.ExtFloodFill(x, y, color, type);
  388. break;
  389. }
  390. case (int)WmfConstants.RECORD_RECTANGLE:
  391. {
  392. int ey = binReader.ReadInt16();
  393. int ex = binReader.ReadInt16();
  394. int sy = binReader.ReadInt16();
  395. int sx = binReader.ReadInt16();
  396. gdi.Rectangle(sx, sy, ex, ey);
  397. break;
  398. }
  399. case (int)WmfConstants.RECORD_SET_PIXEL:
  400. {
  401. int color = binReader.ReadInt32();
  402. int y = binReader.ReadInt16();
  403. int x = binReader.ReadInt16();
  404. gdi.SetPixel(x, y, color);
  405. break;
  406. }
  407. case (int)WmfConstants.RECORD_ROUND_RECT:
  408. {
  409. int rh = binReader.ReadInt16();
  410. int rw = binReader.ReadInt16();
  411. int ey = binReader.ReadInt16();
  412. int ex = binReader.ReadInt16();
  413. int sy = binReader.ReadInt16();
  414. int sx = binReader.ReadInt16();
  415. gdi.RoundRect(sx, sy, ex, ey, rw, rh);
  416. break;
  417. }
  418. case (int)WmfConstants.RECORD_PAT_BLT:
  419. {
  420. long rop = binReader.ReadUint32();
  421. int height = binReader.ReadInt16();
  422. int width = binReader.ReadInt16();
  423. int y = binReader.ReadInt16();
  424. int x = binReader.ReadInt16();
  425. gdi.PatBlt(x, y, width, height, rop);
  426. break;
  427. }
  428. case (int)WmfConstants.RECORD_SAVE_DC:
  429. {
  430. gdi.SeveDC();
  431. break;
  432. }
  433. case (int)WmfConstants.RECORD_PIE:
  434. {
  435. int eyr = binReader.ReadInt16();
  436. int exr = binReader.ReadInt16();
  437. int syr = binReader.ReadInt16();
  438. int sxr = binReader.ReadInt16();
  439. int ey = binReader.ReadInt16();
  440. int ex = binReader.ReadInt16();
  441. int sy = binReader.ReadInt16();
  442. int sx = binReader.ReadInt16();
  443. gdi.Pie(sx, sy, ex, ey, sxr, syr, exr, eyr);
  444. break;
  445. }
  446. case (int)WmfConstants.RECORD_STRETCH_BLT:
  447. {
  448. long rop = binReader.ReadUint32();
  449. int sh = binReader.ReadInt16();
  450. int sw = binReader.ReadInt16();
  451. int sy = binReader.ReadInt16();
  452. int sx = binReader.ReadInt16();
  453. int dh = binReader.ReadInt16();
  454. int dw = binReader.ReadInt16();
  455. int dy = binReader.ReadInt16();
  456. int dx = binReader.ReadInt16();
  457. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  458. gdi.StretchBlt(image, dx, dy, dw, dh, sx, sy, sw, sh, rop);
  459. break;
  460. }
  461. case (int)WmfConstants.RECORD_ESCAPE:
  462. {
  463. byte[] data = binReader.ReadBytes(2 * size);
  464. gdi.Escape(data);
  465. break;
  466. }
  467. case (int)WmfConstants.RECORD_INVERT_RGN:
  468. {
  469. int rgnID = binReader.ReadUint16();
  470. gdi.InvertRgn((Gdi.IGdiRegion)objs[rgnID]);
  471. break;
  472. }
  473. case (int)WmfConstants.RECORD_PAINT_RGN:
  474. {
  475. int objID = binReader.ReadUint16();
  476. gdi.PaintRgn((Gdi.IGdiRegion)objs[objID]);
  477. break;
  478. }
  479. case (int)WmfConstants.RECORD_SELECT_CLIP_RGN:
  480. {
  481. int objID = binReader.ReadUint16();
  482. Gdi.IGdiRegion rgn = (objID > 0) ? (Gdi.IGdiRegion)objs[objID] : null;
  483. gdi.SelectClipRgn(rgn);
  484. break;
  485. }
  486. case (int)WmfConstants.RECORD_SELECT_OBJECT:
  487. {
  488. int objID = binReader.ReadUint16();
  489. gdi.SelectObject(objs[objID]);
  490. break;
  491. }
  492. case (int)WmfConstants.RECORD_SET_TEXT_ALIGN:
  493. {
  494. int align = binReader.ReadInt16();
  495. gdi.SetTextAlign(align);
  496. break;
  497. }
  498. case (int)WmfConstants.RECORD_ARC:
  499. {
  500. int eya = binReader.ReadInt16();
  501. int exa = binReader.ReadInt16();
  502. int sya = binReader.ReadInt16();
  503. int sxa = binReader.ReadInt16();
  504. int eyr = binReader.ReadInt16();
  505. int exr = binReader.ReadInt16();
  506. int syr = binReader.ReadInt16();
  507. int sxr = binReader.ReadInt16();
  508. gdi.Arc(sxr, syr, exr, eyr, sxa, sya, exa, eya);
  509. break;
  510. }
  511. case (int)WmfConstants.RECORD_CHORD:
  512. {
  513. int eya = binReader.ReadInt16();
  514. int exa = binReader.ReadInt16();
  515. int sya = binReader.ReadInt16();
  516. int sxa = binReader.ReadInt16();
  517. int eyr = binReader.ReadInt16();
  518. int exr = binReader.ReadInt16();
  519. int syr = binReader.ReadInt16();
  520. int sxr = binReader.ReadInt16();
  521. gdi.Chord(sxr, syr, exr, eyr, sxa, sya, exa, eya);
  522. break;
  523. }
  524. case (int)WmfConstants.RECORD_BIT_BLT:
  525. {
  526. long rop = binReader.ReadUint32();
  527. int sy = binReader.ReadInt16();
  528. int sx = binReader.ReadInt16();
  529. int height = binReader.ReadInt16();
  530. int width = binReader.ReadInt16();
  531. int dy = binReader.ReadInt16();
  532. int dx = binReader.ReadInt16();
  533. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  534. gdi.BitBlt(image, dx, dy, width, height, sx, sy, rop);
  535. break;
  536. }
  537. case (int)WmfConstants.RECORD_EXT_TEXT_OUT:
  538. {
  539. int rsize = size;
  540. int y = binReader.ReadInt16();
  541. int x = binReader.ReadInt16();
  542. int count = binReader.ReadInt16();
  543. int options = binReader.ReadUint16();
  544. rsize -= 4;
  545. int[] rect = null;
  546. if ((options & 0x0006) > 0)
  547. {
  548. rect = new int[] { binReader.ReadInt16(), binReader.ReadInt16(), binReader.ReadInt16(), binReader.ReadInt16() };
  549. rsize -= 4;
  550. }
  551. byte[] text = binReader.ReadBytes(count);
  552. if (count % 2 == 1)
  553. binReader.ReadByte();
  554. rsize -= (count + 1) / 2;
  555. int[] dx = null;
  556. if (rsize > 0)
  557. {
  558. dx = new int[rsize];
  559. for (int i = 0; i < dx.Length; i++)
  560. dx[i] = binReader.ReadInt16();
  561. }
  562. gdi.ExtTextOut(x, y, options, rect, text, dx);
  563. break;
  564. }
  565. case (int)WmfConstants.RECORD_SET_DIBITS_TO_DEVICE:
  566. {
  567. int colorUse = binReader.ReadUint16();
  568. int scanlines = binReader.ReadUint16();
  569. int startscan = binReader.ReadUint16();
  570. int sy = binReader.ReadInt16();
  571. int sx = binReader.ReadInt16();
  572. int dh = binReader.ReadInt16();
  573. int dw = binReader.ReadInt16();
  574. int dy = binReader.ReadInt16();
  575. int dx = binReader.ReadInt16();
  576. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  577. gdi.SetDIBitsToDevice(dx, dy, dw, dh, sx, sy, startscan, scanlines, image, colorUse);
  578. break;
  579. }
  580. case (int)WmfConstants.RECORD_DIB_BIT_BLT:
  581. {
  582. bool isRop = false;
  583. long rop = binReader.ReadUint32();
  584. int sy = binReader.ReadInt16();
  585. int sx = binReader.ReadInt16();
  586. int height = binReader.ReadInt16();
  587. if (height == 0)
  588. {
  589. height = binReader.ReadInt16();
  590. isRop = true;
  591. }
  592. int width = binReader.ReadInt16();
  593. int dy = binReader.ReadInt16();
  594. int dx = binReader.ReadInt16();
  595. if (isRop)
  596. gdi.DibBitBlt(null, dx, dy, width, height, sx, sy, rop);
  597. else
  598. {
  599. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  600. gdi.DibBitBlt(image, dx, dy, width, height, sx, sy, rop);
  601. }
  602. break;
  603. }
  604. case (int)WmfConstants.RECORD_DIB_STRETCH_BLT:
  605. {
  606. long rop = binReader.ReadUint32();
  607. int sh = binReader.ReadInt16();
  608. int sw = binReader.ReadInt16();
  609. int sx = binReader.ReadInt16();
  610. int sy = binReader.ReadInt16();
  611. int dh = binReader.ReadInt16();
  612. int dw = binReader.ReadInt16();
  613. int dy = binReader.ReadInt16();
  614. int dx = binReader.ReadInt16();
  615. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  616. gdi.DibStretchBlt(image, dx, dy, dw, dh, sx, sy, sw, sh, rop);
  617. break;
  618. }
  619. case (int)WmfConstants.RECORD_STRETCH_DIBITS:
  620. {
  621. long rop = binReader.ReadUint32();
  622. int usage = binReader.ReadUint16();
  623. int sh = binReader.ReadInt16();
  624. int sw = binReader.ReadInt16();
  625. int sy = binReader.ReadInt16();
  626. int sx = binReader.ReadInt16();
  627. int dh = binReader.ReadInt16();
  628. int dw = binReader.ReadInt16();
  629. int dy = binReader.ReadInt16();
  630. int dx = binReader.ReadInt16();
  631. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  632. gdi.StretchDIBits(dx, dy, dw, dh, sx, sy, sw, sh, image, usage, rop);
  633. break;
  634. }
  635. case (int)WmfConstants.RECORD_DELETE_OBJECT:
  636. {
  637. int objID = binReader.ReadUint16();
  638. gdi.DeleteObject(objs[objID]);
  639. objs[objID] = null;
  640. break;
  641. }
  642. case (int)WmfConstants.RECORD_CREATE_PALETTE:
  643. {
  644. int version = binReader.ReadUint16();
  645. int[] entries = new int[binReader.ReadUint16()];
  646. for (int i = 0; i < entries.Length; i++)
  647. entries[i] = binReader.ReadInt32();
  648. for (int i = 0; i < objs.Length; i++)
  649. {
  650. if (objs[i] == null)
  651. {
  652. objs[i] = gdi.CreatePalette(version, entries);
  653. break;
  654. }
  655. }
  656. break;
  657. }
  658. case (int)WmfConstants.RECORD_CREATE_PATTERN_BRUSH:
  659. {
  660. byte[] image = binReader.ReadBytes(size * 2 - binReader.Count);
  661. for (int i = 0; i < objs.Length; i++)
  662. {
  663. if (objs[i] == null)
  664. {
  665. objs[i] = gdi.CreatePatternBrush(image);
  666. break;
  667. }
  668. }
  669. break;
  670. }
  671. case (int)WmfConstants.RECORD_CREATE_PEN_INDIRECT:
  672. {
  673. int style = binReader.ReadUint16();
  674. int width = binReader.ReadInt16();
  675. binReader.ReadInt16();
  676. int color = binReader.ReadInt32();
  677. for (int i = 0; i < objs.Length; i++)
  678. {
  679. if (objs[i] == null)
  680. {
  681. objs[i] = gdi.CreatePenIndirect(style, width, color);
  682. break;
  683. }
  684. }
  685. break;
  686. }
  687. case (int)WmfConstants.RECORD_CREATE_FONT_INDIRECT:
  688. {
  689. int height = binReader.ReadInt16();
  690. int width = binReader.ReadInt16();
  691. int escapement = binReader.ReadInt16();
  692. int orientation = binReader.ReadInt16();
  693. int weight = binReader.ReadInt16();
  694. bool italic = (binReader.ReadByte() == 1);
  695. bool underline = (binReader.ReadByte() == 1);
  696. bool strikeout = (binReader.ReadByte() == 1);
  697. int charset = binReader.ReadByte();
  698. int outPrecision = binReader.ReadByte();
  699. int clipPrecision = binReader.ReadByte();
  700. int quality = binReader.ReadByte();
  701. int pitchAndFamily = binReader.ReadByte();
  702. byte[] faceName = binReader.ReadBytes(size * 2 - binReader.Count);
  703. Gdi.IGdiObject obj = gdi.CreateFontIndirect(height, width, escapement, orientation, weight, italic,
  704. underline, strikeout, charset, outPrecision, clipPrecision, quality, pitchAndFamily,
  705. faceName);
  706. for (int i = 0; i < objs.Length; i++)
  707. {
  708. if (objs[i] == null)
  709. {
  710. objs[i] = obj;
  711. break;
  712. }
  713. }
  714. break;
  715. }
  716. case (int)WmfConstants.RECORD_CREATE_BRUSH_INDIRECT:
  717. {
  718. int style = binReader.ReadUint16();
  719. int color = binReader.ReadInt32();
  720. int hatch = binReader.ReadUint16();
  721. for (int i = 0; i < objs.Length; i++)
  722. {
  723. if (objs[i] == null)
  724. {
  725. objs[i] = gdi.CreateBrushIndirect(style, color, hatch);
  726. break;
  727. }
  728. }
  729. break;
  730. }
  731. case (int)WmfConstants.RECORD_CREATE_RECT_RGN:
  732. {
  733. int ey = binReader.ReadInt16();
  734. int ex = binReader.ReadInt16();
  735. int sy = binReader.ReadInt16();
  736. int sx = binReader.ReadInt16();
  737. for (int i = 0; i < objs.Length; i++)
  738. {
  739. if (objs[i] == null)
  740. {
  741. objs[i] = gdi.CreateRectRgn(sx, sy, ex, ey);
  742. break;
  743. }
  744. }
  745. break;
  746. }
  747. default:
  748. {
  749. //log.fine("unsuppored id find: " + id + " (size=" + size + ")");
  750. Console.Write("unsuppored id find:" + id + "(size=" + size + ")");
  751. break;
  752. }
  753. }
  754. int rest = size * 2 - binReader.Count;
  755. for (int i = 0; i < rest; i++)
  756. {
  757. binReader.ReadByte();
  758. }
  759. }
  760. binReader.Close();
  761. gdi.Footer();
  762. }
  763. catch (Exception)
  764. {
  765. if (isEmpty)
  766. throw new WmfParseException("input file size is zero.");
  767. }
  768. }
  769. #endregion
  770. }
  771. }