I need to generate a whole sheet of QR codes, (eventually about 1000), i am trying to automate the generation in Excel 2016, i currently have a sheet set up and have a URL to the generater using Google Apis, I just change the ID number in the url for it to take me to make the next code and take me to the correct place. I dont want to have to manually go and get the code and copy it into my document for each one.
Does anyone have any ideas that may help me out, i have set up the first 10 and this can be seen on the screenshot attached.
enter image description here
Thanks
You can use this VBA code to your Excel file,then you have to make a selection for the cells that you want to create QR Codes for them, then run the code "InsertQR" by (Alt+F8)
The VBA code will create QR codes for each selected cell as PNG file.
Note: You must be connected to the Internet
Sub InsertQR()
Dim xHttp: Set xHttp = CreateObject("Microsoft.XMLHTTP")
Dim bStrm: Set bStrm = CreateObject("Adodb.Stream")
Dim size: size = 500 'dalam Pixels
Dim QR, Name, val
Dim Invalid: Invalid = "\/:*?" & """" & "<>|"
For Each val In Selection
Name = val.Value
For intChar = 1 To Len(Name)
If InStr(Invalid, LCase(Mid(Name, intChar, 1))) > 0 Then
MsgBox "The file: " & vbCrLf & """" & Name & """" & vbCrLf & vbCrLf & " is invalid!"
Exit Sub
End If
Next
QR = "http://chart.googleapis.com/chart?chs=" & size & "x" & size & "&cht=qr&chl=" & Name
xHttp.Open "GET", QR, False
xHttp.Send
With bStrm
.Type = 1 '//binary
.Open
.write xHttp.responseBody
.savetofile ThisWorkbook.Path & "\" & Name & ".png", 2 '//overwrite
.Close
End With
Next
End Sub
This is the closest thing I could find with what you are trying to do.
https://sites.google.com/site/e90e50fx/home/generate-qrcode-with-excel
It's generate a QR code image but I can't get it to do it for multiple cell values.
Related
I'm trying to adapt an Excel form I created that uses drive locations to save copies of the form, to work with SharePoint in a similar manner. Currently, the first macro is set up such that it will search the contents of a particular folder to determine the next available number in the queue (i.e. if 1, 2 and 4 already exist, it will assign 3) and save the sheet as that next available number. When the sheet is complete, the second macro will save the file with a specified name based on data within the sheet, in another specified location (again based on data defined within the sheet). The drive is in the process of being retired in our company and everything moved to Cloud-based storage, so I would like a way to complete the same actions but using SharePoint directories.
The code for the first macro is as follows:
Dim strDir As String
Dim file As Variant
Dim savename As Integer
Dim savename_string As String
strDir = "R:\Queue\"
savename = 1
savename_string = CStr(savename)
file = Dir(strDir)
While (CInt(savename_string) = savename)
If file <> (savename & ".xlsm") Then
If file = "" Then
savename = savename + 1
Else
file = Dir
End If
ElseIf file = (savename & ".xlsm") Then
savename = savename + 1
savename_string = CStr(savename)
file = Dir(strDir)
End If
Wend
ActiveWorkbook.SaveAs ("R:\Queue\" & savename_string & ".xlsm")
And then the code for the second macro is as follows:
Dim answer As Integer
Dim error As Integer
Dim delete As String
answer = MsgBox("Are you sure you want to save sheet & close?", vbYesNo + vbQuestion, "WARNING")
If answer = vbYes Then
'Define PWO, assembly, terminal, strand, and gauge As Strings, and define which cells they are on the sheet
delete = ActiveWorkbook.Name
ActiveWorkbook.SaveAs ("R:\" & terminal & assembly & Space(1) & gauge & strand & Space(1) & PWO & Space(1) & Format(Now(), "MM-DD-YYYY") & ".xlsm")
Kill ("R:\Queue\" & delete)
ActiveWorkbook.Close
Else
Exit Sub
End If
Currently the second macro works correctly when replacing the locations with the SharePoint URL locations, but when doing the same with the first macro, it returns an error message "Bad file name or number" at the line file = Dir(strDir). Can I get this code in working order, or is there a better way I should go about this? Thanks!
I make entomological specimen labels that come with an embedded QR code. Museum curators can scan the QR codes of a series of specimens in the same group and manipulate data.
The QR code images are inserted as "shapes" (I believe--they respond to shape commands in the macro), generated via VBA code by Jiri Gabriel, with editing by Jonas Heidelberg (https://github.com/JonasHeidelberg/barcode-vba-macro-only).
The macro takes data, populates cells with strings and values (i.e., what gets printed on the human-readable part of the individual labels). When all of the printed text is inserted, the macro iteratively generates one QR code image at a time and places each generated image next to the corresponding human-readable label.
The macro is quick to generate and insert the first few QR code images then gets progressively slower. I presume because Excel is not built to handle a large number of high-resolution images on the same spreadsheet. My sheet design accommodates 220 individual QR code images, but it takes nearly 10 minutes to populate the spreadsheet with 50 QR code images (it takes less than 30 seconds to populate 10 QR code images, so the slowdown is appreciable).
I have tried:
Disable screen updating - does not seem to improve the processing speed
Set calculation to manual - does not seem to improve the processing speed
After generating each QR code image, hide the image by using the following code, and then at the very end, turn all the images visible - seems to help a little bit but not nearly sufficient to make the macro usable at scale.
ActiveSheet.Shapes.SelectAll
Selection.ShapeRange.Visible = False
I looked for solutions to see if the QR code image shapes can be merged into one shape, because after all, wouldn't it be easier to manage a single shape than 200+ individual small shapes? There seems to be no functionality to combine all of the shapes into a single shape.
Another solution I thought about is simultaneously generating all of the QR codes, instead of iteratively, then perhaps it won't have the issue of the later-coming shapes being slow to render due to having to hold all of the previously rendered codes in its memory. I haven't found a way to write the code such that all QR code image shapes are generated in parallel, rather than in sequence.
Another solution I toyed with is to paste the shapes as PNG or some other image that could potentially be easier to deal with, but I get a lot of loss of quality, which seems strange because the QR code should be just a matrix of black and white cells, right? Why do they lose so much quality?
I would suggest an approach based on built in MS Word 2013+ feature (https://support.microsoft.com/en-us/office/field-codes-displaybarcode-6d81eade-762d-4b44-ae81-f9d3d9e07be3). Below is an example of generating 200 QR codes in 10.6 seconds:
Option Explicit
Sub MakeQRcodes()
Const QR_COUNT = 200
Dim fld As Field, tbl As Table, rng As Range
Dim Code As String, i As Integer, t As Single
t = Timer
ThisDocument.Range.Delete
Set tbl = ThisDocument.Tables.Add(Range:=Selection.Range, NumRows:=QR_COUNT, NumColumns:= _
2, DefaultTableBehavior:=wdWord9TableBehavior, AutoFitBehavior:= _
wdAutoFitFixed)
For i = 1 To QR_COUNT
Code = "Insect #" & i ' data can be obtained from Excel spreadsheet
tbl.Cell(i, 1).Range.Text = "QR code for [" & Code & "]:"
Set rng = tbl.Cell(i, 2).Range
rng.Collapse Direction:=wdCollapseStart
Set fld = ThisDocument.Fields.Add(Range:=rng, Type:=wdFieldEmpty, _
Text:="DisplayBarcode """ & Code & """ QR \q 3")
Next i
ThisDocument.ActiveWindow.View.ShowFieldCodes = False
With tbl.Range
.ParagraphFormat.Alignment = wdAlignParagraphCenter
.Cells.VerticalAlignment = wdCellAlignVerticalCenter
End With
Debug.Print "Done " & QR_COUNT & " items in " & Timer - t & " seconds"
End Sub
' Done 200 items in 10,62109 seconds
Result:
Edit2 (VBA Excel code)
Please note that in my experience the DisplayBarcode field works well only with the Latin alphabet. If you have other symbols, check the code on real lines.
Option Explicit
Sub makeQRs()
Dim arr
arr = ThisWorkbook.Sheets("Sheet1").ListObjects("Table1").DataBodyRange.Columns(3)
Call MakeQRcodes(arr)
End Sub
Sub MakeQRcodes(arr) ' arr(n,1)
'you need to add a reference to the "Microsoft Word Object Library" in the Tools-References VBE menu
Dim wd As New Word.Application, doc As Word.Document, fld As Word.Field, tbl As Word.Table, rng As Word.Range
Dim Code As String, i As Integer, QR_count As Integer, t As Single
QR_count = UBound(arr, 1)
t = Timer
wd.Visible = False ' hide the Word app
Set doc = wd.Documents.Add ' create a new Word document
Set tbl = doc.Tables.Add(Range:=doc.Range, NumRows:=QR_count, _
NumColumns:=2, DefaultTableBehavior:=1) 'wdWord9TableBehavior = 1
For i = 1 To QR_count
Code = arr(i, 1)
tbl.Cell(i, 1).Range.Text = "QR code for [" & Code & "]:"
Set rng = tbl.Cell(i, 2).Range
rng.Collapse Direction:=wdCollapseStart
Set fld = doc.Fields.Add(Range:=rng, Type:=-1, _
Text:="DisplayBarcode """ & Code & """ QR \q 3")
Next i
doc.ActiveWindow.View.ShowFieldCodes = False
With tbl.Range ' center text and QR-code in the table cells
.ParagraphFormat.Alignment = 1 'wdAlignParagraphCenter
.Cells.VerticalAlignment = 1 'wdCellAlignVerticalCenter
End With
Application.DisplayAlerts = 0 'wdAlertsNone
With doc
' save the Word doc as .pdf in the same folder as this Excel workbook
.SaveAs2 ThisWorkbook.Path & "\QR.pdf", 17 'wdFormatPDF
.Close False ' close Word document without saving
wd.Quit ' close Word app
End With
Application.DisplayAlerts = -1 'wdAlertsAll
MsgBox "Done " & QR_count & " QR-codes in " & Round(Timer - t, 1) & " seconds," & vbLf _
& "saved in " & ThisWorkbook.Path & "\QR.pdf"
End Sub
Data & result MsgBox
QR.pdf
Once every 3 months we make a file available for our engineers.
This Excel files, pulls data from an Access file and shows it in Excel format.
Since some of this data doesn't change, we don't know whether the engineers haven't looked at it or whether the value isn't changed. What i'm trying to implement is some sort of "confirmation" button so we know the value shown is actually confirmed.
What i'm trying to do is enter an extra column in our access file called "confirmation".
When we pull this data in our excel file, i'm trying to find a way to convert that "confirmation field" into a commandbutton so whenever the data gets pulled, a commandbutton shows up on every line. Whenever the button gets clicked, the data gets saved in our Access file so we know the line is actually confirmed.
Maybe there are some other , easier, ways to do this?
I currently have some code to save excel data in Access but its not working in its current form:
Sub S_SaveDataToDB()
If ActiveSheet.Name = "Estimate" Then
ViKey = 1
Else
ViKey = 2
End If
For i = 1 To ActiveSheet.ListObjects("TB_ACC" & ViKey).ListRows.Count
VsData = "SET [BE] = '" & F_FilterData(ActiveSheet.Cells(7 + i, 17)) & "', [PO STATUS] = '" & F_FilterData(ActiveSheet.Cells(7 + i, 18)) & "', [REMARKS] = '" & F_FilterData(ActiveSheet.Cells(7 + i, 19)) & "', [LOGDATE] = '" & Now() & "', [LOGID] = '" & Environ("Username") & "' WHERE [PO item] = '" & ActiveSheet.Cells(7 + i, 9) & "'"
If Len(F_FilterData(ActiveSheet.Cells(7 + i, 16))) + Len(F_FilterData(ActiveSheet.Cells(7 + i, 17))) + Len(F_FilterData(ActiveSheet.Cells(7 + i, 18))) > 0 Then Call S_UpdateDataInDB(VsData)
Next i
MsgBox "Data has been saved"
and
Sub S_UpdateDataInDB(VsData)
Dim cnDB As New ADODB.Connection
VsDBPath = ThisWorkbook.Sheets("Settings").Range("B2").Value
VsTable = "KCD"
cnDB.Open "Provider=Microsoft.ACE.OLEDB.12.0;" & "Data Source=" & VsDBPath & ";" & "Jet OLEDB:Engine Type=5;" & "Persist Security Info=False;"
cnDB.Execute ("UPDATE " & VsTable & " " & VsData)
cnDB.Close
End Sub
Differences here are:
I want to just save text ("Data confirmed") for that particular cell.
So if one wants to confirm data on Row 8 and clicks "Data confirm". It should only save "Data confirm" for row 8 in access.
Generally, when I'm trying to add a feature to every row in a column, I'll use a hyperlink. It fits neatly into the cell, it can be anchored to a specific cell, and it also shows when it's been followed (the color changes). I've mocked together some code as an example; try to adapt it to your application and let me know if you need help.
First, in a standard module, enter the following code to create the hyperlinks. Presumably, you'd embed this into the code that pulls the data.
Sub PullData()
Dim sh As Worksheet
Dim lastRow As Long
'Pull the data
' DO STUFF
'Identify the range of the pulled data
Set sh = Sheets("PulledData")
lastRow = sh.Range("A" & sh.Rows.Count).End(xlUp).Row
'Loop from row 2 through last row
For i = 2 To lastRow
'Assuming the 'save' option is in Column c
sh.Cells(i, "C").Hyperlinks.Add Anchor:=sh.Cells(i, "C"), Address:="", _
SubAddress:="", TextToDisplay:="Click To Save"
Next i
End Sub
Next, in the worksheet code for the sheet with the data, enter the below code. This tells the application what to do when a hyperlink is clicked. I created a fake function that is meant to mimic saving the data. You can change this as needed, or use a different design if it suits your needs better.
Private Sub Worksheet_FollowHyperlink(ByVal Target As Hyperlink)
'Confirm that this is a hyperlink in column 3
If Not Intersect(Target.Range, Columns(3)) Is Nothing Then
MsgBox SaveData(Target.Range)
End If
End Sub
Private Function SaveData(rng As Range) As Boolean
Debug.Print rng.Address & " has been saved."
SaveData = True
End Function
I have some work to complete where I have 9 tabs of data (some of which contain thousands of lines of data). Each tab contains (amongst others) a policy number, a credit and/or a debit number.
Every policy number will have a match somewhere in the tabs containing an equal credit or debit, e.g.
tab 1 will have Policy number 123 and a credit of £100 and
tab 5 will also have policy number 123 with a debit of £100.
What I'm looking to do is, look through each policy number on every tab and find where the opposite amount is located adding the location address to each policy number.
I'm certainly not looking for anyone to create the coding for me, but what I am looking for is advice. I've looked at using loops but feel this may take a very long time to process. I've also looked at Dictionaries but am relatively new to these so am not very confident.
Is what I'm looking for even possible? And if so any ideas where to start or pointers? Any advice is greatly appreciated. Thanks!
Usage Example
#Matt555, You can test the created XML file with the following code to get the sheet names of policy "123" and debit of 100. I tested the code assuming your titles in row A:A contain "policy" and "debit"
#Peh, You are right, xml dom methods aren't used too often within vba. The advantage of using XML in this connex is a great flexibility in searching via XPath as well as performance over huge files. I prefer it even to arrays or dictionaries when filtering unique values. It is possible to return the found item number in node lists without looping through the whole data set ...
Option Explicit
Sub testPolicy()
Dim policy
Dim debit As Double
policy = "123"
debit = "100"
MsgBox "Policy " & policy & " found in " & vbNewLine & _
findSheetName(policy, debit), vbInformation, "Policy " & policy & " in Tabs"
' You can easily split this to an array and analyze the results
End Sub
Function findSheetName(ByVal policy, Optional ByVal debit) As String
' Purpose: Finds Sheet Names where policy AND/OR debit is found
' Note: Assuming your titles in row A:A contain "policy" and "debit"
' You can declare xDoc also after Option Explicit to make it public
Dim xDoc As Object
Dim xNd As Object ' MSXML.IXMDOMNode
Dim xNdList As Object ' MSXML.IXMLDOMNodeList
Dim s As String
' XPath expression
Dim xPth As String
If IsMissing(debit) Then
xPth = "//row[policy=""" & policy & """]"
Else
xPth = "//row[policy=""" & policy & """][debit=""" & debit & """]"
End If
' XML to memory
Set xDoc = CreateObject("MSXML2.Domdocument.6.0")
' allow XPath
xDoc.setProperty "SelectionLanguage", "XPath"
xDoc.validateOnParse = False
' ========
' LOAD XML
' ========
xDoc.Load ThisWorkbook.Path & "\" & "output.xml"
' Loop thru NodeList
Set xNdList = xDoc.DocumentElement.SelectNodes(xPth)
Debug.Print xPth, xNdList.Length
For Each xNd In xNdList
s = s & xNd.ParentNode.NodeName & "|"
Next xNd
Set xDoc = Nothing
findSheetName = s
End Function
You could
a) create an XML file looping through all sheets,
b) open it via load method and
c) perform a simple XPath search (I can give some examples later)
I modified a recent answer (cf. excel-vba-xml-parsing-performance)
to do step "a)" using late binding thus
a) avoiding a reference to the latest MS XML Version Version 6 (msxml6.dll) and
b) getting data over all xheets. XML allows you structured search via XPath over nodes in a logical structure comparable to HTML. The root node in this example is called data, the following nodes are named with the sheets' names and the subsequent nodes get the names in row A:A of each sheet.
A XML file is a simple text file, which you can open by a text editor. Above all you can use VBA XMLDOM methods to analyze or search through the items (nodes). I will give you examples to relating to your question, but give me some time. => see answer "Usage Example", where I explain some Advantages of XML, too (#Peh).
Please pay Attention to the added notes, too.
Option Explicit
Sub xmlExportSheets()
' Zweck: XML Export over all sheets in workbook
' cf. Site: [excel-vba-xml-parsing-performance][1][https://stackoverflow.com/questions/40986395/excel-vba-xml-parsing-performance/40987237#40987237][1]
' Note: pretty printed raw output with line breaks and indentation using an embedded XSLT stylesheet
On Error GoTo ErrHandle
' A. Declarations
' 1 DECLARE XML DOC OBJECT '
' a) Early Binding: VBA REFERENCE MSXML, v6.0 necessary'
' Dim doc As New MSXML2.DOMDocument60, xslDoc As New MSXML2.DOMDocument60, newDoc As New MSXML2.DOMDocument60
' Dim root As IXMLDOMElement, dataNode As IXMLDOMElement, datesNode As IXMLDOMElement, namesNode As IXMLDOMElement
' b) Late Binding XML Files:
Dim doc As Object
Dim xslDoc As Object
Dim newDoc As Object
' c) Late Binding XML Nodes:
Dim root As Object
Dim sh As Object ' xml node containing Sheet Name
Dim dataNode As Object
Dim datesNode As Object
Dim namesnode As Object
' 2 DECLARE other variables
Dim i As Long
Dim j As Long
Dim tmpValue As Variant
Dim tit As String
Dim ws As Worksheet
' B. XML Docs to Memory
Set doc = CreateObject("MSXML2.Domdocument.6.0")
Set xslDoc = CreateObject("MSXML2.Domdocument.6.0")
Set newDoc = CreateObject("MSXML2.Domdocument.6.0")
' C. Set DocumentElement (= root node)'
Set root = doc.createElement("data")
' D. Create Root Node
doc.appendChild root
' ===========================
' ITERATE THROUGH Sheets
' ===========================
For Each ws In ThisWorkbook.Sheets
Set sh = doc.createElement(ws.Name) '
root.appendChild sh
' ===========================
' ITERATE THROUGH ROWS ' A2:NNn
' ===========================
For i = 2 To ws.UsedRange.Rows.Count ' Sheets(1)
' DATA ROW NODE '
Set dataNode = doc.createElement("row") '
sh.appendChild dataNode
' TABLES NODE (orig.: DATES NODE) '
Set datesNode = doc.createElement(ws.Cells(1, 1)) ' Dates
datesNode.Text = ws.Range("A" & i)
dataNode.appendChild datesNode
' NAMES NODE '
For j = 1 To ws.UsedRange.Columns.Count - 1 ' = 12
tit = ws.Cells(1, j + 1)
tmpValue = ws.Cells(i, j + 1)
Set namesnode = doc.createElement(tit)
namesnode.Text = tmpValue
dataNode.appendChild namesnode
Next j
Next i
Next ws
' =============================
' PRETTY PRINT RAW OUTPUT (XSL)
' =============================
xslDoc.LoadXML "<?xml version=" & Chr(34) & "1.0" & Chr(34) & "?>" _
& "<xsl:stylesheet version=" & Chr(34) & "1.0" & Chr(34) _
& " xmlns:xsl=" & Chr(34) & "http://www.w3.org/1999/XSL/Transform" & Chr(34) & ">" _
& "<xsl:strip-space elements=" & Chr(34) & "*" & Chr(34) & " />" _
& "<xsl:output method=" & Chr(34) & "xml" & Chr(34) & " indent=" & Chr(34) & "yes" & Chr(34) & "" _
& " encoding=" & Chr(34) & "UTF-8" & Chr(34) & "/>" _
& " <xsl:template match=" & Chr(34) & "node() | #*" & Chr(34) & ">" _
& " <xsl:copy>" _
& " <xsl:apply-templates select=" & Chr(34) & "node() | #*" & Chr(34) & " />" _
& " </xsl:copy>" _
& " </xsl:template>" _
& "</xsl:stylesheet>"
' XSLT (Transformation)
xslDoc.async = False
doc.transformNodeToObject xslDoc, newDoc
' =================
' Save the XML File
' =================
newDoc.Save ThisWorkbook.Path & "\Output.xml"
MsgBox "Successfully exported Excel data to " & ThisWorkbook.Path & "\Output.XML!", vbInformation
' Regular End of procedure
Exit Sub
ErrHandle:
MsgBox Err.Number & " - " & Err.Description, vbCritical
Exit Sub
End Sub
Note
Sheet names have to be without spaces
Added Note (important hint):
XML Nodes use titles in first row of every sheet. As the modified procedure gets title names via UsedRange it's important not to have any empty cells in row A:A for this example.
Additional remark
I don't know the reason why my prompt answer (marked as "a") was downgraded by someone. I would find it helpful to argue this :-)
I found a VBA code online that opens up an internal (shared drive) PDF document page in IE (e.g. goes to page 8 of PDF file). I would like to display text in the cell for a user to click (e.g. "Click here to view").
Problem: The cell currently displays '0' and I have to go to the function bar and hit [Enter] to execute.
Excel Version: 2003
Function call:
=GoToPDFpage("S:\...x_2011.pdf",8)
VBA Code:
Function GoToPDFpage(Fname As String, pg As Integer)
Set IE = CreateObject("InternetExplorer.Application")
With IE
.Navigate Fname & "#page=" & pg
.Visible = True
End With
End Function
:EDIT:
I was able to display text, but it's still not a link like I wanted.
="Click to view" & GoToPDFpage("S:\...x_2011.pdf",8)
Thank you for your help.
If you dont have a high complex workbook/worksheet you could try the following:
Turn the "Click to view" cell into a Hyperlink with following characteristics.
Make it point to itself
The text inside the cell must always be the string Page= plus the number that you what the pdf to open in. Eg.: Page=8
Then go to the workseet module and paste the following code:
Private Sub Worksheet_FollowHyperlink(ByVal Target As Hyperlink)
If Left(ActiveCell.Value, 4) = "Page" Then
GoToPDFpage Range("A1").Value, Mid(ActiveCell.Value, 6)
'This code asumes that the file address is writen in the cell A1
End If
'
End Sub
'
The above written code will trigger every time you run a hyperlink in the worksheet.
As the hyperlink always point to itself, the "Activecell.Value" will always have the page number that you want to open.
I'm assuming that you can put the file address in the cell A1. You could modify this portion to point to any other cell. (including: The cell to the right of the current hyperlink, etc).
This might not be the best option, but if you only need a quick feature in a couple of cells, it might be enough.
Hope it helps !
EDIT:
To make each HLink reference to itself, you can select all the cells where you have the links and then run this procedure:
Sub RefHLink()
Dim xCell As Range
For Each xCell In Selection
ActiveSheet.Hyperlinks.Add Anchor:=xCell, Address:="", SubAddress:= _
xCell.Address, ScreenTip:="Click Here", TextToDisplay:="Page="
Next xCell
End Sub
how about letting excel write a batch file then running it?
*edit paths to pdf and AcroRd32.exe
Sub batfile()
Dim retVal
filePath = "path\pdf.bat"
pg = 2
Open filePath For Output As #1
Print #1, "Start /Max /w " & Chr(34) & "Current E-book" & Chr(34) & " " & Chr(34) & "C:\Program Files (x86)\Adobe\Reader 11.0\Reader\AcroRd32.exe" & Chr(34) & " /a " & Chr(34) & "page=" & pg & Chr(34) & " " & Chr(34) & "H:\Documents\RPG\Dragonlance\New folder\Sample File.pdf" & Chr(34) & ""
Close #1
retVal = Shell(strFilePath)
End Sub
Try Menu->Data->Data Validation. In the 2nd tab you can write your message.