513ff234094b883276ecb289fd9839792e2ddb20
chmalee
Tue Nov 3 16:39:53 2020 -0800
First cut of custom table on hgc, no styling
diff --git src/hg/hgc/hgc.c src/hg/hgc/hgc.c
index ba387101..de5d206 100644
--- src/hg/hgc/hgc.c
+++ src/hg/hgc/hgc.c
@@ -1538,85 +1538,157 @@
for (count = 0; col != NULL && count < fieldCount; col = col->next)
{
struct slPair *field;
AllocVar(field);
char *fieldName = col->name;
char *fieldVal = row[count];
field->name = fieldName;
field->val = fieldVal;
slAddHead(&fields, field);
count++;
}
slReverse(fields);
return fields;
}
+void printExtraDetailsTable(char *trackName, char *tableName, char *fileName, struct dyString *tableText)
+// convert a tab-sep table to HTML
+{
+struct lineFile *lf = lineFileOnString(fileName, TRUE, tableText->string);
+char *description = tableName != NULL ? tableName : "Additional Details";
+printf("
");
+jsBeginCollapsibleSection(cart, trackName, "extraTbl", description, FALSE);
+printf("\n"); // closes bedExtraTbl
+jsEndCollapsibleSection();
+printf("
\n"); // close wrapper table
+}
+
+static struct slName *findFieldsInExtraFile(char *detailsTableUrl, struct asColumn *col, struct dyString *ds)
+// return a list of the ${}-enclosed fields from an extra file
+{
+struct slName *foundFields = NULL;
+char *table = netReadTextFileIfExists(hReplaceGbdb(detailsTableUrl));
+if (table)
+ {
+ for (; col != NULL; col = col->next)
+ {
+ char field[256];
+ safef(field, sizeof(field), "${%s}", col->name);
+ if (stringIn(field, table))
+ {
+ struct slName *replaceField = slNameNew(col->name);
+ slAddHead(&foundFields, replaceField);
+ }
+ }
+ dyStringPrintf(ds, "%s", table);
+ slReverse(foundFields);
+ }
+return foundFields;
+}
+
int extraFieldsPrintAs(struct trackDb *tdb,struct sqlResult *sr,char **fields,int fieldCount, struct asObject *as)
// Any extra bed or bigBed fields (defined in as and occurring after N in bed N + types.
// sr may be null for bigBeds.
// Returns number of extra fields actually printed.
{
// We are trying to print extra fields so we need to figure out how many fields to skip
int start = extraFieldsStart(tdb, fieldCount, as);
struct asColumn *col = as->columnList;
char *urlsStr = trackDbSettingClosestToHomeOrDefault(tdb, "urls", NULL);
struct hash* fieldToUrl = hashFromString(urlsStr);
boolean skipEmptyFields = trackDbSettingOn(tdb, "skipEmptyFields");
// make list of fields to skip
char *skipFieldsStr = trackDbSetting(tdb, "skipFields");
struct slName *skipIds = NULL;
if (skipFieldsStr)
skipIds = slNameListFromComma(skipFieldsStr);
// make list of fields that are separated from other fields
char *sepFieldsStr = trackDbSetting(tdb, "sepFields");
struct slName *sepFields = NULL;
if (sepFieldsStr)
sepFields = slNameListFromComma(sepFieldsStr);
+// make list of fields that we want to substitute
+// this setting has format description|URLorFilePath, with the stuff before the pipe optional
+char *extraDetailsTableName = NULL, *extraDetails = cloneString(trackDbSetting(tdb, "extraDetailsTable"));
+if (extraDetails && strchr(extraDetails,'|'))
+ {
+ extraDetailsTableName = extraDetails;
+ extraDetails = strchr(extraDetails,'|');
+ *extraDetails++ = 0;
+ }
+struct dyString *extraTblStr = dyStringNew(0);
+struct slName *detailsTableFields = NULL;
+if (extraDetails)
+ detailsTableFields = findFieldsInExtraFile(extraDetails, col, extraTblStr);
+
// iterate over fields, print as table rows
int count = 0;
for (;col != NULL && count < fieldCount;col=col->next)
{
if (start > 0) // skip past already known fields
{
start--;
continue;
}
int ix = count;
if (sr != NULL)
{
ix = sqlFieldColumn(sr, col->name); // If sr provided, name must match sql columnn name!
if (ix == -1 || ix > fieldCount) // so extraField really just provides a label
continue;
}
char *fieldName = col->name;
if (count == 0)
printf("
\n\n
\n");
+if (detailsTableFields)
+ {
+ printf("
\n");
+ printExtraDetailsTable(tdb->track, extraDetailsTableName, extraDetails, extraTblStr);
+ }
+
return count;
}
int extraFieldsPrint(struct trackDb *tdb,struct sqlResult *sr,char **fields,int fieldCount)
// Any extra bed or bigBed fields (defined in as and occurring after N in bed N + types.
// sr may be null for bigBeds.
// Returns number of extra fields actually printed.
{
struct asObject *as = asForDb(tdb, database);
if (as == NULL)
return 0;
int ret = extraFieldsPrintAs(tdb, sr, fields,fieldCount, as);
//asObjectFree(&as);