Ir al contenido


Foto

Convertir de .doc a .pdf


  • Por favor identifícate para responder
22 respuestas en este tema

#1 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 21 mayo 2014 - 05:22

Bueno, el título es autoexplicativo.
¿Cómo hago para convertir un .doc que tengo en un directorio a un .pdf?
Lo quiero de manera nativa, los clientes no quieren usar pdfcreator o parecidos.
¿Algún código que resuelva el problema?

Gracias.
______________
  • 0

#2 egostar

egostar

    missing my father, I love my mother.

  • Administrador
  • 14.448 mensajes
  • LocationMéxico

Escrito 21 mayo 2014 - 07:37

A reserva de que alguien por aquí haya tenido que desarrollar algo para ello, hay componentes que lo hacen, y sí, ya lo habrás intuido, es de pago :)

Ahí mismo verás componentes para delphi

Saludos
  • 0

#3 Caral

Caral

    Advanced Member

  • Moderador
  • PipPipPip
  • 4.266 mensajes
  • LocationCosta Rica

Escrito 21 mayo 2014 - 07:50

Hola
Esto:



delphi
  1. uses
  2.   OleAuto;
  3. const
  4.   wdExportFormatPDF = 17;
  5. var
  6.   Word, Doc: OleVariant;
  7. begin
  8.   Word := CreateOLEObject('Word.Application');
  9.   Doc := Word.Documents.Open('C:\Document.docx');
  10.   Doc.ExportAsFixedFormat('C:\Document.pdf', wdExportFormatPDF);
  11. end;



Lo vi aqui: http://stackoverflow...ng-word-activex
Saludos
PD: Etiquetas delphi  *-)
  • 0

#4 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 05:53

Hola
Esto:



delphi
  1. uses
  2.   OleAuto;
  3. const
  4.   wdExportFormatPDF = 17;
  5. var
  6.   Word, Doc: OleVariant;
  7. begin
  8.   Word := CreateOLEObject('Word.Application');
  9.   Doc := Word.Documents.Open('C:\Document.docx');
  10.   Doc.ExportAsFixedFormat('C:\Document.pdf', wdExportFormatPDF);
  11. end;



Lo vi aqui: http://stackoverflow...ng-word-activex
Saludos
PD: Etiquetas delphi  *-)


He probado con esta opción y me sale el siguiente error:

"La exportación produjo un error porque esta característica no está instalada"

Lo he probado en W8, 64bits, D7.
También lo he hecho en WXP, 32bits, D7.

En ambos casos me dió el mismo error.
El archivo que usé era .doc y no .docx

¿Cómo arreglo el dilema? La verdad es que está buena la forma de exportación. Tengo instalado Office 2007 en W8 y Office 2003 en WXP.
  • 0

#5 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 05:56

Con un archivo .docx me muestra el mismo error.


  • 0

#6 egostar

egostar

    missing my father, I love my mother.

  • Administrador
  • 14.448 mensajes
  • LocationMéxico

Escrito 22 mayo 2014 - 08:13

Hola

Y no será que intentas crearlos en la raíz de "C", ¿ porque no lo agregas en un directorio personal ? Yo usé el disco "F" de mi máquina y funciona sin problemas.

Saludos
  • 0

#7 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 08:17

Resulta que para que el código funcione bien hay que tener algunas cosas en cuenta:

1) Tener instalada alguna versiónd de Office. En mi caso, tengo Office 2007.
2) Esa instalación debe tener el complemento que le permite a Word salvar archivos como pdf. Eso se consigue en la página de Microsoft.

Con estas dos cositas en su lugar, todo va bien.
Ahora si hace la exportación como lo queremos.

Gracias.
  • 0

#8 Sergio

Sergio

    Advanced Member

  • Moderadores
  • PipPipPip
  • 1.092 mensajes
  • LocationMurcia, España

Escrito 22 mayo 2014 - 09:47

Otra pción es tener instalado OpenOffice o LibreOffice, ambos tienen filtros para exportar a PDF de fábrica, aunque el resultado es el mismo que con MS-Office.

Por cierto, creo que este sistema solo funciona a partir de Office 2007, los anteriores creo que no tenían este filtro de exportación, o al menos no de fábrica leí por algún sitio.
  • 0

#9 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 10:16

Es verdad, hay que instalar el complemento por aparte.

Santiago.
  • 0

#10 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 10:17

Otra pción es tener instalado OpenOffice o LibreOffice, ambos tienen filtros para exportar a PDF de fábrica, aunque el resultado es el mismo que con MS-Office.


Esto es bueno saberlo, no todos quieren comprar una licencia de Office solamente para poder hacer una exportación desde Delphi de sus archivos .doc o .docx
  • 0

#11 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 10:20

Otra pción es tener instalado OpenOffice o LibreOffice, ambos tienen filtros para exportar a PDF de fábrica, aunque el resultado es el mismo que con MS-Office.


¿Cómo hago para llamar al "Word" (Creo que es Write) de LibreOffice?
Para llamar a Word se hace:


delphi
  1. Word := CreateOLEObject('Word.Application');



Gracias.
  • 0

#12 Sergio

Sergio

    Advanced Member

  • Moderadores
  • PipPipPip
  • 1.092 mensajes
  • LocationMurcia, España

Escrito 22 mayo 2014 - 11:20

Mira el código "dual" para manejar word o write que puse aquí: http://www.delphiacc...84036/#msg84036

Creo que no incluye el código para exportar a PDF, pero bueno, si acaso eso lo tengo en otra unit que maneja hojas de cálculo: https://github.com/s...hi-SpreadSheets

En ese código tienes la forma de exportar el documento actual de libreoffice a PDF, la funcion en write debería ser idéntica a esta de Calc.
  • 0

#13 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 04:43

Tal vez Uds. sepan que es esto:
En mi máquina pude exportar bien. Pero en otra PC, WXP, D7 salió el siguiente error:

Method 'ExportAsFixedFormat' not supported by automation object.


P/D: Voy a analizar bien lo que mandaste Sergio, la verdad es que está bien interesante.

Santiago.
  • 0

#14 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 22 mayo 2014 - 05:05

Mira el código "dual" para manejar word o write que puse aquí: http://www.delphiacc...84036/#msg84036

Creo que no incluye el código para exportar a PDF, pero bueno, si acaso eso lo tengo en otra unit que maneja hojas de cálculo: https://github.com/s...hi-SpreadSheets

