2015-11-09 2 views
2

Я работаю над настольной игрой с мобильным телефоном в качестве контроллера. Игра разработана в Unity 3D и использует приложение Android SensoDuino для отправки значений датчиков Accelerometer и Orientation через bluetooth. Значения отправляются с частотой 100 мс. Но есть отставание между движением телефона и его отражением в игре. Как я могу уменьшить отставание и отобразить движение по шкале 1: 1 без каких-либо рывков или прыжков. Вот код, который я использую -Как сгладить акселерометр и значения датчика ориентации в Unity 3D?

После того, как соединение SerialPort сделано, следующий код используется для чтения данных из порта

void recData() { 
    if ((sp != null) && (sp.IsOpen)) { 
     byte tmp; 
     string data = ""; 
     string avalues=""; 
     tmp = (byte) sp.ReadByte(); 
     while(tmp !=255) { 
      data+=((char)tmp); 
      tmp = (byte) sp.ReadByte(); 
      if((tmp=='>') && (data.Length > 30)){ 
       avalues = data; 
       parseValues(avalues); 
       data=""; 
      } 
     } 
    } 
} 

Поскольку Unity не разрешает доступ объектов на главном потоке из другого, я установил логическую переменную moveObject = true в parseValues() (для преобразования входящей строки в float). Это логическое значение проверяется в функции Update(), и если это правда, для перемещения объекта используется следующая функция.

void moveObj(float x, float y) { 
     speed = 15.0f; 
     Vector3 move = Vector3.zero ; 
     move.x = x; 
     move.y = y; 
     move.Normalize(); 
     // low pass filter 
     prevY = (0.8f * prevY) + ((1.0f - 0.8f) * move.y); 
     prevX = (0.8f * prevX) + ((1.0f - 0.8f) * move.x); 

     transform.Translate((-prevX * speed) * Time.deltaTime,(prevY * speed)* Time.deltaTime, -0.1f, Space.World); 
     readyToMove = false; 

Я попытался использовать простой фильтр нижних частот, чтобы сгладить значения и использовать перевод для перемещения объекта. Проблема в том, что нет движения 1: 1. Существует отставание. Как я могу это исправить? Как я могу получить доступ к объектам в основном потоке из другого потока?

+0

Вы пробовали фильтр первого порядка – UserK

ответ

1

Чтобы решить «лаг», вы можете использовать доступные функции интерполяции.

Vector3.SmoothDamp(transform.position, targetPosition, velocity, time); 

Альтернативы:

Vector3.MoveTowards(start.position, end.position, time); 
Vector3.Lerp(start.position, end.position, time); 
+0

Является ли это из-за движения? Или это потому, что скорость передачи данных Bluetooth асинхронна с 60fps Unity? Поэтому флаг проверяется в 'update()', поэтому он проверяется только 60 раз в секунду. Что делать, если Bluetooth отправляет больше данных в секунду? Гораздо правильнее? Если я поместил код движения в поток, он даст мне ошибку основного потока. – dil33pm

+0

Я не очень-то знаком с последовательными портами по единству, но вы, вероятно, правы. Какова скорость передачи данных на последовательном порту? Вы пытались его увеличить? –

+0

Это было 9600, я тоже пробовал с 19200. Только если я мог бы назвать Unity API из другого потока ... Только если бы был бесплатный плагин :( – dil33pm

Смежные вопросы