Excel VBA - código para pular linhas / comando goto

0

Eu construí um código no excel para pegar os dados de uma tabela dinâmica e inseri-los em um gráfico; um gráfico dinâmico diretamente vinculado à tabela não me dará a manobra que estou procurando. A razão pela qual eu passei pelo problema de criar um código tão "complicado" é que, para cada combinação de Plant e Test Info, eu preciso que seja uma entrada separada no gráfico.

Portanto, o ponto principal deste código é percorrer cada combinação de fábrica e informações de teste (os comandos aninhados) e inserir os dados no gráfico. Meu usuário não irá alterar o local da coluna para xey, então os deslocamentos funcionam bem.

Meu problema é que, se a combinação de informações de fábrica / teste não existir, ela é inserida no gráfico de qualquer maneira. Quando tento usar o comando goto e enviá-lo para o Next PI2 usando um errorhandle, ele não funciona (talvez por causa dos comandos if aninhados). Eu estava olhando em volta tentando encontrar um comando que pudesse enviar meu código para uma linha específica no código (ou seja, logo após os comandos do gráfico), mas não tive sorte ...

Alguém sabe de uma maneira de pular para uma determinada linha em caso de erro?

Eu adicionei o conjunto de comandos para continuar na próxima PI2, onde eu digo no erro goto errhandler, então do errhandler vá para a próxima iteração, mas quando eu executo o código e recebo um erro ele não está passando por essa rota , em vez disso, é parar na linha 'intersect'.

Sub CreatePivotChart()

 Dim PF1 As PivotField
 Dim PI1 As PivotItem
 Dim PI2 As PivotItem
 Dim PF2 As PivotField
 Dim chartcount As Integer
 Dim pt As PivotTable
 Set pt = Worksheets("Pivot Table").PivotTables("PivotTable")

'set up pivot field locations 1 - plant and unit , 2 - test conditions

 Set PF1 = Worksheets("PivotTable").PivotTables("PivotTable").PivotFields("Plant")

 Set PF2 = Worksheets("Pivot Table").PivotTables("PivotTable").PivotFields("Test Info")

 'clear the chart from previous run
  chartcount = 0
  Sheets("Pivot Table Graph").ChartObjects("Chart 1").Chart.ChartArea.ClearContents

  On Error GoTo ErrHandler

 'find each visible unit
  For Each PI1 In PF1.PivotItems

  If PI1.Visible = True Then
     Unit = PI1.Name

     For Each PI2 In PF2.PivotItems

     'for each unit and test condition find the information at their intersection
       If PI2.Visible = True Then
       TC = PI2.Name


    'find the information that corresponds to each unit/test condition combination
    Intersect(pt.PivotFields("Plant").PivotItems(Unit).DataRange.EntireRow, pt.PivotFields("Test Info").PivotItems(TC).DataRange).Select
    Selection.Offset(-1, 0).Select
    ForXRanges = "='Pivot Table'!" & Selection.Address
    Selection.Offset(0, 1).Select
    ForYRanges = "='Pivot Table'!" & Selection.Address
    ForRangesName = Unit & "_" & TC

    'for each combination create a new series on the chart
    chartcount = chartcount + 1
    Sheets("Pivot Table Graph").ChartObjects("Chart 1").Activate
    ActiveChart.SeriesCollection.NewSeries
    ActiveChart.SeriesCollection(chartcount).Name = ForRangesName
    ActiveChart.SeriesCollection(chartcount).XValues = ForXRanges
    ActiveChart.SeriesCollection(chartcount).Values = ForYRanges

End If

NextIteration:
Next PI2

End If
Next PI1

Exit Sub

ErrHandler:
Resume NextIteration:

End Sub
    
por Sarah Hartman 13.06.2016 / 20:23

3 respostas

0

Você pode manipular erros sem goto no VBA assim:

Sub ErrorHandling()
Dim A, d

On Error Resume Next    
REM Line that throws an error
A = A / 0
REM Store details about your error before it gets cleared
d = Err.Description

On Error GoTo 0

REM You see and can handle your error message here
MsgBox d  
End Sub

On Error Resume Next Desativa erros de lançamento

On Error GoTo 0 Ativa erros de lançamento e limpa o objeto Err

    
por 14.06.2016 / 10:43
0

Acabei respondendo às minhas próprias perguntas, continuando a procurar em postagens antigas, etc., encontrei o link ser extremamente útil.

Descobri que eu estava tentando usar dois comandos goto, primeiro para ir para o manipulador de erro e ir para a próxima iteração. O que eu precisava fazer era mudar o segundo goto, para retomar.

Obrigado por todos os ajudantes, o código acima funciona perfeitamente!

    
por 15.06.2016 / 13:37
0

Uma abordagem melhor seria testar seus dados com uma instrução if para garantir que seus dados sejam válidos. Caso contrário, não prossiga com o bloco de códigos que pode gerar um erro.

No seu exemplo, isso pode funcionar ... mudar isso:

'find the information that corresponds to each unit/test condition combination
Intersect(pt.PivotFields("Plant").PivotItems(Unit).DataRange.EntireRow, pt.PivotFields("Test Info").PivotItems(TC).DataRange).Select
Selection.Offset(-1, 0).Select
ForXRanges = "='Pivot Table'!" & Selection.Address
Selection.Offset(0, 1).Select
ForYRanges = "='Pivot Table'!" & Selection.Address
ForRangesName = Unit & "_" & TC

'for each combination create a new series on the chart
chartcount = chartcount + 1
Sheets("Pivot Table Graph").ChartObjects("Chart 1").Activate
ActiveChart.SeriesCollection.NewSeries
ActiveChart.SeriesCollection(chartcount).Name = ForRangesName
ActiveChart.SeriesCollection(chartcount).XValues = ForXRanges
ActiveChart.SeriesCollection(chartcount).Values = ForYRanges

Para isso:

'find the information that corresponds to each unit/test condition combination
Set isect = Application.Intersect(pt.PivotFields("Plant").PivotItems(Unit).DataRange.EntireRow, pt.PivotFields("Test Info").PivotItems(TC).DataRange)

If isect Is Nothing Then 
    'Msgbox "Ranges do not intersect"
Else
    isect.Select 

    Selection.Offset(-1, 0).Select
    ForXRanges = "='Pivot Table'!" & Selection.Address
    Selection.Offset(0, 1).Select
    ForYRanges = "='Pivot Table'!" & Selection.Address
    ForRangesName = Unit & "_" & TC

    'for each combination create a new series on the chart
    chartcount = chartcount + 1
    Sheets("Pivot Table Graph").ChartObjects("Chart 1").Activate
    ActiveChart.SeriesCollection.NewSeries
    ActiveChart.SeriesCollection(chartcount).Name = ForRangesName
    ActiveChart.SeriesCollection(chartcount).XValues = ForXRanges
    ActiveChart.SeriesCollection(chartcount).Values = ForYRanges
End If

Eu não posso testar isso porque não tenho sua pasta de trabalho, mas se ela não funcionar, isso deve demonstrar a abordagem.

    
por 15.06.2016 / 15:30