1

私は、非常に大きなアプリケーションへの大規模なプラグイン コンポーネントに取り組んでいます。この特定の View コンポーネントの 90% は非常に動的 (データベース駆動型) であり、プログラムによって実行されます。これには特定の理由 (最小限の XAML) があるため、枠にとらわれずに考えてください。いいえ、何千行ものコードで構成されるコード ベースを元に戻して再構築することはできません。これは将来のバージョンです。

FrameworkElementFactory を介して値、バインディングを設定し、ハンドラーを追加できますが、他のタスクを実行するにはコントロール自体にアクセスする必要があります。1 つのタスクは、ToolTipService を各 FrameworkElement に追加することです。各派生コントロールに Loaded Event を追加し、それをインデックス付きオブジェクト コレクションに追加することでハンドラーを介して管理すれば、それを行うことができますが、これは非常に醜い方法です。

テスト用にこの小さなスニペット (以下) をまとめましたが、目前の問題を網羅しています。

MainWindow.xaml

<Window x:Class="FrameworkElementFactory_Control_Testing.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:local="clr-namespace:FrameworkElementFactory_Control_Testing"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        Title="MainWindow"
        Width="500"
        Height="300"
        mc:Ignorable="d">
    <Grid>
        <StackPanel x:Name="LayoutRoot"
                    Margin="5"
                    Orientation="Vertical" />
    </Grid>
</Window>

MainWindow.xaml.cs

using System;
using System.Windows;
using System.Windows.Controls;
using System.Collections.ObjectModel;

namespace FrameworkElementFactory_Control_Testing
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();

            this.DataContext = this;

            GridObjectCollection = new ObservableCollection<GridObject>() { new GridObject() };
            //GridObjectCollection.Add(new GridObject());

            DoTheGrid();
        }

        public ObservableCollection<GridObject> GridObjectCollection { get; set; }
        public GridObject CurrentGridObject { get; set; }

        private void DoTheGrid()
        {
            DataGrid dg = new DataGrid();

            dg.Margin = new Thickness(5);
            dg.AutoGenerateColumns = false;
            dg.CanUserAddRows = false;
            dg.CanUserDeleteRows = false;
            dg.CanUserSortColumns = false;
            dg.IsReadOnly = true;
            dg.ColumnWidth = new DataGridLength(1, DataGridLengthUnitType.Auto);
            dg.SelectionMode = DataGridSelectionMode.Single;
            dg.SelectedItem = CurrentGridObject;
            dg.ItemsSource = GridObjectCollection;

            DataGridTemplateColumn dgTemplateColumn = new DataGridTemplateColumn();
            FrameworkElementFactory factoryControl = null;

            TextBlock headerName = new TextBlock() { Text = "Button Type" };

            dgTemplateColumn.Header = headerName;

            factoryControl = new FrameworkElementFactory(typeof(Button));
            factoryControl.SetValue(Button.MarginProperty, new Thickness(1));
            factoryControl.SetValue(Button.WidthProperty, Convert.ToDouble("70"));
            factoryControl.SetValue(Button.HeightProperty, Convert.ToDouble("24"));
            factoryControl.SetValue(Button.NameProperty, "btnCLICK_ME");
            factoryControl.SetValue(Button.ContentProperty, "Click Me");
            factoryControl.AddHandler(Button.LoadedEvent, new RoutedEventHandler(ButtonLoaded_Click));

            DataTemplate cellTemplateControl = new DataTemplate();
            cellTemplateControl.VisualTree = factoryControl;
            dgTemplateColumn.CellTemplate = cellTemplateControl;
            dgTemplateColumn.CanUserSort = false;
            dg.Columns.Add(dgTemplateColumn);

            this.LayoutRoot.Children.Add(dg);
        }

        private void ButtonLoaded_Click(object sender, RoutedEventArgs e)
        {
            Button btn = sender as Button;

            //add btn to indexed collection for future reference (this is lame)
        }
    }
}

GridObject.cs

namespace FrameworkElementFactory_Control_Testing
{
    public class GridObject
    {
        public GridObject()
        { }

    }
}

建設的な助けをいただければ幸いです。お時間をいただきありがとうございます。

CT

4

0 に答える 0