FilterDescriptor LogicalOperator must be set last

3 posts, 0 answers
  1. Clive
    Clive avatar
    12 posts
    Member since:
    Sep 2011

    Posted 22 Nov 2011 Link to this post

    Hi,

    I was wondering if an exception could be thrown if you set the ListViewFilterDescriptorCollection's LogicalOperator property before adding filter descriptors to it via the Add method.

    In the example below, typing in 'o' into the left text box works correctly, however typing in 'o' to the second one does not work correctly, no filtering occurs. I have to type in 'o f' for it to begin filtering, but then it only filters on the 'o' and not the 'f' too. Something a bit funny is going on.

    My experience with .Net is 7 years. My experience with Rad is about 1 month.

    OS version and applied service packs

    Microsoft Windows Server 2003, Standard Edition, Service Pack 2

    • Regional and language settings, if different from En-US

    English (Australia)

    • .NET version (.NET2, .NET3, .NET3.5)

    .NET 4.0.30319 SP1Rel, Visual Studio 2010 Version 10.0.40219.1 SP1Rel

    • Exact version of the Telerik product 

    Runtime Version v2.0.50727, Version 2011.3.11.1116

    Thanks,
    Clive

    Imports Telerik.WinControls.Data
      
    Public Class Form9
        Inherits System.Windows.Forms.Form
      
        'Form overrides dispose to clean up the component list.
        <System.Diagnostics.DebuggerNonUserCode()> _
        Protected Overrides Sub Dispose(ByVal disposing As Boolean)
            Try
                If disposing AndAlso components IsNot Nothing Then
                    components.Dispose()
                End If
            Finally
                MyBase.Dispose(disposing)
            End Try
        End Sub
      
        'Required by the Windows Form Designer
        Private components As System.ComponentModel.IContainer
      
        'NOTE: The following procedure is required by the Windows Form Designer
        'It can be modified using the Windows Form Designer.  
        'Do not modify it using the code editor.
        <System.Diagnostics.DebuggerStepThrough()> _
        Private Sub InitializeComponent()
            Dim ListViewDetailColumn5 As Telerik.WinControls.UI.ListViewDetailColumn = New Telerik.WinControls.UI.ListViewDetailColumn("Column 0", "Column 0")
            Dim ListViewDetailColumn6 As Telerik.WinControls.UI.ListViewDetailColumn = New Telerik.WinControls.UI.ListViewDetailColumn("Column 1", "Column 1")
            Dim ListViewDetailColumn7 As Telerik.WinControls.UI.ListViewDetailColumn = New Telerik.WinControls.UI.ListViewDetailColumn("Column 2", "Column 2")
            Dim ListViewDetailColumn8 As Telerik.WinControls.UI.ListViewDetailColumn = New Telerik.WinControls.UI.ListViewDetailColumn("Column 3", "Column 3")
            Dim ListViewDataItem5 As Telerik.WinControls.UI.ListViewDataItem = New Telerik.WinControls.UI.ListViewDataItem("ListViewItem 1", New String() {"one", "two", "three", "four"})
            Dim ListViewDataItem6 As Telerik.WinControls.UI.ListViewDataItem = New Telerik.WinControls.UI.ListViewDataItem("ListViewItem 2", New String() {"five", "six", "seven", "eight"})
            Dim ListViewDataItem7 As Telerik.WinControls.UI.ListViewDataItem = New Telerik.WinControls.UI.ListViewDataItem("ListViewItem 3", New String() {"nine", "ten", "eleven", "twelve"})
            Dim ListViewDataItem8 As Telerik.WinControls.UI.ListViewDataItem = New Telerik.WinControls.UI.ListViewDataItem("ListViewItem 4", New String() {"thirteen", "forteen", "fifteen", "sixteen"})
            Me.RadListView1 = New Telerik.WinControls.UI.RadListView()
            Me.RadTextBox1 = New Telerik.WinControls.UI.RadTextBox()
            Me.RadTextBox2 = New Telerik.WinControls.UI.RadTextBox()
            Me.RadLabel1 = New Telerik.WinControls.UI.RadLabel()
            Me.RadLabel2 = New Telerik.WinControls.UI.RadLabel()
            CType(Me.RadListView1, System.ComponentModel.ISupportInitialize).BeginInit()
            CType(Me.RadTextBox1, System.ComponentModel.ISupportInitialize).BeginInit()
            CType(Me.RadTextBox2, System.ComponentModel.ISupportInitialize).BeginInit()
            CType(Me.RadLabel1, System.ComponentModel.ISupportInitialize).BeginInit()
            CType(Me.RadLabel2, System.ComponentModel.ISupportInitialize).BeginInit()
            Me.SuspendLayout()
            '
            'RadListView1
            '
            ListViewDetailColumn5.HeaderText = "Column 0"
            ListViewDetailColumn6.HeaderText = "Column 1"
            ListViewDetailColumn7.HeaderText = "Column 2"
            ListViewDetailColumn8.HeaderText = "Column 3"
            Me.RadListView1.Columns.AddRange(New Telerik.WinControls.UI.ListViewDetailColumn() {ListViewDetailColumn5, ListViewDetailColumn6, ListViewDetailColumn7, ListViewDetailColumn8})
            Me.RadListView1.GroupItemSize = New System.Drawing.Size(200, 20)
            ListViewDataItem5.Text = "ListViewItem 1"
            ListViewDataItem5.TextImageRelation = System.Windows.Forms.TextImageRelation.ImageBeforeText
            ListViewDataItem6.Text = "ListViewItem 2"
            ListViewDataItem6.TextImageRelation = System.Windows.Forms.TextImageRelation.ImageBeforeText
            ListViewDataItem7.Text = "ListViewItem 3"
            ListViewDataItem7.TextImageRelation = System.Windows.Forms.TextImageRelation.ImageBeforeText
            ListViewDataItem8.Text = "ListViewItem 4"
            ListViewDataItem8.TextImageRelation = System.Windows.Forms.TextImageRelation.ImageBeforeText
            Me.RadListView1.Items.AddRange(New Telerik.WinControls.UI.ListViewDataItem() {ListViewDataItem5, ListViewDataItem6, ListViewDataItem7, ListViewDataItem8})
            Me.RadListView1.ItemSize = New System.Drawing.Size(200, 20)
            Me.RadListView1.ItemSpacing = -1
            Me.RadListView1.Location = New System.Drawing.Point(12, 117)
            Me.RadListView1.Name = "RadListView1"
            Me.RadListView1.Size = New System.Drawing.Size(794, 149)
            Me.RadListView1.TabIndex = 0
            Me.RadListView1.Text = "RadListView1"
            Me.RadListView1.ViewType = Telerik.WinControls.UI.ListViewType.DetailsView
            '
            'RadTextBox1
            '
            Me.RadTextBox1.Location = New System.Drawing.Point(119, 294)
            Me.RadTextBox1.Name = "RadTextBox1"
            Me.RadTextBox1.Size = New System.Drawing.Size(100, 20)
            Me.RadTextBox1.TabIndex = 1
            Me.RadTextBox1.TabStop = False
            '
            'RadTextBox2
            '
            Me.RadTextBox2.Location = New System.Drawing.Point(238, 294)
            Me.RadTextBox2.Name = "RadTextBox2"
            Me.RadTextBox2.Size = New System.Drawing.Size(100, 20)
            Me.RadTextBox2.TabIndex = 1
            Me.RadTextBox2.TabStop = False
            '
            'RadLabel1
            '
            Me.RadLabel1.Location = New System.Drawing.Point(119, 273)
            Me.RadLabel1.Name = "RadLabel1"
            Me.RadLabel1.Size = New System.Drawing.Size(36, 16)
            Me.RadLabel1.TabIndex = 2
            Me.RadLabel1.Text = "Rad 1"
            '
            'RadLabel2
            '
            Me.RadLabel2.Location = New System.Drawing.Point(241, 273)
            Me.RadLabel2.Name = "RadLabel2"
            Me.RadLabel2.Size = New System.Drawing.Size(36, 16)
            Me.RadLabel2.TabIndex = 2
            Me.RadLabel2.Text = "Rad 2"
            '
            'Form9
            '
            Me.AutoScaleDimensions = New System.Drawing.SizeF(6.0!, 13.0!)
            Me.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font
            Me.ClientSize = New System.Drawing.Size(818, 483)
            Me.Controls.Add(Me.RadLabel2)
            Me.Controls.Add(Me.RadLabel1)
            Me.Controls.Add(Me.RadTextBox2)
            Me.Controls.Add(Me.RadTextBox1)
            Me.Controls.Add(Me.RadListView1)
            Me.Name = "Form9"
            Me.Text = "Form9"
            CType(Me.RadListView1, System.ComponentModel.ISupportInitialize).EndInit()
            CType(Me.RadTextBox1, System.ComponentModel.ISupportInitialize).EndInit()
            CType(Me.RadTextBox2, System.ComponentModel.ISupportInitialize).EndInit()
            CType(Me.RadLabel1, System.ComponentModel.ISupportInitialize).EndInit()
            CType(Me.RadLabel2, System.ComponentModel.ISupportInitialize).EndInit()
            Me.ResumeLayout(False)
            Me.PerformLayout()
      
        End Sub
        Friend WithEvents RadListView1 As Telerik.WinControls.UI.RadListView
        Friend WithEvents RadTextBox1 As Telerik.WinControls.UI.RadTextBox
        Friend WithEvents RadTextBox2 As Telerik.WinControls.UI.RadTextBox
        Friend WithEvents RadLabel1 As Telerik.WinControls.UI.RadLabel
        Friend WithEvents RadLabel2 As Telerik.WinControls.UI.RadLabel
      
        Private Sub RadTextBox1_TextChanged(sender As System.Object, e As System.EventArgs) Handles RadTextBox1.TextChanged
            RadListView1.Items.BeginUpdate()
            RadListView1.FilterDescriptors.Clear()
            If String.IsNullOrWhiteSpace(RadTextBox1.Text) Then
                RadListView1.EnableFiltering = False
            Else
                For Each txt In RadTextBox1.Text.Split({" "c}, StringSplitOptions.RemoveEmptyEntries)
                    Dim comp As New CompositeFilterDescriptor()
                    RadListView1.FilterDescriptors.Add(comp)
                    For Each a As Telerik.WinControls.UI.ListViewDetailColumn In RadListView1.Columns
                        Dim typeFilter As New FilterDescriptor(a.Name, FilterOperator.Contains, txt)
                        comp.FilterDescriptors.Add(typeFilter)
                    Next
                    comp.LogicalOperator = FilterLogicalOperator.Or
                Next
                RadListView1.FilterDescriptors.LogicalOperator = FilterLogicalOperator.And
                RadListView1.EnableFiltering = True
            End If
            RadListView1.Items.EndUpdate()
        End Sub
      
        Private Sub RadTextBox2_TextChanged(sender As System.Object, e As System.EventArgs) Handles RadTextBox2.TextChanged
            RadListView1.Items.BeginUpdate()
            RadListView1.FilterDescriptors.Clear()
            If String.IsNullOrWhiteSpace(RadTextBox2.Text) Then
                RadListView1.EnableFiltering = False
            Else
                RadListView1.FilterDescriptors.LogicalOperator = FilterLogicalOperator.And
                For Each txt In RadTextBox2.Text.Split({" "c}, StringSplitOptions.RemoveEmptyEntries)
                    Dim comp As New CompositeFilterDescriptor()
                    RadListView1.FilterDescriptors.Add(comp)
                    comp.LogicalOperator = FilterLogicalOperator.Or
                    For Each a As Telerik.WinControls.UI.ListViewDetailColumn In RadListView1.Columns
                        Dim typeFilter As New FilterDescriptor(a.Name, FilterOperator.Contains, txt)
                        comp.FilterDescriptors.Add(typeFilter)
                    Next
                Next
                RadListView1.EnableFiltering = True
            End If
            RadListView1.Items.EndUpdate()
        End Sub
      
        Public Sub New()
      
            ' This call is required by the designer.
            InitializeComponent()
      
            ' Add any initialization after the InitializeComponent() call.
      
        End Sub
    End Class
  2. Ivan Todorov
    Admin
    Ivan Todorov avatar
    688 posts

    Posted 24 Nov 2011 Link to this post

    Hello Clive,

    Thank you for your question.

    This is happening, because the CompositeFilterDescriptor does not notify its owner for changes in its FilterDescriptors collection. To overcome this, you can either change the logical operator after you have added the descriptors, or you can add the composite filter descriptor to the list view after it has been filled with the child descriptors:
    Private Sub RadTextBox2_TextChanged(sender As System.Object, e As System.EventArgs) Handles RadTextBox2.TextChanged
        RadListView1.Items.BeginUpdate()
        RadListView1.FilterDescriptors.Clear()
        If String.IsNullOrWhiteSpace(RadTextBox2.Text) Then
            RadListView1.EnableFiltering = False
        Else
            RadListView1.FilterDescriptors.LogicalOperator = FilterLogicalOperator.And
            For Each txt In RadTextBox2.Text.Split({" "c}, StringSplitOptions.RemoveEmptyEntries)
                Dim comp As New CompositeFilterDescriptor()
                comp.LogicalOperator = FilterLogicalOperator.Or
                For Each a As Telerik.WinControls.UI.ListViewDetailColumn In RadListView1.Columns
                    Dim typeFilter As New FilterDescriptor(a.Name, FilterOperator.Contains, txt)
                    comp.FilterDescriptors.Add(typeFilter)
                Next
            Next
     
            RadListView1.FilterDescriptors.Add(comp)
            RadListView1.EnableFiltering = True
        End If
        RadListView1.Items.EndUpdate()
    End Sub

    Nevertheless, the CompositeFilterDescriptor should also work in the case you have in your 
    RadTextBox2_TextChanged handler, so I have logged this as an issue in our Public Issue Tracking System. You can find the PITS item on this URL. Your Telerik points have been updated accordingly.

    Should you have further questions, do not hesitate to ask.

    Greetings,
    Ivan Todorov
    the Telerik team

    Q3’11 of RadControls for WinForms is available for download (see what's new). Get it today.

  3. UI for WinForms is Visual Studio 2017 Ready
  4. Clive
    Clive avatar
    12 posts
    Member since:
    Sep 2011

    Posted 24 Nov 2011 Link to this post

    Thanks Ivan, good to know I'm not crazy. I've learnt to always apply the filter operator last.
Back to Top