Comment convertir des fichiers Word en PDF par programme? [fermé]


221

J'ai trouvé plusieurs programmes open-source / freeware qui vous permettent de convertir des fichiers .doc en fichiers .pdf, mais ils sont tous de la variété du pilote d'application / imprimante, sans SDK attaché.

J'ai trouvé plusieurs programmes qui ont un SDK vous permettant de convertir des fichiers .doc en fichiers .pdf, mais ils sont tous du type propriétaire, 2 000 $ par licence ou à peu près.

Quelqu'un connaît-il une solution de programmation propre et peu coûteuse (de préférence gratuite) à mon problème, en utilisant C # ou VB.NET?

Merci!


1
Vérifiez si Pandoc a des liaisons pour votre langue préférée . L'interface de ligne de commande est également très simplepandoc manual.docx -o manual.pdf
Colonel Panic

Vérifiez également le SDK GemBox.Document . Il a une version gratuite et une version peu coûteuse. Il n'utilise ni pilote d'imprimante ni ms office pour convertir des fichiers Word en PDF.
hertzogth

Vous pouvez utiliser docx2pdf pour effectuer cette conversion: github.com/AlJohri/docx2pdf
Al Johri

Réponses:


204

Utilisez une boucle foreach au lieu d'une boucle for - cela a résolu mon problème.

int j = 0;
foreach (Microsoft.Office.Interop.Word.Page p in pane.Pages)
{
    var bits = p.EnhMetaFileBits;
    var target = path1 +j.ToString()+  "_image.doc";
    try
    {
        using (var ms = new MemoryStream((byte[])(bits)))
        {
            var image = System.Drawing.Image.FromStream(ms);
            var pngTarget = Path.ChangeExtension(target, "png");
            image.Save(pngTarget, System.Drawing.Imaging.ImageFormat.Png);
        }
    }
    catch (System.Exception ex)
    {
        MessageBox.Show(ex.Message);  
    }
    j++;
}

Voici une modification d'un programme qui a fonctionné pour moi. Il utilise Word 2007 avec le complément Save As PDF installé. Il recherche dans un répertoire les fichiers .doc, les ouvre dans Word, puis les enregistre au format PDF. Notez que vous devrez ajouter une référence à Microsoft.Office.Interop.Word à la solution.

using Microsoft.Office.Interop.Word;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;

...

// Create a new Microsoft Word application object
Microsoft.Office.Interop.Word.Application word = new Microsoft.Office.Interop.Word.Application();

// C# doesn't have optional arguments so we'll need a dummy value
object oMissing = System.Reflection.Missing.Value;

// Get list of Word files in specified directory
DirectoryInfo dirInfo = new DirectoryInfo(@"\\server\folder");
FileInfo[] wordFiles = dirInfo.GetFiles("*.doc");

word.Visible = false;
word.ScreenUpdating = false;

foreach (FileInfo wordFile in wordFiles)
{
    // Cast as Object for word Open method
    Object filename = (Object)wordFile.FullName;

    // Use the dummy value as a placeholder for optional arguments
    Document doc = word.Documents.Open(ref filename, ref oMissing,
        ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing,
        ref oMissing, ref oMissing, ref oMissing, ref oMissing, ref oMissing,
        ref oMissing, ref oMissing, ref oMissing, ref oMissing);
    doc.Activate();

    object outputFileName = wordFile.FullName.Replace(".doc", ".pdf");
    object fileFormat = WdSaveFormat.wdFormatPDF;

    // Save document into PDF Format
    doc.SaveAs(ref outputFileName,
        ref fileFormat, ref oMissing, ref oMissing,
        ref oMissing, ref oMissing, ref oMissing, ref oMissing,
        ref oMissing, ref oMissing, ref oMissing, ref oMissing,
        ref oMissing, ref oMissing, ref oMissing, ref oMissing);

    // Close the Word document, but leave the Word application open.
    // doc has to be cast to type _Document so that it will find the
    // correct Close method.                
    object saveChanges = WdSaveOptions.wdDoNotSaveChanges;
    ((_Document)doc).Close(ref saveChanges, ref oMissing, ref oMissing);
    doc = null;
}

// word has to be cast to type _Application so that it will find
// the correct Quit method.
((_Application)word).Quit(ref oMissing, ref oMissing, ref oMissing);
word = null;

3
Je vous remercie! Je peux simplement utiliser Aspose de toute façon, si c'est plus rapide que l'automatisation de Word. Mais si je peux tolérer un peu de lenteur, je vais continuer à utiliser votre solution. Merci encore!
Shaul Behr

