Browse Source

Add raw strength value for internal use

Aaron Franke 4 years ago
parent
commit
195d58be0f

+ 12 - 1
core/input/input.cpp

@@ -326,6 +326,15 @@ float Input::get_action_strength(const StringName &p_action) const {
 	return E->get().strength;
 }
 
+float Input::get_action_raw_strength(const StringName &p_action) const {
+	const Map<StringName, Action>::Element *E = action_state.find(p_action);
+	if (!E) {
+		return 0.0f;
+	}
+
+	return E->get().raw_strength;
+}
+
 float Input::get_joy_axis(int p_device, int p_axis) const {
 	_THREAD_SAFE_METHOD_
 	int c = _combine_device(p_axis, p_device);
@@ -603,10 +612,12 @@ void Input::_parse_input_event_impl(const Ref<InputEvent> &p_event, bool p_is_em
 				action.physics_frame = Engine::get_singleton()->get_physics_frames();
 				action.idle_frame = Engine::get_singleton()->get_idle_frames();
 				action.pressed = p_event->is_action_pressed(E->key());
-				action.strength = 0.f;
+				action.strength = 0.0f;
+				action.raw_strength = 0.0f;
 				action_state[E->key()] = action;
 			}
 			action_state[E->key()].strength = p_event->get_action_strength(E->key());
+			action_state[E->key()].raw_strength = p_event->get_action_raw_strength(E->key());
 		}
 	}
 

+ 2 - 0
core/input/input.h

@@ -117,6 +117,7 @@ private:
 		uint64_t idle_frame;
 		bool pressed;
 		float strength;
+		float raw_strength;
 	};
 
 	Map<StringName, Action> action_state;
@@ -266,6 +267,7 @@ public:
 	bool is_action_just_pressed(const StringName &p_action) const;
 	bool is_action_just_released(const StringName &p_action) const;
 	float get_action_strength(const StringName &p_action) const;
+	float get_action_raw_strength(const StringName &p_action) const;
 
 	float get_joy_axis(int p_device, int p_axis) const;
 	String get_joy_name(int p_idx);

+ 43 - 14
core/input/input_event.cpp

@@ -61,12 +61,17 @@ bool InputEvent::is_action_released(const StringName &p_action) const {
 }
 
 float InputEvent::get_action_strength(const StringName &p_action) const {
-	bool pressed;
 	float strength;
-	bool valid = InputMap::get_singleton()->event_get_action_status(Ref<InputEvent>((InputEvent *)this), p_action, &pressed, &strength);
+	bool valid = InputMap::get_singleton()->event_get_action_status(Ref<InputEvent>((InputEvent *)this), p_action, nullptr, &strength);
 	return valid ? strength : 0.0f;
 }
 
+float InputEvent::get_action_raw_strength(const StringName &p_action) const {
+	float raw_strength;
+	bool valid = InputMap::get_singleton()->event_get_action_status(Ref<InputEvent>((InputEvent *)this), p_action, nullptr, nullptr, &raw_strength);
+	return valid ? raw_strength : 0.0f;
+}
+
 bool InputEvent::is_pressed() const {
 	return false;
 }
@@ -83,7 +88,7 @@ String InputEvent::as_text() const {
 	return String();
 }
 
