Использование TableView с неизменяемыми объектами. Ошибка бесконечного цикла
Доброго времени суток.
Задача:
Имеется список неизменяемых объектов. Необходимо отобразить этот список в виде таблице TableView через которую также можно будет его редактировать. Часть полей неизменяемых объектов представлены в виде целых чисел и должны отображаться в ячейках таблицы в виде элемента Spiner.
С чем возникли сложности: У объектов есть несколько операций позволяющих задать значение для некоторых полей или выполнить какие-то вычисления. Поскольку объекты неизменяемы - каждая такая операция создает и возвращает новый объект этого же типа содержащий все внесенные изменения. И тут есть два момента:
- Необходимо заменить старую версию объекта на новую в списке элементов таблицы. Список элементов таблицы представлен типом
ObservableList, так что когда он будет измененTableViewавтоматически обнавиться. - Теперь важный момент со
Spiner. Единственный способ подписаться на события от этого элемента, это подписаться на прослушивание событий от его свойства -spiner.valueProperty().addListener(...). Событие будет срабатывать ВСЕГДА, КОГДА ИЗМЕНЯЕТСЯ ЭТО СВОЙСТВО.
В сумме эти два момента дают следующее: клиент взаимодействует со спинером -> изменяется его свойство valueProperty() -> вызывается слушатель этого свойства -> слушатель изменяет объект текущей строки таблицы и его новую версию записывает в список элементов таблицы -> список (напомню - его тип ObservableList) уведомляет таблицу что он был изменен -> таблица обновляется, обновляя значение каждой ячейки измененной строки и таким образом обновляет свойство valueProperty() нашего спинера -> цепочка начинается сначала...
Самое интересное, что когда таблица обновляет свойство valueProperty() спинера, передаваемое таблицей значение автоматически изменяется в зависимости от последней используемой операции со спинером(клиент нажал стрелку "увеличить" или "уменьшить").
Вопрос: как решить проблему бесконечного цикла обновлений?
P.s. этот пример хорошо демонстрирует главную опасность использования паттерна наблюдатель.