Форум программистов, компьютерный форум, киберфорум
C#: WPF, UWP и Silverlight
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
0 / 0 / 0
Регистрация: 11.07.2026
Сообщений: 12

Странно, но после SelectedItems.Clear, в SelectedItems по прежнему осталась таже строка

11.07.2026, 15:51. Показов 5788. Ответов 76
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Всё должно было быть коротко:
C#
1
private ClsReg CurrentDocItem => lbDoc.SelectedItem as ClsReg;
Но я уже месяц и так, и этак писал. Вот в данный момент о меня такое написано.
C#
1
2
3
4
5
6
7
8
9
10
11
   private ClsReg CurrentDocItem {
         get {
            if(lbDoc.SelectedIndex == -1) {
               lbDoc.Items.Clear();
               lbDoc.SelectedItem = null;
               var x = lbDoc.SelectedItems.Count; 
            }
 
            return lbDoc.SelectedIndex == -1 ? null : lbDoc.Items[lbDoc.SelectedIndex] as ClsReg;
         }
      }
Здесь «lbDoc» это ListBox. У него SelectionMode="Single". Я, как вы видите, и Items.Clear() сделал, и lbDoc.SelectedItem обнулил, но lbDoc.SelectedItems.Count по прежнему возвращает 1. Как так получается? Как я могу это сотворить?
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
11.07.2026, 15:51
Ответы с готовыми решениями:

Привязка к ListBox SelectedItems
Есть простой ListBox с мультиселектом: ListBox SelectionMode="Multiple"...

Правильное отображение selectedItems в Combobox
Всем привет, работаю по MVVM Есть Объект - Object Два свойства - Value1, Value2 -> string Во...

Отладка работы ListView SelectedItems
В проекте есть ListView, при загрузке из базы данных устанавливается IsSelected разным элементам...

76
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
03.09.2026, 12:32
Студворк — интернет-сервис помощи студентам
Цитата Сообщение от wizard41 Посмотреть сообщение
Зачем делегировать этот функционал слою View?
А зачем грузить этим VM и M? Сортировка ведь не влияет на целостность данных, их состав и т.д. Она никаким боком не относится к манипулированию данными, значит это можно спокойно отдать на откуп View. Тем более это будут писать люди, которые разрабатывают UI и это всё в их руках. А те кто пишет MV и M не будут отвлекаться на эту лишнюю работу...

Но если тимлид решил утонуть в MVVM и никоим образом не использовать CB, то флаг ему в руки. Путь бедные прогеры пишут AP/DP/Behavior миллионами, когда, вместо этого, можно решить задачу тремя строками в CB и MVVM нарушен не будет, так как View ничего не знает о формировании данных, он их только отображает, форматирует и если нужно сортирует для того, чтобы пользователь не ломал глаза.

Или я не прав? MVVM инструмент, а не тюрьма, и использовать его нужно с головой, а не упираться рогом
0
Эксперт JavaЭксперт по электроникеЭксперт .NET
 Аватар для wizard41
3463 / 2784 / 575
Регистрация: 04.09.2018
Сообщений: 8,757
Записей в блоге: 3
03.09.2026, 15:33
Andrey-MSK, ну, на все, как говорится, есть время и случай. Использовать некоторые "ухищрения" для решения той или иной задачи - выбор и возможность каждого.
В вашем случае, дело не столько в mvvm, сколько в возможных ограничениях функциональных возможностей слоя View и вероятной лишней "перекачки" данных в будущем.

Слой View не может быть источником "новых данных" или их модификаций. В зависимости от того, как вы отсортировали данные и что именно показываете в данный момент, может затребоваться отдельная информация о некотором предмете из результата сортировки. Так как вы сортируете данные во View, вам придется из View передать некоторые параметры текущего вида обратно в VM, чтобы она сформировала новую выборку. Это не приветствуется не только в самом паттерне mvvm, но и многими конторами в принципе.

