简体   繁体   中英

How to assign values from one sheet into hidden sheet using Excel VBA? (and skip a column within the range?)

Instead of copy-select-pasting cells (lower code), I wish to assign ranges directly and hide the sheet to which values are being filled.

I think the sheet can simply be hidden from view and the macro to fill values based on another sheet's ranges will still work, right?

Trying to assign values on another sheet, I intend to build on this working code (with thanks to Jason Faulkner and aoswald ). (I must place the cells after one blank column from the last set of values. Ideally, the code will assign values from A13:C## (til the last filled row) and likewise E13:E## immediately after it (ie removing column D when assigning values onto the hidden sheet.)

Private Sub CommandButton1_Click()
 Dim DataRange As Variant, Constraint_sheet As Worksheet, Private_sheet As Worksheet
 Set Constraint_sheet = Sheets("Constraint Sheet")
 Set Private_sheet = Sheets("Private")
 DataRange = Constraint_sheet.Range("A13:C300").Value
 With Private_sheet
   .Range(.Range("XFD1").End(xlToLeft).Offset(0, 3), .Range("XFD1").End(xlToLeft).Offset(287, 2)) = DataRange
 End With
End Sub

Here is working code that I am trying to replace and simplify as indicated above. Are there additional simplifications that can be made?

Private Sub CommandButton1_Click()
  Dim MyPassword As String, Private_sheet As Worksheet
  Set Private_sheet = Sheets("Private")
  MyPassword = "string"
  If InputBox("Please enter the password to continue.", "Enter Password") <> MyPassword Then
     Exit Sub
  End If

  Private_sheet.Unprotect MyPassword ' apparently causes clipboard to be erased so do before copying cells

  Columns("B:E").Select
  Application.CutCopyMode = False
  Selection.Copy

    Private_sheet.Select
Private_sheet.Range("XFD1").End(xlToLeft).Offset(0, 3).Select
ActiveCell.PasteSpecial
ActiveCell.CurrentRegion.EntireColumn.Locked = True
ActiveCell.CurrentRegion.Offset(0, -1).EntireColumn.Locked = True
Private_sheet.Protect MyPassword

  ActiveWorkbook.Save

End Sub

Edit: Here is the working code I've developed to replace the above code. What further improvements and simplifications can be made?

Private Sub AddTemplate_Click()
 Dim Exposed_sheet As Worksheet, Hidden_sheet As Worksheet, MyPassword As String

 Set Exposed_sheet = Sheets("Exposed Sheet")
 Set Hidden_sheet = Sheets("Hidden")

  MyPassword = "string"
  'Reference: carriage return in msgbox http://www.ozgrid.com/forum/showthread.php?t=41581
  If InputBox("Please enter the password to continue." & vbNewLine & vbNewLine _
   & "Note: The string you type will be exposed, i.e. not '***'." & vbNewLine _
   & "Note: This will save the Excel file!", "Enter Password: Enter the correct string.") <> MyPassword Then
     Exit Sub
  End If

 ' Reference: .Protect -  https://stackoverflow.com/questions/11746478/excel-macro-run-time-error-1004
  Hidden_sheet.Unprotect MyPassword

 'References:
 ' dynamic referencing: https://stackoverflow.com/questions/45889866/how-to-assign-values-from-one-sheet-into-hidden-sheet-using-excel-vba-and-skip/45889960#45889960
 ' adding text:         https://stackoverflow.com/questions/20612415/adding-text-to-a-cell-in-excel-using-vba
 ' Union to exclude column: https://stackoverflow.com/questions/2376995/exclude-some-columns-while-copying-one-row-to-other
 With Hidden_sheet
    .Cells(1, Columns.Count).End(xlToLeft).Offset(1, 3).Resize(UBound(Exposed_sheet.Range("B6", "D9").Value, 1), UBound(Exposed_sheet.Range("B6", "D9").Value, 2)).Value = Exposed_sheet.Range("B6", "D9").Value
    .Cells(1, Columns.Count).End(xlToLeft).Offset(1, 6).Value = "Volume/Protocol"
    .Cells(1, Columns.Count).End(xlToLeft).Offset(6, 3).Resize(UBound(Union(Exposed_sheet.Range("A13:C300"), Exposed_sheet.Range("E13:E300")).Value, 1), UBound(Union(Exposed_sheet.Range("A13:C300"), Exposed_sheet.Range("E13:E300")).Value, 2)).Value = Union(Exposed_sheet.Range("A13:C300"), Exposed_sheet.Range("E13:E300")).Value
    ' If you change the order putting this prior, you must change the offsets or the cell they count from. -- DB, Aug 28 2017
    .Cells(1, Columns.Count).End(xlToLeft).Offset(0, 3).Resize(1, 3).Merge
    .Cells(1, Columns.Count).End(xlToLeft).Offset(0, 3).Value = Exposed_sheet.Range("A1").Value
 End With

 Hidden_sheet.Protect MyPassword

 ActiveWorkbook.Save

End Sub

Your problem is that (in a regular code module) Range() , Cells() will always reference the ActiveSheet unless you include a worksheet qualifier

Private_sheet.Range(Range("XFD1").End(xlToLeft).Offset(0, 3), _
                    Range("XFD1").End(xlToLeft).Offset(287, 2)) = DataRange

So even though the outer Range() is scoped to Private_sheet , that does not "carry through" to the inner Range calls.

Should be something like:

With Private_sheet
    .Range(.Range("XFD1").End(xlToLeft).Offset(0, 3), _
           .Range("XFD1").End(xlToLeft).Offset(287, 2)) = DataRange
End With

Bit simpler/more flexible:

'EDITED
Private_sheet.Cells(1, Columns.Count).End(xlToLeft).Offset(0, 3) _
  .Resize(UBound(DataRange, 1), UBound(DataRange, 2)).Value = DataRange

In a sheet code module, range references will default to that sheet, but it's still good practise to qualify with a sheet object (eg) Me.Range()

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM