7. Tips/Visual Studio

[Visual Studio .NET 2005] 매크로 : 주석 & 솔루션 탐색기 검색

SSKK 2009. 2. 19. 13:38
Visual Studio 2005 에서 사용하는 매크로입니다.

1. C++에서 클래스 및 함수에 대해 Doxygen 스타일의 주석 템플릿을 생성합니다. 함수 정의 부를 선택하거나, 클래스 선언부를 선택하여 MakeCommentForDoxygen 매크로를 수행하면 됩니다.

2. 현재 활성화된 파일을 솔루션에서 찾고자 하는 경우에 FindInSolutionExplorer 매크로를 수행하면 바로 찾아갑니다. 이 기능은 옵션에서 항상 켜지게 해놓을 수도 있으나 그렇게 하면 저에게는 가끔 여러모로 불편하므로 그 기능을 Off 시켜놓고 이 매크로를 사용합니다.

-> 이 기능은 다음 링크를 참고하자. 



Imports System
Imports EnvDTE
Imports EnvDTE80
Imports EnvDTE90

Public Module Utilities
    Public Sub TrackProjectItem()
        Dim solution As Solution2 = DTE.Solution
        If Not solution.IsOpen OrElse DTE.ActiveDocument Is Nothing Then Return

        solution.FindProjectItem(DTE.ActiveDocument.FullName).ExpandView()

        Dim FileName As String = DTE.ActiveDocument.FullName

        Dim SolutionExplorerPath As String
        Dim items As EnvDTE.UIHierarchyItems = DTE.ToolWindows.SolutionExplorer.UIHierarchyItems
        Dim item As Object = FindItem(items, FileName, SolutionExplorerPath)

        If item Is Nothing Then
            MsgBox("Couldn't find the item in Solution Explorer.")
            Return
        End If

        DTE.Windows.Item(Constants.vsWindowKindSolutionExplorer).Activate()
        DTE.ActiveWindow.Object.GetItem(SolutionExplorerPath).Select(vsUISelectionType.vsUISelectionTypeSelect)
    End Sub

    Public Function FindItem(ByVal Children As UIHierarchyItems, ByVal FileName As String, ByRef SolutionExplorerPath As String) As Object
        For Each CurrentItem As UIHierarchyItem In Children
            Dim TypeName As String = Microsoft.VisualBasic.Information.TypeName(CurrentItem.Object)
            If TypeName = "ProjectItem" Then
                Dim projectitem As EnvDTE.ProjectItem = CType(CurrentItem.Object, EnvDTE.ProjectItem)
                Dim i As Integer = 1
                While i <= projectitem.FileCount
                    If projectitem.FileNames(i) = FileName Then
                        SolutionExplorerPath = CurrentItem.Name
                        Return CurrentItem
                    End If
                    i = i + 1
                End While
            End If

            Dim ChildItem As UIHierarchyItem = FindItem(CurrentItem.UIHierarchyItems, FileName, SolutionExplorerPath)
            If Not ChildItem Is Nothing Then
                SolutionExplorerPath = CurrentItem.Name + "\" + SolutionExplorerPath
                Return ChildItem
            End If
        Next
    End Function
End Module




 Imports System
Imports EnvDTE
Imports EnvDTE80
Imports System.Diagnostics