В некоторых случаях (в моей практике почти везде) - View пишут люди весьма далекие от предмета разработки. Они не в курсе деталей, не знают внутреннюю структуру объектов. Они не смогут сделать полноценную сортировку на своем уровне. Или, для этого, им придется раскрывать больше деталей, чем требуется. А это уже явное проникновение лишнего в слой пользователя.

Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Но если тимлид решил утонуть в MVVM и никоим образом не использовать CB, то флаг ему в руки. Путь бедные прогеры пишут AP/DP/Behavior миллионами, когда, вместо этого, можно решить задачу тремя строками в CB
Если это позволяется и не предвидеться проблем/переработок в будущем - кто ж запрещает то? Каждый такой случай нужно обсуждать предметно.
Просто зачастую, многие этим пользуются: неумение или нежелание делать "по нормальному" пытаются скрыть всякими отмазками..
0
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
03.09.2026, 15:42
Цитата Сообщение от wizard41 Посмотреть сообщение
Слой View не может быть источником "новых данных" или их модификаций. В зависимости от того, как вы отсортировали данные и что именно показываете в данный момент, может затребоваться отдельная информация о некотором предмете из результата сортировки. Так как вы сортируете данные во View, вам придется из View передать некоторые параметры текущего вида обратно в VM, чтобы она сформировала новую выборку. Это не приветствуется не только в самом паттерне mvvm, но и многими конторами в принципе.
Что-то вы тут усложняете. Есть две коллекции, в окне две таблицы Master->Detail. сортируются кастомными сортировщиками в CVS. Выделяешь запись -> жмакаешь кнопку редактирования, в диалоге правишь что надо, жмакаешь Ок, через VM прилетели обновлённые данные записи коллекции, View их отсортировал. Связь выделенной позиции через SelectedItem, привязанные коллекции не меняются. Что тут куда утечёт обратно в VM и что куда проникает?
0
Эксперт JavaЭксперт по электроникеЭксперт .NET
 Аватар для wizard41
3463 / 2784 / 575
Регистрация: 04.09.2018
Сообщений: 8,757
Записей в блоге: 3
03.09.2026, 16:09
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Что-то вы тут усложняете.
Я проговариваю общий смысл, так как мы, пока еще, обсуждаем что-то абстрактное. Тут сложно сказать конкретно - не известен "сценарий" работы конкретного ПО и его объекты.
В целом же, показ текущих данных, выборка, сортировка и прочее - это результат системы команд и действий от пользователя, который перенаправляет View. Все остальное должно выполняться ниже лежащими слоями, которые непосредственно работают с данными.

Я уже много раз говорил это в различных темах и приводил примеры возможных конфузов, если действовать так, как вы задумали.
View - это такой слой, который не должен ни от чего зависеть. Хоть ваш, хоть мой View должен уметь правильно работать с ядром (vm/m, бд и т.п.). Различных вариаций слоя UI может быть несколько, на разных платформах и написанными разными авторами. Вы же полностью зациклили свой View на себя - внедрили в него свою сортировку. Таким образом, остальной функционал приложения оказался "обрезанным". Чтобы это приложение работало - вам придется всем передавать свой View.
А я, например, не хочу ваш вариант View - я хочу сделать свой. И что же получится? Сортировки у меня не будет никакой - мне придется ее делать самому, причем в том месте, которое мне покажется подходящим для этого. И это будет точно не View.

То есть, ваш подход не только не соблюдает mvvm, но и логически выходит не "удобным".
0
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
03.09.2026, 17:18
Цитата Сообщение от wizard41 Посмотреть сообщение
Таким образом, остальной функционал приложения оказался "обрезанным". Чтобы это приложение работало - вам придется всем передавать свой View.
То есть вы предлагаете сделать из VM контроллер/презентер который знает как всё должно выглядеть? Это как бы вообще другое от слова совсем. VM не должна знать где, как, в каком виде, и для чего будет использоваться то что она выдаёт.
Цитата Сообщение от wizard41 Посмотреть сообщение
Сортировки у меня не будет никакой - мне придется ее делать самому, причем в том месте, которое мне покажется подходящим для этого.
А если вы захотите сделать сортировку по другим полям класса, добавить что-то динамическое, как вам поможет сортировка, которую я запеку в VM или в M и выдам эту последовательность в свойство, которое вам не изменить, так как код VM вам вряд ли кто-то даст, а дадут только документацию по публичным свойствам? В том-то и замысел разделения слоёв. Вы ваяете View как вам угодно, со своими сортировками, форматами и т.д., а данные всегда остаются одни и те же, и выдаются именно теми свойствами которыми и должны выдаваться, и в предсказуемом виде - в полусыром, подготовленном для соблюдения логики приложения. Законченный внешний вид этого всего определяет View.
Цитата Сообщение от wizard41 Посмотреть сообщение
То есть, ваш подход не только не соблюдает mvvm, но и логически выходит не "удобным".
С этим я не согласен

Добавлено через 13 минут
wizard41,

Не по теме:

