Create/Add new layer(s) with custom properties

Hi all,

I found a lot of ways to create layers from scripts during my (re)search in the forum, and some of them work for some cases but not for all, or they just stop, and, in general, is a hot topic that always recurs to the most of the KLayout users.

I wanted to ask, is there a code example with a correct way to add a new layer with custom layer properties (e.g. dither_pattern and xfill), and return the index of this layer so it can be used to draw a new object?

Thank you in advance,


  • For reference, this is what I currently use, unsuccessfully:

    def create_layer(
        stream_num     = None,
        data_type      = None,
        dither_pattern = 5,
        fill_color     = 0xff0000,
        frame_color    = 0xff0000,
        width          = 1,
        animation      = 0,
        transparent    = 1,
        visible        = True,
        xfill          = False
        curr_layout_view = pya.LayoutView().current()
        curr_cell_view   = curr_layout_view.active_cellview()
        curr_cell_layout = curr_cell_view.layout()
        if not stream_num :
            stream_num_list = [layer.source_layer for layer in curr_layout_view.each_layer() if not layer.source_name == name]
            stream_num = max(stream_num_list)+1 if stream_num_list else 255
        # if
        if not data_type :
            data_type_list = [layer.source_datatype for layer in curr_layout_view.each_layer() if not layer.source_name == name]
            data_type = max(data_type_list)+1 if data_type_list else 255
        # if
        layer_tech = name+" ("+str(stream_num)+"/"+str(data_type)+ ")"
        layer_info  = pya.LayerInfo(stream_num, data_type, name)
        layer_index = curr_cell_layout.layer(layer_info)
        layer_prop = pya.LayerProperties()
                  = layer_tech
        layer_prop.source_name        = layer_tech
        layer_prop.source_layer       = stream_num
        layer_prop.source_datatype    = data_type
        layer_prop.source_layer_index = layer_index
        layer_prop.dither_pattern     = dither_pattern
        layer_prop.fill_color         = fill_color
        layer_prop.frame_color        = frame_color
        layer_prop.width              = width
        layer_prop.animation          = animation
        layer_prop.transparent        = transparent
        layer_prop.visible            = visible
        curr_layout_view.insert_layer(curr_layout_view.end_layers(), layer_prop)
        return layer_index
    # create_layer
  • Hi Chris,

    actually, this is is the best way I can think of as well. It features everything you require in the general case.

    The API underwent some development, so in the forum there might be outdated versions. Yours is making the right use of the API features, so that's very good.

    I wonder whether you really like auto-picking of the stream numbers, but that's up to you of course. I personally think that if you work with named layers alone you should have a mapping table (see File/Writer Options) when you write such a layout to a GDS file. Only then the mapping is deterministic. But that's a personal viewpoint.

    I have a few general comments:

    • The layer does not need to actually be created with "curr_cell_layout.layer". If it's not created, KLayout will do this for you when you start drawing on it. That's why it's sufficient to load a .lyp file and have an empty layout.
    • "layer_prop.source_layer_index" does not need to be set as this is redundant. KLayout does not need this hint as name, layer and datatype are sufficient. You only need this hint when there is neither a name or layer/datatype.
    • For completeness, you can also set "source_cellview" to "curr_layout_view.active_cellview_index()". This is the "@1" ... in the layer source specification. With this enhancement, your function will also work when the active layout isn't the first one loaded.

    Thanks for sharing this code,


  • edited November 2019

    Hi Matthias,

    Thank you for confirming that this function should work, as I thought that this is the part of my code I should put my efforts on to correct, and for your enhancement comments.

    I updated my version with your last two comments, but as for the first comment, is there any other way I can retrieve the 'layer_index' of the new layer if I don't create it that way?

    Currently, this function creates two layers that are both used when I draw a DBox.
    Also, I should describe the part of the flow that this function does not work as it should:

    We have a PCell and let's say that the generation of the geometry "failed" because "reasons". So we are inside the 'produce_impl' procedure of the PCell, and we need a dummy indication that this PCell failed in its generation. For example, a box with a text that will say "PCell failed" or something (and that's why I don't really care about the stream number and the datatype). This is a corresponding sample code I would like to have:

    dummy_layer_index = create_layer(
                dither_pattern = 5,
                fill_color     = 0x000000,
                frame_color    = 0xff0000,
                width          = 2,
                animation      = 2,
                transparent    = True,
                visible        = True,
                xfill          = True
    dummy_box = pya.DBox(0.0,0.0,200.0,50.0)

    After the User changes PCell properties and the PCell is successfully generated, this dummy layer and shape will be deleted. Also is there any chance to add a layer, and set it as invisible in the Layers tab?


  • Hi Chris,

    The second comment is valid if you don't need the layer index .. if your code does then "layer" is the right function to use.

    Regarding the question about the PCell error layer: currently you can't create a hidden, but visible dummy layer. But it's basically a good suggestion to have such a global error layer. It could be used for many purposes, not just PCell layout generation.

    But basically, if your PCell layout generation code throws an exception, this would be shown as text in the layout. Is there something wrong with this feature?

    Kind regards,


  • edited December 2019

    Hi Matthias,

    OK, I see.

    For development purposes, it is just fine, but I don't want the user seeing "internal" failures. It is more UX friendly to prompt a "black box" failure.


  • So you mean you want to tailor the text you see?

    I guess a feature for this is easier to make than an entire new layer.


  • Hi Matthias,

    Well, as for the contents of the failure message, I've developed something using display_text_impl, but it is not about the text message only. I want to display a box, with a corresponding blinking effect, to indicate that something went astray.

    The problem, as I see it, is that I create the layer inside produce_impl so KLayout does not "see"/"know" the new layer properties so it creates extra layer properties and index, independently from what I've already created, with the same stream number and datatype.


  • Hi Chris,

    you cannot create a layer within a PCell - you can just access an existing one.

    I need to repeat once again that a PCell is not executed within the target layout. In fact, the layout object a PCell is run in is unspecified. Whatever you do to the layout the PCell is executed in won't necessarily affect your target layout. So please don't try. There are good reasons for this decision (i.e. caching), so this will not be changed.

    The projected solution to your problem is: include an error marker layer in your design package (aka technology/layer properties). Define a hidden parameter of layer type with the error layer as the default (via LayerProperties). This parameter will become available in the PCell code and you can output anything there like you would on a usual layer.

    Will this be feasible?


  • Hi Matthias,

    Ok, I thought that it is possible to create a layer to the main layout from wherever you are, whenever you want.

    Thank you for your answer, I think this will be my solution to this issue thank you.


Sign In or Register to comment.