Удаление элемента вкладки на основе его заголовка
Прежде всего, этот вопрос является продолжением этого вопроса. Я чувствую, что получил только половину ответа на свой вопрос.
А также удаление tabItems
, на которое ссылается Name
, я также должен иметь возможность удалять tabItems
, ссылаясь на их Headers
.
При реализации моего ответа и изменении n.Name
на n.Header
, например:
var tabToDelete = tabControl.Items.OfType<TabItem>().SingleOrDefault(n => n.Header == stringValue);
if (tabToDelete != null)
tabControl.Items.Remove(tabToDelete);
Я нахожу, что это не работает одинаково. Должно ли это работать, или мне нужно отредактировать всю эту структуру? Если да, то как бы я это сделал, чтобы сделать уверен, что на tabItem
, который мне нужен, ссылается Header
?
Добавление : когда вкладки, на которые ссылается Name
, удаляются, они удаляются с экрана, в то время как вкладки, на которые ссылается Header
, не удаляются (до тех пор, пока вы вручную не переключите вкладки). Это наводит меня на мысль, что они все еще существуют в программе.
2 ответа:
Ваша проблема в том, что
Header
- это объект, а не строка. Вы сравниваете два значения, как если бы они были, но поскольку заголовок-это объект, вы фактически делаете сравнение ссылок, а не сравнение значений. Вам нужно привестиHeader
к строке, просто вызвав.ToString()
наHeader
.var tabToDelete = tabControl.Items.OfType<TabItem>().SingleOrDefault(n => (n.Header as string) == stringValue); if (tabToDelete != null) tabControl.Items.Remove(tabToDelete);
Если это не решает проблему, вы можете заставить элемент управления перерисовать, вызвав
tabControl.Refresh();
Обновление
Хвала Даниэлю Хименесу за обнаружение возможной нулевой ссылки исключение. Вопрос о том, что
Header
устанавливается в элемент управления, не является проблемой, однако, поскольку все объекты могут вызыватьToString()
, реальная проблема заключается в том, чтоHeader
не устанавливается вообще, что приводит к объектуnull
.
Как сказал Райан, проблема в том, что
Header
может быть элементом управления, а не просто текстом. ЕслиHeader
может бытьnull
,as String
илиConvert.ToString()
будет лучше, чемtoString()
, потому что они оба могут обрабатывать преобразование из нулевых значений, тогда какToString()
создает исключение.Использование
Convert.ToString()
может быть излишним, но если ваши заголовки привязаны к значениям, которые не могут неявно преобразовываться в строки, такие как целые числа, то использованиеConvert.ToString()
сможет их обрабатывать. Также это решение будет обрабатывать случай, если несколько элементов с таким же значением заголовка существуют.private void RemoveTabByHeader(string str) { TabsMain.Items.OfType<TabItem>().Where(t => Convert.ToString(t.Header) == str) .ToList().ForEach(t => TabsMain.Items.Remove(t)); }
Это проверено.
TabControl
правильно обновляется.