vb.net listview display next record - vb.net

I have a problem when displaying the records in ListView. The database I have right now have a 10k + of records (rows). When pulling the data to ListView, It takes a lot of time so I limit the displayed items to 50. I can successfully display the 50 items. But my problem is how do I display the next 51-100 record when the user click the "Next Page" button? I have no idea where to start. Please help me. Thanks.
da = New MySqlDataAdapter
Dim strSql As String = "SELECT * FROM tbl_questions"
ListView1.Items.Clear()
Call connect()
da.SelectCommand = New MySqlCommand(strSql)
da.SelectCommand.Connection = cn
da.Fill(ds)
Dim i As Integer
For i = 0 To ds.Tables(0).Rows.Count - 1
If i = 49 Then
Exit For
End If
Dim lv As ListViewItem = ListView1.Items.Add(ds.Tables(0).Rows(i)("function"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("subject"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("level"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("type"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("question"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("choice_a"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("choice_b"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("choice_c"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("choice_d"))
lv.SubItems.Add(ds.Tables(0).Rows(i)("correct_ans"))
Next
da.Dispose()

I am assuming you are using winforms. The ListView control does have a virtualization feature that you can try by using the ListView.VirtualMode Property and ListView.CacheVirtualItems Event. See if these MSDN links help you.
From above link:
Virtual mode can be useful under many circumstances. If a ListView object must be populated from a very large collection already in memory, creating a ListViewItem object for each entry can be wasteful. In virtual mode, only the items required are created. In other cases, the values of the ListViewItem objects may need to be recalculated frequently, and doing this for the whole collection would produce unacceptable performance. In virtual mode, only the required items are calculated.

Related

read from SQL to Button

please help on this issue, i want to read ID from SQL to different button but still i cant able to do it. please help.
this is the code i tried.
this code read same ID in both button instead of different id in different button. see the screenshot for your reference.
Dim dt As New DataTable
Dim da As New SqlDataAdapter("select Locker_ID from Locker", colnnn)
da.Fill(dt)
For Each row As DataRow In dt.Rows
Button2.Text = row.Item("Locker_ID")
Button1.Text = row.Item("Locker_ID")
Next
You do not only have to loop the rows but also the buttons. If you have 2 locker rows, your loop executes the loop body twice. I.e., the first locker id is assigned to both buttons and then the second locker id is assigned to the same buttons again, overwriting the first value.
Dim dt As New DataTable
Dim da As New SqlDataAdapter("select Locker_ID from Locker", colnnn)
da.Fill(dt)
Dim i As Integer = 1
For Each row As DataRow In dt.Rows
Controls("Button" & i).Text = row.Item("Locker_ID")
i = i + 1
Next
This will assign the first Locker_ID to Button1, the second one to Button2, etc.
The Controls collection allows you to access the controls by name by using a string as index.
Note that you can change the name of the buttons. If you name the buttons where you want to have the locker id as btnLocker1, btnLocker2, btnLocker3 etc. then Controls("btnLocker" & i).Text = row.Item("Locker_ID") will automatically select the right buttons.
It is advisable to give your controls speaking names. Also, do this before creating event handlers. E.g., nobody knows what Sub Button17_Click is supposed to do; however, if you name the button btnPrint, the winforms designer will automatically create a Sub named btnPrint_Click when you double click the button.
See also: For Each Loops

Open Form faster & remove "System.Data.DataRowView" flicker from Combobox data binding

I have plenty Comboboxes on my form (around 20), and all of them are displaying items from different tables of my DB. If I put all code on Form_Load event then Form opens very slow. So I tried to paste code in different varieties, and currently I'm stuck at Combobox_Enter event - now Form loads fast, but when I click on drop-down of combobox I see sometimes "System.Data.DataRowView" flickering before items are loaded in Combobox. Is there any way to achieve both - fast Form opening & Combobox loading Items without flickering ?....So far I tested with Form_Activate,Form_GotFocus(not working) and Combobox_GotFocus,Combobox_MouseHover,Combobox_Click(not exactly perfect). This is an example of how I bind my Comboboxes:
Private Sub Combobox1_Enter(sender As Object, e As EventArgs) Handles Combobox1.Enter
Dim SQL As String = "SELECT Name from MyTable"
Dim dtb As New DataTable()
Using con As OracleConnection = New OracleConnection("Data Source=MyDB;User Id=Lucky;Password=MyPassword;")
Try
con.Open()
Using dad As New OracleDataAdapter(SQL, con)
dad.Fill(dtb)
End Using
Combobox1.DataSource = dtb
Combobox1.DisplayMember = "Name"
con.Close()
Catch ex As Exception
MessageBox.Show(ex.Message)
Finally
con.Dispose()
End Try
Combobox1.SelectedIndex = -1
End Using
End Sub
I also tried with declaring " Public con As OracleConnection", but output is same as I have It now.
Any help appreaciated !
When binding a ComboBox or the like, you should pretty much ALWAYS set the DataSource last. You are not and that's why you see "System.Data.DataRowView" displayed.
When you bind a list to a ComboBox, the control will display data from the column or property specified in the DisplayMember if there is one, otherwise it will call ToString on each item. In your code, you first set the DataSource and, at that point, the DisplayMember is not set so the control calls ToString on each item. The result of that is "System.Data.DataRowView". When you then set the DisplayMember, those values that the control just went to the trouble of generating and displaying are discarded and the DisplayMember is used to get new values.
Even if you weren't seeing that effect, you'd still be wasting your control's time generating values that you don't want. ALWAYS set the DisplayMember, ValueMember or the like before setting the DataSource in code unless you have a specific reason not to. The only reason that I'm aware of is when you're binding a CheckedListBox, which has an issue when DataSource is set last.
By the way, shouldn't you have a test there to only retrieve data if there is no data already loaded? You don't want to reload data if the user returns to the same control, do you?

Showing a single record in datagridview from access database vb.net

What I have is a small application that has a datagridview and an Access DB. There are 10 records in the database and they all show up in the datagridview when the app is launched. I need to be able to do two things:
I need to be able to enter an id number in a textbox and have JUST that record show in the DGV.
I need to be able to have it show all the records again (using a different click event of course).
I am able to choose the record with this:
Dim row As DataRow
row = ProductsDataSet.tblProducts.FindByItemNum(txtNumber.Text)
but I am unable to figure out how to show just that record in the DGV.
(Let me clarify...I THINK I am choosing the record simply because no exceptions are being thrown).
Any guidance here would be greatly appreciated. Thank you.
John
An option is to set the dataSource of your dataGridView to the data you'd like to display. Below is an implementation using dataTables.
Class MyForm
Dim dataTableAll, dataTableOneID, As DataTable
Sub show1ID_Click
Dim id As Integer = InputBox("Enter ID")
dataTable2 = dataTable1.Select("[ID] = id").CopyToTable
dataGridView.DataSource = dataTableOneID
End Sub
Sub showAll_Click
dataGridView.DataSource = dataTableAll
End Sub
End Class

How to Ommit DataGridViewRow from DataSource Based on Another Table's Data

I have a DataGridView filled with Bills from a DataTable (which is set as it's DataSource). These Bills are shown to my engineers so that they can build a Bill of Materials.
This is the SQL query which gets all my Bills:
SELECT *
FROM Bills
ORDER BY Case IsNumeric(JobNumber)
WHEN 1 THEN Replicate('0', 50 - Len(JobNumber)) + JobNumber ELSE JobNumber END
This sorts the bills by job number (some are numbers, some are strings and some are a mix of integers and characters).
Features
They can open the bill to view it (Read only) or to edit it.
Further explanation
If an engineer opens a Bill to edit it, it will be placed in a table named "OpenBills". I do this so that no other engineer can open the same bill and edit it while being worked on. The point of the OpenBills table is to determine which bill is opened. Once I know which bill is opened, I don't want it to be provided in their DataGridView when they go to edit a bill.
On the other hand, when the engineer searches for a bill to open as read-only, they should ALL be displayed (even the ones currently opened). The difference is I simply put a light blue color as the background of the row to notify the user that it is currently opened.
My current 'solution'
I am currently using a CellFormatting event on my DataGridview. In short, I verify if the current Bill being added is in my OpenBills table lst_OpenBills. If it is, then I verify if I am viewing the DataGridView as read-only or for editting mode. If it's in edit mode, I will hide the row. If it is in read-only, I will change it's back color.
Private Sub dgvBills_CellFormatting(sender As Object, e As System.Windows.Forms.DataGridViewCellFormattingEventArgs) Handles dgvBills.CellFormatting
Dim drv As DataRowView
If e.RowIndex >= 0 Then
If e.RowIndex <= dsBOM.Tables("dtBills").Rows.Count - 1 Then
drv = dsBOM.Tables("dtBills").DefaultView.Item(e.RowIndex)
Dim c As Color
If lst_OpenBills.ContainsKey(drv.Item("PK_Bill").ToString) Then
If int_EntryPoint = 0 Then
'Read Only
c = Color.LightBlue
e.CellStyle.BackColor = c
Else
'Edit mode
dgvBills.Rows(e.RowIndex).Visible = False
End If
End If
End If
End If
End Sub
Problem with current solution
I use AlternatingRowStyles to make it easier to read. As you can see in the following comparisons, the edit mode picture should not display the alternating row styles like that. How could I ommit the DataGridViewRow from the DataTable ? Should I just re-apply the AlternatingRowStyles?
Read Only results
Edit mode
Does anyone have any solutions? Perhaps my query to get all my bills isn't appropriate ... I use the same form for both situations (read-only & edit mode). I just differentiate them using an Enum enum_EntryPoint. Any helps or suggestions is appreciated.
You could iterate through the datatable and remove the one you have selected and redraw the datagridview. Not another SQL call just using the datatable you already have. You can reinsert the row if you want, when done, or just use that same beginning datatable to refresh the DGV.
For example if the open bill was id 1287:
Dim dtTemp As DataTable = dtOpenBills.Clone()
For Each dr As DataRow in dtOpenBills.Rows
If Cint(dr("OpenBillID")) <> 1287 Then
Dim drTemp As DataRow = dtTemp.NewRow()
drTemp = dr
dtTemp.Rows.Add(drTemp)
End If
Next
DataGridViewName.DataSource = dtTemp
DataGridViewName.Refresh() 'Might not be needed
You haven't touched the original datatable.

vb.net Bind a combobox to a datasource

Over the past few days, I've read about a thousand forum posts, and looked at many code samples, but I still can't figure this out.
My goal is to populate a combobox with values from an Access 2007 query. I can do this by using the DataSource, DisplayMember and ValueMember properties, but regardless of the data in the query, the comboboxes all just default to the to first item in the items collection and don't change when the main BindingSource is moved. I am binding the controls with this line of code:
ComboBox1.DataSource = DataSet1.qryItemSourceTest
ComboBox1.DisplayMember = "SourceTestDisplayField"
ComboBox1.ValueMember = "SourceTestIDField"
Combobox1.DataBindings.Add(New Binding("SelectedValue", qryTestBindingSource, "TestField", True))
I have also tried using a BindingSource as a DataSource.
I have also tried using an array as a DataSource.
If I drag the control on from the Data Source tab in the IDE, it will scroll through records properly, but it will only display the value and not the query 'look-up' value that I want the combobox to display. I have tried changing the DisplayMember and ValueMember properties of the combobox after dragging it on from the Data Sources tab and that seems to break the functionality as well.
I'm looking for some best practices here. I know I'm missing something easy here and I apologize for post an issue that has already been covered so many times, but I could use some individual help here.
Edit: I eventually was able to accomplish my goal using the Visual Studio IDE Properties window. The second property on a control is a Data Bindings property which expands into exactly what I needed. I just never saw this before because it was not in alphabetically order like everything else.
Hi you can do this code to populate data into combo
Try
Dim cn As New OleDbConnection
cn.ConnectionString = conString
cn.Open()
cmd.Connection = cn
cmd.CommandText = "your query"
'Execte reader function is used to hold more than one value from the table
dr = cmd.ExecuteReader()
' Fill a combo box with the datareader
Do While dr.Read = True
ComboBox1 = dr.Item(0)
Loop
cn.Close()
Catch ex As Exception
MsgBox(ex.Message)
End Try
If you have any more problems don't hesitate to ask.