/* htop - OptionItem.c (C) 2004-2011 Hisham H. Muhammad Released under the GNU GPLv2+, see the COPYING file in the source distribution for its full text. */ #include "OptionItem.h" #include #include #include #include "CRT.h" #include "Macros.h" #include "RichString.h" #include "XUtils.h" static void OptionItem_delete(Object* cast) { OptionItem* this = (OptionItem*)cast; assert (this != NULL); free(this->text); free(this); } static void CheckItem_display(const Object* cast, RichString* out) { const CheckItem* this = (const CheckItem*)cast; assert (this != NULL); RichString_writeAscii(out, CRT_colors[CHECK_BOX], "["); if (CheckItem_get(this)) { RichString_appendAscii(out, CRT_colors[CHECK_MARK], "x"); } else { RichString_appendAscii(out, CRT_colors[CHECK_MARK], " "); } RichString_appendAscii(out, CRT_colors[CHECK_BOX], "] "); RichString_appendWide(out, CRT_colors[CHECK_TEXT], this->super.text); } static void NumberItem_display(const Object* cast, RichString* out) { const NumberItem* this = (const NumberItem*)cast; assert (this != NULL); char buffer[12]; RichString_writeAscii(out, CRT_colors[CHECK_BOX], "["); int written; if (this->scale < 0) { written = xSnprintf(buffer, sizeof(buffer), "%.*f", -this->scale, pow(10, this->scale) * NumberItem_get(this)); } else if (this->scale > 0) { written = xSnprintf(buffer, sizeof(buffer), "%d", (int) (pow(10, this->scale) * NumberItem_get(this))); } else { written = xSnprintf(buffer, sizeof(buffer), "%d", NumberItem_get(this)); } RichString_appendnAscii(out, CRT_colors[CHECK_MARK], buffer, written); RichString_appendAscii(out, CRT_colors[CHECK_BOX], "]"); for (int i = written; i < 5; i++) { RichString_appendAscii(out, CRT_colors[CHECK_BOX], " "); } RichString_appendWide(out, CRT_colors[CHECK_TEXT], this->super.text); } const OptionItemClass OptionItem_class = { .super = { .extends = Class(Object), .delete = OptionItem_delete } }; const OptionItemClass CheckItem_class = { .super = { .extends = Class(OptionItem), .delete = OptionItem_delete, .display = CheckItem_display }, .kind = OPTION_ITEM_CHECK }; const OptionItemClass NumberItem_class = { .super = { .extends = Class(OptionItem), .delete = OptionItem_delete, .display = NumberItem_display }, .kind = OPTION_ITEM_NUMBER }; CheckItem* CheckItem_newByRef(const char* text, bool* ref) { CheckItem* this = AllocThis(CheckItem); this->super.text = xStrdup(text); this->value = false; this->ref = ref; return this; } CheckItem* CheckItem_newByVal(const char* text, bool value) { CheckItem* this = AllocThis(CheckItem); this->super.text = xStrdup(text); this->value = value; this->ref = NULL; return this; } bool CheckItem_get(const CheckItem* this) { if (this->ref) { return *(this->ref); } else { return this->value; } } void CheckItem_set(CheckItem* this, bool value) { if (this->ref) { *(this->ref) = value; } else { this->value = value; } } void CheckItem_toggle(CheckItem* this) { if (this->ref) { *(this->ref) = !*(this->ref); } else { this->value = !this->value; } } NumberItem* NumberItem_newByRef(const char* text, int* ref, int scale, int min, int max) { assert(min <= max); NumberItem* this = AllocThis(NumberItem); this->super.text = xStrdup(text); this->value = 0; this->ref = ref; this->scale = scale; this->min = min; this->max = max; return this; } NumberItem* NumberItem_newByVal(const char* text, int value, int scale, int min, int max) { assert(min <= max); NumberItem* this = AllocThis(NumberItem); this->super.text = xStrdup(text); this->value = CLAMP(value, min, max); this->ref = NULL; this->scale = scale; this->min = min; this->max = max; return this; } int NumberItem_get(const NumberItem* this) { if (this->ref) { return *(this->ref); } else { return this->value; } } void NumberItem_decrease(NumberItem* this) { if (this->ref) { *(this->ref) = CLAMP(*(this->ref) - 1, this->min, this->max); } else { this->value = CLAMP(this->value - 1, this->min, this->max); } } void NumberItem_increase(NumberItem* this) { if (this->ref) { *(this->ref) = CLAMP(*(this->ref) + 1, this->min, this->max); } else { this->value = CLAMP(this->value + 1, this->min, this->max); } } void NumberItem_toggle(NumberItem* this) { if (this->ref) { if (*(this->ref) >= this->max) *(this->ref) = this->min; else *(this->ref) += 1; } else { if (this->value >= this->max) this->value = this->min; else this->value += 1; } }