2016-01-12 3 views
4

Что случилось с Codename Одна анимация? Я использую их много, и с декабря мое приложение больше не работает. Когда я ушел в июне, все было в порядке (и было так больше года).Codename One Animation Trouble (также в демо-версии Solitaire)?

Мое приложение - это шашки (шашки) и доступно в магазинах приложений с 2013 года. После просмотра демо-версии CN1 Poker я полностью переписал свой графический интерфейс, поскольку я хотел добавить такие анимации в свое приложение. Теперь происходит то, что я внезапно получаю индекс из связанных исключений. Я сузил это вниз к следующей ситуации:

cont.addComponent(comp); 
... 
... 
cont.getComponent(0); <-- index out of bound exception: 0 out of 0 

Я уже использовал newVM = истина в июне, который теперь по умолчанию, я считаю. Я попытался исправить ситуацию, добавив

cont.animateLayoutAndWait(100); 

после вызова addComponent. Это фиксировало индекс из связанных исключений, но теперь приложение просто падает в случайные моменты после того, как работает нормально на короткое время. Я попытался, но не смог найти источник проблемы. Что-то изменилось в CN1, так что мой код больше не работает. (См. Также старый форум, поиск «черновиков», где я опубликовал полный список моего основного дизайна.)

Я изучил новую демоверсию Solitaire, которая имеет большую часть функциональности анимации, в которой я нуждаюсь. И версии хранилища приложений Solitaire отлично работают на всех устройствах iOS/Android. Небольшая ошибка заключается в том, что можно перетащить группу карт, включая некоторые, которые направлены вниз, которые направлены вверх во время операции перетаскивания. Также довольно сложно подобрать нужное количество карт. Перетаскивание группы карт также оставляет на экране белый след, что выглядит не очень красиво. Это также происходит в симуляторе.

В качестве эксперимента я переработал свой макет графического интерфейса, чтобы он был похож на код Solitaire: два слоя кнопок, с той лишь разницей, что я использую GridLayout (10,10), где Solitaire использует SolitaireLayout(). Это работает, за исключением одного: если контролер перемещает DOWN на плату, он правильно перемещает НАРУШЕНИЕ других шашек, но если шашка движется вверх по доске, она перемещается под другими шашками.

Мой код выглядит следующим образом:

Button pc = (Button)piecesCnt.getComponentAt(a1); 
Button to = (Button)piecesCnt.getComponentAt(a2); 

piecesCnt.removeComponent(pc); 
piecesCnt.addComponent(a1, createPieceButton(Piece.EMPTY_PIECE, true)); 
piecesCnt.removeComponent(to); 
piecesCnt.addComponent(a2, pc); 

piecesCnt.animateLayoutAndWait(1000); 

Таким образом, кажется, что кнопки всегда рисуются в порядке их GridLayout, в то время как я надеялся, что кнопка анимированных (перемещение) будет обращено последний/сверху, просто как движущиеся карты в Solitaire.

Разница между обработкой анимации в SolitaireLayout vs. GridLayout? Если да, может ли это быть изменено в логике анимации? В противном случае я должен добавить дополнительный слой анимации и много накладных расходов.

И на Android анимация (движение) работает неправильно. Поэтому я решил также самостоятельно построить и протестировать демоверсию Solitaire на своих устройствах с текущей версией CN1 (плагин 3.2.6, libs 2016-01-11). Я изменил анимацию на 10 раз медленнее, чтобы лучше видеть, что происходит. В симуляторе макет и анимация работают в основном отлично, но на устройствах iOS и Android есть много проблем.

Simulator (Windows 7, NetBeans 8.0.2): - Я заменил значки шрифтов текстом, так как они отсутствуют. - Но как получить доступ к меню гамбургеров? Я не вижу 3 точки, и для этого нет места. - Иногда можно перетаскивать группы карт с некоторыми картами с понижением; при перетаскивании они временно перевернуты вверх. - Автовоспроизведение не всегда работает. (Не все ходы воспроизводятся.)

