How to move to next row in dataset and display in hyperlink - vb.net

I'm writing an email application that will be used to send HTML news articles to clients.
I'm using a dataset to return the headlines to display to the client. When I loop through the dataset the the latest record is returned but latest headline link is not displayed. So the outputted HTML is the same headline everytime, which is the first record in the dataset. How do I move to the next record in the data set and get the outputted HTML to display the next/correct headline?
Here is a sample of my code:
'Code to populate dataset
Public Function GetHeadline(ByVal ArticleID As Integer) As DataSet
Try
Dim objConn As SqlConnection = New SqlConnection()
objConn.ConnectionString = myConnectionString
objConn.Open()
ds = New DataSet
ds.Clear()
Dim sqlCommand As String = "SomeSql"
Dim objCmd As SqlCommand = New SqlCommand(sqlCommand, objConn)
Dim dataAdapter As SqlDataAdapter = New SqlDataAdapter(objCmd)
dataAdapter.Fill(ds)
Catch ex As Exception
MsgBox(ex.ToString)
GetHeadline = Nothing
End Try
Return ds
End Function
'Code to populate link
If GroupID = 4 Then
iLocation1 = HTMLbody.IndexOf("{!HeadlineID")
While iLocation1 > 0
iLocation2 = HTMLbody.IndexOf("}", iLocation1)
sHeadLineTag = HTMLbody.Substring(iLocation1 + 1, iLocation2 - iLocation1 - 1)
dtReport = clsGlobal.globalReportCatalog.GetHeadline2()
clsGlobal.globalReportCatalog.SetHeadlinePropertiesFromRow(dtReport.Rows(0))
With clsGlobal.globalReportCatalog
For i As Integer = 0 To dtReport.Rows.Count
If i < dtReport.Rows.Count - 1 Then
i = i + 1
End If
Dim ID As Integer = dtReport.Rows(i)("ArticleID")
sHyperTag = "" & .HeadlineReportName & " - " & .HeadlineTitle & ""
sHeadlineDescription = .HeadlineDescription
HTMLbody = HTMLbody.Replace("{!Report.Description}", sHeadlineDescription)
Next
End With

I don't see why you need
For i As Integer = 0 To dtReport.Rows.Count
If i < dtReport.Rows.Count - 1 Then
i = i + 1
End If
Can't you use
Dim ID As Integer = dtReport.Rows(dtReport.Rows.Count - 1)("ArticleID")
or was there supposed to be a row movenext in the loop you forgot?

Related

DataGridView moves rows to bottom when cell is updated with Unbound data