Складывается ощущение что вы целиком переехали в Java с его MVC. Без обид. Кстати вопросов по Java у меня тоже много



Добавлено через 26 минут
wizard41, Вот то, о чём вы говорите
Контроллер с загрузкой данных.
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
private void loadDrawReportTableData() {
    TableModelUtils.loadAndFillTable(
            () -> reportsRepository.getMainDrawReport(
                    BRANCH.getValue(),
                    selectedGPObject.objectId(),
                    selectedLaborGroup.groupId()),
            DrawReportComparator.getInstance(),
            drawReportTableModel::clear,
            drawReportTableModel::addRow,
            throwable -> {
                logger.error("Ошибка при загрузке отчёта по чертежам", throwable);
                dialogService.showError(
                        MessageTitles.ERROR_MESSAGE_TITLE,
                        "Ошибка при загрузке отчёта по чертежам",
                        throwable.getMessage()
                );
            }
    );
}
Тут я полностью согласен с вашими словами, так как это MVC.
0
Эксперт JavaЭксперт по электроникеЭксперт .NET
 Аватар для wizard41
3463 / 2784 / 575
Регистрация: 04.09.2018
Сообщений: 8,757
Записей в блоге: 3
03.09.2026, 17:32
Andrey-MSK, есть большая разница между тем, что хочет "вторичный" программист и/или пользователь и тем, что именно я, как автор, вкладываю в функционал данного ПО. Так же, при необходимости, могут быть предусмотрены некоторые методики "расширения" функционала, если таковые намечаются в будущем. Но опять же, в рамках дозволенного. Все и вся предусмотреть на все случаи жизни никто не в состоянии.
От сюда, если в ПО должна быть заложена некоторая сортировка, а тем паче, если на ее основании могут быть произведены еще какие-то доп. выборки, то это значит, что данные возможности должны быть реализованы на уровне ядра. Это постулат.

Andrey-MSK, вы в команде работали когда-нибудь? Мне кажется нет.
Если это ПО лично ваше и делается в ед. лице - ваше право как поступать. Но когда вы столкнетесь с децентрализованной разработкой, и тем более в какой-то более-менее серьезной конторе - вам придется следовать строгим критериям. И лучше всего к этому приучаться заранее.
В некоторых таких конторах (в двух последних точно, где я участвовал) - все ваши размышления, которые вы мне пишете - отметут на раз два, даже не слушая. Вам все равно придется переделывать.

По большей части, именно с этой позиции я вам и даю рекомендации. И просто предупреждаю о возможных последствиях и трудностях, которые неизбежно вызовет ваш подход "толкания" логики в View.
Вы думаете я ни разу не пытался смухлевать? Как бы не так! . Но позже поимел много неприятностей и бессонных ночей.
Поэтому, с некоторых пор пытаюсь делать сразу все правильно, возможно, иногда даже через чур излишне правильно.
Зато, внедрение доп. хотелок происходит крайне легко и быстро. Я вам рекомендую выработать такой же подход. Не ленитесь.

Добавлено через 2 минуты
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
так как это MVC.
Ну нет же!
MVC - это MVC, будь то джава или шарп. Мы же говорим именно про MVVM. И здесь вы в View пытаетесь приписать слишком много лишнего.
0
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
03.09.2026, 17:43
wizard41, Ну хорошо. То есть вы предлагаете сортировать всё в VM и написать что-то типа такого?
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Collections.Specialized;
using System.ComponentModel;
using System.Linq;
 
