mirror of
https://github.com/libratbag/libratbag.git
synced 2026-11-07 23:23:52 +01:00
Move the ReportRate into the profile
We don't have mice that can do report rates per resolutions, so let's not commit to that. This is a DBus API break but also a break in ratbagd, piper will need to update to fetch the rate/rates from the profile object now. It's a ratbagctl break as well, ratbagctl info changes slightly and the resolution is not argument anymore for the rate. Fixes #645 Signed-off-by: Peter Hutterer <peter.hutterer@who-t.net>
This commit is contained in:
43
doc/dbus.rst
43
doc/dbus.rst
@@ -244,6 +244,26 @@ org.freedesktop.ratbag1.Profile
|
||||
Provides the object paths of all LEDs in this profile, see
|
||||
:ref:`led`.
|
||||
|
||||
.. attribute:: ReportRate
|
||||
|
||||
:type: u
|
||||
:flags: read-write, mutable
|
||||
|
||||
uint for the report rate in Hz assigned to this profile. This rate
|
||||
must be one of those listed in :attr:`ReportRates`.
|
||||
|
||||
.. attribute:: ReportRates
|
||||
|
||||
:type: au
|
||||
:flags: read-write, constant
|
||||
|
||||
A list of permitted report rates. Values in this list may be used
|
||||
in the :attr:`ReportRate` property. This list is always sorted
|
||||
ascending, the lowest report rate is the first item in the list.
|
||||
|
||||
This list may be empty if the device does not support reading and/or
|
||||
writing to resolutions.
|
||||
|
||||
.. function:: SetActive() → ()
|
||||
|
||||
Set this profile to be the active profile
|
||||
@@ -327,29 +347,6 @@ org.freedesktop.ratbag1.Resolution
|
||||
This list may be empty if the device does not support reading and/or
|
||||
writing to resolutions.
|
||||
|
||||
.. attribute:: ReportRate
|
||||
|
||||
:type: u
|
||||
:flags: read-write, mutable
|
||||
|
||||
uint for the report rate in Hz assigned to this entry
|
||||
|
||||
If the resolution does not have the individual report rate
|
||||
capability, changing the report rate on one resolution will
|
||||
change the report rate on all resolutions.
|
||||
|
||||
.. attribute:: ReportRates
|
||||
|
||||
:type: au
|
||||
:flags: read-write, constant
|
||||
|
||||
A list of permitted report rates. Values in this list may be used
|
||||
in the :attr:`ReportRate` property. This list is always sorted
|
||||
ascending, the lowest report rate is the first item in the list.
|
||||
|
||||
This list may be empty if the device does not support reading and/or
|
||||
writing to resolutions.
|
||||
|
||||
.. function:: SetDefault() → ()
|
||||
|
||||
Set this resolution to be the default
|
||||
|
||||
@@ -430,6 +430,94 @@ ratbagd_profile_get_capabilities(sd_bus *bus,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
ratbagd_profile_get_report_rate(sd_bus *bus,
|
||||
const char *path,
|
||||
const char *interface,
|
||||
const char *property,
|
||||
sd_bus_message *reply,
|
||||
void *userdata,
|
||||
sd_bus_error *error)
|
||||
{
|
||||
struct ratbagd_profile *profile = userdata;
|
||||
struct ratbag_profile *lib_profile = profile->lib_profile;
|
||||
int rate;
|
||||
|
||||
rate = ratbag_profile_get_report_rate(lib_profile);
|
||||
verify_unsigned_int(rate);
|
||||
return sd_bus_message_append(reply, "u", rate);
|
||||
}
|
||||
|
||||
static int
|
||||
ratbagd_profile_get_report_rates(sd_bus *bus,
|
||||
const char *path,
|
||||
const char *interface,
|
||||
const char *property,
|
||||
sd_bus_message *reply,
|
||||
void *userdata,
|
||||
sd_bus_error *error)
|
||||
{
|
||||
struct ratbagd_profile *profile = userdata;
|
||||
struct ratbag_profile *lib_profile = profile->lib_profile;
|
||||
unsigned int rates[8];
|
||||
unsigned int nrates = ARRAY_LENGTH(rates);
|
||||
int r;
|
||||
|
||||
r = sd_bus_message_open_container(reply, 'a', "u");
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
nrates = ratbag_profile_get_report_rate_list(lib_profile,
|
||||
rates, nrates);
|
||||
assert(nrates <= ARRAY_LENGTH(rates));
|
||||
|
||||
for (unsigned int i = 0; i < nrates; i++) {
|
||||
verify_unsigned_int(rates[i]);
|
||||
r = sd_bus_message_append(reply, "u", rates[i]);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
return sd_bus_message_close_container(reply);
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
ratbagd_profile_set_report_rate(sd_bus *bus,
|
||||
const char *path,
|
||||
const char *interface,
|
||||
const char *property,
|
||||
sd_bus_message *m,
|
||||
void *userdata,
|
||||
sd_bus_error *error)
|
||||
{
|
||||
struct ratbagd_profile *profile = userdata;
|
||||
unsigned int rate;
|
||||
int r;
|
||||
|
||||
r = sd_bus_message_read(m, "u", &rate);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
/* basic sanity check */
|
||||
if (rate > 5000)
|
||||
rate = 5000;
|
||||
else if (rate % 100)
|
||||
rate = rate - (rate % 100);
|
||||
|
||||
r = ratbag_profile_set_report_rate(profile->lib_profile, rate);
|
||||
if (r == 0) {
|
||||
sd_bus *bus = sd_bus_message_get_bus(m);
|
||||
sd_bus_emit_properties_changed(bus,
|
||||
profile->path,
|
||||
RATBAGD_NAME_ROOT ".Profile",
|
||||
"ReportRate",
|
||||
NULL);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
const sd_bus_vtable ratbagd_profile_vtable[] = {
|
||||
SD_BUS_VTABLE_START(0),
|
||||
SD_BUS_WRITABLE_PROPERTY("Name", "s",
|
||||
@@ -446,6 +534,11 @@ const sd_bus_vtable ratbagd_profile_vtable[] = {
|
||||
SD_BUS_PROPERTY("Buttons", "ao", ratbagd_profile_get_buttons, 0, 0),
|
||||
SD_BUS_PROPERTY("Leds", "ao", ratbagd_profile_get_leds, 0, 0),
|
||||
SD_BUS_PROPERTY("IsActive", "b", ratbagd_profile_is_active, 0, SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
|
||||
SD_BUS_WRITABLE_PROPERTY("ReportRate", "u",
|
||||
ratbagd_profile_get_report_rate,
|
||||
ratbagd_profile_set_report_rate, 0,
|
||||
SD_BUS_VTABLE_UNPRIVILEGED|SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
|
||||
SD_BUS_PROPERTY("ReportRates", "au", ratbagd_profile_get_report_rates, 0, SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_METHOD("SetActive", "", "u", ratbagd_profile_set_active, SD_BUS_VTABLE_UNPRIVILEGED),
|
||||
SD_BUS_VTABLE_END,
|
||||
};
|
||||
|
||||
@@ -150,13 +150,6 @@ ratbagd_resolution_get_capabilities(sd_bus *bus,
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
cap = RATBAG_RESOLUTION_CAP_INDIVIDUAL_REPORT_RATE;
|
||||
if (ratbag_resolution_has_capability(lib_resolution, cap)) {
|
||||
r = sd_bus_message_append(reply, "u", cap);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
cap = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION;
|
||||
if (ratbag_resolution_has_capability(lib_resolution, cap)) {
|
||||
r = sd_bus_message_append(reply, "u", cap);
|
||||
@@ -299,95 +292,6 @@ ratbagd_resolution_set_resolution(sd_bus *bus,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
ratbagd_resolution_get_report_rate(sd_bus *bus,
|
||||
const char *path,
|
||||
const char *interface,
|
||||
const char *property,
|
||||
sd_bus_message *reply,
|
||||
void *userdata,
|
||||
sd_bus_error *error)
|
||||
{
|
||||
struct ratbagd_resolution *resolution = userdata;
|
||||
struct ratbag_resolution *lib_resolution = resolution->lib_resolution;
|
||||
int rate;
|
||||
|
||||
rate = ratbag_resolution_get_report_rate(lib_resolution);
|
||||
verify_unsigned_int(rate);
|
||||
return sd_bus_message_append(reply, "u", rate);
|
||||
}
|
||||
|
||||
static int
|
||||
ratbagd_resolution_get_report_rates(sd_bus *bus,
|
||||
const char *path,
|
||||
const char *interface,
|
||||
const char *property,
|
||||
sd_bus_message *reply,
|
||||
void *userdata,
|
||||
sd_bus_error *error)
|
||||
{
|
||||
struct ratbagd_resolution *resolution = userdata;
|
||||
struct ratbag_resolution *lib_resolution = resolution->lib_resolution;
|
||||
unsigned int rates[8];
|
||||
unsigned int nrates = ARRAY_LENGTH(rates);
|
||||
int r;
|
||||
|
||||
r = sd_bus_message_open_container(reply, 'a', "u");
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
nrates = ratbag_resolution_get_report_rate_list(lib_resolution,
|
||||
rates, nrates);
|
||||
assert(nrates <= ARRAY_LENGTH(rates));
|
||||
|
||||
for (unsigned int i = 0; i < nrates; i++) {
|
||||
verify_unsigned_int(rates[i]);
|
||||
r = sd_bus_message_append(reply, "u", rates[i]);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
return sd_bus_message_close_container(reply);
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
ratbagd_resolution_set_report_rate(sd_bus *bus,
|
||||
const char *path,
|
||||
const char *interface,
|
||||
const char *property,
|
||||
sd_bus_message *m,
|
||||
void *userdata,
|
||||
sd_bus_error *error)
|
||||
{
|
||||
struct ratbagd_resolution *resolution = userdata;
|
||||
unsigned int rate;
|
||||
int r;
|
||||
|
||||
r = sd_bus_message_read(m, "u", &rate);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
/* basic sanity check */
|
||||
if (rate > 5000)
|
||||
rate = 5000;
|
||||
else if (rate % 100)
|
||||
rate = rate - (rate % 100);
|
||||
|
||||
r = ratbag_resolution_set_report_rate(resolution->lib_resolution,
|
||||
rate);
|
||||
if (r == 0) {
|
||||
sd_bus *bus = sd_bus_message_get_bus(m);
|
||||
sd_bus_emit_properties_changed(bus,
|
||||
resolution->path,
|
||||
RATBAGD_NAME_ROOT ".Resolution",
|
||||
"ReportRate",
|
||||
NULL);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
const sd_bus_vtable ratbagd_resolution_vtable[] = {
|
||||
SD_BUS_VTABLE_START(0),
|
||||
SD_BUS_PROPERTY("Index", "u", NULL, offsetof(struct ratbagd_resolution, index), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
@@ -399,11 +303,6 @@ const sd_bus_vtable ratbagd_resolution_vtable[] = {
|
||||
ratbagd_resolution_set_resolution, 0,
|
||||
SD_BUS_VTABLE_UNPRIVILEGED|SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
|
||||
SD_BUS_PROPERTY("Resolutions", "au", ratbagd_resolution_get_resolutions, 0, SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_WRITABLE_PROPERTY("ReportRate", "u",
|
||||
ratbagd_resolution_get_report_rate,
|
||||
ratbagd_resolution_set_report_rate, 0,
|
||||
SD_BUS_VTABLE_UNPRIVILEGED|SD_BUS_VTABLE_PROPERTY_EMITS_CHANGE),
|
||||
SD_BUS_PROPERTY("ReportRates", "au", ratbagd_resolution_get_report_rates, 0, SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_METHOD("SetActive", "", "u", ratbagd_resolution_set_active, SD_BUS_VTABLE_UNPRIVILEGED),
|
||||
SD_BUS_METHOD("SetDefault", "", "u", ratbagd_resolution_set_default, SD_BUS_VTABLE_UNPRIVILEGED),
|
||||
SD_BUS_VTABLE_END,
|
||||
|
||||
@@ -64,14 +64,16 @@ static const struct ratbag_test_device ratbagd_test_device_descr = {
|
||||
}
|
||||
},
|
||||
.resolutions = {
|
||||
{ .xres = 100, .yres = 200, .hz = 1000,
|
||||
.dpi_min = 50, .dpi_max = 5000,
|
||||
.report_rates = { 500, 1000 } },
|
||||
{ .xres = 200, .yres = 300, .hz = 1000, .active = true, .dflt = true },
|
||||
{ .xres = 300, .yres = 400, .hz = 1000 },
|
||||
{ .xres = 100, .yres = 200,
|
||||
.dpi_min = 50, .dpi_max = 5000},
|
||||
{ .xres = 200, .yres = 300, .active = true, .dflt = true },
|
||||
{ .xres = 300, .yres = 400 },
|
||||
},
|
||||
.active = true,
|
||||
.dflt = false,
|
||||
.hz = 1000,
|
||||
.report_rates = {500, 1000},
|
||||
|
||||
.leds = {
|
||||
{
|
||||
.mode = RATBAG_LED_OFF,
|
||||
@@ -108,10 +110,11 @@ static const struct ratbag_test_device ratbagd_test_device_descr = {
|
||||
.key = 7 },
|
||||
},
|
||||
.resolutions = {
|
||||
{ .xres = 1100, .yres = 1200, .hz = 2000, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 1200, .yres = 1300, .hz = 2000, .dflt = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 1300, .yres = 1400, .hz = 2000, .active = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 1100, .yres = 1200, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 1200, .yres = 1300, .dflt = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 1300, .yres = 1400, .active = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
},
|
||||
.hz = 2000,
|
||||
.active = false,
|
||||
.dflt = true,
|
||||
.name = "test profile 2",
|
||||
@@ -137,10 +140,11 @@ static const struct ratbag_test_device ratbagd_test_device_descr = {
|
||||
.button = 3 },
|
||||
},
|
||||
.resolutions = {
|
||||
{ .xres = 2100, .yres = 2200, .hz = 3000, .active = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 2200, .yres = 2300, .hz = 3000, .dflt = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 2300, .yres = 2400, .hz = 3000, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 2100, .yres = 2200, .active = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 2200, .yres = 2300, .dflt = true, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
{ .xres = 2300, .yres = 2400, .caps = RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION },
|
||||
},
|
||||
.hz = 3000,
|
||||
.leds = {
|
||||
{
|
||||
.mode = RATBAG_LED_ON,
|
||||
|
||||
@@ -428,7 +428,7 @@ etekcity_read_profile(struct ratbag_profile *profile)
|
||||
struct etekcity_settings_report *setting_report;
|
||||
uint8_t *buf;
|
||||
unsigned int report_rate;
|
||||
int dpi_x, dpi_y, hz;
|
||||
int dpi_x, dpi_y;
|
||||
int rc;
|
||||
unsigned int report_rates[] = { 125, 250, 500, 1000 };
|
||||
|
||||
@@ -456,24 +456,24 @@ etekcity_read_profile(struct ratbag_profile *profile)
|
||||
report_rate = 0;
|
||||
}
|
||||
|
||||
ratbag_profile_set_report_rate_list(profile, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
ratbag_profile_set_report_rate(profile, report_rate);
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
dpi_x = setting_report->xres[resolution->index] * 50;
|
||||
dpi_y = setting_report->yres[resolution->index] * 50;
|
||||
hz = report_rate;
|
||||
if (!(setting_report->dpi_mask & (1 << resolution->index))) {
|
||||
/* the profile is disabled, overwrite it */
|
||||
dpi_x = 0;
|
||||
dpi_y = 0;
|
||||
hz = 0;
|
||||
}
|
||||
|
||||
ratbag_resolution_set_resolution(resolution, dpi_x, dpi_y, hz);
|
||||
ratbag_resolution_set_resolution(resolution, dpi_x, dpi_y);
|
||||
ratbag_resolution_set_cap(resolution,
|
||||
RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION);
|
||||
resolution->is_active = (resolution->index == setting_report->current_dpi);
|
||||
|
||||
ratbag_resolution_set_report_rate_list(resolution, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
}
|
||||
|
||||
ratbag_profile_for_each_button(profile, button)
|
||||
|
||||
@@ -978,6 +978,7 @@ gskill_read_resolutions(struct ratbag_profile *profile,
|
||||
struct gskill_profile_report *report)
|
||||
{
|
||||
struct gskill_profile_data *pdata = profile_to_pdata(profile);
|
||||
unsigned int rates[] = { 500, 1000 }; /* let's assume that is true */
|
||||
int dpi_x, dpi_y, hz, i;
|
||||
|
||||
log_debug(profile->device->ratbag,
|
||||
@@ -985,16 +986,17 @@ gskill_read_resolutions(struct ratbag_profile *profile,
|
||||
profile->index, report->dpi_num);
|
||||
|
||||
hz = GSKILL_MAX_POLLING_RATE / (report->polling_rate + 1);
|
||||
ratbag_profile_set_report_rate_list(profile, rates, ARRAY_LENGTH(rates));
|
||||
ratbag_profile_set_report_rate(profile, hz);
|
||||
|
||||
for (i = 0; i < report->dpi_num; i++) {
|
||||
_cleanup_resolution_ struct ratbag_resolution *resolution = NULL;
|
||||
unsigned int rates[] = { 500, 1000 }; /* let's assume that is true */
|
||||
|
||||
dpi_x = report->dpi_levels[i].x * GSKILL_DPI_UNIT;
|
||||
dpi_y = report->dpi_levels[i].y * GSKILL_DPI_UNIT;
|
||||
|
||||
resolution = ratbag_profile_get_resolution(profile, i);
|
||||
ratbag_resolution_set_resolution(resolution, dpi_x, dpi_y, hz);
|
||||
ratbag_resolution_set_resolution(resolution, dpi_x, dpi_y);
|
||||
resolution->is_active = (i == report->current_dpi_level);
|
||||
pdata->res_idx_to_dev_idx[i] = i;
|
||||
|
||||
@@ -1003,8 +1005,6 @@ gskill_read_resolutions(struct ratbag_profile *profile,
|
||||
|
||||
ratbag_resolution_set_dpi_list_from_range(resolution,
|
||||
GSKILL_MIN_DPI, GSKILL_MAX_DPI);
|
||||
ratbag_resolution_set_report_rate_list(resolution, rates,
|
||||
ARRAY_LENGTH(rates));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -429,8 +429,7 @@ hidpp10drv_read_profile(struct ratbag_profile *profile)
|
||||
|
||||
ratbag_resolution_set_resolution(res,
|
||||
p.dpi_modes[res->index].xres,
|
||||
p.dpi_modes[res->index].yres,
|
||||
p.refresh_rate);
|
||||
p.dpi_modes[res->index].yres);
|
||||
ratbag_resolution_set_cap(res,
|
||||
RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION);
|
||||
if (profile->is_active &&
|
||||
@@ -458,10 +457,11 @@ hidpp10drv_read_profile(struct ratbag_profile *profile)
|
||||
ratbag_resolution_set_dpi_list(res, dpis, hidpp10->dpi_count);
|
||||
}
|
||||
|
||||
ratbag_resolution_set_report_rate_list(res, rates,
|
||||
ARRAY_LENGTH(rates));
|
||||
}
|
||||
|
||||
ratbag_profile_set_report_rate_list(profile, rates, ARRAY_LENGTH(rates));
|
||||
ratbag_profile_set_report_rate(profile, p.refresh_rate);
|
||||
|
||||
ratbag_profile_for_each_button(profile, button)
|
||||
hidpp10drv_read_button(button);
|
||||
|
||||
|
||||
@@ -805,7 +805,7 @@ hidpp20drv_read_resolution_dpi(struct ratbag_profile *profile)
|
||||
sensor = &drv_data->sensors[0];
|
||||
|
||||
/* FIXME: retrieve the refresh rate */
|
||||
ratbag_resolution_set_resolution(res, sensor->dpi, sensor->dpi, 0);
|
||||
ratbag_resolution_set_resolution(res, sensor->dpi, sensor->dpi);
|
||||
ratbag_resolution_set_dpi_list_from_range(res,
|
||||
sensor->dpi_min,
|
||||
sensor->dpi_max);
|
||||
@@ -823,13 +823,11 @@ hidpp20drv_read_resolution_dpi(struct ratbag_profile *profile)
|
||||
if (rc < 0)
|
||||
return rc;
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, res)
|
||||
ratbag_resolution_set_report_rate_list(res,
|
||||
drv_data->report_rates,
|
||||
drv_data->num_report_rates);
|
||||
ratbag_profile_set_report_rate_list(profile,
|
||||
drv_data->report_rates,
|
||||
drv_data->num_report_rates);
|
||||
} else {
|
||||
ratbag_profile_for_each_resolution(profile, res)
|
||||
ratbag_resolution_set_report_rate_list(res, &default_rate, 1);
|
||||
ratbag_profile_set_report_rate_list(profile, &default_rate, 1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
@@ -1017,8 +1015,7 @@ hidpp20drv_read_profile_8100(struct ratbag_profile *profile)
|
||||
|
||||
ratbag_resolution_set_resolution(res,
|
||||
p->dpi[res->index],
|
||||
p->dpi[res->index],
|
||||
p->report_rate);
|
||||
p->dpi[res->index]);
|
||||
|
||||
if (profile->is_active &&
|
||||
res->index == (unsigned int)dpi_index)
|
||||
@@ -1032,10 +1029,12 @@ hidpp20drv_read_profile_8100(struct ratbag_profile *profile)
|
||||
ratbag_resolution_set_dpi_list_from_range(res,
|
||||
sensor->dpi_min,
|
||||
sensor->dpi_max);
|
||||
ratbag_resolution_set_report_rate_list(res,
|
||||
drv_data->report_rates,
|
||||
drv_data->num_report_rates);
|
||||
}
|
||||
|
||||
ratbag_profile_set_report_rate_list(profile,
|
||||
drv_data->report_rates,
|
||||
drv_data->num_report_rates);
|
||||
ratbag_profile_set_report_rate(profile, p->report_rate);
|
||||
}
|
||||
|
||||
static void
|
||||
|
||||
@@ -443,6 +443,9 @@ logitech_g300_read_profile(struct ratbag_profile *profile)
|
||||
|
||||
hz = logitech_g300_raw_to_frequency(report->frequency);
|
||||
|
||||
ratbag_profile_set_report_rate_list(profile, &hz, 1);
|
||||
ratbag_profile_set_report_rate(profile, hz);
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
struct logitech_g300_resolution *res =
|
||||
&report->dpi_levels[resolution->index];
|
||||
@@ -451,13 +454,11 @@ logitech_g300_read_profile(struct ratbag_profile *profile)
|
||||
|
||||
resolution->dpi_x = res->dpi * 250;
|
||||
resolution->dpi_y = res->dpi * 250;
|
||||
resolution->hz = hz;
|
||||
resolution->is_default = res->is_default;
|
||||
resolution->is_active = res->is_default;
|
||||
|
||||
ratbag_resolution_set_dpi_list(resolution, dpis,
|
||||
ARRAY_LENGTH(dpis));
|
||||
ratbag_resolution_set_report_rate_list(resolution, &hz, 1);
|
||||
}
|
||||
|
||||
ratbag_profile_for_each_button(profile, button)
|
||||
@@ -534,12 +535,13 @@ logitech_g300_write_profile(struct ratbag_profile *profile)
|
||||
struct ratbag_led *led;
|
||||
|
||||
uint8_t *buf;
|
||||
unsigned int hz;
|
||||
int rc;
|
||||
|
||||
pdata = &drv_data->profile_data[profile->index];
|
||||
report = &pdata->report;
|
||||
|
||||
report->frequency = logitech_g300_frequency_to_raw(profile->hz);
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
struct logitech_g300_resolution *res =
|
||||
&report->dpi_levels[resolution->index];
|
||||
@@ -550,12 +552,6 @@ logitech_g300_write_profile(struct ratbag_profile *profile)
|
||||
if (profile->is_active && resolution->is_active)
|
||||
logitech_g300_set_current_resolution(device,
|
||||
resolution->index);
|
||||
|
||||
/* The same hz is used for all resolutions */
|
||||
if (resolution->index == 0) {
|
||||
hz = resolution->hz;
|
||||
report->frequency = logitech_g300_frequency_to_raw(hz);
|
||||
}
|
||||
}
|
||||
|
||||
list_for_each(button, &profile->buttons, link) {
|
||||
|
||||
@@ -438,19 +438,19 @@ logitech_g600_read_profile(struct ratbag_profile *profile)
|
||||
return;
|
||||
}
|
||||
|
||||
ratbag_profile_set_report_rate_list(profile, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
ratbag_profile_set_report_rate(profile, 1000 / (report->frequency + 1));
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
resolution->dpi_x = report->dpi[resolution->index] * 50;
|
||||
resolution->dpi_y = report->dpi[resolution->index] * 50;
|
||||
resolution->hz = 1000 / (report->frequency + 1);
|
||||
resolution->is_default = report->dpi_default - 1U == resolution->index;
|
||||
resolution->is_active = resolution->is_default;
|
||||
|
||||
ratbag_resolution_set_dpi_list_from_range(resolution,
|
||||
LOGITECH_G600_DPI_MIN,
|
||||
LOGITECH_G600_DPI_MAX);
|
||||
ratbag_resolution_set_report_rate_list(resolution, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
}
|
||||
|
||||
ratbag_profile_for_each_button(profile, button)
|
||||
@@ -531,6 +531,8 @@ logitech_g600_write_profile(struct ratbag_profile *profile)
|
||||
pdata = &drv_data->profile_data[profile->index];
|
||||
report = &pdata->report;
|
||||
|
||||
report->frequency = (1000 / profile->hz) - 1;
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
report->dpi[resolution->index] = resolution->dpi_x / 50;
|
||||
|
||||
@@ -539,10 +541,6 @@ logitech_g600_write_profile(struct ratbag_profile *profile)
|
||||
|
||||
if (profile->is_active && resolution->is_active)
|
||||
active_resolution = resolution->index;
|
||||
|
||||
/* The same hz is used for all resolutions */
|
||||
if (resolution->index == 0)
|
||||
report->frequency = (1000 / resolution->hz) - 1;
|
||||
}
|
||||
|
||||
list_for_each(button, &profile->buttons, link) {
|
||||
|
||||
@@ -702,7 +702,7 @@ roccat_read_profile(struct ratbag_profile *profile)
|
||||
struct roccat_settings_report *setting_report;
|
||||
uint8_t *buf;
|
||||
unsigned int report_rate;
|
||||
int dpi_x, dpi_y, hz;
|
||||
int dpi_x, dpi_y;
|
||||
int rc;
|
||||
unsigned int report_rates[] = { 125, 250, 500, 1000 };
|
||||
|
||||
@@ -730,24 +730,24 @@ roccat_read_profile(struct ratbag_profile *profile)
|
||||
report_rate = 0;
|
||||
}
|
||||
|
||||
ratbag_profile_set_report_rate_list(profile, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
ratbag_profile_set_report_rate(profile, report_rate);
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
dpi_x = setting_report->xres[resolution->index] * 50;
|
||||
dpi_y = setting_report->yres[resolution->index] * 50;
|
||||
hz = report_rate;
|
||||
if (!(setting_report->dpi_mask & (1 << resolution->index))) {
|
||||
/* the profile is disabled, overwrite it */
|
||||
dpi_x = 0;
|
||||
dpi_y = 0;
|
||||
hz = 0;
|
||||
}
|
||||
|
||||
ratbag_resolution_set_resolution(resolution, dpi_x, dpi_y, hz);
|
||||
ratbag_resolution_set_resolution(resolution, dpi_x, dpi_y);
|
||||
ratbag_resolution_set_cap(resolution,
|
||||
RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION);
|
||||
resolution->is_active = (resolution->index == setting_report->current_dpi);
|
||||
|
||||
ratbag_resolution_set_report_rate_list(resolution, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
ratbag_resolution_set_dpi_list_from_range(resolution, 200, 8200);
|
||||
}
|
||||
|
||||
|
||||
@@ -307,6 +307,9 @@ steelseries_probe(struct ratbag_device *device)
|
||||
profile->is_active = true;
|
||||
|
||||
ratbag_profile_set_cap(profile, RATBAG_PROFILE_CAP_WRITE_ONLY);
|
||||
ratbag_profile_set_report_rate_list(profile, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
ratbag_profile_set_report_rate(profile, 1000);
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
if (resolution->index == 0) {
|
||||
@@ -327,10 +330,6 @@ steelseries_probe(struct ratbag_device *device)
|
||||
* by all known devices. */
|
||||
resolution->dpi_x = 800 * (resolution->index + 1);
|
||||
resolution->dpi_y = 800 * (resolution->index + 1);
|
||||
|
||||
ratbag_resolution_set_report_rate_list(resolution, report_rates,
|
||||
ARRAY_LENGTH(report_rates));
|
||||
resolution->hz = 1000;
|
||||
}
|
||||
|
||||
ratbag_profile_for_each_button(profile, button) {
|
||||
@@ -434,9 +433,9 @@ steelseries_write_dpi(struct ratbag_resolution *resolution)
|
||||
}
|
||||
|
||||
static int
|
||||
steelseries_write_report_rate(struct ratbag_resolution *resolution)
|
||||
steelseries_write_report_rate(struct ratbag_profile *profile)
|
||||
{
|
||||
struct ratbag_device *device = resolution->profile->device;
|
||||
struct ratbag_device *device = profile->device;
|
||||
int device_version = ratbag_device_data_steelseries_get_device_version(device->data);
|
||||
int ret;
|
||||
size_t buf_len;
|
||||
@@ -445,15 +444,15 @@ steelseries_write_report_rate(struct ratbag_resolution *resolution)
|
||||
if (device_version == 1) {
|
||||
buf_len = STEELSERIES_REPORT_SIZE_SHORT;
|
||||
buf[0] = STEELSERIES_ID_REPORT_RATE_SHORT;
|
||||
buf[2] = 1000 / resolution->hz;
|
||||
buf[2] = 1000 / profile->hz;
|
||||
} else if (device_version == 2) {
|
||||
buf_len = STEELSERIES_REPORT_SIZE;
|
||||
buf[0] = STEELSERIES_ID_REPORT_RATE;
|
||||
buf[2] = 1000 / resolution->hz;
|
||||
buf[2] = 1000 / profile->hz;
|
||||
} else if (device_version == 3) {
|
||||
buf_len = STEELSERIES_REPORT_SIZE;
|
||||
buf[0] = STEELSERIES_ID_REPORT_RATE_PROTOCOL3;
|
||||
buf[2] = 1000 / resolution->hz;
|
||||
buf[2] = 1000 / profile->hz;
|
||||
} else {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
@@ -882,6 +881,10 @@ steelseries_write_profile(struct ratbag_profile *profile)
|
||||
int rc;
|
||||
bool buttons_dirty = false;
|
||||
|
||||
rc = steelseries_write_report_rate(profile);
|
||||
if (rc != 0)
|
||||
return rc;
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
if (!resolution->dirty)
|
||||
continue;
|
||||
@@ -894,9 +897,6 @@ steelseries_write_profile(struct ratbag_profile *profile)
|
||||
if (resolution->index > 0)
|
||||
continue;
|
||||
|
||||
rc = steelseries_write_report_rate(resolution);
|
||||
if (rc != 0)
|
||||
return rc;
|
||||
}
|
||||
|
||||
ratbag_profile_for_each_button(profile, button) {
|
||||
|
||||
@@ -175,6 +175,7 @@ test_read_profile(struct ratbag_profile *profile)
|
||||
unsigned int i;
|
||||
bool active_set = false;
|
||||
bool default_set = false;
|
||||
size_t nrates = 0;
|
||||
|
||||
assert(profile->index < d->num_profiles);
|
||||
|
||||
@@ -182,29 +183,30 @@ test_read_profile(struct ratbag_profile *profile)
|
||||
p0 = &d->profiles[0];
|
||||
r0 = &p0->resolutions[0];
|
||||
|
||||
for (size_t r = 0; r < ARRAY_LENGTH(p0->report_rates); r++) {
|
||||
if (p0->report_rates[r] > 0)
|
||||
nrates++;
|
||||
}
|
||||
|
||||
if (nrates > 0)
|
||||
ratbag_profile_set_report_rate_list(profile,
|
||||
p0->report_rates,
|
||||
nrates);
|
||||
ratbag_profile_set_report_rate(profile, p->hz);
|
||||
|
||||
for (i = 0; i < d->num_resolutions; i++) {
|
||||
_cleanup_resolution_ struct ratbag_resolution *res = NULL;
|
||||
size_t nrates = 0;
|
||||
|
||||
r = &p->resolutions[i];
|
||||
|
||||
res = ratbag_profile_get_resolution(profile, i);
|
||||
assert(res);
|
||||
ratbag_resolution_set_resolution(res, r->xres, r->yres, r->hz);
|
||||
ratbag_resolution_set_resolution(res, r->xres, r->yres);
|
||||
if (r0->dpi_min != 0 && r0->dpi_max != 0)
|
||||
ratbag_resolution_set_dpi_list_from_range(res,
|
||||
r0->dpi_min,
|
||||
r0->dpi_max);
|
||||
|
||||
for (size_t r = 0; r < ARRAY_LENGTH(r0->report_rates); r++) {
|
||||
if (r0->report_rates[r] > 0)
|
||||
nrates++;
|
||||
}
|
||||
|
||||
if (nrates > 0)
|
||||
ratbag_resolution_set_report_rate_list(res,
|
||||
r0->report_rates,
|
||||
nrates);
|
||||
|
||||
res->is_active = r->active;
|
||||
if (r->active)
|
||||
@@ -213,7 +215,6 @@ test_read_profile(struct ratbag_profile *profile)
|
||||
if (r->dflt)
|
||||
default_set = true;
|
||||
ratbag_resolution_set_cap(res, r->caps);
|
||||
res->hz = r->hz;
|
||||
}
|
||||
|
||||
/* special case triggered by the test suite when num_resolutions is 0 */
|
||||
|
||||
@@ -125,17 +125,10 @@ enum ratbag_profile_capability {
|
||||
* @ingroup enums
|
||||
*/
|
||||
enum ratbag_resolution_capability {
|
||||
/**
|
||||
* The report rate can be set per resolution mode. If this property
|
||||
* is not available, all resolutions within the same profile have
|
||||
* the same report rate and changing one changes the others.
|
||||
*/
|
||||
RATBAG_RESOLUTION_CAP_INDIVIDUAL_REPORT_RATE = 1,
|
||||
|
||||
/**
|
||||
* The resolution can be set for x and y separately.
|
||||
*/
|
||||
RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION,
|
||||
RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION = 1,
|
||||
};
|
||||
|
||||
/**
|
||||
|
||||
@@ -250,10 +250,7 @@ struct ratbag_resolution {
|
||||
|
||||
unsigned int dpi_x; /**< x resolution in dpi */
|
||||
unsigned int dpi_y; /**< y resolution in dpi */
|
||||
unsigned int hz; /**< report rate in Hz */
|
||||
|
||||
unsigned int rates[8];
|
||||
size_t nrates;
|
||||
|
||||
bool is_active;
|
||||
bool is_default;
|
||||
@@ -291,6 +288,10 @@ struct ratbag_profile {
|
||||
struct list resolutions;
|
||||
struct list leds;
|
||||
|
||||
unsigned int hz; /**< report rate in Hz */
|
||||
unsigned int rates[8]; /**< report rates available */
|
||||
size_t nrates; /**< number of entries in rates */
|
||||
|
||||
unsigned int num_resolutions;
|
||||
|
||||
bool is_active; /**< profile is the currently active one */
|
||||
@@ -485,11 +486,10 @@ ratbag_action_keycode_from_macro(struct ratbag_button_action *action,
|
||||
|
||||
static inline void
|
||||
ratbag_resolution_set_resolution(struct ratbag_resolution *res,
|
||||
int dpi_x, int dpi_y, int hz)
|
||||
int dpi_x, int dpi_y)
|
||||
{
|
||||
res->dpi_x = dpi_x;
|
||||
res->dpi_y = dpi_y;
|
||||
res->hz = hz;
|
||||
}
|
||||
|
||||
static inline void
|
||||
@@ -546,19 +546,19 @@ ratbag_resolution_set_dpi_list(struct ratbag_resolution *res,
|
||||
}
|
||||
|
||||
static inline void
|
||||
ratbag_resolution_set_report_rate_list(struct ratbag_resolution *res,
|
||||
unsigned int *rates,
|
||||
size_t nrates)
|
||||
ratbag_profile_set_report_rate_list(struct ratbag_profile *profile,
|
||||
unsigned int *rates,
|
||||
size_t nrates)
|
||||
{
|
||||
assert(nrates <= ARRAY_LENGTH(res->rates));
|
||||
_Static_assert(sizeof(*rates) == sizeof(*res->rates), "Mismatching size");
|
||||
assert(nrates <= ARRAY_LENGTH(profile->rates));
|
||||
_Static_assert(sizeof(*rates) == sizeof(*profile->rates), "Mismatching size");
|
||||
|
||||
for (size_t i = 0; i < nrates; i++) {
|
||||
res->rates[i] = rates[i];
|
||||
profile->rates[i] = rates[i];
|
||||
if (i > 0)
|
||||
assert(rates[i] > rates[i - 1]);
|
||||
}
|
||||
res->nrates = nrates;
|
||||
profile->nrates = nrates;
|
||||
}
|
||||
|
||||
static inline void
|
||||
|
||||
@@ -51,13 +51,11 @@ struct ratbag_test_button {
|
||||
|
||||
struct ratbag_test_resolution {
|
||||
int xres, yres;
|
||||
int hz;
|
||||
bool active;
|
||||
bool dflt;
|
||||
uint32_t caps;
|
||||
|
||||
int dpi_min, dpi_max;
|
||||
unsigned int report_rates[5];
|
||||
};
|
||||
|
||||
struct ratbag_test_color {
|
||||
@@ -83,6 +81,9 @@ struct ratbag_test_profile {
|
||||
bool dflt;
|
||||
bool disabled;
|
||||
uint32_t caps[10];
|
||||
|
||||
int hz;
|
||||
unsigned int report_rates[5];
|
||||
};
|
||||
|
||||
struct ratbag_test_device {
|
||||
|
||||
@@ -241,6 +241,8 @@ ratbag_sanity_check_device(struct ratbag_device *device)
|
||||
|
||||
ratbag_device_for_each_profile(device, profile) {
|
||||
struct ratbag_resolution *resolution;
|
||||
unsigned int vals[300];
|
||||
unsigned int nvals = ARRAY_LENGTH(vals);
|
||||
|
||||
/* Allow max 1 active profile */
|
||||
if (profile->is_active) {
|
||||
@@ -263,9 +265,6 @@ ratbag_sanity_check_device(struct ratbag_device *device)
|
||||
}
|
||||
|
||||
ratbag_profile_for_each_resolution(profile, resolution) {
|
||||
unsigned int vals[300];
|
||||
unsigned int nvals = ARRAY_LENGTH(vals);
|
||||
|
||||
nvals = ratbag_resolution_get_dpi_list(resolution, vals, nvals);
|
||||
if (nvals == 0) {
|
||||
log_bug_libratbag(ratbag,
|
||||
@@ -274,13 +273,14 @@ ratbag_sanity_check_device(struct ratbag_device *device)
|
||||
goto out;
|
||||
}
|
||||
|
||||
nvals = ratbag_resolution_get_report_rate_list(resolution, vals, nvals);
|
||||
if (nvals == 0) {
|
||||
log_bug_libratbag(ratbag,
|
||||
"%s: invalid report rate list\n",
|
||||
device->name);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
nvals = ratbag_profile_get_report_rate_list(profile, vals, nvals);
|
||||
if (nvals == 0) {
|
||||
log_bug_libratbag(ratbag,
|
||||
"%s: invalid report rate list\n",
|
||||
device->name);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1028,7 +1028,6 @@ ratbag_resolution_has_capability(struct ratbag_resolution *resolution,
|
||||
enum ratbag_resolution_capability cap)
|
||||
{
|
||||
switch (cap) {
|
||||
case RATBAG_RESOLUTION_CAP_INDIVIDUAL_REPORT_RATE:
|
||||
case RATBAG_RESOLUTION_CAP_SEPARATE_XY_RESOLUTION:
|
||||
break;
|
||||
default:
|
||||
@@ -1096,29 +1095,12 @@ ratbag_resolution_set_dpi_xy(struct ratbag_resolution *resolution,
|
||||
}
|
||||
|
||||
LIBRATBAG_EXPORT enum ratbag_error_code
|
||||
ratbag_resolution_set_report_rate(struct ratbag_resolution *resolution,
|
||||
unsigned int hz)
|
||||
ratbag_profile_set_report_rate(struct ratbag_profile *profile,
|
||||
unsigned int hz)
|
||||
{
|
||||
if (ratbag_resolution_has_capability(resolution,
|
||||
RATBAG_RESOLUTION_CAP_INDIVIDUAL_REPORT_RATE)) {
|
||||
if (resolution->hz != hz) {
|
||||
resolution->hz = hz;
|
||||
resolution->dirty = true;
|
||||
resolution->profile->dirty = true;
|
||||
}
|
||||
} else {
|
||||
struct ratbag_profile *profile = resolution->profile;
|
||||
struct ratbag_resolution *res;
|
||||
|
||||
/* No indvidual report rate per resolution. Loop through all of
|
||||
* them and update. */
|
||||
ratbag_profile_for_each_resolution(profile, res) {
|
||||
if (res->hz != hz) {
|
||||
res->hz = hz;
|
||||
res->dirty = true;
|
||||
profile->dirty = true;
|
||||
}
|
||||
}
|
||||
if (profile->hz != hz) {
|
||||
profile->hz = hz;
|
||||
profile->dirty = true;
|
||||
}
|
||||
|
||||
return RATBAG_SUCCESS;
|
||||
@@ -1161,27 +1143,27 @@ ratbag_resolution_get_dpi_y(struct ratbag_resolution *resolution)
|
||||
}
|
||||
|
||||
LIBRATBAG_EXPORT int
|
||||
ratbag_resolution_get_report_rate(struct ratbag_resolution *resolution)
|
||||
ratbag_profile_get_report_rate(struct ratbag_profile *profile)
|
||||
{
|
||||
return resolution->hz;
|
||||
return profile->hz;
|
||||
}
|
||||
|
||||
LIBRATBAG_EXPORT size_t
|
||||
ratbag_resolution_get_report_rate_list(struct ratbag_resolution *resolution,
|
||||
unsigned int *rates,
|
||||
size_t nrates)
|
||||
ratbag_profile_get_report_rate_list(struct ratbag_profile *profile,
|
||||
unsigned int *rates,
|
||||
size_t nrates)
|
||||
{
|
||||
_Static_assert(sizeof(*rates) == sizeof(*resolution->rates), "type mismatch");
|
||||
_Static_assert(sizeof(*rates) == sizeof(*profile->rates), "type mismatch");
|
||||
|
||||
assert(nrates > 0);
|
||||
|
||||
if (resolution->nrates == 0)
|
||||
if (profile->nrates == 0)
|
||||
return 0;
|
||||
|
||||
memcpy(rates, resolution->rates,
|
||||
sizeof(unsigned int) * min(nrates, resolution->nrates));
|
||||
memcpy(rates, profile->rates,
|
||||
sizeof(unsigned int) * min(nrates, profile->nrates));
|
||||
|
||||
return resolution->nrates;
|
||||
return profile->nrates;
|
||||
}
|
||||
|
||||
LIBRATBAG_EXPORT bool
|
||||
|
||||
116
src/libratbag.h
116
src/libratbag.h
@@ -685,6 +685,61 @@ ratbag_profile_is_active(struct ratbag_profile *profile);
|
||||
enum ratbag_error_code
|
||||
ratbag_profile_set_active(struct ratbag_profile *profile);
|
||||
|
||||
/**
|
||||
* @ingroup profile
|
||||
*
|
||||
* Set the report rate in Hz for the profile.
|
||||
*
|
||||
* A value of 0 hz disables the mode.
|
||||
*
|
||||
* If the profile mode is the currently active profile,
|
||||
* the change takes effect immediately.
|
||||
*
|
||||
* @param profile A previously initialized ratbag profile
|
||||
* @param hz Set to the report rate in Hz, may be 0
|
||||
*
|
||||
* @return zero on success or an error code on failure
|
||||
*/
|
||||
enum ratbag_error_code
|
||||
ratbag_profile_set_report_rate(struct ratbag_profile *profile,
|
||||
unsigned int hz);
|
||||
|
||||
/**
|
||||
* @ingroup profile
|
||||
*
|
||||
* Get the report rate in Hz for the profile.
|
||||
*
|
||||
* @param profile A previously initialized ratbag profile
|
||||
*
|
||||
* @return The report rate for this profile in Hz
|
||||
*/
|
||||
int
|
||||
ratbag_profile_get_report_rate(struct ratbag_profile *profile);
|
||||
|
||||
/**
|
||||
* @ingroup profile
|
||||
*
|
||||
* Get the number of report rates in Hz available for this profile.
|
||||
* The list of report rates is sorted in ascending order but may be filtered
|
||||
* by libratbag and does not necessarily reflect all report rates supported by
|
||||
* the physical device.
|
||||
*
|
||||
* This function writes at most nrates values but returns the number of
|
||||
* report rates available on this resolution. In other words, if it returns a
|
||||
* number larger than nrates, call it again with an array the size of the
|
||||
* return value.
|
||||
*
|
||||
* @param[out] rates Set to the supported report rates in ascending order
|
||||
* @param[in] nrates The number of elements in resolutions
|
||||
*
|
||||
* @return The number of valid items in rates. If the returned value
|
||||
* is larger than nrates, the list was truncated.
|
||||
*/
|
||||
size_t
|
||||
ratbag_profile_get_report_rate_list(struct ratbag_profile *profile,
|
||||
unsigned int *rates,
|
||||
size_t nrates);
|
||||
|
||||
/**
|
||||
* @ingroup profile
|
||||
*
|
||||
@@ -913,67 +968,6 @@ ratbag_resolution_get_dpi_x(struct ratbag_resolution *resolution);
|
||||
int
|
||||
ratbag_resolution_get_dpi_y(struct ratbag_resolution *resolution);
|
||||
|
||||
/**
|
||||
* @ingroup resolution
|
||||
*
|
||||
* Set the report rate in Hz for the resolution mode.
|
||||
*
|
||||
* A value of 0 hz disables the mode.
|
||||
*
|
||||
* If the resolution mode is the currently active mode and the profile is
|
||||
* the currently active profile, the change takes effect immediately.
|
||||
*
|
||||
* If the resolution does not have the @ref
|
||||
* RATBAG_RESOLUTION_CAP_INDIVIDUAL_REPORT_RATE capability, changing the
|
||||
* report rate on one resolution changes the report rate for all resolutions
|
||||
* in this profile.
|
||||
*
|
||||
* @param resolution A previously initialized ratbag resolution
|
||||
* @param hz Set to the report rate in Hz, may be 0
|
||||
*
|
||||
* @return zero on success or an error code on failure
|
||||
*/
|
||||
enum ratbag_error_code
|
||||
ratbag_resolution_set_report_rate(struct ratbag_resolution *resolution,
|
||||
unsigned int hz);
|
||||
|
||||
/**
|
||||
* @ingroup resolution
|
||||
*
|
||||
* Get the report rate in Hz for the resolution mode.
|
||||
*
|
||||
* A value of 0 hz indicates the mode is disabled.
|
||||
*
|
||||
* @param resolution A previously initialized ratbag resolution
|
||||
*
|
||||
* @return The report rate for this resolution in Hz
|
||||
*/
|
||||
int
|
||||
ratbag_resolution_get_report_rate(struct ratbag_resolution *resolution);
|
||||
|
||||
/**
|
||||
* @ingroup resolution
|
||||
*
|
||||
* Get the number of report rates in Hz available for this resolution.
|
||||
* The list of report rates is sorted in ascending order but may be filtered
|
||||
* by libratbag and does not necessarily reflect all report rates supported by
|
||||
* the physical device.
|
||||
*
|
||||
* This function writes at most nrates values but returns the number of
|
||||
* report rates available on this resolution. In other words, if it returns a
|
||||
* number larger than nrates, call it again with an array the size of the
|
||||
* return value.
|
||||
*
|
||||
* @param[out] rates Set to the supported report rates in ascending order
|
||||
* @param[in] nrates The number of elements in resolutions
|
||||
*
|
||||
* @return The number of valid items in rates. If the returned value
|
||||
* is larger than nrates, the list was truncated.
|
||||
*/
|
||||
size_t
|
||||
ratbag_resolution_get_report_rate_list(struct ratbag_resolution *resolution,
|
||||
unsigned int *rates,
|
||||
size_t nrates);
|
||||
/**
|
||||
* @ingroup resolution
|
||||
*
|
||||
|
||||
@@ -59,11 +59,10 @@ const struct ratbag_test_device sane_device = {
|
||||
.profiles = {
|
||||
{
|
||||
.resolutions = {
|
||||
{ .xres = 100, .yres = 200, .hz = 1000,
|
||||
.dpi_min = 100, .dpi_max = 5000,
|
||||
.report_rates = { 500, 1000 } },
|
||||
{ .xres = 200, .yres = 300, .hz = 1000 },
|
||||
{ .xres = 300, .yres = 400, .hz = 1000 },
|
||||
{ .xres = 100, .yres = 200,
|
||||
.dpi_min = 100, .dpi_max = 5000 },
|
||||
{ .xres = 200, .yres = 300 },
|
||||
{ .xres = 300, .yres = 400 },
|
||||
},
|
||||
.leds = {
|
||||
{ .type = RATBAG_LED_TYPE_SIDE, },
|
||||
@@ -71,21 +70,24 @@ const struct ratbag_test_device sane_device = {
|
||||
},
|
||||
.active = true,
|
||||
.dflt = false,
|
||||
.report_rates = { 500, 1000 },
|
||||
.hz = 1000,
|
||||
},
|
||||
{
|
||||
.resolutions = {
|
||||
{ .xres = 1100, .yres = 1200, .hz = 2000 },
|
||||
{ .xres = 1200, .yres = 1300, .hz = 2000 },
|
||||
{ .xres = 1300, .yres = 1400, .hz = 2000 },
|
||||
{ .xres = 1100, .yres = 1200 },
|
||||
{ .xres = 1200, .yres = 1300 },
|
||||
{ .xres = 1300, .yres = 1400 },
|
||||
},
|
||||
.active = false,
|
||||
.dflt = true,
|
||||
.hz = 2000,
|
||||
},
|
||||
{
|
||||
.resolutions = {
|
||||
{ .xres = 2100, .yres = 2200, .hz = 3000 },
|
||||
{ .xres = 2200, .yres = 2300, .hz = 3000 },
|
||||
{ .xres = 2300, .yres = 2400, .hz = 3000 },
|
||||
{ .xres = 2100, .yres = 2200 },
|
||||
{ .xres = 2200, .yres = 2300 },
|
||||
{ .xres = 2300, .yres = 2400 },
|
||||
},
|
||||
.leds = {
|
||||
{
|
||||
@@ -103,6 +105,7 @@ const struct ratbag_test_device sane_device = {
|
||||
},
|
||||
.active = false,
|
||||
.dflt = false,
|
||||
.hz = 3000,
|
||||
},
|
||||
},
|
||||
.destroyed = device_destroyed,
|
||||
@@ -356,27 +359,30 @@ START_TEST(device_resolutions)
|
||||
.profiles = {
|
||||
{
|
||||
.resolutions = {
|
||||
{ .xres = 100, .yres = 200, .hz = 1000,
|
||||
.dpi_min = 50, .dpi_max = 5000,
|
||||
.report_rates = { 500, 1000 } },
|
||||
{ .xres = 200, .yres = 300, .hz = 1000, .active = true },
|
||||
{ .xres = 300, .yres = 400, .hz = 1000 },
|
||||
{ .xres = 100, .yres = 200,
|
||||
.dpi_min = 50, .dpi_max = 5000 },
|
||||
{ .xres = 200, .yres = 300, .active = true },
|
||||
{ .xres = 300, .yres = 400 },
|
||||
},
|
||||
.active = true,
|
||||
.hz = 1000,
|
||||
.report_rates = { 500, 1000 },
|
||||
},
|
||||
{
|
||||
.resolutions = {
|
||||
{ .xres = 1100, .yres = 1200, .hz = 2000 },
|
||||
{ .xres = 1200, .yres = 1300, .hz = 2000, .active = true },
|
||||
{ .xres = 1300, .yres = 1400, .hz = 2000 },
|
||||
{ .xres = 1100, .yres = 1200 },
|
||||
{ .xres = 1200, .yres = 1300, .active = true },
|
||||
{ .xres = 1300, .yres = 1400 },
|
||||
},
|
||||
.hz = 2000,
|
||||
},
|
||||
{
|
||||
.resolutions = {
|
||||
{ .xres = 2100, .yres = 2200, .hz = 3000 },
|
||||
{ .xres = 2200, .yres = 2300, .hz = 3000, .active = true },
|
||||
{ .xres = 2300, .yres = 2400, .hz = 3000 },
|
||||
{ .xres = 2100, .yres = 2200 },
|
||||
{ .xres = 2200, .yres = 2300, .active = true },
|
||||
{ .xres = 2300, .yres = 2400 },
|
||||
},
|
||||
.hz = 3000,
|
||||
},
|
||||
},
|
||||
.destroyed = device_destroyed,
|
||||
@@ -392,6 +398,8 @@ START_TEST(device_resolutions)
|
||||
nresolutions = ratbag_profile_get_num_resolutions(p);
|
||||
ck_assert_int_eq(nresolutions, 3);
|
||||
|
||||
rate = ratbag_profile_get_report_rate(p);
|
||||
|
||||
for (j = 0; j < nresolutions; j++) {
|
||||
unsigned int dpis[200];
|
||||
int ndpis = ARRAY_LENGTH(dpis);
|
||||
@@ -400,7 +408,6 @@ START_TEST(device_resolutions)
|
||||
|
||||
xres = ratbag_resolution_get_dpi_x(res);
|
||||
yres = ratbag_resolution_get_dpi_y(res);
|
||||
rate = ratbag_resolution_get_report_rate(res);
|
||||
is_active = ratbag_resolution_is_active(res);
|
||||
|
||||
ndpis = ratbag_resolution_get_dpi_list(res, dpis, ndpis);
|
||||
|
||||
@@ -362,6 +362,26 @@ class RatbagdProfile(metaclass=MetaRatbag):
|
||||
@param enabled The new state, as boolean"""
|
||||
libratbag.ratbag_profile_set_enabled(self._profile, enabled)
|
||||
|
||||
@property
|
||||
def report_rate(self):
|
||||
"""The report rate in Hz."""
|
||||
return libratbag.ratbag_profile_get_report_rate(self._profile)
|
||||
|
||||
@report_rate.setter
|
||||
def report_rate(self, rate):
|
||||
"""Set the report rate in Hz.
|
||||
|
||||
@param rate The new report rate, as int
|
||||
"""
|
||||
libratbag.ratbag_profile_set_report_rate(self._profile, rate)
|
||||
|
||||
@property
|
||||
def report_rates(self):
|
||||
"""The list of supported report rates"""
|
||||
rates = [0 for i in range(300)]
|
||||
n = libratbag.ratbag_resolution_get_report_rate_list(self._profile, rates)
|
||||
return rates[:n]
|
||||
|
||||
@property
|
||||
def resolutions(self):
|
||||
"""A list of RatbagdResolution objects with this profile's resolutions.
|
||||
@@ -454,19 +474,6 @@ class RatbagdResolution(metaclass=MetaRatbag):
|
||||
else:
|
||||
libratbag.ratbag_resolution_set_dpi(self._res, res[0])
|
||||
|
||||
@property
|
||||
def report_rate(self):
|
||||
"""The report rate in Hz."""
|
||||
return libratbag.ratbag_resolution_get_report_rate(self._res)
|
||||
|
||||
@report_rate.setter
|
||||
def report_rate(self, rate):
|
||||
"""Set the report rate in Hz.
|
||||
|
||||
@param rate The new report rate, as int
|
||||
"""
|
||||
libratbag.ratbag_resolution_set_report_rate(self._res, rate)
|
||||
|
||||
@property
|
||||
def resolutions(self):
|
||||
"""The list of supported DPI values"""
|
||||
@@ -474,13 +481,6 @@ class RatbagdResolution(metaclass=MetaRatbag):
|
||||
n = libratbag.ratbag_resolution_get_dpi_list(self._res, dpis)
|
||||
return dpis[:n]
|
||||
|
||||
@property
|
||||
def report_rates(self):
|
||||
"""The list of supported report rates"""
|
||||
rates = [0 for i in range(300)]
|
||||
n = libratbag.ratbag_resolution_get_report_rate_list(self._res, rates)
|
||||
return rates[:n]
|
||||
|
||||
@property
|
||||
def is_active(self):
|
||||
"""True if this is the currently active resolution, False
|
||||
|
||||
@@ -194,12 +194,11 @@ def print_resolution(d, p, r, level):
|
||||
else:
|
||||
dpi = "{}".format(r.resolution[0])
|
||||
|
||||
print(" " * level + "{}: {}dpi @ {}Hz{}{}".format(r.index,
|
||||
dpi,
|
||||
r.report_rate,
|
||||
" (active)" if r.is_active else "",
|
||||
" (default)" if r.is_default else "",
|
||||
))
|
||||
print(" " * level + "{}: {}dpi{}{}".format(r.index,
|
||||
dpi,
|
||||
" (active)" if r.is_active else "",
|
||||
" (default)" if r.is_default else "",
|
||||
))
|
||||
|
||||
|
||||
def print_profile(d, p, level):
|
||||
@@ -208,6 +207,7 @@ def print_profile(d, p, level):
|
||||
" (active)" if p.is_active else ""))
|
||||
if p.enabled:
|
||||
print(" " * level + "Name: {}".format(p.name or 'n/a'))
|
||||
print(" " * level + "Report Rate: {}Hz".format(p.report_rate))
|
||||
print(" " * level + "Resolutions:")
|
||||
for r in p.resolutions:
|
||||
print_resolution(d, p, r, level + 2)
|
||||
@@ -405,19 +405,19 @@ def func_dpi_set(r, args):
|
||||
|
||||
|
||||
def func_report_rate_get(r, args):
|
||||
r, p, d = find_resolution(r, args)
|
||||
print(r.report_rate)
|
||||
p, d = find_profile(r, args)
|
||||
print(p.report_rate)
|
||||
|
||||
|
||||
def func_report_rate_get_all(r, args):
|
||||
r, p, d = find_resolution(r, args)
|
||||
rates = r.report_rates
|
||||
p, d = find_profile(r, args)
|
||||
rates = p.report_rates
|
||||
print(" ".join([str(x) for x in rates]))
|
||||
|
||||
|
||||
def func_report_rate_set(r, args):
|
||||
r, p, d = find_resolution(r, args)
|
||||
r.report_rate = args.rate_n
|
||||
p, d = find_profile(r, args)
|
||||
p.report_rate = args.rate_n
|
||||
|
||||
|
||||
def func_resolution_get(r, args):
|
||||
@@ -817,10 +817,6 @@ active profile if none is given.""",
|
||||
of_type: link,
|
||||
dest: 'dpi',
|
||||
},
|
||||
{
|
||||
of_type: link,
|
||||
dest: 'rate',
|
||||
},
|
||||
],
|
||||
},
|
||||
},
|
||||
@@ -868,8 +864,7 @@ active resolution of the active profile if none are given.""",
|
||||
name: 'rate',
|
||||
help_str: """Access report rate information
|
||||
|
||||
Rate commands work on the given profile and resolution, or on the
|
||||
active resolution of the active profile if none are given.""",
|
||||
Rate commands work on the given profile, or on the active profile if none is given.""",
|
||||
tag: 'rate',
|
||||
group: 'Rate',
|
||||
switch: [
|
||||
|
||||
@@ -259,14 +259,14 @@ class TestRatbagCtlResolution(TestRatbagCtl):
|
||||
|
||||
def test_resolution_n_get(self):
|
||||
r = self.launch_good_test("test_device resolution 1 get")
|
||||
self.assertEqual(r, "1: 1200x1300dpi @ 2000Hz (default)")
|
||||
self.assertEqual(r, "1: 1200x1300dpi (default)")
|
||||
self.launch_fail_test("test_device resolution 10 get")
|
||||
self.launch_fail_test("test_device resolution 1 get X")
|
||||
self.launch_fail_test("resolution 1 get X")
|
||||
|
||||
def test_profile_resolution(self):
|
||||
r = self.launch_good_test("test_device profile 2 resolution 2 get")
|
||||
self.assertEqual(r, "2: 2300x2400dpi @ 3000Hz")
|
||||
self.assertEqual(r, "2: 2300x2400dpi")
|
||||
|
||||
def test_resolution_default_get(self):
|
||||
command = "resolution default get"
|
||||
@@ -393,13 +393,14 @@ class TestRatbagCtlReportRate(TestRatbagCtl):
|
||||
self.launch_fail_test("test_device " + command + " 100 X")
|
||||
|
||||
def test_prefix_rate(self):
|
||||
r = self.launch_good_test("test_device rate get")
|
||||
self.assertEqual(int(r), 1000)
|
||||
r = self.launch_good_test("test_device profile 1 rate get")
|
||||
self.assertEqual(int(r), 2000)
|
||||
r = self.launch_good_test("test_device profile 1 resolution 1 rate get")
|
||||
self.assertEqual(int(r), 2000)
|
||||
r = self.launch_good_test("test_device resolution 2 rate get")
|
||||
self.assertEqual(int(r), 1000)
|
||||
r = self.launch_good_test("test_device profile 2 rate get")
|
||||
self.assertEqual(int(r), 3000)
|
||||
self.launch_fail_test("test_device profile 1 profile 1 rate get")
|
||||
self.launch_fail_test("test_device profile 1 resolution 0 rate get")
|
||||
self.launch_fail_test("test_device profile 1 resolution 1 resolution 2 rate get")
|
||||
|
||||
|
||||
|
||||
@@ -449,6 +449,24 @@ class RatbagdProfile(_RatbagdDBus):
|
||||
@param enabled The new state, as boolean"""
|
||||
self._set_dbus_property("Enabled", "b", enabled)
|
||||
|
||||
@GObject.Property
|
||||
def report_rate(self):
|
||||
"""The report rate in Hz."""
|
||||
return self._get_dbus_property("ReportRate")
|
||||
|
||||
@report_rate.setter
|
||||
def report_rate(self, rate):
|
||||
"""Set the report rate in Hz.
|
||||
|
||||
@param rate The new report rate, as int
|
||||
"""
|
||||
self._set_dbus_property("ReportRate", "u", rate)
|
||||
|
||||
@GObject.Property
|
||||
def report_rates(self):
|
||||
"""The list of supported report rates"""
|
||||
return self._get_dbus_property("ReportRates") or []
|
||||
|
||||
@GObject.Property
|
||||
def resolutions(self):
|
||||
"""A list of RatbagdResolution objects with this profile's resolutions.
|
||||
@@ -497,8 +515,7 @@ class RatbagdProfile(_RatbagdDBus):
|
||||
class RatbagdResolution(_RatbagdDBus):
|
||||
"""Represents a ratbagd resolution."""
|
||||
|
||||
CAP_INDIVIDUAL_REPORT_RATE = 1
|
||||
CAP_SEPARATE_XY_RESOLUTION = 2
|
||||
CAP_SEPARATE_XY_RESOLUTION = 1
|
||||
|
||||
def __init__(self, object_path):
|
||||
_RatbagdDBus.__init__(self, "Resolution", object_path)
|
||||
@@ -557,29 +574,11 @@ class RatbagdResolution(_RatbagdDBus):
|
||||
variant = GLib.Variant('(uu)', resolution);
|
||||
self._set_dbus_property("Resolution", "v", variant)
|
||||
|
||||
@GObject.Property
|
||||
def report_rate(self):
|
||||
"""The report rate in Hz."""
|
||||
return self._get_dbus_property("ReportRate")
|
||||
|
||||
@report_rate.setter
|
||||
def report_rate(self, rate):
|
||||
"""Set the report rate in Hz.
|
||||
|
||||
@param rate The new report rate, as int
|
||||
"""
|
||||
self._set_dbus_property("ReportRate", "u", rate)
|
||||
|
||||
@GObject.Property
|
||||
def resolutions(self):
|
||||
"""The list of supported DPI values"""
|
||||
return self._get_dbus_property("Resolutions") or []
|
||||
|
||||
@GObject.Property
|
||||
def report_rates(self):
|
||||
"""The list of supported report rates"""
|
||||
return self._get_dbus_property("ReportRates") or []
|
||||
|
||||
@GObject.Property
|
||||
def is_active(self):
|
||||
"""True if this is the currently active resolution, False
|
||||
|
||||
Reference in New Issue
Block a user