Subversion Repositories Kolibri OS

Rev

Rev 9896 | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. (*
  2.     Copyright 2016, 2018, 2020-2023 Anton Krotov
  3.  
  4.     This file is part of fb2read.
  5.  
  6.     fb2read is free software: you can redistribute it and/or modify
  7.     it under the terms of the GNU General Public License as published by
  8.     the Free Software Foundation, either version 3 of the License, or
  9.     (at your option) any later version.
  10.  
  11.     fb2read is distributed in the hope that it will be useful,
  12.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14.     GNU General Public License for more details.
  15.  
  16.     You should have received a copy of the GNU General Public License
  17.     along with fb2read. If not, see <http://www.gnu.org/licenses/>.
  18. *)
  19.  
  20. MODULE SelEnc;
  21.  
  22. IMPORT
  23.     SU := SysUtils, W := Window, S := Strings, SYSTEM, K := KOSAPI, File;
  24.  
  25.  
  26. CONST
  27.         AUTO     =  15;
  28.         CP866    =  16;
  29.         CP1251   =  17;
  30.         CP1252   =  18;
  31.         CP1250   =  19;
  32.         UTF8     =  20;
  33.  
  34.     BtnH     =  30;
  35.     BtnW     = 150;
  36.     BtnX     =   5;
  37.     BtnY     =  10;
  38.     BtnInter =  10;
  39.  
  40.     tempfile* = "/tmp0/1/~temp.fb2";
  41.  
  42.  
  43. VAR
  44.     Window: W.tWindow;
  45.     pos, mem, mem2, pos2: INTEGER;
  46.  
  47.  
  48. PROCEDURE Buttons;
  49. VAR
  50.     Y : INTEGER;
  51. BEGIN
  52.     Y := BtnY;
  53.     SU.CreateButton(AUTO,   BtnX, Y, BtnW, BtnH, SU.btnColor, "AUTO"   ); INC(Y, BtnH + BtnInter);
  54.     SU.CreateButton(CP866,  BtnX, Y, BtnW, BtnH, SU.btnColor, "CP-866" ); INC(Y, BtnH + BtnInter);
  55.     SU.CreateButton(CP1251, BtnX, Y, BtnW, BtnH, SU.btnColor, "CP-1251"); INC(Y, BtnH + BtnInter);
  56.     SU.CreateButton(CP1252, BtnX, Y, BtnW, BtnH, SU.btnColor, "CP-1252"); INC(Y, BtnH + BtnInter);
  57.     SU.CreateButton(CP1250, BtnX, Y, BtnW, BtnH, SU.btnColor, "CP-1250"); INC(Y, BtnH + BtnInter);
  58.     SU.CreateButton(UTF8,   BtnX, Y, BtnW, BtnH, SU.btnColor, "UTF-8"  )
  59. END Buttons;
  60.  
  61.  
  62. PROCEDURE DrawWindow;
  63. BEGIN
  64.         SU.GetSystemColors;
  65.     SU.WindowRedrawStatus(1);
  66.     SU.DefineAndDrawWindow(Window.left, Window.top, Window.width, Window.height,
  67.           SU.winColor, LSL(ORD({0, 1}), 4) + 4, Window.caption);
  68.     Buttons;
  69.     SU.WindowRedrawStatus(2)
  70. END DrawWindow;
  71.  
  72.  
  73. PROCEDURE getch (): CHAR;
  74. VAR
  75.         ch: CHAR;
  76. BEGIN
  77.         SYSTEM.GET(mem + pos, ch);
  78.         INC(pos)
  79.         RETURN ch
  80. END getch;
  81.  
  82.  
  83. PROCEDURE WriteStr (s: ARRAY OF CHAR);
  84. BEGIN
  85.         SYSTEM.MOVE(SYSTEM.ADR(s[0]), mem2 + pos2, LENGTH(s));
  86.         pos2 := pos2 + LENGTH(s)
  87. END WriteStr;
  88.  
  89.  
  90. PROCEDURE WriteChar (ch: CHAR);
  91. BEGIN
  92.         SYSTEM.PUT(mem2 + pos2, ch);
  93.         INC(pos2)
  94. END WriteChar;
  95.  
  96.  
  97. PROCEDURE convert (ibuf, size: INTEGER; out: S.STRING; encoding: INTEGER);
  98. CONST
  99.         buf_size = 1024*16;
  100. VAR
  101.         F: File.FS;
  102.         n: INTEGER;
  103.         CR: BOOLEAN;
  104.         ch: CHAR;
  105.         buffer: ARRAY buf_size OF BYTE;
  106. BEGIN
  107.         mem := ibuf;
  108.         pos := 0;
  109.         F := File.Create(out);
  110.         mem2 := SYSTEM.ADR(buffer[0]);
  111.         pos2 := 0;
  112.         WriteStr('<?xml encoding = "');
  113.         CASE encoding OF
  114.         |CP866  : WriteStr("cp866")
  115.         |CP1251 : WriteStr("windows-1251")
  116.         |CP1252 : WriteStr("windows-1252")
  117.         |CP1250 : WriteStr("windows-1250")
  118.         |UTF8   : WriteStr("utf-8")
  119.         ELSE
  120.                 SU.Halt
  121.         END;
  122.         WriteStr('"?>' + 0DX + 0AX + "<FictionBook><body>");
  123.  
  124.         WHILE pos < size DO
  125.                 IF pos2 > buf_size - 32 THEN
  126.                         n := File.Write(F, mem2, pos2);
  127.                         pos2 := 0
  128.                 END;
  129.                 ch := getch();
  130.                 CASE ch OF
  131.                 |"<": WriteStr("&lt;")
  132.                 |">": WriteStr("&gt;")
  133.                 |"&": WriteStr("&amp;")
  134.                 |"'": WriteStr("&apos;")
  135.                 |'"': WriteStr("&quot;")
  136.                 |0DX: WriteStr("<empty-line/>")
  137.                 |0AX: IF ~CR THEN WriteStr("<empty-line/>") END
  138.                 | 0X: WriteChar(20X)
  139.                 ELSE
  140.                         WriteChar(ch)
  141.                 END;
  142.                 CR := ch = 0DX
  143.         END;
  144.  
  145.         WriteStr("</body></FictionBook>");
  146.         n := File.Write(F, mem2, pos2);
  147.         File.Close(F)
  148. END convert;
  149.  
  150.  
  151. PROCEDURE auto (ptr, size: INTEGER): INTEGER;
  152. VAR
  153.     enc: INTEGER;
  154.  
  155.  
  156.     PROCEDURE SearchPair (ptr, size: INTEGER; chr1, chr2: BYTE): BOOLEAN;
  157.     VAR
  158.         c, c0: BYTE;
  159.         res: BOOLEAN;
  160.  
  161.     BEGIN
  162.         c := 0;
  163.         res := FALSE;
  164.         WHILE (size > 0) & ~res DO
  165.             c0 := c;
  166.             SYSTEM.GET(ptr, c);
  167.             IF (c = chr2) & (c0 = chr1) THEN
  168.                 res := TRUE
  169.             END;
  170.             INC(ptr);
  171.             DEC(size)
  172.         END
  173.  
  174.         RETURN res
  175.     END SearchPair;
  176.  
  177.  
  178. BEGIN
  179.     IF SearchPair(ptr, size, 208, 190) THEN
  180.         enc := UTF8
  181.     ELSE
  182.         IF SearchPair(ptr, size, 239, 240) OR SearchPair(ptr, size, 241, 242) THEN
  183.             enc := CP1251
  184.         ELSE
  185.             enc := CP866
  186.         END
  187.     END
  188.     RETURN enc
  189. END auto;
  190.  
  191.  
  192. PROCEDURE ButtonClick (fname: S.STRING);
  193. VAR
  194.     encoding: INTEGER;
  195.     program, file: S.STRING;
  196.     data, size: INTEGER;
  197. BEGIN
  198.     data := File.Load(fname, size);
  199.     SU.ErrorIf(data = 0, 1);
  200.     encoding := SU.GetButtonCode();
  201.     IF encoding = AUTO THEN
  202.         encoding := auto(data, size)
  203.     END;
  204.     convert(data, size, tempfile, encoding);
  205.     S.PtrToString(K.GetName(), program);
  206.     file := tempfile;
  207.     file[0] := "!";
  208.     SU.Run(program, SYSTEM.ADR(file));
  209.     SU.Halt
  210. END ButtonClick;
  211.  
  212.  
  213. PROCEDURE Show* (fname: S.STRING);
  214. VAR
  215.     X1, Y1, X2, Y2: INTEGER;
  216. BEGIN
  217.     SU.SetEventsMask({0, 2, 31});
  218.     SU.GetScreenArea(X1, Y1, X2, Y2);
  219.     W.init(Window, 0, 0, BtnX * 2 + BtnW + 10, (BtnH + BtnInter) * 6 + BtnY * 2 + SU.SkinHeight() - 5, "Encoding");
  220.     Window.left := (X2 - X1 - Window.width) DIV 2;
  221.     Window.top  := (Y2 - Y1 - Window.height) DIV 2;
  222.     DrawWindow;
  223.     WHILE TRUE DO
  224.         CASE SU.WaitForEvent() OF
  225.         |1: DrawWindow
  226.         |3: ButtonClick(fname)
  227.         END
  228.     END
  229. END Show;
  230.  
  231.  
  232. END SelEnc.