namespace VModels.Extensions
{
    /// <summary>
    /// <br>Предоставляет методы расширения для отслеживания изменений свойств элементов внутри <see cref="ObservableCollection{T}"/>.</br>
    /// <br>Стандартная <see cref="ObservableCollection{T}"/> уведомляет только об изменении структуры коллекции (добавление/удаление элементов),</br>
    /// <br>но не о том, что изменились свойства самого объекта. Этот класс решает эту проблему.</br>
    /// </summary>
    public static class ObservableCollectionExtensions
    {
        /// <summary>
        /// Подписывается на события изменения свойств элементов коллекции и структуру самой коллекции.
        /// </summary>
        /// <typeparam name="T">Тип элементов коллекции, реализующий <see cref="INotifyPropertyChanged"/>.</typeparam>
        /// <param name="collection">Коллекция, изменения которой нужно отслеживать.</param>
        /// <param name="onChanged">Действие, вызываемое при любом изменении (изменение свойства элемента, добавление/удаление элемента).</param>
        /// <param name="trackExistingItems">
        /// <br>Флаг, указывающий, нужно ли сразу подписываться на элементы, уже находящиеся в коллекции при вызове метода.</br>
        /// <br>По умолчанию false — подписка происходит только на новые элементы.</br>
        /// <br>Это полезно, чтобы не помечать данные как "измененные" сразу после загрузки.</br>
        /// </param>
        /// <returns>
        /// <br>Объект <see cref="IDisposable"/>.</br>
        /// <br>Для предотвращения утечек памяти необходимо вызвать <c>Dispose()</c> на возвращенном объекте,</br>
        /// <br>когда коллекция более не нуждается в отслеживании изменений (например, при закрытии ViewModel).</br>
        /// </returns>
        /// <exception cref="ArgumentNullException">
        /// Возникает, если <paramref name="collection"/> или <paramref name="onChanged"/> равны null.
        /// </exception>
        public static IDisposable TrackItemChanges<T>(this ObservableCollection<T> collection,
                                                      Action onChanged,
                                                      bool trackExistingItems = false)
            where T : class, INotifyPropertyChanged
        {
            ArgumentNullException.ThrowIfNull(collection);
            ArgumentNullException.ThrowIfNull(onChanged);
 
            Dictionary<T, PropertyChangedEventHandler> subscriptions = new Dictionary<T, PropertyChangedEventHandler>();
 
            void OnCollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
            {
                // Подписка на добавленные элементы
                if (e.NewItems != null)
                {
                    foreach (T item in e.NewItems)
                    {
                        if (item != null)
                        {
                            PropertyChangedEventHandler handler = new PropertyChangedEventHandler((s, args) => onChanged());
                            item.PropertyChanged += handler;
                            subscriptions[item] = handler;
                        }
                    }
                }
 
                // Отписка от удаленных элементов
                if (e.OldItems != null)
                {
                    foreach (T item in e.OldItems)
                    {
                        if (subscriptions.TryGetValue(item, out PropertyChangedEventHandler handler))
                        {
                            item.PropertyChanged -= handler;
                            subscriptions.Remove(item);
                        }
                    }
                }
 
                // Обработка полной замены коллекции
                if (e.Action == NotifyCollectionChangedAction.Reset)
                {
                    foreach (T item in subscriptions.Keys.ToList())
                        item.PropertyChanged -= subscriptions[item];
 
                    subscriptions.Clear();
                }
 
                // Уведомляем об изменении (но не при пустом Changed)
                onChanged();
            }
 
            collection.CollectionChanged += OnCollectionChanged;
 
            // Подписываемся на уже существующие элементы только если явно запрошено
            if (trackExistingItems)
            {
                foreach (T item in collection)
                {
                    if (item != null)
                    {
                        PropertyChangedEventHandler handler = new PropertyChangedEventHandler((s, args) => onChanged());
                        item.PropertyChanged += handler;
                        subscriptions[item] = handler;
                    }
                }
            }
 
            return new CollectionChangeTracker<T>(collection, subscriptions, OnCollectionChanged);
        }
 
        /// <summary>
        /// Внутренний класс для управления подписками и обеспечения корректной очистки ресурсов при вызове Dispose().
        /// </summary>
        private class CollectionChangeTracker<T> : IDisposable
            where T : class, INotifyPropertyChanged
        {
            private readonly ObservableCollection<T> _collection;
            private readonly Dictionary<T, PropertyChangedEventHandler> _subscriptions;
            private readonly NotifyCollectionChangedEventHandler _handler;
            private bool _disposed;
 
            public CollectionChangeTracker(ObservableCollection<T> collection,
                                           Dictionary<T, PropertyChangedEventHandler> subscriptions,
                                           NotifyCollectionChangedEventHandler handler)
            {
                _collection = collection;
                _subscriptions = subscriptions;
                _handler = handler;
                _disposed = false;
            }
 
            public void Dispose()
            {
                if (_disposed)
                    return;
 
                _disposed = true;
                _collection.CollectionChanged -= _handler;
 
                foreach (T item in _subscriptions.Keys.ToList())
                    item.PropertyChanged -= _subscriptions[item];
 
                _subscriptions.Clear();
            }
        }
    }
}
и запускать это на любое изменение данных, а коллекция будет сама себя сортировать и перерисовывать UI? Это я написал при помощи ИИ, мне нужно было решить проблему изменения данных в коллекции относительно оригинала, что бы проверять в команде на сохранение.
0
Эксперт JavaЭксперт по электроникеЭксперт .NET
 Аватар для wizard41
