0

ListBox.Items.Removeを使用してリストボックスから動的に作成されたボタンを削除しようとしていますが、 「ItemsSource が使用されている間、操作は無効です。代わりに ItemsControl.ItemsSource を使用して要素にアクセスして変更してください。」というエラーが表示され続けます。問題は、私のコードではItemsControl.ItemsSourceが有効なオプションではないことです。

コードの概要: ListBox と [追加] ボタンと [削除] ボタンを含む MainWindow があります。ボタンを追加すると、名と姓を入力できるウィンドウが表示されます。「完了」をクリックすると、新しく作成されたプロファイルのボタンがリストボックスに追加されます (このボタンをクリックすると、プロファイルにアクセスできます)。名字と姓がラベルにバインドされていることを除いて、プロファイル コードを空として含めませんでした。

それらを削除するためにボタン/プロファイルにアクセス/変更するにはどうすればよいですか? データバインディングに関係していることは知っていますが、アイテムを削除する方法について完全に混乱しています。

どんな助けでも大歓迎です。以下に、MainWindow と ProfileCreator のコードを含めました。

<Window x:Class="SavingButtons.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="350" Width="525">

<Window.Resources>
    <DataTemplate x:Key="UserTemplate">
        <StackPanel Orientation="Horizontal">
            <Button Name="TestAddButton" Click="TestAddButton_Clicked" Content="{Binding FirstName}" Width="100" Height="40"></Button> 
        </StackPanel>
    </DataTemplate>
</Window.Resources>

<Grid>
    <Button Name="AddProfileButton" Content="Add Profile" HorizontalAlignment="Left" Margin="22,29,0,0" VerticalAlignment="Top" Width="75" Click="AddProfileButton_Click"/>
    <ListBox Name="ButtonHoldersListbox" IsSynchronizedWithCurrentItem="True" ItemsSource="{Binding}" ItemTemplate="{StaticResource UserTemplate}" HorizontalAlignment="Left" Height="202" Margin="22,69,0,0" VerticalAlignment="Top" Width="183" />
    <Button Name="DeleteUserButton" Click="DeleteUserButton_Click" Content="Delete User" HorizontalAlignment="Left" Margin="246,69,0,0" VerticalAlignment="Top" Width="105"/>
</Grid>

namespace SavingButtons
{
public partial class MainWindow : Window
{
    NewProfile np;
    public int buttonNumberID;
    public MainWindow()
    {
        InitializeComponent();
        np = new NewProfile(this);
    }

    private void AddProfileButton_Click(object sender, RoutedEventArgs e)
    {
        np.Show();
    }
    //adds button to listbox
    internal void TestAddButton_Clicked(object sender, RoutedEventArgs e)
    {
        Button cmd = (Button)sender;
        if (cmd.DataContext is User)
        {
            //Profile is where the finished information is displayed//
            Profile pro = new Profile();
            pro.DataContext = cmd.DataContext;
            pro.Show();
        }
    }
    //this is where confusion ensues
    private void DeleteUserButton_Click(object sender, RoutedEventArgs e)
    {
        //error occurs here
        ButtonHoldersListbox.Items.Remove(ButtonHoldersListbox.SelectedItem);

    }
}
}

プロフィール作成者:

<Window x:Class="SavingButtons.NewProfile"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="NewProfile" Height="300" Width="500">
<Grid>
    <Label Content="FirstName" HorizontalAlignment="Left" Margin="64,44,0,0" VerticalAlignment="Top"/>
    <Label Content="LastName" HorizontalAlignment="Left" Margin="64,97,0,0" VerticalAlignment="Top"/>
    <Button Name="UploadImageButton" Click="UploadImageButton_Click" Content="Upload Image" HorizontalAlignment="Left" Margin="64,146,0,0" VerticalAlignment="Top" Width="75"/>

    <TextBox Name="FirstNameTextBox" HorizontalAlignment="Left" Height="23" Margin="126,47,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="120"/>
    <TextBox Name="LastNameTextBox" HorizontalAlignment="Left" Height="23" Margin="126,99,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="120"/>
    <Image Name="imgPhoto" HorizontalAlignment="Left" Height="100" Margin="173,146,0,0" VerticalAlignment="Top" Width="100"/>

    <Button Name="ProfileFinishedLaunch" Content="Done" HorizontalAlignment="Left" Margin="360,232,0,0" VerticalAlignment="Top" Width="75" Click="ProfileFinishedLaunch_Click"/>
