【问题标题】:Get name of parent shape when click on a child shape单击子形状时获取父形状的名称
【发布时间】:2021-09-08 21:35:00
【问题描述】:

我有 2 个名为“Group1”和“Group2”的分组形状,每个包含 2 个名为“Rectangle1”和“Rectangle2”的形状。

当我在任意两个分组形状中单击“Rectangle1”时,它总是返回“Group1”(按顺序排在第一位)。

是否有返回特定子形状的分组形状名称而不更改其名称?

谢谢。

Public Sub ReturnParentName()
   Dim shp as Shape

   Set shp = ActiveSheet.Shapes(Application.Caller).ParentGroup
   MsgBox shp.Name
End Sub

【问题讨论】:

  • .Name 将返回子形状名称而不是父名称。
  • 您在什么情况下尝试在讨论中返回名称?在分配给组特定形状的子中?否则,Applicatin.Caller 不会返回任何内容。
  • 我有许多子形状分配给同一个公共子。
  • 所以,隐含的答案是肯定的,在讨论中的形状调用的子中......这种理解正确吗?如果是,请查看我发布的答案。
  • 是的,没错。

标签: excel vba


【解决方案1】:

请用这种方式试试:

Sub CommonProcedure_Click()
   Debug.Print Application.Caller 'the shape name
   Debug.Print ActiveSheet.Shapes(Application.Caller).Parent.Name      'the sheet keeping the shape/group name
   If ActiveSheet.Shapes(Application.Caller).Child Then
        Debug.Print ActiveSheet.Shapes(Application.Caller).ParentGroup.Name
    Else
        Debug.Print "Not in a group..."
    End If
End Sub

为了自动更改同名形状的名称,您可以使用下一个代码。它需要添加对“Microsoft Scripting Runtime”的引用。可以使用后期绑定来完成,但我认为应该受益于智能感知建议:

Sub changeShapesSameName()
   Dim sh As Shape, shG As Shape, dict As New Scripting.dictionary
   For Each sh In ActiveSheet.Shapes
       If sh.Type = 6 Then
            For Each shG In sh.GroupItems
                    If Not dict.Exists(shG.Name) Then
                        dict.Add shG.Name, shG.Id
                    Else
                        If dict(shG.Name) <> shG.Id Then shG.Name = shG.Name & shG.Id
                        dict.Add shG.Name, shG.Id 'only to see the sheets balance at the end
                    End If
            Next
       Else
            If Not dict.Exists(sh.Name) Then
                    dict.Add sh.Name, sh.Id
            Else
                    If dict(sh.Name) <> sh.Id Then sh.Name = sh.Name & sh.Id
                    dict.Add sh.Name, sh.Id       'only to see the sheets balance at the end
            End If
       End If
   Next
   Debug.Print dict.count            'total number of individual shapes
   Debug.Print Join(dict.Keys, "|")  'dictionary keys (all shapes name)
   Debug.Print Join(dict.items, ":") 'dictionary items (all shapes IDs)
End Sub

如果还没有添加必要的引用,接下来的代码会自动添加:

Sub addScrRunTimeRef()
  'Add a reference to 'Microsoft Scripting Runtime':
  'In case of error ('Programmatic access to Visual Basic Project not trusted'):
  'Options->Trust Center->Trust Center Settings->Macro Settings->Developer Macro Settings->
  '         check "Trust access to the VBA project object model"
  On Error Resume Next
  Application.VBE.ActiveVBProject.References.AddFromFile "C:\Windows\SysWOW64\scrrun.dll"
  If err.Number = 32813 Then
        err.Clear: On Error GoTo 0
        MsgBox "The reference already exists...": Exit Sub
  Else
        On Error GoTo 0
        MsgBox """Microsoft Scripting Runtime"" reference added successfully..."
  End If
End Sub

【讨论】:

  • .ParentGroup.Name 始终返回“Group1”,即使单击的形状是“Group2”中的“Rectangle1”。如果我将 2 个分组形状重新排序以使“Group2”低于“Group1”,它将始终返回“Group2”。
  • @user3286479 仅当有更多形状具有相同名称。这是你工作表中的现实吗?
  • 是的。每个组都包含一个同名“Rectangle1”的形状。是否有任何解决方法可以在不更改其中一个名称的情况下解决此问题?
  • @user3286479 恐怕不是。代码根据活动工作表中的形状名称定义对象。从理论上讲,它返回与名称匹配的第一个对象,或者一个形状数组。我无法重现这种情况。你能在讨论中分享工作簿吗?或者尝试解释你是如何“成功”为同一张纸上的形状命名的?我做不到......从理论上讲,Excel 一定不允许这样做,但我听说在某些情况下会这样做。我无法重现您的情况。
  • 我使用Excel 2016,在同一个工作表中为多个形状定义相同的名称没有问题。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-07-28
  • 1970-01-01
  • 1970-01-01
  • 2017-10-04
  • 2020-08-30
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多