-bool InputEvent::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const {
+bool InputEvent::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const {
 	return false;
 }
 
@@ -307,7 +312,7 @@ String InputEventKey::as_text() const {
 	return kc;
 }
 
-bool InputEventKey::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const {
+bool InputEventKey::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const {
 	Ref<InputEventKey> key = p_event;
 	if (key.is_null()) {
 		return false;
@@ -329,8 +334,12 @@ bool InputEventKey::action_match(const Ref<InputEvent> &p_event, bool *p_pressed
 		if (p_pressed != nullptr) {
 			*p_pressed = key->is_pressed();
 		}
+		float strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
 		if (p_strength != nullptr) {
-			*p_strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
+			*p_strength = strength;
+		}
+		if (p_raw_strength != nullptr) {
+			*p_raw_strength = strength;
 		}
 	}
 	return match;
@@ -470,7 +479,7 @@ Ref<InputEvent> InputEventMouseButton::xformed_by(const Transform2D &p_xform, co
 	return mb;
 }
 
-bool InputEventMouseButton::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const {
+bool InputEventMouseButton::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const {
 	Ref<InputEventMouseButton> mb = p_event;
 	if (mb.is_null()) {
 		return false;
@@ -481,8 +490,12 @@ bool InputEventMouseButton::action_match(const Ref<InputEvent> &p_event, bool *p
 		if (p_pressed != nullptr) {
 			*p_pressed = mb->is_pressed();
 		}
+		float strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
 		if (p_strength != nullptr) {
-			*p_strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
+			*p_strength = strength;
+		}
+		if (p_raw_strength != nullptr) {
+			*p_raw_strength = strength;
 		}
 	}
 
@@ -713,7 +726,7 @@ bool InputEventJoypadMotion::is_pressed() const {
 	return Math::abs(axis_value) >= 0.5f;
 }
 
-bool InputEventJoypadMotion::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const {
+bool InputEventJoypadMotion::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const {
 	Ref<InputEventJoypadMotion> jm = p_event;
 	if (jm.is_null()) {
 		return false;
@@ -721,8 +734,9 @@ bool InputEventJoypadMotion::action_match(const Ref<InputEvent> &p_event, bool *
 
 	bool match = (axis == jm->axis); // Matches even if not in the same direction, but returns a "not pressed" event.
 	if (match) {
+		float jm_abs_axis_value = Math::abs(jm->get_axis_value());
 		bool same_direction = (((axis_value < 0) == (jm->axis_value < 0)) || jm->axis_value == 0);
-		bool pressed = same_direction ? Math::abs(jm->get_axis_value()) >= p_deadzone : false;
+		bool pressed = same_direction && jm_abs_axis_value >= p_deadzone;
 		if (p_pressed != nullptr) {
 			*p_pressed = pressed;
 		}
@@ -731,12 +745,19 @@ bool InputEventJoypadMotion::action_match(const Ref<InputEvent> &p_event, bool *
 				if (p_deadzone == 1.0f) {
 					*p_strength = 1.0f;
 				} else {
-					*p_strength = CLAMP(Math::inverse_lerp(p_deadzone, 1.0f, Math::abs(jm->get_axis_value())), 0.0f, 1.0f);
+					*p_strength = CLAMP(Math::inverse_lerp(p_deadzone, 1.0f, jm_abs_axis_value), 0.0f, 1.0f);
 				}
 			} else {
 				*p_strength = 0.0f;
 			}
 		}
+		if (p_raw_strength != nullptr) {
+			if (same_direction) { // NOT pressed, because we want to ignore the deadzone.
+				*p_raw_strength = jm_abs_axis_value;
+			} else {
+				*p_raw_strength = 0.0f;
+			}
+		}
 	}
 	return match;
 }
@@ -782,7 +803,7 @@ float InputEventJoypadButton::get_pressure() const {
 	return pressure;
 }
 
-bool InputEventJoypadButton::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const {
+bool InputEventJoypadButton::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const {
 	Ref<InputEventJoypadButton> jb = p_event;
 	if (jb.is_null()) {
 		return false;
@@ -793,8 +814,12 @@ bool InputEventJoypadButton::action_match(const Ref<InputEvent> &p_event, bool *
 		if (p_pressed != nullptr) {
 			*p_pressed = jb->is_pressed();
 		}
+		float strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
 		if (p_strength != nullptr) {
-			*p_strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
+			*p_strength = strength;
+		}
+		if (p_raw_strength != nullptr) {
+			*p_raw_strength = strength;
 		}
 	}
 
@@ -997,7 +1022,7 @@ bool InputEventAction::is_action(const StringName &p_action) const {
 	return action == p_action;
 }
 
-bool InputEventAction::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const {
+bool InputEventAction::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const {
 	Ref<InputEventAction> act = p_event;
 	if (act.is_null()) {
 		return false;
@@ -1008,8 +1033,12 @@ bool InputEventAction::action_match(const Ref<InputEvent> &p_event, bool *p_pres
 		if (p_pressed != nullptr) {
 			*p_pressed = act->pressed;
 		}
+		float strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
 		if (p_strength != nullptr) {
-			*p_strength = (p_pressed != nullptr && *p_pressed) ? 1.0f : 0.0f;
+			*p_strength = strength;
+		}
+		if (p_raw_strength != nullptr) {
+			*p_raw_strength = strength;
 		}
 	}
 	return match;

+ 7 - 6
core/input/input_event.h

@@ -173,6 +173,7 @@ public:
 	bool is_action_pressed(const StringName &p_action, bool p_allow_echo = false) const;
 	bool is_action_released(const StringName &p_action) const;
 	float get_action_strength(const StringName &p_action) const;
+	float get_action_raw_strength(const StringName &p_action) const;
 
 	// To be removed someday, since they do not make sense for all events
 	virtual bool is_pressed() const;
@@ -182,7 +183,7 @@ public:
 
 	virtual Ref<InputEvent> xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs = Vector2()) const;
 
-	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const;
+	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const;
 	virtual bool shortcut_match(const Ref<InputEvent> &p_event) const;
 	virtual bool is_action_type() const;
 
@@ -283,7 +284,7 @@ public:
 	uint32_t get_keycode_with_modifiers() const;
 	uint32_t get_physical_keycode_with_modifiers() const;
 
-	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const override;
+	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
 	virtual bool shortcut_match(const Ref<InputEvent> &p_event) const override;
 
 	virtual bool is_action_type() const override { return true; }
@@ -342,7 +343,7 @@ public:
 	bool is_doubleclick() const;
 
 	virtual Ref<InputEvent> xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs = Vector2()) const override;
-	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const override;
+	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
 
 	virtual bool is_action_type() const override { return true; }
 	virtual String as_text() const override;
@@ -399,7 +400,7 @@ public:
 
 	virtual bool is_pressed() const override;
 
-	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const override;
+	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
 
 	virtual bool is_action_type() const override { return true; }
 	virtual String as_text() const override;
@@ -426,7 +427,7 @@ public:
 	void set_pressure(float p_pressure);
 	float get_pressure() const;
 
-	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const override;
+	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
 	virtual bool shortcut_match(const Ref<InputEvent> &p_event) const override;
 
 	virtual bool is_action_type() const override { return true; }
@@ -511,7 +512,7 @@ public:
 
 	virtual bool is_action(const StringName &p_action) const;
 
-	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float p_deadzone) const override;
+	virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
 
 	virtual bool shortcut_match(const Ref<InputEvent> &p_event) const override;
 	virtual bool is_action_type() const override { return true; }

+ 8 - 4
core/input/input_map.cpp

@@ -94,7 +94,7 @@ List<StringName> InputMap::get_actions() const {
 	return actions;
 }
 
-List<Ref<InputEvent>>::Element *InputMap::_find_event(Action &p_action, const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength) const {
+List<Ref<InputEvent>>::Element *InputMap::_find_event(Action &p_action, const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength) const {
 	ERR_FAIL_COND_V(!p_event.is_valid(), nullptr);
 
 	for (List<Ref<InputEvent>>::Element *E = p_action.inputs.front(); E; E = E->next()) {
@@ -105,7 +105,7 @@ List<Ref<InputEvent>>::Element *InputMap::_find_event(Action &p_action, const Re
 
 		int device = e->get_device();
 		if (device == ALL_DEVICES || device == p_event->get_device()) {
-			if (e->action_match(p_event, p_pressed, p_strength, p_action.deadzone)) {
+			if (e->action_match(p_event, p_pressed, p_strength, p_raw_strength, p_action.deadzone)) {
 				return E;
 			}
 		}
@@ -179,7 +179,7 @@ bool InputMap::event_is_action(const Ref<InputEvent> &p_event, const StringName
 	return event_get_action_status(p_event, p_action);
 }
 
-bool InputMap::event_get_action_status(const Ref<InputEvent> &p_event, const StringName &p_action, bool *p_pressed, float *p_strength) const {
+bool InputMap::event_get_action_status(const Ref<InputEvent> &p_event, const StringName &p_action, bool *p_pressed, float *p_strength, float *p_raw_strength) const {
 	Map<StringName, Action>::Element *E = input_map.find(p_action);
 	ERR_FAIL_COND_V_MSG(!E, false, "Request for nonexistent InputMap action '" + String(p_action) + "'.");
 
@@ -196,7 +196,8 @@ bool InputMap::event_get_action_status(const Ref<InputEvent> &p_event, const Str
 
 	bool pressed;
 	float strength;
-	List<Ref<InputEvent>>::Element *event = _find_event(E->get(), p_event, &pressed, &strength);
+	float raw_strength;
+	List<Ref<InputEvent>>::Element *event = _find_event(E->get(), p_event, &pressed, &strength, &raw_strength);
 	if (event != nullptr) {
 		if (p_pressed != nullptr) {
 			*p_pressed = pressed;
@@ -204,6 +205,9 @@ bool InputMap::event_get_action_status(const Ref<InputEvent> &p_event, const Str
 		if (p_strength != nullptr) {
 			*p_strength = strength;
 		}
+		if (p_raw_strength != nullptr) {
+			*p_raw_strength = raw_strength;
+		}
 		return true;
 	} else {
 		return false;

+ 2 - 2
core/input/input_map.h

@@ -54,7 +54,7 @@ private:
 
 	mutable Map<StringName, Action> input_map;
 
-	List<Ref<InputEvent>>::Element *_find_event(Action &p_action, const Ref<InputEvent> &p_event, bool *p_pressed = nullptr, float *p_strength = nullptr) const;
+	List<Ref<InputEvent>>::Element *_find_event(Action &p_action, const Ref<InputEvent> &p_event, bool *p_pressed = nullptr, float *p_strength = nullptr, float *p_raw_strength = nullptr) const;
 
 	Array _action_get_events(const StringName &p_action);
 	Array _get_actions();
@@ -78,7 +78,7 @@ public:
 
 	const List<Ref<InputEvent>> *action_get_events(const StringName &p_action);
 	bool event_is_action(const Ref<InputEvent> &p_event, const StringName &p_action) const;
-	bool event_get_action_status(const Ref<InputEvent> &p_event, const StringName &p_action, bool *p_pressed = nullptr, float *p_strength = nullptr) const;
+	bool event_get_action_status(const Ref<InputEvent> &p_event, const StringName &p_action, bool *p_pressed = nullptr, float *p_strength = nullptr, float *p_raw_strength = nullptr) const;
 
 	const Map<StringName, Action> &get_action_map() const;
 	void load_from_globals();