Question

J'ai une macro VBA Excel que je dois exécuter lors de l'accès au fichier à partir d'un fichier de commandes, mais pas à chaque fois que je l'ouvre (et donc de ne pas utiliser l'événement de fichier ouvert). Y at-il un moyen d'exécuter la macro à partir de la ligne de commande ou d'un fichier batch? Je ne suis pas au courant d'une telle commande.

Supposons un environnement Windows NT.

Était-ce utile?

La solution

Vous pouvez lancer Excel, ouvrez le classeur et exécutez la macro à partir d'un fichier VBScript.

Copiez le code ci-dessous dans le Bloc-notes.

Mise à jour du ' MyWorkbook.xls ' et ' MaMacro paramètres.

Enregistrer avec une extension VBS et l'exécuter.

Option Explicit

On Error Resume Next

ExcelMacroExample

Sub ExcelMacroExample() 

  Dim xlApp 
  Dim xlBook 

  Set xlApp = CreateObject("Excel.Application") 
  Set xlBook = xlApp.Workbooks.Open("C:\MyWorkbook.xls", 0, True) 
  xlApp.Run "MyMacro"
  xlApp.Quit 

  Set xlBook = Nothing 
  Set xlApp = Nothing 

End Sub 

La ligne clé qui exécute la macro est:

xlApp.Run "MaMacro"

Autres conseils

La façon la plus simple de le faire est de:

1) Démarrez Excel à partir de votre fichier batch pour ouvrir le classeur contenant votre macro:

EXCEL.EXE /e "c:\YourWorkbook.xls"

2) Appelez votre macro de l'événement Workbook_Open du classeur, telles que:

Private Sub Workbook_Open()
    Call MyMacro1          ' Call your macro
    ActiveWorkbook.Save    ' Save the current workbook, bypassing the prompt
    Application.Quit       ' Quit Excel
End Sub

Ceci renvoie maintenant le contrôle de votre fichier batch pour faire un autre traitement.

La méthode indiquée ci-dessous permet d'exécuter macro Excel défini à partir du fichier batch, il utilise la variable d'environnement pour passer le nom macro de lot à Excel.

Mettez ce code dans le fichier batch (utilisez vos chemins pour EXCEL.EXE et le classeur):

Set MacroName=MyMacro
"C:\Program Files\Microsoft Office\Office15\EXCEL.EXE" "C:\MyWorkbook.xlsm"

Mettre ce code Excel VBA ThisWorkbook Objet:

Private Sub Workbook_Open()
    Dim strMacroName As String
    strMacroName = CreateObject("WScript.Shell").Environment("process").Item("MacroName")
    If strMacroName <> "" Then Run strMacroName
End Sub

Et mettre votre code VBA Excel Module, comme la façon suivante:

Sub MyMacro()
    MsgBox "MyMacro is running..."
End Sub

Lancer le fichier batch et obtenir le résultat:

 bo&icirc;te de dialogue de macro

Pour le cas où vous ne comptez pas utiliser une macro juste mettre Set MacroName= valeur vide du lot.

vous pouvez écrire un script VBScript pour créer une instance d'Excel via la méthode CreateObject (), puis ouvrez le classeur et exécutez la macro. Vous pouvez soit appeler le vbscript directement, ou appelez le vbscript à partir d'un fichier batch.

Voici une ressource que je viens de tombé accross: http://www.codeguru.com/forum/showthread.php?t= 376401

Je l'ai toujours testé le nombre de classeurs ouverts dans Workbook_Open (). Si elle est 1, le classeur a été ouvert par la ligne de commande (ou l'utilisateur a fermé tous les classeurs, puis a ouvert celui-ci).

If Workbooks.Count = 1 Then

    ' execute the macro or call another procedure - I always do the latter  
    PublishReport

    ThisWorkbook.Save

    Application.Quit

End If

Si vous êtes plus à l'aise dans Excel / VBA, utilisez l'événement ouvert et tester l'environnement. Soit un fichier de signal, une entrée de registre ou une variable d'environnement qui contrôle ce que l'événement ouvert fait

Vous pouvez créer le fichier / réglage extérieur et test dans (utiliser GetEnviromentVariable pour env-vars) et tester facilement. J'ai écrit VBScript mais les similitudes avec VBA me causent plus Angst que la facilité ..

[plus]

Si je comprends bien le problème, vous souhaitez utiliser une feuille de calcul normalement plus / de temps en temps mais ont courir dans le lot et faire quelque chose supplémentaire / différent. Vous pouvez ouvrir la feuille de la ligne de commande excel.exe mais vous ne pouvez pas contrôler ce qu'il fait à moins qu'il ne sait où il est. L'utilisation d'une variable d'environnement est relativement simple et permet de tester la feuille de calcul facile.

Pour clarifier les choses, utiliser la fonction ci-dessous pour examiner l'environnement. Dans un module déclare:

Private Declare Function GetEnvVar Lib "kernel32" Alias "GetEnvironmentVariableA" _
    (ByVal lpName As String, ByVal lpBuffer As String, ByVal nSize As Long) As Long