I have a DataGridView that is styled with code and is using data from a SQLite Database
The Database is NOT bound to the DataGridView. A number of events are triggered when I click on a row.
First the Database is updated with today's date.
And the cell that contain's that date reflects the change.
I then call a sort on the column based on the cells value. With this code
dgvLinks.Sort(dgvLinks.Columns(3), ListSortDirection.Ascending)
The process works as expected with no issues IF I omit these lines of code from the Sub Routine ViewSearches() that populates the DataGridView.
If rowCount <= 25 Then
maxRowCount = 25 - rowCount
For iA = 1 To maxRowCount
dgvLinks.Rows.Add(" ")
Next
End If
I can use these empty rows if I make a call to repopulate the DataGridView with ViewSearches()
I am trying to avoid this design as it seems like a over use of resource.
The ERROR that is happening is the 4 rows that contain data are moved to the bottom of the DataGridView and above these 4 rows with data are the empty rows. I will post the relevant code below.
My question How can I keep the empty rows and populate DataGridView so the rows with data are at the top of the DataGridView?
Here is a Screen Shot after I selected LID 2. It is updated and bubbled to the bottom of the DGV.
Private Sub ViewSearches()
Dim intID As Integer
Dim strChannelName As String
Dim strLinkAddress As String
Dim strLastVisit As String
Dim strLinkType As String
Dim rowCount As Integer
Dim maxRowCount As Integer
'Dim emptyStr As String = " "
Using conn As New SQLiteConnection($"Data Source = '{gv_dbName}';Version=3;")
conn.Open()
Using cmd As New SQLiteCommand("", conn)
'cmd.CommandText = "SELECT * FROM LinkTable"
' Line of CODE Above works with If statement in While rdr
'==========================================================
'cmd.CommandText = "SELECT * FROM LinkTable WHERE ytSiteType = 'News'"
cmd.CommandText = "SELECT * FROM LinkTable WHERE ytSiteType = #site"
cmd.Parameters.Add("#site", DbType.String).Value = gvSLT
Using rdr As SQLite.SQLiteDataReader = cmd.ExecuteReader
'dgvLinks.DataSource = rdr
'Statement Above use when DB is bound to dgvLinks
'=================================================
While rdr.Read()
intID = CInt((rdr("LID")))
strChannelName = rdr("ytChannelName").ToString
strLinkAddress = rdr("ytLinkAddress").ToString
strLastVisit = rdr("ytLastVisit").ToString
strLinkType = rdr("ytSiteType").ToString
'If strLinkType = gvSLT Then
dgvLinks.Rows.Add(intID, strChannelName, strLinkAddress, strLastVisit)
rowCount = rowCount + 1
'End If
End While
dgvLinks.Sort(dgvLinks.Columns(3), ListSortDirection.Ascending)
End Using
If rowCount <= 25 Then
maxRowCount = 25 - rowCount
For iA = 1 To maxRowCount
dgvLinks.Rows.Add(" ")
Next
End If
End Using
End Using
'FindEmpty()
End Sub
Click Event with Update to Database
Private Sub dgvLinks_CellClick(sender As System.Object, e As System.Windows.Forms.DataGridViewCellEventArgs) Handles dgvLinks.CellClick
selRow = e.RowIndex
If e.RowIndex = -1 Then
gvalertType = "4"
frmAlert.ShowDialog()
Exit Sub
End If
'Dim col As DataGridViewColumn = Me.dgvLinks.Columns(e.ColumnIndex)
Dim row As DataGridViewRow = Me.dgvLinks.Rows(e.RowIndex)
If row.Cells(2).Value Is Nothing Then
gvalertType = "5"
frmAlert.ShowDialog()
Return
Exit Sub
ElseIf gvTxType = "View" Then
webPAGE = row.Cells(2).Value.ToString()
siteID = CInt(row.Cells(0).Value.ToString())
UpdateSiteData()
''MsgBox("Stop " & selRow)
'dgvLinks.ClearSelection()
'dgvLinks.Refresh()
'dgvLinks.RefreshEdit()
Process.Start(webPAGE)
'dgvLinks.Columns.Clear()
''dgvLinks.Rows.Clear()
''ViewSearches()
ElseIf gvTxType = "Delete" Or gvTxType = "Update" Then
gvID = CInt(row.Cells(0).Value)
gvSiteName = row.Cells(1).Value.ToString
gvSiteURL = row.Cells(2).Value.ToString
frmADE.Show()
Close()
End If
End Sub
Update Routine
Public Sub UpdateSiteData()
Dim dateToday = Date.Today
dateToday = CDate(CDate(Date.Today).ToString("M-d-yyyy"))
Using conn As New SQLiteConnection($"Data Source = '{gv_dbName}';Version=3;"),
cmd As New SQLiteCommand("UPDATE LinkTable SET ytLastVisit = #ytLastVisit WHERE LID =" & siteID, conn)
conn.Open()
cmd.Parameters.Add("#ytLastVisit", DbType.String).Value = dateToday.ToString("M-d-yyyy")
cmd.ExecuteNonQuery()
dgvLinks.Rows(selRow).Cells(3).Value = dateToday.ToString("M-d-yyyy")
'Line of code above INSERTS value in Last Visit Column at the correct ROW
'NOT needed if you reload data from the database
'=========================================================================
'dgvLinks.Refresh()
'dgvLinks.RefreshEdit()
dgvLinks.Sort(dgvLinks.Columns(3), ListSortDirection.Ascending)
End Using
End Sub
You will see a number of things I have tried commented out.
As I said I can FIX the issue if I make a call to the ViewSearches() Sub Routine.
Private Sub StyleDGV()
'Sets Design of the DataGridView
'===============================
dgvLinks.DefaultCellStyle.Font = New Font("Times New Roman", 13.0F, FontStyle.Bold)
dgvLinks.ColumnCount = 4
dgvLinks.Columns(0).Width = 60 'ID
dgvLinks.Columns(1).Width = 325 'Site Name 325
dgvLinks.Columns(2).Width = 860 'Site Url 860
dgvLinks.Columns(3).Width = 154 'LastVisit 140
'Option with no blank rows increase col count to 5
'OR increase width of col(3) WHY? because the scroll bar is not showing
' TOTAL Width 1450 Height 488
'=============================
'To Set Col Header Size Mode = Enabled
'To Set Col Header Default Cell Styles DO in Properties
'dgvLinks.Columns(6).DefaultCellStyle.Format = "c"
dgvLinks.ColumnHeadersHeight = 10 'Sans Serif 'Tahoma
dgvLinks.ColumnHeadersDefaultCellStyle.Font = New Font("Sans Serif", 12.0F, FontStyle.Bold)
dgvLinks.ColumnHeadersDefaultCellStyle.ForeColor = Color.Blue
dgvLinks.DefaultCellStyle.BackColor = Color.LightGoldenrodYellow
'DGV Header Names
dgvLinks.Columns(0).Name = "LID"
dgvLinks.Columns(1).Name = "Site Name"
dgvLinks.Columns(2).Name = "Site URL"
dgvLinks.Columns(3).Name = "Last Visit"
dgvLinks.Columns(0).SortMode = DataGridViewColumnSortMode.NotSortable
dgvLinks.Columns(1).SortMode = DataGridViewColumnSortMode.NotSortable
dgvLinks.Columns(2).SortMode = DataGridViewColumnSortMode.NotSortable
dgvLinks.Columns(3).SortMode = DataGridViewColumnSortMode.NotSortable
End Sub
Any one following this question the FIX that permitted keeping the empty rows was to just omit the sort command in the Update to Database Sub Routine
As far as getting the data from the SQLite DB into the grid… you almost have it in the ViewSearches method. The command text looks good; however you are using an SQLiteDataReader. This is resorting to reading the data line by line.
I suggest you use the SQLiteDataAdapter instead. With it you can get the DataTable from the DB in one shot. First create and initialize a DataSet, then create a new SQLiteDataAdapter then add your command to the data adapter something like…
DataSet ds = new DataSet();
using (SQLiteDataAdapter sqlDA = new SQLiteDataAdapter()) {
conn.Open();
sqlDA.SelectCommand = cmd.CommanText;
sqlDA.Fill(ds, “tableName”);
if (ds.Tables.Count > 0) {
//return ds.Tables[“tableName”];
dgvLinks.DataSource = ds.Tables[“tableName”];
}
}
This will add a DataTable to the DataSet ds called “tableName” if the query succeeded.
Then simply use that DataTable as a DataSource to the grid… something like…
dgvLinks.DataSource = ds.Tables[“tableName”];

