views:

202

answers:

2

I worked out the C# code to create an ImageButton (below) that has three images (one base-image and two overlays) and three text boxes as the face of the button. I am inheriting from the Button class, which unfortunately includes several components that I didn't realize would surface until after coding and need to remove, namely the bright-blue surrounding border on IsMouseOver, and any visible borders between the buttons, as the buttons will end up in a wrapPanel and the borders need to be seamless. Now that the format has been worked out in C#, I expect that I need to translate to XAML so that I can create a ControlTemplate to get the functionality necessary, however I am not certain as to the process of translating from C# to XAML. I would appreciate if anyone is aware of a good overview/resource that discusses what will be required to convert so that I can translate appropriately? Thanks.

public class ACover : Button
    {
        Image cAImage = null;
        Image jCImage = null;
        Image jCImageOverlay = null;
        TextBlock ATextBlock = null;
        TextBlock AbTextBlock = null;
        TextBlock RDTextBlock = null;
        private string _TracksXML = "";

        public ACover() 
        {
            Grid cArtGrid = new Grid();

            cArtGrid.Background = new SolidColorBrush(Color.FromRgb(38, 44, 64));
            cArtGrid.Margin = new System.Windows.Thickness(5, 10, 5, 10);
            RowDefinition row1 = new RowDefinition();
            row1.Height = new GridLength(225); 
            RowDefinition row2 = new RowDefinition();
            row2.Height = new GridLength(0, GridUnitType.Auto);
            RowDefinition row3 = new RowDefinition();
            row3.Height = new GridLength(0, GridUnitType.Auto);
            RowDefinition row4 = new RowDefinition();
            row4.Height = new GridLength(0, GridUnitType.Auto);
            cArtGrid.RowDefinitions.Add(row1);
            cArtGrid.RowDefinitions.Add(row2);
            cArtGrid.RowDefinitions.Add(row3);
            cArtGrid.RowDefinitions.Add(row4);

            ColumnDefinition col1 = new ColumnDefinition();
            col1.Width = new GridLength(0, GridUnitType.Auto);
            cArtGrid.ColumnDefinitions.Add(col1);

            jCImage = new Image();
            jCImage.Height = 240;
            jCImage.Width = 260;
            jCImage.VerticalAlignment = VerticalAlignment.Top;
            jCImage.Source = new BitmapImage(new Uri(Properties.Settings.Default.pathToGridImages + "jc.png", UriKind.Absolute));
            cArtGrid.Children.Add(jCImage);

            cArtImage = new Image();
            cArtImage.Height = 192;
            cArtImage.Width = 192;
            cArtImage.Margin = new System.Windows.Thickness(3, 7, 0, 0);
            cArtImage.VerticalAlignment = VerticalAlignment.Top;
            cArtGrid.Children.Add(cArtImage);

            jCImageOverlay = new Image();
            jCImageOverlay.Height = 192;
            jCImageOverlay.Width = 192;
            jCImageOverlay.Margin = new System.Windows.Thickness(3, 7, 0, 0);
            jCImageOverlay.VerticalAlignment = VerticalAlignment.Top;
            jCImageOverlay.Source = new BitmapImage(new Uri( Properties.Settings.Default.pathToGridImages + "jc-overlay.png", UriKind.Absolute));
            cArtGrid.Children.Add(jCImageOverlay);

            ATextBlock = new TextBlock();
            ATextBlock.Foreground = new SolidColorBrush(Color.FromRgb(173, 176, 198));
            ATextBlock.Margin = new Thickness(10, -10, 0, 0);
            cArtGrid.Children.Add(ATextBlock);

            AlTextBlock = new TextBlock();
            AlTextBlock.Margin = new Thickness(10, 0, 0, 0);
            AlTextBlock.Foreground = new SolidColorBrush(Color.FromRgb(173, 176, 198));
            cArtGrid.Children.Add(AlTextBlock);

            RDTextBlock = new TextBlock();
            RDTextBlock.Margin = new Thickness(10, 0, 0, 0);
            RDTextBlock.Foreground = new SolidColorBrush(Color.FromRgb(173, 176, 198));
            cArtGrid.Children.Add(RDTextBlock);

            Grid.SetColumn(jCImage, 0);
            Grid.SetRow(jCImage, 0);
            Grid.SetColumn(jCImageOverlay, 0);
            Grid.SetRow(jCImageOverlay, 0);
            Grid.SetColumn(cArtImage, 0);
            Grid.SetRow(cArtImage, 0);

            Grid.SetColumn(ATextBlock, 0);
            Grid.SetRow(ATextBlock, 1);
            Grid.SetColumn(AlTextBlock, 0);
            Grid.SetRow(AlTextBlock, 2);
            Grid.SetColumn(RDTextBlock, 0);
            Grid.SetRow(RDTextBlock, 3);
            this.Content = cArtGrid;
        }

        public string A
        {
            get { if (ATextBlock != null) return ATextBlock.Text;
                else return String.Empty; }
            set { if (ATextBlock != null) ATextBlock.Text = value; }
        }

        public string Al
        {
            get { if (AlTextBlock != null) return AlTextBlock.Text;
                  else return String.Empty; }
            set { if (AlTextBlock != null) AlTextBlock.Text = value; }
        }

        public string RD
        {
            get { if (RDTextBlock != null) return RDTextBlock.Text;
                  else return String.Empty; }
            set { if (RDTextBlock != null) RDTextBlock.Text = value; }
        }

        public ImageSource Image
        {
            get { if (cArtImage != null) return cArtImage.Source;
                  else return null; }
            set { if (cArtImage != null) cArtImage.Source = value; }
        }

        public string TracksXML
        {
            get { return _TracksXML; }
            set { _TracksXML = value; }
        }

        public double ImageWidth
        {
            get { if (cArtImage != null) return cArtImage.Width;
                  else return double.NaN;  }
            set { if (cArtImage != null) cArtImage.Width = value; }
        }

        public double ImageHeight
        {
            get { if (cArtImage != null) return cArtImage.Height;
                  else return double.NaN;  }
            set { if (cArtImage != null) cArtImage.Height = value; }
        }
    }
