How to hide multiple columns in Excel sheet? - excel

I'm using 4 sequential columns from sheet 1 to generate charts in sheet 2. I want to hide those 4 columns in sheet 1.
I've tried the below code to hide the columns:
Set allColumns = dataSheet.Columns("J:M")
allColumns.Hidden = True

Constants and References
Sub AllCol()
Const cVntSheet As Variant = "Sheet1" ' Worksheet Name/Index
Const cStrRange As String = "J:M" ' Range Address
Dim dataSheet As Worksheet ' Worksheet
' Create a reference to the worksheet.
Set dataSheet = Worksheets(cVntSheet)
' Hide the range.
dataSheet.Columns(cStrRange).Hidden = True
End Sub

Swap Sheet1 with your actual sheet name.
Sub HideMe()
ThisWorkbook.Sheets("Sheet1").Columns("J:M").Hidden = True
End Sub
Notice this can be done in one line. If you want to use variables (workbook or worksheets), they should build the above string when combined
Something like:
Dim wb as Workbook: Set wb = ThisWorkbook
Dim ws as Worksheet: Set ws = wb.Sheets("Sheet1")
Dim hm as String: hm = "J:M"
ws.Columns(hm).Hidden = True
If you substitute your variables into the last line, you will end up with the exact same line of code shown in the first sub.

Related

Sum values from one Worksheet in another Worksheet

I am trying to sum values from my original worksheet in specific cells in my newly created worksheet, which has a template to fill out.
When I used macro recorder, it references the worksheet name, which would not be useful as the worksheet name changes depending on which worksheet I am working in when I run the code.
So I tried changing the worksheet name to a variable "XCXX".
The first argument works so I thought everything was okay, however, on the second argument, it keeps trying to open a file, when it should simply go back to XCXX and pull the values.
Is it a problem with my activesheet changing?
Sub AddWorkbooks()
Dim ChangeOrder As Range
Dim XCXX As Worksheet
Dim CoForm As Worksheet
Set XCXX = ActiveSheet
Set CoForm = Worksheets("+CO Form+")
'Set wbNew = Workbooks.Add
CoForm.Copy After:=Sheets(ActiveSheet.Index)
With CoForm
Range("A6:D6").Select
ActiveCell.FormulaR1C1 = XCXX.Range("D2").Value
Range("AD81").Select
ActiveCell.FormulaR1C1 = "='XCXX'!R[-64]C[-24]+'XCXX'!R[-64]C[-23]"
End With
End Sub
This should be close:
Sub AddWorkbooks()
Dim ChangeOrder As Range
Dim XCXX As Worksheet, wb As Workbook
Dim CoForm As Worksheet, CoFormCopy As Worksheet
Set wb = ActiveWorkbook
Set XCXX = ActiveSheet
Set CoForm = wb.Worksheets("+CO Form+")
CoForm.Copy After:=XCXX
Set CoFormCopy = XCXX.Next 'the copy of "+CO Form+"
With CoFormCopy 'assuming you want to work with the copy?
.Range("A6:D6").Value = XCXX.Range("D2").Value
.Range("AD81").FormulaR1C1 = _
Replace("='<nm>'!R[-64]C[-24]+'<nm>'!R[-64]C[-23]", "<nm>", XCXX.Name)
End With
End Sub
Note when using With you need to use a period to link (eg) Range() with the object used in the With statement, otherwise it defaults to the active sheet.
Also generally there's no need to select a range to do something with it.

List a variable range of tabs

I am trying to get a list of the names of the sheets starting from a specific sheet, as I don't need the names of the tabs before that sheet. The problem is that these sheets will have variable length and sheet name from quarter to quarter (they might change name and decrease or increase in number).
This is what I have done but I get it wrong, but mind that my VBA level is null.
Sub XX1()
Dim x As Integer
Dim wb As Workbook: Set wb = ThisWorkbook
Dim WKS As Worksheet: Set WKS = wb.Sheets("10")
x = 1
For Each WKS In Worksheets
Sheets("Directory").Cells(x, 1) = WKS.Name
x = x + 1
Next WKS
End Sub
I want to get, from the sheet called S (is the sheet number 10), all the sheet names and list them in another sheet, called 'Directory'.
You will need to use the Worksheets.Index attribute to do this.
Here it is:
Sub XX1()
Dim x As Integer
Dim wb As Workbook
Dim wks As Worksheet
Dim sh As Worksheet
Set wb = ThisWorkbook
Set wks = wb.Sheets("10")
x = 1
For Each sh In Worksheets
If sh.Index >= wks.Index Then
Sheets("Directory").Cells(x, 1).Value = sh.Name
x = x + 1
End If
Next sh
End Sub
Obviously the result will change if you manually move the worksheets in your workbook.

Copy Data from Sheet to another based on drop-down value

