These are the errors:
Error 1 Cannot implicitly convert type 'Plantool.xRoute.Point' to 'Plantool.xMap.Point'
Error 2 Cannot implicitly convert type 'Plantool.xRoute.Point' to 'Plantool.xMap.Point'
Error 3 Cannot implicitly convert type 'Plantool.xRoute.LineString' to 'Plantool.xMap.LineString'
I have this code which comes with a namespace.
using Plantool; //Contains xMap, xServer, xLocate
And this is the function in question.
/* createMap()
* Input: WaypointDesc[], Route
* Output: string mapURL
* Edited 21/12/12 - Davide Nguyen
*/
private static string createMap(xRoute.WaypointDesc[] waypointDesc, xRoute.Route route)
{
#region boundingBox
// Set boundingBox fand use corners from the calculated route
xMap.BoundingBox boundingBox = new xMap.BoundingBox();
boundingBox.leftTop = route.totalRectangle.rightTop;
boundingBox.rightBottom = route.totalRectangle.leftBottom;
#endregion
#region mapParams
// Build mapParams
xMap.MapParams mapParams = new xMap.MapParams();
mapParams.showScale = true;
mapParams.useMiles = false;
#endregion
#region imageInfo
// Create imageInfo and set the frame size and image format. NOTE: 1052; 863
xMap.ImageInfo imageInfo = new xMap.ImageInfo();
imageInfo.format = xMap.ImageFileFormat.PNG;
imageInfo.height = 1052;
imageInfo.width = 863;
imageInfo.imageParameter = "";
#endregion
#region layers
// Create a line from the calculated route
xMap.LineString[] lineStrings = new xMap.LineString[] { route.polygon };
xMap.Lines[] lines = new xMap.Lines[1];
xMap.LineOptions options = new xMap.LineOptions();
xMap.LinePartOptions partoptions = new xMap.LinePartOptions();
partoptions.color = new xMap.Color();
partoptions.visible = true;
partoptions.width = -10;
options.mainLine = partoptions;
lines[0] = new xMap.Lines();
lines[0].wrappedLines = lineStrings;
lines[0].options = options;
// Define customLayer that contains the object lines and set layers.
xMap.CustomLayer customLayer = new xMap.CustomLayer();
customLayer.visible = true;
customLayer.drawPriority = 100;
customLayer.wrappedLines = lines;
customLayer.objectInfos = xMap.ObjectInfoType.NONE;
customLayer.centerObjects = true;
xMap.Layer[] layers = new xMap.Layer[] { customLayer };
#endregion
#region includeImageInResponse
// Set argument includeImageInResponse to false (default).
Boolean includeImageInResponse = false;
#endregion
// Return object map using the following method.
xMap.Map map = xMapClient.renderMapBoundingBox(boundingBox, mapParams, imageInfo, layers, includeImageInResponse, null);
// Retrieve the image
string result = "http://" + map.image.url;
// Return the drawn map
return result;
}
The problem lies with the boundingBox object and the lineString object. route.totalRectangle contains a Point object from the xRoute namespace which is identical to that of xMap. Is there anyway to copy or convert it?
This issue does not seem to happen in java examples, but it does in C#. I am sure that if I can solve this error, the other ones will be solved aswell. I have searched my ass off on the API, but it may help you:
xMap:
http://xserver.ptvgroup.com/fileadmin/files/PTV-COMPONENTS/DeveloperZone/Documents/PTV_xServer/API/xMapAPI/pages/apidoc.html
xRoute: http://xserver.ptvgroup.com/fileadmin/files/PTV-COMPONENTS/DeveloperZone/Documents/PTV_xServer/API/xRouteAPI/pages/apidoc.html
Still digging myself.
In C# you cannot convert from one type to another, even if they are for all purposes identical, without copying all the properites, etc. unless an implicit conversion exists.
So you can either write a implicit conversion opertor as shown in link above or you could use a tool like AutoMapper to copy between the two objects
I have found another solution for this issue in the meanwhile whilst randomly playing with the code and the API and this is a partial solution for two of the errors by copying over the well known text values from one object to another. Hopefully I can do the same for the linestring part. I am posting this just incase anyone else comes across this and finds it a usefull solution. New code region below.
// Set boundingBox fand use corners from the calculated route
xMap.BoundingBox boundingBox = new xMap.BoundingBox();
xMap.Point rightTop = new xMap.Point();
rightTop.wkt = route.totalRectangle.rightTop.wkt;
xMap.Point leftBottom = new xMap.Point();
leftBottom.wkt = route.totalRectangle.leftBottom.wkt;
boundingBox.leftTop = rightTop;
boundingBox.rightBottom = leftBottom;
EDIT: Same solution for the linestrings.
// Solution: Cannot implicitly conver ttype xRoute.LineString to xMap.LineString
xMap.LineString maproute = new xMap.LineString();
maproute.wkt = route.polygon.wkt;
// Create a line from the calculated route
xMap.LineString[] lineStrings = new xMap.LineString[] { maproute };
Thanks for the help, I hope someone might find this solution usefull aswell.
Review this for your own purposes... but one option is to use a JSON Parser to serialize one class into JSON, then to deserialize it back into a different class. Short and simple answer, but if all you are looking for is to grab properties from Contoso.Project.UrMom, and transfer them directly to Albiet.Project.UrMom, it works well.
I've found this other alternative that is based on serialization of the objects. As far as I'm concerned it has the disadvantage of accessing the disk.
How did you create the client classes from the WSDL's?
I prefer to create them via command line:
WSDL /sharetypes /out:"XServer.cs" /namespace:"Plantool"
"https://xroute-eu-n-test.cloud.ptvgroup.com/xlocate/ws/XLocate?WSDL"
"https://xroute-eu-n-test.cloud.ptvgroup.com/xroute/ws/XRoute?WSDL"
"https://xroute-eu-n-test.cloud.ptvgroup.com/xtour/ws/XTour?WSDL"
/sharetypes ensures that classes such as Point will be merged intoa single shared class
This also works fine with the xServer2 API and it's WSDLs.
Related
i have opened solidworks assembly (swDocumentTypes_e.swDocASSEMBLY) using C# and i have iterated through all the features in order to get all the Sketchs called 'ISO/XXX' under each part of the assembly, here is the code
public void openFile(string skeletonFilePath)
{
object[] Features = null;
int i = 0;
string FeatType = null;[1]
string FeatTypeName = null;
if (string.IsNullOrWhiteSpace(skeletonFilePath)) { return; }
ModelDoc2 model = _sldWorks.OpenDoc("C:PATH/fileName.SLDASM", (int)swDocumentTypes_e.swDocASSEMBLY);
Feature swFeat = default(Feature);
SelectionMgr swSelMgr = default(SelectionMgr);
swSelMgr = (SelectionMgr)model.SelectionManager;
swFeat = (Feature)model.FirstFeature();
while ((swFeat != null))
{
FeatType = swFeat.Name;
FeatTypeName = swFeat.GetTypeName2();
if ((FeatTypeName == "Reference")
{
Debug.Print(" Name of feature: " + swFeat.Name);
Debug.Print(" Type of feature: " + swFeat.GetTypeName2());
}
swFeat = (Feature)swFeat.GetNextFeature();
}
}
the problem:
each time i try to extract the items under the feature (of one part) i got an exception, i have to tried these ways:
swFeat.GetDefinition() // i've got null exception
swFeat.GetSpecificFeature2() // i've got dynamic value which i don't know the class i need to cast with
var childs = (Object[])swFeatSupport.GetChildren(); // i've got only to constraints under the part
example of project
Your code is only iterating over top level features. You can use IFeature::GetFirstSubFeature() and IFeature::GetNextSubFeature to get sub feature. Make this function recursive so it will iterate over all features, regardless of how many levels deep they are. Another layer you need to consider is the components - you need to iterate over components in an assembly first if you need feature data in the context of individual parts.
Here's an example from the Solidworks API documentation. Its poorly written (IMO) but it will guide you in the right direction.
Consider follwing method of copying/cloning an object (all fields are copied into a new object)
public AangepastWerk CloneAdjustedWork(AangepastWerk pAdjustedWork)
{
return new AangepastWerk()
{
AangepastWerkID = pAdjustedWork.AangepastWerkID,
ArbeidsOngeval = pAdjustedWork.ArbeidsOngeval,
DatumCreatie = pAdjustedWork.DatumCreatie,
DatumLaatsteWijziging = pAdjustedWork.DatumLaatsteWijziging,
DatumOngeval = pAdjustedWork.DatumOngeval,
GewijzigdDoor = pAdjustedWork.GewijzigdDoor,
NietErkend = pAdjustedWork.NietErkend,
Stamnummer = pAdjustedWork.Stamnummer,
Verzorging = pAdjustedWork.Verzorging,
VerzorgingId = pAdjustedWork.VerzorgingId
};
}
I have a form that opens up a childform where two objects (2 times the same object of the type mentioned above) is being passed. I open up the form like this:
//my selected Record
Record rec = DateGridAdjustedWorks.ActiveRecord;
AangepastWerk AWorkObject = (AangepastWerk)((DataRecord)rec).DataItem;
AangepastWerk AWorkObjectBackup = _Vm.CloneAdjustedWork(AWorkObject);
WindowModifyAdjustedWork windowForModify = new WindowModifyAdjustedWork(AWorkObject,AWorkObjectBackup, true);
windowForModify.Closing += new CancelEventHandler(OnModifyAWClosing);
windowForModify.ShowDialog();
In that childform I set the first object as DataContext. _adjustedWork and _adjustedWorkCopy are properties of the form
_adjustedWork = pAdjustedWork;
GridAdjustedWork.DataContext = AdjustedWork;
_adjustedWorkCopy = pAdjustedWorkCopy;
The Issue:
In the form i have the ability to alter the object while retaining the original object. the user can see the originalobject, so he has the possibilities to keep track of the changes (request by the user) BUT if i change something in my _adjustedWork (the object that is my datacontext) then my _adjustedWorkCopy (without any actions performed upon it in my code-behind) is changed aswell. My question to you bright minds is: Why does this happen and how do i work around it? What am i missing here (probably something very basic)?
I always do deep cloning with serializing to json.
In example with Servicestack you can:
var json = myObject.ToJson();
var clonedObject = json.FromJson<MyObject>();
return clonedObject;
Maybe this can help.
Found the reason why the Cloned Object recieved the changes as well
public AangepastWerk CloneAdjustedWork(AangepastWerk pAdjustedWork)
{
return new AangepastWerk()
{
AangepastWerkID = pAdjustedWork.AangepastWerkID,
ArbeidsOngeval = pAdjustedWork.ArbeidsOngeval,
DatumCreatie = pAdjustedWork.DatumCreatie,
DatumLaatsteWijziging = pAdjustedWork.DatumLaatsteWijziging,
DatumOngeval = pAdjustedWork.DatumOngeval,
GewijzigdDoor = pAdjustedWork.GewijzigdDoor,
NietErkend = pAdjustedWork.NietErkend,
Stamnummer = pAdjustedWork.Stamnummer,
Verzorging = pAdjustedWork.Verzorging, <------------ Issue lies here
VerzorgingId = pAdjustedWork.VerzorgingId
};
}
pAdjustedWork.Verzorging is an object in this case. I needed to clone this object aswell.I assumed (incorrectly) that cloning as above mentionned would create a new separate 'VerzorgingsObject'.
The solution to my problem is:
MedicalCare_VM mcare_VM = new MedicalCare_VM();
return new AangepastWerk()
{
AangepastWerkID = pAdjustedWork.AangepastWerkID,
ArbeidsOngeval = pAdjustedWork.ArbeidsOngeval,
DatumCreatie = pAdjustedWork.DatumCreatie,
DatumLaatsteWijziging = pAdjustedWork.DatumLaatsteWijziging,
DatumOngeval = pAdjustedWork.DatumOngeval,
GewijzigdDoor = pAdjustedWork.GewijzigdDoor,
NietErkend = pAdjustedWork.NietErkend,
Stamnummer = pAdjustedWork.Stamnummer,
Verzorging = mcare_VM.CloneMedicalCare(pAdjustedWork.Verzorging),
VerzorgingId = pAdjustedWork.VerzorgingId
};
Cloning in:
Verzorging = mcare_VM.CloneMedicalCare(pAdjustedWork.Verzorging)
uses the same logic as mentioned before (copying every field).
I'm currently working on a basic drawing program. One of the requirements is to be able to save the list of drawn objects and load it back in. So far, I have written a save function that exports all items of the list to an XML format, and I'm currently working on the loading-part.
Whenever the program encounters a "< RechthoekTool >" (Dutch for RectangleTool), it executes the following code:
//Create new tool.
RechthoekTool tool = new RechthoekTool();
//Turn <Startpoint> and <Endpoint> into actual points
var sp = Regex.Replace(xn["Startpunt"].InnerText, #"[\{\}a-zA-Z=]", "").Split(',');
tool.startpunt = new Point(int.Parse(sp[0]), int.Parse(sp[1]));
var ep = Regex.Replace(xn["Eindpunt"].InnerText, #"[\{\}a-zA-Z=]", "").Split(',');
tool.eindpunt = new Point(int.Parse(ep[0]), int.Parse(ep[1]));
//Set colour and width of brush
string kleur = xn["Dikte"].InnerText;
kleur.Replace(#"Color [", "");
kleur.Replace(#"]", "");
Color c = Color.FromName(kleur);
tool.kwastkleur = c;
tool.kwast = new SolidBrush(c);
tool.dikte = int.Parse(xn["Dikte"].InnerText);
//Add to list
s.listItems.Add(tool);
Whenever I run the program, I get the 'NullReferenceException was unhandled' error("Object reference not set to an instance of an object.") at
s.listItems.Add(tool);
I do, however, instantiate the tool right at the beginning, don't I? What could be causing this error? Some Googling told me it might be because I forgot to assign a property, but as far as I can tell I've got them all covered...
Help would be greatly appreciated.
The error is due to s or s.listItems not being instantiated.
Without seeing more code, it's difficult to know which is null, but at a guess you are creating a new object for s, which contains a property/field listItems, but you aren't assigning a list to listItems.
The problem is that you aren't instantiating listItems or s. Not enough information is given to tell you how to instantiate s but you can do the other one like this:
s.listItems = new List<RechthoekTool>();
If you don't instantiate something using the new keyword; it simply won't work.
Using your code, try this:
//Create new tool.
RechthoekTool tool = new RechthoekTool();
//Turn <Startpoint> and <Endpoint> into actual points
var sp = Regex.Replace(xn["Startpunt"].InnerText, #"[\{\}a-zA-Z=]", "").Split(',');
tool.startpunt = new Point(int.Parse(sp[0]), int.Parse(sp[1]));
var ep = Regex.Replace(xn["Eindpunt"].InnerText, #"[\{\}a-zA-Z=]", "").Split(',');
tool.eindpunt = new Point(int.Parse(ep[0]), int.Parse(ep[1]));
//Set colour and width of brush
string kleur = xn["Dikte"].InnerText;
kleur.Replace(#"Color [", "");
kleur.Replace(#"]", "");
Color c = Color.FromName(kleur);
tool.kwastkleur = c;
tool.kwast = new SolidBrush(c);
tool.dikte = int.Parse(xn["Dikte"].InnerText);
List<RechthoekTool> s = new List<RechthoekTool>(); // You can now use your list.
//Add to list
s.listItems.Add(tool);
In Revit 2013 I have tool that I'm making that copies dimensions from one drafting view to another. I've got it to properly create a new version of a dimension including the Curve, DimensionType, and References but I'm having trouble with the properties Above, Below, Prefix, and Suffix. They copy just fine if at least one of them has a value. However, if none of them have a value then it will throw an AccessViolationException when I try to access them. I have tried to catch that exception but it bubbles up and it crashes Revit (I'm assuming it's caused by native code that fails).
How can I check to see if these properties have any value when I do my copying without triggering this AccessViolationException?
Autodesk Discussion Group Question
The DimensionData class is my own used for storing the dimension information so that it can be used to create the dimension in a separate document.
private IEnumerable<DimensionData> GetDimensionDataSet(Document document,
View view)
{
if (document == null)
throw new ArgumentNullException("document");
if (view == null)
throw new ArgumentNullException("view");
List<DimensionData> dimensionDataSet = new List<DimensionData>();
FilteredElementCollector dimensionCollector =
new FilteredElementCollector(document, view.Id);
dimensionCollector.OfClass(typeof(Dimension));
foreach (Dimension oldDimension in dimensionCollector)
{
Line oldDimensionLine = (Line)oldDimension.Curve;
string dimensionTypeName = oldDimension.DimensionType.Name;
List<ElementId> oldReferences = new List<ElementId>();
foreach (Reference oldReference in oldDimension.References)
oldReferences.Add(oldReference.ElementId);
DimensionData dimensionData;
try
{
string prefix = oldDimension.Prefix;
dimensionData = new DimensionData(oldDimensionLine,
oldReferences,
dimensionTypeName,
prefix,
oldDimension.Suffix,
oldDimension.Above,
oldDimension.Below);
}
catch (AccessViolationException)
{
dimensionData = new DimensionData(oldDimensionLine,
oldReferences, dimensionTypeName);
}
dimensionDataSet.Add(dimensionData);
}
return dimensionDataSet;
}
Regarding transactions: As far as I'm aware, you are only required to be inside a transaction when you are making any sort of CHANGE (modifications, deletions, additions). If all you are doing is collecting dimension information, you would not need a transaction, but when you use that information to create new dimensions in another document, that code would have to be inside a transaction. I have had a number of programs under development which did not yet modify the document but simply collected parameter settings and posted them to a TaskDialog.Show(). These programs worked fine, and I don't see anything in your code that actually modifies your model, so that doesn't seem to be your issue.
It seems like I bug.
Can you post the issue to the ADN Support?
The solution I can suggest is to use Parameters of the Dimension element instead of Dimension class properties.
For example, you can get Suffix and Prefix by following code
var suffixParameter =
oldDimension.get_Parameter(BuiltInParameter.SPOT_SLOPE_SUFFIX);
string suffix = null;
if (suffixParameter != null)
{
suffix = suffixParameter.AsString();
}
var prefixParameter =
oldDimension.get_Parameter(BuiltInParameter.SPOT_SLOPE_PREFIX);
string prefix = null;
if (prefixParameter != null)
{
prefix = prefixParameter.AsString();
}
Unfortunatelly, I don't tell you how to get Above and Below Properties via parameters, because I don't have a project to test. But you can easily determine parameters using BuiltInParameter Checker
Hope it helps.
Does anyone out there use the .Net topology suite?
I'm a bit stuck, I'm trying to get the envelope so I can validate dimensions
According to http://resources.esri.com/help/9.3/arcgisengine/dotnet/c6e6b26c-be52-4176-b1e5-bb628d10acd0.htm (using the C# example at the bottom of the page)
I'm taking and IGeometry type (boundary) and casting that polygon's envelope to an IEnvelope (envelope) with which I am hoping to look at the width and height properties
But envelope is always null
IGeometry boundary;
var wktReader = new WKTReader(OSGBGeometryFactory.Factory);
boundary = wktReader.Read(projectDTO.BoundaryWKT);
IEnvelope envelope = boundary.Envelope as IEnvelope;
Can anyone help, this is my first time with this suite.
What I'm trying to work out is if following this example I already have an IGeometry type (my boundary variable) why is it null when I try and cast it.
using ESRI.ArcGIS.Geometry;
class temp
{
public void test()
{
// Create an empty polygon object.
IArea areaPolygon = new PolygonClass();
// Cast to the IGeometry interface of the polygon object.
IGeometry geometryPolygon = (IGeometry)areaPolygon;
// Use the .Envelope property on the IGeometry interface of the
// polygon object to get an envelope object.
IEnvelope envelope = geometryPolygon.Envelope;
// Test to make sure you have an envelope object.
if (envelope is Envelope)
{
// The polygon object and resulting envelope are empty.
if (envelope.IsEmpty)
{
System.Windows.Forms.MessageBox.Show("The envelope is empty.");
}
}
}
}
Do I need to create a new polygon and try casting that (i.e., replicate the IArea areaPolygon = new PolygonClass();)?
I too faced the same problem. It is an issue of the API developer using a weird naming convention for Envelope. IGeometry.Envelope is actually an IGeometry object. You should instead use IGeometry.EnvelopeInternal instead.
IGeometry boundary;
var wktReader = new WKTReader(OSGBGeometryFactory.Factory);
boundary = wktReader.Read(projectDTO.BoundaryWKT);
IEnvelope envelope = boundary.EnvelopeInternal;
I am not sure what OSGBGeometryFactory.Factory does, as a reader ususally takes some WKT. Here is an example that does what you want, where the WKT was created by buffering a point in postgis, for what it is worth.
WKTReader rdr = new WKTReader();
Polygon poly =(Polygon) rdr.Read(
"POLYGON((10 0,9.23879532511287 -3.82683432365089,7.07106781186548 -7.07106781186547,3.82683432365091 -9.23879532511286,1.61554255216634e-14 -10,-3.82683432365088 -9.23879532511287,-7.07106781186546 -7.07106781186549,-9.23879532511286 -3.82683432365092,-10 -3.23108510433268e-14,-9.23879532511288 3.82683432365086,-7.0710678118655 7.07106781186545,-3.82683432365094 9.23879532511285,-4.62458305157398e-14 10,3.82683432365085 9.23879532511289,7.07106781186544 7.07106781186551,9.23879532511284 3.82683432365095,10 0))");
GeoAPI.Geometries.ICoordinate [] coords = poly.Envelope.Coordinates;
double width = coords[2].X - coords[0].X;
double height = coords[2].Y - coords[0].Y;
Console.WriteLine("width={0:f}, height={1:f}", width, height);