3463 / 2784 / 575
Регистрация: 04.09.2018
Сообщений: 8,757
Записей в блоге: 3
03.09.2026, 18:40
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
То есть вы предлагаете
Скажем так, я пока ничего не предлагаю конкретного, т.к. не знаком с целью конкретной реализации.
Пока что, я направляю вас на раздумья, по поводу организации взаимодействия логики слоев.
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
что-то типа такого?
Возможно да. Расширение как вариант. Опять же, нет понимания для чего это..

Считаю, здесь сейчас важна не столько сама реализация, сколько понимание того - где ее разместить и как.
Для выяснения - небольшое тестовое задание, чтобы понять как вы мыслите:
1. Вы показываете некоторое число в окне. Со временем, необходимо изменить кол-во знаков после запятой.
2. (Усложнение +): то же, что и п.1, но число является частью некоторого текста.
3. (Усложнение ++): все что выше, но нужно иметь возможность пользователю менять кол-во знаков.
4. (Усложнение +++): ко всему этому, добавляется возможность отобразить число прописью.

Ваши действия?
(Идеальный вариант - View не трогаем вообще!)

Добавлено через 42 секунды
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
сама себя сортировать и перерисовывать UI?
не сама себя, а по запросу пользователя (по сигналам от UI).

Добавлено через 41 минуту
Andrey-MSK, или вот, ситуация ближе к вашему случаю:
View, получив "сырую" коллекцию данных, отсортировал ее (сам) и показал. Теперь, нам нужно из показанных данных отобразить список каких-то деталей (часть объекта), причем в том же порядке, в каком сейчас это видит пользователь.

VM, в вашем случае, о том что видит пользователь и в каком порядке - ничего не знает. Поэтому, у вас будет как минимум два варианта:
а) передать обратно в VM текущее представление, VM делает новую выборку и выкидывает (опять же!) во View коллекцию, согласно текущему виду.
б) передать в VM параметр, по которому произведется новая выборка, VM опять же перекидывает "сырые" данные обратно в View, а View снова по каким-то своим соображениям ее сортирует, чтобы она соответствовала текущему представлению основной коллекции.

В случае, когда порядком отображения командует сама VM - она сама уже будет находится в необходимом состоянии, по которому можно за один проход получить пачку новых данных, причем именно в том виде, который сейчас отображается у пользователя. В этом как раз и задача VM. Формировать показ (не данные!) нужным образом.
0
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
04.09.2026, 08:47
Цитата Сообщение от wizard41 Посмотреть сообщение
Теперь, нам нужно из показанных данных отобразить список каких-то деталей (часть объекта), причем в том же порядке, в каком сейчас это видит пользователь.
У меня сортировка идёт только для порядка отображения. Нет таких случаев как вы предлагаете. Нет выборок согласно того что показывается и т.д. По сути - у меня простейший вариант упорядочивания данных и это упорядочивание ни на что не влияет, кроме как на отображение. Потому я вам и говорил что вы усложняете.
Цитата Сообщение от wizard41 Посмотреть сообщение
Для выяснения - небольшое тестовое задание, чтобы понять как вы мыслите:
Вот когда мне нужно будет такое провернуть, тогда и буду думать. Первое что приходит на ум - написать Behavior, который будет форматировать определённые части строки согласно выбора модификатора. Можно конечно и VM напрячь с этим, но продумывать нужно будет гибкость этого всего. В настоящий момент мне достаточно в привязке StringFormat=N2 и цепочки StackPanel для формирования чего-то из многих частей..

Добавлено через 2 минуты
Цитата Сообщение от wizard41 Посмотреть сообщение
2. (Усложнение +): то же, что и п.1, но число является частью некоторого текста.
String.Join() и последующая привязка к элементу UI.
Цитата Сообщение от wizard41 Посмотреть сообщение
3. (Усложнение ++): все что выше, но нужно иметь возможность пользователю менять кол-во знаков.
String.Join() и последующая привязка к элементу UI.
Цитата Сообщение от wizard41 Посмотреть сообщение
4. (Усложнение +++): ко всему этому, добавляется возможность отобразить число прописью.
Разобраться с падежами и далее String.Join() и последующая привязка к элементу UI.
0
Эксперт JavaЭксперт по электроникеЭксперт .NET
 Аватар для wizard41