Function GetEnvironmentVariable(var As String) As String
Dim numChars As Long

    GetEnvironmentVariable = String(255, " ")

    numChars = GetEnvVar(var, GetEnvironmentVariable, 255)

End Function

Dans le classeur événement ouvert (comme d'autres):

Private Sub Workbook_Open()
    If GetEnvironmentVariable("InBatch") = "TRUE" Then
        Debug.Print "Batch"
    Else
        Debug.Print "Normal"
    End If
End Sub

Ajoutez dans le code actif selon le cas. Dans le fichier batch, utilisez

set InBatch=TRUE

Au lieu de comparer directement les chaînes (VB ne les trouvera pas égale depuis GetEnvironmentVariable retourne une chaîne de longueur 255) écrire ceci:

Private Sub Workbook_Open()     
    If InStr(1, GetEnvironmentVariable("InBatch"), "TRUE", vbTextCompare) Then
        Debug.Print "Batch"  
        Call Macro
    Else    
        Debug.Print "Normal"     
    End If 

End Sub 

@ Robert. J'ai essayé d'adapter votre code avec un chemin relatif, et a créé un fichier batch pour exécuter le VBS

Le VBS démarre et se ferme, mais ne lance pas la macro ... Toute idée de l'endroit où la question pourrait être?

Option Explicit

On Error Resume Next

ExcelMacroExample

Sub ExcelMacroExample() 

  Dim xlApp 
  Dim xlBook 

  Set xlApp = CreateObject("Excel.Application")
  Set objFSO = CreateObject("Scripting.FileSystemObject")
  strFilePath = objFSO.GetAbsolutePathName(".") 
  Set xlBook = xlApp.Workbooks.Open(strFilePath, "Excels\CLIENTES.xlsb") , 0, True) 
  xlApp.Run "open_form"


  Set xlBook = Nothing 
  Set xlApp = Nothing 

End Sub

J'ai enlevé le « Application.Quit » parce que ma macro appelle un userform prendre soin.

Vive

EDIT

Je l'ai effectivement travaillé dehors, juste au cas où quelqu'un veut lancer un userform « aussi bien » une application autonome:

Questions que je faisais face:

1 - Je ne voulais pas utiliser l'événement Workbook_Open comme Excel est verrouillé en lecture seule. 2 - La commande de lot est limité que le fait que (à ma connaissance), il ne peut pas appeler la macro

.

J'ai d'abord écrit une macro pour lancer mon userform tout en cachant l'application:

Sub open_form()
 Application.Visible = False
 frmAddClient.Show vbModeless
End Sub

J'ai ensuite créé un vbs pour lancer cette macro (le faire avec un chemin relatif a été difficile):

dim fso
dim curDir
dim WinScriptHost
set fso = CreateObject("Scripting.FileSystemObject")
curDir = fso.GetAbsolutePathName(".")
set fso = nothing

Set xlObj = CreateObject("Excel.application")
xlObj.Workbooks.Open curDir & "\Excels\CLIENTES.xlsb"
xlObj.Run "open_form"

Et j'ai finalement fait un fichier batch pour exécuter le VBS ...

@echo off
pushd %~dp0
cscript Add_Client.vbs

Notez que j'ai également inclus le "Back to visible" dans mon Userform_QueryClose:

Private Sub cmdClose_Click()
Unload Me
End Sub

Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
    ThisWorkbook.Close SaveChanges:=True
    Application.Visible = True
    Application.Quit
End Sub

En tout cas, merci pour votre aide, et j'espère que cela vous aidera si quelqu'un a besoin

Vous pouvez vérifier si Excel est déjà ouvert. Il n'y a pas besoin de créer un autre isntance

   If CheckAppOpen("excel.application")  Then
           'MsgBox "App Loaded"
            Set xlApp = GetObject(, "excel.Application")   
   Else
            ' MsgBox "App Not Loaded"
            Set  wrdApp = CreateObject(,"excel.Application")   
   End If

Je suis partie à C #. Je l'ai couru à l'aide LINQPad suivante. Mais il pourrait tout aussi facilement être compilé avec et a couru à travers csc l'appelé de la ligne de commande.

Ne pas oublier d'ajouter des packages Excel à l'espace de noms.

void Main()
{
    var oExcelApp = (Microsoft.Office.Interop.Excel.Application)System.Runtime.InteropServices.Marshal.GetActiveObject("Excel.Application");
    try{
        var WB = oExcelApp.ActiveWorkbook;
        var WS = (Worksheet)WB.ActiveSheet;
        ((string)((Range)WS.Cells[1,1]).Value).Dump("Cell Value"); //cel A1 val
        oExcelApp.Run("test_macro_name").Dump("macro");
    }
    finally{
        if(oExcelApp != null)
            System.Runtime.InteropServices.Marshal.ReleaseComObject(oExcelApp);
        oExcelApp = null;
    }
}
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top