Public Module Module1

    Function InsertNewLine(ByRef doc As Document, ByVal str As String)

        doc.Selection.NewLine()

        doc.Selection.StartOfLine()

        doc.Selection.Text = str

    End Function

    Enum DocType
        CPPSOURCE = 0
        CPPHEADER = 1
        RESOURCE = 2
        ETC = 3
    End Enum

    Function GetDocType(ByVal strName As String) As DocType
        Dim strUpperName As String
        strUpperName = UCase(strName)

        If InStr(strUpperName, UCase(".h")) > 0 Then
            GetDocType = DocType.CPPHEADER
        ElseIf InStr(strUpperName, UCase(".cpp")) > 0 Then
            GetDocType = DocType.CPPSOURCE
        Else
            GetDocType = DocType.ETC
        End If
    End Function

    Function GetHItemsType(ByVal strName As String) As DocType
        Dim strUpperName As String
        strUpperName = UCase(strName)
        If strUpperName = UCase("Source Files") Then
            GetHItemsType = DocType.CPPSOURCE
        ElseIf strUpperName = UCase("Header files") Then
            GetHItemsType = DocType.CPPHEADER
        ElseIf strUpperName = UCase("Resource Files") Then
            GetHItemsType = DocType.RESOURCE
        Else
            GetHItemsType = DocType.ETC
        End If
    End Function

    Function SelectItem(ByRef win As Window, ByRef UIChildItemList As UIHierarchyItems, ByRef doc As Document) As Boolean
        Dim uiProjectItem As UIHierarchyItem
        Dim blExpanded As Boolean

        Dim UISolutionItem As UIHierarchyItem
        UISolutionItem = UIChildItemList.Item(1)

        For Each uiProjectItem In UISolutionItem.UIHierarchyItems
            If uiProjectItem.UIHierarchyItems.Count <> 0 Then
                If (uiProjectItem.Name = doc.ProjectItem.ContainingProject.Name) Then

                    Dim uiSubItem As UIHierarchyItem
                    For Each uiSubItem In uiProjectItem.UIHierarchyItems
                        Dim type1 As DocType
                        Dim type2 As DocType

                        type1 = GetDocType(doc.Name)
                        type2 = GetHItemsType(uiSubItem.Name)

                        If type1 = type2 Then
                            Dim uiItem As UIHierarchyItem
                            For Each uiItem In uiSubItem.UIHierarchyItems
                                If uiItem.Name = doc.Name Then
                                    win.Activate()
                                    uiItem.Select(vsUISelectionType.vsUISelectionTypeSelect)
                                    GoTo END_SELECTITEM
                                End If
                            Next
                        End If
                    Next

                    GoTo END_SELECTITEM
                End If
            End If
        Next
