Excel VBA質問箱 IV

当質問箱は、有志のボランティア精神のおかげで成り立っています。
問題が解決したら、必ずお礼をしましょうね。
本サイトの基本方針をまとめました。こちら をご一読ください。

投稿種別の選択が必要です。ご注意ください。
迷惑投稿防止のため、URLの入力を制限しています。ご了承ください。


2069 / 13645 ツリー ←次へ | 前へ→

【70167】マクロ無しブックの作成時 かかこ 11/10/18(火) 11:25 質問[未読]
【70168】Re:マクロ無しブックの作成時 UO3 11/10/18(火) 12:11 発言[未読]
【70170】Re:マクロ無しブックの作成時 かかこ 11/10/18(火) 13:20 お礼[未読]
【70174】Re:マクロ無しブックの作成時 かかこ 11/10/18(火) 15:28 質問[未読]
【70175】Re:マクロ無しブックの作成時 かかこ 11/10/18(火) 15:50 質問[未読]
【70180】Re:マクロ無しブックの作成時 UO3 11/10/18(火) 19:26 回答[未読]
【70181】Re:マクロ無しブックの作成時 UO3 11/10/18(火) 19:38 回答[未読]
【70193】Re:マクロ無しブックの作成時 かかこ 11/10/19(水) 9:45 お礼[未読]
【70197】Re:マクロ無しブックの作成時 SS 11/10/19(水) 11:07 発言[未読]
【70205】Re:マクロ無しブックの作成時 かかこ 11/10/19(水) 15:57 質問[未読]
【70206】Re:マクロ無しブックの作成時 かかこ 11/10/19(水) 16:09 質問[未読]
【70208】Re:マクロ無しブックの作成時 UO3 11/10/19(水) 18:58 回答[未読]
【70210】Re:マクロ無しブックの作成時 SS 11/10/19(水) 19:32 回答[未読]
【70225】Re:マクロ無しブックの作成時 かかこ 11/10/20(木) 15:19 お礼[未読]

【70167】マクロ無しブックの作成時
質問  かかこ  - 11/10/18(火) 11:25 -

引用なし
パスワード
   こんにちは、よろしくお願いします。
作成したファイルを年度末に前年分として
マクロを抜いたファイルとして保存したくて下記コードを書きました。
(恥ずかしながら殆どコピペです)

問題なのは 下記コードで・・・問題と書いてある部分です。
これは私が足しました。
arrayの部分の"さしすせそ" & smonth & "月" も私が足しました。

本ブックにはさしすせそ4〜3月のシートがあるのですが、これが非固定です。
4月しかないこともあれば、4〜3月までびっちりある場合もある。
4,5,7,8,12のように飛び飛びのこともあります。
下記のように書くと、
 
WBK1.Worksheets(tblSH).Copy

の部分でエラーになります。
解りにくいかもしれませんが、正しいコードをご教示いただけないでしょうか

Private Sub CommandButton17_Click()

Const cnsTITLE = "マクロなしブックの作成"
  Const cnsFILTER = "Excelワークブック (*.xls),*.xls"
  Dim xlAPP As Application
  Dim WBK1 As Workbook          ' 本ブック
  Dim WBK2 As Workbook          ' 作成ブック
  Dim objVBCOMPO As Object
  Dim strFILENAME As String
  Dim tblSH As Variant
  Dim lngLines As Long
  Dim smonth As Long
  
 
  smonth = 1 Or 2 Or 3 Or 4 Or 5 Or 6 Or 7 Or 8 Or 9 Or 10 Or 11 Or 12・・・問題
  
  tblSH = Array("あいう", "あいうえ", "あいうえお", "かきく", "かきくけ", "かきくけこ", "さしす", "さしすせ", "さしすせそ" & smonth & "月")
   

  Set xlAPP = Application
  Set WBK1 = ThisWorkbook        

  xlAPP.StatusBar = "出力するファイル名を指定して下さい。"
  strFILENAME = xlAPP.GetSaveAsFilename(InitialFileName:="データ年度.xls", _
    FileFilter:=cnsFILTER, Title:=cnsTITLE)
  
  If StrConv(strFILENAME, vbUpperCase) = "FALSE" Then Exit Sub
  If strFILENAME = WBK1.FullName Then
    MsgBox "本ブックとは違うファイル名を指定して下さい。", , cnsTITLE
    GoTo MAKE_NEWBOOK_WO_MACROS_EXIT
  End If
 
  WBK1.Worksheets(tblSH).Copy
  Set WBK2 = ActiveWorkbook       
 

  For Each objVBCOMPO In WBK2.VBProject.VBComponents
    With objVBCOMPO.CodeModule
  
      lngLines = .CountOfLines
      If lngLines <> 0 Then .DeleteLines 1, lngLines
    End With
  Next objVBCOMPO
  WBK2.SaveAs Filename:=strFILENAME
  WBK2.Close False
  Set WBK2 = Nothing