4
Oui, ce n'est pas le plus rapide mais c'est difficile de battre le prix. :-) Heureux d'avoir pu aider.
Eric Ness

10
Avec Office 2007 SP2, vous n'avez plus besoin de l'enregistrer au format PDF. J'ai également utilisé cette technique avec succès pour Excel et Powerpoint.
RichardOD

5
Avez-vous utilisé cette méthode sur un serveur avec une application Web? Je reçois beaucoup de problèmes sans mentionner que ce n'est pas recommandé par MS. support.microsoft.com/default.aspx?scid=kb;EN-US;q257757#kb2 J'ai entendu dire que ASPose est génial mais c'est assez cher.
Prabu

6
Um ... si word n'est pas installé, je pense que l'emballage de l'assemblage interop sera le moindre de vos soucis. Ce code nécessite un mot à installer.
BrainSlugs83

35

Pour résumer pour les utilisateurs de vb.net, l'option gratuite (doit avoir installé office):

Téléchargement de Microsoft Office Assembies:

Exemple VB.NET:

        Dim word As Application = New Application()
        Dim doc As Document = word.Documents.Open("c:\document.docx")
        doc.Activate()
        doc.SaveAs2("c:\document.pdf", WdSaveFormat.wdFormatPDF)
        doc.Close()

3
Fonctionne toujours en 2015. Avec Office 2013, vous n'avez pas besoin de télécharger le PIA séparément.
Adam Anderson

3
Et BOOM s'il ouvre une boîte de message et demande quelque chose - par exemple dans une application web ... ou fait 2 documents en même temps ...
Stefan Steiger

Une option freemium (via nodejs et edge.js ou Javascript.NET) est npmjs.com/package/@nativedocuments/docx-wasm (pas besoin de Word)
JasonPlutext

14

PDFCreator possède un composant COM, appelable depuis .NET ou VBScript (exemples inclus dans le téléchargement).

Mais, il me semble qu'une imprimante est exactement ce dont vous avez besoin - il suffit de mélanger cela avec l'automatisation de Word , et vous devriez être prêt à partir.


où est ce composant COM? Et que signifie "mik"? Était-ce censé être "mix"?
Shaul Behr

Le composant COM est inclus dans le téléchargement, avec des exemples. Et oui, c'était censé être "mix".
Mark Brackett

4
Pour info - si vous suivez cette voie, PDFCreator regroupe les logiciels malveillants dans le programme d'installation. Il s'agit d'un problème permanent avec PDFCreator depuis 2009.
Phil Gorley

2
@PhilGorley Malware? et cette réponse est +8 ...
Mzn

@Mzn - FWIW, prêter attention et décocher les installations des addons fonctionne toujours pour moi. Je ne le vois pas différemment de la merde de regroupement Oracle dans le programme d'installation Java; c'est ennuyeux, mais cela ne vaut pas la peine d'éviter le logiciel pour moi (ouais, OK, l'adware PdfCreator est probablement infiniment moins utile et plus intrusif que ce qu'Oracle pousse ces jours-ci ... Je ne veux toujours pas l'un d'eux).
Mark Brackett

12

Je voulais juste ajouter que j'ai utilisé les bibliothèques Microsoft.Interop, en particulier la fonction ExportAsFixedFormat que je n'ai pas vue utilisée dans ce fil.

using Microsoft.Office.Interop.Word;
using System.Runtime.InteropServices;
using System.IO;
using Microsoft.Office.Core;

Application app;

public string CreatePDF(string path, string exportDir)
{
    Application app = new Application();
    app.DisplayAlerts = WdAlertLevel.wdAlertsNone;
    app.Visible = true;

    var objPresSet = app.Documents;
    var objPres = objPresSet.Open(path, MsoTriState.msoTrue, MsoTriState.msoTrue, MsoTriState.msoFalse);

    var pdfFileName = Path.ChangeExtension(path, ".pdf");
    var pdfPath = Path.Combine(exportDir, pdfFileName);

    try
    {
        objPres.ExportAsFixedFormat(
            pdfPath,
            WdExportFormat.wdExportFormatPDF,
            false,
            WdExportOptimizeFor.wdExportOptimizeForPrint,
            WdExportRange.wdExportAllDocument
        );
    }
    catch
    {
        pdfPath = null;
    }
    finally
    {
        objPres.Close();
    }
    return pdfPath;
}

