 	// your shader should terminate!
 
 	// return true if iso surface was hit, fals if not
-
-
-	return false;
+    float marchedDistance = tmin;
+    float currentStep;
+    bool hit = false;
+    int sphere;
+    Ray marchingRay = ray;
+
+	while(marchedDistance <= tmax && !hit)
+    {
+        nearestDistance(marchingRay.origin, currentStep);
+        marchingRay.origin += currentStep * marchingRay.direction;
+        marchedDistance += currentStep;
+        hit = hitSphere(marchingRay.origin, sphere);
+    }
+
+    material = materials[sphere];
+    normal = normalize(marchingRay.origin - blobs[sphere].position);
+    t = marchedDistance;
+
+	return hit;
 }
 
 // Task_5_3 - ToDo End

// ... your helper functions

// ... more ...
bool nearestIntersection(in Ray ray, float t)
{
    float dist = INFINITE;
    float t0;
    float t1;

	for(int i = 0; i < SIZE; ++i)
	{
        if(intersects(blobs[i], ray, t0, t1) && t0 < dist)
        {
            dist = t0;
        }
	}

    t = dist;
	return dist < INFINITY;
}

bool farthestIntersection()
{
    float dist = 0;
    float t0;
    float t1;

	for(int i = 0; i < SIZE; ++i)
	{
        if(intersects(blobs[i], ray, t0, t1) && t0 > dist)
        {
            dist = t0;
        }
	}

    t = dist;
	return dist > INFINITY;
}


bool trace(in Ray ray, out vec3 normal, out Material material, out float t)
{

	// find nearest and farthest intersection for all metaballs
	// hint: use for loop, INFINITE, SIZE, intersect, min and max...



	float tmin;
	float tmax;

	if(!farthestIntersection(ray, tmax) || !nearestIntersection(ray, tmin))
    {
        return false;
    }

	// implement raymarching within your tmin and tmax
	// hint: e.g., use while loop, THRESHOLD, and implment yourself