</Grid>

 namespace SavingButtons
{
public partial class NewProfile : Window
{
    public ObservableCollection<User> ProfileList;
    public MainWindow mMain;

    public NewProfile(MainWindow main)
    {
        InitializeComponent();
        ProfileList = new ObservableCollection<User>();
        mMain = main;
    }

    //loads image
    private void UploadImageButton_Click(object sender, RoutedEventArgs e)
    {
        OpenFileDialog op = new OpenFileDialog();
        op.Title = "Select a picture";
        op.Filter = "All supported graphics|*.jpg;*.jpeg;*.png|" +
            "JPEG (*.jpg;*.jpeg)|*.jpg;*.jpeg|" +
            "Portable Network Graphic (*.png)|*.png";
        if (op.ShowDialog() == true)
        {
            imgPhoto.Source = new BitmapImage(new System.Uri(op.FileName));
        }
    }
    //creates a new user out of all the info, inserts new user into the collection, adds new button
    private void ProfileFinishedLaunch_Click(object sender, RoutedEventArgs e)
    {
        mMain.buttonNumberID++;
        ProfileList.Add(new User { FirstName = FirstNameTextBox.Text, LastName = LastNameTextBox.Text, imgPhoto = imgPhoto.Source });

        mMain.ButtonHoldersListbox.DataContext = ProfileList; 

        mMain.Show();
        this.Hide();
    }
4

3 に答える 3

1

You are setting yourListbox` をその他のウィンドウ プロパティに追加し、新しいアイテムが追加されるたびにそれを行います。

ItemsSourceリストボックスの項目がプロパティへのバインドによって設定され、この場合ListBox.Itemsは読み取り専用であるため、項目を直接削除または追加できないため、エラーが発生します。

今あるものの代わりにObservableCollection<User>、クラスにプロパティを追加し、このプロパティMainWindowにバインドしListBoxます。NewProfileウィンドウで、新しいユーザー アイテムをこのコレクションに追加する必要があります。削除操作は、そのコレクション (実際には送信者DataContext)からアイテムを削除することで機能します。

public partial class MainWindow : Window
{
    public ObservableCollection<User> Profiles {get; set;}

    //...

    private void DeleteUserButton_Click(object sender, RoutedEventArgs e)
    {
      var removable = ButtonHoldersListbox.SelectedItem as User;
      if(removable != null)
        Profiles.Remove(removable);
    }
}


<ListBox Name="ButtonHoldersListbox" IsSynchronizedWithCurrentItem="True" ItemsSource="{Binding Profiles}" ItemTemplate="{StaticResource UserTemplate}" HorizontalAlignment="Left" Height="202" Margin="22,69,0,0" VerticalAlignment="Top" Width="183" />


public partial class NewProfile : Window
{

//creates a new user out of all the info, inserts new user into the collection, adds new button
private void ProfileFinishedLaunch_Click(object sender, RoutedEventArgs e)
{
    mMain.buttonNumberID++;
    var newUser = new User { FirstName = FirstNameTextBox.Text, LastName = LastNameTextBox.Text, imgPhoto = imgPhoto.Source };

    mMain.Profiles.Add(newUser); 

    //Don't set the listbox.DataContext here

    mMain.Show();
    this.Hide();
}
于 2013-09-02T08:00:10.760 に答える
0

itemsource を usercontrol に設定すると、アイテムを直接操作できなくなります。代わりに itemsource を編集してください。簡単な例を挙げてください。

 public partial class MainWindow : Window
{
    ObservableCollection<int> ProfileList;
    public MainWindow()
    {
        InitializeComponent();
        ProfileList = new ObservableCollection<int>();
        this.DataContext = ProfileList;
    }

    private void btnAdd_Click(object sender, RoutedEventArgs e)
    {
        Random r = new Random();
        int num = r.Next(100);
        ProfileList.Add(num);
        //lstShow.Items.Add(num);   error!
    }

    private void btnDel_Click(object sender, RoutedEventArgs e)
    {
        if (lstShow.SelectedIndex > -1)
        {
            ProfileList.Remove((int)lstShow.SelectedItem);
            //lstShow.Items.Remove((int)lstShow.SelectedItem);   error!
        }
    }
}
于 2013-09-02T08:13:37.880 に答える