def _draw_jig(self, glpane, color, highlighted = False):
        """
        [overrides superclass method]
        """
        del color
        self._update_props()
        if not self._should_draw():
            return

        drawrad = 0.1
        posns = [a.posn() for a in self.atoms]
        normcolor = self._drawing_color()

        # russ 080530: Support for patterned highlighting drawing modes.
        selected = self.picked
        patterned = isPatternedDrawing(select = selected, highlight = highlighted)
        if patterned:
            # Patterned selection drawing needs the normal drawing first.
            drawcylinder( normcolor, posns[0], posns[1], drawrad)
            startPatternedDrawing(select = selected, highlight = highlighted)
            pass
        # Draw solid color, or overlay pattern in highlight or selection color.
        drawcylinder(
            (highlighted and env.prefs[hoverHighlightingColor_prefs_key] or
             selected and env.prefs[selectionColor_prefs_key] or
             normcolor), posns[0], posns[1], drawrad)
        if patterned:
            # Reset from patterned drawing mode.
            endPatternedDrawing(select = selected, highlight = highlighted)
            pass
        return
    def _draw_jig(self, glpane, color, highlighted=False):
        """
        [overrides superclass method]
        """
        del color
        self._update_props()
        if not self._should_draw():
            return

        drawrad = 0.1
        posns = [a.posn() for a in self.atoms]
        normcolor = self._drawing_color()

        # russ 080530: Support for patterned highlighting drawing modes.
        selected = self.picked
        patterned = isPatternedDrawing(select=selected, highlight=highlighted)
        if patterned:
            # Patterned selection drawing needs the normal drawing first.
            drawcylinder(normcolor, posns[0], posns[1], drawrad)
            startPatternedDrawing(select=selected, highlight=highlighted)
            pass
        # Draw solid color, or overlay pattern in highlight or selection color.
        drawcylinder(
            (highlighted and env.prefs[hoverHighlightingColor_prefs_key]
             or selected and env.prefs[selectionColor_prefs_key] or normcolor),
            posns[0], posns[1], drawrad)
        if patterned:
            # Reset from patterned drawing mode.
            endPatternedDrawing(select=selected, highlight=highlighted)
            pass
        return
