JoinData: Can't create output feature class. the workspaces is not connected.

3642
11
08-08-2011 11:58 PM
SebastianKrings
Occasional Contributor
Hello,

I have a FeatureClass with polylines and one point. I know the point must (almost) lie on one of the polylines.

The Point is stored as shape in a featureClass created by in a scratchworkspace.

To identify which polyline it is I make use of the ISpatialJoin Interface.
The Polyline FeatureClass is set as sourceTable, while the point FeatureClass is set as the JoinTable (both are casted to ITable before)

when now executing
IFeatureClass nearestContour = join.JoinNearest(name, -1);


I will get the Error as in subject:
Can't create output feature class. the workspaces is not connected.


Which workspace is meant? The scratch? Theres no order to close its connection. Is there may another way to create a feature class for a given IPoint, without workspaces?

the whole code:
private double getheightAtPoint(IFeatureClass contourClass, IPoint point)
        {
            try
            {
                IScratchWorkspaceFactory2 scratchWorkspaceFactory = (IScratchWorkspaceFactory2)new FileGDBScratchWorkspaceFactory();
                IWorkspace scratchWorkspace = (IWorkspace)scratchWorkspaceFactory.CreateNewScratchWorkspace();
                IFeatureClass pointClass = Utilities.Instance.CreateFeatureClassInWorkspace("tmpPoint", (IFeatureWorkspace)scratchWorkspace);

                IFeature pointFeature = pointClass.CreateFeature();
                pointFeature.Shape = point;

                IFeatureCursor contourCursor = contourClass.Search(null, false);
                IFeature contourFeature = contourCursor.NextFeature();
                IPolyline pPolyline = contourFeature.Shape as IPolyline;
                
                double height = 0;
                ISpatialJoin join = new SpatialJoinClass();

                join.SourceTable = contourClass as ITable;
                join.JoinTable = pointClass as ITable;

                IName name = new FeatureClassName();
                name.NameString = "nearestContour";

                IFeatureClass nearestContour = join.JoinNearest(name, -1);
                int index = nearestContour.Fields.FindField("Contour");

                if (index != -1)
                {
                    height = (Double)(nearestContour as IRow).get_Value(index);
                }
                else
                {
                    throw new NullReferenceException("Es konnte kein Contour-Feld gefunden werden!");
                }
                return height;
            }
            catch (Exception e)
            {
                throw e;
            }

Thanks for any help and ideas.
0 Kudos
11 Replies
DubravkoAntonic
New Contributor III
0 Kudos
SebastianKrings
Occasional Contributor
hi,

thanks for this idea.

Yes of course I do.
Within the method
 IFeatureClass pointClass = Utilities.Instance.CreateFeatureClassInWorkspace("tmpPoint", (IFeatureWorkspace)scratchWorkspace);

there is an edit session created and the featureClass stored.


There is another thing I recognized:
                IFeature pointFeature = pointClass.CreateFeature();
                pointFeature.Shape = point as IGeometry;


After the shape is set, the references within the point of OID, X, Y, M Z will have an entry that an exception was thrown.
When I do something like:
IPoint testPoint2 = new Point();
                testPoint2.PutCoords(point.X, point.Y);


It's ok (only the Y coordinate will change after the 7th decimal place)

and when I then want to get the feature back through
 IFeatureCursor testCursor = pointClass.Search(null, true);
                IFeature testFeature = testCursor.NextFeature();
                IGeometry testGeom = testFeature.Shape;
                IPoint testPoint = testGeom as IPoint;


The testPoint has the exceptions as well.

I never had problems like this when using a shape for polyline.
0 Kudos
DubravkoAntonic
New Contributor III
Yes of course I do.
Within the method
  IFeatureClass pointClass =  Utilities.Instance.CreateFeatureClassInWorkspace("tmpPoint",  (IFeatureWorkspace)scratchWorkspace);
there is an edit session created and the featureClass stored.
Exception is connected with scratchWorkspace.

After the shape is set, the references within the point of OID, X, Y, M Z will have an entry that an exception was thrown.
Is your edit session closed after returning fromUtilities.Instance.CreateFeatureClassInWorkspace?


The testPoint has the exceptions as well.
Parameter IPoint point memeber could be geometry element from another feature. If yes, you didn't created it or cloned, you should clone or create new PointClass object.
After changing feature attributes you should store changes IFeature.Store
0 Kudos
SebastianKrings
Occasional Contributor
hi

Yes the edit session within create feature is closed.
But I don't need another edit session. when I understood the documentation of IFeatureClass.createFeature() right then I do not need an editsession for calling Feature.Store().

But before I could do this the Exceptions arise.

When using an EditSession it will fail also (doesnt matter whether using EditOperation or not):

IScratchWorkspaceFactory2 scratchWorkspaceFactory = (IScratchWorkspaceFactory2)new FileGDBScratchWorkspaceFactory();
                IWorkspace scratchWorkspace = (IWorkspace)scratchWorkspaceFactory.CreateNewScratchWorkspace();
                IFeatureClass pointClass = Utilities.Instance.CreateFeatureClassInWorkspace("tmpPoint", (IFeatureWorkspace)scratchWorkspace);

                IWorkspaceEdit scratchWorkspaceEdit = (IWorkspaceEdit)scratchWorkspace;
                scratchWorkspaceEdit.StartEditing(false);
                scratchWorkspaceEdit.StartEditOperation();

                IFeature pointFeature = pointClass.CreateFeature();
                pointFeature.Shape = point as IGeometry;

                scratchWorkspaceEdit.StartEditOperation();
                scratchWorkspaceEdit.StopEditing(true);


The parameter IPoint is from IPolyline.FromPoint();
How could this be corrupt?


edit:
I tried some IPoints to set as Shape:
IPoint point1 (as parameter)
 IPoint point2 = point;
                IPoint point3 = new Point();
                point3.X = point.X;
                point3.Y = point.Y;
                point3.SpatialReference = point.SpatialReference;
                IPoint point4 = new Point();
                point4.X = point.X;
                point4.Y = point.Y;


point 1 to 3 will have exceptions.
Only Point4 without the spatial reference will succeed (with minimal changed Y-coordinate)
0 Kudos
DubravkoAntonic
New Contributor III
I see the problem in
pointFeature.Shape = point as IGeometry;
You should clone this point or create new one before using this point

part
testPoint2.PutCoords(point.X, point.Y);
is just fine because you created new Point
but this point doesn't have the SpatialReference at this moment. Check for it.
0 Kudos
SebastianKrings
Occasional Contributor
hi


ok, I have to "clone" it. But for understanding, why?

By default it has no spatial reference. If I assign the spatial reference from the point parameter (as point3 in my example) it will gain exceptions.
If I continue wihtout the clonedPoint will get a spatial reference (when feature is stored).

One thing I noticed is, that when doing
IPoint newPoint = new PointClass();

the exceptions bill be within newPoint.
After executing
newPoint.PutCoords(point.X, point.Y);

the exceptions has gone away and the coords are in and spatial reference is null.

Why is there mentioned that these fields have triggered an exception instead of setting them null or leaving them clear?


Soi when I go furher through the code, it will still fail on
IFeatureClass nearestContour = join.JoinNearest(name, -1);

With message from subject.

Does JoinNearest need some edit session?
Does the assignd feature class nead a workspace?

Thanks!
0 Kudos
DubravkoAntonic
New Contributor III
Clonning - important because using one object in two objects is not possible if you do not create objectas twice. Create is possible by new operator or by deep cloning. ArcObjects AO implementation if geometry objects does not allow to insert one object into another but rather reguires to insret new object. Look in SDK geometry for maybe a clearer and extensive explanation.

newPoint.PutCoords(point.X, point.Y);
Exception there would be if point object is null or newPoint is null. Can't imagine other scenario.

JoinNearest doesnt require edit session
FeatureClass requires workspace.

Now I dont have idea why you get exception if newPoint and point objects are not null.
0 Kudos
SebastianKrings
Occasional Contributor
hey

hm maybe I wrote it missunderstandly

When I Create a new Object
IPoint newPoint = new PointClass();

Intellisense says that the attributes (X, Y, Z, M, OID) have released an exception

when i assign the coordinates
newPoint.PutCoords(point.X, point.Y);

Intellisense doesnt say any more that some exception had been thrown.
then, X, Y are as put, M and Z have the value "NaN", spatial reference is null and the OID is 0.

so when you say its not possible to have an object reference twice for different use (which also makes sense) then this part is ok

so, you said the FeatureClass needs a workspace
its about this line:
IFeatureClass nearestContour = join.JoinNearest(name, -1);

should this function or must I create a feature class within the workspace and then assign it from the returned featureClass? (which doesnt make sense)

edit:
I tried something but with no different result:
ISpatialJoin join = new SpatialJoinClass();
                join.SourceTable = contourClass as ITable;
                join.JoinTable = point as ITable;
                IName name = new FeatureClassName();
                name.NameString = "nearestContour";
IFeatureClass nearestContour = join.JoinNearest(name, -1);


contourClass is a featureClass(one single polyline) from a real GDB Workspace
point is also a featureClass (one single point) stored in the same GDB
both are lying on top of each other

why does the nearest join fail?
is the method corrupt or are some of my parameters wrong?
cant get any information about it from the documentation

thanks
0 Kudos
DubravkoAntonic
New Contributor III
It will take us away from problem, but:

Try to store FeatureClass , you can't do it without workspace. It can exist but without Parent FeatureDataSet object it doesn't know where it belongs in space because it has no Projection information. I don't know more detail then that.


Spatial reference data is stored in FeatureDataSet and FeatureClass does not implement SpatialReference class but interface and since it does not belongs to parent object. Therefore it interface methods will return null values or throw exception.

About SpatialJoin. I didn't try this one but it makes sense to get exception because it doen't have spatialreference. Try to use IGeometryBag to solve this problem, because this is one main role of IGeomtryBag.
http://resources.esri.com/help/9.3/ArcGISDesktop/ArcObjects/esrigeometry/IGeometryBag.htm
0 Kudos