How to find the adjacent cell value in excel using VB.NET - vb.net

I am stuck with this sitaution. I read the forum and have tried numerous methods to solve this but nothings working.
Here is the scenario:
I am autogenerating an excel worksheet using vb.net. This worksheet gets populated with 200 data values in column A and 200 different data values in column B. I then find the maximum value of column B with its associated address (e.g. maxvalue = 2.59, address $B$89 ). I now need to find the value of the adjacent cell (in column A) and display that value in a message box.
Any help will be much appreciated.
Thanks
Sudhir

Dim xlsApp As Excel.Application = Nothing
Dim xlsWorkBooks As Excel.Workbooks = Nothing
Dim xlsWB As Excel.Workbook = Nothing
Try
xlsApp = New Excel.Application
xlsApp.Visible = True
xlsWorkBooks = xlsApp.Workbooks
xlsWB = xlsWorkbooks.Open("c:\my_excel_file.xls")
xlsWB.Range("B89").Select 'This will move the cursor to B89 cell
Dim myValue as String = ""
myValue = xlsWB.Activecell.Offset(0,-1).Value
'Offset(0,-1) means we are interested in the
'cell in which lies on the same row (0 for y axis)
'and to the left of the current one, by one cell
'which means -1 . If we want the cell in column D92 then
'we would use Offset(3,2)
Catch ex As Exception
Finally
xlsWB.Close()
xlsWB = Nothing
xlsApp.Quit()
xlsApp = Nothing
End Try

Related

Excel VBA: Generate N Number of Sheets Based on Cel Value

I want to create a macro that will generate N number of template sheets based on the value of a cel. For example, User inputs 4 into this particular cell and it subsequently generates 4 new sheets in the workbook of this template.
I've searched all through Stack overflow for a question that matches mine but none do. The closest I found was this and although the inital headline question asks generally the same question, when going into detail the user who asked this changes their question to"insert number of cells based on a cell value". Still I used this as a starting point.
Sub CreateSheets()
Dim facilitiesNum As Integer
facilitiesNum = Range("B2").Value
sheetsNeeded = facilitiesNum
With ThisWorkbook.Sheets
For i = sheetsNeeded To Master.Range("B2").Value2
.Item("TemplateSheet").Copy After:=.Item(.Count)
.Item(.Count).Name = sheetsNeeded
Next
End With
End Sub
I am new to VBA so I could be very off syntax-wise but in pseudocode my goal is
numberOfTemplates = cell value
numSheetsNeeded = numberOfTemplates
For i = numSheetsNeeded To NumOfTemp:
create sheets using numSheetsNeeded as reference for how many need to be
generated
How do I go about doing this?
If you just want to add new sheets this should be enough
Sub CreateSheets()
Dim facilitiesNum As Long
facilitiesNum = Range("B2").Value
With ThisWorkbook.Sheets
For i = 1 To facilitiesNum
.Item("TemplateSheet").Copy After:=.Item(.Count)
.Item(.Count).Name = i
Next i
End With
end sub

Determine if a VBComponent regards a workbook or a worksheet

The following code allows me to go through the workbook and worksheets that have macros:
For Each VBCmp In ActiveWorkbook.VBProject.VBComponents
Msgbox VBCmp.Name
Msgbox VBcmp.Type
Next VBCmp
As this page shows, for a workbook and a sheet, their type are both 100, ie, vbext_ct_Document. But I still want to distinguish them: I want to know which VBCmp is about a workbook, which one is about a worksheet.
Note that VBCmp.Name can be changed, they are not necessarily always ThisWorkbook or Sheet1, so it is not a reliable information for what I am after.
Does anyone know if there exists a property about that?
Worksheet objects and Workbook objects both have a CodeName property which will match the VBCmp.Name property, so you can compare the two for a match.
Sub Tester()
Dim vbcmp
For Each vbcmp In ActiveWorkbook.VBProject.VBComponents
Debug.Print vbcmp.Name, vbcmp.Type, _
IIf(vbcmp.Name = ActiveWorkbook.CodeName, "Workbook", "")
Next vbcmp
End Sub
This is the Function I'm using to deal with exported code (VBComponent's method) where I add a preffix to the name of the resulting file. I'm working on an application that will rewrite, among other statements, API Declares, from 32 to 64 bits. I'm planning to abandon XL 32 bits definitely. After exportation I know from where did the codes came from, so I'll rewrite them and put back on the Workbook.
Function fnGetDocumentTypePreffix(ByRef oVBComp As VBIDE.VBComponent) As String
'ALeXceL#Gmail.com
Dim strWB_Date1904 As String
Dim strWS_EnableCalculation As String
Dim strChrt_PlotBy As String
Dim strFRM_Cycle As String
On Error Resume Next
strWB_Date1904 = oVBComp.Properties("Date1904")
strWS_EnableCalculation = oVBComp.Properties("EnableCalculation")
strChrt_PlotBy = oVBComp.Properties("PlotBy")
strFRM_Cycle = oVBComp.Properties("Cycle")
If strWB_Date1904 <> "" Then
fnGetDocumentTypePreffix = "WB_"
ElseIf strWS_EnableCalculation <> "" Then
fnGetDocumentTypePreffix = "WS_"
ElseIf strChrt_PlotBy <> "" Then
fnGetDocumentTypePreffix = "CH_"
ElseIf strFRM_Cycle <> "" Then
fnGetDocumentTypePreffix = "FR_"
Else
Stop 'This isn't expected to happen...
End If
End Function

