# HG changeset patch # User Sascha L. Teichmann # Date 1707641481 -3600 # Node ID a57be8bfb6eaad7585026949f84fe560a0945820 # Parent d56e043bbbca6485df415398c0b19a48a223dd3f More suited file names. diff -r d56e043bbbca -r a57be8bfb6ea pkg/mesh/loader.go --- a/pkg/mesh/loader.go Sun Feb 11 09:49:25 2024 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,81 +0,0 @@ -// This is Free Software under GNU Affero General Public License v >= 3.0 -// without warranty, see README.md and license for details. -// -// SPDX-License-Identifier: AGPL-3.0-or-later -// License-Filename: LICENSES/AGPL-3.0.txt -// -// Copyright (C) 2018 by via donau -// – Österreichische Wasserstraßen-Gesellschaft mbH -// Software engineering by Intevation GmbH -// -// Author(s): -// * Sascha L. Teichmann - -package mesh - -import ( - "bufio" - "bytes" - "compress/gzip" - "encoding/binary" - "errors" - "fmt" -) - -const magicHeader = "SR3D" - -// Bytes serializes this tree to a byte slice. -func (s *STRTree) Bytes() ([]byte, error) { - - var buf bytes.Buffer - w, err := gzip.NewWriterLevel(&buf, gzip.BestSpeed) - if err != nil { - return nil, err - } - - if err := s.serializeV1(w); err != nil { - return nil, err - } - - if err := w.Close(); err != nil { - return nil, err - } - - return buf.Bytes(), nil -} - -// FromBytes restores a STRTree from a binary representation. -func (s *STRTree) FromBytes(data []byte, version *int64) error { - r, err := gzip.NewReader(bytes.NewReader(data)) - if err != nil { - return err - } - return s.deserialize(bufio.NewReader(r), version) -} - -func (s *STRTree) deserialize(r *bufio.Reader, version *int64) error { - - header, err := r.Peek(8) - if err != nil { - return err - } - - if bytes.HasPrefix(header, []byte(magicHeader)) { - realVersion := int64(binary.LittleEndian.Uint32(header[4:])) - if version != nil && realVersion != *version { - return fmt.Errorf("sounding result version mismatch: Have %d expect %d", - realVersion, *version) - } - return s.deserializeVn(r, realVersion) - } - - return s.deserializeV1(r) -} - -func (s *STRTree) deserializeVn(r *bufio.Reader, version int64) error { - if version == 1 { - return s.deserializeV1(r) - } - // TODO: Implement me! - return errors.New("not implemented, yet") -} diff -r d56e043bbbca -r a57be8bfb6ea pkg/mesh/meshserialize.go --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/pkg/mesh/meshserialize.go Sun Feb 11 09:51:21 2024 +0100 @@ -0,0 +1,81 @@ +// This is Free Software under GNU Affero General Public License v >= 3.0 +// without warranty, see README.md and license for details. +// +// SPDX-License-Identifier: AGPL-3.0-or-later +// License-Filename: LICENSES/AGPL-3.0.txt +// +// Copyright (C) 2018 by via donau +// – Österreichische Wasserstraßen-Gesellschaft mbH +// Software engineering by Intevation GmbH +// +// Author(s): +// * Sascha L. Teichmann + +package mesh + +import ( + "bufio" + "bytes" + "compress/gzip" + "encoding/binary" + "errors" + "fmt" +) + +const magicHeader = "SR3D" + +// Bytes serializes this tree to a byte slice. +func (s *STRTree) Bytes() ([]byte, error) { + + var buf bytes.Buffer + w, err := gzip.NewWriterLevel(&buf, gzip.BestSpeed) + if err != nil { + return nil, err + } + + if err := s.serializeV1(w); err != nil { + return nil, err + } + + if err := w.Close(); err != nil { + return nil, err + } + + return buf.Bytes(), nil +} + +// FromBytes restores a STRTree from a binary representation. +func (s *STRTree) FromBytes(data []byte, version *int64) error { + r, err := gzip.NewReader(bytes.NewReader(data)) + if err != nil { + return err + } + return s.deserialize(bufio.NewReader(r), version) +} + +func (s *STRTree) deserialize(r *bufio.Reader, version *int64) error { + + header, err := r.Peek(8) + if err != nil { + return err + } + + if bytes.HasPrefix(header, []byte(magicHeader)) { + realVersion := int64(binary.LittleEndian.Uint32(header[4:])) + if version != nil && realVersion != *version { + return fmt.Errorf("sounding result version mismatch: Have %d expect %d", + realVersion, *version) + } + return s.deserializeVn(r, realVersion) + } + + return s.deserializeV1(r) +} + +func (s *STRTree) deserializeVn(r *bufio.Reader, version int64) error { + if version == 1 { + return s.deserializeV1(r) + } + // TODO: Implement me! + return errors.New("not implemented, yet") +} diff -r d56e043bbbca -r a57be8bfb6ea pkg/mesh/meshserialize_v1.go --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/pkg/mesh/meshserialize_v1.go Sun Feb 11 09:51:21 2024 +0100 @@ -0,0 +1,300 @@ +// This is Free Software under GNU Affero General Public License v >= 3.0 +// without warranty, see README.md and license for details. +// +// SPDX-License-Identifier: AGPL-3.0-or-later +// License-Filename: LICENSES/AGPL-3.0.txt +// +// Copyright (C) 2024 by via donau +// – Österreichische Wasserstraßen-Gesellschaft mbH +// Software engineering by Intevation GmbH +// +// Author(s): +// * Sascha L. Teichmann + +package mesh + +import ( + "bufio" + "encoding/binary" + "io" + "math" + + "gemma.intevation.de/gemma/pkg/log" +) + +func (s *STRTree) serializeV1(w io.Writer) error { + if err := s.tin.serializeV1(w); err != nil { + return err + } + + if err := binary.Write(w, binary.LittleEndian, uint8(s.Entries)); err != nil { + return err + } + + if err := s.serializeIndexV1(w); err != nil { + return err + } + + if err := s.serializeBBoxesV1(w); err != nil { + return err + } + + return nil +} + +func (s *STRTree) serializeBBoxesV1(w io.Writer) error { + + if err := binary.Write(w, binary.LittleEndian, int32(len(s.bboxes))); err != nil { + return err + } + + var err error + + write := func(v float64) { + if err == nil { + err = binary.Write(w, binary.LittleEndian, math.Float64bits(v)) + } + } + for _, box := range s.bboxes { + write(box.X1) + write(box.Y1) + write(box.X2) + write(box.Y2) + } + + return err +} + +func (s *STRTree) serializeIndexV1(w io.Writer) error { + + if err := binary.Write(w, binary.LittleEndian, int32(len(s.index))); err != nil { + return err + } + + var buf [binary.MaxVarintLen32]byte + + var last int32 + var written int + + for _, x := range s.index { + delta := x - last + n := binary.PutVarint(buf[:], int64(delta)) + for p := buf[:n]; len(p) > 0; p = p[n:] { + var err error + if n, err = w.Write(p); err != nil { + return err + } + written += n + } + last = x + } + + log.Infof("compressed index in bytes: %d %.2f (%d %.2f)\n", + written, + float64(written)/(1024*1024), + 4*len(s.index), + float64(4*len(s.index))/(1024*1024), + ) + + return nil +} + +func (t *Tin) serializeV1(w io.Writer) error { + + if err := binary.Write(w, binary.LittleEndian, t.EPSG); err != nil { + return err + } + + if err := t.Min.Write(w); err != nil { + return err + } + if err := t.Max.Write(w); err != nil { + return err + } + + if err := binary.Write( + w, binary.LittleEndian, uint32(len(t.Vertices))); err != nil { + return err + } + + var err error + vwrite := func(v float64) { + if err == nil { + err = binary.Write(w, binary.LittleEndian, math.Float64bits(v)) + } + } + + for _, v := range t.Vertices { + vwrite(v.X) + vwrite(v.Y) + vwrite(v.Z) + } + + if err != nil { + return err + } + log.Infof("vertices %d (%d)\n", len(t.Vertices), len(t.Vertices)*3*8) + + if err := binary.Write( + w, binary.LittleEndian, uint32(len(t.Triangles))); err != nil { + return err + } + + var buf [binary.MaxVarintLen32]byte + var written int + var last int32 + for _, triangle := range t.Triangles { + for _, idx := range triangle { + value := idx - last + n := binary.PutVarint(buf[:], int64(value)) + for p := buf[:n]; len(p) > 0; p = p[n:] { + var err error + if n, err = w.Write(p); err != nil { + return err + } + written += n + } + last = idx + } + } + log.Infof("compressed tin indices in bytes: %d (%d)\n", + written, 3*4*len(t.Triangles)) + + return nil +} + +func (s *STRTree) deserializeBBoxesV1(r *bufio.Reader) error { + + var numBBoxes int32 + if err := binary.Read(r, binary.LittleEndian, &numBBoxes); err != nil { + return err + } + + bboxes := make([]Box2D, numBBoxes) + s.bboxes = bboxes + + var err error + + read := func(v *float64) { + if err == nil { + err = binary.Read(r, binary.LittleEndian, v) + } + } + + for i := range bboxes { + read(&bboxes[i].X1) + read(&bboxes[i].Y1) + read(&bboxes[i].X2) + read(&bboxes[i].Y2) + } + + return err +} + +func (s *STRTree) deserializeIndexV1(r *bufio.Reader) error { + var numIndex int32 + if err := binary.Read(r, binary.LittleEndian, &numIndex); err != nil { + return err + } + index := make([]int32, numIndex) + s.index = index + + var last int32 + for i := range index { + v, err := binary.ReadVarint(r) + if err != nil { + return err + } + value := int32(v) + last + index[i] = value + last = value + } + + return nil +} + +func (s *STRTree) deserializeV1(r *bufio.Reader) error { + s.tin = new(Tin) + if err := s.tin.deserializeV1(r); err != nil { + return err + } + var numEntries uint8 + if err := binary.Read(r, binary.LittleEndian, &numEntries); err != nil { + return err + } + s.Entries = int(numEntries) + + if err := s.deserializeIndexV1(r); err != nil { + return err + } + + return s.deserializeBBoxesV1(r) +} + +// deserializeV1 restores a TIN from a binary representation. +func (t *Tin) deserializeV1(r *bufio.Reader) error { + + if err := binary.Read(r, binary.LittleEndian, &t.EPSG); err != nil { + return err + } + + log.Infof("EPSG: %d\n", t.EPSG) + + if err := t.Min.Read(r); err != nil { + return err + } + + if err := t.Max.Read(r); err != nil { + return err + } + + log.Infof("BBOX: [[%f, %f, %f], [%f, %f, %f]]\n", + t.Min.X, t.Min.Y, t.Min.Z, + t.Max.X, t.Max.Y, t.Max.Z) + + var numVertices uint32 + if err := binary.Read(r, binary.LittleEndian, &numVertices); err != nil { + return err + } + + log.Infof("vertices: %d\n", numVertices) + + vertices := make([]Vertex, numVertices) + t.Vertices = vertices + + for i := range vertices { + if err := vertices[i].Read(r); err != nil { + return err + } + } + + var numTriangles uint32 + if err := binary.Read(r, binary.LittleEndian, &numTriangles); err != nil { + return err + } + + log.Infof("triangles: %d\n", numTriangles) + + indices := make([]int32, 3*numTriangles) + triangles := make([][]int32, numTriangles) + t.Triangles = triangles + + var last int32 + + for i := range triangles { + tri := indices[:3] + indices = indices[3:] + triangles[i] = tri + for j := range tri { + v, err := binary.ReadVarint(r) + if err != nil { + return err + } + value := int32(v) + last + tri[j] = value + last = value + } + } + + return nil +} diff -r d56e043bbbca -r a57be8bfb6ea pkg/mesh/serialize_v1.go --- a/pkg/mesh/serialize_v1.go Sun Feb 11 09:49:25 2024 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,300 +0,0 @@ -// This is Free Software under GNU Affero General Public License v >= 3.0 -// without warranty, see README.md and license for details. -// -// SPDX-License-Identifier: AGPL-3.0-or-later -// License-Filename: LICENSES/AGPL-3.0.txt -// -// Copyright (C) 2024 by via donau -// – Österreichische Wasserstraßen-Gesellschaft mbH -// Software engineering by Intevation GmbH -// -// Author(s): -// * Sascha L. Teichmann - -package mesh - -import ( - "bufio" - "encoding/binary" - "io" - "math" - - "gemma.intevation.de/gemma/pkg/log" -) - -func (s *STRTree) serializeV1(w io.Writer) error { - if err := s.tin.serializeV1(w); err != nil { - return err - } - - if err := binary.Write(w, binary.LittleEndian, uint8(s.Entries)); err != nil { - return err - } - - if err := s.serializeIndexV1(w); err != nil { - return err - } - - if err := s.serializeBBoxesV1(w); err != nil { - return err - } - - return nil -} - -func (s *STRTree) serializeBBoxesV1(w io.Writer) error { - - if err := binary.Write(w, binary.LittleEndian, int32(len(s.bboxes))); err != nil { - return err - } - - var err error - - write := func(v float64) { - if err == nil { - err = binary.Write(w, binary.LittleEndian, math.Float64bits(v)) - } - } - for _, box := range s.bboxes { - write(box.X1) - write(box.Y1) - write(box.X2) - write(box.Y2) - } - - return err -} - -func (s *STRTree) serializeIndexV1(w io.Writer) error { - - if err := binary.Write(w, binary.LittleEndian, int32(len(s.index))); err != nil { - return err - } - - var buf [binary.MaxVarintLen32]byte - - var last int32 - var written int - - for _, x := range s.index { - delta := x - last - n := binary.PutVarint(buf[:], int64(delta)) - for p := buf[:n]; len(p) > 0; p = p[n:] { - var err error - if n, err = w.Write(p); err != nil { - return err - } - written += n - } - last = x - } - - log.Infof("compressed index in bytes: %d %.2f (%d %.2f)\n", - written, - float64(written)/(1024*1024), - 4*len(s.index), - float64(4*len(s.index))/(1024*1024), - ) - - return nil -} - -func (t *Tin) serializeV1(w io.Writer) error { - - if err := binary.Write(w, binary.LittleEndian, t.EPSG); err != nil { - return err - } - - if err := t.Min.Write(w); err != nil { - return err - } - if err := t.Max.Write(w); err != nil { - return err - } - - if err := binary.Write( - w, binary.LittleEndian, uint32(len(t.Vertices))); err != nil { - return err - } - - var err error - vwrite := func(v float64) { - if err == nil { - err = binary.Write(w, binary.LittleEndian, math.Float64bits(v)) - } - } - - for _, v := range t.Vertices { - vwrite(v.X) - vwrite(v.Y) - vwrite(v.Z) - } - - if err != nil { - return err - } - log.Infof("vertices %d (%d)\n", len(t.Vertices), len(t.Vertices)*3*8) - - if err := binary.Write( - w, binary.LittleEndian, uint32(len(t.Triangles))); err != nil { - return err - } - - var buf [binary.MaxVarintLen32]byte - var written int - var last int32 - for _, triangle := range t.Triangles { - for _, idx := range triangle { - value := idx - last - n := binary.PutVarint(buf[:], int64(value)) - for p := buf[:n]; len(p) > 0; p = p[n:] { - var err error - if n, err = w.Write(p); err != nil { - return err - } - written += n - } - last = idx - } - } - log.Infof("compressed tin indices in bytes: %d (%d)\n", - written, 3*4*len(t.Triangles)) - - return nil -} - -func (s *STRTree) deserializeBBoxesV1(r *bufio.Reader) error { - - var numBBoxes int32 - if err := binary.Read(r, binary.LittleEndian, &numBBoxes); err != nil { - return err - } - - bboxes := make([]Box2D, numBBoxes) - s.bboxes = bboxes - - var err error - - read := func(v *float64) { - if err == nil { - err = binary.Read(r, binary.LittleEndian, v) - } - } - - for i := range bboxes { - read(&bboxes[i].X1) - read(&bboxes[i].Y1) - read(&bboxes[i].X2) - read(&bboxes[i].Y2) - } - - return err -} - -func (s *STRTree) deserializeIndexV1(r *bufio.Reader) error { - var numIndex int32 - if err := binary.Read(r, binary.LittleEndian, &numIndex); err != nil { - return err - } - index := make([]int32, numIndex) - s.index = index - - var last int32 - for i := range index { - v, err := binary.ReadVarint(r) - if err != nil { - return err - } - value := int32(v) + last - index[i] = value - last = value - } - - return nil -} - -func (s *STRTree) deserializeV1(r *bufio.Reader) error { - s.tin = new(Tin) - if err := s.tin.deserializeV1(r); err != nil { - return err - } - var numEntries uint8 - if err := binary.Read(r, binary.LittleEndian, &numEntries); err != nil { - return err - } - s.Entries = int(numEntries) - - if err := s.deserializeIndexV1(r); err != nil { - return err - } - - return s.deserializeBBoxesV1(r) -} - -// deserializeV1 restores a TIN from a binary representation. -func (t *Tin) deserializeV1(r *bufio.Reader) error { - - if err := binary.Read(r, binary.LittleEndian, &t.EPSG); err != nil { - return err - } - - log.Infof("EPSG: %d\n", t.EPSG) - - if err := t.Min.Read(r); err != nil { - return err - } - - if err := t.Max.Read(r); err != nil { - return err - } - - log.Infof("BBOX: [[%f, %f, %f], [%f, %f, %f]]\n", - t.Min.X, t.Min.Y, t.Min.Z, - t.Max.X, t.Max.Y, t.Max.Z) - - var numVertices uint32 - if err := binary.Read(r, binary.LittleEndian, &numVertices); err != nil { - return err - } - - log.Infof("vertices: %d\n", numVertices) - - vertices := make([]Vertex, numVertices) - t.Vertices = vertices - - for i := range vertices { - if err := vertices[i].Read(r); err != nil { - return err - } - } - - var numTriangles uint32 - if err := binary.Read(r, binary.LittleEndian, &numTriangles); err != nil { - return err - } - - log.Infof("triangles: %d\n", numTriangles) - - indices := make([]int32, 3*numTriangles) - triangles := make([][]int32, numTriangles) - t.Triangles = triangles - - var last int32 - - for i := range triangles { - tri := indices[:3] - indices = indices[3:] - triangles[i] = tri - for j := range tri { - v, err := binary.ReadVarint(r) - if err != nil { - return err - } - value := int32(v) + last - tri[j] = value - last = value - } - } - - return nil -}