I have an excel sheet with the following:
So, what I am trying to achi
Perfect Code here: (write in button)
DataObject o = (DataObject)Clipboard.GetDataObject();
if (o.GetDataPresent(DataFormats.Text))
{
if (myDataGridView.RowCount > 0)
myDataGridView.Rows.Clear();
if (myDataGridView.ColumnCount > 0)
myDataGridView.Columns.Clear();
bool columnsAdded = false;
string[] pastedRows = Regex.Split(o.GetData(DataFormats.Text).ToString().TrimEnd("\r\n".ToCharArray()), "\r\n");
int j=0;
foreach (string pastedRow in pastedRows)
{
string[] pastedRowCells = pastedRow.Split(new char[] { '\t' });
if (!columnsAdded)
{
for (int i = 0; i < pastedRowCells.Length; i++)
myDataGridView.Columns.Add("col" + i, pastedRowCells[i]);
columnsAdded = true;
continue;
}
myDataGridView.Rows.Add();
int myRowIndex = myDataGridView.Rows.Count - 1;
using (DataGridViewRow myDataGridViewRow = myDataGridView.Rows[j])
{
for (int i = 0; i < pastedRowCells.Length; i++)
myDataGridViewRow.Cells[i].Value = pastedRowCells[i];
}
j++;
}
}
Modified from Latheesan's code.
using System.Linq;
DataTable xDataTable = new DataTable();
DataObject XClipboardDat = (DataObject)Clipboard.GetDataObject();
if (XClipboardDat.GetDataPresent(DataFormats.Text))
{
string[] XClipboardRows = Regex.Split(XClipboardDat.GetData(DataFormats.Text).ToString(), @"[\r\n]+").Where(y => !string.IsNullOrEmpty(y.ToString())).ToArray();
IEnumerable<string[]> XDatRowCol = XClipboardRows.Select(xRow => Regex.Split(xRow, @"[\t]+").Where(y => !string.IsNullOrEmpty(y.ToString())).ToArray());
int ColNum = XDatRowCol.Select(XDatRow => XDatRow.Length).ToArray().Max<int>();
for (int i = 0; i < ColNum; i++) { xDataTable.Columns.Add(); }
foreach(string[] XDatRow in XDatRowCol) { xDataTable.Rows.Add(XDatRow); }
dataGridView2.DataSource = xDataTable;
}
A really nice solution was posted here:
But, one line needs to be changed:
if (dgv.Rows.Count < (r + rowsInClipboard.Length))
dgv.Rows.Add(r + rowsInClipboard.Length - dgv.Rows.Count);
needs to be changed to:
if (dgv.Rows.Count < (r + rowsInClipboard.Length))
dgv.Rows.Add(r + rowsInClipboard.Length+1 - dgv.Rows.Count);
If this line isn't changes, the last row pasted will not be passed to SQL.
I've just modified @Latheesan's code as below which is the shortest version.
DataObject o = (DataObject)Clipboard.GetDataObject();
if (o.GetDataPresent(DataFormats.Text))
{
if (myDataGridView.Rows.Count > 0)
myDataGridView.Rows.Clear();
if (myDataGridView.Columns.Count > 0)
myDataGridView.Columns.Clear();
bool columnsAdded = false;
string[] pastedRows = Regex.Split(o.GetData(DataFormats.Text).ToString().TrimEnd("\r\n".ToCharArray()), "\r\n");
foreach (string pastedRow in pastedRows)
{
string[] pastedRowCells = pastedRow.Split(new char[] { '\t' });
if (!columnsAdded)
{
for (int i = 0; i < pastedRowCells.Length; i++)
myDataGridView.Columns.Add("col" + i, pastedRowCells[i]);
columnsAdded = true;
continue;
}
myDataGridView.Rows.Add(pastedRowCells);
//***You don't need following lines, use just above line. ***
//myDataGridView.Rows.Add();
//int myRowIndex = myDataGridView.Rows.Count - 1;
//using (DataGridViewRow myDataGridViewRow = myDataGridView.Rows[myRowIndex])
//{
// for (int i = 0; i < pastedRowCells.Length; i++)
// myDataGridViewRow.Cells[i].Value = pastedRowCells[i];
//}
}
}
I know it's some years later, but I was looking for a solution for this problem and found BASA's modification of Latheesan's code. It only worked partially, so modifying it, I would like to add this solution for future browsers:
private void Paste(DataGridView d)
{
DataObject o = (DataObject)Clipboard.GetDataObject();
if (o.GetDataPresent(DataFormats.StringFormat))
{
string[] pastedRows = Regex.Split(o.GetData(DataFormats.StringFormat).ToString().TrimEnd("\r\n".ToCharArray()), "\r");
int j = 0;
try { j = d.CurrentRow.Index; } catch { }
foreach (string pastedRow in pastedRows)
{
DataGridViewRow r = new DataGridViewRow();
r.CreateCells(d, pastedRow.Split(new char[] { '\t' }));
d.Rows.Insert(j, r);
j++;
}
}
}
After some digging around, I found that I have to add columns first, then add a new row, get the row index of the newly created row, and then set the cell values.
Here's the updated code:
DataObject o = (DataObject)Clipboard.GetDataObject();
if (o.GetDataPresent(DataFormats.Text))
{
if (myDataGridView.RowCount > 0)
myDataGridView.Rows.Clear();
if (myDataGridView.ColumnCount > 0)
myDataGridView.Columns.Clear();
bool columnsAdded = false;
string[] pastedRows = Regex.Split(o.GetData(DataFormats.Text).ToString().TrimEnd("\r\n".ToCharArray()), "\r\n");
foreach (string pastedRow in pastedRows)
{
string[] pastedRowCells = pastedRow.Split(new char[] { '\t' });
if (!columnsAdded)
{
for (int i = 0; i < pastedRowCells.Length; i++)
myDataGridView.Columns.Add("col" + i, pastedRowCells[i]);
columnsAdded = true;
continue;
}
myDataGridView.Rows.Add();
int myRowIndex = myDataGridView.Rows.Count - 1;
using (DataGridViewRow myDataGridViewRow = myDataGridView.Rows[myRowIndex])
{
for (int i = 0; i < pastedRowCells.Length; i++)
myDataGridViewRow.Cells[i].Value = pastedRowCells[i];
}
}
}
}
And here it is working:
Happy to accept criticisms and useful tips on improving this. This code is quite slow...