Unable to assign formula to cell range in Excel

Someone else's code in the project, that I am trying to fix up.
listO.Range(i, j).FormulaR1C1 = FormulaMatrix(i, j)
where FormulaMatrix(i, j) is always a String value. Whatever random/test value, I try with, is being assigned successfully, except when it is a formula, eg.
=IF(LENGTH([#Units])>0;[#SalesAmount]-[#DiscountAmount]0)
If I remove the = sign in the beginning of the formula, it gets assigned correctly, but then it's useless, because it's not a formula.
#Units, #SalesAmount, #DiscountAmount are references/names of columns.
So, when assigning a formula, I get an exception HRESULT: 0x800A03EC. I looked up in this answer in order to get explanation and followed some of the instructions there. I determined that my problem is the following: the problem happens due to a function entered in a cell and it is trying to update another cell.
Checked out also this post. I tried quite different (like putting just the formulas without = and then run over again and put the equal signs), but same problem.
I am clueless of how to approach this.
.formulalocalworks! (While .formula, .value and .formular1c1 don't.)
I've just started working with VB.NET and came into a very similar issue. This was my simplified data at first (Table1 in Sheet1):
Then after applying the code below I had this:
The whole code for the form:
Imports Excel = Microsoft.Office.Interop.Excel
Public Class Form1
'~~> Define your Excel Objects
Dim xlApp As New Excel.Application
Dim xlWorkBook As Excel.Workbook
Dim xlWorkSheet As Excel.Worksheet
Dim strAddress As String = "C:\Temp\SampleNew.xlsx"
Dim list1 As Object
Private Sub btnOpen_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnOpen.Click
'~~> Add a New Workbook (IGNORING THE TWO DOT RULE)
xlWorkBook = xlApp.Workbooks.Open(strAddress)
'~~> Display Excel
xlApp.Visible = True
'~~> Set the relevant sheet that we want to work with
xlWorkSheet = xlWorkBook.Sheets("Sheet1")
With xlWorkSheet
'~~> Change the range into a tabular format
list1 = .ListObjects("Table1")
End With
list1.range(2, 4).formulalocal = "=IF(LEN([#Month])>5;[#Income]-[#MoneySpent];0)"
'~~> Save the file
xlApp.DisplayAlerts = False
xlWorkBook.SaveAs(Filename:=strAddress, FileFormat:=51)
xlApp.DisplayAlerts = True
'~~> Close the File
xlWorkBook.Close()
'~~> Quit the Excel Application
xlApp.Quit()
'~~> Clean Up
releaseObject(xlApp)
releaseObject(xlWorkBook)
End Sub
'~~> Release the objects
Private Sub releaseObject(ByVal obj As Object)
Try
System.Runtime.InteropServices.Marshal.ReleaseComObject(obj)
obj = Nothing
Catch ex As Exception
obj = Nothing
Finally
GC.Collect()
End Try
End Sub
End Class
#Siddharth Rout helped a lot to build this code, as he owns this awesome site: http://www.siddharthrout.com/
The error might be coming from your current data, respectively, the layout of the sheet. I would suggest you to check what is inside the listO.Range(i, j).FormulaR1C1 before you assign the formula.
I have had a case where the range has already got wrong data inside, and then strangely, I don't know why, I cannot assign the new formula.
If that is the case - try clearing the value of the range and then assigning the formula:
listO.Range(i, j).FormulaR1C1 = ""
listO.Range(i, j).FormulaR1C1 = FormulaMatrix(i, j)
The problem might be with your formula. Try this-
=IF(LEN([#Units])>0,[#SalesAmount]-[#DiscountAmount],0)
If this doesn't work, I would try using the .formula method instead of .formulaR1C1.. Is there any reason in particular you are using R1C1 references?

VB Com Error for Naming Sheets on a Worksheet

I keep getting an error that says
"An unhandled exception of type
'System.Runtime.InteropServices.COMException' occurred in
Microsoft.VisualBasic.dll"
Additional information: Exception from HRESULT: 0x800A03EC"
on the line where I'm trying to change the name of the sheets from Workbook reportApp. On my timeWorkbook there are headings in cells A1, then cell D1, and so on.
I want it to loop until there is no more values, but I can't change the name. I can change the name of the sheets in that workbook if I put reportApp.Sheets(s).Name = "Name this sheet", but I don't want to do that. I was wondering if there was any problem with my type or code that would get around this?
Private Sub generateReportButton_Click(sender As Object, e As EventArgs) Handles generateReportButton.Click
Dim timeApp As Excel.Application = New Excel.Application
Dim timeClockPath As String = "C:\Users\njryn_000\Desktop\Project ACC\Clock-In Excel\TimeClock.xlsx"
Dim timeWorkbook As Excel.Workbook = timeApp.Workbooks.Open(timeClockPath, ReadOnly:=False, IgnoreReadOnlyRecommended:=True, Editable:=True)
Dim timeWorksheet As Excel.Worksheet = timeWorkbook.Worksheets("TA")
Dim reportApp As Excel.Application = New Excel.Application
Dim reportPath As String = "C:\Users\njryn_000\Desktop\Project ACC\Report\Blank Timecard Report9.xlsx"
Dim reportWorkbook As Excel.Workbook = reportApp.Workbooks.Open(reportPath, ReadOnly:=False, IgnoreReadOnlyRecommended:=True, Editable:=True)
Dim reportWorksheet As Excel.Worksheet = reportWorkbook.Worksheets("Sheet" & 1)
Dim s As Integer
Dim i As Integer
Dim f As Integer
Dim taName As String
Dim taID As String
i = 0
f = 0
s = 1
With timeWorksheet.Range("A1")
Do
i += 3
s += 1
reportApp.Sheets(s).Name = timeWorksheet.Range("A1").Offset(0, i).Value
Loop Until IsNothing(timeWorksheet.Range("A1").Offset(0, 0).Offset(0, i).Value)
You've already solved your problem but you may not be able to add an answer yet so here is some feedback.
When you use a With block you can then refer to whatever you referenced at the top of that block with a single dot ('.') after that. Its a syntax which reduces writing the same thing over and over. In the snippet below I've removed all references to timeWorksheet.Range("A1") and added a leading dot.
With timeWorksheet.Range("A1")
Do
i += 3
s += 1
' Since you are using a With block this statement is simplified.
reportApp.Sheets(s).Name = .Offset(0, i).Value
' I removed the .Offset(0, 0) as it is redundant.
' If you have it in to solve a bug you can put it back.
Loop Until IsNothing(.Offset(0, i).Value)
' More code here...
End With
Also you've realised that you can use the Val() function to fix your code. Reading the documentation, it explains that this function will take a string and begin reading a number from it, ignoring whitespace. As soon as it reaches a non-numeric, non-whitespace character it stops and returns the number ignoring whatever else is in the string.
It seems that this isn't really solving your problem, it just works around it. I'd look at what other characters are present in the cells you are looping through and deal with them explicitly. Otherwise you might end up with strange results.

Find specific data in excel sheet using vb.net

I have been trying to find a specific data in Excel through a WinForm application and then try to fetch the next value in the same row using vb.net.
Example:
ElementName Value
Age 24
Name John Clan
Music Rock
Suppose if I want to find Age. then I want to make the code return as 24 searching it from Excel file.
I tried pulling the whole Excel data into a Dataset but it wasn't helpful.
Kindly guide me.
Imports Interop = Microsoft.Office.Interop.Excel
'Find In Excel
Private Function FindValueInExcel(ByVal sTextToFind)
Dim currentFind As Interop.Range = Nothing
Dim firstFind As Interop.Range = Nothing
Dim xlappFirstFile As Interop.Application = Nothing
Dim sSearchedValue As String
xlappFirstFile = CreateObject("Excel.Application")
xlappFirstFile.Workbooks.Open("D:\Sample.xlsx")
Dim rngSearchValue As Interop.Range = xlappFirstFile.Range("A1", "C5")
currentFind = rngSearchValue.Find(sTextToFind, , _
Interop.XlFindLookIn.xlValues, Interop.XlLookAt.xlPart, _
Interop.XlSearchOrder.xlByRows, Interop.XlSearchDirection.xlNext, False)
If Not currentFind Is Nothing Then
sSearchedValue = DirectCast(DirectCast(currentFind.EntireRow, Microsoft.Office.Interop.Excel.Range).Value2, System.Object)(1, 3).ToString()
Else
sSearchedValue = ""
End If
Return sSearchedValue
End Function
Link which helped me - http://msdn.microsoft.com/en-us/library/e4x1k99a.aspx?cs-save-lang=1&cs-lang=vb#code-snippet-1