3463 / 2784 / 575
Регистрация: 04.09.2018
Сообщений: 8,757
Записей в блоге: 3
04.09.2026, 14:16
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
У меня сортировка идёт только для порядка отображения. Нет таких случаев как вы предлагаете.
Ну понятно. Нет, эти тезисы я предложил для чисто алгоритмического представления решения такого рода задач. Не писать ничего, без кода - просто представить пути решения.
Суть этого - понять, что не всегда перекладывание логики в View удобно и полезно.

Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Вот когда мне нужно будет такое провернуть, тогда и буду думать.
Ну я так и понял
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Первое что приходит на ум - написать Behavior, который будет ...
Применение разного рода конвертеров, видимо, вами не рассматривается?
Вот я и хотел посмотреть, на сколько "сильно" вы можете работать со слоями..

Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Потому я вам и говорил что вы усложняете.
Ладно. Мои советы/утверждения совсем не догма и не прямое руководство к действию. Я всего лишь огласил принципы, как обычно это делается в профессиональных кругах..
Если ваше собственное решение (через View) вас устраивает и допускается, то делайте так и не слушайте никого .
О возможных проблемах в дальнейшем - я выше говорил. Решать вам.
1
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
04.09.2026, 14:53
Цитата Сообщение от wizard41 Посмотреть сообщение
Применение разного рода конвертеров, видимо, вами не рассматривается?
Первым в голову не пришло, но в процессе раздумий может и додумался бы
Цитата Сообщение от wizard41 Посмотреть сообщение
Я всего лишь огласил принципы, как обычно это делается в профессиональных кругах..
Я ничего против не имел и не имею, приятно поспорить с умным человеком
Цитата Сообщение от wizard41 Посмотреть сообщение
Если ваше собственное решение (через View) вас устраивает и допускается, то делайте так и не слушайте никого
Ну почему не слушай, слушать тоже нужно А так я сам по себе, всё в одном лице - придумал, спроектировал, пинка себе дал, написал -> работает, народ не жалуется

Вот сижу время от времени переписываю по мере получения новых знаний. Первый вариант приложухи был ваще жесть в плане кода, но работало блин
Цитата Сообщение от wizard41 Посмотреть сообщение
О возможных проблемах в дальнейшем
Не тот возраст уже у меня про дальнейшее в профессиональных кругах.

Добавлено через 25 минут
Цитата Сообщение от wizard41 Посмотреть сообщение
Применение разного рода конвертеров, видимо, вами не рассматривается?
Можно конечно докрутить вот этот
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
using System;
using System.Globalization;
using System.Windows.Data;
 
namespace DBClient.Converters
{
    [ValueConversion(typeof(decimal?), typeof(string))]
    public class DecimalNullableValueConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {
            decimal? dValue = (decimal?)value;
            return dValue?.ToString(culture);
        }
 
        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {
            string dValue = value.ToString();
 
            dValue = dValue.Trim();
 
            if (dValue.Contains('.'))
                dValue = dValue.Replace(".", ",");
 
            if (decimal.TryParse(dValue, NumberStyles.Any, culture, out decimal result))
                return result;
 
            if (dValue == "")
                value = null;
 
            return value;
        }
    }
}
1
Эксперт JavaЭксперт по электроникеЭксперт .NET
 Аватар для wizard41
3463 / 2784 / 575
Регистрация: 04.09.2018
Сообщений: 8,757
Записей в блоге: 3
04.09.2026, 17:33
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Не тот возраст уже у меня про дальнейшее
"И мне не двадцать пять!..." (с) И. Тальков, "Таня".
Не считаю, что возраст может ограничивать стремление к познанию чего-то нового.. Мне вон тоже, без малого полтинник
Но ничего, пытаемся, так сказать, остатками зубов погрызть гранит науки .

А то, что я иногда так "бесповоротно" и "принципиально" формулирую свои умозаключения - это, в каком то смысле дань (осадок/остаток) прошлой академической деятельности.. Студентам нельзя давать много воли для решения задач. А то, загордятся раньше времени и не поймут суть процесса! .
Сказано делать вот так - значит только так! (преподавал вышмат в нескольких институтах).

