The problem: In my environment (64-bit Windows 10) I have tens of thousands of old-format Word documents (.doc) that must be updated to the new .docx format. These documents are spread across thousands of folders on a share drive. I have found some code that can automate this process, but it relies on methods in the Word object model that security policies won't allow.
In the Trust Center, under "File Block Settings", I have word 6.0, word 95, word 97 and word 2000 documents blocked. No way to change these -- settings are managed by my organization.
That said, even though I can't open them using VBA, I can manually open some of these doc files. I'm thinking that a really old-school approach might work: Open a blank Word application, then use send-keys to open the doc files and then save in the new docx format.
I can start Word in VBA
Dim objWordApplication as Word.Application
set objWordApplication = CreateObject("Word.Application")
objectWordApplication.Visible = True
My specific questions: Once the Word object is running, what do I "send" to it to get it to open a file named xyz.doc? That is, in the following code, what is "ABC"?
objWordApplication.SendKeys ("ABCxyz", true)
FYSA, my environment is very strictly controlled. Solutions that invoke any third-party programs, changes to security settings, and other "non-vanilla" actions just won't fly. Finally, for some reason my questions seem like "homework" to some people, so I assure everyone that this is a production-level problem, not homework.
Thanks in advance for any assistance.
Related
I'm using Word 2019 and have created macros I want to send to other organisations.
However, when I transfer the document (.docm) or the template (.dotm) the recipient doesn't get the macros (although everything else goes across). On the Developer ribbon, there is no entry for the macro itself or the VBA code.
I know I can export the macro to a *.bas file which the recipient can then import but I'd like to do it directly.
There is no problem with transferring Excel macros but I can't get Word to work.
Can anybody help?
This is most likely to have 2 possible reasons:
Did you really choose "Word Macro-Enabled Document" as file format? It could be that you saved a normal "Word Document" with the file extension .docm. Note that the file extension does not defined the file format.
If this happend you have actually a Word document (without macros) but with the wrong file extension .docm. Make sure you choose the correct format not only the correct extension.
You can easily test this:
Save your file as macro enabled file docm.
Close Word completely.
Re-Open your file. If the macro is still there your file format is correct.
If you send your file via email it can be that your recepient does not allow to recieve macro enabled files, and his email server is stripping off the macro from the Word file.
If this is the case, then you cannot do much to prevent this. It is in the responsibility of the recepient. The only way to get through this kind of filter is to pack your file into a password protected zip archive so the email server cannot access the Word file. But not that doing so can violate the recepients policies. Also if the reciepient's company did it right they won't allow password protected zip archives via email because the could tunnel through their email filters.
Best solution in this case it to provide the file via some cloud share (Google Drive, Dropbox, One Drive, what ever, …) and send the recipient a link only.
That is because of your AV blocking macros to be saved in your PC. Macros have been used in the past by threat actors and Microsoft has applied a protection to them.
When you edit a document with macros, word creates a hidden file which is the macro you are running, now when you try to save that file, it gets caught by AV. Since AV thinks it is an evil activity. It gets saved on your system because your directory is now a Trusted Location and it is okay.
A workaround is to install Windows 7 with Microsoft Office 2007 to get what you want since Windows 7 has little to no security.
Thanks
I am looking for some tips how to resolve a problem with distributing macro to other users in my company.
I’ve created a specific workbook which holds a bunch of various types of data such as dates, strings and numbers. Each of the users have to manage the same types of data, so we use this workbook as a template. Data is stored in a columns to which I’ve applied a conditional formatting and data validation to prevent users from inserting wrong values. This Workbook contains few Worksheets with specific names. Names of this worksheets appear in the code – to make some specific calculations for each one of them (based on the name of the worksheet).
The problem is that there is a probability that in the future I would like to make some changes to the code for example to make my macro more efficient or to implement some changes that are necessary.
I’ve searched through the internet to find the best solution and I think the best is to create an Add-In to Excel. But I’ve some questions about that.
Is this really the best solution? Can someone give me a hint to make it in a better way?
If Add-In is the best, is there a way to add this only to specific workbooks (which are my template)?
Is it possible to install Add-in when someone opens a specific workbook (using Workbook_Open) and uninstall it when workbooks is closing (using Workbook_BeforeClose). I’ve looked for answers on the web, but this matter is not clear to me. If this is possible, would it affect speed of the closing/opening workbooks?
Thanks for any help/advice!
Put the add-in on the network drive and mark it as read-only. Use a local copy to make updates. Make sure to set it to read only each time you copy it, and make sure people are running off the network drive.
Often times when people install an Add-In, they answer YES to the question about copying it to their local drive and that is not the right answer. If they accidentally click YES you will need to edit their registry to remove the local reference.
For distributing an add-in through a shared drive with your own development copy I would highly suggest to read the following link.
It has a description of the installation process, including a very important point that braX brought up in his answer - answering No when asked about copying to personal add-in folder.
Below is an adjusted code from the link that I use to save add-ins. It goes into a normal module in the add-in itself. It saves an add-in a folder and sets its attribute to Read only so that whenever it is used by somebody it will not be locked. This setup allows you to update the file by running this macro at any time without needing to chase down users and get them to close Excel.
Private Sub Deploy()
Dim FolderOnSharedDrive as String
FolderOnSharedDrive = "Folder path to store add-in in here"
With ThisWorkbook
On Error Resume Next
SetAttr FolderOnSharedDrive & .Name, vbNormal
On Error GoTo 0
.SaveCopyAs FolderOnSharedDrive & .Name
SetAttr FolderOnSharedDrive & .Name, vbReadOnly
MsgBox "Deploy Completed to " & FolderOnSharedDrive & .Name
End With
End Sub
It is a good idea to add checks for filepath and perhaps some error-handling.
As to some other issues you bring up:
Add-ins can include worksheets that are not visible that you can use to store settings, paths, etc.
It is possible to make add-in appear only on specific workbooks but it will take some effort:
Include a ribbon for an add-in that includes callback for visibility. Set it to visible whenever specific workbook(template) is active. It will still be loaded to memory in any Excel instance
You can programatically add add-ins on open and remove on close as you suggested, check this question to see some options.
Adding/removing add-ins on close or open will definitely affect the speed, but I cannot say if it will be noticeable.
I have encountered a stumbling block that exceeds my experience in working with MS Word macros. Until recently, I have not had much need to use macros in Word or Excel, and what little bit I have needed was completely internal to the document or spreadsheet.
Now I find myself needing guidance on creating a macro that will draw on external files to create a temporary new file.
Within a working folder, I have a Master Document and numerous daughter documents. The daughter documents all have file tags/keywords.
What I need is protected document (it can be DOC, PDF or HTML) that when opened will run a macro that will (1) query the user for a search term, (2) search all the files in the folder for file tags or keywords that match (3) open all those matching files into a single html page for display.
All the source files are Word 2010 but can be saved as PDF or HTML if it makes things easier.
Thanks in advance.
Word's Master Document 'feature' is a disaster waiting to happen! Use it only if you don't value your work. See:
https://wordmvp.com/FAQs/General/WhyMasterDocsCorrupt.htm
http://www.addbalance.com/word/masterdocuments.htm
As for opening all your source documents in a single window, that's not possible unless you actually merge those documents into a single file. The code for that is complex. For some code to get you started, see:
https://www.mrexcel.com/forum/general-excel-discussion-other-questions/1037570-vba-combine-differently-formatted-word-files-into-1-while-preserving-layouts-post4980503.html#post4980503
I created a VBA-macro which will be used by some word-documents within my company. The macro detects tags and removes chapters from a document. This document is created by another program. So the macro should be separately distributable.
Is it possible to generate an executable which adds the macro to the user running the executable?
Is there another way to package macros and install them on a user's computer?
Thanks
The easiest way to deploy Macros is via a template. Create your Macro and save the file as .dotm (macro-enabled template). I think you will get a suggestion where to save your .dotm-file.
Any colleague who wants to use your template simply has to put it in that directory (I think it's C:\Users\[UserName]\AppData\Roaming\Microsoft\Templates). After that, he should be able to use the macros while working on any word document.
There are basically five ways to do this:
1) Send everyone a text file with your macro that they can paste into their own Normal template. This is fine for very simple macros that are unlikely to have any name conflicts with macros users create themselves, but it does require basic knowledge of the VB editor.
2) Send everyone a .bas file that you create by exporting a module that contains your macro(s). This gives you a little more control and avoids copy/paste errors. Still requires basic understanding of the VB editor (or decent instructions from you).
3) Package your macros in a template (.dotm file) that lives in the Templates folder. Users can apply that template to any document they're creating and gain access to your macro(s). No VB knowledge required; this is done through the standard Word New File process. Also allows you to include styles or other things if you want.
4) Package your macros as a global template (.dotm file) that lives in the Startup folder. Users will have access to your macro(s) in every file they work on, no need to apply your template. This is good if what you are doing is central to your team's workflow and doesn't require that you include styles with your macro. You can also build in UI elements. (There can be issues with this approach in Word 2011; users may not have immediate access to the global template but it is easy enough to get back.)
Both 3 and 4 do require that the user initially place the .dotm file in the right place. You can help them with this (one approach is to use another Word doc as a "setup" file that, when run, places the template in the presumed correct folder). Obviously that requires more work on your part so how far you'd want to go with that depends on you and your business needs.
5) Additionally, if you have control over the creation of the document itself (rather than just the macro) you can embed a macro in the document. You can place the macro itself in the document's ThisDocument module (find your document in the Project Explorer and then open Microsoft Word Objects). Then save the document as .docm (macro-enabled document). Users should be instructed to enable macros when they open the document (different versions of Word use slightly different interfaces for prompting the user about this, but it's always pretty obvious).
Over the last 7 years I have been deploying my Word VBA in a different way. The software is a Word add-in that makes it easier for teachers to provide feedback on assignments. It is distributed as a 30 day trial and if the user buys it they are given a key which enables them to use eMarking Assistant for a year. You can test the deployment system at http://eMarkingAssistant.com
The deployment and licensing mechanism is given below:
save the vba in a macro enabled document i.e. a .docm file
in Windows rename the file to be a .doc file
use Orlando's excellent "VBA decompiler and compacter" from http://orlando.mvps.org/VBADecompilerMore.asp to remove compiled code and references to specific Office versions from the .doc and compact the document
ask the user to download the .doc file
ask the user to open the .doc file and ensure that macros are enabled
let the user trial the software in the document
if they want to use the software in any document they click an "install" button in the document to copy the vba code to to a .dotm file in their Word startup folder (so it is loaded automagically)
if they want to buy a subscription to use the software, they pay using paypal and I send them a key which unlocks the software until the end of the subscription
Advantages of this process are:
a single document can be used on all versions of Office for Windows from Office 97 to Office 2016 (32 bit and 64 bit).
the install and uninstall all happen within Office so the suer does not need to admin rights over their computer
users do not need to install the software until they have used it in the document
users do not need to use another program to unzip or install the software
Peter Evans
I am programmatically generating Office Documents (in my case Word or Excel 2007) using automation in VBA (in this example MS Access 2007, but that should not change much) under Windows 7. This works fine.
Since the documents are automatically generated I don't want them to show up in the recent lists. For recent list in Word I can just add "AddToRecentFiles:=False" when saving the document (see example) or I could delete the entries afterwards through "Application.RecentFiles ..."
My code
Set objWord = CreateObject("Word.Application")
Set curDocument = objWord.Documents.Add
curDocument.SaveAs FileName:=Folder + "text.doc", FileFormat:=wdFormatDocument,
AddToRecentFiles:=False
curDocument.Close
Problem is I could not find a way to disable the recent lists from Windows 7 (i.e. jump list with recent items in the taskbar for Word or last used folders in Explorer and recent list for Word in Start menu).
I am aware these lists are stored under %APPDATA%\Microsoft\Windows\Recent\AutomaticDestinations and I have found out that to manipulate Jumplist there is the "WindowsAPICodePack" (that I can not use from VBA, right?).
To add an item the the recent list I can use the old API SHAddToRecentDocs from the "shell32.dll" library but deleting with this API function does not work anymore as it only seems to affect the entries in the old "/recent" folder (and even deletes everything what is not my intention). Presentations on the Windows 7 Taskbar API too only seem to mention how to add items but not how to avoid doing so or to delete specific entries.
Am I missing something or is there no -- easy and ideally usable from within VBA -- way to manipulate (or temporerally disable) the recording Windows 7 does?
Kind regards
Andreas
I have encountered a similar problem when programmatically dealing with Word and other office documents with Sharepoint.
You can access the JumpList object via the PresentationFramework library (.Net 4) or the WindowsAPICodePack for 3.5 (and possibly earlier) however there does not appear to be a way to programmatically delete JumpListItems.
I found a post which suggests that you can disable Word from adding items to the JumpList via registry key. http://www.add-in-express.com/forum/read.php?PAGEN_1=2&FID=5&TID=8124#nav_start This shouldn't be too hard to do programmatically (if you have admin rights on the machine generating the documents).
I haven't had a chance to try out whether this works yet. If you find a more elegant solution please let me know!
Update: In my solution I ended up regenerating the jumplist based on the Word Recent files list (I looped backwards through the internal Word recent files list and called JumpList.AddToRecent method for each file).