Здравствуйте, уважаемые форумчане!
Цель: отследить были ли произведены изменения в ячейке и если были, то перекрасить ее в другой цвет и показать кнопку Сохранить изменения, если изменения небыли произведены (или передумали вводить изменения), вернуть цвет обратно. Делается это с целью записи изменений в массив с указанием где именно внести изменения и внести их в xml из которого таблица и заполнялась.
Столкнулся с некоторыми проблемами, решить которые надеюсь в Вашей помощью.
Мои изыскания по достижению вышеописанной цели (за одно кому-то время сэкономлю с реализацией частичных решений):
Ниже привожу пример добывания вновь введенного текста, для меня это пока основная проблема (процесс сравнения и перекрашивания ячеек не обсуждаю и не описываю).
Начинаю с простого считывания текста по событию TextEvent.TEXT_INPUT и присвоение глобальной переменной _changedKey:
ActionScript 3 |
1
2
3
4
5
6
7
8
9
10
11
| private var _changedKey:String;
.......................................
dataGrid.addEventListener(TextEvent.TEXT_INPUT, onGridTextInputHandler);
protected function onGridTextInputHandler(event:TextEvent):void
{
_changedKey = event.target.text;
}
// ех, если бы оно сразу ловило свежевведенный текст, но в _changedKey не дописывается последний введенный символ |
|
Как выясняется, с помощью события DataGrid --> TextEvent.TEXT_INPUT, не получится обновлять текст, так как данное событие выводит старый текст, т.е. на шаг опаздывает и не обновит переменную _changedKey 'свежим' текстом.
Самое простое решение присвоить последний вводимый символ запаздывающему тексту:
ActionScript 3 |
1
2
3
4
5
6
7
8
9
10
| private var _changedKey:String;
.......................................
dataGrid.addEventListener(TextEvent.TEXT_INPUT, onGridTextInputHandler);
protected function onGridTextInputHandler(event:TextEvent):void
{
_changedKey = event.target.text + event.text; //измененная строка
} |
|
Недостаток: если мы поменяем позицию каретки и захотим продолжать вводит текст в середине слова, он всеравно продолжит присваиваться вконце слова.
Решение: Написать функцию, которая учитывает позицию каретки и присваивает новый символ в нужное место в слове.
ActionScript 3 |
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
| private var _changedKey:String;
private var _keyArrTemp: Array; //объявляем массив
private var _caret:uint; //объявляем переменную для каретки
.......................................
dataGrid.addEventListener(TextEvent.TEXT_INPUT, onGridTextInputHandler);
dataGrid.addEventListener(KeyboardEvent.KEY_DOWN, onGridKeyDownHandler); //вешаем новый слушатель
protected function onGridTextInputHandler(event:TextEvent):void
{
_changedKey = event.target.text + event.text;
convertSymbols(event.text, 'add'); // получаем введенный текст
}
protected function onGridKeyDownHandler(keyevent:KeyboardEvent):void
{
_caret = keyevent.target.caretIndex; // считываем позицию каретки
}
protected function convertSymbols(text:String, backspace:String, ind:uint = 1):void
{
switch (backspace)
{
case 'add':
_keyArrTemp = _changedKey.split(''); // бью слово на буквы и записываем в массив
_keyArrTemp.splice(_caret, 0, text); //записываю новую букву в позицию каретки
break
}
_changedKey = _keyArrTemp.toString().split(',').join('');
} |
|
Работает. Но дальше вступает проблемка.. TextEvent.TEXT_INPUT - не умеет ловить клавиши Backspace и Del. поэтому нужно прослушивать нажатие клавиш клавиатуры. Программно ловим упомянутые клавиши:
ActionScript 3 |
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
| private var _changedKey:String;
private var _keyArrTemp: Array; //объявляем массив
private var _caret:uint;
.......................................
dataGrid.addEventListener(TextEvent.TEXT_INPUT, onGridTextInputHandler);
dataGrid.addEventListener(KeyboardEvent.KEY_DOWN, onGridKeyDownHandler);
protected function onGridTextInputHandler(event:TextEvent):void
{
_changedKey = event.target.text + event.text;
convertSymbols(event.text, 'add');
}
protected function onGridKeyDownHandler(keyevent:KeyboardEvent):void
{
_caret = keyevent.target.caretIndex; // считываем позицию каретки
if (_changedKey == '') _changedKey = keyevent.currentTarget.selectedItem[_colName];
if (keyevent.keyCode == 8) convertSymbols(_changedKey, 'back'); // ловим клавишу backspace
if (keyevent.keyCode == 127 || keyevent.keyCode == 46) // ловим клавишу del
convertSymbols(_changedKey, 'del');
}
protected function convertSymbols(text:String, backspace:String, ind:uint = 1):void
{
switch (backspace)
{
case 'back':
_keyArrTemp = text.split('');
_keyArrTemp.splice(_caret-1, ind);
break;
case 'del':
_keyArrTemp = text.split('');
_keyArrTemp.splice(_caret, ind);
break
case 'add':
_keyArrTemp = _changedKey.split('');
_keyArrTemp.splice(_caret, 0, text);
break
}
_changedKey = _keyArrTemp.toString().split(',').join('');
} |
|
Кто заметил неизвестную переменную _colName, она берется со слушателя DataGridEvent.ITEM_EDIT_BEGIN :
ActionScript 3 |
1
2
3
4
5
6
| dataGrid.addEventListener(DataGridEvent.ITEM_EDIT_BEGIN, onGridItemSelectedHandler);
protected function onGridItemSelectedHandler(eObj:Object):void
{
_colName = eObj.target.columns[eObj.columnIndex].dataField;
} |
|
Ну так вот, дальше вступают следующие проблемы:
1. Как считывать редактирование текста, ели пользователю захотелось через зажатый Shift+стрелка влево (право) выделить текст и нажать Del (и еще хуже Backspace). Сработает алгоритм удаления Del или Back и удалится не то что нужно...
2. При выделении мышой нескольких букв и нажатии Ctrl-X нужно снова таки ловить эту комбинацию, высчитывать каретки, количесво выделенных букв... Короче гемор..
Пока в поисках простого решения данной задачи... Хоть бери каким-то образом отключай поддержку комбинаций клавиш, выделение Shift'ом и т.п. чтобы все работало, да и как отключить эти комбинации...
Вижу решение проблемы в том, чтобы каким-то образом искусственно генерировать событие TextEvent.TEXT_INPUT (та даже просто добавлять пробел вконце и сплитить его) дабы считывался вновь введенный текст... Но как это сделать.
Ну или может кто подскажет как он отслеживает изменения в ячейке DataGrid?
У кого какие идеи? Неужели и дальше придется велосипед изобретать?
.