MAKE_NEWBOOK_WO_MACROS_EXIT:
  Set WBK1 = Nothing
  Set xlAPP = Nothing

Unload Me
End Sub

【70168】Re:マクロ無しブックの作成時
発言  UO3  - 11/10/18(火) 12:11 -

引用なし
パスワード
   ▼かかこ さん:

こんにちは

この種の処理自体はあまり感心しない(?)ので、コードそのものは読んでいません。
お困りのポイントについてのみ。

その前に、前提なんですが、ブックをコピーする際に、要は、元ブックにある
全てのシートをコピーするんですよね。

であれば、

WBK1.Worksheets.Copy

でOKです。smonth も tblSH も不要です。

以下は所感です。

データブックとマクロブックを同じものにすると、この種の問題がでますね。
(つまり、マクロを削除しておきたいという要件)
これは、今回のように、保存のみならず、たとえば、このブックを第三者に
配布したい、その際に、やはりマクロを削除して渡したいということも多いと思います。

これら「配布の問題」に対しては、いろんなサイトで方法がのべられており、そのどれかを
参照されて、このコードを作成されたんでしょうが、私自身は

・データブックにはマクロを持たせない。
・マクロブックでデータブックを開いて処理して、保存する。

開く方法はコード内で固定でファイル名を与える以外に、アップされたコードで既にお使いの
ファイル指定のダイアログで選ばせるという方法もありますね。

こうしておけば、いつでも、データブックを名前を付けて保存することが可能になりますし
コピーをそのまま第三者に渡すこともできるわけです。

【70170】Re:マクロ無しブックの作成時
お礼  かかこ  - 11/10/18(火) 13:20 -

引用なし
パスワード
   ▼UO3 さん:

早速のご回答ありがとうございます。

>その前に、前提なんですが、ブックをコピーする際に、要は、元ブックにある
>全てのシートをコピーするんですよね。

説明不足ですみません。じつは全てのシートではないのです。
ですが、教えていただいたとおり
WBK1.Worksheets.Copyとして
いらないシートを削除することで解決しました。
ありがとうございました。

>・データブックにはマクロを持たせない。
>・マクロブックでデータブックを開いて処理して、保存する。

これは一番間違いがない方法ですね。
ありがとうございます。勉強になりました。

【70174】Re:マクロ無しブックの作成時
質問  かかこ  - 11/10/18(火) 15:28 -

引用なし
パスワード
   一度、解決したのですが、又問題が出てしまいました。
新しいブックにシートコピーしたはいいのですが、
コントロールオブジェクトも一緒にコピーされてしまいました。

之を消さないといけないことに気付いて下記のようなコードをセーブする前に付け足したのですが、うまくいきません

  WBK2.Worksheets.Select

     ActiveSheet.Shapes.SelectAll
    Selection.Delete

とやると、メモリ不足のエラーが出ます。
そこで、またHPを探し倒して
  WBK2.Worksheets.Select 

 Dim objAS As Shape
  For Each objAS In ActiveSheet.Shapes
    objAS.Delete
  Next

と書くと、今度は1004エラーが出てしまいます。
どこがおかしいのでしょうか?

【70175】Re:マクロ無しブックの作成時
質問  かかこ  - 11/10/18(火) 15:50 -

引用なし
パスワード
   書き忘れましたが、コントロールオブジェクト(マクロを走らせるボタン)は
複数のシート上にあります。

【70180】Re:マクロ無しブックの作成時
回答  UO3  - 11/10/18(火) 19:26 -

引用なし
パスワード
   ▼かかこ さん:

>  For Each objAS In ActiveSheet.Shapes
>    objAS.Delete
>  Next
>
>と書くと、今度は1004エラーが出てしまいます。

ActiveSheetでいいかどうかは別にして、このコードそのものでは1004エラーにはならないはずですが?
エラーになったコードはどこだったのでしょうか?

いずれにしても、地道に削除するということなら、私も以下のように書きますけど。

  Dim sh As Worksheet

これを定義しておいた上で

  For Each sh In WBK2.Worksheets
    For Each objAS In sh.Shapes
      objAS.Delete
    Next
  Next

【70181】Re:マクロ無しブックの作成時
回答  UO3  - 11/10/18(火) 19:38 -

引用なし
パスワード
   ▼かかこ さん:

追伸です。

>  WBK2.Worksheets.Select