VB.NET I generated pictureboxes and LOOP it to my rows.Count, the problem is how can i call the PHOTOS?

So basically i generated picture boxes through codes to increment it whenever i ADD data in my database.. my problem is how can i get the PHOTOS from my database to be in my picture boxes.
Here is my code:
connection.Open()
cmd.Connection = connection
cmd.CommandType = CommandType.Text
cmd.CommandText = "SELECT ID, Candidate_Name, Candidate_Fname,c_Photo from softeng.candidates"
da.SelectCommand = cmd
da.Fill(pdt)
For j As Integer = 0 To pdt.Rows.Count - 1
Dim a As String = pdt.Rows(j).Item(0)
Dim b As String = pdt.Rows(j).Item(1)
Dim c As String = pdt.Rows(j).Item(2)
Dim pb As New PictureBox
Dim lb As New Label
lb.Name = "lbid" & j
lb.Text = "Candidate ID:" & a & vbCrLf & b + c & vbCrLf
lb.AutoSize = True
lb.Size = New Point(100, 100)
pb.Name = "pb" & j
pb.Text = a
pb.AutoSize = True
pb.Size = New Point(100, 100)
pb.BorderStyle = BorderStyle.Fixed3D
FlowLayoutPanel1.Controls.Add(pb)
FlowLayoutPanel1.Controls.Add(lb)
Next
connection.Close()
Catch ex As Exception
MessageBox.Show(ex.Message)
End Try
My codes for retrieving Pictures from my Database
Dim data As Byte() = DirectCast(dr("Photo"), Byte())
Dim ms As New MemoryStream(data)
PictureBox1.Image = Image.FromStream(ms)
How can i put it to my code so i can retrieve photos when im looping my picture boxes?
Basically, you must make sure you are saving the images as binaries in database, then basically you read the binary information and convert it to an image object, showing in your control.
I'm pretty sure the link below has everything you need:
https://www.aspsnippets.com/Articles/Display-Binary-Image-from-Database-in-PictureBox-control-in-Windows-Application-using-C-and-VBNet.aspx