На iOS 9.2 (iPad 4), iOS 8.4 (iPhone 4): - [?] Отображается в меню гамбургера. - После запуска задняя панель карты заднего плана прыгает на дно контейнера/экрана. - Иногда, в анимации с раздачей от карты, карты в самой правой таблице временно обращены вверх, а карты, уже стоящие вверх, переворачиваются вниз. Однако конечное состояние сделки является правильным. - Отменить/Повторить: иногда получается обратная сторона карты на палубе 0 и обращенная вниз на палубе 1. - Повтор иногда «перескакивает» на новый макет вместо оживления. Только для iPhone: - Последовательность автовоспроизведения движется слева от непоследовательного состояния основы: верхние карты сердца-J, club-10, club-K, diamond-Q; т. е. 2 клубных карты на разных стопках фундамента.

На Android 5.1.1 (Nexus 7) есть еще проблемы. - Адаптация сделки от колоды не очень привлекательна. Карты вставляются (сдвигаются) в нижней части столов таблицы, поэтому они скользят по другим картам. Движущиеся карты должны быть обращены вниз, но обычно должны стоять вверх, всегда отображая первую карту, нанесенную на таблицу 1. Карты в самой правой таблице временно отображаются вверх. Наконец, карты, уже стоящие вверх, перевернуты вниз и назад. Однако конечное состояние сделки является правильным. - Автовоспроизведение также неверно, если несколько шагов подряд. Во время анимации несколько карточек фондов, стоящих вверх, изменяют свою ценность карты (спереди) временно. Также движущиеся карты скользят под карточкой фундамента (а иногда и заканчиваются, но это исключение). - После завершения игры хорошо выполненный экран поврежден, так как текст кажется отображаемым не наложенным, а под картами (в большом белом пространстве), которые только частично видны в крошечной части в верхней части экрана , - Запуск новой игры часто терпит неудачу, потому что сделка с колодой не запускается; на экране изображена колода и четыре царя на фундаменте с пустой таблицей. При постукивании по колоде раздаётся карта, и хорошо показана последовательность. Иногда повторение этих результатов приводит к успешному запуску новой игры.

Все это заняло много времени, и у меня все еще нет приложения, которое работает снова, что очень расстраивает. Имея так много проблем с этой темой, даже с загруженным демо-приложением, создание такого типа приложения с помощью Codename. Кажется, что вы строите на зыбучих песках. Пожалуйста помоги!

ответ

1

Вы должны, вероятно, просто спросил, когда вы запускали в неприятности вместо того чтобы работать так тяжело на посту. Да, мы сделали существенное изменение смены совместимости как часть исправления ошибок для долговременных проблем с анимацией (где параллельная анимация может столкнуться).

Это привело к некоторым столкновениям, но уменьшило несоответствия между устройствами/имитатором, что всегда хорошо.

Мы объявили это здесь: https://www.codenameone.com/blog/new-animation-manager.html

Это на самом деле гораздо проще создать портативную анимации теперь, как все будет синхронизироваться, чтобы избежать столкновений анимации, например, если вы делаете Component.removeComponent() во время анимации, он будет неявно добавлен в очередь анимации и выполнен после завершения анимации, а не сразу.

Чтобы отложить следующее действие до тех пор, после анимации мы имеем:

form.getAnimationManager().flushAnimation(() -> doThisAfterAnimation()); 

Намного проще и не особый случай глобальных блокировок.

Его немного сложно «переместить» код непосредственно на новый подход, но похоже, что ваша анимационная логика основана на анимации, принимающей 1000 мс, и что она полностью закончена, когда метод возвращает, что может не всегда быть в этом случае (в качестве дополнения/удалить вызовы или другую логику может мешать).

В прошлом единственный способ гарантировать анимацию был завершен, чтобы разделить их на части, но теперь вы можете просто использовать flushAnimation, чтобы убедиться, что все анимации завершены. Имейте в виду, что некоторые вещи, которые не являются явно анимацией, теперь могут стать анимацией случайно, например. компонент add/remove станет анимацией, если при вызове будет выполняться анимация ...