これを読みとばしていました。

まず実行時 wbk2が最前面ブックではない場合、ここで1004になります。

で、最前面ブックだった場合は objAS.Delete ここで1004になります。
シートを全て選択した上でActiveSheetからShapeを抽出すると
そのシェープに対しては操作できなくなるようです。

ですので、WBK2.Worksheets.Select を削除した上で
私がアップした様なコードにしてお試しください。

【70193】Re:マクロ無しブックの作成時
お礼  かかこ  - 11/10/19(水) 9:45 -

引用なし
パスワード
   ▼UO3 さん:

何度もすみません。ご回答ありがとうございます

>で、最前面ブックだった場合は objAS.Delete ここで1004になります。

そうです。そこで1004になりました
HPを探すとシート上の全てのシェープを消すという処理はたくさん検索にひっかかるのですが、ブック全体というのが見つけられませんでした。

>シートを全て選択した上でActiveSheetからShapeを抽出すると
>そのシェープに対しては操作できなくなるようです。

そうだったのですか。勉強になります。
教えていただいたコードでうまくいきました。
助かりました。ありがとうございます。

【70197】Re:マクロ無しブックの作成時
発言  SS  - 11/10/19(水) 11:07 -

引用なし
パスワード
   ▼かかこ さん:

こんにちは、すでにUO3さんのご助言で対処方法を見つけられたようですが
最初の質問はこういうことかな?ということで作ってみました。
興味がありましたら確認してみてください。

  '対象シート名の登録
  Dim i As Integer, j As Integer
  Dim Dic As Variant, WS As Variant
  Set Dic = CreateObject("Scripting.Dictionary")
  tblSH = Array("あいう", "あいうえ", "あいうえお", _
        "かきく", "かきくけ", "かきくけこ", _
        "さしす", "さしすせ", "さしすせそ")
  For i = 1 To UBound(tblSH)
    For j = 1 To 12
      Dic.Add tblSH(i) & j & "月", 1
    Next j
  Next i
  
  'ワークシートの名前確認
  For Each WS In WBK1.Sheets
    If Dic.Exists(WS.Name) Then
      WS.Copy After:=WBK2.Sheets(Sheets.Count)
    End If
  Next WS
  Set Dic = Nothing

>▼UO3 さん:
>
>早速のご回答ありがとうございます。
>
>>その前に、前提なんですが、ブックをコピーする際に、要は、元ブックにある
>>全てのシートをコピーするんですよね。
>
>説明不足ですみません。じつは全てのシートではないのです。
>ですが、教えていただいたとおり
>WBK1.Worksheets.Copyとして
>いらないシートを削除することで解決しました。
>ありがとうございました。
>
>>・データブックにはマクロを持たせない。
>>・マクロブックでデータブックを開いて処理して、保存する。
>
>これは一番間違いがない方法ですね。
>ありがとうございます。勉強になりました。

【70205】Re:マクロ無しブックの作成時
質問  かかこ  - 11/10/19(水) 15:57 -

引用なし
パスワード
   ▼SS さん:

ありがとうございます。早速コード使わせていただきました。
私が書いたのよりずっと早くて快適なのですが、私の説明が下手だったのかうまくいかないところがありましたので、どこがおかしいかご指導よろしくお願いします。

お示しのコードを参考に以下のように書きました

Private Sub CommandButton17_Click() 
  
Const cnsTITLE = "マクロなしブックの作成"
  Const cnsFILTER = "Excelワークブック (*.xls),*.xls"
  Dim xlAPP As Application
  Dim WBK1 As Workbook         
  Dim WBK2 As Workbook         
  Dim objVBCOMPO As Object
  Dim strFILENAME As String
  Dim lngLines As Long
  Dim i As Integer, j As Integer
  Dim Dic As Variant, WS As Variant
  
  Set xlAPP = Application
  Set WBK1 = ThisWorkbook
  Set Dic = CreateObject("Scripting.Dictionary")
  tblSH = Array("あいう", "あいうえ", "あいうえお", _
        "かきく", "かきくけ", "かきくけこ", _
        "さしす", "さしすせ", "さしすせそ")
                           ・・・問題(1)

  xlAPP.StatusBar = "出力するファイル名を指定して下さい。"
  strFILENAME = xlAPP.GetSaveAsFilename(InitialFileName:="データ年度.xls", _
    FileFilter:=cnsFILTER, Title:=cnsTITLE)
 
  If StrConv(strFILENAME, vbUpperCase) = "FALSE" Then Exit Sub
  If strFILENAME = WBK1.FullName Then
    MsgBox "本ブックとは違うファイル名を指定して下さい。", , cnsTITLE
    GoTo MAKE_NEWBOOK_WO_MACROS_EXIT
  End If
 
    Set WBK2 = ActiveWorkbook       
 
    For i = 1 To UBound(tblSH)
    For j = 1 To 12
      Dic.Add tblSH(i) & j & "月", 1
    Next j
  Next i
 
  'ワークシートの名前確認
  For Each WS In WBK1.Sheets
    If Dic.Exists(WS.Name) Then
      WS.Copy After:=WBK2.Sheets(Sheets.Count)
    End If
  Next WS
  Set Dic = Nothing

  For Each objVBCOMPO In WBK2.VBProject.VBComponents
    With objVBCOMPO.CodeModule
    
      lngLines = .CountOfLines
      If lngLines <> 0 Then .DeleteLines 1, lngLines
    End With
  Next objVBCOMPO

  Dim sh As Worksheet

  For Each sh In WBK2.Worksheets
    For Each objAS In sh.Shapes
      objAS.Delete
    Next
  Next

  WBK2.SaveAs Filename:=strFILENAME
  WBK2.Close False
  Set WBK2 = Nothing
 MAKE_NEWBOOK_WO_MACROS_EXIT:
  Set WBK1 = Nothing
  Set xlAPP = Nothing

