private double CalculateDistance(int doc)
            {
                var document = currentIndexReader.Document(doc);

                if (document == null)
                {
                    return(double.NaN);
                }
                var field = document.GetField(Constants.SpatialShapeFieldName);

                if (field == null)
                {
                    return(double.NaN);
                }
                var   shapeAsText = field.StringValue;
                Shape shape;

                try
                {
                    shape = spatialField.ReadShape(shapeAsText);
                }
                catch (InvalidOperationException)
                {
                    return(double.NaN);
                }
                var pt = shape as Point;

                if (pt == null)
                {
                    pt = shape.GetCenter();
                }
                return(spatialField.GetContext().GetDistCalc().Distance(pt, originPt));
            }
Пример #2
0
        private static Shape HandleWkt(Query query, MethodExpression expression, QueryMetadata metadata, BlittableJsonReaderObject parameters, string fieldName,
                                       SpatialField spatialField)
        {
            var wktValue = GetValue(fieldName, query, metadata, parameters, (ValueExpression)expression.Arguments[0]);

            AssertValueIsString(fieldName, wktValue.Type);

            SpatialUnits?spatialUnits = null;

            if (expression.Arguments.Count == 2)
            {
                spatialUnits = GetSpatialUnits(query, expression.Arguments[3] as ValueExpression, metadata, parameters, fieldName);
            }

            return(spatialField.ReadShape((string)wktValue.Value, spatialUnits));
        }
Пример #3
0
        public static Sort GetSort(this IndexQuery self, IndexDefinition indexDefinition, AbstractViewGenerator viewGenerator)
        {
            var spatialQuery = self as SpatialIndexQuery;
            var sortedFields = self.SortedFields;

            if (sortedFields == null || sortedFields.Length <= 0)
            {
                if (spatialQuery == null || string.IsNullOrEmpty(self.Query) == false)
                {
                    return(null);
                }
                sortedFields = new[] { new SortedField(Constants.DistanceFieldName), };
            }

            return(new Sort(sortedFields
                            .Select(sortedField =>
            {
                if (sortedField.Field == Constants.TemporaryScoreValue)
                {
                    return SortField.FIELD_SCORE;
                }
                if (sortedField.Field.StartsWith(Constants.RandomFieldName))
                {
                    var parts = sortedField.Field.Split(new[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
                    if (parts.Length < 2)                 // truly random
                    {
                        return new RandomSortField(Guid.NewGuid().ToString());
                    }
                    return new RandomSortField(parts[1]);
                }
                if (sortedField.Field.StartsWith(Constants.CustomSortFieldName))
                {
                    var parts = sortedField.Field.Split(new[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
                    if (parts.Length < 2)                 // truly random
                    {
                        throw new InvalidOperationException("Cannot figure out type for custom sort");
                    }
                    return new CustomSortField(parts[1], self, parts[0][parts[0].Length - 1] == '-');
                }
                if (sortedField.Field.StartsWith(Constants.DistanceFieldName))
                {
                    SpatialField spatialField = null;
                    Shape shape;

                    if (sortedField.Field.Length == Constants.DistanceFieldName.Length)
                    {
                        if (spatialQuery == null)
                        {
                            throw new InvalidOperationException("Illegal Spatial Sort Parameter: Blank Spatial sort cannot be used without a spatial query");
                        }

                        spatialField = viewGenerator.GetSpatialField(spatialQuery.SpatialFieldName);

                        shape = spatialField.ReadShape(spatialQuery.QueryShape);
                    }
                    else
                    {
                        var sortParams = sortedField.Field.Split(';');
                        double lat, lng;

                        if (sortParams.Length < 3 || !double.TryParse(sortParams[1], out lat) || !double.TryParse(sortParams[2], out lng))
                        {
                            throw new InvalidOperationException("Illegal Spatial Sort Parameter");
                        }


                        string spatialFieldName;

                        if (sortParams.Length >= 4)
                        {
                            spatialFieldName = sortParams[3];
                        }
                        else
                        {
                            if (spatialQuery == null)
                            {
                                spatialFieldName = Constants.DefaultSpatialFieldName;
                            }
                            else
                            {
                                spatialFieldName = spatialQuery.SpatialFieldName;
                            }
                        }

                        spatialField = viewGenerator.GetSpatialField(spatialFieldName);

                        shape = new PointImpl(lng, lat, spatialField.GetContext());
                    }
                    var dsort = new SpatialDistanceFieldComparatorSource(spatialField, shape.GetCenter());
                    return new SortField(sortedField.Field, dsort, sortedField.Descending);
                }
                var sortOptions = GetSortOption(indexDefinition, sortedField.Field, self);

                if (sortOptions == null || sortOptions == SortOptions.None)
                {
                    return new SortField(sortedField.Field, CultureInfo.InvariantCulture, sortedField.Descending);
                }

                if (sortOptions.Value == SortOptions.Short)
                {
                    sortOptions = SortOptions.Int;
                }
                return new SortField(sortedField.Field, (int)sortOptions.Value, sortedField.Descending);
            })
                            .ToArray()));
        }