Exemplo n.º 3
0
    def draw(
            self,
            highlighted=False,
            selected=False,
            patterning=True,
            highlight_color=None,
            draw_shader_primitives=True,  #bruce 090312 renamed from draw_primitives
            transform_nonshaders=True,  #bruce 090312 renamed from transform_DLs
    ):
        """
        Simple all-in-one interface to CSDL drawing.

        Allocate a CSDL in the parent class and fill it with the ColorSorter:
            self.csdl = ColorSortedDisplayList()
            ColorSorter.start(glpane, self.csdl)
            drawsphere(...), drawcylinder(...), drawpolycone(...), and so on.
            ColorSorter.finish()

        Then when you want to draw the display lists call csdl.draw() with the
        desired options:

        @param highlighted: Whether to draw highlighted.

        @param selected: Whether to draw selected.

        @param patterning: Whether to apply patterned drawing styles for
          highlighting and selection, according to the prefs settings.
          If not set, it's as if the solid-color prefs are chosen.

        @param highlight_color: Option to over-ride the highlight color set in
          the color scheme preferences.

        @param draw_shader_primitives: Whether to draw our shader primitives.
            Defaults to True.

        @param transform_nonshaders: Whether to apply self.transformControl to
            our non-shader drawing (such as DLs). Defaults to True.
        """

        patterned_highlighting = (patterning and
                                  isPatternedDrawing(highlight=highlighted))
        halo_selection = (selected and env.prefs[selectionColorStyle_prefs_key]
                          == SS_HALO)
        halo_highlighting = (
            highlighted
            and env.prefs[hoverHighlightingColorStyle_prefs_key] == HHS_HALO)

        # KLUGES which should be replaced by our having suitable new attrs,
        # such as glpane or glprefs or glresourcecontext (replacing drawing_globals):

        drawing_phase = drawing_globals.drawing_phase  # kluge in CSDL.draw

        # (the other kluge is not having glpane.glprefs to pass to apply_material,
        #  in draw; we do have glpane in finish but no point in using it there
        #  until we have it in .draw too, preferably by attr rather than arg
        #  (should review that opinion).)

        # Russ 081128 (clarified, bruce 090218):
        #
        # GLPrimitiveSet.draw() calls this method (CSDL.draw) on the CSDLs
        # in its _CSDLs_with_nonshader_drawing attribute (a list of CSDLs),
        # passing draw_shader_primitives = False to only draw the DLs, and
        # transform_nonshaders = False to avoid redundantly applying their
        # TransformControls.
        #
        # It gathers the shader primitives in a set of CSDLs into one big
        # drawIndex per primitive type, and draws each drawIndex in a big batch.
        #
        # This method (CSDL.draw) is also called to
        # draw *both* DLs and primitives in a CSDL, e.g. for hover-highlighting.
        #
        # Russ 081208: Skip drawing shader primitives while in GL_SELECT.
        #
        # Bruce 090218: support cylinders too.
        prims_to_do = (drawing_phase != "glselect" and draw_shader_primitives
                       and (self.spheres or self.cylinders))
        if prims_to_do:
            # Cache drawing indices for just the primitives in this CSDL,
            # in self.drawIndices, used in self.draw_shader_primitives below.
            if not self.drawIndices:
                for shader, primitives in self.shaders_and_primitive_lists():
                    self.drawIndices[shader] = shader.makeDrawIndex(primitives)
                    continue
                pass
            pass

        if self._drawing_funcs and drawing_phase != "glselect_glname_color":  #bruce 090312
            # These ignore our drawing-style args;
            # they also are cleared independently of start/finish,
            # and changing them doesn't set our last-changed timestamp.
            # All this is intentional. (Though we might decide to add a kind
            # which does participate in patterned drawing; this might require
            # supplying more than one func, or a dict of colors and nocolor
            # funcs....)
            if self.transformControl and transform_nonshaders:
                glPushMatrix()
                self.transformControl.applyTransform()
            for func in self._drawing_funcs:
                try:
                    func()
                except:
                    msg = "bug: exception in drawing_func %r in %r, skipping it" % (
                        func, self)
                    print_compact_traceback(msg + ": ")
                    pass
                continue
            if self.transformControl and transform_nonshaders:
                glPopMatrix()
            pass

        # Normal or selected drawing are done before a patterned highlight
        # overlay, and also when not highlighting at all.  You'd think that when
        # we're drawing a solid highlight appearance, there'd be no need to draw
        # the normal appearance first, because it will be obscured by the
        # highlight.  But halo selection extends beyond the object and is only
        # obscured by halo highlighting.  [russ 080610]
        # Russ 081208: Skip DLs when drawing shader-prims with glnames-as-color.
        DLs_to_do = (drawing_phase != "glselect_glname_color"
                     and self.has_nonempty_DLs())

        # the following might be changed, then are used repeatedly below;
        # this simplifies the various ways we can handle transforms [bruce 090224]
        callList = glCallList  # how to call a DL, perhaps inside our transform
        transform_once = False  # whether to transform exactly once around the
        # following code (as opposed to not at all, or once per callList)

        if self.transformControl and transform_nonshaders:
            if prims_to_do and DLs_to_do:
                # shader primitives have transform built in, but DLs don't,
                # so we need to get in and out of local coords repeatedly
                # (once for each callList) during the following
                # (note similar code in DrawingSet.draw): [bruce 090224]
                callList = self._callList_inside_transformControl
            elif DLs_to_do:
                # we need to get into and out of local coords just once
                transform_once = True
            else:
                pass  # nothing special needed for just shader prims (or nothing)
            pass

        if transform_once:
            glPushMatrix()
            self.transformControl.applyTransform()

        if (patterned_highlighting or not highlighted
                or (halo_selection and not halo_highlighting)):
            if selected:
                # Draw the selected appearance.
                if prims_to_do:  # Shader primitives.
                    self.draw_shader_primitives(highlighted, selected,
                                                patterning, highlight_color)
                    pass

                if DLs_to_do:  # Display lists.
                    # If the selection mode is patterned, the selected_dl does
                    # first normal drawing and then draws an overlay.
                    callList(self.selected_dl)
                    pass
                pass
            else:
                # Plain, old, solid drawing of the base object appearance.
                if prims_to_do:
                    self.draw_shader_primitives()  # Shader primitives.
                    pass

                if DLs_to_do:
                    callList(self.color_dl)  # Display lists.
                    pass
                pass
            pass

        if highlighted:

            if prims_to_do:  # Shader primitives.
                self.draw_shader_primitives(highlighted, selected, patterning,
                                            highlight_color)
                pass

            if DLs_to_do:  # Display lists.
                if patterned_highlighting:
                    # Set up a patterned drawing mode for the following draw.
                    startPatternedDrawing(highlight=highlighted)
                    pass

                # Draw a highlight overlay (solid, or in an overlay pattern.)
                if highlight_color is not None:
                    hcolor = highlight_color
                else:
                    hcolor = env.prefs[hoverHighlightingColor_prefs_key]
                apply_material(hcolor)
                callList(self.nocolor_dl)

                if patterned_highlighting:
                    # Reset from a patterned drawing mode set up above.
                    endPatternedDrawing(highlight=highlighted)
                    pass
                pass

            pass

        if transform_once:
            glPopMatrix()

        return