0

Извините, я пропустил сообщение в блоге о новом менеджере анимации от 16 декабря. Демо-версия Solitaire October 8, и я проверил Руководство для разработчиков от 31 декабря, поэтому я думал, что я в курсе последних событий. Тем не менее, мне непонятно, как использовать новый менеджер анимации. В новом Руководстве разработчика Januari 11 ничего не говорится по этой теме, и ваш ответ/сообщение в блоге не очень сложны.

Это также очень поможет, если демоверсия Solitaire будет обновлена ​​для работы с новым менеджером анимации.

Теперь мои вопросы:

1) Как переписать следующий код, чтобы использовать новый менеджер анимации? Это реалистичный сценарий, потому что у меня есть анимация с несколькими шагами, которые должны выполняться последовательно.

// simplified code (background layer omitted) 
public void start() { 
    if(current != null){ 
     current.show(); 
     return; 
    } 

    Form form = new Form("Draughts 2"); 
    Container piecesCnt = new Container(new GridLayout(10, 10)); 
    for (int i=0; i<100; i++) { 
     piecesCnt.addComponent(createPieceButton(piece(i), true)); 
    } 
    form.addComponent(piecesCnt); 
    form.show(); 

    new UITimer(() -> { 
     testAnimation(piecesCnt, 0,9 , 9,0); // moves UNDER other pieces 
     testAnimation(piecesCnt, 9,0 , 0,9); // " OVER "  " 
     testAnimation(piecesCnt, 1,0 , 9,8); // " OVER "  " 
     testAnimation(piecesCnt, 9,8 , 1,0); // " UNDER "  " 
    }).schedule(1500, false, form); 
} 

private void testAnimation(Container piecesCnt, int x1,int y1, int x2,int y2) { 
    int a1 = 10 * y1 + x1; 
    int a2 = 10 * y2 + x2;   
    Button pc = (Button)piecesCnt.getComponentAt(a1); 
    Button to = (Button)piecesCnt.getComponentAt(a2); 
    piecesCnt.removeComponent(pc); 
    piecesCnt.addComponent(a1, createPieceButton(Piece.EMPTY_PIECE, true)); 
    piecesCnt.removeComponent(to); 
    piecesCnt.addComponent(a2, pc); 
    piecesCnt.animateLayoutAndWait(1000); 
} 

2) Есть ли переписывание это также решить проблему штучного (проверки), движущихся под вместо более других частей?

3) Как сделать паузу между двумя вызовами TestAnimation? (. Не спя, очевидно)


Обновление 2016-01-14 (смотрите также раздел Комментарий):

Я попробовал две вещи с flushAnimations:

1) Используйте функцию как это:

private void flushAnimations(Form f) { 
    f.getAnimationManager().flushAnimation(() -> {}); 
} 

и называть это между последовательными анимациями. Это не работает.

2) Вложенные flushAnimations:

testAnimation(piecesCnt, 0,9 , 9,0); 
f.getAnimationManager().flushAnimation(() -> { 
    testAnimation(piecesCnt, 9,0 , 0,9); 
    f.getAnimationManager().flushAnimation(() -> { 
     testAnimation(piecesCnt, 1,0 , 9,8); 
     f.getAnimationManager().flushAnimation(() -> { 
      testAnimation(piecesCnt, 9,8 , 1,0); 
     }); 
    }); 
}); 

Это, кажется, работает на прошивке, но не на моем Android устройства: обычно после второй анимации экран мерцает и переходит к следующему состоянию, а не анимация. Кроме того, это нехорошее решение.

Тогда я попробовал решение UITimer:

