unsafe private void DrawFixedRings(float radius, float scale, Graphics g)
        {
            //SmoothingMode old_mode = g.SmoothingMode;
            //g.SmoothingMode = SmoothingMode.AntiAlias;

            int         ring_count = this.mesher.GetNumberOfRings();
            RingStruct *ring_ptr   = this.mesher.GetFirstRing();

            using (Pen pen = new Pen(this.cRings.SelectedColor))
                for (int i = 0; i < ring_count; i++)
                {
                    RingStruct *r = &ring_ptr[i];
                    if ((r->radius == 0) || (!r->@fixed))
                    {
                        continue;
                    }
                    g.DrawEllipse(pen,
                                  (float)((radius - r->radius) * scale + 5),
                                  (float)((radius - r->radius) * scale + 5),
                                  (float)((r->radius * 2) * scale),
                                  (float)((r->radius * 2) * scale)
                                  );
                }

            //g.SmoothingMode = old_mode;
        }
        /*
         * private unsafe void UpdatePreview()
         * {
         *  float radius = (float)this.mesher.GetRadius();
         *  float sx = (this.pictureBox1.Width - 10) / (radius * 2);
         *  float sy = (this.pictureBox1.Height - 10) / (radius * 2);
         *  float scale = Math.Min(sx, sy);
         *
         *  Bitmap bmp = new Bitmap(this.pictureBox1.Width, this.pictureBox1.Height, System.Drawing.Imaging.PixelFormat.Format32bppRgb);
         *  using (Graphics g = Graphics.FromImage(bmp))
         *  {
         *      g.FillRectangle(Brushes.White, new Rectangle(Point.Empty, bmp.Size));
         *
         *      int node_count = this.mesher.GetNumberOfPlainNodes();
         *      NodeStruct* node_ptr = this.mesher.GetFirstPlainNode();
         *      int element_count = this.mesher.GetNumberOfPlainElements();
         *      ElementStruct* element_ptr = this.mesher.GetFirstPlainElement();
         *      int ring_count = this.mesher.GetNumberOfRings();
         *      RingStruct* ring_ptr = this.mesher.GetFirstRing();
         *
         *      for (int i = 0; i < element_count; i++, element_ptr++)
         *      {
         *          NodeStruct* n1 = &node_ptr[element_ptr->node1];
         *          NodeStruct* n2 = &node_ptr[element_ptr->node2];
         *          NodeStruct* n3 = &node_ptr[element_ptr->node3];
         *
         *          float x1 = (float)(n1->x * scale + 5);
         *          float y1 = (float)((2 * radius - n1->y) * scale + 5);
         *          float x2 = (float)(n2->x * scale + 5);
         *          float y2 = (float)((2 * radius - n2->y) * scale + 5);
         *          float x3 = (float)(n3->x * scale + 5);
         *          float y3 = (float)((2 * radius - n3->y) * scale + 5);
         *
         *          g.DrawLines(Pens.Black, new PointF[] { new PointF(x1, y1), new PointF(x2, y2), new PointF(x3, y3) });
         *      }
         *
         *      for (int i = 0; i < ring_count; i++)
         *      {
         *          RingStruct* r = &ring_ptr[i];
         *          if ((r->radius == 0) || (!r->@fixed))
         *              continue;
         *          g.DrawEllipse(Pens.Red,
         *              (float)((radius - r->radius) * scale + 5),
         *              (float)((radius - r->radius) * scale + 5),
         *              (float)((r->radius * 2) * scale),
         *              (float)((r->radius * 2) * scale)
         *              );
         *      }
         *
         *      for (int i = 0; i < node_count; i++, node_ptr++)
         *      {
         *          float nx = (float)(node_ptr->x * scale + 5);
         *          float ny = (float)((2 * radius - node_ptr->y) * scale + 5);
         *          g.FillRectangle(Brushes.DarkGreen, nx - 1, ny - 1, 3, 3);
         *      }
         *
         *      // sparse function
         *      float step = 0.5f;
         *      float x = step;
         *      using(Pen p = new Pen(Color.Red, 2))
         *          while (x <= radius)
         *          {
         *              float y1 = (float)this.mesher.SparseFunction(x - step);
         *              float y2 = (float)this.mesher.SparseFunction(x);
         *              //y1 = x - step;
         *              //y2 = x;
         *              float x1 = (float)((radius + x - step) * scale + 5);
         *              float x2 = (float)((radius + x) * scale + 5);
         *              y1 = (float)((radius - y1) * scale + 5);
         *              y2 = (float)((radius - y2) * scale + 5);
         *              g.DrawLine(p, x1, y1, x2, y2);
         *              x += step;
         *          }
         *  }
         *
         *  this.pictureBox1.Image = bmp;
         * }
         */

        private unsafe void UpdateListView()
        {
            this.listView1.Items.Clear();
            int         ring_count = this.mesher.GetNumberOfRings();
            RingStruct *rs         = this.mesher.GetFirstRing();
            RingStruct *old_rs     = this.mesher.GetFirstRing();

            for (int i = 0; i < ring_count; i++, old_rs = rs, rs++)
            {
                int          nodes = this.mesher.GetNumberOfNodesOnRing(i);
                ListViewItem li    = new ListViewItem(new string[] {
                    rs->radius.ToString("N3"),
                    (rs->radius - old_rs->radius).ToString("N3"),
                    rs->density.ToString("N3"),
                    (rs->density - old_rs->density).ToString("N3"),
                    nodes.ToString()
                });

                if (rs->error)
                {
                    li.ForeColor = Color.Red;
                }
                this.listView1.Items.Add(li);
            }

            // statystyka

            int base_nodes     = this.mesher.GetNumberOfPlainNodes();
            int base_triangles = this.mesher.GetNumberOfPlainElements();
            int layers         = this.mesher.GetNumberOfSpatialLayers();

            int spatial_nodes    = base_nodes * layers;
            int spatial_elements = (base_triangles * 3) * (layers - 1);

            this.lblBaseNodes.Text      = base_nodes.ToString("###,###,###,##0");
            this.lblBaseTriangles.Text  = base_triangles.ToString("###,###,###,##0");
            this.lblSpatialNodes.Text   = spatial_nodes.ToString("###,###,###,##0");
            this.lblStaialElements.Text = spatial_elements.ToString("###,###,###,##0");
            this.lblSpatialLayers.Text  = layers.ToString();
        }