Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions etc/iptsd.conf
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,15 @@
##
# DisableOnStylus = false


##
## What condition the stylus must be in to disable the touchscreen if DisableOnStylus = true
## connected - Disable if stylus is sending packets (old behavior and default)
## active - Disable if stylus is hovering or being used
## contact - Disable if stylus is in contact with the screen
##
# DisableOnStylusLevel = connected

##
## How many centimeters a contact can be outside of the screen and still get registered.
##
Expand Down
40 changes: 36 additions & 4 deletions src/apps/daemon/daemon.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,13 +20,24 @@
namespace iptsd::apps::daemon {

class Daemon : public core::Application {
private:
// Put this enum here as this class is the only one that needs to quickly reference it
enum class DisableOnStylusLevel : u8 {
Connected = 0,
Active,
Contact,
};

private:
// The touch device.
std::optional<TouchDevice> m_touch = std::nullopt;

// The stylus device.
std::optional<StylusDevice> m_stylus = std::nullopt;

// The state of the config setting Touchscreen.DisableOnStylusLevel
DisableOnStylusLevel m_disable_on_stylus_level = DisableOnStylusLevel::Connected;

public:
Daemon(const core::Config &config, const core::DeviceInfo &info)
: core::Application(config, info)
Expand All @@ -40,6 +51,13 @@ class Daemon : public core::Application {

if (m_info.is_touchscreen() && !m_config.stylus_disable)
m_stylus.emplace(config, info);

if (m_config.touchscreen_disable_on_stylus_level == "active")
m_disable_on_stylus_level = DisableOnStylusLevel::Active;
else if (m_config.touchscreen_disable_on_stylus_level == "contact")
m_disable_on_stylus_level = DisableOnStylusLevel::Contact;
else // catch nonexistent/invalid level as connected, which is the old behavior
m_disable_on_stylus_level = DisableOnStylusLevel::Connected;
}

void on_start() override
Expand All @@ -61,8 +79,17 @@ class Daemon : public core::Application {

// Enable the touchscreen if it was disabled by a stylus that is no longer active.
if (m_config.touchscreen_disable_on_stylus && m_stylus.has_value()) {
if (!m_stylus->active() && !m_touch->enabled())
m_touch->enable();
if ((m_disable_on_stylus_level == DisableOnStylusLevel::Active &&
!m_stylus->active()) ||
(m_disable_on_stylus_level == DisableOnStylusLevel::Contact &&
!m_stylus->contact()) ||
// stylus cant report a state after its disconnected (obviously), so
// just check if its active for reenabling after connection (this was
// the old behavior)
(m_disable_on_stylus_level == DisableOnStylusLevel::Connected &&
!m_stylus->active()))
if (!m_touch->enabled())
m_touch->enable();
}

m_touch->update(contacts);
Expand All @@ -82,8 +109,13 @@ class Daemon : public core::Application {
return;

if (m_config.touchscreen_disable_on_stylus && m_touch.has_value()) {
if (m_touch->enabled())
m_touch->disable();
if ((m_disable_on_stylus_level == DisableOnStylusLevel::Active &&
m_stylus->active()) ||
(m_disable_on_stylus_level == DisableOnStylusLevel::Contact &&
m_stylus->contact()) ||
(m_disable_on_stylus_level == DisableOnStylusLevel::Connected))
if (m_touch->enabled())
m_touch->disable();
}

m_stylus->update(stylus);
Expand Down
14 changes: 14 additions & 0 deletions src/apps/daemon/stylus.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,9 @@ class StylusDevice {
// Whether the stylus is currently in proximity and sending data.
bool m_active = false;

// Whether the stylus is making contact with the screen
bool m_contact = false;

// The last known state of the stylus.
ipts::samples::Stylus m_last;

Expand Down Expand Up @@ -82,6 +85,7 @@ class StylusDevice {
void update(const ipts::samples::Stylus &data)
{
m_active = data.proximity;
m_contact = data.contact;

// Switching tools within one frame causes issues, lift the stylus for one frame.
if (m_last.rubber != data.rubber)
Expand Down Expand Up @@ -156,6 +160,16 @@ class StylusDevice {
return m_active;
}

/*!
* Whether the stylus is currently making contact with the screen.
*
* @return true if, well, it speaks for itself.
*/
[[nodiscard]] bool contact() const
{
return m_contact;
}

private:
/*!
* Calculates the tilt of the stylus on X and Y axis.
Expand Down
1 change: 1 addition & 0 deletions src/core/generic/config.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ class Config {
bool touchscreen_disable = false;
bool touchscreen_disable_on_palm = false;
bool touchscreen_disable_on_stylus = false;
std::string touchscreen_disable_on_stylus_level = "connected";
f64 touchscreen_overshoot = 0.5;

// [Touchpad]
Expand Down
1 change: 1 addition & 0 deletions src/core/linux/config-loader.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,7 @@ class ConfigLoader {
this->get(ini, "Touchscreen", "Disable", m_config.touchscreen_disable);
this->get(ini, "Touchscreen", "DisableOnPalm", m_config.touchscreen_disable_on_palm);
this->get(ini, "Touchscreen", "DisableOnStylus", m_config.touchscreen_disable_on_stylus);
this->get(ini, "Touchscreen", "DisableOnStylusLevel", m_config.touchscreen_disable_on_stylus_level);
this->get(ini, "Touchscreen", "Overshoot", m_config.touchscreen_overshoot);

this->get(ini, "Touchpad", "Disable", m_config.touchpad_disable);
Expand Down