Так что, Andrey-MSK, в некотором смысле, вы для меня тоже "студент"! Звиняйте! .
Особенно, когда здесь подворачивается какая-нибудь тема для разговора.
Ибо, "Иных уж нет, а те далече.." (с) А.С. Пушкин "Евгений Онегин".
1
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
04.09.2026, 20:09
Цитата Сообщение от wizard41 Посмотреть сообщение
Но ничего, пытаемся, так сказать, остатками зубов погрызть гранит науки
Мы всю жизнь учимся, такая уж наша доля у инженеров
Цитата Сообщение от wizard41 Посмотреть сообщение
вы для меня тоже "студент"
Не вопрос
Цитата Сообщение от wizard41 Посмотреть сообщение
преподавал вышмат в нескольких институтах
0
Модератор
Эксперт .NET
 Аватар для Элд Хасп
16166 / 11286 / 2892
Регистрация: 21.04.2018
Сообщений: 33,175
Записей в блоге: 2
04.09.2026, 20:54
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Мы всю жизнь учимся, такая уж наша доля у инженеров
Цитата Сообщение от Andrey-MSK Посмотреть сообщение
Я не запнулся, просто продолжаю расспросы про чистый CodeBehind
Может не целиком за всей дискуссией проследил, но моё скромное мнение.

1) Не надо смешивать MVVM и "запрет Code Behind". Они совершенно между собой не связаны. В MVVM нет никаких правил на счёт реализации View.

2) Вы правы на все 100%, когда чисто визуальную сортировку не прокидываете в ViewModel.
wizard41 прав на все 100%, когда пишет о том, что в общем случае сортировка чаще всего это сортировка исходных данных, так как выборка целиком всех данных в View не происходит. Поэтому сортировка при ленивой выгрузке - это задача Модели.

3) Вы не правы когда полагаетесь в реализации только на Code Behind. Вашу реализацию можно сделать через производный тип, через статические хелперы, через Attached Property. Какой вариант из них (включая ваш) оптимальнее.... это зависит от того, что считать "оптимальным". В современном программировании один из критериев оптимальности это возможность тестирования (юнит и интергральное). Code Behind очень трудно автоматически тестировать. А затраты на тестирование в современном продакшен это часто значительно больше затрат чем на саму разработку.
1
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
04.09.2026, 22:36
Элд Хасп, Да не, мы тут вроде разобрались wizard41, даёт советы со своего опыта работы в конторах, которые профессионально занимаются разработкой. Там свои критерии и правила. Я ему возражал со своей колокольни, где всё делаю в одну каску и мне всё ясно и понятно где и что происходит в рамках моего проекта
Цитата Сообщение от Элд Хасп Посмотреть сообщение
Не надо смешивать MVVM и "запрет Code Behind". Они совершенно между собой не связаны. В MVVM нет никаких правил на счёт реализации View.
100% согласен, но много где есть упётрые тимлидеры, которые не приемлют такое поведение
Цитата Сообщение от Элд Хасп Посмотреть сообщение
так как выборка целиком всех данных в View не происходит
View никогда исходные данные не выбирает, он показывает то, что ему дают и просто сортирует их в удобоваримом варианте для пользователя, ну к примеру 10-002, 01-003, 02-004 и т.д. Вам ведь проще видеть это как 01-003, 02-004, 10-002. Вот про эту сортировку мы и спорили

Добавлено через 3 минуты
Цитата Сообщение от Элд Хасп Посмотреть сообщение
Какой вариант из них (включая ваш) оптимальнее....
Я выбрал CVS, так как это проще и можно в три строчки привязать кастомный сортировщик

Добавлено через 18 минут
Цитата Сообщение от Элд Хасп Посмотреть сообщение
Поэтому сортировка при ленивой выгрузке - это задача Модели
Ленивой загрузки у меня нет, я гружу только то что нужно. Потому сортирует у меня только View, так как вся логика в моем приложении работает на сырых данных, СУБД (Model) и VM.

Добавлено через 17 минут
Гружу примерно так, по параметрам, и получаю то что нужно
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
public async Task<List<KSGWorkDrawData>> GetKSGWorkDrawDataAsync(int systemID)
{
    string sqlText = "dbo.spBRSelectKSGWorkDrawDataN";
 
    try
    {
        using (SqlConnection sqlConnection = new SqlConnection(_connectionString))
        {
            using (SqlCommand sqlCommand = new SqlCommand(sqlText, sqlConnection) { CommandType = CommandType.StoredProcedure })
            {
                sqlCommand.AddInputParameter("@idDrawSys", systemID, SqlDbType.Int);
 
                await sqlCommand.Connection.OpenAsync();
 
                using (SqlDataReader sqlDataReader = await sqlCommand.ExecuteReaderAsync())
                    return await SqlMapper.MapToListAsync(sqlDataReader, KSGWorkDrawDataMapper);
            }
        }
    }
    catch (SqlException sqlEx)
    {
        throw new ApplicationException(string.Format("T-SQL #{0} - {1}", sqlEx.Number, sqlEx.Message), sqlEx);
    }
    catch (Exception ex)
    {
        throw new ApplicationException(ex.Message, ex);
    }
}
0
Эксперт JavaЭксперт по электроникеЭксперт .NET
 Аватар для wizard41
