Ejemplo n.º 1
0
    /**
     *  Set up the data object with empty UltrasoundPoint%s representing the points
     *  that need to be scanned.
     *
     *  This is analagous to setting up the view frustum in traditional 3D graphics.
     */
    private void EstablishScanningPlane(ref UltrasoundScanData data)
    {
        OnionLogger.globalLog.PushInfoLayer("Pre-populating data");

        UltrasoundProbeConfiguration config = data.GetProbeConfig();

        // nearZ and farZ represent near and far clipping "planes" (they're really arcs)
        float nearZ = config.GetMinScanDistance();
        float farZ  = config.GetMaxScanDistance();

        float arcSizeDegrees    = config.GetArcSizeInDegrees();
        int   scanlines         = config.GetNumberOfScanlines();
        int   pointsPerScanline = config.GetPointsPerScanline();

        for (int i = 0; i < scanlines; ++i)
        {
            UltrasoundScanline scanline = new UltrasoundScanline(config.GetPosition());
            float   angleInDegrees      = -(arcSizeDegrees / 2) + i * arcSizeDegrees / (scanlines - 1);
            float   angleInRadians      = Mathf.Deg2Rad * angleInDegrees;
            Vector2 trajectory          = new Vector2(Mathf.Sin(angleInRadians), Mathf.Cos(angleInRadians));

            for (int j = 0; j < pointsPerScanline; ++j)
            {
                float           d = nearZ + j * (farZ - nearZ) / (pointsPerScanline - 1);
                Vector2         positionOnPlane      = d * trajectory;
                Vector3         positionInWorldSpace = WorldSpaceFromProjectedPosition(positionOnPlane, config);
                UltrasoundPoint point = new UltrasoundPoint(positionInWorldSpace, positionOnPlane);
                scanline.AddUltrasoundPoint(point);
            }

            data.AddScanline(scanline);
        }

        OnionLogger.globalLog.PopInfoLayer();
    }
    /**
     *  Instantiate a new instance of UltrasoundScanData.
     *  @param config The configuration settings associated with the probe object.
     */
    public UltrasoundScanData(UltrasoundProbeConfiguration config)
    {
#if UNITY_EDITOR
        UltrasoundDebug.Assert(null != config, "Null config used in constructor", this);
#endif
        this.probeConfig = config;
        scanlines        = new List <UltrasoundScanline>();
    }
Ejemplo n.º 3
0
 /**
  *	Based on a probe configuration, determine which organs can possibly appear in the image.
  *	@param scanlines The list of scanlines to be checked.
  *	@param config The current UltrasoundProbeConfiguration
  *	@return A culled list of GameObjects to test for collisions.
  */
 public IList <GameObject> HitableOrgansOnScanlines(IList <UltrasoundScanline> scanlines,
                                                    UltrasoundProbeConfiguration config)
 {
     OnionLogger.globalLog.PushInfoLayer("HORAYOrganCuller");
     CheckScanlines(scanlines);
     RemoveExpiredObjects();
     OnionLogger.globalLog.PopInfoLayer();
     return(new List <GameObject>(currentVisibleOrgans.Values));
 }
Ejemplo n.º 4
0
    /**
     *	Helper method to calculate a Vector3 (WorldSpace) from a Projected Position in local space.
     *	@param positionInPlane A Vector2 representing a point in the scanning plane.
     *	@param config The UltrasoundProbeConfiguration object, used for rotation and translation.
     *	@return A 3D point in world space.
     */
    private Vector3 WorldSpaceFromProjectedPosition(Vector2 positionInPlane,
                                                    UltrasoundProbeConfiguration config)
    {
        Vector3 positionInWorldSpace = new Vector3(positionInPlane.x, 0, positionInPlane.y);

        // Apply rotation, using Quaternion's overloaded * operator.
        positionInWorldSpace = config.GetRotation() * positionInWorldSpace;

        positionInWorldSpace += config.GetPosition();
        return(positionInWorldSpace);
    }
Ejemplo n.º 5
0
    /**
     *  Since the pulse will lose energy after interacting with tissue at a point, we will
     *  need to recalculate the pulse intensity after processing each UltrasoundPoint.
     *
     *  @param previousPulseIntensity The intensity of the pulse that hit this point.
     *  @param previousOrgan The properties of the organ at this point.
     *  @param config The probe configuration. (Used for normalizing energy loss for higher res display)
     *
     *  @return The new intensity to use for the next UltrasoundPoint.
     */
    private float PulseIntensityAfterPoint(float previousPulseIntensity,
                                           HorayMaterialProperties previousOrgan,
                                           UltrasoundProbeConfiguration config)
    {
        // When calculating energy lost, we need to normalize for the number of points in the display.
        float resolutionCoefficient = config.GetPointsPerScanline();
        float energyLost            = (previousOrgan.echogenicity + previousOrgan.attenuation) / resolutionCoefficient;
        float newIntensity          = previousPulseIntensity - energyLost;

        return(newIntensity);
    }