I have several sheets in one workbook. I want to copy-paste the data (entire content) from different sheets to sheet 1 (let's say from B6) based on the drop-down value in 'A2' in Sheet 1. Drop-down consists of names of all the other sheets. So, if I select Sheet 2 in drop-down, it should copy entire content from Sheet 2 to Sheet 1, starting from B6.
Here is the macro, I created for it. But it's not working. Can you help me figure out what's wrong with my code?
Sub Button21_Click()
Dim wb As Workbook
Dim criteria As String
Application.ScreenUpdating = False
'Set values for your variables.
Set wb = ThisWorkbook
criteria = wb.Sheets("Sheet1").Range("A2")
Dim TT As ListObject
For i = 1 To Sheets.Count
With Sheets(i)
For Each TT In Sheets(i).ListObjects
If TT.Name = criteria Then TT.Range.Copy Sheets("Sheet1").Range("B6:Q22").PasteSpecial: Exit Sub
Next
End With
Next
Application.ScreenUpdating = True
End Sub
Here's code that does work.
Sub Button21_Click()
Dim Wb As Workbook
Dim Criteria As String
Dim i As Integer ' loop counter: Sheets
Dim Tbl As ListObject ' loop object
'Set values for your variables.
Set Wb = ThisWorkbook
Criteria = Wb.Sheets("Sheet1").Range("A2")
Application.ScreenUpdating = False
For i = 1 To Wb.Sheets.Count ' { "Shees(1)" is in the ActiveWorkbook
' { which may be different from Wb
For Each Tbl In Wb.Sheets(i).ListObjects
If Tbl.Name = Criteria Then
Tbl.Range.Copy
Wb.Worksheets("Sheet1").Range("B6").PasteSpecial
Exit Sub
End If
Next Tbl
Next i
Application.ScreenUpdating = True
End Sub
You should declare all variables, not only objects. And it's better to prepare your tools before starting on the job, i.e. declare variables before writing code that uses them.
What's the point of declaring Set Wb = ThisWorkbook if you use the default workbook (= ActiveWorkbook) thereafter?
PasteSpecial needs its own line. The construct you used would deliver the argument for the Copy object's Destination property. The latter is an address and can't include the PasteSpecial method.
It's enough to specify the first cell to paste to.
Note that the ListObject's Range comprises of the entire table. Use the DataBodyRange to specify only data (without headers and totals).

How can I convert a string variable to a worksheet object on VBA?

My problem is complex, I do not know if somebody has had this problem.
I want to convert a string ("Sheet1", "Sheet2", etc.) to an object in a particular case in a worksheet. With that, I can use a code Sheet3.Range("A1").Value, but I want to replace the number 3 with any I need.
I have a workbook with a worksheet called "CSV", in this sheet has a table called "t_csv". This worksheet is used to translate some text between Spanish and English.
CSV sheet example
I programed the routine to do that as follows (it works if you have the same order on the tab bar and VBA Index).
Sub tranlation()
Dim lang As String
Dim Sheet As Integer
Dim vcell As String
Dim data As String
‘Get the language from a buttom btn_esp or btn_eng from userform called “f_Login”
If f_Login.btn_esp.Value = True Then lang = "Español"
If f_Login.btn_eng.Value = True Then lang = "English"
‘Bucle to get the data from table “t_csv” located in sheet “CSV” (Sheet2)
For i = 1 To Sheet2.ListObjects("t_csv").DataBodyRange.Rows.Count
With Sheet2.ListObjects("t_csv")
Sheet = .ListColumns("Hoja").DataBodyRange(i).Value
vcell = .ListColumns("Celda").DataBodyRange(i).Value
'It uses the lang variable to choose the respective column on table "t_csv"
data = .ListColumns(lang).DataBodyRange(i).Value
‘write the text in corresnponding cell (code to be changed)
**Sheets(Sheet).Range(vcell).Value = dato**
End With
Next i
End Sub
The problem with the function Sheets() or Worksheets() is that they call the worksheets numbering the worksheets on the workbook's tab bar (from left to right). But I want to call the sheets with the VBA worksheet number because I have specific order on the workbook's tab bar.
Order in my tab bar
Order in my VBA index
I tried to use a code like this (it does not work because "Sheet" & Sheet is a string variable):
Dim SheetIndex As Worksheet
Set SheetIndex = “Sheet” & Sheet
SheetIndex.Range(vcell).value = data
But if I use the next code:
Dim HojaIndex As Worksheet
Set HojaIndex = Sheet3
HojaIndex.Range(vcell).value = data
This code works, but I want to substitute the number 3 automatically by whatever number I get from the table "t_csv".
I am guessing that the solution is to use the function CallByName, but I don't understand how can I use it. I saw some examples and I tried, but I could not make it work.
------- UPDATE ------- UPDATE ------- UPDATE ------- UPDATE ------- UPDATE ------- UPDATE -------
Thanks to #Tim Williams. I could solve my problem, I did some modifications inspired in his answer. I share the final answer if somebody has the same problem.
Function SheetByCodeName(SheetCodeName As String) As Worksheet
Dim ws As Worksheet
For Each ws In ThisWorkbook.Worksheets
If ws.CodeName = SheetCodeName Then
Set SheetByCodeName = ws
Exit Function
End If
Next ws
End Function
Sub tranlation()
Dim lang As String
Dim Sheet As String 'Update variable type from Integer to String
Dim vcell As String
Dim data As String
Dim SheetName As Worksheet 'New variable to set the sheet name
‘Get the language from a buttom btn_esp or btn_eng from userform called “f_Login”
If f_Login.btn_esp.Value = True Then lang = "Español"
If f_Login.btn_eng.Value = True Then lang = "English"
‘Bucle to get the data from table “t_csv” located in sheet “CSV” (Sheet2)
For i = 1 To Sheet2.ListObjects("t_csv").DataBodyRange.Rows.Count
With Sheet2.ListObjects("t_csv")
Sheet = "Sheet" & .ListColumns("Hoja").DataBodyRange(i).Value
vcell = .ListColumns("Celda").DataBodyRange(i).Value
'It uses the lang variable to choose the respective column on table "t_csv"
data = .ListColumns(lang).DataBodyRange(i).Value
‘*-NEW CODE*- write the text in corresnponding cell
Set Sheet = SheetByCodeName(Sheet)
Sheet.Range(vcell).Value = data
‘*-NEW CODE*- write the text in corresnponding cell
End With
Next i
End Sub
Sub tester()
Debug.Print SheetByCodename("xxx").Name
End Sub
'Return a worksheet from its codeName (or Nothing if not match)
' Defaults to ThisWorkbook if a workbook is not passed
Function SheetByCodename(nm As String, Optional wb As Workbook = Nothing) As Worksheet
Dim ws As Object
If wb Is Nothing Then Set wb = ThisWorkbook
For Each ws In ThisWorkbook.Worksheets
If ws.CodeName = nm Then
Set SheetByCodename = ws
Exit Function
End If
Next ws
End Function

Making sheet name the same as cell value

I am currently working on macro in a workbook with multiple worksheets, that aims to show and hide certain worksheets based on the values in a master worksheet. The worksheet names are also contained in the master worksheet and the main procedure looks at these values when referencing to a worksheet it needs to show or hide. The problem with this method is that, the macro will produce errors if the user changes the worksheet tab names. I was hoping to insert an additional procedure that makes the tab names of each worksheet equal to the values in the respective cell of the master worksheet. I came up with the following:
Sub SheetName()
If Not ActiveWorkbook Is ThisWorkbook Then Exit Sub
Dim DataImport As Worksheet
Set DataImport = ThisWorkbook.Worksheets("Data Import")
DataImport.Range("A13").Value = Sheet1.Name
End Sub
This code works fine but there are about 100+ worksheets in this workbook. I was wondering if there is a more efficient way to do this, as opposed to typing the same procedure 100 times. I've tried storing the worksheet code names in an array and looping the same procedure through the array, for example:
Sub test()
Dim DataImport As Worksheet
Set DataImport = ThisWorkbook.Worksheets("Data Import")
Dim index As Long
Dim ws(0 To 2) As Worksheet
Set ws = Array(Sheet1, Sheet2, Sheet3)
For i = 13 To 14
index = i - 13
DataImport.Cells(i, "A").Value = ws(index).Name
Next i
End Sub
but the error message "Can't Assign to Array" shows up. Sorry in advance if my code looks garbage, I am still new to VBA and I still have quite a lot to learn.
If you list the sheet codenames in ColA of your master sheet, then this code will update columns B and C with the current sheet tab names and indexes respectively:
Sub UpdateIndex()
Dim ws As Worksheet, cn As String, m
For Each ws In ThisWorkbook.Worksheets
cn = ws.CodeName
If cn <> DataImport.CodeName Then
'look for the codename in the Import sheet
m = Application.Match(cn, DataImport.Columns(1), 0)
If Not IsError(m) Then
'got a match - update this row
DataImport.Cells(m, "B").Value = ws.Name 'tab name
DataImport.Cells(m, "C").Value = ws.Index 'sheet index
End If
End If
Next ws
End Sub
Assumes you set the code name for your "Data Import" worksheet to DataImport.
If your code is driven by the sheet codename, it doesn't matter whether the user renames the tabs or changes the sheet order.
For your second attempt, you can use Excel built-in Sheets object and Workbook.Sheets collection:
Sub test()
Dim DataImport As Worksheet
Set DataImport = ThisWorkbook.Worksheets("Data Import")
Dim index As Long
Dim ws As Excel.Sheets
Set ws = ThisWorkbook.Sheets
For i = 13 To 14
index = i - 13
DataImport.Cells(i, "A").Value = ws(index).Name
Next i
End Sub

Resources