Skip to content

Commit

Permalink
layout_description uses string_replace
Browse files Browse the repository at this point in the history
  • Loading branch information
alex-courtis committed Dec 9, 2024
1 parent 7f47ae5 commit 7c8cc9e
Show file tree
Hide file tree
Showing 2 changed files with 55 additions and 98 deletions.
123 changes: 35 additions & 88 deletions src/layout.c
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
#include <stdint.h>
#include <stdbool.h>
#include <stdio.h>
#include <string.h>

#include "river-layout-v3.h"

Expand All @@ -10,6 +11,7 @@
#include "slist.h"
#include "tag.h"
#include "cfg.h"
#include "util.h"

#include "layout.h"

Expand Down Expand Up @@ -51,6 +53,9 @@ const char *layout_image(const struct Demand* const demand, const struct Tag* co
snprintf(desc, sizeof(desc), "├─┤ ├─┤");
}
break;
default:
return NULL;
break;
}

return desc;
Expand All @@ -60,108 +65,50 @@ const char *layout_description(const struct Demand* const demand, const struct T
if (!demand || !tag)
return "";

char name[8] = "";
switch (tag->layout_cur) {
case LEFT:
snprintf(name, sizeof(name), "left");
break;
case RIGHT:
snprintf(name, sizeof(name), "right");
break;
case TOP:
snprintf(name, sizeof(name), "top");
break;
case BOTTOM:
snprintf(name, sizeof(name), "bottom");
break;
case WIDE:
snprintf(name, sizeof(name), "wide");
break;
case MONOCLE:
snprintf(name, sizeof(name), "monocle");
break;
}
double ratio = 0;
unsigned int count = 0;
const char *image = layout_image(demand, tag);
char count[10] = "{c}";
char ratio[10] = "{r}";
switch(tag->layout_cur) {
case LEFT:
case RIGHT:
case TOP:
case BOTTOM:
count = tag->count_master;
ratio = tag->ratio_master;
snprintf(count, 10, "%d", tag->count_master);
snprintf(ratio, 10, "%g", tag->ratio_master);
break;
case WIDE:
count = tag->count_wide_left;
ratio = tag->ratio_wide;
snprintf(count, 10, "%d", tag->count_wide_left);
snprintf(ratio, 10, "%g", tag->ratio_wide);
break;
case MONOCLE:
count = demand->view_count;
ratio = 1.0;
snprintf(count, 10, "%d", demand->view_count);
snprintf(ratio, 10, "%g", 1.0);
break;
default:
break;
}

static char desc[LAYOUT_FORMAT_LEN+5];
int j = 0;
int escaped = 0;
bool in_brackets = false;
for (int i = 0; cfg->layout_format[i] != '\0'; i++) {
if (escaped > 0) {
switch (cfg->layout_format[i]) {
case 'n':
desc[j] = '\n';
break;
case 't':
desc[j] = '\t';
break;
case 'r':
desc[j] = '\r';
break;
case 'v':
desc[j] = '\v';
break;
case '{':
desc[j] = '{';
break;
case '}':
desc[j] = '}';
break;
default:
break;
}
j++;
} else if (cfg->layout_format[i] == '{')
in_brackets = true;
else if (cfg->layout_format[i] == '}' && in_brackets) {
switch (cfg->layout_format[i-1]) {
case RATIO:
j += snprintf(desc+j, sizeof(desc)-j, "%g", ratio);
break;
case COUNT:
j += snprintf(desc+j, sizeof(desc)-j, "%u", count);
break;
case LAYOUT:
j += snprintf(desc+j, sizeof(desc)-j, "%s", image);
break;
case NAME:
j += snprintf(desc+j, sizeof(desc)-j, "%s", name);
}
in_brackets = false;
} else if (cfg->layout_format[i] == '\\' && !in_brackets)
escaped = 2;
else if (!in_brackets) {
desc[j] = cfg->layout_format[i];
j++;
}
const char *image = layout_image(demand, tag);
const char *name = layout_name(tag->layout_cur);

escaped -= 1;
if (escaped < 0)
escaped = 0;
}
static char desc[LAYOUT_FORMAT_LEN + 5];

char *counted, *ratioed, *imaged, *named;
char *escaped_n, *escaped_t, *escaped_r, *escaped_v;

counted = string_replace(cfg->layout_format, "{c}", count);
ratioed = string_replace(counted, "{r}", ratio);
imaged = string_replace(ratioed, "{l}", image ? image : "{l}");
named = string_replace(imaged, "{n}", name ? name : "{n}");

escaped_n = string_replace(named, "\\n", "\n");
escaped_t = string_replace(escaped_n, "\\t", "\t");
escaped_r = string_replace(escaped_t, "\\r", "\r");
escaped_v = string_replace(escaped_r, "\\v", "\v");

strncpy(desc, escaped_v, LAYOUT_FORMAT_LEN + 5);

// terminate the string
desc[j] = '\0';
free(counted); free(ratioed); free(imaged); free(named);
free(escaped_n); free(escaped_t); free(escaped_r); free(escaped_v);

return desc;
}
Expand Down
30 changes: 20 additions & 10 deletions tst/tst-layout.c
Original file line number Diff line number Diff line change
Expand Up @@ -82,41 +82,51 @@ void layout_image__monocle(void **state) {
assert_str_equal(layout_image(&demand2, &tag), "│ 2 │");
}