En ese código tienes la forma de exportar el documento actual de libreoffice a PDF, la funcion en write debería ser idéntica a esta de Calc.


Sergio, estoy intentando compilar la unit uDocumentoTexto que pasaste en uno de los links pero me dice que no puede ubicar a la unit: "Launch"
¿Dónde la consigo?

Santiago.
  • 0

#15 Sergio

Sergio

    Advanced Member

  • Moderadores
  • PipPipPip
  • 1.092 mensajes
  • LocationMurcia, España

Escrito 23 mayo 2014 - 02:26

Tal vez Uds. sepan que es esto:
En mi máquina pude exportar bien. Pero en otra PC, WXP, D7 salió el siguiente error:

Method 'ExportAsFixedFormat' not supported by automation object.


P/D: Voy a analizar bien lo que mandaste Sergio, la verdad es que está bien interesante.

Santiago.


La version de Excel creo que va a ser, la función está a partir de Excel2007 (confirmado en msn).
  • 0

#16 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 23 mayo 2014 - 02:59

Sergio, cuando quiero compilar me indica que no tengo la unit "Launch". ¿Dónde la consigo?
Pongo el código de la clase que indicas:


delphi
  1. // *********************************************
  2. // ** Object for dual WordProcessing managing **
  3. // ** using Word or OpenOffice automaticaly  **
  4. // ** By: Sergio Hernandez                    **
  5. // ** oficina(at)hcsoft.net, CopyLeft 2004    **
  6. // ** Version 0.3 20-10-2009 (DDMMYYYY)      **
  7. // ** Use it freely, change it, etc.          **
  8. // *********************************************
  9.  
  10. {EXAMPLE OF USE
  11.   //Create object: We have two flavours:
  12.   //(A) from an existing file...
  13.   TxtDoc:= TDocumentoTexto.create(OpenDialog.FileName, false);
  14.   //(B) from a blank document...
  15.   TxtDoc:= TDocumentoTexto.create(thcOpenOffice, true); //OpenOffice doc if possible, please
  16.   TxtDoc.FileName:= 'C:\MyNewDoc'; //Needs a file name before you SaveDoc!
  17.   //--end of creation.
  18.   //Change a text (search&replace)
  19.   TxtDoc.ChangeOneValue('<MyClient>', 'Cocoa company, ltd.');
  20.   //Preview print...
  21.   TxtDoc.ShowPrintPreview
  22.   TxtDoc.PrintDoc;
  23.   TxtDoc.SaveDoc;
  24.   TxtDoc.SaveToPDF('C:\MyPDF.pdf');
  25.   TxtDoc.Free;
  26. }
  27.  
  28. {ABOUT CONVERTING DOC TO PDF:
  29.   //Force opening the .doc file with OOo like this:
  30.   TxtDoc:= TDocumentoTexto.create(thcOpenOffice, true);
  31.   TxtDoc.LoadDoc('C:\MyWord.doc');
  32.   //Now that OOo has imported the .doc, convert it:
  33.   TxtDoc.SaveToPDF('C:\MyPDF.pdf');
  34.   TxtDoc.Free;
  35. }
  36.  
  37. {HISTORIY:
  38. V0.3 - SaveToPDF for OpenOffice added from www.oooforum.org/forum/viewtopic.phtml?t=22344
  39. V0.2 - WaitForIddle added to avoid Word behavior (saving before completing work)
  40. V0.1 - Initial version, it works ok.
  41. }
  42.  
  43. {TODO LIST:
  44.   -No functions to add text, change font, bold, etc.
  45.   -Can I know the OOo writer printing status like in Word?
  46.   -Can I know if Word/Writer is doing something in background?
  47. }
  48.  
  49. unit UDocumentoTexto;
  50.  
  51. interface
  52.  
  53. uses Variants, SysUtils, ComObj, Classes, Launch;
  54.  
  55. //thcError: Tried to open but both failes
  56. //thcNone:  Haven't tried still to open
  57. type TTipoDoc = (thcError, thcNone, thcWord, thcOpenOffice);
  58.  
  59. type TDocumentoTexto = class(TObject)
  60. private
  61.   fVisible:  boolean;
  62.   //Program loaded stuff...
  63.   procedure  LoadProg;
  64.   procedure  CloseProg;
  65.   function  GetProgLoaded: boolean;
  66.   procedure  NewDoc;
  67.   procedure  LoadDoc;
  68.   procedure  CloseDoc;
  69.   function  GetDocLoaded: boolean;
  70.   function  GetIsWord: boolean;
  71.   function  GetIsOpenOffice: boolean;
  72.   procedure  SetVisible(v: boolean);
  73.   //OpenOffice only stuff...
  74.   function  FileName2URL(FileName: string): string;
  75.   procedure  ooDispatch(ooCommand: string; ooParams: variant);
  76.   function  ooCreateValue(ooName: string; ooData: variant): variant;
  77.   function  isNullEmpty(thisVariant: Variant): Boolean;
  78. public
  79.   Tipo: TTipoDoc;        //Witch program was used to manage the doc?
  80.   FileName:    string;    //In windows FileName format C:\MyDoc.XXX
  81.   Programa:    variant;  //Word or OpenOfice instance created.
  82.   DeskTop:    variant;  //OpenOffice desktop reference (not used now).
  83.   Document:    variant;  //Document opened.
  84.   //Object internals...
  85.   constructor  Create(Name: string; MakeVisible: boolean); overload;
  86.   constructor  Create(MyTipo: TTipoDoc; MakeVisible: boolean); overload;
  87.   destructor  Destroy; override;
  88.   //Program loaded stuff...
  89.   function    SaveDoc: boolean;
  90.   function    SaveToPDF(FileName: string): boolean;
  91.   function    PrintDoc: boolean;
  92.   procedure    ShowPrintPreview;
  93.   property    ProgLoaded: boolean    read GetProgLoaded;
  94.   property    DocLoaded:  boolean    read GetDocLoaded;
  95.   property    IsWord: boolean        read GetIsWord;
  96.   property    IsOpenOffice: boolean  read GetIsOpenOffice;
  97.   property    Visible: boolean        read fVisible          write SetVisible;
  98.   //Special function (Search & Replace)
  99.   procedure    ChangeOneValue(SearchTxt, ReplaceTxt: String; Headers: boolean = true);
  100.   //Wait until word end doing its things
  101.   function    WaitForIddle(MaxSec: double = 30): double;
  102. end;
  103.  
  104. var
  105.   CoInitFlags: Integer = -1;
  106.  
  107. const
  108.   SearchAll: integer = 2; //Word search_for_all (0=None, 1=Once, 2=All)
  109.  
  110. implementation
  111.  
  112. // ************************
  113. // ** Create and destroy **
  114. // ************************
  115.  
  116. //Create with an empty doc of requested type (use thcWord, thcOpenOffice)
  117. //Remember to define FileName before calling to SaveDoc
  118. constructor TDocumentoTexto.Create(MyTipo: TTipoDoc; MakeVisible: boolean);
  119. var
  120.   i: integer;
  121.   IsFirstTry: boolean;
  122. begin
  123.   //Close all opened things first...
  124.   CloseDoc;
  125.   CloseProg;
  126.   //I will try to open twice, so if Word fails, OpenOffice is used instead
  127.   IsFirstTry:= true;
  128.   for i:= 1 to 2 do begin
  129.     //Try to open OpenOffice...
  130.     if (MyTipo = thcOpenOffice) or (MyTipo = thcNone)then begin
  131.       try
  132.         Programa:= CreateOleObject('com.sun.star.ServiceManager');
  133.       except
  134.       end;
  135.       if ProgLoaded then begin
  136.         Tipo:= thcOpenOffice;
  137.         break;
  138.       end else begin
  139.         if IsFirstTry then begin
  140.           //Try Excel as my second choice
  141.           MyTipo:= thcWord;
  142.           IsFirstTry:= false;
  143.         end else begin
  144.           //Both failed!
  145.           break;
  146.         end;
  147.       end;
  148.     end;
  149.     //Try to open Word...
  150.     if (MyTipo = thcWord) or (MyTipo = thcNone) then begin
  151.       try
  152.         Programa:= CreateOleObject('Word.Application');
  153.       except
  154.       end;
  155.       if ProgLoaded then begin
  156.         Tipo:= thcWord;
  157.         break;
  158.       end else begin
  159.         if IsFirstTry then begin
  160.           //Try OpenOffice as my second choice
  161.           MyTipo:= thcOpenOffice;
  162.           IsFirstTry:= false;
  163.         end else begin
  164.           //Both failed!
  165.           break;
  166.         end;
  167.       end;
  168.     end;
  169.   end;
  170.   //Was it able to open any of them?
  171.   if Tipo = thcNone then begin
  172.     Tipo:= thcError;
  173.     raise Exception.Create('TDocumentoTexto.create failed, may be no Office is installed?');
  174.   end;
  175.   //Add a blank document...
  176.   fVisible:= MakeVisible;
  177.   NewDoc;
  178. end;
  179.  
  180. constructor TDocumentoTexto.Create(Name: string; MakeVisible: boolean);
  181. begin
  182.   //Close all opened things first...
  183.   CloseDoc;
  184.   CloseProg;
  185.   Tipo:= thcNone;
  186.   //Store values...
  187.   FileName:= Name;
  188.   //Open program and document...
  189.   LoadProg;
  190.   LoadDoc;
  191.   //Visible?
  192.   Visible:= MakeVisible;
  193. end;
  194.  
  195. destructor TDocumentoTexto.Destroy;
  196. begin
  197.   CloseProg;
  198.   inherited;
  199. end;
  200.  
  201. // *************************
  202. // ** Loading the program **
  203. // ** Word or OpenOffice  **
  204. // *************************
  205.  
  206. procedure TDocumentoTexto.LoadProg;
  207. begin
  208.   if ProgLoaded then CloseProg;
  209.   if (UpperCase(ExtractFileExt(FileName))='.DOC') then begin
  210.     //Word is the primary choice...
  211.     try
  212.       Programa:= CreateOleObject('Word.Application');
  213.     except end;
  214.     if ProgLoaded then Tipo:= thcWord;
  215.   end;
  216.   //Not lucky with Word? Another filetype? Let's go with OpenOffice...
  217.   if Tipo = thcNone then begin
  218.     //Try with OpenOffice...
  219.     try
  220.       Programa:= CreateOleObject('com.sun.star.ServiceManager');
  221.     except end;
  222.     if ProgLoaded then Tipo:= thcOpenOffice;
  223.   end;
  224.   //Still no program loaded?
  225.   if not ProgLoaded then begin
  226.     Tipo:= thcError;
  227.     raise Exception.Create('TDocumentoTexto.LoadProg failed, may be no Office is installed?');
  228.   end;
  229. end;
  230.  
  231. procedure TDocumentoTexto.CloseProg;
  232. begin
  233.   if not Visible then CloseDoc;
  234.   if ProgLoaded then begin
  235.     try
  236.       if IsWord then begin
  237.         Programa.Quit;
  238.         Programa:= Null;
  239.       end;
  240.       if IsOpenOffice then begin
  241.         Desktop.Dispose;
  242.         Desktop:= unassigned;
  243.         Programa.Dispose;
  244.       end;
  245.       Programa:= Unassigned;
  246.     except end;
  247.   end;
  248.   Tipo:= thcNone;
  249. end;
  250.  
  251. //Is there any prog loaded? Witch one?
  252. function TDocumentoTexto.GetProgLoaded: boolean;
  253. begin
  254.   result:= not isNullEmpty(Programa);
  255. end;
  256. function  TDocumentoTexto.GetIsWord: boolean;
  257. begin
  258.   result:= (Tipo=thcWord);
  259. end;
  260. function  TDocumentoTexto.GetIsOpenOffice: boolean;
  261. begin
  262.   result:= (Tipo=thcOpenOffice);
  263. end;
  264.  
  265. // ************************
  266. // ** Loading a document **
  267. // ************************
  268.  
  269. procedure TDocumentoTexto.NewDoc;
  270. var ooParams: variant;
  271. begin
  272.   //Is the program running? (Word or OpenOffice)
  273.   if not ProgLoaded then raise Exception.Create('No program loaded for the new document.');
  274.   //Is there a doc already loaded?
  275.   CloseDoc;
  276.   DeskTop:= Unassigned;
  277.   //OK, now try to create the doc...
  278.   if IsWord then begin
  279.     Programa.WorkBooks.Add;
  280.     Programa.Visible:= Visible;
  281.     Document:= Programa.ActiveWorkBook;
  282.   end;
  283.   if IsOpenOffice then begin
  284.     Desktop:=  Programa.CreateInstance('com.sun.star.frame.Desktop');
  285.     //Optional parameters (visible)...
  286.     ooParams:=    VarArrayCreate([0, 0], varVariant);
  287.     ooParams[0]:= ooCreateValue('Hidden', false); // çç not Visible);
  288.     //Create the document...
  289.     Document:= Desktop.LoadComponentFromURL('private:factory/swriter', '_blank', 0, ooParams);
  290.   end;
  291. end;
  292.  
  293. procedure TDocumentoTexto.LoadDoc;
  294. var ooParams: variant;
  295. begin
  296.   if FileName='' then exit;
  297.   //Is the program running? (Word or OpenOffice)
  298.   if not ProgLoaded then LoadProg;
  299.   //Is there a doc already loaded?
  300.   CloseDoc;
  301.   DeskTop:= Unassigned;
  302.   //OK, now try to open the doc...
  303.   if IsWord then begin
  304.     Document:= Programa.Documents.Open(string(FileName),,,,,,,,,,,true);
  305.   end;
  306.   if IsOpenOffice then begin
  307.     Desktop:=  Programa.CreateInstance('com.sun.star.frame.Desktop');
  308.     //Optional parameters (visible)...
  309.     ooParams:=    VarArrayCreate([0, 0], varVariant);
  310.     ooParams[0]:= ooCreateValue('Hidden', false); //Should be "not Visible" but didn't work ok
  311.     //Open the document...
  312.     Document:= Desktop.LoadComponentFromURL(FileName2URL(FileName), '_blank', 0, ooParams);
  313.     if isNullEmpty(Document) then
  314.       raise Exception.Create('Could load the  document "'+FileName+'".');
  315.   end;
  316.   if Tipo=thcNone then
  317.     raise Exception.Create('Could load the document "'+FileName+'". No Word processor installed?.');
  318. end;
  319.  
  320. function TDocumentoTexto.SaveDoc: boolean;
  321. begin
  322.   result:= false;
  323.   if DocLoaded then begin
  324.     if IsWord then begin
  325.       Document.Save;
  326.       result:= true;
  327.     end;
  328.     if IsOpenOffice then begin
  329.       //There is another method, more powerfull, see SaveToPDF function.
  330.       Document.Store;
  331.       result:= true;
  332.     end;
  333.   end;
  334. end;
  335.  
  336. //If you are using OOo, you can export to PDF directly.
  337. //In word, the only choice is to use a PDF printer, out of our scope here!
  338. //NOTE: If you open a HTML in OOo, the param 0 need to be diferent as commented
  339. //Code refactored from an example by Ryan at:
  340. //  http://www.oooforum.org/forum/viewtopic.phtml?t=22344
  341. function TDocumentoTexto.SaveToPDF(FileName: string): boolean;
  342. var ooParams: variant;
  343. begin
  344.   result:= false;
  345.   if DocLoaded then begin
  346.     if IsOpenOffice then begin //Word can't export to PDF!
  347.       ooParams:= VarArrayCreate([0, 0], varVariant);
  348.       //If the doc loaded is a HTML, you should use this param[0] instead:
  349.       //ooParam[0]:= ooCreateValue('FilterName', 'writer_web_pdf_Export')
  350.       ooParams[0]:= ooCreateValue('FilterName', 'writer_pdf_Export');
  351.       Document.StoreToURL(FileName2URL(FileName), ooParams);
  352.     end;
  353.   end;
  354. end;
  355.  
  356. //Print the Doc...
  357. function TDocumentoTexto.PrintDoc: boolean;
  358. var ooParams: variant;
  359. begin
  360.   result:= false;
  361.   if DocLoaded then begin
  362.     if IsWord then begin
  363.       Document.PrintOut;
  364.       while Programa.BackgroundPrintingStatus > 0 do
  365.         sleep(500);
  366.       result:= true;
  367.     end;
  368.     if IsOpenOffice then begin
  369.       ooParams:=  VarArrayCreate([0, 0], varVariant);
  370.       ooParams[0]:= ooCreateValue('Wait', true);
  371.       Document.Print(ooParams);
  372.       //Can't know printing status (maybe it is possible)
  373.       //So wait for process to iddle (under 0.5% CPU)
  374.       WaitForIddle;
  375.       result:= true;
  376.     end;
  377.   end;
  378. end;
  379.  
  380. procedure TDocumentoTexto.ShowPrintPreview;
  381. begin
  382.   if DocLoaded then begin
  383.     //Force visibility of the doc...
  384.     Visible:= true;
  385.     if IsWord then
  386.       Document.PrintOut(,,,true);
  387.     if IsOpenOffice then
  388.       ooDispatch('.uno:PrintPreview', Unassigned);
  389.   end;
  390. end;
  391.  
  392. procedure TDocumentoTexto.SetVisible(v: boolean);
  393. begin
  394.   if DocLoaded and (v<>fVisible) then begin
  395.     if IsWord then
  396.       Programa.Visible:= v;
  397.     if IsOpenOffice then begin
  398.       Document.getCurrentController.getFrame.getContainerWindow.setVisible(v);
  399.     end;
  400.     fVisible:= v;
  401.   end;
  402. end;
  403.  
  404. procedure TDocumentoTexto.CloseDoc;
  405. begin
  406.   if DocLoaded then begin
  407.     //Close it...
  408.     try
  409.       if IsOpenOffice then Document.Dispose;
  410.       if IsWord      then Document.close;
  411.     except end;
  412.     //Clean up "pointer"...
  413.     Document:= Null;
  414.   end;
  415. end;
  416.  
  417. function TDocumentoTexto.GetDocLoaded: boolean;
  418. begin
  419.   result:= not isNullEmpty(Document);
  420. end;
  421.  
  422. procedure TDocumentoTexto.ChangeOneValue(SearchTxt, ReplaceTxt: String; Headers: boolean = true);
  423. var  j, Paso: integer;
  424.     Txt, Busca, Reemp: string;
  425.     ooBuscador: variant;
  426. begin
  427.   case Tipo of
  428.   thcWord: begin
  429.       //Word can't replace with a text longer than 250!
  430.       if length(ReplaceTxt) < 250 then begin
  431.         Programa.ActiveDocument.Content.Find.Execute(SearchTxt, true, false, false, false, false,,,, ReplaceTxt, SearchAll);
  432.         if Headers then begin
  433.           //Search in page header...
  434.           Programa.ActiveWindow.ActivePane.View.SeekView:=  9; //9 = wdSeekCurrentPageHeader
  435.           Programa.Selection.Find.Execute(SearchTxt, true, false, false, false, false,,,,ReplaceTxt,SearchAll);
  436.           //Search on footer...
  437.           Programa.ActiveWindow.ActivePane.View.SeekView:= 10; //10 = wdSeekCurrentPageFooter
  438.           Programa.Selection.Find.Execute(SearchTxt, true, false, false, false, false,,,,ReplaceTxt,SearchAll);
  439.         end;
  440.         //You can wait for Word to finish 0.1 secs. uncomenting next line...
  441.         //sleep(100);
  442.         //...but calling WaitForIddle after all your replaces is a better choice!
  443.       end else begin
  444.         //I have to "chop" the text into pieces of max. 240 chars!
  445.         //NOTE: Coping from array N[] to D[] can make a DLL run out of memory
  446.         //and raise rare errors, so I make it char by char!
  447.         Busca:= ''; for j:= 1 to Length(SearchTxt)  do Busca:= Busca+SearchTxt[j];
  448.         Reemp:= ''; for j:= 1 to Length(ReplaceTxt) do Reemp:= Reemp+ReplaceTxt[j];
  449.         Paso:= 1;
  450.         repeat
  451.           Txt:=  copy(Reemp,1,240);
  452.           Reemp:= copy(Reemp,241,9999);
  453.           if (Reemp<>'') then
  454.             Txt:= Txt+'[@#@'+IntToStr(Paso)+']';
  455.           Programa.ActiveDocument.Content.Find.Execute(Busca,true,false,false,false,false,,,,Txt,SearchAll);
  456.           Busca:= '[@#@'+IntToStr(Paso)+']';
  457.           inc(Paso);
  458.           //Need to wait for Word to finish before processing the next txt piece
  459.           sleep(100);
  460.         until (Reemp='');
  461.       end;
  462.     end;
  463.   thcOpenOffice: begin
  464.       if isNullEmpty(Document) then
  465.         raise Exception.Create('No text document loaded');
  466.       ooBuscador:= Document.createReplaceDescriptor;
  467.       ooBuscador.SearchString:=  SearchTxt;
  468.       ooBuscador.ReplaceString:= ReplaceTxt;
  469.       Document.ReplaceAll(ooBuscador);
  470.     end;
  471.   end;
  472. end;
  473.  
  474. //Wait for Word to end up with all instruction we have through at it.
  475. //As Word diggest them asincronous, you never know if you are finish
  476. //and you can end up saving BEFORE all previous commands are done!
  477. //It detects it by measuring the proc %CPU usage until it drops below 0.5%
  478. function TDocumentoTexto.WaitForIddle(MaxSec: double = 30): double;
  479. var ProcName: string;
  480. begin
  481.   //Process Name...
  482.   if Tipo=thcWord then ProcName:= 'WINWORD.EXE'
  483.   else                ProcName:= 'swriter.exe';
  484.   //Wait for the %CPU to drop below 0.5%
  485.   result:= WaitExeIddle(ProcName, 1, MaxSec);
  486. end;
  487.  
  488. // ***************************
  489. // ** OpenOffice only stuff **
  490. // ***************************
  491.  
  492. //Change 'C:\File.txt' into 'file:///c:/File.txt' (for OpenOffice OpenURL)
  493. function TDocumentoTexto.FileName2URL(FileName: string): string;
  494. begin
  495.   result:= '';
  496.   if LowerCase(copy(FileName,1,8))<>'file:///' then
  497.     result:= 'file:///';
  498.   result:= result + StringReplace(FileName, '\', '/', [rfReplaceAll, rfIgnoreCase]);
  499. end;
  500.  
  501. function TDocumentoTexto.ooCreateValue(ooName: string; ooData: variant): variant;
  502. var
  503.   ooReflection: variant;
  504. begin
  505.   if IsOpenOffice then begin
  506.     ooReflection:= Programa.createInstance('com.sun.star.reflection.CoreReflection');
  507.     ooReflection.forName('com.sun.star.beans.PropertyValue').createObject(result);
  508.     result.Name := ooName;
  509.     result.Value:= ooData;
  510.   end else begin
  511.     raise Exception.Create('ooValue imposible to create, load OpenOffice first!');
  512.   end;
  513. end;
  514.  
  515. procedure TDocumentoTexto.ooDispatch(ooCommand: string; ooParams: variant);
  516. var
  517.   ooDispatcher, ooFrame: variant;
  518. begin
  519.   if DocLoaded and IsOpenOffice then begin
  520.     if (VarIsEmpty(ooParams) or VarIsNull(ooParams)) then
  521.       ooParams:= VarArrayCreate([0, -1], varVariant);
  522.     ooFrame:= Document.getCurrentController.getFrame;
  523.     ooDispatcher:= Programa.createInstance('com.sun.star.frame.DispatchHelper');
  524.     ooDispatcher.executeDispatch(ooFrame, ooCommand, '', 0, ooParams);
  525.   end else begin
  526.     raise Exception.Create('Dispatch imposible, load a OpenOffice doc first!');
  527.   end;
  528. end;
  529.  
  530. function TDocumentoTexto.isNullEmpty(thisVariant: Variant): Boolean;
  531. begin
  532.   Result:= VarIsEmpty(thisVariant) or VarIsNull(thisVariant) or VarIsClear(thisVariant);
  533. end;
  534.  
  535. end.



El problema es aquí:


delphi
  1. //...
  2. unit UDocumentoTexto;
  3.  
  4. interface
  5.  
  6. uses Variants, SysUtils, ComObj, Classes, Launch;
  7.  
  8. //...



Gracias nuevamente.
Santiago.
  • 0

#17 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 23 mayo 2014 - 03:27

La encontré:
Está en: http://www.daniweb.c...execute-to-work

Pongo el código para los que no quieren irse "tan lejos":


delphi
  1. {************************************************************************}
  2. {*                                                                      *}
  3. {*      file      : Launch.PAS                                        *}
  4. {*                                                                      *}
  5. {*      type      : unit                                              *}
  6. {*                                                                      *}
  7. {*      location  : \QUIRT\SRC\DELPHI                                  *}
  8. {*                                                                      *}
  9. {*      purpose    : Launch external programs                          *}
  10. {*                                                                      *}
  11. {*      author    : Lennert Ploeger (NKI / AVL)                        *}
  12. {*                                                                      *}
  13. {*      date      : 19980325                                          *}
  14. {*                                                                      *}
  15. {*      portability: 32 bit delphi only (V2.0 up)                      *}
  16. {*                                                                      *}
  17. {*      notes      : None                                              *}
  18. {*                                                                      *}
  19. {************************************************************************}
  20. {* Updates:
  21. When            Who    What
  22. 19980325        lsp    Created
  23. 19980331        lsp    Search for programs in PATH using SearchPath()
  24. 19980609        lsp    Allow white-spaces for the program to launch
  25. 19980709        lsp    Allow 'prog' to be empty in StartProgram
  26. 19980731        lsp    Enclose both file and directory names in double quotes
  27. 19980901        lsp    Removed some obsolete functions
  28. 19981004        mvh    Added RunProgram (waits until ready)
  29. 19981005        mvh    Renamed to RunProgramBlocking (waits until ready)
  30. 19981020        lsp    Program launched in RunProgramBlocking() is started
  31.                         minimized and not given focus
  32. 19990110        mvh    RunProgramBlocking returns value
  33. 19990111        lsp    Fixed comment about CloseHandle()
  34. 19990112      mvh     Added RunProgramWaiting, shortened code by reuse
  35. 19990425        lsp    FileUtil -> QFileUtil
  36. 19990609        lsp    Removed QFileUtil dependency
  37. *}
  38. unit Launch;
  39. interface
  40. //Para pasar de ProcId a THandle
  41. type
  42.   TWindowRec = record
  43.     Handle: THandle;
  44.     ProcessId: Cardinal;
  45.     WindowName: PChar;
  46.   end;
  47.   PWindowRec = ^TWindowRec;
  48. function LocateProgramInSearchPath(ProgramName: string): string;
  49. procedure StartProgram(prog, workdir: string; params: array of string);
  50. function RunProgramBlocking(prog, workdir: string; params: array of string): integer;
  51. function RunFileBlocking(fichero: string): boolean;
  52. function RunProgramWaiting(prog, workdir: string; params: array of string): integer;
  53. function ProgramStarter(prog, workdir: string; params: array of string; showmode: integer): integer;
  54. //HCSoft...
  55. //Localizar Handler de un proceso a partir del filename del ejecutable
  56. function GetProcHandle(ExeFileName: string): THandle;
  57. //Hacer cosas a partir del THandle...
  58. function KillProc(H: THandle): boolean;
  59. function WaitProcIddle(H: THandle; MinSeg: double = 1; MaxSeg: double = 30): double;
  60. //Hacer cosas a partir del FileName...
  61. function WaitExeIddle(ExeFileName: string; MinSeg: double = 0.1; MaxSeg: double = 10): double;
  62. function KillTask(ExeFileName: string): boolean;
  63. implementation
  64. uses
  65.   SysUtils, Dialogs, Windows, Forms, FileCtrl, ShellAPI, HCBase, Tlhelp32;
  66.  
  67. // Routine to retrieve file information using a file/dirname
  68. function FileDirNameWin32FindData(FullPathName: string; var Win32FindData: TWin32FindData): boolean;
  69. var
  70.   Handle: THandle;
  71. begin
  72.   Handle := FindFirstFile(PChar(FullPathName), Win32FindData);
  73.   if Handle <> INVALID_HANDLE_VALUE then
  74.   begin
  75.     Windows.FindClose(Handle);
  76.     Result := True;
  77.   end
  78.   else
  79.     Result := False;
  80. end;
  81. // Search for 'ProgramName' in %PATH% using Win API function 'SearchPath'
  82. function LocateProgramInSearchPath(ProgramName: string): string;
  83. type
  84.   BufType = array[0..255] of char;
  85. var
  86.   SPPath: BufType;
  87.   PathPtr: PChar;
  88. begin
  89.   if SearchPath(nil, PChar(ProgramName), nil, 255, SPPath, PathPtr)>0 then
  90.     Result := StrPas(SPPath)
  91.   else
  92.     Result := ProgramName;
  93. end;
  94. function TestExistence(const Name: string): boolean;
  95. begin
  96.   Result := FileExists(Name) or DirectoryExists(Name);
  97. end;
  98. // Internal common code for the 3 exported program starters
  99. function ProgramStarter(prog, workdir: string;
  100.                         params: array of string; showmode: integer): integer;
  101. var
  102.   StartInf : TStartupInfo;
  103.   ProcInf  : TProcessInformation;
  104.   args    : string;
  105.   progtmp  : string;
  106.   pAppName : PChar;
  107.   pworkdir : PChar;
  108.   i        : integer;
  109. begin
  110.   // It appears that it is also possible to call ShellExecute, what seems
  111.   // to be a bit a higher level function:
  112.   // ShellExecute(handle, "open", path_to_file, NULL, NULL, SW_SHOWNORMAL);
  113.   // Another alternative can be calling WinExec, but with the drawback of
  114.   // not having the possibility to specify the work directory.
  115.   ZeroMemory(@StartInf, sizeof(TStartupInfo));
  116.   ZeroMemory(@ProcInf, sizeof(TProcessInformation));
  117.   StartInf.cb      := sizeof(TStartupInfo);
  118.   StartInf.dwFlags := STARTF_USESHOWWINDOW ;
  119.   StartInf.wShowWindow := showmode;
  120.   // To call CreateProcess() we should be carefull to enclose files
  121.   // passed in 'lpCommandLine' in double quotes ('"') to make sure that
  122.   // it understands where one starts and ends. The pecularity is that the
  123.   // name of the executable should NOT be enclosed in double quotes. Passing
  124.   // both the file and the arguments in lpCommandLine and leaving
  125.   // lpApplicationName empty is no option, since the application and
  126.   // arguments should be white-space delimited that way.
  127.   progtmp := prog;
  128.   if not FileExists(progtmp) then
  129.     progtmp := LocateProgramInSearchPath(progtmp);
  130.   if Length(prog)>0 then
  131.     args := '"' + prog + '"';
  132.   for i:=low(params) to high(params) do
  133.   begin
  134.     // Enclose file and directory names in double quotes to get them seperated properly
  135.     if TestExistence(params[i]) then
  136.     begin
  137.       if Length(args)>0 then // Try to add spaces only when necessary
  138.         args := args + ' "' + params[i] + '"'
  139.       else
  140.         args := '"' + params[i] + '"'
  141.     end
  142.     else if Length(params[i])>0 then
  143.     begin
  144.       if Length(args)>0 then // Try to add spaces only when necessary
  145.         args := args + ' ' + params[i]
  146.       else
  147.         args := params[i];
  148.     end;
  149.   end;
  150.   if Length(workdir)>0 then
  151.     pworkdir := PChar(workdir)
  152.   else
  153.     pworkdir := nil;
  154.   if Length(progtmp)>0 then
  155.     pAppName := PChar(progtmp)
  156.   else
  157.     pAppName := nil;
  158.   if not CreateProcess(pAppName, PChar(args), nil, nil, False, 0, nil,
  159.     pworkdir, StartInf, ProcInf) then
  160.     MessageDlg('El programa ' + prog + ' no ha podido ser ejecutado', mtError, [mbOk], 0);
  161.   // The handles for both the process and the main thread must be closed through
  162.   // calls to CloseHandle. These handles are not needed, so it is best to close
  163.   // them immediately after the process is created.
  164.   result := ProcInf.hProcess;
  165.   CloseHandle(ProcInf.hThread);
  166. end;
  167. // routine to start program 'prog' using the file-parameters in 'params'.
  168. // Be carefull with passing [] for the params, since the stackpointer seems
  169. // to get corrupt. However, starting a program with no arguments can be done
  170. // using StartProgram(program, workdir, [ ' ' ]).
  171. procedure StartProgram(prog, workdir: string; params: array of string);
  172. var
  173.   hProcess: integer;
  174. begin
  175.   hProcess := ProgramStarter(prog, workdir, params, SW_SHOWDEFAULT);
  176.   CloseHandle(hProcess);
  177. end;
  178. // routine to run program 'prog' using the file-parameters in 'params'.
  179. // and wait until it is finished
  180. // Be careful with passing [] for the params, since the stackpointer seems
  181. // to get corrupt. However, starting a program with no arguments can be done
  182. // using StartProgram(program, workdir, [ ' ' ]).
  183. function RunProgramBlocking(prog, workdir: string; params: array of string): integer;
  184. var
  185.   hProcess: integer;
  186.   j      : Cardinal;
  187. begin
  188.   hProcess := ProgramStarter(prog, workdir, params, SW_SHOWMINNOACTIVE);
  189.   WaitForSingleObject(hProcess, INFINITE);
  190.   GetExitCodeProcess(hProcess, j);
  191.   result := integer(j);
  192.   CloseHandle(hProcess);
  193. end;
  194. function RunFileBlocking(fichero: string): boolean;
  195. var
  196.   SEI: TShellExecuteInfo;
  197. begin
  198.   //Ejecuto el fichero con el programa adecuado...
  199.   FillChar(SEI, SizeOf(SEI), 0); // Wipe the record to start with
  200.   Result:= true;
  201.   with SEI do
  202.   begin
  203.     cbSize := SizeOf(SEI);
  204.     fMask := see_Mask_NoCloseProcess;
  205.     Wnd := Application.MainForm.Handle;
  206.     lpVerb := 'open';
  207.     lpFile := PAnsiChar(fichero);
  208.     lpDirectory := PChar(ExtractFilePath(fichero));
  209.     nShow := sw_ShowNormal;
  210.     if not ShellExecuteEx(@SEI) then
  211.       Result:= False;
  212.   end;
  213.   //Espero a que liberen el fichero...
  214.   //WaitForSingleObjet no se debe usar si se va a abrir una ventana porque
  215.   //el proceso que llama deja de procesar mensajes y la ventana nueva cuelga:
  216.   //http://msdn.microsoft.com/en-us/library/ms687032%28VS.85%29.aspx
  217.   while WaitForSingleObject(SEI.hProcess, 100) = WAIT_TIMEOUT do
  218.     Application.ProcessMessages;
  219. end;
  220. // routine to run program 'prog' using the file-parameters in 'params'.
  221. // and wait until it is finished. During the wait, however, messages are
  222. // processed so that the user interface remains 'live'.
  223. function RunProgramWaiting(prog, workdir: string; params: array of string): integer;
  224. var
  225.   hProcess: integer;
  226.   j        : Cardinal;
  227. begin
  228.   hProcess := ProgramStarter(prog, workdir, params, SW_SHOWMINNOACTIVE);
  229.   while WaitForSingleObject(hProcess, 10) = WAIT_TIMEOUT do
  230.     Application.ProcessMessages;
  231.   GetExitCodeProcess(hProcess, j);
  232.   result := integer(j);
  233.   CloseHandle(hProcess);
  234. end;
  235. // **************************************************************************
  236. // ** AÑADIDO SERGIO PARA MENEJAR PROCESOS POR SU HANDLE O SU EXE FILENAME **
  237. // **************************************************************************
  238. function FileTime2Milliseconds(FileTime: TFileTime): integer;
  239. var ST: TSystemTime;
  240. begin
  241.   FileTimeToSystemTime(FileTime, ST);
  242.   result:= ST.wMilliseconds + 1000 *
  243.           (ST.wSecond + 60 * (ST.wMinute + 60 * ST.wHour)) ;
  244. end;
  245. //Sabemos 'WINWORD.EXE', dame un THandle del proceso para hacerle putadillas
  246. function GetProcHandle(ExeFileName: string): THandle;
  247. var
  248.   ContinueLoop: BOOL;
  249.   FSnapshotHandle: THandle;
  250.   FProcessEntry32: TProcessEntry32;
  251. begin
  252.   result:= 0;
  253.   FSnapshotHandle:= CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
  254.   FProcessEntry32.dwSize:= Sizeof(FProcessEntry32);
  255.   ContinueLoop:= Process32First(FSnapshotHandle, FProcessEntry32);
  256.   while integer(ContinueLoop) <> 0 do begin
  257.     if ((UpperCase(ExtractFileName(FProcessEntry32.szExeFile)) = UpperCase(ExeFileName))
  258.     or (UpperCase(FProcessEntry32.szExeFile) = UpperCase(ExeFileName))) then begin
  259.       result:= OpenProcess(PROCESS_ALL_ACCESS, FALSE, FProcessEntry32.th32ProcessID);
  260.       break;
  261.     end;
  262.     ContinueLoop:= Process32Next(FSnapshotHandle, FProcessEntry32);
  263.   end;
  264.   CloseHandle(FSnapshotHandle);
  265. end;
  266. //Mata este proceso!
  267. function KillProc(H: THandle): boolean;
  268. const PROCESS_TERMINATE=$0001;
  269. begin
  270.   result:= (Integer(TerminateProcess(H, 0))<>0);
  271. end;
  272. //Espera a que un Proceso use menos del 1% de la CPU.
  273. //Si no encuentra el proceso, esperara MinSeg, y si lo encuentra pero no baja
  274. //del 1%, se esperara un maximo de MaxSeg.
  275. function WaitProcIddle(H: THandle; MinSeg: double = 1; MaxSeg: double = 30): double;
  276. var
  277.   LastProcTime, NewProcTime, UsedTime: integer; //Milisegundos todo
  278.   CreaTime, ExitTime, UserTime, KernelTime: TFileTime;
  279. const
  280.   WAIT_FOR_MS: integer = 1000; //Cada 1 segundo (1000 ms) vuelves a mirar
  281.   IDDLE_LOWER: integer =    5; //Usados < 5 ms = (%CPU<0.5) salimos
  282. begin
  283.   //Llevo esperando 0 segundos...
  284.   result:= 0;
  285.   //Igual no lo encuentro...
  286.   if (H=0) then begin
  287.     //Pues no esta, espero algo y me voy...
  288.     sleep(round(MinSeg*1000));
  289.   end else begin
  290.     //Proceso encontrado, a esperar...
  291.     if GetProcessTimes(H, CreaTime, ExitTime, KernelTime, UserTime)=BOOL(0) then exit;
  292.     LastProcTime:= FileTime2Milliseconds(KernelTime) + FileTime2Milliseconds(UserTime);
  293.     //Cada decima de segundo, recalculo...
  294.     repeat
  295.       sleep(WAIT_FOR_MS);
  296.       result:= result + (WAIT_FOR_MS/1000);
  297.       //Rescato tiempo dle proceso actualizado...
  298.       if GetProcessTimes(H, CreaTime, ExitTime, KernelTime, UserTime)=BOOL(0) then exit;
  299.       NewProcTime:= FileTime2Milliseconds(KernelTime) + FileTime2Milliseconds(UserTime);
  300.       UsedTime:= (NewProcTime - LastProcTime);
  301.       if (UsedTime) < IDDLE_LOWER then
  302.         break;
  303.       LastProcTime:= NewProcTime;
  304.     until (result >= MaxSeg);
  305.   end;
  306. end;
  307. // ***************************************************
  308. // ** MANEJO PROCESOS SABIENDO SU NOMBRE DE FICHERO **
  309. // ***************************************************
  310. //Espera a que una tarea baje del 1%CPU usando su filename
  311. function WaitExeIddle(ExeFileName: string; MinSeg: double = 0.1; MaxSeg: double = 10): double;
  312. begin
  313.   result:= WaitProcIddle(GetProcHandle(ExeFileName), MinSeg, MaxSeg);
  314. end;
  315. //Mata programa por su nombre...
  316. function KillTask(ExeFileName: string): boolean;
  317. begin
  318.   result:= KillProc(GetProcHandle(ExeFileName));
  319. end;
  320. end.



Nota: La unit "HCBase" no tiene uso, se puede sacar sin problemas. De hecho si no la sacamos no permite la compilación.
Ya me dirá Sergio si estoy en lo cierto.
Gracias.
  • 0

#18 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 23 mayo 2014 - 04:04

Ohh, el código está bastante bueno.
Justo encima del método SaveToPDF dice:

If you are using OOo, you can export to PDF directly.
In word, the only choice is to use a PDF printer, out of our scope here!
NOTE: If you open a HTML in OOo, the param 0 need to be diferent as commented
Code refactored from an example by Ryan at: http://www.oooforum....c.phtml?t=22344
:smiley:

De igual manera, no deja de estar bueno.
Una vuelta de tuerca mas y podemos tener un exportador PDF que lo haga desde OpenOffice y Office.

Saludos.


  • 0

#19 santiago14

santiago14

    Advanced Member

  • Miembros
  • PipPipPip
  • 334 mensajes
  • LocationCerrillos - Salta - Argentina

Escrito 24 mayo 2014 - 06:37

Ohh, el código está bastante bueno.
Justo encima del método SaveToPDF dice:

If you are using OOo, you can export to PDF directly.
In word, the only choice is to use a PDF printer, out of our scope here!
NOTE: If you open a HTML in OOo, the param 0 need to be diferent as commented
Code refactored from an example by Ryan at: http://www.oooforum....c.phtml?t=22344
:smiley:

De igual manera, no deja de estar bueno.
Una vuelta de tuerca mas y podemos tener un exportador PDF que lo haga desde OpenOffice y Office.

Saludos.


  • 0

#20 Sergio

Sergio

    Advanced Member

  • Moderadores
  • PipPipPip
  • 1.092 mensajes
  • LocationMurcia, España

Escrito 26 mayo 2014 - 05:23

Olvide el tema del launch.pas y hcbase, bueno, cosas del directo!

El launch.pas que uso es el que has encontrado, solo le añadi en mi caso 3 o 4 funciones extras para "cosas raras" que no se usan en esta unit, así que la que has encontrado es la correcta.

HCBase es una unit que metemos siempre con funciones nuestras se usen o no, por si acaso.

Y lo del mensaje sobre convertir a PDF en MS-Office, bueno, nuestras apps corren en sistemas que escapan de nuestro control, y nunca sabemos si usan Word 97, 2007, OpenOffice, LibreOffice, o lo que sea, ni si tienen o no instalado tal o cual añadido, así que realmente nuestras apps siempre usan una impresora PDF para convertir, sea el tipo de fichero que sea, a PDF (aunque sea con LibreOffice).

Si fuerzas el uso por defecto de una impresora PDF y sobre el fichero haces click derecho, Imprimir, obtienes un PDF, así que si automatizas esto, puedes convertir de autocad a pdf de forma automatica, por eso no nos complicamos la vida.
  • 0




IP.Board spam blocked by CleanTalk.