blockUI(piecesCnt); 
new UITimer(() -> { testAnimation(piecesCnt, 0,9 , 9,0); }).schedule(2000, false, f); 
new UITimer(() -> { testAnimation(piecesCnt, 9,0 , 0,9); }).schedule(3500, false, f); 
new UITimer(() -> { testAnimation(piecesCnt, 1,0 , 9,8); }).schedule(5000, false, f); 
new UITimer(() -> { testAnimation(piecesCnt, 9,8 , 1,0); }).schedule(6500, false, f); 
new UITimer(() -> { 
    unblockUI(piecesCnt); 
}).schedule(8000, false, f); 

private boolean blocked = false;  
private void blockUI(Container piecesCnt) { 
    blocked = true; 
    int n = piecesCnt.getComponentCount(); 
    for (int i=0; i<n; i++) { 
     piecesCnt.getComponentAt(i).setDraggable(false); 
    } 
} 
private void unblockUI(Container piecesCnt) { 
    ... 
} 

Это работает, но это также не очень желательным решением. У меня есть функция autoplay, которая воспроизводит целую игру, состоящую из> 100 ходов, причем каждый ход состоит из 1 или более шагов анимации. Пользователь может прервать этот процесс, нажав кнопку остановки.

Мне очень хотелось бы посмотреть, как демо-ролики Poker and Solitaire (Autoplay!) Должны быть закодированы с помощью новой обработки анимации.

Пожалуйста, найдите минутку, чтобы перейти по этой ссылке, чтобы узнать, о какой функциональности я говорю: http://toernooibase.kndb.nl/opvraag/applet.php?taal=1&kl=46&Id=4579&r=10&jr=16&wed=845502. Просто нажмите кнопку автовоспроизведения ('>') под доской. (Мое приложение также может играть в игру, и вы можете настроить его на 1 минуту за ход, в течение которого графический интерфейс заблокирован.)

Я видел, что Руководство разработчика было обновлено 13 января и теперь имеет глава/приложение по программированию в повседневной игре. Это хорошо, хотя версия CN1Poker, которую он перечисляет, по-прежнему не работает должным образом на устройстве Android: анимация карт раздачи показывает, что карты в основном прыгают и иногда сползают на свои позиции. (Он отлично работает в симуляторе и на устройствах iOS.)

Как вы можете сказать, что «на самом деле МНОГО проще создавать переносимую анимацию сейчас»? Думаю, в моем случае на самом деле это стало намного сложнее. Мне нужна альтернатива для старого подхода, который также используется в демо-играх в покер и пасьянс: используйте animateLayoutAndWait и не добавьте/удалите действия во время анимации (также убедитесь, что программа логики).

Являясь основным подписчиком (в течение 3 лет), я должен использовать последнюю версию CN1, но с текущей версией CN1 я больше не знаю, как это кодировать. Я думаю, что это довольно фундаментальная проблема, так как все игры используют такую ​​функциональность.

+0

Он не решает проблему 2, поскольку это относится к Z-упорядочению. Просто поместите компонент «позже» в список компонентов. Вы можете использовать 'UITimer' для задержки следующего вызова, как всегда. Я немного пересмотрел свой ответ. Обратите внимание, что вы не должны указывать обновления в качестве ответа, но вместо этого отредактируйте исходный вопрос с дальнейшими подробностями (без изменения его «основного вопроса») или просто создайте новый вопрос, который полностью прекрасен. –

+0

Я не понимаю, как решить проблему Z-упорядочения. Что вы подразумеваете под «поместите компонент« позже »в список компонентов? Компонент был добавлен последним (по времени), но, конечно, он не может быть последним в порядке GridLayout, потому что его место имеет смысл: это шахматная доска. (Как это работает в старой демо-версии Solitaire?) Я обновил свое второе сообщение, чтобы попробовать ваши предложения с помощью flushAnimation и UITimer. –

+0

Он должен иметь последний индекс компонента, так что макет сетки немного проблематичен в этом смысле, поскольку он не был предназначен для z-упорядочения. Я не уверен, есть ли решение для этого с сеткой. Вероятно, вы можете использовать 'TableLayout', который не чувствителен к z-упорядочению при использовании с ограничением. Хотя его гораздо более «шелушащийся» для некоторых сложных обычаев. –