Commit 53fa75c852

Loris Cro <kappaloris@gmail.com>
2022-03-28 18:50:52
autodoc: improved frontend rendering
1 parent 36c4b1a
Changed files (3)
lib/docs/index.html
@@ -634,7 +634,15 @@
               <h2>Examples</h2>
               <ul id="listFnExamples" class="examples"></ul>
             </div>
-          </section>
+             <div id="sectTests" class="hidden">
+              <h2>Tests</h2>
+              <div class="table-container">
+                <table>
+                  <tbody id="listTests"></tbody>
+                </table>
+              </div>
+            </div>
+		  </section>
         </div>
         <div class="flex-filler"></div>
       </div>
lib/docs/main.js
@@ -176,6 +176,8 @@ var zigAnalysis;
     var domListPkgs = document.getElementById("listPkgs");
     var domSectTypes = document.getElementById("sectTypes");
     var domListTypes = document.getElementById("listTypes");
+    var domSectTests = document.getElementById("sectTests");
+    var domListTests = document.getElementById("listTests");
     var domSectNamespaces = document.getElementById("sectNamespaces");
     var domListNamespaces = document.getElementById("listNamespaces");
     var domSectErrSets = document.getElementById("sectErrSets");
@@ -349,6 +351,7 @@ var zigAnalysis;
 
             if ("declRef" in value) {
                 value = zigAnalysis.decls[value.declRef].value;
+                continue;
             }
 
             return value;
@@ -439,6 +442,7 @@ var zigAnalysis;
         domSectMainPkg.classList.add("hidden");
         domSectPkgs.classList.add("hidden");
         domSectTypes.classList.add("hidden");
+        domSectTests.classList.add("hidden");
         domSectNamespaces.classList.add("hidden");
         domSectErrSets.classList.add("hidden");
         domSectFns.classList.add("hidden");
@@ -845,10 +849,10 @@ var zigAnalysis;
         if ("call" in typeValue) {
             var result = "";
             var call = zigAnalysis.calls[typeValue.call];
-            var functionName = typeValueName(call.func);
+            var functionName = typeValueName(call.func, wantHtml, wantLink, fnDecl, linkFnNameDecl);
             result += functionName + "(";
             for (var j = 0; j < call.args.length; j += 1) {
-              result += typeValueName(call.args[j]);
+              result += typeValueName(call.args[j], wantHtml, wantLink, fnDecl, linkFnNameDecl);
               if (j != call.args.length -1) result += ",";
             }
 
@@ -878,6 +882,22 @@ var zigAnalysis;
             return result;
         }
 
+        if ("declRef" in typeValue) {
+            return zigAnalysis.decls[typeValue.declRef].name;
+        }
+
+        if ("string" in typeValue) {
+            return typeValue.string + " (string)";
+        }
+
+        if ("anytype" in typeValue) {
+            return "anytype";
+        }
+
+        if ("this" in typeValue) {
+            return "this";
+        }
+
         console.assert("type" in typeValue)
         var typeIndex = typeValue.type;
         var typeObj = zigAnalysis.types[typeIndex];
