private Token TokenForLocation(VSLocation location) { Token resultToken = Token.Nothing; switch (location) { case VSLocation.Editor: resultToken = Token.Editor; break; case VSLocation.Output: resultToken = Token.Output; break; case VSLocation.SolutionExplorer: resultToken = Token.SolutionExplorer; break; case VSLocation.Nothing: resultToken = Token.Nothing; break; } return(resultToken); }
public Fixation(float x, float y, int startTime, int endTime, VSLocation location) { this.x = x; this.y = y; this.startTime = startTime; this.endTime = endTime; this.location = location; }
private void StoreGazePoint(object sender, GazePointEventArgs args) { int elapsedMilliseconds = (int)(GetUnixMillisecondsForNow() - startTime); // If we are tracking Visual Studio locations VSLocation location = trackingVSLocation ? (VSLocation)GetVSWindowForScreenPoint(new System.Windows.Point(args.X, args.Y)) : VSLocation.Nothing; GazePoint gazePoint = new GazePoint((float)args.X, (float)args.Y, elapsedMilliseconds, location); gazePoints.Add(gazePoint); }
private int CountFixationsInLocation(List <Fixation> fixations, VSLocation vsLocation) { int count = 0; foreach (Fixation fixation in fixations) { if (fixation.location == vsLocation) { count++; } } return(count); }
private VSLocation MaxInCount(Dictionary <VSLocation, int> counts) { VSLocation majority = VSLocation.Nothing; int currentMax = 0; foreach (VSLocation key in counts.Keys) { if (counts[key] > currentMax) { currentMax = counts[key]; majority = key; } } return(majority); }
// Converts raw gaze input into fixations. public List <Fixation> CalculateFixations(int windowSize, float peakThreshold, float radius, int clipAmount) { ClipRawPoints(clipAmount); if (rawPoints == null || rawPoints.Count == 0) { Console.WriteLine("RawPoints is null or contains no points. Unable to calculate fixations."); return(new List <Fixation>()); } Console.WriteLine("Calculating fixations..."); List <Point> allPoints = ConvertGazePointsToPoints(rawPoints); // Create the array to store the differences in the windows for each point. float[] differences = new float[rawPoints.Count]; for (int i = 0; i < rawPoints.Count; i++) { differences[i] = 0; } // 1: find the mean of the sliding window before and after sample i for (int i = windowSize; i <= (rawPoints.Count - windowSize) - 1; i++) { List <Point> leftWindow = allPoints.GetRange(i - windowSize, windowSize); List <Point> rightWindow = allPoints.GetRange(i + 1, windowSize); Point meanBefore = GeometricMean(leftWindow); Point meanAfter = GeometricMean(rightWindow); // 2: create vector "d", with distances between before and after windows float axbxSquared = (meanBefore.x - meanAfter.x) * (meanBefore.x - meanAfter.x); float aybySquared = (meanBefore.y - meanAfter.y) * (meanBefore.y - meanAfter.y); float difference = (float)Math.Sqrt(axbxSquared + aybySquared); differences[i] = difference; } // Testing /* * Console.WriteLine("Differences:"); * int count = 0; * foreach(float difference in differences) { * Console.Write(count++ + ":" + difference + ", "); * } * Console.Write("\n"); */ // End Testing // 3: create peak vector and find peaks (that is, find the large(est) differences in means of the sliding windows) // Create the array to store the differences in the windows for each point. float[] peaks = new float[rawPoints.Count]; for (int i = 0; i < rawPoints.Count; i++) { peaks[i] = 0; } for (int i = 1; i < rawPoints.Count - 1; i++) { // if this is a peak if (differences[i] > differences[i - 1] && differences[i] > differences[i + 1]) { peaks[i] = differences[i]; } } // Testing /* * Console.WriteLine("Peaks:"); * count = 0; * foreach(float peak in peaks) { * Console.Write(count++ + ":" + peak + ", "); * } * Console.Write("\n"); */ // End Testing // 4: remove peaks that are too close to each other (only want the largest difference per sliding window) for (int i = windowSize; i <= (rawPoints.Count - windowSize) - 1; i++) { if (peaks[i] != 0) { // check left side for (int j = i - windowSize; j < i; j++) { if (peaks[j] < peaks[i]) { peaks[j] = 0; } } // check right side for (int j = i + 1; j <= i + windowSize; j++) { if (peaks[j] < peaks[i]) { peaks[j] = 0; } } } } // Testing /* * Console.WriteLine("Peaks after removing nearby peaks:"); * count = 0; * foreach(float peak in peaks) { * Console.Write(count++ + ":" + peak + ", "); * } * Console.Write("\n"); */ // End Testing // 5: create list with the indices of the peaks in the peak vector // only add the peaks greater than some threshold, this works the same as a naieve algorithm, we only consider it a saccade if the distance is over a vertain threshold. List <int> peakIndices = new List <int>(); for (int i = 0; i < rawPoints.Count; i++) { if (peaks[i] > peakThreshold) { peakIndices.Add(i); } } // Testing /* * Console.WriteLine("Peak Indices"); * count = 0; * foreach(float index in peakIndices) { * Console.Write(count++ + ":" + index + ", "); * } * Console.Write("\n"); */ // End Testing // 6a: estimate the spacial position of all the fixations between candidate saccades (peaks) // use the geometric median of all the raw points // 6b: fixations that are closer together than a specified range are merged together. // float shortestDistance = 0; // used in 6b List <Fixation> fixations = new List <Fixation>(); //while(shortestDistance < radius) { // used in 6b fixations.Clear(); // 6a for (int i = 1; i <= peakIndices.Count - 1; i++) { int rawFromIndex = peakIndices[i - 1]; int rawToIndex = peakIndices[i]; List <GazePoint> points = new List <GazePoint>(); for (int rawIndex = rawFromIndex; rawIndex <= rawToIndex; rawIndex++) { points.Add(rawPoints[rawIndex]); } VSLocation majorityLocation = MajorityVSLocation(points.ToArray()); Point median = GeometricMedian(ConvertGazePointsToPoints(points)); int startTime = points[0].timestamp; int endTime = points[points.Count - 1].timestamp; Fixation fixation = new Fixation(median.x, median.y, startTime, endTime, majorityLocation); fixations.Add(fixation); } // 6b /* * shortestDistance = float.MaxValue; * * for(int i = 1; i <= fixations.Count - 1; i++) { * * int index = 0; * Point a = new Point(fixations[i - 1].x, fixations[i - 1].y); * Point b = new Point(fixations[i].x, fixations[i].y); * * float distance = EuclideanDistance(a, b); * * if(distance < shortestDistance) { * shortestDistance = distance; * index = i; * } * * if (shortestDistance < radius) { * try { * peakIndices.RemoveAt(index); // BUG: When removing peakIndices, all indices move down a slot, can remove at index and expect all other indices to stay the same... * } * catch(Exception e) { * Console.WriteLine(e.Message); * Console.WriteLine("index:" + index); * Console.WriteLine(peakIndices.Count); * } * } * } * } */ // Testing /* * Console.WriteLine("Fixations:"); * count = 0; * foreach(Fixation fixation in fixations) { * Console.Write(count++ + ":" + fixation.x + "," + fixation.y + ", "); * } * Console.Write("\n"); */ // End Testing return(fixations); }
public GazePoint(float x, float y, int timestamp, VSLocation location) : base(x, y) { this.timestamp = timestamp; this.exists = true; this.location = location; }