Пример #1
0
    public void Update()
    {
        if (addBlob)
        {
            addBlob = false;
            VoxelBlob tempBlob = new VoxelBlob(targetVoxelLength, 1, targetVoxelLength, false);
            myManager.AddVoxelBlob(Convert(tempBlob));

            Text.Log("added picture");
        }
    }
Пример #2
0
    /// <summary>
    /// Uses a silhouette scanning setup
    /// </summary>
    /// <returns>The scan.</returns>
    IEnumerator SilhouetteScan()
    {
        Text.Log("SilhouetteScan.");
        bool isCancelled = false;

        manager.pauseUpdateCollision = true;
        m_blobSize = manager.m_blob.size;

        foreach (ScanningCamera sc in calibratedCameras)
        {
            yield return(Scheduler.StartCoroutine(sc.StartCapturing()));

            yield return(Scheduler.StartCoroutine(sc.TakeCalibrationPicture()));

            sc.Stop();
        }

        m_scanDataBlob = new byte[m_blobSize.x, m_blobSize.y, m_blobSize.z];
        m_readyToScan  = false;
        bool shouldBreak = false;

        Dispatcher <Panel> .Broadcast(PanelController.kEventClosePanel, Panel.Message);

        Dispatcher <string, PanelController.Handler, PanelController.Handler> .Broadcast(
            PanelController.kEventConfirm, kPlaceObjectString,
            delegate { m_readyToScan = true; },
            delegate { m_readyToScan = shouldBreak = true; StopCameras(); }
            );

        yield return(new WaitUntil(() => m_readyToScan || shouldBreak));

        if (shouldBreak)
        {
            yield break;
        }

        m_readyToScan = false;
        Dispatcher <string, string, PanelController.Handler, PanelController.Handler> .Broadcast(
            PanelController.kEventShowProgress,
            Scanner.kOnScanningProgress, "Scanning {0:0%}", Nop,
            delegate {
            isCancelled  = true;
            m_isScanning = false;
            scanningView.SetActive(false);
            StopCameras();
        });

        float initialTime = Time.realtimeSinceStartup;

        scanningView.SetActive(true);
        m_isScanning = true;

        m_workQueue = new Queue <ScanWorkPacket>();
        int numThreads = Math.Max(1, System.Environment.ProcessorCount / 2);

        Text.Log(@"Starting {0} thread{1}.", numThreads, Text.S(numThreads));
        m_rowsProcessed = 0;
        foreach (Thread t in m_scanningThreads)
        {
            if (t.IsAlive)
            {
                t.Abort();
            }
        }
        m_scanningThreads.Clear();
        for (int i = 0; i < numThreads; ++i)
        {
            Thread worker = new Thread(ImageProcessor);
            worker.Start();
            m_scanningThreads.Add(worker);
        }

        int cameraIndex  = 0;
        int rowsExpected = 0;

        foreach (ScanningCamera sc in calibratedCameras)
        {
            yield return(Scheduler.StartCoroutine(sc.StartCapturing()));

            scanningView.renderer.material.mainTexture = sc.webcamImage;

            for (int i = 0; i < numberOfSilhouettePicsToTake; i++)
            {
                yield return(Scheduler.StartCoroutine(sc.TakePicture()));

                float progressAddition = (cameraIndex == 1) ? 0.5f : 0f;
                Dispatcher <float> .Broadcast(kOnScanningProgress, ((float)i / (float)numberOfSilhouettePicsToTake) /
                                              (float)calibratedCameras.Count + progressAddition);

                rowsExpected += sc.imageHeight;
                m_workQueue.Enqueue(new ScanWorkPacket(centerOfVoxelBlob, sc));

                if (Scheduler.ShouldYield())
                {
                    yield return(null);
                }

                Matrix eulerRotate = Matrix.Zero(3, 1);
                eulerRotate[1, 0] = -m_rotationPerPicture;                      // The original.
                //eulerRotate[1,0] = m_rotationPerPicture;

                Matrix rotateAroundY = Matrix.Zero(3, 3);
                OpenCV.cvRodrigues2(eulerRotate.matPtr, rotateAroundY.matPtr, IntPtr.Zero);

                sc.worldToCameraRotation = sc.worldToCameraRotation * rotateAroundY;

                OpenCV.cvReleaseMat(ref rotateAroundY.matPtr);
                OpenCV.cvReleaseMat(ref eulerRotate.matPtr);

                pc.BeginMotorChanges(m_workingPrinter);
                pc.RotateBySteps(0,
                                 m_workingPrinter.platform.stepsPerRotation / numberOfSilhouettePicsToTake,
                                 m_workingPrinter.horizTrack.stepDirection,
                                 Change.Execute);
                pc.EndMotorChanges();
                yield return(Scheduler.StartCoroutine(pc.WaitUntilDoneMoving()));

                if (isCancelled)
                {
                    pc.TurnBacklightOff();
                    m_workQueue.Clear();
                    //if (printer.serialController != null) {
                    //	printer.serialController.ClearRxBuffer();
                    //}
                    scanningView.SetActive(false);
                    StopCameras();
                    yield break;
                }
            }
            sc.Stop();
            ++cameraIndex;
        }
        scanningView.SetActive(false);

        Dispatcher <string, string, PanelController.Handler, PanelController.Handler> .Broadcast(
            PanelController.kEventShowProgress,
            Scanner.kOnScanningProgress, "Processing {0:0%}", Nop,
            // TODO: Actually cancel things…to do this, we may need to make some changes
            // in the blob format and undo system.
            null);

        do
        {
            // NOTE: Changed 2.0 -> 5.0f
            yield return(new WaitSeconds(5.0f));

            Dispatcher <float> .Broadcast(kOnScanningProgress, ((float)m_rowsProcessed / (float)rowsExpected) * 0.75f);
        } while (m_rowsProcessed < rowsExpected && !isCancelled);
        m_isScanning = false;

        VoxelBlob blob = new VoxelBlob(m_blobSize.x, m_blobSize.y, m_blobSize.z, false);

        yield return(Scheduler.StartCoroutine(SetVoxelsInBlob((byte)cutThreshold, blob, m_scanDataBlob, null)));

        m_scanDataBlob = null;

        Dispatcher <float> .Broadcast(kOnScanningProgress, 0.75f);

        yield return(Scheduler.StartCoroutine(manager.AddVoxelBlob(blob, Vector3.zero)));

        manager.pauseUpdateCollision = false;
        while (manager.isUpdating)
        {
            yield return(new WaitSeconds(1.0f));
        }

        Dispatcher <float> .Broadcast(kOnScanningProgress, 1f);

        Text.Log("Done scanning and updating meshes after {0} sec.", Time.realtimeSinceStartup - initialTime);

        pc.TurnBacklightOff();
        Contract.Assert(m_workQueue.Count == 0, @"Didn't process {0} image{1}.",
                        m_workQueue.Count, Text.S(m_workQueue.Count));
    }