mirror of https://gitlab.com/nakst/essence
replace EsListViewSetColumns
This commit is contained in:
parent
128022faa4
commit
a4374b3aa5
|
@ -41,14 +41,9 @@ const char *errorTypeStrings[] = {
|
|||
|
||||
#include "string.cpp"
|
||||
|
||||
EsListViewColumn folderOutputColumns[] = {
|
||||
#define COLUMN_NAME (0)
|
||||
{ INTERFACE_STRING(FileManagerColumnName), ES_LIST_VIEW_COLUMN_HAS_MENU },
|
||||
#define COLUMN_TYPE (1)
|
||||
{ INTERFACE_STRING(FileManagerColumnType), ES_LIST_VIEW_COLUMN_HAS_MENU },
|
||||
#define COLUMN_SIZE (2)
|
||||
{ INTERFACE_STRING(FileManagerColumnSize), ES_LIST_VIEW_COLUMN_HAS_MENU | ES_TEXT_H_RIGHT },
|
||||
};
|
||||
|
||||
#define LOAD_FOLDER_BACK (1)
|
||||
#define LOAD_FOLDER_FORWARD (2)
|
||||
|
|
|
@ -167,24 +167,16 @@ bool InstanceLoadFolder(Instance *instance, String path /* takes ownership */, i
|
|||
}
|
||||
|
||||
void InstanceRefreshViewType(Instance *instance) {
|
||||
EsCommandSetCheck(&instance->commandViewDetails, instance->viewSettings.viewType == VIEW_DETAILS ? ES_CHECK_CHECKED : ES_CHECK_UNCHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewTiles, instance->viewSettings.viewType == VIEW_TILES ? ES_CHECK_CHECKED : ES_CHECK_UNCHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewThumbnails, instance->viewSettings.viewType == VIEW_THUMBNAILS ? ES_CHECK_CHECKED : ES_CHECK_UNCHECKED, false);
|
||||
|
||||
if (instance->viewSettings.viewType == VIEW_DETAILS) {
|
||||
EsCommandSetCheck(&instance->commandViewDetails, ES_CHECK_CHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewTiles, ES_CHECK_UNCHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewThumbnails, ES_CHECK_UNCHECKED, false);
|
||||
|
||||
EsListViewChangeStyles(instance->list, &styleFolderView, ES_STYLE_LIST_ITEM, nullptr, nullptr, ES_LIST_VIEW_COLUMNS, ES_LIST_VIEW_TILED);
|
||||
EsListViewSetColumns(instance->list, folderOutputColumns, sizeof(folderOutputColumns) / sizeof(folderOutputColumns[0]));
|
||||
EsListViewAddAllColumns(instance->list);
|
||||
} else if (instance->viewSettings.viewType == VIEW_TILES) {
|
||||
EsCommandSetCheck(&instance->commandViewTiles, ES_CHECK_CHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewDetails, ES_CHECK_UNCHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewThumbnails, ES_CHECK_UNCHECKED, false);
|
||||
|
||||
EsListViewChangeStyles(instance->list, &styleFolderViewTiled, ES_STYLE_LIST_ITEM_TILE, nullptr, nullptr, ES_LIST_VIEW_TILED, ES_LIST_VIEW_COLUMNS);
|
||||
} else if (instance->viewSettings.viewType == VIEW_THUMBNAILS) {
|
||||
EsCommandSetCheck(&instance->commandViewThumbnails, ES_CHECK_CHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewTiles, ES_CHECK_UNCHECKED, false);
|
||||
EsCommandSetCheck(&instance->commandViewDetails, ES_CHECK_UNCHECKED, false);
|
||||
|
||||
EsListViewChangeStyles(instance->list, &styleFolderViewTiled, &styleFolderItemThumbnail, nullptr, nullptr, ES_LIST_VIEW_TILED, ES_LIST_VIEW_COLUMNS);
|
||||
}
|
||||
}
|
||||
|
@ -738,7 +730,7 @@ int ListCallback(EsElement *element, EsMessage *message) {
|
|||
EsCommandSetCallback(EsCommandByID(instance, ES_COMMAND_PASTE), nullptr);
|
||||
return 0;
|
||||
} else if (message->type == ES_MSG_LIST_VIEW_GET_CONTENT) {
|
||||
int column = message->getContent.column, index = message->getContent.index;
|
||||
int column = message->getContent.columnID, index = message->getContent.index;
|
||||
EsAssert(index < (int) instance->listContents.Length() && index >= 0);
|
||||
ListEntry *listEntry = &instance->listContents[index];
|
||||
FolderEntry *entry = listEntry->entry;
|
||||
|
@ -1084,7 +1076,10 @@ void InstanceCreateUI(Instance *instance) {
|
|||
instance->list = EsListViewCreate(splitter, ES_CELL_FILL | ES_LIST_VIEW_COLUMNS | ES_LIST_VIEW_MULTI_SELECT, &styleFolderView);
|
||||
instance->list->accessKey = 'L';
|
||||
instance->list->messageUser = ListCallback;
|
||||
EsListViewSetColumns(instance->list, folderOutputColumns, sizeof(folderOutputColumns) / sizeof(folderOutputColumns[0]));
|
||||
EsListViewRegisterColumn(instance->list, COLUMN_NAME, INTERFACE_STRING(FileManagerColumnName), ES_LIST_VIEW_COLUMN_HAS_MENU);
|
||||
EsListViewRegisterColumn(instance->list, COLUMN_TYPE, INTERFACE_STRING(FileManagerColumnType), ES_LIST_VIEW_COLUMN_HAS_MENU);
|
||||
EsListViewRegisterColumn(instance->list, COLUMN_SIZE, INTERFACE_STRING(FileManagerColumnSize), ES_LIST_VIEW_COLUMN_HAS_MENU | ES_TEXT_H_RIGHT);
|
||||
EsListViewAddAllColumns(instance->list);
|
||||
EsListViewInsertGroup(instance->list, 0);
|
||||
|
||||
// Toolbar:
|
||||
|
|
|
@ -1,12 +1,5 @@
|
|||
#include <essence.h>
|
||||
|
||||
EsListViewColumn columns[] = {
|
||||
// Title Flags Initial width
|
||||
{ "Name", -1, ES_FLAGS_DEFAULT, 150 },
|
||||
{ "Age", -1, ES_TEXT_H_RIGHT, 100 },
|
||||
{ "Favorite color", -1, ES_DRAW_CONTENT_RICH_TEXT, 150 },
|
||||
};
|
||||
|
||||
void AddPerson(EsListView *list, const char *name, int age, const char *favoriteColor) {
|
||||
char ageString[16];
|
||||
EsStringFormat(ageString, sizeof(ageString), "%d%c", age, 0);
|
||||
|
@ -26,7 +19,10 @@ void _start() {
|
|||
EsInstance *instance = EsInstanceCreate(message, "List", -1);
|
||||
EsPanel *wrapper = EsPanelCreate(instance->window, ES_CELL_FILL, ES_STYLE_PANEL_WINDOW_DIVIDER);
|
||||
EsListView *list = EsListViewCreate(wrapper, ES_CELL_FILL | ES_LIST_VIEW_COLUMNS | ES_LIST_VIEW_FIXED_ITEMS);
|
||||
EsListViewSetColumns(list, columns, sizeof(columns) / sizeof(columns[0]));
|
||||
EsListViewRegisterColumn(list, 0, "Name", -1, ES_FLAGS_DEFAULT, 150);
|
||||
EsListViewRegisterColumn(list, 1, "Age", -1, ES_TEXT_H_RIGHT, 100);
|
||||
EsListViewRegisterColumn(list, 2, "Favorite color", -1, ES_DRAW_CONTENT_RICH_TEXT, 150);
|
||||
EsListViewAddAllColumns(list);
|
||||
AddPerson(list, "Alice", 20, "\a#e00]Red");
|
||||
AddPerson(list, "Bob", 30, "\a#080]Green");
|
||||
AddPerson(list, "Cameron", 40, "\a#00f]Blue");
|
||||
|
|
|
@ -26,23 +26,6 @@ struct Instance : EsInstance {
|
|||
#define DISPLAY_GENERAL_LOG (3)
|
||||
#define DISPLAY_MEMORY (12)
|
||||
|
||||
EsListViewColumn listViewProcessesColumns[] = {
|
||||
{ "Name", -1, 0, 150 },
|
||||
{ "PID", -1, ES_TEXT_H_RIGHT, 120 },
|
||||
{ "Memory", -1, ES_TEXT_H_RIGHT, 120 },
|
||||
{ "CPU", -1, ES_TEXT_H_RIGHT, 120 },
|
||||
{ "Handles", -1, ES_TEXT_H_RIGHT, 120 },
|
||||
{ "Threads", -1, ES_TEXT_H_RIGHT, 120 },
|
||||
};
|
||||
|
||||
EsListViewColumn listViewContextSwitchesColumns[] = {
|
||||
{ "Time stamp (ms)", -1, ES_TEXT_H_RIGHT, 150 },
|
||||
{ "CPU", -1, ES_TEXT_H_RIGHT, 150 },
|
||||
{ "Process", -1, 0, 150 },
|
||||
{ "Thread", -1, 0, 150 },
|
||||
{ "Count", -1, 0, 150 },
|
||||
};
|
||||
|
||||
const EsStyle styleMonospacedTextbox = {
|
||||
.inherit = ES_STYLE_TEXTBOX_NO_BORDER,
|
||||
|
||||
|
@ -323,7 +306,7 @@ void UpdateDisplay(Instance *instance, int index) {
|
|||
|
||||
int ListViewProcessesCallback(EsElement *element, EsMessage *message) {
|
||||
if (message->type == ES_MSG_LIST_VIEW_GET_CONTENT) {
|
||||
int column = message->getContent.column, index = message->getContent.index;
|
||||
int column = message->getContent.columnID, index = message->getContent.index;
|
||||
ProcessItem *item = &processes[index];
|
||||
if (column == 0) GET_CONTENT("%s", item->data.nameBytes, item->data.name);
|
||||
else if (column == 1) { if (item->data.pid == -1) GET_CONTENT("n/a"); else GET_CONTENT("%d", item->data.pid); }
|
||||
|
@ -357,13 +340,6 @@ void AddTab(EsElement *toolbar, uintptr_t index, const char *label, bool asDefau
|
|||
if (asDefault) EsButtonSetCheck(button, ES_CHECK_CHECKED);
|
||||
}
|
||||
|
||||
void AddListView(EsListView **pointer, EsElement *switcher, EsUICallback callback, EsListViewColumn *columns, size_t columnsSize, uint64_t additionalFlags) {
|
||||
*pointer = EsListViewCreate(switcher, ES_CELL_FILL | ES_LIST_VIEW_COLUMNS | additionalFlags);
|
||||
(*pointer)->messageUser = callback;
|
||||
EsListViewSetColumns(*pointer, columns, columnsSize / sizeof(EsListViewColumn));
|
||||
EsListViewInsertGroup(*pointer, 0);
|
||||
}
|
||||
|
||||
void TerminateProcess(Instance *instance, EsElement *, EsCommand *) {
|
||||
if (selectedPID == 0 /* Kernel */) {
|
||||
// Terminating the kernel process is a meaningless action; the closest equivalent is shutting down.
|
||||
|
@ -394,8 +370,16 @@ void ProcessApplicationMessage(EsMessage *message) {
|
|||
|
||||
instance->textboxGeneralLog = EsTextboxCreate(switcher, ES_TEXTBOX_MULTILINE | ES_CELL_FILL | ES_ELEMENT_DISABLED, &styleMonospacedTextbox);
|
||||
|
||||
AddListView(&instance->listViewProcesses, switcher, ListViewProcessesCallback,
|
||||
listViewProcessesColumns, sizeof(listViewProcessesColumns), ES_LIST_VIEW_SINGLE_SELECT);
|
||||
instance->listViewProcesses = EsListViewCreate(switcher, ES_CELL_FILL | ES_LIST_VIEW_COLUMNS | ES_LIST_VIEW_SINGLE_SELECT);
|
||||
instance->listViewProcesses->messageUser = ListViewProcessesCallback;
|
||||
EsListViewRegisterColumn(instance->listViewProcesses, 0, "Name", -1, 0, 150);
|
||||
EsListViewRegisterColumn(instance->listViewProcesses, 1, "PID", -1, ES_TEXT_H_RIGHT, 120);
|
||||
EsListViewRegisterColumn(instance->listViewProcesses, 2, "Memory", -1, ES_TEXT_H_RIGHT, 120);
|
||||
EsListViewRegisterColumn(instance->listViewProcesses, 3, "CPU", -1, ES_TEXT_H_RIGHT, 120);
|
||||
EsListViewRegisterColumn(instance->listViewProcesses, 4, "Handles", -1, ES_TEXT_H_RIGHT, 120);
|
||||
EsListViewRegisterColumn(instance->listViewProcesses, 5, "Threads", -1, ES_TEXT_H_RIGHT, 120);
|
||||
EsListViewAddAllColumns(instance->listViewProcesses);
|
||||
EsListViewInsertGroup(instance->listViewProcesses, 0);
|
||||
|
||||
instance->panelMemoryStatistics = EsPanelCreate(switcher,
|
||||
ES_CELL_FILL | ES_PANEL_TABLE | ES_PANEL_HORIZONTAL | ES_PANEL_V_SCROLL_AUTO, &stylePanelMemoryStatistics);
|
||||
|
|
|
@ -7559,12 +7559,6 @@ struct InspectorWindow : EsInstance {
|
|||
EsTextbox *textboxCategoryFilter;
|
||||
};
|
||||
|
||||
EsListViewColumn inspectorElementListColumns[] = {
|
||||
{ "Name", -1, 0, 300 },
|
||||
{ "Bounds", -1, 0, 200 },
|
||||
{ "Information", -1, 0, 200 },
|
||||
};
|
||||
|
||||
int InspectorElementItemCallback(EsElement *element, EsMessage *message) {
|
||||
InspectorWindow *inspector = (InspectorWindow *) element->instance;
|
||||
|
||||
|
@ -7670,7 +7664,7 @@ int InspectorElementListCallback(EsElement *element, EsMessage *message) {
|
|||
InspectorWindow *inspector = (InspectorWindow *) element->instance;
|
||||
|
||||
if (message->type == ES_MSG_LIST_VIEW_GET_CONTENT) {
|
||||
int column = message->getContent.column, index = message->getContent.index;
|
||||
int column = message->getContent.columnID, index = message->getContent.index;
|
||||
EsAssert(index >= 0 && index < (int) inspector->elements.Length());
|
||||
InspectorElementEntry *entry = &inspector->elements[index];
|
||||
|
||||
|
@ -8047,7 +8041,10 @@ void InspectorSetup(EsWindow *window) {
|
|||
|
||||
inspector->elementList = EsListViewCreate(panel1, ES_CELL_FILL | ES_LIST_VIEW_COLUMNS | ES_LIST_VIEW_SINGLE_SELECT);
|
||||
inspector->elementList->messageUser = InspectorElementListCallback;
|
||||
EsListViewSetColumns(inspector->elementList, inspectorElementListColumns, sizeof(inspectorElementListColumns) / sizeof(EsListViewColumn));
|
||||
EsListViewRegisterColumn(inspector->elementList, 0, "Name", -1, 0, 300);
|
||||
EsListViewRegisterColumn(inspector->elementList, 1, "Bounds", -1, 0, 200);
|
||||
EsListViewRegisterColumn(inspector->elementList, 2, "Information", -1, 0, 200);
|
||||
EsListViewAddAllColumns(inspector->elementList);
|
||||
EsListViewInsertGroup(inspector->elementList, 0);
|
||||
|
||||
{
|
||||
|
|
|
@ -39,11 +39,20 @@ struct ListViewFixedString {
|
|||
|
||||
struct ListViewFixedItem {
|
||||
ListViewFixedString firstColumn;
|
||||
// TODO Store the strings in an array per-ListViewColumn.
|
||||
Array<ListViewFixedString> otherColumns;
|
||||
EsGeneric data;
|
||||
uint32_t iconID;
|
||||
};
|
||||
|
||||
struct ListViewColumn {
|
||||
char *title;
|
||||
size_t titleBytes;
|
||||
uint32_t id;
|
||||
uint32_t flags;
|
||||
double width;
|
||||
};
|
||||
|
||||
int ListViewProcessItemMessage(EsElement *element, EsMessage *message);
|
||||
|
||||
struct EsListView : EsElement {
|
||||
|
@ -88,8 +97,8 @@ struct EsListView : EsElement {
|
|||
size_t emptyMessageBytes;
|
||||
|
||||
EsElement *columnHeader;
|
||||
EsListViewColumn *columns;
|
||||
size_t columnCount;
|
||||
Array<ListViewColumn> registeredColumns;
|
||||
Array<uint32_t> activeColumns; // Indices into registeredColumns.
|
||||
int columnResizingOriginalWidth;
|
||||
int64_t totalColumnWidth;
|
||||
|
||||
|
@ -685,7 +694,7 @@ struct EsListView : EsElement {
|
|||
position += visibleItem->element->width;
|
||||
} else if ((flags & ES_LIST_VIEW_COLUMNS) && ((~flags & ES_LIST_VIEW_CHOICE_SELECT) || (this->scroll.enabled[0]))) {
|
||||
int indent = visibleItem->indent * style->gapWrap;
|
||||
int firstColumn = columns[0].width * theming.scale + secondaryCellStyle->gapMajor;
|
||||
int firstColumn = activeColumns.Length() ? (registeredColumns[activeColumns[0]].width * theming.scale + secondaryCellStyle->gapMajor) : 0;
|
||||
visibleItem->startAtSecondColumn = indent > firstColumn;
|
||||
if (indent > firstColumn) indent = firstColumn;
|
||||
visibleItem->element->InternalMove(totalColumnWidth - indent, visibleItem->size,
|
||||
|
@ -1174,12 +1183,12 @@ struct EsListView : EsElement {
|
|||
if (flags & ES_LIST_VIEW_COLUMNS) {
|
||||
EsRectangle bounds = EsRectangleAddBorder(element->GetBounds(), element->style->insets);
|
||||
|
||||
for (uintptr_t i = item->startAtSecondColumn ? 1 : 0; i < columnCount; i++) {
|
||||
m.getContent.column = i;
|
||||
for (uintptr_t i = item->startAtSecondColumn ? 1 : 0; i < activeColumns.Length(); i++) {
|
||||
m.getContent.columnID = registeredColumns[activeColumns[i]].id;
|
||||
m.getContent.icon = 0;
|
||||
buffer.position = 0;
|
||||
|
||||
bounds.r = bounds.l + columns[i].width * theming.scale
|
||||
bounds.r = bounds.l + registeredColumns[activeColumns[i]].width * theming.scale
|
||||
- element->style->insets.r - element->style->insets.l;
|
||||
|
||||
if (i == 0) {
|
||||
|
@ -1195,10 +1204,10 @@ struct EsListView : EsElement {
|
|||
UIStyle *style = useSelectedCellStyle ? selectedCellStyle : i ? secondaryCellStyle : primaryCellStyle;
|
||||
style->PaintText(message->painter, element, bounds,
|
||||
(char *) _buffer, buffer.position, m.getContent.icon,
|
||||
columns[i].flags, i ? nullptr : &selection);
|
||||
registeredColumns[activeColumns[i]].flags, i ? nullptr : &selection);
|
||||
}
|
||||
|
||||
bounds.l += columns[i].width * theming.scale + secondaryCellStyle->gapMajor;
|
||||
bounds.l += registeredColumns[activeColumns[i]].width * theming.scale + secondaryCellStyle->gapMajor;
|
||||
|
||||
if (i == 0) {
|
||||
bounds.l -= item->indent * style->gapWrap;
|
||||
|
@ -1580,7 +1589,7 @@ struct EsListView : EsElement {
|
|||
if (flags & ES_LIST_VIEW_COLUMNS) {
|
||||
int offset = primaryCellStyle->metrics->iconSize + primaryCellStyle->gapMinor
|
||||
+ style->insets.l - inlineTextbox->style->insets.l;
|
||||
inlineTextbox->InternalMove(columns[0].width * theming.scale - offset, item->element->height,
|
||||
inlineTextbox->InternalMove(registeredColumns[activeColumns[0]].width * theming.scale - offset, item->element->height,
|
||||
item->element->offsetX + offset, item->element->offsetY);
|
||||
} else if (flags & ES_LIST_VIEW_TILED) {
|
||||
if (style->metrics->layoutVertical) {
|
||||
|
@ -1669,6 +1678,10 @@ struct EsListView : EsElement {
|
|||
visibleItems[i].element->Destroy();
|
||||
}
|
||||
|
||||
for (uintptr_t i = 0; i < registeredColumns.Length(); i++) {
|
||||
EsHeapFree(registeredColumns[i].title);
|
||||
}
|
||||
|
||||
for (uintptr_t i = 0; i < fixedItems.Length(); i++) {
|
||||
for (uintptr_t j = 0; j < fixedItems[i].otherColumns.Length(); j++) {
|
||||
EsHeapFree(fixedItems[i].otherColumns[j].string);
|
||||
|
@ -1685,6 +1698,8 @@ struct EsListView : EsElement {
|
|||
fixedItems.Free();
|
||||
visibleItems.Free();
|
||||
groups.Free();
|
||||
activeColumns.Free();
|
||||
registeredColumns.Free();
|
||||
} else if (message->type == ES_MSG_KEY_UP) {
|
||||
if (message->keyboard.scancode == ES_SCANCODE_LEFT_CTRL || message->keyboard.scancode == ES_SCANCODE_RIGHT_CTRL) {
|
||||
SelectPreview();
|
||||
|
@ -1874,10 +1889,10 @@ struct EsListView : EsElement {
|
|||
EsAssert(index < fixedItems.Length());
|
||||
ListViewFixedString emptyString = {};
|
||||
ListViewFixedItem *item = &fixedItems[index];
|
||||
ListViewFixedString *string = message->getContent.column == 0 ? &item->firstColumn
|
||||
: message->getContent.column <= item->otherColumns.Length() ? &item->otherColumns[message->getContent.column - 1] : &emptyString;
|
||||
ListViewFixedString *string = message->getContent.columnID == 0 ? &item->firstColumn
|
||||
: message->getContent.columnID <= item->otherColumns.Length() ? &item->otherColumns[message->getContent.columnID - 1] : &emptyString;
|
||||
EsBufferFormat(message->getContent.buffer, "%s", string->bytes, string->string);
|
||||
if (message->getContent.column == 0) message->getContent.icon = item->iconID;
|
||||
if (!activeColumns.Length() || message->getContent.columnID == registeredColumns[activeColumns[0]].id) message->getContent.icon = item->iconID;
|
||||
} else if (message->type == ES_MSG_LIST_VIEW_IS_SELECTED && (flags & ES_LIST_VIEW_FIXED_ITEMS)) {
|
||||
message->selectItem.isSelected = message->selectItem.index == fixedItemSelection;
|
||||
} else {
|
||||
|
@ -1900,11 +1915,30 @@ int ListViewProcessItemMessage(EsElement *_element, EsMessage *message) {
|
|||
void ListViewCalculateTotalColumnWidth(EsListView *view) {
|
||||
view->totalColumnWidth = -view->secondaryCellStyle->gapMajor;
|
||||
|
||||
for (uintptr_t i = 0; i < view->columnCount; i++) {
|
||||
view->totalColumnWidth += view->columns[i].width * theming.scale + view->secondaryCellStyle->gapMajor;
|
||||
for (uintptr_t i = 0; i < view->activeColumns.Length(); i++) {
|
||||
view->totalColumnWidth += view->registeredColumns[view->activeColumns[i]].width * theming.scale + view->secondaryCellStyle->gapMajor;
|
||||
}
|
||||
}
|
||||
|
||||
int ListViewColumnHeaderMessage(EsElement *element, EsMessage *message) {
|
||||
EsListView *view = (EsListView *) element->userData.p;
|
||||
|
||||
if (message->type == ES_MSG_LAYOUT) {
|
||||
int x = view->style->insets.l - view->scroll.position[0];
|
||||
|
||||
for (uintptr_t i = 0; i < element->children.Length(); i += 2) {
|
||||
EsElement *item = element->children[i], *splitter = element->children[i + 1];
|
||||
ListViewColumn *column = &view->registeredColumns[item->userData.u];
|
||||
int splitterLeft = splitter->style->preferredWidth - view->secondaryCellStyle->gapMajor;
|
||||
item->InternalMove(column->width * theming.scale - splitterLeft, element->height, x, 0);
|
||||
splitter->InternalMove(splitter->style->preferredWidth, element->height, x + column->width * theming.scale - splitterLeft, 0);
|
||||
x += column->width * theming.scale + view->secondaryCellStyle->gapMajor;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void EsListViewChangeStyles(EsListView *view, const EsStyle *style, const EsStyle *itemStyle,
|
||||
const EsStyle *headerItemStyle, const EsStyle *footerItemStyle, uint32_t addFlags, uint32_t removeFlags) {
|
||||
// TODO Animating changes.
|
||||
|
@ -1938,29 +1972,11 @@ void EsListViewChangeStyles(EsListView *view, const EsStyle *style, const EsStyl
|
|||
view->columnHeader = EsCustomElementCreate(view, ES_CELL_FILL, ES_STYLE_LIST_COLUMN_HEADER);
|
||||
view->columnHeader->cName = "column header";
|
||||
view->columnHeader->userData = view;
|
||||
|
||||
view->columnHeader->messageUser = [] (EsElement *element, EsMessage *message) {
|
||||
EsListView *view = (EsListView *) element->userData.p;
|
||||
|
||||
if (message->type == ES_MSG_LAYOUT) {
|
||||
int x = view->style->insets.l - view->scroll.position[0];
|
||||
|
||||
for (uintptr_t i = 0; i < element->children.Length(); i += 2) {
|
||||
EsElement *item = element->children[i], *splitter = element->children[i + 1];
|
||||
EsListViewColumn *column = view->columns + item->userData.u;
|
||||
int splitterLeft = splitter->style->preferredWidth - view->secondaryCellStyle->gapMajor;
|
||||
item->InternalMove(column->width * theming.scale - splitterLeft, element->height, x, 0);
|
||||
splitter->InternalMove(splitter->style->preferredWidth, element->height, x + column->width * theming.scale - splitterLeft, 0);
|
||||
x += column->width * theming.scale + view->secondaryCellStyle->gapMajor;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
};
|
||||
|
||||
view->columnHeader->messageUser = ListViewColumnHeaderMessage;
|
||||
view->scroll.fixedViewport[1] = view->columnHeader->style->preferredHeight;
|
||||
} else if ((~view->flags & ES_LIST_VIEW_COLUMNS) && view->columnHeader) {
|
||||
EsElementDestroy(view->columnHeader);
|
||||
view->activeColumns.Free();
|
||||
view->columnHeader = nullptr;
|
||||
view->scroll.fixedViewport[1] = 0;
|
||||
}
|
||||
|
@ -2245,7 +2261,7 @@ void EsListViewRemoveAll(EsListView *view, EsListViewIndex group) {
|
|||
|
||||
int ListViewColumnHeaderItemMessage(EsElement *element, EsMessage *message) {
|
||||
EsListView *view = (EsListView *) element->parent->parent;
|
||||
EsListViewColumn *column = view->columns + element->userData.u;
|
||||
ListViewColumn *column = &view->registeredColumns[element->userData.u];
|
||||
|
||||
if (message->type == ES_MSG_PAINT) {
|
||||
EsMessage m = { ES_MSG_LIST_VIEW_GET_COLUMN_SORT };
|
||||
|
@ -2267,59 +2283,67 @@ int ListViewColumnHeaderItemMessage(EsElement *element, EsMessage *message) {
|
|||
return ES_HANDLED;
|
||||
}
|
||||
|
||||
void EsListViewSetColumns(EsListView *view, EsListViewColumn *columns, size_t columnCount) {
|
||||
EsMessageMutexCheck();
|
||||
int ListViewColumnSplitterMessage(EsElement *element, EsMessage *message) {
|
||||
EsListView *view = (EsListView *) element->parent->parent;
|
||||
ListViewColumn *column = &view->registeredColumns[element->userData.u];
|
||||
|
||||
EsAssert(view->flags & ES_LIST_VIEW_COLUMNS); // List view does not have columns flag set.
|
||||
if (message->type == ES_MSG_MOUSE_LEFT_DOWN) {
|
||||
view->columnResizingOriginalWidth = column->width * theming.scale;
|
||||
} else if (message->type == ES_MSG_MOUSE_LEFT_DRAG) {
|
||||
int width = message->mouseDragged.newPositionX - message->mouseDragged.originalPositionX + view->columnResizingOriginalWidth;
|
||||
int minimumWidth = element->style->metrics->minimumWidth;
|
||||
if (width < minimumWidth) width = minimumWidth;
|
||||
column->width = width / theming.scale;
|
||||
ListViewCalculateTotalColumnWidth(view);
|
||||
EsElementRelayout(element->parent);
|
||||
EsElementRelayout(view);
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return ES_HANDLED;
|
||||
}
|
||||
|
||||
void EsListViewAddAllColumns(EsListView *view) {
|
||||
EsElementDestroyContents(view->columnHeader);
|
||||
view->activeColumns.Free();
|
||||
|
||||
view->columns = columns;
|
||||
view->columnCount = columnCount;
|
||||
|
||||
for (uintptr_t i = 0; i < columnCount; i++) {
|
||||
EsElement *columnHeaderItem = EsCustomElementCreate(view->columnHeader, ES_CELL_FILL,
|
||||
(columns[i].flags & ES_LIST_VIEW_COLUMN_HAS_MENU) ? ES_STYLE_LIST_COLUMN_HEADER_ITEM_HAS_MENU : ES_STYLE_LIST_COLUMN_HEADER_ITEM);
|
||||
for (uintptr_t i = 0; i < view->registeredColumns.Length(); i++) {
|
||||
view->activeColumns.Add(i);
|
||||
|
||||
EsStyle *style = (view->registeredColumns[i].flags & ES_LIST_VIEW_COLUMN_HAS_MENU) ? ES_STYLE_LIST_COLUMN_HEADER_ITEM_HAS_MENU : ES_STYLE_LIST_COLUMN_HEADER_ITEM;
|
||||
EsElement *columnHeaderItem = EsCustomElementCreate(view->columnHeader, ES_CELL_FILL, style);
|
||||
columnHeaderItem->messageUser = ListViewColumnHeaderItemMessage;
|
||||
columnHeaderItem->cName = "column header item";
|
||||
columnHeaderItem->userData = i;
|
||||
|
||||
if (!columns[i].width) {
|
||||
columns[i].width = (i ? view->secondaryCellStyle : view->primaryCellStyle)->preferredWidth / theming.scale;
|
||||
}
|
||||
|
||||
EsElement *splitter = EsCustomElementCreate(view->columnHeader, ES_CELL_FILL, ES_STYLE_LIST_COLUMN_HEADER_SPLITTER);
|
||||
|
||||
splitter->messageUser = [] (EsElement *element, EsMessage *message) {
|
||||
EsListViewColumn *column = (EsListViewColumn *) element->userData.p;
|
||||
EsListView *view = (EsListView *) element->parent->parent;
|
||||
|
||||
if (message->type == ES_MSG_MOUSE_LEFT_DOWN) {
|
||||
view->columnResizingOriginalWidth = column->width * theming.scale;
|
||||
} else if (message->type == ES_MSG_MOUSE_LEFT_DRAG) {
|
||||
int width = message->mouseDragged.newPositionX - message->mouseDragged.originalPositionX + view->columnResizingOriginalWidth;
|
||||
int minimumWidth = element->style->metrics->minimumWidth;
|
||||
if (width < minimumWidth) width = minimumWidth;
|
||||
column->width = width / theming.scale;
|
||||
ListViewCalculateTotalColumnWidth(view);
|
||||
EsElementRelayout(element->parent);
|
||||
EsElementRelayout(view);
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return ES_HANDLED;
|
||||
},
|
||||
|
||||
splitter->messageUser = ListViewColumnSplitterMessage;
|
||||
splitter->cName = "column header splitter";
|
||||
splitter->userData = columns + i;
|
||||
splitter->userData = i;
|
||||
}
|
||||
|
||||
ListViewCalculateTotalColumnWidth(view);
|
||||
view->scroll.Refresh();
|
||||
}
|
||||
|
||||
void EsListViewRegisterColumn(EsListView *view, uint32_t id, const char *title, ptrdiff_t titleBytes, uint32_t flags, double initialWidth) {
|
||||
EsMessageMutexCheck();
|
||||
EsAssert(view->flags & ES_LIST_VIEW_COLUMNS); // List view does not have columns flag set.
|
||||
|
||||
if (!initialWidth) {
|
||||
initialWidth = (view->registeredColumns.Length() ? view->secondaryCellStyle : view->primaryCellStyle)->preferredWidth / theming.scale;
|
||||
}
|
||||
|
||||
ListViewColumn column = {};
|
||||
column.id = id;
|
||||
column.flags = flags;
|
||||
column.width = initialWidth;
|
||||
if (titleBytes == -1) titleBytes = EsCStringLength(title);
|
||||
HeapDuplicate((void **) &column.title, &column.titleBytes, title, titleBytes);
|
||||
view->registeredColumns.Add(column);
|
||||
}
|
||||
|
||||
void EsListViewContentChanged(EsListView *view) {
|
||||
EsMessageMutexCheck();
|
||||
|
||||
|
|
|
@ -1417,12 +1417,6 @@ struct EsCommand {
|
|||
STRING title;
|
||||
};
|
||||
|
||||
struct EsListViewColumn {
|
||||
STRING title;
|
||||
uint32_t flags;
|
||||
double width;
|
||||
};
|
||||
|
||||
struct EsApplicationStartupRequest {
|
||||
int64_t id;
|
||||
STRING filePath;
|
||||
|
@ -1642,8 +1636,8 @@ struct EsMessageGetContent {
|
|||
EsListViewIndex group;
|
||||
uint32_t icon;
|
||||
uint32_t drawContentFlags;
|
||||
uint32_t columnID;
|
||||
EsBuffer *buffer;
|
||||
uint8_t column;
|
||||
};
|
||||
|
||||
struct EsMessageGetIndent {
|
||||
|
@ -2570,7 +2564,8 @@ function EsListView *EsListViewCreate(EsElement *parent, uint64_t flags = ES_FLA
|
|||
function EsListViewIndex EsListViewGetIndexFromItem(EsElement *element, EsListViewIndex *group = ES_NULL);
|
||||
function void EsListViewEnumerateVisibleItems(EsListView *view, EsListViewEnumerateVisibleItemsCallback callback);
|
||||
|
||||
function void EsListViewSetColumns(EsListView *view, EsListViewColumn *columns, size_t columnCount);
|
||||
function void EsListViewRegisterColumn(EsListView *view, uint32_t id, STRING title = BLANK_STRING, uint32_t flags = ES_FLAGS_DEFAULT, double initialWidth = 0);
|
||||
function void EsListViewAddAllColumns(EsListView *view); // Call after registering the columns to add them to the header. Call again after EsListViewChangeStyles, as needed.
|
||||
function void EsListViewSetEmptyMessage(EsListView *view, STRING message = BLANK_STRING);
|
||||
function void EsListViewSetMaximumItemsPerBand(EsListView *view, int maximumItemsPerBand);
|
||||
function void EsListViewSelectNone(EsListView *view);
|
||||
|
|
|
@ -119,3 +119,4 @@ private define ES_STYLE_SCROLLBAR_THUMB_VERTICAL (ES_STYLE_CAST(1369))
|
|||
define ES_STYLE_TOOLBAR_SPACER (ES_STYLE_CAST(5))
|
||||
define ES_STYLE_TOOLBAR_BUTTON_GROUP_SEPARATOR (ES_STYLE_CAST(7))
|
||||
define ES_STYLE_TOOLBAR_SPACER_SMALL (ES_STYLE_CAST(3))
|
||||
define ES_STYLE_LIST_CHOICE_ITEM_2X (ES_STYLE_CAST(9))
|
||||
|
|
Binary file not shown.
BIN
res/Theme.dat
BIN
res/Theme.dat
Binary file not shown.
|
@ -137,9 +137,11 @@ EsEventReset=135
|
|||
EsEventSet=136
|
||||
EsInstanceCloseReference=137
|
||||
EsInstanceClose=138
|
||||
EsListViewRegisterColumn=139
|
||||
EsMutexAcquire=140
|
||||
EsMutexDestroy=141
|
||||
EsMutexRelease=142
|
||||
EsListViewAddAllColumns=143
|
||||
EsSchedulerYield=145
|
||||
EsSleep=146
|
||||
EsSpinlockAcquire=147
|
||||
|
@ -309,7 +311,6 @@ EsFileDelete=311
|
|||
EsBufferReadInto=312
|
||||
EsListViewRemoveAll=313
|
||||
EsSystemShowShutdownDialog=314
|
||||
EsListViewSetColumns=315
|
||||
EsListViewSelect=316
|
||||
EsUndoClear=317
|
||||
EsMessageReceive=318
|
||||
|
|
Loading…
Reference in New Issue