Unload Me
End Sub

問題(1) 後ろに1〜12月を付けたいシート(さしすせそ)と、コピーしたいシート(さしすせそ以外)のみ書きましたが全シートコピーされてしまう。
問題(2) 新しく作られたブックを立ち上げると、データのみのはずなのにマクロの警告が出る
問題(3)  新しいブックが保存されて落ちると、本ブックまで落ちる(保存はされません)

以上です。よろしくお願いします。

【70206】Re:マクロ無しブックの作成時
質問  かかこ  - 11/10/19(水) 16:09 -

引用なし
パスワード
   ああもう、説明が下手でいやになってしまう。しかも投稿した後気付くとは。

>問題(1) 後ろに1〜12月を付けたいシート(さしすせそ)と、コピーしたいシート(さしすせそ以外)のみ書きましたが全シートコピーされてしまう。

についてですが、もう少し詳しく説明します。

例)本ブックに下記の16シートがあるとします。
まえがき、あいう、あいうえ、あいうえお、かきく、かきくけ、かきくけこ、さしす、さしすせ、さしすせそ4月、さしすせそ6月、さしすせそ7月、さしすせそ10月、たちつてと、まみむめも、あとがき

このうち、
あいう、あいうえ、あいうえお、かきく、かきくけ、かきくけこ、さしす、さしすせ、さしすせそ4月、さしすせそ6月、さしすせそ7月、さしすせそ10月の12シートのみ新ブックにコピーしたいという意味でした。

あと、あいうえお等をコード例に使ったのは失敗でした。実際は全シート名にこんなに法則性はありません。(りんご、みかん、とかにすればよかった)

何度もすみません

【70208】Re:マクロ無しブックの作成時
回答  UO3  - 11/10/19(水) 18:58 -

引用なし
パスワード
   ▼かかこ さん:

▼かかこ さん:

(一度アップしましたが、削除して少し改善したものを再度アップします)

コピーした後削除するのではなく、必要なものだけをコピーしたいということなら、
以下のようなコードでも。

Sub Test()
  Dim sh As Worksheet
  Dim WBK2 As Workbook
  Dim v() As Variant
  Dim ng As Variant
  Dim k As Long
 
  Set WBK2 = ThisWorkbook 'Testのため仮に
 
  ng = Array("AAA", "BBB", "CCC") '不要シート名 何枚でも
  ReDim v(1 To WBK2.Worksheets.Count)
 
  For Each sh In WBK2.Worksheets
    If Not IsNumeric(Application.Match(sh.Name, ng, 0)) Then
      k = k + 1
      v(k) = sh.Name
    End If
  Next
 
  ReDim Preserve v(1 To k)
 
  WBK2.Worksheets(v).Copy
 
End Sub

【70210】Re:マクロ無しブックの作成時
回答  SS  - 11/10/19(水) 19:32 -

引用なし
パスワード
   ▼かかこ さん:
作ってみました。自分勝手に弄っていますので参考程度にみて下さい。
先ずは問題への対応から

>問題(1) 後ろに1〜12月を付けたいシート(さしすせそ)と、コピーしたいシート(さしすせそ以外)のみ書きましたが全シートコピーされてしまう。
 コピーするワークシート名のルールを勘違いしていました。
 記述を省力化したいのかなと考えていました。
 規則性がないようでしたら全て配列に収めてしまった方が良いと思います。