Image.FromStream is not a member of System.Windows.Forms.DataGridViewImageColumn

So I use this code to display my data in a DataGridView:
Sub display_Infodata()
DGUSERS.Rows.Clear()
Dim sql As New MySqlDataAdapter("select * from tbl_info", con)
Dim ds As New DataSet
DGUSERS.AllowUserToAddRows = False
DGUSERS.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill
DGUSERS.RowTemplate.Height = 40
sql.Fill(ds, 0)
For i As Integer = 0 To ds.Tables(0).Rows.Count - 1
Dim xx As Integer = DGUSERS.Rows.Add
Dim uid As String = ds.Tables(0).Rows(i).Item(0).ToString
Dim sqls As New MySqlDataAdapter("select * from tbl_other where userid='" & uid & "'", con)
Dim dss As New DataSet
sqls.Fill(dss, 0)
With DGUSERS.Rows(xx)
If dss.Tables(0).Rows.Count > 0 Then
.Cells(0).Value = uid
.Cells(1).Value = ds.Tables(0).Rows(i).Item(2).ToString
.Cells(2).Value = ds.Tables(0).Rows(i).Item(3).ToString
.Cells(3).Value = ds.Tables(0).Rows(i).Item(4).ToString
.Cells(4).Value = ds.Tables(0).Rows(i).Item(5).ToString
.Cells(5).Value = ds.Tables(0).Rows(i).Item(6).ToString
.Cells(6).Value = dss.Tables(0).Rows(0).Item(1).ToString
.Cells(7).Value = ds.Tables(0).Rows(0).Item(2).ToString
.Cells(8).Value = ds.Tables(0).Rows(0).Item(8).ToString
.Cells(9).Value = ds.Tables(0).Rows(0).Item("Image")
.Cells(10).Value = dss.Tables(0).Rows(0).Item(2).ToString
.Cells(11).Value = dss.Tables(0).Rows(0).Item(3).ToString
Else
End If
End With
Next
End Sub
It displays and works, but my problem is that when I try to display the data in the DataGridView of another form it shows the following error:
This is what I use:
Try
With View_Info
Dim index As Integer
Dim selectedRow As DataGridViewRow
selectedRow = DGUSERS.Rows(index)
.UserID.Text = DGUSERS.SelectedRows(0).Cells("UserID").Value
.UserType.Text = DGUSERS.SelectedRows(0).Cells("UserType").Value
.Fname.Text = DGUSERS.SelectedRows(0).Cells("Firstname").Value
.Mname.Text = DGUSERS.SelectedRows(0).Cells("Middlename").Value
.Lname.Text = DGUSERS.SelectedRows(0).Cells("Lastname").Value
.Contact.Text = DGUSERS.SelectedRows(0).Cells("Contact").Value
.Standing.Text = DGUSERS.SelectedRows(0).Cells("Standing").Value
.Guardian.Text = DGUSERS.SelectedRows(0).Cells("Guardian").Value
.ContactG.Text = DGUSERS.SelectedRows(0).Cells("GuardianContact").Value
.DPCreated.Text = DGUSERS.SelectedRows(0).Cells("DateCreated").Value
.DPValidity.Text = DGUSERS.SelectedRows(0).Cells("Validity").Value
Dim img As Byte()
img = DGUSERS.SelectedRows(0).Cells("Image").Value
Dim ms As New MemoryStream(img)
.UploadImage.Image = Image.FromStream(ms)
.Show()
.Focus()
End With
Catch ex As Exception
MsgBox(ex.Message & " Please select a corresponding records.", MsgBoxStyle.Exclamation)
End Try
Any help please?
It's hard to see the full picture, but the problem is most likely that you have created a DataGridViewImageColumn which you've chosen to call Image.
The compiler will always choose local variables, properties or classes over library/pre-imported namespace objects with the same name. Thus, your column by the name Image will be used rather than System.Drawing.Image because the former is "more local".
Try specifying the namespace as well and it should work:
.UploadImage.Image = System.Drawing.Image.FromStream(ms)
So what I did to solve this is by:
Dim pCell As New DataGridViewImageCell
pCell = Me.DGUSERS.Item("Picture", e.RowIndex)
.UploadImage.Image = byteArrayToImage(pCell.Value)
and using this function:
Private Function byteArrayToImage(ByVal byt As Byte()) As Image
Dim ms As New System.IO.MemoryStream()
Dim drwimg As Image = Nothing
Try
ms.Write(byt, 0, byt.Length)
drwimg = New Bitmap(ms)
Finally
ms.Close()
End Try
Return drwimg
End Function

