Finally I found a way to write VISIO MACRO from Visual Studio using Visual Basic.
Refer http://support.microsoft.com/kb/303872
Dim vsoDoc As Microsoft.Office.Interop.Visio.Document
Dim objPrj As Microsoft.Vbe.Interop.VBProject
Dim objModule As Microsoft.Vbe.Interop.VBComponent
Dim CR_LF As String = Chr(10) & Chr(13)
' Create a new Visio application
vsoDoc = Application.Documents.Add("")
' Get VB project object
objPrj = vsoDoc.VBProject
' SetVBComponents
' If VBComponents is 0, append macros to "ThisDocument"
objModule = objPrj.VBComponents(0)
' Define macro
strCode = "Private Sub Document_PageChanged(ByVal Page As IVPage)" & CR_LF & _
"test" & CR_LF & _
"End Sub"
' Write macro to ThisDocument
objModule.CodeModule.AddFromString(strCode)
' SetVBComponents
' If VBComponents is not 0, append macros to other module (e.g., Module1)
objModule = objPrj.VBComponents.Add(VBA.vbext_ComponentType.vbext_ct_Document)
' Define macro
strCode = "sub VBAMacro()" & CR_LF & _
" msgbox ""VBA Macro called""" & CR_LF & _
"end sub"
' Write macro to Module1
objModule.CodeModule.AddFromString(strCode)
P.S When executing above code, I had an error, "Programmatic access to Office VBA project is denied". This error is occurred because Microsoft disables VBA project execution for security purpose. So, to resolve this error, follow guidelines provided by Microsoft.
http://support.microsoft.com/kb/282830
2012년 10월 3일 수요일
2012년 9월 17일 월요일
Error encountered while reading module 'Microsoft.Office.Tools.Common.v9.0
I encountered the following error when I created a Unit Test project in Visual Studio 2008 and tried to add a module to the test project.
The following error was encountered while reading module 'Microsoft.Office.Tools.Common.v9.0': Could not resolve type reference: [office]Microsoft.Office.Core.IRibbonExtensibility.
I instantly got the resolution of the problem at http://blogs.msdn.com/b/tolong/archive/2007/12/02/missing-office-microsoft-office-core-reference.aspx when I googled.
That's easy. Just add COM library, Microsoft Office 12.0 Object Library, to the project.
But I had to struggle to work the unit test project for because I added the COM library to the unit test project instead of my project. I thought the test project needs the library because I didn't have such error when I add/modify my program...
Now, I can use the unit test project in Visual Studio 2008 after add the library my Project rather than the unit test project.
2012년 8월 30일 목요일
Visio SDK - Add Context Menu
To add user-defined features to the context menu, which is a menu shown when users click mouse right button, see the following code fragment.
Basically,
1. Define some variables
' Used in the marker event context string
Public Const CONTEXT_BEGIN_MARKER As String = "/"
Public Const CONTEXT_EVENT As String = "EVENT="
Public Const CONTEXT_SOLUTION As String = "SOLUTION="
Public Const SHAPE_RMA_CONNECTS_COMMAND_ID As Short = 100
Public Const SHAPE_RMA_CONNECTS_COMMAND_ID_STR As String = "100"
Public Const CONTEXT_SDK As String = "SDK"
' Caption of the right menu action item
Public Const RMA_MENU_CAPTION As String = "&Add Attributes"
' Formula of the right menu action item
Public Const RMA_MENU_FORMULA As String = "RUNADDONWARGS(""" & "QueueMarkerEvent"", """ & CONTEXT_BEGIN_MARKER & CONTEXT_EVENT & SHAPE_RMA_CONNECTS_COMMAND_ID_STR & CONTEXT_BEGIN_MARKER & CONTEXT_SOLUTION & CONTEXT_SDK & """)"
3. Add codes to Application_MarkerEvent to catch a event from the context menu and to do something
Private Sub Application_MarkerEvent(ByVal app As Microsoft.Office.Interop.Visio.Application, ByVal SequenceNum As Integer, ByVal ContextString As String) Handles Application.MarkerEvent
If ContextString <> "" And ContextString.Contains("/cmd=DoubleClick") Then
Msgbox( ContextString)
End If
End Sub
Basically,
1. Define some variables
' Used in the marker event context string
Public Const CONTEXT_BEGIN_MARKER As String = "/"
Public Const CONTEXT_EVENT As String = "EVENT="
Public Const CONTEXT_SOLUTION As String = "SOLUTION="
Public Const SHAPE_RMA_CONNECTS_COMMAND_ID As Short = 100
Public Const SHAPE_RMA_CONNECTS_COMMAND_ID_STR As String = "100"
Public Const CONTEXT_SDK As String = "SDK"
' Caption of the right menu action item
Public Const RMA_MENU_CAPTION As String = "&Add Attributes"
' Formula of the right menu action item
Public Const RMA_MENU_FORMULA As String = "RUNADDONWARGS(""" & "QueueMarkerEvent"", """ & CONTEXT_BEGIN_MARKER & CONTEXT_EVENT & SHAPE_RMA_CONNECTS_COMMAND_ID_STR & CONTEXT_BEGIN_MARKER & CONTEXT_SOLUTION & CONTEXT_SDK & """)"
2. Attach following code to each shape
' It doesn't exist yet, so add the right menu
' action item.
intActionRow = Shape.AddRow(Microsoft.Office.Interop.Visio.VisSectionIndices.visSectionAction, Microsoft.Office.Interop.Visio.VisRowIndices.visRowLast, Microsoft.Office.Interop.Visio.VisRowIndices.visRowAction)
' Set the menu caption.
vsoCell = Shape.CellsSRC(Microsoft.Office.Interop.Visio.VisSectionIndices.visSectionAction, intActionRow, Microsoft.Office.Interop.Visio.VisCellIndices.visActionMenu)
' Set our caption string.
strMenuCaption = StringToFormulaForString(RMA_MENU_CAPTION)
vsoCell.FormulaU = strMenuCaption
' Set the action for the menu item.
vsoCell = Shape.CellsSRC(Microsoft.Office.Interop.Visio.VisSectionIndices.visSectionAction, intActionRow, Microsoft.Office.Interop.Visio.VisCellIndices.visActionAction)
vsoCell.FormulaU = RMA_MENU_FORMULA
' Release all objects related to this copy of the master
' before calling close which will delete this copy.
' Failure to do this can cause an exception to be thrown.
'UPGRADE_NOTE: Object vsoCell may not be destroyed until it is garbage collected. Click for more: 'ms-help://MS.VSCC.v90/dv_commoner/local/redirect.htm?keyword="6E35BFF6-CD74-4B09-9689-3E1A43DF8969"'
vsoCell = Nothing
3. Add codes to Application_MarkerEvent to catch a event from the context menu and to do something
Private Sub Application_MarkerEvent(ByVal app As Microsoft.Office.Interop.Visio.Application, ByVal SequenceNum As Integer, ByVal ContextString As String) Handles Application.MarkerEvent
If ContextString <> "" And ContextString.Contains("/cmd=DoubleClick") Then
Msgbox( ContextString)
End If
End Sub
2012년 8월 22일 수요일
Visio SDK - Set a page active
In order to set focus a certain page in Visio, use
Application.ActiveWindow.Page = pageName
In my case, I need to active the first page of Visio whenever new page is added. Thus, following code is added on that purpose.
Application.ActiveWindow.Page = Application.Documents.Item(1).Pages.Item(1).NameU
2012년 8월 21일 화요일
Visio SDK Event Handling - Double Click
First approach...
As there is no event APIs for the Shape Double Click in Visio, I added codes to Application_BeforeShapeTextEdit.
As there is no event APIs for the Shape Double Click in Visio, I added codes to Application_BeforeShapeTextEdit.
Guessing from the event name and behavior of Visio, the API seems to be designed to process something before user edits text of the shape. As of now, the event is work well for my intent.
Although this approach is not perfect solution to get double click event, it is manageable solution.
Second approach
Close to perfect solution.
Add following code to cells of Visio shape
queryString = "=QUEUEMARKEREVENT("" /cmd=DoubleClick /source="
queryString = queryString & Shape.NameU & """)"
Shape.Cells("EventDblClick").Formula = queryString
And then add codes to Application_MarkerEvent
Private Sub Application_MarkerEvent(ByVal app As Microsoft.Office.Interop.Visio.Application, ByVal SequenceNum As Integer, ByVal ContextString As String) Handles Application.MarkerEvent
Dim sourceTag As String
If ContextString <> "" And ContextString.Contains("/cmd=DoubleClick") Then
sourceTag = "/source="
MsgBox("DoubleClick at ShapeID: " + ContextString.Substring(ContextString.IndexOf(sourceTag) + sourceTag.Length))
End If
End Sub
Although this approach is not perfect solution to get double click event, it is manageable solution.
Second approach
Close to perfect solution.
Add following code to cells of Visio shape
queryString = "=QUEUEMARKEREVENT("" /cmd=DoubleClick /source="
queryString = queryString & Shape.NameU & """)"
Shape.Cells("EventDblClick").Formula = queryString
And then add codes to Application_MarkerEvent
Private Sub Application_MarkerEvent(ByVal app As Microsoft.Office.Interop.Visio.Application, ByVal SequenceNum As Integer, ByVal ContextString As String) Handles Application.MarkerEvent
Dim sourceTag As String
If ContextString <> "" And ContextString.Contains("/cmd=DoubleClick") Then
sourceTag = "/source="
MsgBox("DoubleClick at ShapeID: " + ContextString.Substring(ContextString.IndexOf(sourceTag) + sourceTag.Length))
End If
End Sub
2011년 2월 22일 화요일
Visio 2007 Programming: Add master and change its name when new shape is added to a page
This code replace master name with its shape name.
Originally master is named like master.. The following code changes the name, master. to shape name such as Square, Pentagon, and etc.
Private Sub Application_ShapeAdded(ByVal Shape As Microsoft.Office.Interop.Visio.Shape) Handles Application.ShapeAdded
Dim strShapeName As String = ""
Dim nCount As Integer
Dim nMasterCnt As Integer
Dim tempMaster As Visio.Master
Dim tempMasterName As String
' Check whether a same type of shape is already added
' If a same type of shape exists, the name of newly added shape will
' ShapeName.Number. The period mark will be used to determine
' the duplication of shapes and the number represents
' the total number of shapes in the document
strShapeName = Shape.NameU
' Place newly added shape to the stencil as a master
vsoStencil.Drop(Shape, 1, 1)
' Set name for newly added master
' Get the number of masters in the stencil
nMasterCnt = vsoStencil.Masters.Count
For i = 1 To nMasterCnt
tempMaster = vsoStencil.Masters.Item(i)
tempMasterName = tempMaster.Shapes.ItemU(1).NameU
If tempMasterName = Shape.NameU Then
vsoStencil.Masters.ItemU(i).Name = Shape.NameU
End If
Next
End Sub
Originally master is named like master.
Private Sub Application_ShapeAdded(ByVal Shape As Microsoft.Office.Interop.Visio.Shape) Handles Application.ShapeAdded
Dim strShapeName As String = ""
Dim nCount As Integer
Dim nMasterCnt As Integer
Dim tempMaster As Visio.Master
Dim tempMasterName As String
' Check whether a same type of shape is already added
' If a same type of shape exists, the name of newly added shape will
' ShapeName.Number. The period mark will be used to determine
' the duplication of shapes and the number represents
' the total number of shapes in the document
strShapeName = Shape.NameU
' Place newly added shape to the stencil as a master
vsoStencil.Drop(Shape, 1, 1)
' Set name for newly added master
' Get the number of masters in the stencil
nMasterCnt = vsoStencil.Masters.Count
For i = 1 To nMasterCnt
tempMaster = vsoStencil.Masters.Item(i)
tempMasterName = tempMaster.Shapes.ItemU(1).NameU
If tempMasterName = Shape.NameU Then
vsoStencil.Masters.ItemU(i).Name = Shape.NameU
End If
Next
End Sub
2011년 2월 20일 일요일
Visio 2007 Programming: Change stencil title
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.OpenEx("Basic Shapes.vss", _
VisOpenSaveArgs.visOpenDocked + VisOpenSaveArgs.visOpenCopy)
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
End Class
Above code creates a blank document with docked basic shape stencil. However, the title of stencil window is "Stencil 2" and the number is constantly changing whenever a new document is created. So, How do I set the title with a meaningful name?
To solve this problem, add following statement after a document is created or opened.
vsoDoc.Title = "Basic Shapes"
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.OpenEx("Basic Shapes.vss", _
VisOpenSaveArgs.visOpenDocked + VisOpenSaveArgs.visOpenCopy)
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
End Class
Above code creates a blank document with docked basic shape stencil. However, the title of stencil window is "Stencil 2" and the number is constantly changing whenever a new document is created. So, How do I set the title with a meaningful name?
To solve this problem, add following statement after a document is created or opened.
vsoDoc.Title = "Basic Shapes"
Visio 2007 Programming: Create new document with basic shape stencil
Following skeleton codes are generated through "New Project" -> Visual Basic -> Visio Add-in.
Public Class ThisAddIn
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
End Class
1. Import Visio Interoperability reference before the class definition and define a variable, vsoDoc for Visio document.
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.OpenEx("Basic Shapes.vss", _
VisOpenSaveArgs.visOpenDocked + VisOpenSaveArgs.visOpenCopy)
P.S Test following codes and see the difference with the above codes
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.add("Basic Shapes.vss")
Public Class ThisAddIn
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
End Class
1. Import Visio Interoperability reference before the class definition and define a variable, vsoDoc for Visio document.
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
2. Add codes of Visio document creation in ThisAddIn_Startup()
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.OpenEx("Basic Shapes.vss", _
visOpenDocked + visOpenCopy)
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
3. To resolve errors with the flags visOpenDocked and visOpenCopy, append VisOpenSaveArgs to each flag. If VisOpenSaveArgs is not used, Visual Studio shows errors such as "Name 'visOpenDocked' is not declared."
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.OpenEx("Basic Shapes.vss", _
visOpenDocked + visOpenCopy)
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
3. To resolve errors with the flags visOpenDocked and visOpenCopy, append VisOpenSaveArgs to each flag. If VisOpenSaveArgs is not used, Visual Studio shows errors such as "Name 'visOpenDocked' is not declared."
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs ) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.OpenEx("Basic Shapes.vss", _
VisOpenSaveArgs.visOpenDocked + VisOpenSaveArgs.visOpenCopy)
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
P.S Test following codes and see the difference with the above codes
Imports Microsoft.Office.Interop.Visio
Public Class ThisAddIn
Private vsoDoc As Visio.Document
Private Sub ThisAddIn_Startup(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Startup
vsoDoc = Application.Documents.Add("")
vsoDoc = Application.Documents.add("Basic Shapes.vss")
End Sub
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
End Class
Private Sub ThisAddIn_Shutdown(ByVal sender As Object, _
ByVal e As System.EventArgs) _
Handles Me.Shutdown
End Sub
End Class
피드 구독하기:
글 (Atom)