>問題(2) 新しく作られたブックを立ち上げると、データのみのはずなのにマクロの警告が出る
 自ファイルを名前を付けて保存しているのでマクロが入っています。
>問題(3)  新しいブックが保存されて落ちると、本ブックまで落ちる(保存はされません)
 上の問題と一緒で本ブックはその前に落ちています。

あとOption Explicitはデフォールトにした方が良いですよ。

Sub test()
 
  Const cnsTITLE = "マクロなしブックの作成"
  Const cnsFILTER = "Excelワークブック (*.xls),*.xls"
  Dim xlAPP As Application
  Dim WBK1 As Workbook
  Dim WBK2 As Workbook
  Dim objVBCOMPO As Object
  Dim strFILENAME As String
  Dim lngLines As Long
  Dim i As Integer, j As Integer, Temp As Integer
  Dim tblSH As Variant
  Dim SN As Variant, WS As Variant
  Dim sh As Worksheet
  Dim objAS As Object
 
  Set xlAPP = Application
  Set WBK1 = ThisWorkbook
  
  tblSH = Array("あいう", "あいうえ", "あいうえお", _
        "かきく", "かきくけ", "かきくけこ", _
        "さしす", "さしすせ", "さしすせそ", _
        "さしすせそ4月", "さしすせそ6月", _
        "さしすせそ7月", "さしすせそ10月")

  xlAPP.StatusBar = "出力するファイル名を指定して下さい。"
  strFILENAME = xlAPP.GetSaveAsFilename(InitialFileName:="データ年度.xls", _
    FileFilter:=cnsFILTER, Title:=cnsTITLE)
 
  If StrConv(strFILENAME, vbUpperCase) = "FALSE" Then
    Exit Sub
  ElseIf strFILENAME = WBK1.FullName Then
    MsgBox "本ブックとは違うファイル名を指定して下さい。", , cnsTITLE
    GoTo MAKE_NEWBOOK_WO_MACROS_EXIT
  Else
    'Sheet1のみのWorkbookをつくり前述名前をつけます。
    Temp = Application.SheetsInNewWorkbook
    Application.SheetsInNewWorkbook = 1
    Workbooks.Add
    Application.SheetsInNewWorkbook = Temp
    ActiveWorkbook.SaveAs Filename:=strFILENAME
    Set WBK2 = ActiveWorkbook
  End If

  'ワークシートの名前確認
  '配列を一度Dicに入れた方が良いのかは分かりません。
  For Each WS In WBK1.Sheets
    For Each SN In tblSH
      If SN = WS.Name Then
        WS.Copy After:=WBK2.Sheets(Sheets.Count)
        Exit For
      End If
    Next SN
  Next WS
  'Sheet1以外にSheetがある場合Sheet1を削除します。
  'もしSheet1が必要なら消してください。
  '確認したい場合はApplication.DisplayAlerts関連を消してください。
  If WBK2.Sheets.Count > 1 Then
    Application.DisplayAlerts = False
    WBK2.Worksheets("Sheet1").Delete
    Application.DisplayAlerts = True
  End If

  For Each sh In WBK2.Worksheets
    For Each objAS In sh.Shapes
      objAS.Delete
    Next
  Next

  WBK2.Close
  Set WBK2 = Nothing
Exit Sub
MAKE_NEWBOOK_WO_MACROS_EXIT:
  Set WBK1 = Nothing
  Set xlAPP = Nothing
End Sub

【70225】Re:マクロ無しブックの作成時
お礼  かかこ  - 11/10/20(木) 15:19 -

引用なし
パスワード
   ▼UO3さん:
▼SSさん:

ありがとうございました。UO3さんの方法で解決しました。助かりました。

ただ、このコード、ものすごく処理が遅いんですね。これはUO3さんの方法のせいではなく、元のコードが処理の遅いものなのだと思います。どこかのHPから
拾ってきたものですが。

SSさんの方法は速いので試してみたんですけれど、

>本ブックにはさしすせそ4〜3月のシートがあるのですが、これが非固定です。
>4月しかないこともあれば、4〜3月までびっちりある場合もある。
>4,5,7,8,12のように飛び飛びのこともあります。

の部分を直すのがうまくいかなかったので、出来ませんでした。
(これは後々の私の説明がへたくそだったせいで伝わらなかったと思われます。重ね重ねすみません)
せっかくご教示いただいたのに申し訳ありません。
余談ですが、VBAだけじゃなく何をしたいかをちゃんと伝える文章の勉強もしなくては(笑)

2069 / 13645 ツリー ←次へ | 前へ→
ページ:  ┃  記事番号:
2610219
(SS)C-BOARD v3.8 is Free