Ejemplo n.º 6
0
    /**
     *  Retrieve the current probe configuration.
     *	@return The UltrasoundProbeConfiguration of the probe GameObject.
     */
    public UltrasoundProbeConfiguration GetProbeConfig()
    {
        UltrasoundProbeConfiguration config = new UltrasoundProbeConfiguration(this.transform);

        config.SetMaxScanDistance(this.MaxDistance);
        config.SetMinScanDistance(this.MinDistance);
        config.SetArcSizeInDegrees(this.ArcSizeInDegrees);
        config.SetNumberOfScanlines(this.NumberOfScanlines);
        config.SetPointsPerScanline(this.PointsPerScanline);
        return(config);
    }
    public UltrasoundScanData SendScanData()
    {
        OnionLogger.globalLog.PushInfoLayer("HORAYProbeOutput");

        UltrasoundProbeConfiguration currentConfig =
            probeGameObject.GetComponent <HorayBehavior>().GetProbeConfig();
        UltrasoundScanData data = new UltrasoundScanData(currentConfig);

        probe.PopulateData(ref data);

        OnionLogger.globalLog.PopInfoLayer();
        return(data);
    }
    /**
     *  Maps a point in the probe's scanning plane to a pixel index in the image.
     *  @param imageHeight The height of the image being rendered.
     *  @param imageWidth The width of the image being rendered.
     *  @param vector2 The point in the scanning plane to be mapped.
     *  @param probeConfig The UltrasoundProbeConfiguration of the probe object.
     *  @return The corresponding index in the image at which to render the point.
     */
    protected int MapScanningPlaneToPixelCoordinate(int imageHeight,
                                                    int imageWidth,
                                                    Vector2 vector2,
                                                    UltrasoundProbeConfiguration probeConfig)
    {
        float pixelsPerWorldUnit = Mathf.Min(imageWidth, imageHeight) / probeConfig.GetMaxScanDistance();
        int   xCenter            = imageWidth / 2;

        int newX = (int)(xCenter - pixelsPerWorldUnit * vector2.x);
        int newY = imageHeight - (int)(pixelsPerWorldUnit * vector2.y);

        int pixelMapping = newY * imageWidth + newX;

        return(pixelMapping);
    }
    /**
     *  Copy constructor to instantiate a new UltrasoundProbeConfiguration from another.
     *
     *  @param config The other UltrasoundProbeConfiguration object.
     *  @throw ArgumentNullException
     */
    public UltrasoundProbeConfiguration(UltrasoundProbeConfiguration config)
    {
        UltrasoundDebug.Assert(null != config,
                               "Null UltrasoundProbeConfiguration used for copy constructor.",
                               this);
        this.SetPosition(config.GetPosition());
        this.SetRotation(config.GetRotation());

        this.maxDistance       = config.GetMaxScanDistance();
        this.minDistance       = config.GetMinScanDistance();
        this.arcSizeInDegrees  = config.GetArcSizeInDegrees();
        this.pointsPerScanline = config.GetPointsPerScanline();
        this.numberOfScanlines = config.GetNumberOfScanlines();
        this.gain = config.GetGain();
    }
    public UltrasoundScanData SendScanData()
    {
        UltrasoundProbeConfiguration config = new UltrasoundProbeConfiguration();

        config.SetMaxScanDistance(MAX_Y);
        config.SetMinScanDistance(MIN_Y);
        UltrasoundScanData data = new UltrasoundScanData(config);

        for (float i = MIN_X; i <= MAX_X; i += STEPSIZE)
        {
            UltrasoundScanline scanline = new UltrasoundScanline(config.GetPosition());

            for (float j = MIN_Y; j <= MAX_Y; j += STEPSIZE)
            {
                UltrasoundPoint p = new UltrasoundPoint(Vector3.zero, new Vector2(i * (j / MAX_Y), j));
                p.SetBrightness(Random.Range(0f, 1f));  // Generate noise.
                scanline.AddUltrasoundPoint(p);
            }

            data.AddScanline(scanline);
        }

        return(data);
    }