def zAxis(self, row, zStructuralNode, zAspectStructuralNodes, discriminatorsTable):
        if zStructuralNode is not None:
            label = zStructuralNode.header(lang=self.lang)
            choiceLabel = None
            effectiveStructuralNode = zStructuralNode
            if zStructuralNode.choiceStructuralNodes: # same as combo box selection in GUI mode
                if not discriminatorsTable:
                    self.zStrNodesWithChoices.insert(0, zStructuralNode) # iteration from last is first
                try:
                    effectiveStructuralNode = zStructuralNode.choiceStructuralNodes[zStructuralNode.choiceNodeIndex]
                    choiceLabel = effectiveStructuralNode.header(lang=self.lang)
                    if not label and choiceLabel:
                        label = choiceLabel # no header for choice
                        choiceLabel = None
                except __HOLE__:
                    pass
            if choiceLabel:
                if self.dataCols > 3:
                    zLabelSpan = 2
                else:
                    zLabelSpan = 1
                zChoiceLabelSpan = self.dataCols - zLabelSpan
            else:
                zLabelSpan = self.dataCols
            if self.type == HTML:
                etree.SubElement(self.rowElts[row-1], "{http://www.w3.org/1999/xhtml}th",
                                 attrib={"class":"zAxisHdr",
                                         "style":"max-width:200pt;text-align:left;border-bottom:.5pt solid windowtext",
                                         "colspan": str(zLabelSpan)} # "2"}
                                 ).text = label
                if choiceLabel:
                    etree.SubElement(self.rowElts[row-1], "{http://www.w3.org/1999/xhtml}th",
                                     attrib={"class":"zAxisHdr",
                                             "style":"max-width:200pt;text-align:left;border-bottom:.5pt solid windowtext",
                                             "colspan": str(zChoiceLabelSpan)} # "2"}
                                     ).text = choiceLabel
            elif self.type == XML:
                # headers element built for first pass on z axis
                if discriminatorsTable:
                    brkdownNode = zStructuralNode.breakdownNode
                    if zStructuralNode.choiceStructuralNodes: # same as combo box selection in GUI mode
                        # hdrElt.set("label", label)
                        if discriminatorsTable:
                            def zSpan(zNode, startNode=False):
                                if startNode:
                                    thisSpan = 0
                                elif zStructuralNode.choiceStructuralNodes:
                                    thisSpan = len(zStructuralNode.choiceStructuralNodes)
                                else:
                                    thisSpan = 1
                                return sum(zSpan(z) for z in zNode.childStructuralNodes) + thisSpan
                            span = zSpan(zStructuralNode, True)
                            for i, choiceStructuralNode in enumerate(zStructuralNode.choiceStructuralNodes):
                                choiceLabel = choiceStructuralNode.header(lang=self.lang)
                                cellElt = etree.Element(self.tableModelQName("cell"),
                                                        attrib={"span": str(span)} if span > 1 else None)
                                self.headerCells[i].append((brkdownNode, cellElt))
                                # self.structuralNodeModelElements.append((zStructuralNode, cellElt))
                                elt = etree.SubElement(cellElt, self.tableModelQName("label"))
                                if choiceLabel:
                                    elt.text = choiceLabel
                        #else: # choiceLabel from above 
                        #    etree.SubElement(hdrElt, self.tableModelQName("label")
                        #                     ).text = choiceLabel
                    else: # no combo choices, single label
                        cellElt = etree.Element(self.tableModelQName("cell"))
                        self.headerCells[0].append((brkdownNode, cellElt))
                        # self.structuralNodeModelElements.append((zStructuralNode, cellElt))
                        elt = etree.SubElement(cellElt, self.tableModelQName("label"))
                        if label:
                            elt.text = label

            for aspect in aspectModels[self.aspectModel]:
                if effectiveStructuralNode.hasAspect(aspect, inherit=True): #implies inheriting from other z axes
                    if aspect == Aspect.DIMENSIONS:
                        for dim in (effectiveStructuralNode.aspectValue(Aspect.DIMENSIONS, inherit=True) or emptyList):
                            zAspectStructuralNodes[dim].add(effectiveStructuralNode)
                    else:
                        zAspectStructuralNodes[aspect].add(effectiveStructuralNode)
            for zStructuralNode in zStructuralNode.childStructuralNodes:
                self.zAxis(row + 1, zStructuralNode, zAspectStructuralNodes, discriminatorsTable)
dataset/ETHPy150Open Arelle/Arelle/arelle/ViewFileRenderedGrid.py/ViewRenderedGrid.zAxis