7
Juste une note pour ceux qui ne savent pas que vous avez besoin d'Office installé sur la machine pour utiliser les bibliothèques Microsoft Interop.
Sam Rueby

Agréable! Je suggère de définir app.Visible = false;et d'ajouter un appel à app.Quit();dans le bloc enfin.
Dan Korn


5

J'ai traversé la douleur de Word en PDF lorsque quelqu'un m'a vidé de 10000 fichiers de mots à convertir en PDF. Maintenant, je l'ai fait en C # et j'ai utilisé Word Interop mais c'était lent et s'est écrasé si j'essayais d'utiliser PC du tout .. très frustrant.

Cela m'a amené à découvrir que je pouvais vider les interops et leur lenteur ..... pour Excel j'utilise (EPPLUS) puis j'ai découvert que vous pouvez obtenir un outil gratuit appelé Spire qui permet de convertir en PDF ... avec des limitations!

http://www.e-iceblue.com/Introduce/free-doc-component.html#.VtAg4PmLRhE


Merci pour cette excellente solution sans utiliser Interop. Pourquoi est-il si difficile de trouver un convertisseur docx en PDF gratuit?
mbdavis

J'avais de grands espoirs pour cela, mais la version gratuite est limitée à 3 pages de sortie PDF. La version complète est très chère si vous avez besoin de déploiements illimités.
grinder22

grinder22 GemBox.Document a également une version gratuite avec limitation de taille et une version payante. Cependant, il comprend un déploiement sans redevance afin que vous puissiez créer et publier un nombre illimité de projets sans frais supplémentaires.
hertzogth

3

Code et solution Microsoft.Office.Interop.Wordfaciles à utiliser pour convertir WORD en PDF

using Word = Microsoft.Office.Interop.Word;

private void convertDOCtoPDF()
{

  object misValue = System.Reflection.Missing.Value;
  String  PATH_APP_PDF = @"c:\..\MY_WORD_DOCUMENT.pdf"

  var WORD = new Word.Application();

  Word.Document doc   = WORD.Documents.Open(@"c:\..\MY_WORD_DOCUMENT.docx");
  doc.Activate();

  doc.SaveAs2(@PATH_APP_PDF, Word.WdSaveFormat.wdFormatPDF, misValue, misValue, misValue, 
  misValue, misValue, misValue, misValue, misValue, misValue, misValue);

  doc.Close();
  WORD.Quit();


  releaseObject(doc);
  releaseObject(WORD);

}

Ajoutez cette procédure pour libérer de la mémoire:

private void releaseObject(object obj)
{
  try
  {
      System.Runtime.InteropServices.Marshal.ReleaseComObject(obj);
      obj = null;
  }
  catch (Exception ex)
  {
      //TODO
  }
  finally
  {
     GC.Collect();
  }
}

Faut-il appeler GC.Collect? N'y a-t-il pas une autre façon de ne marquer que la partie de la mémoire qui y est liée pour la libérer sur le prochain GC automatique?
Preza8

2

Semble être quelques informations pertinentes ici:

Conversion de documents MS Word en PDF dans ASP.NET

De plus, avec Office 2007 ayant une fonctionnalité de publication au format PDF, je suppose que vous pouvez utiliser la bureautique pour ouvrir le fichier * .DOC dans Word 2007 et enregistrer au format PDF. Je n'aime pas trop la bureautique car elle est lente et sujette à la suspension, mais je la lance juste là-bas ...


Aspose peut fonctionner, mais c'est extrêmement cher.
Shaul Behr

1

Le complément Microsoft PDF pour Word semble être la meilleure solution pour l'instant, mais vous devez prendre en compte qu'il ne convertit pas tous les documents Word correctement en PDF et dans certains cas, vous verrez une énorme différence entre le mot et le PDF de sortie. Malheureusement, je n'ai trouvé aucune API capable de convertir correctement tous les documents Word. La seule solution que j'ai trouvée pour garantir une conversion à 100% était de convertir les documents via un pilote d'imprimante. L'inconvénient est que les documents sont mis en file d'attente et convertis un par un, mais vous pouvez être sûr que le pdf résultant est exactement le même que la mise en page des documents Word. Personnellement, j'ai préféré utiliser UDC (Universal Document Converter) et installé Foxit Reader (version gratuite) sur le serveur, puis j'ai imprimé les documents en lançant un "Processus" et en définissant sa propriété Verb sur "print".

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.