Пример #1
0
func ReadNormals(fileName string) []Vector {
	file, err := os.Open(fileName)
	common.Check(err)
	defer file.Close()

	scanner := bufio.NewScanner(file)
	scanner.Split(bufio.ScanWords)

	var normals []Vector

	for scanner.Scan() {
		x, err := strconv.ParseFloat(scanner.Text(), 64)
		common.Check(err)

		scanner.Scan()
		y, err := strconv.ParseFloat(scanner.Text(), 64)
		common.Check(err)

		scanner.Scan()
		z, err := strconv.ParseFloat(scanner.Text(), 64)
		common.Check(err)

		normals = append(normals, Vector{x, y, z})
	}
	common.Check(scanner.Err())
	return normals
}
Пример #2
0
func NewKdTree(fileName string, mesh *TriangleMesh) *KdTree {
	file, err := os.Open(fileName)
	common.Check(err)
	defer file.Close()

	reader := bufio.NewReader(file)

	var nodesCount int32
	err = binary.Read(reader, binary.LittleEndian, &nodesCount)
	common.Check(err)

	nodes := make([]node, nodesCount)
	err = binary.Read(reader, binary.LittleEndian, &nodes)
	common.Check(err)

	var triangleIndicesCount int32
	err = binary.Read(reader, binary.LittleEndian, &triangleIndicesCount)
	common.Check(err)

	triangleIndices := make([]int32, triangleIndicesCount)
	err = binary.Read(reader, binary.LittleEndian, &triangleIndices)
	common.Check(err)

	return &KdTree{
		nodes:           nodes,
		triangleIndices: triangleIndices,
		mesh:            mesh,
		meshBounds:      NewBBox64FromBBox32(mesh.GetBounds()),
	}
}
Пример #3
0
func ReadNumbersFromFile(fileName string) []int32 {
	file, err := os.Open(fileName)
	common.Check(err)
	defer file.Close()

	reader := bufio.NewReader(file)

	var numbersCount int32
	err = binary.Read(reader, binary.LittleEndian, &numbersCount)
	common.Check(err)

	numbers := make([]int32, numbersCount)
	err = binary.Read(reader, binary.LittleEndian, &numbers)
	common.Check(err)
	return numbers
}
Пример #4
0
func (kdTree *KdTree) SaveToFile(fileName string) {
	file, err := os.Create(fileName)
	common.Check(err)
	defer file.Close()

	writer := bufio.NewWriter(file)

	nodesCount := int32(len(kdTree.nodes))
	err = binary.Write(writer, binary.LittleEndian, nodesCount)
	common.Check(err)

	err = binary.Write(writer, binary.LittleEndian, kdTree.nodes)
	common.Check(err)

	triangleIndicesCount := int32(len(kdTree.triangleIndices))
	err = binary.Write(writer, binary.LittleEndian, triangleIndicesCount)
	common.Check(err)

	err = binary.Write(writer, binary.LittleEndian, kdTree.triangleIndices)
	common.Check(err)

	err = writer.Flush()
	common.Check(err)
}
func LoadTriangleMesh(fileName string) *TriangleMesh {
	const (
		headerSize        = 80
		facetSize         = 50
		maxVerticesCount  = math.MaxInt32
		maxTrianglesCount = math.MaxInt32
	)

	file, err := os.Open(fileName)
	common.Check(err)
	defer file.Close()

	// get file size
	stat, err := file.Stat()
	common.Check(err)
	fileSize := stat.Size()

	// read file content
	fileContent := make([]byte, fileSize)
	bytesRead, err := file.Read(fileContent)
	common.Check(err)

	if int64(bytesRead) != fileSize {
		common.RuntimeError(fmt.Sprintf("failed to read %d bytes from file %s",
			fileSize, fileName))
	}

	// validate file content
	asciiStlHeader := []byte{0x73, 0x6f, 0x6c, 0x69, 0x64}
	if bytes.Equal(fileContent[0:5], asciiStlHeader) {
		common.RuntimeError("ascii stl files are not supported: " + fileName)
	}

	if fileSize < headerSize+4 {
		common.RuntimeError("invalid binary stl file: " + fileName)
	}

	buffer := bytes.NewBuffer(fileContent[headerSize:])

	var trianglesCount int32
	err = binary.Read(buffer, binary.LittleEndian, &trianglesCount)
	common.Check(err)

	if trianglesCount > maxTrianglesCount {
		common.RuntimeError("triangles limit exceeded: " + fileName)
	}

	expectedSize := int64(headerSize + 4 + trianglesCount*facetSize)
	if fileSize != expectedSize {
		common.RuntimeError("invalid size of binary stl file: " + fileName)
	}

	// read mesh data
	mesh := new(TriangleMesh)
	mesh.normals = make([]Vector32, trianglesCount)
	mesh.triangles = make([][3]int32, trianglesCount)

	uniqueVertices := make(map[Vector32]int32)

	for i := 0; i < int(trianglesCount); i++ {
		binary.Read(buffer, binary.LittleEndian, &mesh.normals[i])

		for k := 0; k < 3; k++ {
			var v Vector32
			binary.Read(buffer, binary.LittleEndian, &v)
			vertexIndex, found := uniqueVertices[v]
			if !found {
				if len(mesh.vertices) > maxVerticesCount {
					common.RuntimeError("vertices limit exceeded: " + fileName)
				}
				vertexIndex = int32(len(mesh.vertices))
				uniqueVertices[v] = vertexIndex
				mesh.vertices = append(mesh.vertices, v)
			}
			mesh.triangles[i][k] = vertexIndex
		}
		var attribsCount uint16
		binary.Read(buffer, binary.LittleEndian, &attribsCount)
	}
	return mesh
}