@@ -1133,7 +1153,7 @@ var zigAnalysis;
                     if (typeObj.params) {
                         var fields = null;
                         var isVarArgs = false;
-                        var fnNode = zigAnalysis.astNodes[fnDecl.src];
+                        var fnNode = zigAnalysis.astNodes[typeObj.src];
                         fields = fnNode.fields;
                         isVarArgs = fnNode.varArgs;
 
@@ -1411,12 +1431,17 @@ var zigAnalysis;
 
     function categorizeDecls(decls,
         typesList, namespacesList, errSetsList,
-        fnsList, varsList, valsList) {
+        fnsList, varsList, valsList, testsList) {
 
         for (var i = 0; i < decls.length; i += 1) {
             var decl = zigAnalysis.decls[decls[i]];
             var declValue = resolveValue(decl.value);
 
+            if (decl.isTest) {
+                testsList.push(decl);
+                continue;
+            }
+
             if (decl.kind === 'var') {
                 varsList.push(decl);
                 continue;
@@ -1427,11 +1452,15 @@ var zigAnalysis;
                     let c  = zigAnalysis.calls[declValue.call];
                     console.assert("comptimeExpr" in c.ret);
                     let fDecl = resolveValue(c.func);
-                    console.assert("type" in fDecl);
-                    let fType = zigAnalysis.types[fDecl.type];
-                    console.assert("type" in fType.ret);
-                    if (fType.ret.type === typeTypeId) {
-                        typesList.push(decl);
+                    if ("type" in fDecl) {
+                        console.assert("type" in fDecl);
+                        let fType = zigAnalysis.types[fDecl.type];
+                        console.assert("type" in fType.ret);
+                        if (fType.ret.type === typeTypeId) {
+                            typesList.push(decl);
+                        } else {
+                            valsList.push(decl);
+                        }
                     } else {
                         valsList.push(decl);
                     }
@@ -1468,13 +1497,14 @@ var zigAnalysis;
         var fnsList = [];
         var varsList = [];
         var valsList = [];
+        var testsList = [];
 
         categorizeDecls(container.pubDecls,
             typesList, namespacesList, errSetsList,
-            fnsList, varsList, valsList);
+            fnsList, varsList, valsList, testsList);
         if (curNav.showPrivDecls) categorizeDecls(container.privDecls,
             typesList, namespacesList, errSetsList,
-            fnsList, varsList, valsList);
+            fnsList, varsList, valsList, testsList);
 
 
         typesList.sort(byNameProperty);
@@ -1483,6 +1513,7 @@ var zigAnalysis;
         fnsList.sort(byNameProperty);
         varsList.sort(byNameProperty);
         valsList.sort(byNameProperty);
+        testsList.sort(byNameProperty);
 
         if (container.src != null) {
             var docs = zigAnalysis.astNodes[container.src].docs;
@@ -1638,6 +1669,33 @@ var zigAnalysis;
             }
             domSectValues.classList.remove("hidden");
         }
+
+        if (testsList.length !== 0) {
+            resizeDomList(domListTests, testsList.length,
+                '<tr><td><a href="#"></a></td><td></td><td></td></tr>');
+            for (var i = 0; i < testsList.length; i += 1) {
+                var decl = testsList[i];
+                var trDom = domListTests.children[i];
+
+                var tdName = trDom.children[0];
+                var tdNameA = tdName.children[0];
+                var tdType = trDom.children[1];
+                var tdDesc = trDom.children[2];
+
+                tdNameA.setAttribute('href', navLinkDecl(decl.name));
+                tdNameA.textContent = decl.name;
+
+                tdType.innerHTML = typeValueName(typeOfDecl(decl), true, true);
+
+                var docs = zigAnalysis.astNodes[decl.src].docs;
+                if (docs != null) {
+                    tdDesc.innerHTML = shortDescMarkdown(docs);
+                } else {
+                    tdDesc.textContent = "";
+                }
+            }
+            domSectTests.classList.remove("hidden");
+        }
     }
 
     function operatorCompare(a, b) {
src/Autodoc.zig
@@ -354,6 +354,7 @@ const DocData = struct {
     const Decl = struct {
         name: []const u8,
         kind: []const u8,
+        isTest: bool,
         src: usize, // index into astNodes
         // typeRef: TypeRef,
         value: WalkResult,
@@ -621,7 +622,6 @@ const DocData = struct {
                 .@"undefined" => |v| try std.json.stringify(v, options, w),
                 .@"null" => |v| try std.json.stringify(v, options, w),
                 .typeOf, .sizeOf => |v| try std.json.stringify(v, options, w),
-                .compileError => |v| try std.json.stringify(v, options, w),
                 .fieldRef => |v| try std.json.stringify(
                     struct { fieldRef: FieldRef }{ .fieldRef = v },
                     options,
@@ -645,6 +645,11 @@ const DocData = struct {
                     options,
                     w,
                 ),
+                .compileError => |v| try std.json.stringify(
+                    struct { compileError: []const u8 }{ .compileError = v },
+                    options,
+                    w,
+                ),
                 .string => |v| try std.json.stringify(
                     struct { string: []const u8 }{ .string = v },
                     options,
@@ -1678,7 +1683,7 @@ fn walkDecls(
         extra_index += 1;
         const decl_name_index = file.zir.extra[extra_index];
         extra_index += 1;
-        const decl_index = file.zir.extra[extra_index];
+        const value_index = file.zir.extra[extra_index];
         extra_index += 1;
         const doc_comment_index = file.zir.extra[extra_index];
         extra_index += 1;
@@ -1722,7 +1727,7 @@ fn walkDecls(
                     const idx = self.ast_nodes.items.len;
                     const file_source = file.getSource(self.module.gpa) catch unreachable; // TODO fix this
                     const source_of_decltest_function = srcloc: {
-                        const func_index = getBlockInlineBreak(file.zir, decl_index);
+                        const func_index = getBlockInlineBreak(file.zir, value_index);
                         // a decltest is always a function
                         const tag = file.zir.instructions.items(.tag)[Zir.refToIndex(func_index).?];
                         std.debug.assert(tag == .extended);
@@ -1785,6 +1790,7 @@ fn walkDecls(
                 self.decls.items[decls_slot_index] = .{
                     ._analyzed = true,
                     .name = "test",
+                    .isTest = true,
                     .src = ast_node_index,
                     .value = .{ .type = 0 },
                     .kind = "const",
@@ -1822,7 +1828,7 @@ fn walkDecls(
         const walk_result = if (is_test) // TODO: decide if tests should show up at all
             DocData.WalkResult{ .void = {} }
         else
-            try self.walkInstruction(file, scope, decl_index);
+            try self.walkInstruction(file, scope, value_index);
 
         if (is_pub) {
             try decl_indexes.append(self.arena, decls_slot_index);
@@ -1848,6 +1854,7 @@ fn walkDecls(
         self.decls.items[decls_slot_index] = .{
             ._analyzed = true,
             .name = name,
+            .isTest = is_test,
             .src = ast_node_index,
             // .typeRef = decl_type_ref,
             .value = walk_result,
@@ -1859,7 +1866,7 @@ fn walkDecls(
             for (paths.items) |resume_info| {
                 try self.tryResolveRefPath(
                     resume_info.file,
-                    decl_index,
+                    value_index,
                     resume_info.ref_path,
                 );
             }
@@ -2283,7 +2290,7 @@ fn analyzeFunction(
             .ret = ret_type_ref,
         },
     };
-    return DocData.WalkResult{ .type = self.types.items.len - 1 };
+    return DocData.WalkResult{ .type = type_slot_index };
 }
 
 fn collectUnionFieldInfo(
@@ -2553,10 +2560,12 @@ fn typeOfWalkResult(self: *Autodoc, wr: DocData.WalkResult) !DocData.WalkResult
 }
 
 fn getBlockInlineBreak(zir: Zir, inst_index: usize) Zir.Inst.Ref {
+    const tags = zir.instructions.items(.tag);
     const data = zir.instructions.items(.data);
     const pl_node = data[inst_index].pl_node;
     const extra = zir.extraData(Zir.Inst.Block, pl_node.payload_index);
     const break_index = zir.extra[extra.end..][extra.data.body_len - 1];
+    std.debug.assert(tags[break_index] == .break_inline);
     return data[break_index].@"break".operand;
 }