END_SELECTITEM:
    End Function

    Sub FindInSolutionExplorer()
        Dim lCount As Long
        Dim i As Long
        Dim win As Window
        lCount = Application.Windows.Count

        Dim w1 As Window
        w1 = DTE.Windows.Item(Constants.vsWindowKindSolutionExplorer)

        Dim doc As Document
        doc = ActiveDocument

        Dim UIHItem As UIHierarchy
        Dim file As UIHierarchyItem

        UIHItem = w1.Object

        SelectItem(w1, UIHItem.UIHierarchyItems, doc)
    End Sub

 

    Function GetParam(ByVal str As String) As String

        Dim iIndexFound As Integer

        Dim strTemp As String

 

        strTemp = Trim(str)

        iIndexFound = InStr(str, " ", CompareMethod.Text)

        If iIndexFound > 0 Then

            GetParam = Trim(Right(strTemp, Len(strTemp) - iIndexFound))

        Else

            GetParam = strTemp

        End If

    End Function

 

    Function RemoveComment(ByVal str As String) As String

        Dim iCommentPrefixFound As Integer

        Dim iCommentPostfixFound As Integer

        Dim strTemp As String

 

        RemoveComment = str

        iCommentPrefixFound = InStr(RemoveComment, "/*", CompareMethod.Text)

        While iCommentPrefixFound > 0

            strTemp = Right(RemoveComment, Len(RemoveComment) - iCommentPrefixFound + 1)

            iCommentPostfixFound = InStr(strTemp, "*/", CompareMethod.Text)

            If iCommentPostfixFound > 0 Then

                RemoveComment = Left(RemoveComment, iCommentPrefixFound - 1)

                strTemp = Right(strTemp, Len(strTemp) - iCommentPostfixFound - 1)

                RemoveComment = RemoveComment & strTemp

            Else

                RemoveComment = Left(RemoveComment, iCommentPrefixFound - 1)

                Exit While

            End If

            iCommentPrefixFound = InStr(RemoveComment, "/*", CompareMethod.Text)

        End While

 

    End Function

 

    Sub MakeCommentForDoxygen()

        Dim strDelimFormat As String = "//////////////////////////////////////////////////////////////////////////"

        Dim strBriefFormat As String = "/// @brief" & CStr(Chr(9)) & CStr(Chr(9))

        Dim strAuthorFormat As String = "/// @author" & CStr(Chr(9)) & CStr(Chr(9))

        Dim strVersionFormat As String = "/// @version" & CStr(Chr(9)) & "v1.0"

        Dim strDateFormat As String = "/// @date" & CStr(Chr(9)) & CStr(Chr(9))

        Dim strRemarkFormat As String = "/// @remark" & CStr(Chr(9)) & CStr(Chr(9))

        Dim strReturnFormat As String = "/// @return" & CStr(Chr(9)) & CStr(Chr(9))

        Dim strParamFormat As String = "/// @param" & CStr(Chr(9))

        Dim FuncAll As String = DTE.ActiveDocument.Selection.Text

        Dim iIndexFound As Integer

        Dim strTemp As String

        Dim strInput As String

        Dim strClass As String = "Class"

        Dim currentDate As Date

 

        Dim strBriefDesc As String

 

        FuncAll = RemoveComment(FuncAll)    ' /* */ 로 끝나는 주석을 제거함.

 

        ' 선택된 텍스트를 가져옴

        FuncAll = FuncAll.Replace(CStr(CStr(Chr(9))), " ")

        FuncAll = Trim(FuncAll.Replace(CStr(vbCrLf), ""))

 

        Dim curDocument As Document

        curDocument = ActiveDocument   ' 현재 다큐먼트를 저장

 

 

        ' 클래스인지 함수 인지 검사

        iIndexFound = InStr(UCase(FuncAll), UCase(strClass), CompareMethod.Text)

        Dim iTemp As Integer

        iTemp = iIndexFound - 1

        If iTemp > 0 Then

            strTemp = Mid(FuncAll, iIndexFound - 1, 1)  ' class 키워드 앞에 다른 문자가 붙으면 클래스가 아님.

            If strTemp <> " " Then

                iIndexFound = 0

            End If

        End If

 

        If iIndexFound > 0 Then ' 클래스이다

            strTemp = Right(FuncAll, FuncAll.Length - iIndexFound - Len(strClass) + 1)

            iIndexFound = InStr(strTemp, ":", CompareMethod.Text)

            If (iIndexFound > 0) Then

                strTemp = Left(strTemp, iIndexFound - 1)

                strTemp = Trim(strTemp)

            End If

 

            If strTemp.Length <> 0 Then

                ' 클래스 주석을 추가하자

                ' 입력을 먼저 받고 입력이 있을 경우에만 아래를 추가하자

                ' Brief

                'strInput = InputBox("Insert a brief into " & strTemp)        ' 현재 strTemp는 클래스 명이다

                'strTemp = Trim(strInput)

                'If strTemp.Length = 0 Then

                '    Exit Sub

                'End If

 

                ' Delimitor

                curDocument.Selection.GotoLine(curDocument.Selection.TopLine)

                curDocument.Selection.StartOfLine(EnvDTE.vsStartOfLineOptions.vsStartOfLineOptionsFirstText)

                InsertNewLine(curDocument, strDelimFormat)

 

                ' brief 추가

                strBriefDesc = strBriefFormat & strInput

                InsertNewLine(curDocument, strBriefDesc)

 

                ' version

                InsertNewLine(curDocument, strVersionFormat)

 

                ' Date

                currentDate = Date.Now

                strTemp = strDateFormat & Trim(CStr(currentDate.Year())) & "/" & Trim(CStr(currentDate.Month())) & "/" & Trim(CStr(currentDate.Day()))

                InsertNewLine(curDocument, strTemp)

 

                ' Author

                strTemp = System.Security.Principal.WindowsIdentity.GetCurrent().Name()

                iIndexFound = InStr(strTemp, "\", CompareMethod.Text)

                If iIndexFound > 0 Then

                    strTemp = Right(strTemp, Len(strTemp) - iIndexFound)

                End If

                strTemp = strAuthorFormat & strTemp

                InsertNewLine(curDocument, strTemp)

 

                ' Delimitor

                InsertNewLine(curDocument, strDelimFormat)

                curDocument.Selection.NewLine()

            End If

        Else    ' 함수인지 검사

            iIndexFound = InStr(FuncAll, "(", CompareMethod.Text)

            If iIndexFound > 0 Then

                Dim strFunc As String

                Dim strReturn As String

                Dim strParams As String

                Dim strReturnDesc As String

 

                strFunc = Left(FuncAll, iIndexFound - 1)    ' 괄호앞 전체

                strTemp = Right(FuncAll, Len(FuncAll) - iIndexFound)   ' 괄호 이후 뒤쪽

 

                ' strFunc에서 반환값 추출

                iIndexFound = InStrRev(strFunc, " ", -1, CompareMethod.Text)

                If iIndexFound > 0 Then

                    strReturn = Trim(Left(strFunc, iIndexFound))

                Else

                    strReturn = ""

                End If

 

                iIndexFound = InStr(strTemp, ")", CompareMethod.Text)

                If iIndexFound > 0 Then

                    strParams = Trim(Left(strTemp, iIndexFound - 1))

 

                    Dim strParamList As String()

                    Dim strParamDesc As String()

                    Dim iParamCount As Integer = 0

                    Dim iCount As Integer

 

                    ' 파라미터 갯수 파악하기

                    If Len(strParams) <> 0 Then

                        strTemp = strParams

 

                        iIndexFound = InStr(strTemp, ",", CompareMethod.Text)

                        If iIndexFound > 0 Then

                            ' 파라미터가 1개 이상이다

 

                            ' 콤마 갯수를 센 후에 어레이를 잡고 파라미터를 대입하자 (무식하지만 귀찮다)

                            Dim iCommaCount As Integer = 0

                            While iIndexFound > 0

                                iCommaCount = iCommaCount + 1

                                strTemp = Right(strTemp, Len(strTemp) - iIndexFound)

                                iIndexFound = InStr(strTemp, ",", CompareMethod.Text)

                            End While

 

                            iParamCount = iCommaCount + 1

                            ReDim strParamList(iParamCount)

                            strTemp = strParams

                            iIndexFound = InStr(strTemp, ",", CompareMethod.Text)

                            iCount = 1

                            While iIndexFound > 0

                                strParamList(iCount) = Trim(Left(strTemp, iIndexFound - 1))

                                strTemp = Right(strTemp, Len(strTemp) - iIndexFound)

                                iIndexFound = InStr(strTemp, ",", CompareMethod.Text)

                                iCount = iCount + 1

                            End While

 

                            strParamList(iCount) = Trim(strTemp)

 

                        Else

                            iParamCount = 1

                            ReDim strParamList(iParamCount)

                            strParamList(iParamCount) = strTemp

                        End If

                    End If

 

                    ' Brief 얻기

                    'strBriefDesc = InputBox("Insert a brief into " & strFunc)

                    'If Len(strBriefDesc) = 0 Then

                    '    Exit Sub

                    'End If

 

                    ReDim strParamDesc(iParamCount)

                    ' 파라미터에 대한 brief 얻기

                    'For iCount = 1 To iParamCount

                    '    If iParamCount <> 1 Or UCase(strParamList(1)) <> "VOID" Then

                    '        strParamDesc(iCount) = InputBox("Insert a brief into " & strParamList(iCount))

                    '    End If

                    'Next iCount

 

                    ' Return에 대한 brief 얻기

                    'If Len(strReturn) <> 0 And UCase(strReturn) <> "VOID" Then

                    '    strReturnDesc = InputBox("Inser a brief into the return value")

                    'End If

 

                    ' Delimitor

 

                    curDocument.Activate()

                    curDocument.Selection.GotoLine(curDocument.Selection.TopLine)

                    curDocument.Selection.StartOfLine(EnvDTE.vsStartOfLineOptions.vsStartOfLineOptionsFirstText)

                    InsertNewLine(curDocument, strDelimFormat)

 

                    ' brief 추가

                    strBriefDesc = strBriefFormat & strBriefDesc

                    InsertNewLine(curDocument, strBriefDesc)

 

                    ' 파라미터에 대한 정보 추가

                    For iCount = 1 To iParamCount

                        If iParamCount <> 1 Or UCase(strParamList(1)) <> "VOID" Then

                            strTemp = GetParam(strParamList(iCount))

                            strTemp = strParamFormat & strTemp & CStr(Chr(9)) & strParamDesc(iCount)

                            InsertNewLine(curDocument, strTemp)

                        End If

                    Next

 

                    If Len(strReturn) <> 0 And UCase(strReturn) <> "VOID" Then

                        ' Return 추가

                        strReturnDesc = strReturnFormat & strReturnDesc

                        InsertNewLine(curDocument, strReturnDesc)

                    End If

 

                    InsertNewLine(curDocument, strRemarkFormat)

 

                    ' Delimitor

                    InsertNewLine(curDocument, strDelimFormat)

 

                    curDocument.Selection.NewLine()

                    curDocument.Selection.StartOfLine()

                End If

            End If

        End If

 

        curDocument.Save()

 

        'Temp = FuncAll.IndexOf("(")

        'If Temp < 0 Then Exit Sub

 

    End Sub

 

End Module