Exemplo n.º 4
0
    def finish(self, sorted_by_color):  #bruce 090224 split this out of caller
        """
        Finish collecting new primitives for use in self, and store them all
        in self, ready to be drawn in various ways.

        [meant to be called only by ColorSorter.start, for now]
        """
        ##        self._reset()
        ##            # (note: this deallocates any existing display lists)

        if self.transformControl and (self.spheres or self.cylinders):
            self.updateTransform()
            # needed to do the transform for the first time,
            # even if it didn't change. Review: refactor to
            # whereever we first compile these down? That
            # might be a different place in self.draw vs.
            # draw from DrawingSet.

        selColor = env.prefs[selectionColor_prefs_key]

        # Note: if sorted_by_color is empty, current code still builds all
        # toplevel display lists, though they are noops. This may be needed
        # by some client code which uses those dls directly. Client code
        # wanting to know if it needs to draw our dls should test
        # self.has_nonempty_DLs(), which tests self._per_color_dls,
        # or self.has_nonshader_drawing(), which reports on that or any
        # other kind of nonshader (immediate mode opengl) drawing we might
        # have. [bruce 090225/090312 comment]

        # First build the lower level per-color sublists of primitives.

        for color, funcs in sorted_by_color.iteritems():
            sublists = [glGenLists(1), 0]

            # Remember the display list ID for this color.
            self._per_color_dls.append([color, sublists])

            glNewList(sublists[0], GL_COMPILE)
            opacity = color[3]

            if opacity == -1:
                #russ 080306: "Unshaded colors" for lines are signaled
                # by an opacity of -1 (4th component of the color.)
                glDisable(GL_LIGHTING)  # Don't forget to re-enable it!
                pass

            for func, params, name in funcs:
                if name:
                    glPushName(name)
                else:
                    pass  ## print "bug_2: attempt to push non-glname", name
                func(params)  # Call the draw worker function.
                if name:
                    glPopName()
                    pass
                continue

            if opacity == -1:
                # Enable lighting after drawing "unshaded" objects.
                glEnable(GL_LIGHTING)
                pass
            glEndList()

            if opacity == -2:
                # piotr 080419: Special case for drawpolycone_multicolor
                # create another display list that ignores
                # the contents of color_array.
                # Remember the display list ID for this color.

                sublists[1] = glGenLists(1)

                glNewList(sublists[1], GL_COMPILE)

                for func, params, name in funcs:
                    if name:
                        glPushName(name)
                    else:
                        pass  ## print "bug_3: attempt to push non-glname", name
                    if func == drawpolycone_multicolor_worker:
                        # Just to be sure, check if the func
                        # is drawpolycone_multicolor_worker
                        # and call drawpolycone_worker instead.
                        # I think in the future we can figure out
                        # a more general way of handling the
                        # GL_COLOR_MATERIAL objects. piotr 080420
                        pos_array, color_array_junk, rad_array = params
                        drawpolycone_worker((pos_array, rad_array))
                    elif func == drawtriangle_strip_worker:
                        # piotr 080710: Multi-color modification
                        # for triangle_strip primitive (used by
                        # reduced protein style).
                        pos_array, normal_array, color_array_junk = params
                        drawtriangle_strip_worker(
                            (pos_array, normal_array, None))
                    if name:
                        glPopName()
                        pass
                    continue
                glEndList()

            continue

        # Now the upper-level lists call all of the per-color sublists.
        #### REVIEW: these are created even when empty. Is that necessary?
        # [bruce 090224 Q]

        # One with colors.
        color_dl = self.color_dl = glGenLists(1)
        glNewList(color_dl, GL_COMPILE)

        for color, dls in self._per_color_dls:

            opacity = color[3]
            if opacity < 0:
                #russ 080306: "Unshaded colors" for lines are signaled
                # by a negative alpha.
                glColor3fv(color[:3])
                # piotr 080417: for opacity == -2, i.e. if
                # GL_COLOR_MATERIAL is enabled, the color is going
                # to be ignored, anyway, so it is not necessary
                # to be tested here
            else:
                apply_material(color)

            glCallList(dls[0])

            continue
        glEndList()

        # A second one without any colors.
        nocolor_dl = self.nocolor_dl = glGenLists(1)
        glNewList(nocolor_dl, GL_COMPILE)
        for color, dls in self._per_color_dls:
            opacity = color[3]

            if opacity == -2 \
               and dls[1] > 0:
                # piotr 080420: If GL_COLOR_MATERIAL is enabled,
                # use a regular, single color dl rather than the
                # multicolor one. Btw, dls[1] == 0 should never
                # happen.
                glCallList(dls[1])
            else:
                glCallList(dls[0])

        glEndList()

        # A third DL implements the selected appearance.
        selected_dl = self.selected_dl = glGenLists(1)
        glNewList(selected_dl, GL_COMPILE)
        # russ 080530: Support for patterned selection drawing modes.
        patterned = isPatternedDrawing(select=True)
        if patterned:
            # Patterned drawing needs the colored dl drawn first.
            glCallList(color_dl)
            startPatternedDrawing(select=True)
            pass
        # Draw solid color (unpatterned) or an overlay pattern, in the
        # selection color.
        apply_material(selColor)
        glCallList(nocolor_dl)
        if patterned:
            # Reset from patterning drawing mode.
            endPatternedDrawing(select=True)
        glEndList()
        pass
    def draw(
        self,
        highlighted=False,
        selected=False,
        patterning=True,
        highlight_color=None,
        draw_shader_primitives=True,  # bruce 090312 renamed from draw_primitives
        transform_nonshaders=True,  # bruce 090312 renamed from transform_DLs
    ):
        """
        Simple all-in-one interface to CSDL drawing.

        Allocate a CSDL in the parent class and fill it with the ColorSorter:
            self.csdl = ColorSortedDisplayList()
            ColorSorter.start(glpane, self.csdl)
            drawsphere(...), drawcylinder(...), drawpolycone(...), and so on.
            ColorSorter.finish()

        Then when you want to draw the display lists call csdl.draw() with the
        desired options:

        @param highlighted: Whether to draw highlighted.

        @param selected: Whether to draw selected.

        @param patterning: Whether to apply patterned drawing styles for
          highlighting and selection, according to the prefs settings.
          If not set, it's as if the solid-color prefs are chosen.

        @param highlight_color: Option to over-ride the highlight color set in
          the color scheme preferences.

        @param draw_shader_primitives: Whether to draw our shader primitives.
            Defaults to True.

        @param transform_nonshaders: Whether to apply self.transformControl to
            our non-shader drawing (such as DLs). Defaults to True.
        """

        patterned_highlighting = patterning and isPatternedDrawing(highlight=highlighted)
        halo_selection = selected and env.prefs[selectionColorStyle_prefs_key] == SS_HALO
        halo_highlighting = highlighted and env.prefs[hoverHighlightingColorStyle_prefs_key] == HHS_HALO

        # KLUGES which should be replaced by our having suitable new attrs,
        # such as glpane or glprefs or glresourcecontext (replacing drawing_globals):

        drawing_phase = drawing_globals.drawing_phase  # kluge in CSDL.draw

        # (the other kluge is not having glpane.glprefs to pass to apply_material,
        #  in draw; we do have glpane in finish but no point in using it there
        #  until we have it in .draw too, preferably by attr rather than arg
        #  (should review that opinion).)

        # Russ 081128 (clarified, bruce 090218):
        #
        # GLPrimitiveSet.draw() calls this method (CSDL.draw) on the CSDLs
        # in its _CSDLs_with_nonshader_drawing attribute (a list of CSDLs),
        # passing draw_shader_primitives = False to only draw the DLs, and
        # transform_nonshaders = False to avoid redundantly applying their
        # TransformControls.
        #
        # It gathers the shader primitives in a set of CSDLs into one big
        # drawIndex per primitive type, and draws each drawIndex in a big batch.
        #
        # This method (CSDL.draw) is also called to
        # draw *both* DLs and primitives in a CSDL, e.g. for hover-highlighting.
        #
        # Russ 081208: Skip drawing shader primitives while in GL_SELECT.
        #
        # Bruce 090218: support cylinders too.
        prims_to_do = drawing_phase != "glselect" and draw_shader_primitives and (self.spheres or self.cylinders)
        if prims_to_do:
            # Cache drawing indices for just the primitives in this CSDL,
            # in self.drawIndices, used in self.draw_shader_primitives below.
            if not self.drawIndices:
                for shader, primitives in self.shaders_and_primitive_lists():
                    self.drawIndices[shader] = shader.makeDrawIndex(primitives)
                    continue
                pass
            pass

        if self._drawing_funcs and drawing_phase != "glselect_glname_color":  # bruce 090312
            # These ignore our drawing-style args;
            # they also are cleared independently of start/finish,
            # and changing them doesn't set our last-changed timestamp.
            # All this is intentional. (Though we might decide to add a kind
            # which does participate in patterned drawing; this might require
            # supplying more than one func, or a dict of colors and nocolor
            # funcs....)
            if self.transformControl and transform_nonshaders:
                glPushMatrix()
                self.transformControl.applyTransform()
            for func in self._drawing_funcs:
                try:
                    func()
                except:
                    msg = "bug: exception in drawing_func %r in %r, skipping it" % (func, self)
                    print_compact_traceback(msg + ": ")
                    pass
                continue
            if self.transformControl and transform_nonshaders:
                glPopMatrix()
            pass

        # Normal or selected drawing are done before a patterned highlight
        # overlay, and also when not highlighting at all.  You'd think that when
        # we're drawing a solid highlight appearance, there'd be no need to draw
        # the normal appearance first, because it will be obscured by the
        # highlight.  But halo selection extends beyond the object and is only
        # obscured by halo highlighting.  [russ 080610]
        # Russ 081208: Skip DLs when drawing shader-prims with glnames-as-color.
        DLs_to_do = drawing_phase != "glselect_glname_color" and self.has_nonempty_DLs()

        # the following might be changed, then are used repeatedly below;
        # this simplifies the various ways we can handle transforms [bruce 090224]
        callList = glCallList  # how to call a DL, perhaps inside our transform
        transform_once = False  # whether to transform exactly once around the
        # following code (as opposed to not at all, or once per callList)

        if self.transformControl and transform_nonshaders:
            if prims_to_do and DLs_to_do:
                # shader primitives have transform built in, but DLs don't,
                # so we need to get in and out of local coords repeatedly
                # (once for each callList) during the following
                # (note similar code in DrawingSet.draw): [bruce 090224]
                callList = self._callList_inside_transformControl
            elif DLs_to_do:
                # we need to get into and out of local coords just once
                transform_once = True
            else:
                pass  # nothing special needed for just shader prims (or nothing)
            pass

        if transform_once:
            glPushMatrix()
            self.transformControl.applyTransform()

        if patterned_highlighting or not highlighted or (halo_selection and not halo_highlighting):
            if selected:
                # Draw the selected appearance.
                if prims_to_do:  # Shader primitives.
                    self.draw_shader_primitives(highlighted, selected, patterning, highlight_color)
                    pass

                if DLs_to_do:  # Display lists.
                    # If the selection mode is patterned, the selected_dl does
                    # first normal drawing and then draws an overlay.
                    callList(self.selected_dl)
                    pass
                pass
            else:
                # Plain, old, solid drawing of the base object appearance.
                if prims_to_do:
                    self.draw_shader_primitives()  # Shader primitives.
                    pass

                if DLs_to_do:
                    callList(self.color_dl)  # Display lists.
                    pass
                pass
            pass

        if highlighted:

            if prims_to_do:  # Shader primitives.
                self.draw_shader_primitives(highlighted, selected, patterning, highlight_color)
                pass

            if DLs_to_do:  # Display lists.
                if patterned_highlighting:
                    # Set up a patterned drawing mode for the following draw.
                    startPatternedDrawing(highlight=highlighted)
                    pass

                # Draw a highlight overlay (solid, or in an overlay pattern.)
                if highlight_color is not None:
                    hcolor = highlight_color
                else:
                    hcolor = env.prefs[hoverHighlightingColor_prefs_key]
                apply_material(hcolor)
                callList(self.nocolor_dl)

                if patterned_highlighting:
                    # Reset from a patterned drawing mode set up above.
                    endPatternedDrawing(highlight=highlighted)
                    pass
                pass

            pass

        if transform_once:
            glPopMatrix()

        return
    def finish(self, sorted_by_color):  # bruce 090224 split this out of caller
        """
        Finish collecting new primitives for use in self, and store them all
        in self, ready to be drawn in various ways.

        [meant to be called only by ColorSorter.start, for now]
        """
        ##        self._reset()
        ##            # (note: this deallocates any existing display lists)

        if self.transformControl and (self.spheres or self.cylinders):
            self.updateTransform()
            # needed to do the transform for the first time,
            # even if it didn't change. Review: refactor to
            # whereever we first compile these down? That
            # might be a different place in self.draw vs.
            # draw from DrawingSet.

        selColor = env.prefs[selectionColor_prefs_key]

        # Note: if sorted_by_color is empty, current code still builds all
        # toplevel display lists, though they are noops. This may be needed
        # by some client code which uses those dls directly. Client code
        # wanting to know if it needs to draw our dls should test
        # self.has_nonempty_DLs(), which tests self._per_color_dls,
        # or self.has_nonshader_drawing(), which reports on that or any
        # other kind of nonshader (immediate mode opengl) drawing we might
        # have. [bruce 090225/090312 comment]

        # First build the lower level per-color sublists of primitives.

        for color, funcs in sorted_by_color.iteritems():
            sublists = [glGenLists(1), 0]

            # Remember the display list ID for this color.
            self._per_color_dls.append([color, sublists])

            glNewList(sublists[0], GL_COMPILE)
            opacity = color[3]

            if opacity == -1:
                # russ 080306: "Unshaded colors" for lines are signaled
                # by an opacity of -1 (4th component of the color.)
                glDisable(GL_LIGHTING)  # Don't forget to re-enable it!
                pass

            for func, params, name in funcs:
                if name:
                    glPushName(name)
                else:
                    pass  ## print "bug_2: attempt to push non-glname", name
                func(params)  # Call the draw worker function.
                if name:
                    glPopName()
                    pass
                continue

            if opacity == -1:
                # Enable lighting after drawing "unshaded" objects.
                glEnable(GL_LIGHTING)
                pass
            glEndList()

            if opacity == -2:
                # piotr 080419: Special case for drawpolycone_multicolor
                # create another display list that ignores
                # the contents of color_array.
                # Remember the display list ID for this color.

                sublists[1] = glGenLists(1)

                glNewList(sublists[1], GL_COMPILE)

                for func, params, name in funcs:
                    if name:
                        glPushName(name)
                    else:
                        pass  ## print "bug_3: attempt to push non-glname", name
                    if func == drawpolycone_multicolor_worker:
                        # Just to be sure, check if the func
                        # is drawpolycone_multicolor_worker
                        # and call drawpolycone_worker instead.
                        # I think in the future we can figure out
                        # a more general way of handling the
                        # GL_COLOR_MATERIAL objects. piotr 080420
                        pos_array, color_array_junk, rad_array = params
                        drawpolycone_worker((pos_array, rad_array))
                    elif func == drawtriangle_strip_worker:
                        # piotr 080710: Multi-color modification
                        # for triangle_strip primitive (used by
                        # reduced protein style).
                        pos_array, normal_array, color_array_junk = params
                        drawtriangle_strip_worker((pos_array, normal_array, None))
                    if name:
                        glPopName()
                        pass
                    continue
                glEndList()

            continue

        # Now the upper-level lists call all of the per-color sublists.
        #### REVIEW: these are created even when empty. Is that necessary?
        # [bruce 090224 Q]

        # One with colors.
        color_dl = self.color_dl = glGenLists(1)
        glNewList(color_dl, GL_COMPILE)

        for color, dls in self._per_color_dls:

            opacity = color[3]
            if opacity < 0:
                # russ 080306: "Unshaded colors" for lines are signaled
                # by a negative alpha.
                glColor3fv(color[:3])
                # piotr 080417: for opacity == -2, i.e. if
                # GL_COLOR_MATERIAL is enabled, the color is going
                # to be ignored, anyway, so it is not necessary
                # to be tested here
            else:
                apply_material(color)

            glCallList(dls[0])

            continue
        glEndList()

        # A second one without any colors.
        nocolor_dl = self.nocolor_dl = glGenLists(1)
        glNewList(nocolor_dl, GL_COMPILE)
        for color, dls in self._per_color_dls:
            opacity = color[3]

            if opacity == -2 and dls[1] > 0:
                # piotr 080420: If GL_COLOR_MATERIAL is enabled,
                # use a regular, single color dl rather than the
                # multicolor one. Btw, dls[1] == 0 should never
                # happen.
                glCallList(dls[1])
            else:
                glCallList(dls[0])

        glEndList()

        # A third DL implements the selected appearance.
        selected_dl = self.selected_dl = glGenLists(1)
        glNewList(selected_dl, GL_COMPILE)
        # russ 080530: Support for patterned selection drawing modes.
        patterned = isPatternedDrawing(select=True)
        if patterned:
            # Patterned drawing needs the colored dl drawn first.
            glCallList(color_dl)
            startPatternedDrawing(select=True)
            pass
        # Draw solid color (unpatterned) or an overlay pattern, in the
        # selection color.
        apply_material(selColor)
        glCallList(nocolor_dl)
        if patterned:
            # Reset from patterning drawing mode.
            endPatternedDrawing(select=True)
        glEndList()
        pass