Search code examples
c#winrt-xamlsemantic-zoom

Semantic zoom - letters containing no children not appearing


For my semantic zoom control, I'm trying to get the letters containing no children to appear but I'm having trouble achieving this as with the code I currently have, only the letters containing children are appearing. Struggling to figure out which section of code I need to modify or add in order to achieve want I want. Any ideas?

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace EELL
{
    using System;
    using Windows.UI.Xaml.Data;
    using Windows.UI.Xaml.Media;

#if DISABLE_SAMPLE_DATA
    internal class SampleDataSource { }
#else

    public class Item : System.ComponentModel.INotifyPropertyChanged
    {
        public event System.ComponentModel.PropertyChangedEventHandler PropertyChanged;

        protected virtual void OnPropertyChanged(string propertyName)
        {
            if (this.PropertyChanged != null)
            {
                this.PropertyChanged(this, new System.ComponentModel.PropertyChangedEventArgs(propertyName));
            }
        }

        private string _Station = string.Empty;
        public string Station
        {
            get
            {
                return this._Station;
            }

            set
            {
                if (this._Station != value)
                {
                    this._Station = value;
                    this.OnPropertyChanged("Station");
                }
            }
        }

        private string _Zone = string.Empty;
        public string Zone
        {
            get
            {
                return this._Zone;
            }

            set
            {
                if (this._Zone != value)
                {
                    this._Zone = value;
                    this.OnPropertyChanged("Zone");
                }
            }
        }

        private string _Link = string.Empty;
        public string Link
        {
            get
            {
                return this._Link;
            }

            set
            {
                if (this._Link != value)
                {
                    this._Link = value;
                    this.OnPropertyChanged("Link");
                }
            }
        }
    }

    public class GroupInfoList<T> : List<object>
    {

        public object Key { get; set; }


        public new IEnumerator<object> GetEnumerator()
        {
            return (System.Collections.Generic.IEnumerator<object>)base.GetEnumerator();
        }
    }


    public class StoreData
    {
        public StoreData()
        {
            Item item;

            item = new Item();
            item.Station = "Aldgate";
            item.Link = "/Lines and Stations/Metropolitan/Aldgate_(Metropolitan).xaml";
            Collection.Add(item);


            item = new Item();
            item.Station = "Moorgate";
            item.Link = "/Lines and Stations/Metropolitan/MOG_(Metropolitan).xaml";
            Collection.Add(item);
        }



        private ItemCollection _Collection = new ItemCollection();

        public ItemCollection Collection
        {
            get
            {
                return this._Collection;
            }
        }

        internal List<GroupInfoList<object>> GetGroupsByCategory()
        {
            List<GroupInfoList<object>> groups = new List<GroupInfoList<object>>();

            var query = from item in Collection
                        orderby ((Item)item).Zone
                        group item by ((Item)item).Zone into g
                        select new { GroupName = g.Key, Items = g };
            foreach (var g in query)
            {
                GroupInfoList<object> info = new GroupInfoList<object>();
                info.Key = g.GroupName;
                foreach (var item in g.Items)
                {
                    info.Add(item);
                }
                groups.Add(info);
            }

            return groups;
        }

        internal List<GroupInfoList<object>> GetGroupsByLetter()
        {
            List<GroupInfoList<object>> groups = new List<GroupInfoList<object>>();

            var query = from item in Collection
                        orderby ((Item)item).Station
                        group item by ((Item)item).Station[0] into g
                        select new { GroupName = g.Key, Items = g };
            foreach (var g in query)
            {
                GroupInfoList<object> info = new GroupInfoList<object>();
                info.Key = g.GroupName;
                foreach (var item in g.Items)
                {
                    info.Add(item);
                }
                groups.Add(info);
            }

            return groups;

        }
    }

    public class ItemCollection : IEnumerable<Object>
    {
        private System.Collections.ObjectModel.ObservableCollection<Item> itemCollection = new System.Collections.ObjectModel.ObservableCollection<Item>();

        public IEnumerator<Object> GetEnumerator()
        {
            return itemCollection.GetEnumerator();
        }

        System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
        {
            return GetEnumerator();
        }

        public void Add(Item item)
        {
            itemCollection.Add(item);
        }
    }
#endif
}

Error enter image description here


Solution

  • Updated Code:

    internal List<GroupInfoList<object>> GetGroupsByLetter()
        {
          var letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZ".ToList();
            var groupByAlphabets = from letter in letters
                       select new
                       {
                           Key = letter,
                           Items = (from item in Collection
                                    where ((Item)item).Station.StartsWith(letter.ToString(), StringComparison.CurrentCultureIgnoreCase)
                                    orderby ((Item)item).Station
                                    group item by ((Item)item).Station[0] into g
                                    select g)
                       };
    
            List<GroupInfoList<object>> groups = new List<GroupInfoList<object>>();
    
            foreach (var g in groupByAlphabets)
            {
                GroupInfoList<object> info = new GroupInfoList<object>();
                info.Key = g.Key;
                foreach (var item in g.Items)
                {
                    info.Add(item);
                }
                groups.Add(info);
            }
    
            return groups;
        }
    

    // The code above should give you the groups by Alphabets

    <Style x:Key="mainGridViewStyle" TargetType="GridView">
    <Setter Property="GroupStyleSelector" Value="{StaticResource GridViewGroupStyleSelector}" />
    
    <views:GridViewGroupStyleSelector x:Key="GridViewGroupStyleSelector" />
    
    <GroupStyle x:Key="gridViewGroupStyle" HidesIfEmpty="True">
        <GroupStyle.HeaderTemplate>
            <DataTemplate>
                <Grid x:Name="headerGrid">
                    <StackPanel Orientation="Horizontal" Margin="-7,0,0,-7">
                      <TextBlock Style="{StaticResource SubheaderTextBlockStyle}" Text="{Binding HeaderIdentifier}" />
                        </Button>
                    </StackPanel>
                </Grid>
            </DataTemplate>
        </GroupStyle.HeaderTemplate>
    </GroupStyle>
    
      public class GridViewGroupStyleSelector : GroupStyleSelector
    {
        protected override GroupStyle SelectGroupStyleCore(object group, uint level)
        {
            return (GroupStyle)App.Current.Resources["gridViewGroupStyle"];
        }
    }
    

    So what we have here:

    • The mainGridView is my primary gridview.
    • It has a style defined for it called mainGridViewStyle, one of the properties we set in it are GroupStyleSelector
    • The GroupStyleSelector is defined as a static resource as GridViewGroupStyleSelector.
    • The actual implementation is done in a codefile as class GridViewGroupStyleSelector
    • This selector provides the actual group style which is called gridViewGroupStyle, and in this style we mark the attribute HidesIfEmpty is True or false.