3463 / 2784 / 575
Регистрация: 04.09.2018
Сообщений: 8,757
Записей в блоге: 3
05.09.2026, 13:49
Andrey-MSK, а чем у вас VM занимается?
0
 Аватар для Andrey-MSK
3397 / 2283 / 388
Регистрация: 14.08.2018
Сообщений: 7,755
Записей в блоге: 4
14.09.2026, 08:46
wizard41, Ну как чем. Гоняет данные между View и DA. Строит сложные объекты привязки и потом разбирает их для DA. Команды, управляет режимами работы View ну и т.д.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
14.09.2026, 08:46

Работа с SelectedItems ListBox
Здравствуйте, делаю приложение на WPF, решил попробовать делать его по паттерну MVVM. Появилась...

Datagrid получить SelectedItems mvvm
С привязкой SelectedItem все понятно &lt;DataGrid SelectedItem=&quot;{Binding GridSelectedItem}&quot;&gt; ...

Один скролл для всех вкладок - при смене вкладок в TabControl положение скролла остается на прежнем месте
Добрый вечер) Почему при смене вкладок в TabControl положение скрола остается на прежнем месте,...

listbox SelectionChanged clear
привествую. Вопрос есть допустим список из 10 элементов в listbox. я нажимаю на один из них он...

ошибка в TreeView.Items.Clear();
В общем обработчик нажатия кнопки должен добавить в ListSpec один объект, а потом обновить дерево,...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
77
Ответ Создать тему
Новые блоги и статьи
Беседа с ИИ о программистах, недопускающих к созданию и правке кода генеративные ИИ и причины этого
zorxor 21.09.2026
Раньше я радовался или получал некоторые эмоции, пусть небольшие, но всё же, от самого процесса написания кода, рекомпиляции и запуска, видя постепенное развитие программы и прочее. А теперь лень. . .
Мобильное приложение ColorStep
pavlinmavlin 17.09.2026
Реализовал приложение Красный, Зеленый, Синий в Unity3d + c#. Название изменил на ColorStep. Приложение прошло модерацию и теперь доступно для скачивания. Делал его сам, шаг за шагом — и вот,. . .
Запрет дублирования строк в табличной части
Maks 13.09.2026
Реализация из решения ниже выполнена на нетиповом справочнике "Нормы ТО" с табличной часть "Виды ТО", разработанного в КА2, со следующими реквизитами: - ВидТО (СправочникСсылка. ВидыТО); - ВидГСМ. . .
Скрипты Tampermonkey для CyberForum, ChatGPT, Claude и пр.
Jin X 06.09.2026
Скрипты Tampermonkey для CyberForum, ChatGPT, Claude и пр. Работая с форумом и нейросетями в браузере часто хочется что-то подкорректировать или добавить какого-то функционала. Ниже прикреплён. . .
Программа опроса у.з. расходомера SLS-720F
Argus19 02.09.2026
Программа опроса у. з. расходомера SLS-720F Программа опрашивает один раз в минуту три ультразвуковых расходомера SLS-720F через интерфейс RS-485 по протоколу Modbus RTU. Опрашиваются регистры. . .
Hyper-V: Компьютер должен поддерживать доверенный платформенный модуль 2.0.
Maks 31.08.2026
При установке Windows 11 на виртуальную машину Hyper-V 2-го поколения вылезла такая ошибка: Решение: в параметрах виртуальной машины, в разделе "Безопасность" (Security) активировать флаг. . .
Архитектура биовида Стива в Майнкрафте: Зачем бонобо кубический каннибализм
anaschu 30.08.2026
Кубический Вагинокапитализм в Minecraft: Математический инвариант ОДУ и рок Стивов-бонобо Главная задача разработанной «Модели Всего» — наглядно продемонстрировать наличие системной «судьбы». . .
Оттачиваю умение писать js программы.
russiannick 30.08.2026
Проектом выходного дня стало написание Книги шифров Виженера. Итогом стала версия 200, синий туман. Синий туман назван так, потому что замораживает текст под собой. Нажатие синих кнопок управляют. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru