In my previous post I have described how to synchronize two ListBox objects. Here I will show, how to synchronize two ListView objects.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace SyncLists
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
this.listView1.View = View.Details;
this.listView2.View = View.Details;
for (int j = 0; j < 10; j++)
{
this.listView1.Columns.Add("c" + j.ToString());
this.listView2.Columns.Add("c" + j.ToString());
}
for (int j = 0; j < 300; j++)
{
ListViewItem item = new ListViewItem("item" + j.ToString());
for (int k = 1; k < 10; k++)
{
item.SubItems.Add("sub item" + k.ToString());
}
this.listView1.Items.Add(item);
this.listView2.Items.Add(item.Clone() as ListViewItem);
}
this.listView1.Scroll += new ListViewEx.ScrollHandler(listView1_Scroll);
}
[DllImport("user32.dll")]
static extern IntPtr SendMessage(IntPtr hWnd, int Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll")]
static extern int SetScrollPos(IntPtr hWnd, int nBar, int nPos, bool bRedraw);
private const int WM_HSCROLL = 0x114;
private const int WM_VSCROLL = 0x115;
private const int SBS_HORZ = 0;
private const int SBS_VERT = 1;
void listView1_Scroll(object sender, MyScrollEventArgs e)
{
ListViewEx listVw = sender as ListViewEx;
Int16 hi = (Int16)((int)e.WParam >> 16);//position
Int16 lo = (Int16)e.WParam;//scroll type
if (e.Orientation == ScrollOrientation.VerticalScroll)
{
if (lo == 5) //SB_THUMBTRACK
{
if (SetScrollPos(this.listView2.Handle, SBS_VERT, hi, true) != 0)
{
SendMessage(this.listView2.Handle, WM_VSCROLL,
(IntPtr)(4 + 0x10000 * hi), IntPtr.Zero);
}
}
else
{
SendMessage(this.listView2.Handle, WM_VSCROLL, e.WParam, IntPtr.Zero);
}
}
if (e.Orientation == ScrollOrientation.HorizontalScroll)
{
if (lo == 5)//SB_THUMBTRACK
{
SetScrollPos(this.listView2.Handle, SBS_HORZ, hi, true);
SendMessage(this.listView2.Handle, WM_HSCROLL,
(IntPtr)(4 + 0x10000 * hi), IntPtr.Zero);
}
else
{
SendMessage(this.listView2.Handle, WM_HSCROLL, e.WParam, IntPtr.Zero);
}
}
}
}
public class ListViewEx : ListView
{
public delegate void ScrollHandler(object sender, MyScrollEventArgs e);
public event ScrollHandler Scroll;
public void OnScroll(MyScrollEventArgs e)
{
if (Scroll != null)
{
Scroll(this, e);
}
}
private const int WM_HSCROLL = 0x114;
private const int WM_VSCROLL = 0x115;
protected override void WndProc(ref Message m)
{
if (m.Msg == WM_VSCROLL)
{
MyScrollEventArgs e = new MyScrollEventArgs();
e.WParam = m.WParam;
e.Orientation = ScrollOrientation.VerticalScroll;
OnScroll(e);
}
if (m.Msg == WM_HSCROLL)
{
MyScrollEventArgs e = new MyScrollEventArgs();
e.WParam = m.WParam;
e.Orientation = ScrollOrientation.HorizontalScroll;
OnScroll(e);
}
base.WndProc(ref m);
}
}
public class MyScrollEventArgs : EventArgs
{
private ScrollOrientation orientation;
private IntPtr wParam;
public IntPtr WParam
{
get { return wParam; }
set { wParam = value; }
}
public ScrollOrientation Orientation
{
get { return orientation; }
set { orientation = value; }
}
}
}