public override void Process(ChannelGrid grid, int channel) { float s = Mathf.Sqrt(Width * Height / (float)m_UniqueGridPoints.Count); if (s > 1) { s *= c_SizeMult; foreach (Vector2Int p in m_UniqueGridPoints) { int gx = p.x; int gy = p.y; float v = grid.Read(channel, gx, gy); float invZ = 1 - m_AuxGrid.Read(0, gx, gy); var kernel = m_Kernels[Mathf.Min(Mathf.RoundToInt(s * invZ), c_MaxRadius - 1)]; for (int i = 0, n = kernel.Count; i < n; i++) { int x = gx + kernel[i].x; int y = gy + kernel[i].y; if (m_AuxGrid.TryRead(1, x, y, out float k)) { m_AuxGrid.Write(1, x, y, Mathf.Max(kernel[i].value, k)); m_AuxGrid.Write(2, x, y, Mathf.Max(m_AuxGrid.Read(2, x, y), v)); Expand(x, y); } } } for (int x = m_xMin; x <= m_xMax; x++) { for (int y = m_yMin; y <= m_yMax; y++) { if (m_AuxGrid.Read(1, x, y) > c_Threshold) { grid.Write(channel, x, y, m_AuxGrid.Read(2, x, y)); m_UniqueGridPoints.Add(new Vector2Int(x, y)); } } } } }
public override void Process(ChannelGrid grid, int channel) { // Side length of squares around points required for filling w * h, // *if* points were distributed evenly. We're adding some value // to this below for preventing gaps. int w = Width; int h = Height; float s = Mathf.Sqrt(w * h / (float)m_UniqueGridPoints.Count); if (s > 1) { int size = Mathf.RoundToInt(s) + 2; // TBD add. value // Bottom/left offset (padding). int xPad = m_xMin - (size - w % size) / 2; int yPad = m_yMin - (size - h % size) / 2; int nx = 0, ny = 0; foreach (Vector2Int p in m_UniqueGridPoints) { int sx = (p.x - xPad) / size; int sy = (p.y - yPad) / size; nx = Mathf.Max(nx, sx); ny = Mathf.Max(ny, sy); // For 3D, we sample the max (closest) value. // For 2D, point values are identical anyway. m_Samples[sx, sy] = Mathf.Max(m_Samples[sx, sy], grid.Read(channel, p)); } // Replace grid points with squares (size x size). m_UniqueGridPoints.Clear(); for (int sx = 0; sx <= nx; sx++) { for (int sy = 0; sy <= ny; sy++) { float value = m_Samples[sx, sy]; if (value > 0) { int gx = xPad + sx * size; int gy = yPad + sy * size; for (int x = 0; x < size; x++) { for (int y = 0; y < size; y++) { Vector2Int p = new Vector2Int(gx + x, gy + y); if (grid.TryRead(channel, p, out float prev)) { // 3D: storing max value for distance channel (closest). // TODO // 2D: neighbouring down-sampled areas might overlap and // their max value isn't necessarily what we want to observe? grid.Write(channel, p, Mathf.Max(prev, value)); m_UniqueGridPoints.Add(p); } } } } } } } // else: keep original points. }