void layout_image__invalid(void **state) {
struct Tag tag = { .layout_cur = 0, };

struct Demand demand1 = { .view_count = 1 };
assert_nul(layout_image(&demand1, &tag));

struct Demand demand2 = { .view_count = 2 };
assert_nul(layout_image(&demand2, &tag));
}

void layout_description_info__none(void **state) {
struct Demand demand = { 0 };
struct Tag tag = { 0 };

assert_true(cfg_set_layout_format("foo"));
assert_true(cfg_set_layout_format("{c}{l}{r}{n}"));

assert_str_equal(layout_description(&demand, &tag), "foo");
assert_str_equal(layout_description(&demand, &tag), "{c}{l}{r}{n}");
}

void layout_description_info__monocle(void **state) {
struct Demand demand = { .view_count = 9, };
struct Tag tag = { .layout_cur = MONOCLE, };

assert_true(cfg_set_layout_format("image: {l} count: {c} ratio: {r} end"));
assert_true(cfg_set_layout_format("image: {l} count: {c} ratio: {r} name: {n} end"));

// TODO #21 remove the monocle count
assert_str_equal(layout_description(&demand, &tag), "image: │ 9 │ count: 9 ratio: 1 end");
assert_str_equal(layout_description(&demand, &tag), "image: │ 9 │ count: 9 ratio: 1 name: monocle end");
}

void layout_description_info__lrtb(void **state) {
struct Demand demand = { .view_count = 9, };
struct Tag tag = { .layout_cur = LEFT, .count_master = 2, .count_wide_left = 3, .ratio_master = 0.4, .ratio_wide = 0.5, };

assert_true(cfg_set_layout_format("image: {l} count: {c} ratio: {r} end"));
assert_true(cfg_set_layout_format("image: {l} count: {c} ratio: {r} name: {n} end"));

assert_str_equal(layout_description(&demand, &tag), "image: │ ├─┤ count: 2 ratio: 0.4 end");
assert_str_equal(layout_description(&demand, &tag), "image: │ ├─┤ count: 2 ratio: 0.4 name: left end");
}

void layout_description_info__wide(void **state) {
struct Demand demand = { .view_count = 9, };
struct Tag tag = { .layout_cur = WIDE, .count_master = 2, .count_wide_left = 3, .ratio_master = 0.4, .ratio_wide = 0.5, };

assert_true(cfg_set_layout_format("image: {l} count: {c} ratio: {r} end"));
assert_true(cfg_set_layout_format("image: {l} count: {c} ratio: {r} name: {n} end"));

assert_str_equal(layout_description(&demand, &tag), "image: ├─┤ ├─┤ count: 3 ratio: 0.5 end");
assert_str_equal(layout_description(&demand, &tag), "image: ├─┤ ├─┤ count: 3 ratio: 0.5 name: wide end");
}

void layout_description_info__invalids(void **state) {
Expand All @@ -126,8 +136,7 @@ void layout_description_info__invalids(void **state) {
// manually set an invalid layout
strcpy(((struct Cfg*)cfg)->layout_format, "image: {foo} count: {c c} ratio: {rATIO} end");

// TODO #21 this is not correct; count should not be substituted
assert_str_equal(layout_description(&demand, &tag), "image: count: 3 ratio: end");
assert_str_equal(layout_description(&demand, &tag), "image: {foo} count: {c c} ratio: {rATIO} end");
}

void layout_description_info__escapes(void **state) {
Expand All @@ -147,6 +156,7 @@ int main(void) {
TEST(layout_image__bottom),
TEST(layout_image__wide),
TEST(layout_image__monocle),
TEST(layout_image__invalid),

TEST(layout_description_info__none),
TEST(layout_description_info__monocle),
Expand Down

0 comments on commit 7c8cc9e

Please sign in to comment.