mirror of
https://github.com/overte-org/overte.git
synced 2025-08-09 18:42:58 +02:00
Moving conditionals and endpoints out of UserInputMapper
Conflicts: libraries/controllers/src/controllers/UserInputMapper.cpp
This commit is contained in:
parent
2c2273df0b
commit
0fdd32709f
37 changed files with 766 additions and 332 deletions
|
@ -24,9 +24,22 @@
|
||||||
|
|
||||||
#include "Logging.h"
|
#include "Logging.h"
|
||||||
|
|
||||||
#include "Endpoint.h"
|
#include "impl/conditionals/AndConditional.h"
|
||||||
#include "Route.h"
|
#include "impl/conditionals/EndpointConditional.h"
|
||||||
#include "Mapping.h"
|
#include "impl/conditionals/ScriptConditional.h"
|
||||||
|
|
||||||
|
#include "impl/endpoints/ActionEndpoint.h"
|
||||||
|
#include "impl/endpoints/AnyEndpoint.h"
|
||||||
|
#include "impl/endpoints/ArrayEndpoint.h"
|
||||||
|
#include "impl/endpoints/CompositeEndpoint.h"
|
||||||
|
#include "impl/endpoints/InputEndpoint.h"
|
||||||
|
#include "impl/endpoints/JSEndpoint.h"
|
||||||
|
#include "impl/endpoints/ScriptEndpoint.h"
|
||||||
|
#include "impl/endpoints/StandardEndpoint.h"
|
||||||
|
|
||||||
|
#include "impl/Route.h"
|
||||||
|
#include "impl/Mapping.h"
|
||||||
|
|
||||||
|
|
||||||
namespace controller {
|
namespace controller {
|
||||||
const uint16_t UserInputMapper::ACTIONS_DEVICE = Input::INVALID_DEVICE - 0xFF;
|
const uint16_t UserInputMapper::ACTIONS_DEVICE = Input::INVALID_DEVICE - 0xFF;
|
||||||
|
@ -42,300 +55,6 @@ controller::UserInputMapper::UserInputMapper() {
|
||||||
|
|
||||||
namespace controller {
|
namespace controller {
|
||||||
|
|
||||||
class ScriptEndpoint : public Endpoint {
|
|
||||||
Q_OBJECT;
|
|
||||||
public:
|
|
||||||
ScriptEndpoint(const QScriptValue& callable)
|
|
||||||
: Endpoint(Input::INVALID_INPUT), _callable(callable) {
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual float value();
|
|
||||||
virtual void apply(float newValue, float oldValue, const Pointer& source);
|
|
||||||
|
|
||||||
protected:
|
|
||||||
Q_INVOKABLE void updateValue();
|
|
||||||
Q_INVOKABLE virtual void internalApply(float newValue, float oldValue, int sourceID);
|
|
||||||
private:
|
|
||||||
QScriptValue _callable;
|
|
||||||
float _lastValue = 0.0f;
|
|
||||||
};
|
|
||||||
|
|
||||||
class StandardEndpoint : public VirtualEndpoint {
|
|
||||||
public:
|
|
||||||
StandardEndpoint(const Input& input) : VirtualEndpoint(input) {}
|
|
||||||
virtual bool writeable() const override { return !_written; }
|
|
||||||
virtual bool readable() const override { return !_read; }
|
|
||||||
virtual void reset() override {
|
|
||||||
apply(0.0f, 0.0f, Endpoint::Pointer());
|
|
||||||
apply(Pose(), Pose(), Endpoint::Pointer());
|
|
||||||
_written = _read = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual float value() override {
|
|
||||||
_read = true;
|
|
||||||
return VirtualEndpoint::value();
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void apply(float newValue, float oldValue, const Pointer& source) override {
|
|
||||||
// For standard endpoints, the first NON-ZERO write counts.
|
|
||||||
if (newValue != 0.0) {
|
|
||||||
_written = true;
|
|
||||||
}
|
|
||||||
VirtualEndpoint::apply(newValue, oldValue, source);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual Pose pose() override {
|
|
||||||
_read = true;
|
|
||||||
return VirtualEndpoint::pose();
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void apply(const Pose& newValue, const Pose& oldValue, const Pointer& source) override {
|
|
||||||
if (newValue != Pose()) {
|
|
||||||
_written = true;
|
|
||||||
}
|
|
||||||
VirtualEndpoint::apply(newValue, oldValue, source);
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
bool _written { false };
|
|
||||||
bool _read { false };
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
class JSEndpoint : public Endpoint {
|
|
||||||
public:
|
|
||||||
JSEndpoint(const QJSValue& callable)
|
|
||||||
: Endpoint(Input::INVALID_INPUT), _callable(callable) {
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual float value() {
|
|
||||||
float result = (float)_callable.call().toNumber();;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void apply(float newValue, float oldValue, const Pointer& source) {
|
|
||||||
_callable.call(QJSValueList({ QJSValue(newValue) }));
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
QJSValue _callable;
|
|
||||||
};
|
|
||||||
|
|
||||||
float ScriptEndpoint::value() {
|
|
||||||
updateValue();
|
|
||||||
return _lastValue;
|
|
||||||
}
|
|
||||||
|
|
||||||
void ScriptEndpoint::updateValue() {
|
|
||||||
if (QThread::currentThread() != thread()) {
|
|
||||||
QMetaObject::invokeMethod(this, "updateValue", Qt::QueuedConnection);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
_lastValue = (float)_callable.call().toNumber();
|
|
||||||
}
|
|
||||||
|
|
||||||
void ScriptEndpoint::apply(float newValue, float oldValue, const Pointer& source) {
|
|
||||||
internalApply(newValue, oldValue, source->getInput().getID());
|
|
||||||
}
|
|
||||||
|
|
||||||
void ScriptEndpoint::internalApply(float newValue, float oldValue, int sourceID) {
|
|
||||||
if (QThread::currentThread() != thread()) {
|
|
||||||
QMetaObject::invokeMethod(this, "internalApply", Qt::QueuedConnection,
|
|
||||||
Q_ARG(float, newValue),
|
|
||||||
Q_ARG(float, oldValue),
|
|
||||||
Q_ARG(int, sourceID));
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
_callable.call(QScriptValue(),
|
|
||||||
QScriptValueList({ QScriptValue(newValue), QScriptValue(oldValue), QScriptValue(sourceID) }));
|
|
||||||
}
|
|
||||||
|
|
||||||
static const Input INVALID_STANDARD_INPUT = Input(UserInputMapper::STANDARD_DEVICE, Input::INVALID_CHANNEL, ChannelType::INVALID);
|
|
||||||
|
|
||||||
class CompositeEndpoint : public Endpoint, Endpoint::Pair {
|
|
||||||
public:
|
|
||||||
CompositeEndpoint(Endpoint::Pointer first, Endpoint::Pointer second)
|
|
||||||
: Endpoint(Input::INVALID_INPUT), Pair(first, second) {
|
|
||||||
if (first->getInput().device == UserInputMapper::STANDARD_DEVICE &&
|
|
||||||
second->getInput().device == UserInputMapper::STANDARD_DEVICE) {
|
|
||||||
this->_input = INVALID_STANDARD_INPUT;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual float value() {
|
|
||||||
float result = first->value() * -1.0f + second->value();
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void apply(float newValue, float oldValue, const Pointer& source) {
|
|
||||||
// Composites are read only
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
class ArrayEndpoint : public Endpoint {
|
|
||||||
friend class UserInputMapper;
|
|
||||||
public:
|
|
||||||
using Pointer = std::shared_ptr<ArrayEndpoint>;
|
|
||||||
ArrayEndpoint() : Endpoint(Input::INVALID_INPUT) { }
|
|
||||||
|
|
||||||
virtual float value() override {
|
|
||||||
return 0.0;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void apply(float newValue, float oldValue, const Endpoint::Pointer& source) override {
|
|
||||||
for (auto& child : _children) {
|
|
||||||
if (child->writeable()) {
|
|
||||||
child->apply(newValue, oldValue, source);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual bool readable() const override { return false; }
|
|
||||||
|
|
||||||
private:
|
|
||||||
Endpoint::List _children;
|
|
||||||
};
|
|
||||||
|
|
||||||
class AnyEndpoint : public Endpoint {
|
|
||||||
friend class UserInputMapper;
|
|
||||||
public:
|
|
||||||
using Pointer = std::shared_ptr<AnyEndpoint>;
|
|
||||||
AnyEndpoint(Endpoint::List children) : Endpoint(Input::INVALID_INPUT), _children(children) {
|
|
||||||
bool standard = true;
|
|
||||||
// Ensure if we're building a composite of standard devices the composite itself
|
|
||||||
// is treated as a standard device for rule processing order
|
|
||||||
for (auto endpoint : children) {
|
|
||||||
if (endpoint->getInput().device != UserInputMapper::STANDARD_DEVICE) {
|
|
||||||
standard = false;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (standard) {
|
|
||||||
this->_input = INVALID_STANDARD_INPUT;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual float value() override {
|
|
||||||
float result = 0.0f;
|
|
||||||
for (auto& child : _children) {
|
|
||||||
float childResult = child->value();
|
|
||||||
if (childResult != 0.0f && result == 0.0f) {
|
|
||||||
result = childResult;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void apply(float newValue, float oldValue, const Endpoint::Pointer& source) override {
|
|
||||||
qFatal("AnyEndpoint is read only");
|
|
||||||
}
|
|
||||||
|
|
||||||
// AnyEndpoint is used for reading, so return false if any child returns false (has been written to)
|
|
||||||
virtual bool writeable() const override {
|
|
||||||
for (auto& child : _children) {
|
|
||||||
if (!child->writeable()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual bool readable() const override {
|
|
||||||
for (auto& child : _children) {
|
|
||||||
if (!child->readable()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
Endpoint::List _children;
|
|
||||||
};
|
|
||||||
|
|
||||||
class InputEndpoint : public Endpoint {
|
|
||||||
public:
|
|
||||||
InputEndpoint(const Input& id = Input::INVALID_INPUT)
|
|
||||||
: Endpoint(id) {
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual float value() override {
|
|
||||||
_read = true;
|
|
||||||
if (isPose()) {
|
|
||||||
return pose().valid ? 1.0f : 0.0f;
|
|
||||||
}
|
|
||||||
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
|
||||||
auto deviceProxy = userInputMapper->getDeviceProxy(_input);
|
|
||||||
if (!deviceProxy) {
|
|
||||||
return 0.0f;
|
|
||||||
}
|
|
||||||
return deviceProxy->getValue(_input, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
// FIXME need support for writing back to vibration / force feedback effects
|
|
||||||
virtual void apply(float newValue, float oldValue, const Pointer& source) override {}
|
|
||||||
|
|
||||||
virtual Pose pose() override {
|
|
||||||
_read = true;
|
|
||||||
if (!isPose()) {
|
|
||||||
return Pose();
|
|
||||||
}
|
|
||||||
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
|
||||||
auto deviceProxy = userInputMapper->getDeviceProxy(_input);
|
|
||||||
if (!deviceProxy) {
|
|
||||||
return Pose();
|
|
||||||
}
|
|
||||||
return deviceProxy->getPose(_input, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void apply(const Pose& newValue, const Pose& oldValue, const Pointer& source) override { }
|
|
||||||
|
|
||||||
virtual bool writeable() const { return false; }
|
|
||||||
virtual bool readable() const { return !_read; }
|
|
||||||
virtual void reset() { _read = false; }
|
|
||||||
|
|
||||||
private:
|
|
||||||
bool _read { false };
|
|
||||||
};
|
|
||||||
|
|
||||||
class ActionEndpoint : public Endpoint {
|
|
||||||
public:
|
|
||||||
ActionEndpoint(const Input& id = Input::INVALID_INPUT)
|
|
||||||
: Endpoint(id) {
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual float value() override { return _currentValue; }
|
|
||||||
virtual void apply(float newValue, float oldValue, const Pointer& source) override {
|
|
||||||
_currentValue += newValue;
|
|
||||||
if (_input != Input::INVALID_INPUT) {
|
|
||||||
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
|
||||||
userInputMapper->deltaActionState(Action(_input.getChannel()), newValue);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual Pose pose() override { return _currentPose; }
|
|
||||||
virtual void apply(const Pose& newValue, const Pose& oldValue, const Pointer& source) override {
|
|
||||||
_currentPose = newValue;
|
|
||||||
if (!_currentPose.isValid()) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (_input != Input::INVALID_INPUT) {
|
|
||||||
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
|
||||||
userInputMapper->setActionState(Action(_input.getChannel()), _currentPose);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void reset() override {
|
|
||||||
_currentValue = 0.0f;
|
|
||||||
_currentPose = Pose();
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
float _currentValue{ 0.0f };
|
|
||||||
Pose _currentPose{};
|
|
||||||
};
|
|
||||||
|
|
||||||
UserInputMapper::~UserInputMapper() {
|
UserInputMapper::~UserInputMapper() {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1019,33 +738,6 @@ Endpoint::Pointer UserInputMapper::parseEndpoint(const QJsonValue& value) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
class AndConditional : public Conditional {
|
|
||||||
public:
|
|
||||||
using Pointer = std::shared_ptr<AndConditional>;
|
|
||||||
|
|
||||||
AndConditional(Conditional::List children) : _children(children) { }
|
|
||||||
|
|
||||||
virtual bool satisfied() override {
|
|
||||||
for (auto& conditional : _children) {
|
|
||||||
if (!conditional->satisfied()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
Conditional::List _children;
|
|
||||||
};
|
|
||||||
|
|
||||||
class EndpointConditional : public Conditional {
|
|
||||||
public:
|
|
||||||
EndpointConditional(Endpoint::Pointer endpoint) : _endpoint(endpoint) {}
|
|
||||||
virtual bool satisfied() override { return _endpoint && _endpoint->value() != 0.0; }
|
|
||||||
private:
|
|
||||||
Endpoint::Pointer _endpoint;
|
|
||||||
};
|
|
||||||
|
|
||||||
Conditional::Pointer UserInputMapper::parseConditional(const QJsonValue& value) {
|
Conditional::Pointer UserInputMapper::parseConditional(const QJsonValue& value) {
|
||||||
if (value.isArray()) {
|
if (value.isArray()) {
|
||||||
// Support "when" : [ "GamePad.RB", "GamePad.LB" ]
|
// Support "when" : [ "GamePad.RB", "GamePad.LB" ]
|
||||||
|
@ -1290,4 +982,3 @@ void UserInputMapper::disableMapping(const Mapping::Pointer& mapping) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#include "UserInputMapper.moc"
|
|
||||||
|
|
|
@ -16,8 +16,8 @@
|
||||||
|
|
||||||
#include <QtCore/QObject>
|
#include <QtCore/QObject>
|
||||||
|
|
||||||
#include "Input.h"
|
#include "../Input.h"
|
||||||
#include "Pose.h"
|
#include "../Pose.h"
|
||||||
|
|
||||||
class QScriptValue;
|
class QScriptValue;
|
||||||
|
|
|
@ -12,8 +12,8 @@
|
||||||
#include <QtCore/QObject>
|
#include <QtCore/QObject>
|
||||||
#include <QtCore/QString>
|
#include <QtCore/QString>
|
||||||
|
|
||||||
#include "../Mapping.h"
|
#include "Mapping.h"
|
||||||
#include "../Endpoint.h"
|
#include "Endpoint.h"
|
||||||
|
|
||||||
class QJSValue;
|
class QJSValue;
|
||||||
class QScriptValue;
|
class QScriptValue;
|
||||||
|
|
|
@ -11,10 +11,12 @@
|
||||||
|
|
||||||
#include <QtCore/QObject>
|
#include <QtCore/QObject>
|
||||||
|
|
||||||
#include "../Filter.h"
|
#include "Filter.h"
|
||||||
#include "../Route.h"
|
#include "Route.h"
|
||||||
#include "../Mapping.h"
|
#include "Mapping.h"
|
||||||
|
|
||||||
#include "../UserInputMapper.h"
|
#include "../UserInputMapper.h"
|
||||||
|
|
||||||
class QJSValue;
|
class QJSValue;
|
||||||
class QScriptValue;
|
class QScriptValue;
|
||||||
class QJsonValue;
|
class QJsonValue;
|
||||||
|
|
|
@ -0,0 +1,20 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "AndConditional.h"
|
||||||
|
|
||||||
|
using namespace controller;
|
||||||
|
|
||||||
|
bool AndConditional::satisfied() {
|
||||||
|
for (auto& conditional : _children) {
|
||||||
|
if (!conditional->satisfied()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
|
@ -0,0 +1,32 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/20
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_AndConditional_h
|
||||||
|
#define hifi_Controllers_AndConditional_h
|
||||||
|
|
||||||
|
#include "../Conditional.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class AndConditional : public Conditional {
|
||||||
|
public:
|
||||||
|
using Pointer = std::shared_ptr<AndConditional>;
|
||||||
|
|
||||||
|
AndConditional(Conditional::List children) : _children(children) { }
|
||||||
|
|
||||||
|
virtual bool satisfied() override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
Conditional::List _children;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,9 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "EndpointConditional.h"
|
|
@ -0,0 +1,27 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/20
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_EndpointConditional_h
|
||||||
|
#define hifi_Controllers_EndpointConditional_h
|
||||||
|
|
||||||
|
#include "../Conditional.h"
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class EndpointConditional : public Conditional {
|
||||||
|
public:
|
||||||
|
EndpointConditional(Endpoint::Pointer endpoint) : _endpoint(endpoint) {}
|
||||||
|
virtual bool satisfied() override { return _endpoint && _endpoint->value() != 0.0; }
|
||||||
|
private:
|
||||||
|
Endpoint::Pointer _endpoint;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
#endif
|
|
@ -0,0 +1,9 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "NotConditional.h"
|
|
@ -0,0 +1,16 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/20
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_NotConditional_h
|
||||||
|
#define hifi_Controllers_NotConditional_h
|
||||||
|
|
||||||
|
#include "../Conditional.h"
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,27 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "ScriptConditional.h"
|
||||||
|
|
||||||
|
#include <QtCore/QThread>
|
||||||
|
|
||||||
|
using namespace controller;
|
||||||
|
|
||||||
|
bool ScriptConditional::satisfied() {
|
||||||
|
updateValue();
|
||||||
|
return _lastValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScriptConditional::updateValue() {
|
||||||
|
if (QThread::currentThread() != thread()) {
|
||||||
|
QMetaObject::invokeMethod(this, "updateValue", Qt::QueuedConnection);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
_lastValue = _callable.call().toBool();
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/20
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_ScriptConditional_h
|
||||||
|
#define hifi_Controllers_ScriptConditional_h
|
||||||
|
|
||||||
|
#include <QtCore/QObject>
|
||||||
|
|
||||||
|
#include <QtScript/QScriptValue>
|
||||||
|
|
||||||
|
#include "../Conditional.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class ScriptConditional : public QObject, public Conditional {
|
||||||
|
Q_OBJECT;
|
||||||
|
public:
|
||||||
|
ScriptConditional(const QScriptValue& callable) : _callable(callable) { }
|
||||||
|
virtual bool satisfied() override;
|
||||||
|
protected:
|
||||||
|
Q_INVOKABLE void updateValue();
|
||||||
|
private:
|
||||||
|
QScriptValue _callable;
|
||||||
|
bool _lastValue { false };
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
#endif
|
|
@ -0,0 +1,40 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "ActionEndpoint.h"
|
||||||
|
|
||||||
|
#include <DependencyManager.h>
|
||||||
|
|
||||||
|
#include "../../UserInputMapper.h"
|
||||||
|
|
||||||
|
using namespace controller;
|
||||||
|
|
||||||
|
void ActionEndpoint::apply(float newValue, float oldValue, const Pointer& source) {
|
||||||
|
_currentValue += newValue;
|
||||||
|
if (_input != Input::INVALID_INPUT) {
|
||||||
|
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
||||||
|
userInputMapper->deltaActionState(Action(_input.getChannel()), newValue);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void ActionEndpoint::apply(const Pose& newValue, const Pose& oldValue, const Pointer& source) {
|
||||||
|
_currentPose = newValue;
|
||||||
|
if (!_currentPose.isValid()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (_input != Input::INVALID_INPUT) {
|
||||||
|
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
||||||
|
userInputMapper->setActionState(Action(_input.getChannel()), _currentPose);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void ActionEndpoint::reset() {
|
||||||
|
_currentValue = 0.0f;
|
||||||
|
_currentPose = Pose();
|
||||||
|
}
|
||||||
|
|
|
@ -0,0 +1,41 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_ActionEndpoint_h
|
||||||
|
#define hifi_Controllers_ActionEndpoint_h
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
#include "../../Actions.h"
|
||||||
|
#include <DependencyManager.h>
|
||||||
|
|
||||||
|
#include "../../UserInputMapper.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class ActionEndpoint : public Endpoint {
|
||||||
|
public:
|
||||||
|
ActionEndpoint(const Input& id = Input::INVALID_INPUT) : Endpoint(id) { }
|
||||||
|
|
||||||
|
virtual float value() override { return _currentValue; }
|
||||||
|
virtual void apply(float newValue, float oldValue, const Pointer& source) override;
|
||||||
|
|
||||||
|
virtual Pose pose() override { return _currentPose; }
|
||||||
|
virtual void apply(const Pose& newValue, const Pose& oldValue, const Pointer& source) override;
|
||||||
|
|
||||||
|
virtual void reset() override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
float _currentValue{ 0.0f };
|
||||||
|
Pose _currentPose{};
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,63 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "AnyEndpoint.h"
|
||||||
|
|
||||||
|
#include "../../UserInputMapper.h"
|
||||||
|
|
||||||
|
using namespace controller;
|
||||||
|
|
||||||
|
AnyEndpoint::AnyEndpoint(Endpoint::List children) : Endpoint(Input::INVALID_INPUT), _children(children) {
|
||||||
|
bool standard = true;
|
||||||
|
// Ensure if we're building a composite of standard devices the composite itself
|
||||||
|
// is treated as a standard device for rule processing order
|
||||||
|
for (auto endpoint : children) {
|
||||||
|
if (endpoint->getInput().device != UserInputMapper::STANDARD_DEVICE) {
|
||||||
|
standard = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (standard) {
|
||||||
|
this->_input.device = UserInputMapper::STANDARD_DEVICE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
float AnyEndpoint::value() {
|
||||||
|
float result = 0;
|
||||||
|
for (auto& child : _children) {
|
||||||
|
float childResult = child->value();
|
||||||
|
if (childResult != 0.0f) {
|
||||||
|
result = childResult;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
void AnyEndpoint::apply(float newValue, float oldValue, const Endpoint::Pointer& source) {
|
||||||
|
qFatal("AnyEndpoint is read only");
|
||||||
|
}
|
||||||
|
|
||||||
|
// AnyEndpoint is used for reading, so return false if any child returns false (has been written to)
|
||||||
|
bool AnyEndpoint::writeable() const {
|
||||||
|
for (auto& child : _children) {
|
||||||
|
if (!child->writeable()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool AnyEndpoint::readable() const {
|
||||||
|
for (auto& child : _children) {
|
||||||
|
if (!child->readable()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
|
@ -0,0 +1,32 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_AnyEndpoint_h
|
||||||
|
#define hifi_Controllers_AnyEndpoint_h
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class AnyEndpoint : public Endpoint {
|
||||||
|
friend class UserInputMapper;
|
||||||
|
public:
|
||||||
|
AnyEndpoint(Endpoint::List children);
|
||||||
|
virtual float value() override;
|
||||||
|
virtual void apply(float newValue, float oldValue, const Endpoint::Pointer& source) override;
|
||||||
|
virtual bool writeable() const override;
|
||||||
|
virtual bool readable() const override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
Endpoint::List _children;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,9 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "ArrayEndpoint.h"
|
|
@ -0,0 +1,43 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_ArrayEndpoint_h
|
||||||
|
#define hifi_Controllers_ArrayEndpoint_h
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class ArrayEndpoint : public Endpoint {
|
||||||
|
friend class UserInputMapper;
|
||||||
|
public:
|
||||||
|
using Pointer = std::shared_ptr<ArrayEndpoint>;
|
||||||
|
ArrayEndpoint() : Endpoint(Input::INVALID_INPUT) { }
|
||||||
|
|
||||||
|
virtual float value() override {
|
||||||
|
return 0.0;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void apply(float newValue, float oldValue, const Endpoint::Pointer& source) override {
|
||||||
|
for (auto& child : _children) {
|
||||||
|
if (child->writeable()) {
|
||||||
|
child->apply(newValue, oldValue, source);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual bool readable() const override { return false; }
|
||||||
|
|
||||||
|
private:
|
||||||
|
Endpoint::List _children;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,32 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "CompositeEndpoint.h"
|
||||||
|
|
||||||
|
#include "../../UserInputMapper.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
CompositeEndpoint::CompositeEndpoint(Endpoint::Pointer first, Endpoint::Pointer second)
|
||||||
|
: Endpoint(Input::INVALID_INPUT), Pair(first, second) {
|
||||||
|
if (first->getInput().device == UserInputMapper::STANDARD_DEVICE &&
|
||||||
|
second->getInput().device == UserInputMapper::STANDARD_DEVICE) {
|
||||||
|
this->_input.device = UserInputMapper::STANDARD_DEVICE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
float CompositeEndpoint::value() {
|
||||||
|
float result = first->value() * -1.0f + second->value();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
void CompositeEndpoint::apply(float newValue, float oldValue, const Pointer& source) {
|
||||||
|
// Composites are read only
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -0,0 +1,26 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_CompositeEndpoint_h
|
||||||
|
#define hifi_Controllers_CompositeEndpoint_h
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
class CompositeEndpoint : public Endpoint, Endpoint::Pair {
|
||||||
|
public:
|
||||||
|
CompositeEndpoint(Endpoint::Pointer first, Endpoint::Pointer second);
|
||||||
|
|
||||||
|
virtual float value() override;
|
||||||
|
virtual void apply(float newValue, float oldValue, const Pointer& source) override;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,41 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "InputEndpoint.h"
|
||||||
|
|
||||||
|
#include <DependencyManager.h>
|
||||||
|
|
||||||
|
#include "../../UserInputMapper.h"
|
||||||
|
|
||||||
|
using namespace controller;
|
||||||
|
float InputEndpoint::value(){
|
||||||
|
_read = true;
|
||||||
|
if (isPose()) {
|
||||||
|
return pose().valid ? 1.0f : 0.0f;
|
||||||
|
}
|
||||||
|
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
||||||
|
auto deviceProxy = userInputMapper->getDeviceProxy(_input);
|
||||||
|
if (!deviceProxy) {
|
||||||
|
return 0.0f;
|
||||||
|
}
|
||||||
|
return deviceProxy->getValue(_input, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
Pose InputEndpoint::pose() {
|
||||||
|
_read = true;
|
||||||
|
if (!isPose()) {
|
||||||
|
return Pose();
|
||||||
|
}
|
||||||
|
auto userInputMapper = DependencyManager::get<UserInputMapper>();
|
||||||
|
auto deviceProxy = userInputMapper->getDeviceProxy(_input);
|
||||||
|
if (!deviceProxy) {
|
||||||
|
return Pose();
|
||||||
|
}
|
||||||
|
return deviceProxy->getPose(_input, 0);
|
||||||
|
}
|
||||||
|
|
|
@ -0,0 +1,39 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_InputEndpoint_h
|
||||||
|
#define hifi_Controllers_InputEndpoint_h
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class InputEndpoint : public Endpoint {
|
||||||
|
public:
|
||||||
|
InputEndpoint(const Input& id = Input::INVALID_INPUT)
|
||||||
|
: Endpoint(id) {
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual float value() override;
|
||||||
|
// FIXME need support for writing back to vibration / force feedback effects
|
||||||
|
virtual void apply(float newValue, float oldValue, const Pointer& source) override {}
|
||||||
|
virtual Pose pose() override;
|
||||||
|
virtual void apply(const Pose& newValue, const Pose& oldValue, const Pointer& source) override { }
|
||||||
|
|
||||||
|
virtual bool writeable() const { return false; }
|
||||||
|
virtual bool readable() const { return !_read; }
|
||||||
|
virtual void reset() { _read = false; }
|
||||||
|
|
||||||
|
private:
|
||||||
|
bool _read { false };
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,9 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "JSEndpoint.h"
|
|
@ -0,0 +1,41 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_JSEndpoint_h
|
||||||
|
#define hifi_Controllers_JSEndpoint_h
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
#include <QtQml/QJSValue>
|
||||||
|
#include <QtQml/QJSValueList>
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class JSEndpoint : public Endpoint {
|
||||||
|
public:
|
||||||
|
JSEndpoint(const QJSValue& callable)
|
||||||
|
: Endpoint(Input::INVALID_INPUT), _callable(callable) {
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual float value() {
|
||||||
|
float result = (float)_callable.call().toNumber();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void apply(float newValue, float oldValue, const Pointer& source) {
|
||||||
|
_callable.call(QJSValueList({ QJSValue(newValue) }));
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
QJSValue _callable;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,43 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "ScriptEndpoint.h"
|
||||||
|
|
||||||
|
#include <QtCore/QThread>
|
||||||
|
|
||||||
|
using namespace controller;
|
||||||
|
|
||||||
|
float ScriptEndpoint::value() {
|
||||||
|
updateValue();
|
||||||
|
return _lastValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScriptEndpoint::updateValue() {
|
||||||
|
if (QThread::currentThread() != thread()) {
|
||||||
|
QMetaObject::invokeMethod(this, "updateValue", Qt::QueuedConnection);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
_lastValue = (float)_callable.call().toNumber();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScriptEndpoint::apply(float newValue, float oldValue, const Pointer& source) {
|
||||||
|
internalApply(newValue, oldValue, source->getInput().getID());
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScriptEndpoint::internalApply(float newValue, float oldValue, int sourceID) {
|
||||||
|
if (QThread::currentThread() != thread()) {
|
||||||
|
QMetaObject::invokeMethod(this, "internalApply", Qt::QueuedConnection,
|
||||||
|
Q_ARG(float, newValue),
|
||||||
|
Q_ARG(float, oldValue),
|
||||||
|
Q_ARG(int, sourceID));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
_callable.call(QScriptValue(),
|
||||||
|
QScriptValueList({ QScriptValue(newValue), QScriptValue(oldValue), QScriptValue(sourceID) }));
|
||||||
|
}
|
|
@ -0,0 +1,39 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_ScriptEndpoint_h
|
||||||
|
#define hifi_Controllers_ScriptEndpoint_h
|
||||||
|
|
||||||
|
#include <QtScript/QScriptValue>
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class ScriptEndpoint : public Endpoint {
|
||||||
|
Q_OBJECT;
|
||||||
|
public:
|
||||||
|
ScriptEndpoint(const QScriptValue& callable)
|
||||||
|
: Endpoint(Input::INVALID_INPUT), _callable(callable) {
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual float value();
|
||||||
|
virtual void apply(float newValue, float oldValue, const Pointer& source);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
Q_INVOKABLE void updateValue();
|
||||||
|
Q_INVOKABLE virtual void internalApply(float newValue, float oldValue, int sourceID);
|
||||||
|
private:
|
||||||
|
QScriptValue _callable;
|
||||||
|
float _lastValue = 0.0f;
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -0,0 +1,9 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "StandardEndpoint.h"
|
|
@ -0,0 +1,60 @@
|
||||||
|
//
|
||||||
|
// Created by Bradley Austin Davis 2015/10/23
|
||||||
|
// Copyright 2015 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
#ifndef hifi_Controllers_StandardEndpoint_h
|
||||||
|
#define hifi_Controllers_StandardEndpoint_h
|
||||||
|
|
||||||
|
#include "../Endpoint.h"
|
||||||
|
|
||||||
|
namespace controller {
|
||||||
|
|
||||||
|
class StandardEndpoint : public VirtualEndpoint {
|
||||||
|
public:
|
||||||
|
StandardEndpoint(const Input& input) : VirtualEndpoint(input) {}
|
||||||
|
virtual bool writeable() const override { return !_written; }
|
||||||
|
virtual bool readable() const override { return !_read; }
|
||||||
|
virtual void reset() override {
|
||||||
|
apply(0.0f, 0.0f, Endpoint::Pointer());
|
||||||
|
apply(Pose(), Pose(), Endpoint::Pointer());
|
||||||
|
_written = _read = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual float value() override {
|
||||||
|
_read = true;
|
||||||
|
return VirtualEndpoint::value();
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void apply(float newValue, float oldValue, const Pointer& source) override {
|
||||||
|
// For standard endpoints, the first NON-ZERO write counts.
|
||||||
|
if (newValue != 0.0) {
|
||||||
|
_written = true;
|
||||||
|
}
|
||||||
|
VirtualEndpoint::apply(newValue, oldValue, source);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual Pose pose() override {
|
||||||
|
_read = true;
|
||||||
|
return VirtualEndpoint::pose();
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void apply(const Pose& newValue, const Pose& oldValue, const Pointer& source) override {
|
||||||
|
if (newValue != Pose()) {
|
||||||
|
_written = true;
|
||||||
|
}
|
||||||
|
VirtualEndpoint::apply(newValue, oldValue, source);
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
bool _written { false };
|
||||||
|
bool _read { false };
|
||||||
|
};
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
Loading…
Reference in a new issue