A: 

XAML basically represents an object graph, so the translation should normally be pretty mechanical:

  • C# new translates to a XAML element tag, e.g. Grid cArtGrid = new Grid(); translates to <Grid Name="cArtGrid"></Grid>.
  • C# property setters translate to attributes if the value is simple, e.g. cArtGrid.Background = new SolidColorBrush(Color.FromRgb(38, 44, 64)); translates to <Grid Background="#FF262C40">.
  • If the property value is complex, you'll need to use XAML property element syntax.
  • Adding to collections typically requires XAML property element syntax, e.g. <Grid><Grid.RowDefinitions><RowDefinition Height="225" /></Grid.RowDefinitions></Grid>.
  • But for the Children collection you can just put the element directly inside e.g. cArtGrid.Children.Add(jCImage); becomes <Grid><Image ... /></Grid>. (The same applies to the Content property though this won't really affect you here.)
  • Attached property SetXxx calls translate into attributes with the dot notation e.g. Grid.SetColumn(ATextBlock, 0); becomes <Grid><TextBlock Grid.Column="0" /></Grid>.
  • You'll need to understand how value types like colours and thicknesses are represented e.g. the #AARRGGBB notation for colours and the CSV notation for thicknesses. MSDN will usually show this for the relevant types or properties that have those types.

In general, looking up the property in MSDN and looking at the XAML syntax should give you a good start.

itowlson
A: 

It sounds like you're attempting to extend the button with some new functionality. So the first thing you want to do is take advantage of the dependency system so that your properties can be bound in XAML. Look at this article on MSDN for information on declaring new dependency properties.

A prime candidate for a dependency property would be the Image property.

Actually, what I recommend is using the new CustomControl template in visual studio to provide some boilerplate code for you. Part of the boilerplate is declaring a themes.xaml file which provides a default template for your control. That template is what will hold your translated XAML for your control.

The good thing about XAML is that it is an initialization language. Once you get the dependency properties declared on your AlbumCover you bind to them in the template for your control. For more details about how this works, look at Charles Petzold's article on creating lookless controls in WPF.

You've got the basic look and functionality for your control in place. Following these two resources should help you integrate within the WPF ecosystem.

Mike Brown