Performance improvement on vb.net code

I need to write 50 million records with 72 columns into text file, the file size is growing as 9.7gb .
I need to check each and every column length need to format as according to the length as defined in XML file.
Reading records from oracle one by one and checking the format and writing into text file.
To write 5 crores records it is taking more than 24 hours. how to increase the performance in the below code.
Dim valString As String = Nothing
Dim valName As String = Nothing
Dim valLength As String = Nothing
Dim valDataType As String = Nothing
Dim validationsArray As ArrayList = GetValidations(Directory.GetCurrentDirectory() + "\ReportFormat.xml")
Console.WriteLine("passed xml")
Dim k As Integer = 1
Try
Console.WriteLine(System.DateTime.Now())
Dim selectSql As String = "select * from table where
" record_date >= To_Date('01-01-2014','DD-MM-YYYY') and record_date <= To_Date('31-12-2014','DD-MM-YYYY')"
Dim dataTable As New DataTable
Dim oracleAccess As New OracleConnection(System.Configuration.ConfigurationManager.AppSettings("OracleConnection"))
Dim cmd As New OracleCommand()
cmd.Connection = oracleAccess
cmd.CommandType = CommandType.Text
cmd.CommandText = selectSql
oracleAccess.Open()
Dim Tablecolumns As New DataTable()
Using oracleAccess
Using writer = New StreamWriter(Directory.GetCurrentDirectory() + "\FileName.txt")
Using odr As OracleDataReader = cmd.ExecuteReader()
Dim sbHeaderData As New StringBuilder
For i As Integer = 0 To odr.FieldCount - 1
sbHeaderData.Append(odr.GetName(i))
sbHeaderData.Append("|")
Next
writer.WriteLine(sbHeaderData)
While odr.Read()
Dim sbColumnData As New StringBuilder
Dim values(odr.FieldCount - 1) As Object
Dim fieldCount As Integer = odr.GetValues(values)
For i As Integer = 0 To fieldCount - 1
Dim vals As Array = validationsArray(i).ToString.ToUpper.Split("|")
valName = vals(0).trim
valDataType = vals(1).trim
valLength = vals(2).trim
Select Case valDataType
Case "VARCHAR2"
If values(i).ToString().Length = valLength Then
sbColumnData.Append(values(i).ToString())
'sbColumnData.Append("|")
ElseIf values(i).ToString().Length > valLength Then
sbColumnData.Append(values(i).ToString().Substring(0, valLength))
'sbColumnData.Append("|")
Else
sbColumnData.Append(values(i).ToString().PadRight(valLength))
'sbColumnData.Append("|")
End If
Case "NUMERIC"
valLength = valLength.Substring(0, valLength.IndexOf(","))
If values(i).ToString().Length = valLength Then
sbColumnData.Append(values(i).ToString())
'sbColumnData.Append("|")
Else
sbColumnData.Append(values(i).ToString().PadLeft(valLength, "0"c))
'sbColumnData.Append("|")
End If
'sbColumnData.Append((values(i).ToString()))
End Select
Next
writer.WriteLine(sbColumnData)
k = k + 1
Console.WriteLine(k)
End While
End Using
writer.WriteLine(System.DateTime.Now())
End Using
End Using
Console.WriteLine(System.DateTime.Now())
'Dim Adpt As New OracleDataAdapter(selectSql, oracleAccess)
'Adpt.Fill(dataTable)
Return Tablecolumns
Catch ex As Exception
Console.WriteLine(System.DateTime.Now())
Console.WriteLine("Error: " & ex.Message)
Console.ReadLine()
Return Nothing
End Try

