簡體   English   中英

如何引用具有相同名稱但在不同工作表上的圖表?

[英]How do I reference charts with the same name, but on different worksheets?

我有兩個包含圖表的工作表,並使用宏來運行包含圖表的所有工作表並更新圖表中的值。

但是,在嘗試在第一個工作表之后引用工作表中的圖表時遇到問題 - 盡管工作表的引用發生了更改,但對圖表的引用卻沒有。

循環看起來像這樣:

For Each ws In ThisWorkbook.Worksheets
  Debug.Print ws.Name
  Debug.Print ws.ChartObjects("Kortsone").Chart.Name
  With ws.ChartObjects("Kortsone").Chart
    ...
  End With
Next ws

我到達即時窗口的輸出如下:

Grafar ovn 3
Grafar ovn 3 Kortsone
Grafar ovn 4
Grafar ovn 3 Kortsone

正如您所看到的對工作表的引用更改,但圖表引用沒有。

有沒有辦法解決這個問題,還是我必須用獨特的名稱重命名我的所有圖表?

我正在使用Excel 2013

- 編輯 -我現在已根據評論中的建議進行了一些測試,看來打印到即時窗口的內容取決於當前活動工作表的內容。

嘗試使用for each chartobject遇到了與之前相同的問題:

Sub test2()
  Dim ws As Worksheet
  Dim ch As ChartObject

  For Each ws In ThisWorkbook.Worksheets
    For Each ch In ws.ChartObjects
      If ws.CodeName = "Graf4" Then
      Debug.Print ws.Name
      Debug.Print ch.Name
      Debug.Print ch.Chart.Name
      End If
    Next ch
  Next ws
End Sub

放棄:

Grafar ovn 4
Kortsone
Grafar ovn 3 Kortsone
Grafar ovn 4
Langsone
Grafar ovn 3 Langsone
...

正如您所發現的, Workheet.ChartObjects方法將找到正確的ChartObject,但訪問Chartobject.Chart屬性將返回ActiveSheet的圖表。 如果按名稱或索引號引用ChartObject,則無關緊要。

如果使用Worksheet.Shapes方法查找ChartObject,則行為相同。

此行為與早期版本的Excel不同。 我確認代碼在Excel XP / 2002中有效,並且在2016年不起作用。我不確定行為何時發生變化。 它可能是2013年,或者它可能是2013年和2016年的補丁? Office for Mac 2016中的行為是相同的(即。不起作用)

在Microsoft提出修復之前,您必須訪問Chart屬性之前激活工作表或激活ChartObject。

Sub test()
  Dim ws As Worksheet
  Dim co As ChartObject
  For Each ws In ThisWorkbook.Worksheets
    Debug.Print ws.Name
    Set co = ws.ChartObjects("Kortsone")

    ws.Activate
    'or
    co.Activate

    Debug.Print co.Chart.Name
    With ws.ChartObjects("Kortsone").Chart
    End With
  Next ws
End Sub

我建議您暫時禁用ScreenUpdating,並在完成后重新激活原始活動表。

GetChart將返回特定工作表上的圖表對象。

getChart將圖表對象存儲在Static Collection Static Collection將保留在內存中,直到代碼中斷或工作簿關閉。

第一次調用getChart所有圖表對象時,所有工作表都會被激活,每個工作表上的每個圖表都會添加到集合中。 之后,圖表只是在靜態集合中查找。

如果圖表(例如在調用函數后添加了圖表)不在集合中,則函數將自行重新加載。

獲取圖表

Function getChart(ChartName As String, WorkSheetName As String, Optional Reload As Boolean) As Chart
    Dim ws As Worksheet, ActiveWS As Worksheet
    Dim co As ChartObject
    Static ChartCollection As Collection

    If ChartCollection Is Nothing Or Reload Then
        Application.ScreenUpdating = False

        Set ChartCollection = New Collection
        Set ActiveWS = ActiveSheet
        For Each ws In ThisWorkbook.Worksheets
            ws.Activate
            For Each co In ws.ChartObjects
                ChartCollection.Add co.Chart, ws.Name & "!" & co.Name
            Next
        Next ws

        ActiveWS.Activate
        Application.ScreenUpdating = True
    End If

    On Error Resume Next
    Set getChart = ChartCollection(WorkSheetName & "!" & ChartName)

    If Err.Number <> 0 And Not Reload Then Set getChart = getChart(ChartName, WorkSheetName, True)

    On Error GoTo 0

End Function

測試

Sub Test()
    Dim ws As Worksheet
    Dim ch As Chart
    Dim msg As String
    Dim Start: Start = Timer

    For Each ws In ThisWorkbook.Worksheets
        Set ch = getChart("Kortsone", ws.Name)
        If Not ch Is Nothing Then

            msg = msg & ws.Name & "!" & ch.Name & " - Validated:" & (ws.Name = ch.Parent.Parent.Name) & vbCrLf

        End If
    Next ws
    msg = msg & "Time in Seconds: " & Timer - Start
    MsgBox msg
End Sub

ChartWorksheet.ChartObject.Chart之間存在差異。

說清楚

  • 工作表中創建圖表 ,Excel會創建ChartObject以包含Chart 因此, ChartChildObject的子代,而ChildObject又是Worksheet的子代。
  • 當您將圖表創建為工作表時,它是一個Chart (或者您可以稱之為“圖表工作表”),等同於Worksheet

因此, Worksheet.ChartObject.ChartChart Worksheet.ChartObject.Chart的不同之處如下:

  • Worksheet.ChartObject.Chart中的Chart包含Chart所有屬性。
  • Chart表包含Chart所有屬性和工作表的某些屬性。

因此.Name屬性應該用於Chart表,但不適用於Worksheet.ChartObject.Chart

我說在調用ChartObject.Chart.Name時附加顯示活動表名稱不是錯誤,而是調試錯誤。 ChartObject.Chart首先不會也不應該有一個Name 您可以調用ChartObject.Chart.Name因為Chart對象模型的intellisense中存在重疊。 如果微軟不允許這樣做,就會有一個錯誤。

簡而言之,請記住圖表沒有名稱,它是ChartObject或帶有名稱的Sheet 相比之下,圖表有ChartTitle

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM