Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature: transform the display #43

Closed
wants to merge 11 commits into from
11 changes: 11 additions & 0 deletions inc/cfg.h
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,11 @@ struct UserMode {
bool warned_no_mode;
};

struct UserTransform {
char *name_desc;
int32_t transform;
alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
};

struct Cfg {
char *dir_path;
char *file_path;
Expand All @@ -66,6 +71,7 @@ struct Cfg {
enum AutoScale auto_scale;
struct SList *user_scales;
struct SList *user_modes;
struct SList *user_transform;
struct SList *max_preferred_refresh_name_desc;
struct SList *disabled_name_desc;
enum LogThreshold log_threshold;
Expand All @@ -78,6 +84,7 @@ enum CfgElement {
AUTO_SCALE,
SCALE,
MODE,
TRANSFORM,
LAPTOP_DISPLAY_PREFIX,
MAX_PREFERRED_REFRESH,
LOG_THRESHOLD,
Expand All @@ -102,10 +109,14 @@ struct Cfg *cfg_default(void);

struct UserMode *cfg_user_mode_default(void);

struct UserTransform *cfg_user_transform_default(void);

void cfg_user_scale_free(void *user_scale);

void cfg_user_mode_free(void *user_mode);

void cfg_user_transform_free(void *user_transform);

void cfg_destroy(void);

void cfg_free(struct Cfg *cfg);
Expand Down
3 changes: 3 additions & 0 deletions inc/head.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,9 @@ struct HeadState {
// layout coords
int32_t x;
int32_t y;

// Display rotataion
enum wl_output_transform transform;
};

struct Head {
Expand Down
129 changes: 129 additions & 0 deletions src/cfg.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,21 @@ bool equal_user_mode_name(const void *value, const void *data) {
return strcasecmp(lhs->name_desc, rhs->name_desc) == 0;
}

bool equal_user_transform_name(const void *value, const void *data) {
if (!value || !data) {
return false;
}

struct UserTransform *lhs = (struct UserTransform*)value;
struct UserTransform *rhs = (struct UserTransform*)data;

if (!lhs->name_desc || !rhs->name_desc) {
return false;
}

return strcasecmp(lhs->name_desc, rhs->name_desc) == 0;
}

bool equal_user_scale_name(const void *value, const void *data) {
if (!value || !data) {
return false;
Expand Down Expand Up @@ -164,6 +179,25 @@ bool equal_user_mode(const void *value, const void *data) {
return true;
}

bool equal_user_transform(const void *value, const void *data) {
if (!value || !data) {
return false;
}

struct UserTransform *lhs = (struct UserTransform*)value;
struct UserTransform *rhs = (struct UserTransform*)data;

alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
if (!lhs->name_desc || !rhs->name_desc) {
return false;
}

if (!lhs->transform || !rhs->transform) {
return false;
}

return true;
}

bool invalid_user_scale(const void *value, const void *data) {
if (!value) {
return true;
Expand Down Expand Up @@ -275,6 +309,15 @@ struct Cfg *clone_cfg(struct Cfg *from) {
slist_append(&to->user_modes, to_user_mode);
}

// TRANSFORM
for (i = from->user_transform; i; i = i->nex) {
struct UserTransform *from_user_transform = (struct UserTransform*)i->val;
struct UserTransform *to_user_transform = (struct UserTransform*)calloc(1, sizeof(struct UserTransform));
to_user_transform->name_desc = strdup(from_user_transform->name_desc);
to_user_transform->transform = from_user_transform->transform;
slist_append(&to->user_transform, to_user_transform);
}

// LAPTOP_DISPLAY_PREFIX
if (from->laptop_display_prefix) {
to->laptop_display_prefix = strdup(from->laptop_display_prefix);
Expand Down Expand Up @@ -333,6 +376,11 @@ bool equal_cfg(struct Cfg *a, struct Cfg* b) {
return false;
}

// TRANSFORM
if (!slist_equal(a->user_transform, b->user_transform, equal_user_transform)) {
return false;
}

// LAPTOP_DISPLAY_PREFIX
char *al = a->laptop_display_prefix;
char *bl = b->laptop_display_prefix;
Expand Down Expand Up @@ -378,6 +426,14 @@ struct UserMode *cfg_user_mode_default() {
return user_mode;
}

struct UserTransform *cfg_user_transform_default() {
struct UserTransform *user_transform = (struct UserTransform*)calloc(1, sizeof(struct UserTransform));

user_transform->transform = WL_OUTPUT_TRANSFORM_NORMAL;

return user_transform;
}

bool resolve_paths(struct Cfg *cfg, const char *prefix, const char *suffix) {
if (!cfg)
return false;
Expand Down Expand Up @@ -516,6 +572,24 @@ void cfg_parse_node(struct Cfg *cfg, YAML::Node &node) {
}
}

if (node["TRANSFORM"]) {
for (const auto &transform : node["TRANSFORM"]) {
struct UserTransform *user_transform = cfg_user_transform_default();

if (!parse_node_val_string(transform, "NAME_DESC", &user_transform->name_desc, "TRANSFORM", "")) {
cfg_user_mode_free(user_transform);
alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
continue;
}
if (!parse_node_val_int(transform, "DEGREE", &user_transform->transform, "TRANSFORM", user_transform->name_desc)) {
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We will need to be more strict about the value here: only a few values are applicable, and we need to account for flipped.

We can use a similar scheme to sway:

Can be one of "90", "180", "270" for rotation; or "FLIPPED", "FLIPPED-90", "FLIPPED-180", "FLIPPED-270" to apply a rotation and flip, or "NORMAL" to apply no transform.

convert.c methods similar to auto_scale_val and auto_scale_name will need to be created to perform that validation and conversion.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need time to figure out this one. Not getting enough time from work :(

Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is no rush

cfg_user_transform_free(user_transform);
continue;
}

slist_remove_all_free(&cfg->user_transform, equal_user_transform_name, user_transform, cfg_user_transform_free);
slist_append(&cfg->user_transform, user_transform);
}
}

if (node["MAX_PREFERRED_REFRESH"]) {
const auto &name_desc = node["MAX_PREFERRED_REFRESH"];
for (const auto &name_desc : name_desc) {
Expand Down Expand Up @@ -612,6 +686,22 @@ void cfg_emit(YAML::Emitter &e, struct Cfg *cfg) {
e << YAML::EndSeq;
}

if (cfg->user_transform) {
e << YAML::Key << "TRANSFORM";
e << YAML::BeginSeq;
for (struct SList *i = cfg->user_modes; i; i = i->nex) {
alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
struct UserTransform *user_transform = (struct UserTransform*)i->val;
e << YAML::BeginMap;
e << YAML::Key << "NAME_DESC";
e << YAML::Value << user_transform->name_desc;

e << YAML::Key << "DEGREE";
e << YAML::Value << user_transform->transform;
e << YAML::EndMap;
}
e << YAML::EndSeq;
}

if (cfg->laptop_display_prefix) {
e << YAML::Key << "LAPTOP_DISPLAY_PREFIX";
e << YAML::Value << cfg->laptop_display_prefix;
Expand Down Expand Up @@ -690,6 +780,12 @@ void validate_warn(struct Cfg *cfg) {
struct UserMode *user_mode = (struct UserMode*)i->val;
warn_short_name_desc(user_mode->name_desc, "MODE");
}
for (i = cfg->user_transform; i; i = i->nex) {
if (!i->val)
continue;
struct UserTransform *user_transform = (struct UserTransform*) i->val;
warn_short_name_desc(user_transform->name_desc, "TRANSFORM");
}
for (i = cfg->order_name_desc; i; i = i->nex) {
if (!i->val)
continue;
Expand Down Expand Up @@ -786,6 +882,19 @@ struct Cfg *merge_set(struct Cfg *to, struct Cfg *from) {
merged_user_mode->warned_no_mode = set_user_mode->warned_no_mode;
}

// TRANSFORM
struct UserTransform *set_user_transform = NULL;
struct UserTransform *merged_user_transform = NULL;
for (i = from->user_transform; i; i = i->nex) {
set_user_transform = (struct UserTransform*)i->val;
if (!(merged_user_transform = (struct UserTransform*)slist_find_equal_val(merged->user_transform, equal_user_transform_name, set_user_transform))) {
merged_user_transform = cfg_user_transform_default();
merged_user_transform->name_desc = strdup(set_user_transform->name_desc);
slist_append(&merged->user_modes, merged_user_transform);
alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
}
merged_user_transform->transform = set_user_transform->transform;
}

// DISABLED
for (i = from->disabled_name_desc; i; i = i->nex) {
if (!slist_find_equal(merged->disabled_name_desc, slist_equal_strcasecmp, i->val)) {
Expand Down Expand Up @@ -815,6 +924,11 @@ struct Cfg *merge_del(struct Cfg *to, struct Cfg *from) {
slist_remove_all_free(&merged->user_modes, equal_user_mode_name, i->val, cfg_user_mode_free);
}

// TRANSFORM
for (i = from->user_transform; i; i = i->nex) {
slist_remove_all_free(&merged->user_transform, equal_user_transform_name, i->val, cfg_user_transform_free);
}

// DISABLED
for (i = from->disabled_name_desc; i; i = i->nex) {
slist_remove_all_free(&merged->disabled_name_desc, slist_equal_strcasecmp, i->val, NULL);
Expand Down Expand Up @@ -982,6 +1096,11 @@ void cfg_free(struct Cfg *cfg) {
}
slist_free(&cfg->user_modes);

for (struct SList *i = cfg->user_transform; i; i = i->nex) {
cfg_user_transform_free((struct UserTransform*)i->val);
}
slist_free(&cfg->user_transform);

for (struct SList *i = cfg->max_preferred_refresh_name_desc; i; i = i->nex) {
free(i->val);
}
Expand Down Expand Up @@ -1021,3 +1140,13 @@ void cfg_user_mode_free(void *data) {
free(user_mode);
}

void cfg_user_transform_free(void *data) {
struct UserTransform *user_transform = (struct UserTransform*)data;

if (!user_transform)
return;

free(user_transform->name_desc);
free(user_transform);
}

13 changes: 11 additions & 2 deletions src/head.c
Original file line number Diff line number Diff line change
Expand Up @@ -182,12 +182,21 @@ void head_scaled_dimensions(struct Head *head) {
return;
}

if (head->transform % 2 == 0) {
if (head->transform == WL_OUTPUT_TRANSFORM_NORMAL ||
alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
head->transform == WL_OUTPUT_TRANSFORM_180) {

head->scaled.width = head->desired.mode->width;
head->scaled.height = head->desired.mode->height;
} else {

} else if (head->transform == WL_OUTPUT_TRANSFORM_90 ||
head->transform == WL_OUTPUT_TRANSFORM_270) {

head->scaled.width = head->desired.mode->height;
head->scaled.height = head->desired.mode->width;

} else {
head->scaled.width = head->desired.mode->width;
head->scaled.height = head->desired.mode->height;
}

head->scaled.height = (int32_t)((double)head->scaled.height * 256 / head->desired.scale + 0.5);
Expand Down
10 changes: 10 additions & 0 deletions src/layout.c
Original file line number Diff line number Diff line change
Expand Up @@ -183,6 +183,14 @@ void desire_scale(struct Head *head) {
}
}

void desire_transform(struct Head *head) {
alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
if (!head->desired.enabled)
return;

// enable transfomation
head->desired.transform = WL_OUTPUT_TRANSFORM_180;
}

void desire(void) {

for (struct SList *i = heads; i; i = i->nex) {
Expand All @@ -193,6 +201,7 @@ void desire(void) {
desire_enabled(head);
desire_mode(head);
desire_scale(head);
desire_transform(head);

head_scaled_dimensions(head);
}
Expand Down Expand Up @@ -240,6 +249,7 @@ void apply(void) {
head->zwlr_config_head = zwlr_output_configuration_v1_enable_head(zwlr_config, head->zwlr_head);
zwlr_output_configuration_head_v1_set_scale(head->zwlr_config_head, head->desired.scale);
zwlr_output_configuration_head_v1_set_position(head->zwlr_config_head, head->desired.x, head->desired.y);
zwlr_output_configuration_head_v1_set_transform(head->zwlr_config_head, head->desired.transform);
alex-courtis marked this conversation as resolved.
Show resolved Hide resolved
} else {
zwlr_output_configuration_v1_disable_head(zwlr_config, head->zwlr_head);
}
Expand Down
2 changes: 1 addition & 1 deletion src/listener_head.c
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ static void transform(void *data,
int32_t transform) {
struct Head *head = data;

head->transform = transform;
head->current.transform = transform;
}

static void scale(void *data,
Expand Down