how to update specific cell in data grid view using SQL and VB.net

I am trying to update a specific cell in datagridview using vb.net and sql ( or any other method)
I am using this code to split somme strings and save it into database.
Private Sub SalveazaData()
Dim list As String() = rtbComData.Text.Split(Environment.NewLine.ToCharArray())
SmdDataDataSet1.SearchAdrese.Rows.Clear()
SmdTableTableAdapter.ClearSearchAdrese()
Me.SearchAdreseTableAdapter.Update(Me.SmdDataDataSet1.SearchAdrese)
For Each Row As String In list
If Not (Row = "AT+DSCAN" Or Row = "OK" Or Row = "" Or Row = "AT+RSSI") Then
Dim s As String() = Split(Row, "|")
Dim aRow As smdDataDataSet1.smdTableRow = SmdDataDataSet1.smdTable.NewsmdTableRow()
aRow.Model = s(0)
aRow.AdresaUnica = s(1)
aRow.StatusModul = "ACTIVE"
Try
SmdDataDataSet1.SearchAdrese.Rows.Add(s(1))
SmdDataDataSet1.smdTable.Rows.Add(aRow)
Catch ex As Exception
Dim u As String
u = SmdTableTableAdapter.UpdateInactivActiv()
End Try
End If
Next
'selectzr()
salveaza()
status()
DataGridView1.Refresh()
End Sub
The table has the columns
Model | Adresa Unica | Status | time | InstAddress |
ZR 123456 active
ZR 654321 active
What i want to do is update the row with the address "123456" or "654321" and write in their specific cell , in this case the cell from the column | time | a value .
Can you please help me .?
I have made some digging and i have fund an answer.
please see below the code i've used in my application
Private Sub GroupCommandRtime()
Dim list As String() = rtbComData.Text.Split(Environment.NewLine.ToCharArray())`enter code here`
Dim ListaAdrese As List(Of String) = GetAdreseID()
For Each Row As String In list
For Each _Adresa As String In ListaAdrese
If Not (Row = "at+remote=" Or Row = "AT+RSSI" Or Row = "OK") Then
Try
Dim s As String() = Split(Row, " ")
Dim con As New SqlConnection
Dim cmd As New SqlCommand
con.ConnectionString = "Data Source=.\SQLEXPRESS;AttachDbFilename=|DataDirectory|\Database\smdData.mdf;Integrated Security=True;User Instance=True"
con.Open()
cmd.Connection = con
cmd.CommandText = "UPDATE smdTable SET datetime='" + s(3) + "' WHERE AdresaUnica = '" + s(0) + "'"
cmd.ExecuteNonQuery()
Me.SmdTableTableAdapter.Fill(Me.SmdDataDataSet1.smdTable)
DataGridView1.Refresh()
Catch ex As Exception
End Try
End If
Next
Next
End Sub