• ベストアンサー

ShapeのVBAの中での取り扱い

ShapeのVBAの中での取り扱いに関して、サジェスチョン願います。 Shapeに文字が書き込まれていない段階で、選択して文字を読み込み判定しようとするとエラーとなります。 下記のVBAでは、5番目のShapeが該当します。 このエラーを防ぐためには、On Error Resume Nextが有効ですが、他の方法を探しています。例えば、charactor=trueみたいなもの。 ----- Sub Shapeの調査() Dim nametemp(10) As String Dim temp As Integer Dim i As Integer Dim aaa As Variant 'On Error Resume Next ActiveSheet.Shapes.AddShape(msoShapeRectangle, 50, 50, 50, 50).Select ActiveSheet.Shapes.AddShape(msoShapeOval, 100, 100, 50, 50).Select ActiveSheet.Shapes.AddTextbox(msoTextOrientationHorizontal, 150, 150, 50, 50).Select ActiveSheet.Shapes.AddShape(msoShapeRectangle, 200, 200, 50, 50).Select ActiveSheet.Shapes.AddShape(msoShapeOval, 250, 250, 50, 50).Select temp = ActiveSheet.Shapes.Count For i = 1 To temp ActiveSheet.Shapes(i).Select nametemp(i) = ActiveSheet.Shapes(i).Name Next For i = 1 To temp / 2 + 1 '4つのshapeに対し、文字を書き込もうとする ActiveSheet.Shapes(nametemp(i)).Select Selection.Characters.Text = "" Next For i = 1 To temp / 2 '3つに対して、文字を書き込む ActiveSheet.Shapes(nametemp(i)).Select Selection.Characters.Text = "zzzzz" Next For i = 1 To temp ActiveSheet.Shapes(nametemp(i)).Select aaa = Selection.Characters.Text '<--5番目のShapeに対し If aaa = "zzzzz" Then MsgBox (aaa)'<--errorとなる。 Next End Sub

質問者が選んだベストアンサー

  • ベストアンサー
  • Wendy02
  • ベストアンサー率57% (3570/6232)
回答No.3

こんにちは。 >エラーは、これ以外にも起き得るというのが、On Error Resume Nextを使いたくない理由です。 おっしゃっている意味が良く分りません。 実行時エラーは、内容がどんなであれ、あくまでも、エラーとして、実行コードとしての要件には満たしません。今回は、これでよいのかもしれませんが、エラー番号で判定し処理するのは、エラー処理ルーチンを使う場合です。これは、On Error Resume Nextよりも、もう一段レベルの高い技術です。 どのように On Error Resume Next を想像しているか分りませんが、プロシージャー内の行頭で、On Error Resume Next をポンと置いて、これで安泰だっていうのは、それは、ある意味「初心者のVBAの反則技」です。 そうではなく、エラーの生じるところだけ、On Error Resume Next と On Error Goto 0 ではさんで、エラーが発生したところを回避させる方式です。これは、実際、エラー値のあるものを引数にした時など、回避する方法がありません。そういう場合に良く使う方法です。今回のように、まだ、変数 aaaが生きている場合は、"TypeName" や "VarType" で取れることはあります。(i.e. If VarType(aaa)= vbString Then ...) しかし、そうでない場合は、エラートラップ以外の方法を探すというのは、なかなか大変なことになることがあります。 でも、私は、#1で申したことは、以下のようにすればよいことを指しているのです。今、私が考えている範疇/私のレベルでは、問題がないように思います。どこかいけない部分があるのでしょうか?  With ActiveSheet   ・   ・   For i = 1 To temp      With .Shapes(i).DrawingObject       On Error Resume Next  'エラートラップ開始       aaa = .Characters.Text        If aaa = "zzzzz" Then          MsgBox i & " : " & aaa        End If       On Error GoTo 0  'エラートラップ終了      End With    Next   End With

noname#95859
質問者

お礼

ありがとうございます。 >On Error Resume Next と On Error Goto 0 ではさん >で、エラーが発生したところを回避させる方式です。 On Error Goto 0で終了させることができるのですね。知りませんでした。昔、サブルーチンに飛んだ中でエラーが発生した時に、呼び出し元で定義してあったエラー処理を実行してしまい、困った思いをしました。 これなら、ローカルな処理として扱えます。大変参考になりました。重ねて御礼を申し上げます。

その他の回答 (2)

  • ja7awu
  • ベストアンサー率62% (292/464)
回答No.2

こんな感じでいいと思いますが・・・ aaa = Selection.Characters.Text If TypeName(aaa) = "String" Then  If aaa = "zzzzz" Then MsgBox (aaa) End If

noname#95859
質問者

お礼

ありがとうございます。TypeNameというのがあるのですね。Help等で、そこにたどり着けるようになりたいものです。

  • Wendy02
  • ベストアンサー率57% (3570/6232)
回答No.1

こんにちは。 >このエラーを防ぐためには、On Error Resume Nextが有効ですが、他の方法を探しています。 私は、その方法が簡単でよいと思います。失礼ですが、ObjectをSelectして、そのSelection から、プロパテイを取るというのは、まだ、慣れていないような気がします。 その段階で、なぜ、エラートラップがいけないのか分りません。私なら、その場面で、On Error Resume Next を使っています。 なぜ、エラーが起こるのか、お分りになっていないのではないでしょうか?理由は、Textプロパティ自体が生成されていないので、値を取れないのですから、そういう場合は、エラートラップで良いはずです。 以下のようなコードを、私は、公開コードでは、書かないですね。また、オートシェイプの名前を配列に入れるようなこともしませんね。Shapes.Count が取れているのだから、それで、Shapes(Index)でループすれば済みます。 例えば、   With ActiveSheet  ・  ・  ・   For i = 1 To temp      With .Shapes(nametemp(i)).DrawingObject       aaa = .Characters.Text       '↓ここ       If Not IsNull(.Font.Size) Then         If aaa = "zzzzz" Then          MsgBox i & " : " & aaa         End If       End If      End With    Next    End With

noname#95859
質問者

お礼

ありがとうございます。エラーは、これ以外にも起き得るというのが、On Error Resume Nextを使いたくない理由です。エラーコードをチェックすれば良いと言われそうですが。まだ、慣れていないのが本当のところかと思います。Not IsNull(.Font.Size) これを教えていただいたのは、ありがたいです。

関連するQ&A