Jump to content


  • Posts

  • Joined

  • Last visited

Everything posted by relume

  1. Hello I am wondering if there is an easy assignment command for objects to change layers as it is for classes (vs.setClass or vs.setClassN). Can it be true, that this should be only possible by duplicating the object first (by vs.CreateDuplicateObject) and thereafter deleting the original? In the VW GUI info-Palette with the appropriate pop-list the task seems more as an reasignment than a duplication (or a hidden cut/past operation). Many thanks in advance and best regrads,
  2. Hello Importing many Shape files into a VW document can be very time consuming. So I would like to write a pyhton script, that will take all Shape files from a folder list and import every file into the VW document. On the VectorScript reference page I can find the command "vs.LegacyShapefileImp()" and the description "Use the old UI to import files". There is no example and nor further specification why this is "legacy" and which command is the actual replacement command. Has any body used a new vs command to import Shape files and could therefore reference me the appropriate documentation? Many thanks in advance and best regards, André
  3. Hello So my approach is, also by condoning the issues with the FindObjAtPt_Create (e.g. the function does not search on the objects precise shape but on its bounding box), it the following script (may be it may help others and save time): def object_atPt_list(vPoint_ToSearch, vPoint_ToSearch_Tolerance = 0, vLayers_ToSearch = None, vSelection_Criteria = ''): import vest.base.vw._ vLayer_Active_handle = vs.ActLayer() vLayer_Active_name = vs.GetLName(vLayer_Active_handle) vXorg, vYorg = vs.GetOrigin() vPoint_ToSearch_new_X = vXorg+vPoint_ToSearch[0] vPoint_ToSearch_new_Y = vYorg+vPoint_ToSearch[1] # vs.AlrtDialog('X/Y Org : ' + str(vXorg) + '/' + str(vYorg) + '\n' + 'PointToSearch new X/Y : ' + str(vPoint_ToSearch_new_X) + '/' + str(vPoint_ToSearch_new_Y)) if vLayers_ToSearch is None: vLayers_ToSearch = layers_info_list('visible') vObjects_ToSearch = 0 if vSelection_Criteria != '': vs.DSelectAll() vs.SelectObj(vSearch_Selection_Criteria) vObjects_ToSearch = 2 vObject_Handle_list = list() for vLayers_ToSearch_item in vLayers_ToSearch: vs.Layer(vLayers_ToSearch_item["name"]) vSearch_Container_start = vs.Handle() vSearch_list = vs.FindObjAtPt_Create(vSearch_Container_start, vObjects_ToSearch, 0, vPoint_ToSearch_new_X, vPoint_ToSearch_new_Y, vPoint_ToSearch_Tolerance) # 2 = selected only; 0 = shalow vSearch_list_size = vs.FindObjAtPt_GetCount(vSearch_list) for i in range(vSearch_list_size): vObject_handle = vs.FindObjAtPt_GetObj( vSearch_list, i ) vObject_Handle_list.append(vObject_handle) # vs.AlrtDialog( 'Index: ' + str(i) + '\n' + 'Obj Type: ' + str(vs.GetTypeN(vObject_handle))) vs.FindObjAtPt_Delete( vSearch_list ) if vSelection_Criteria != '': vs.DSelectAll() vs.Layer(vLayer_Active_name) # vs.AlrtDialog ("vest.base.vw.objects.object_atPt_list : vObject_Handle_list : " + str(vObject_Handle_list)) return(vObject_Handle_list) and the called script snippet "layers_info_list" to get a layers list to search in, if the layers list is not provided in the function parameters: def layers_info_list(vVisibility="all"): vLayer_list = list() vLayer_handle = vs.FLayer() vLayer_id = 1 while vLayer_handle != None: vLayer_attributes = {} vLayer_attributes["id"] = vLayer_id vLayer_attributes["handle"] = vLayer_handle vLayer_attributes["name"] = vs.GetLName(vLayer_handle) vLayer_visibility = vs.GetLVis(vLayer_handle) vLayer_attributes["visibility"] = vLayer_visibility vLayer_attributes["scale"] = vs.GetLScale(vLayer_handle) vLayer_attributes["options"] = vs.GetLayerOptions() vLayer_attributes["mode"] = vs.GetLayerRenderMode(vLayer_handle) vLayer_id += 1 if vVisibility == "visible" and vLayer_visibility == 0: # normal vLayer_list.append(vLayer_attributes) elif vVisibility == "visible_all" and (vLayer_visibility == 0 or vLayer_visibility == 2): # normal or grayed vLayer_list.append(vLayer_attributes) elif vVisibility == "grayed" and vLayer_visibility == 2: # grayed vLayer_list.append(vLayer_attributes) elif vVisibility == "invisible" and vLayer_visibility == 1: # invisible vLayer_list.append(vLayer_attributes) elif vVisibility == "all": vLayer_list.append(vLayer_attributes) vLayer_handle = vs.NextLayer(vLayer_handle) return (vLayer_list) best regards
  4. Hello Thank you very much. Yes this is the approach I am considering - although I hopped for a more convenient way. I have addressed the issue with the origin shift already some years ago (see my post (3rd entry) : FindObjAtPt_Create any working example? I have documented the issue with the circle/arc object in the same post (see 4th entry). best regards
  5. Hello Pat Thank you for considering my question. vs.ForEachObjectAtPoint has similiar issues - works only on the active layer and does not enter in grouped objects.
  6. Hello I am still struggling with this very basic geometric search problem. I am looking for an approach to select 2D objects by a 2D point (preferably with a "pick radius") that lays within the objects to be searched/selected or are overlapped by the pick radius. The issues with the vs functions are still the same as reported some years ago: FindObjAtPt_Create any working example? basic but sever issues with the vs.FindObjAtPt_Create functions are: works only on the active layer and not over all layers or a selection of layers (e.g. visible ones) works only if the document origin does not have been moved - that is a very sever issue does not work correctly on arcs and other object types So my question is, are there any alternative approaches now with python to achieve this? Many thanks for any hint and best regards.
  7. Hello I wanted to install the "pandas" library and found problems using the Marionette.VerifyOrGetLib() function but also with the above script from DomC that is similar to the Marionette.VerifyOrGetLib() function. Further for both functions/scripts an URL to a specific version of library to be installed is needed. But pip.main() has the possibility to get the right library version for the VectorWorks Python environment (acutally in VW2018 is 3.5.2). I was able to install the library "numpy" with the following command : pip.main(['install', 'numpy', '--target', vPathToMy_VW_PythonExternals_Folder]) But this did not work for the library "pandas" as the appropriate pip.main() command rised an error saying that there is no correct matching version. But by passing an "-q" parameter "pandas" installs correctly: pip.main(['install', 'numpy', '-q', '--target', vPathToMy_VW_PythonExternals_Folder]) Then I tried also to install "pillow" and it installed also correctly (version 5.0.0) with all dependencies. But there is some problem with probing for correct installation. While the lib distribution is called "pillow", the name to retrieve it with pip.main(), testing the existence and for importing the lib has to be named "PIL". For this reason Morionette.VeriyOrGetLib() does not work. So the installed lib "pillow" has to be tested and imported by: importlib.import_module('PIL') So a script that encompass this problem could be as this: import os import sys import importlib import vs appfolder = vs.GetFolderPath(1) appuserfldr = vs.GetFolderPath(12) cmd = 'Python Externals' if (sys.platform == 'darwin'): pos = appfolder.find(':') appfolder = appfolder[pos:] appfolder = appfolder.replace(':','/') pos = appuserfldr.find(':') appuserfldr = appuserfldr[pos:] appuserfldr = appuserfldr.replace(':','/') cmd = appuserfldr + cmd vs.AlrtDialog("path : " + cmd) if not os.path.exists(cmd): os.makedirs(cmd) #libToimport = 'numpy' #libToimport = 'pandas' libToimport = 'pillow' libToimportAlias = 'PIL' try: importlib.import_module(libToimportAlias) except ImportError: import pip pip.main(['install', '--upgrade', '-q', libToimport, '--target', cmd ]) importlib.import_module(libToimportAlias) try: importlib.import_module(libToimportAlias) exit_code = True vs.AlrtDialog('is installed : '+ libToimport) except ImportError: vs.AlrtDialog('not installed : '+ libToimport) Best regards P.S. And not to forget to reference the python search path to "~/Library/Applications Support/VectorWorks/.../Python Externals"
  8. Hello Pat Thank you very much for answering. I had a flawed reasoning so the command vs.GetRField(object_handle, record_name, field_name) works correct, when passing a record handle to it. Although is somewhat tautologous as in this way a handle to the record and the name to the same record has to be given. So the code would be by referencing the code snippet above: import vs vHandle = "" vRecordsNum = vs.NumRecords(vHandle) vs.AlrtDialog("Databases : " + str(vRecordsNum)) for vRecordID in range(1, vRecordsNum+1): vRecordHandle = vs.GetRecord(vHandle, vRecordID) vRecordName = vs.GetName(vRecordHandle) vFieldsNum = vs.NumFields(vRecordHandle) for vFieldID in range(1, vFieldsNum+1): vFieldName = vs.GetFldName(vRecordHandle, vFieldID) vFieldType = vs.GetFldType(vRecordHandle, vFieldID) vFieldFlag = vs.GetFldFlag(vRecordHandle, vFieldID) vFieldValue = vs.GetRField(vRecordHandle, vRecordName, vFieldName) vMessage = "Record : " + vRecordName + " Field : " + str(vFieldID) + " : " + vFieldName + " : " + str(vFieldType) + " : " + str(vFieldFlag) + " : " + vFieldValue vs.AlrtDialog(vMessage) best regards, André
  9. Hello Thank you very much for your answers. Yes I used the Name Node for starting my Marionette Network. But original I was scripting a python script to read out different object properties like surface/area etc. by clicking with the mouse on it. In a hurry I wanted to verify with the Marionette Network on different objects in the drawing, if my script is using the correct vs.commands. So ideally I could borrow some code portions of the Marionette Network. So I think I stay for certain uses with scripts ... best regards, André
  10. Hello I wonder if I have missed something with marionette. I want to create a marionette network, on which I can get an object-handle as an input to the marionette network by clicking with the mouse/cursor on any object in the drawing. At the moment I can not figure out how to accomplish this (in a hurry). Many thanks in advance
  11. Hello I try to clone/merge databases (record format) by python scripting. So far I can copy database definitions by vs.GetFldName, vs.GetFldType, vs.GetFldFlag but I have not seen any possibility to get the default field value (fieldValue), that can be set by vs.NewField(recName, fieldName, fieldValue, fType, fFlag). Is there any known workaround to get this default field value? Many thanks in advance,
  12. Hello Many thanks for the diverse inputs. If I understand Dom's input correctly about the vs.Message window in VW2018, the window appearance has improved, but still it will show only at the end of the script? As Dom mentioned the use of a subprocess for logging to a file (more precisely to open it on MacOS in TextEdit), I had today a look at python and tkinter to implement a message window that "lives" in its own process. At the moment I have no working solution, but it seems to be feasible to communicate from the VW2018 python environment over sockets/pipes to a tkinter window's mainloop. best regards
  13. Hello Nebeor Thank you for your suggestion. The log-file approach is some kind of a workaround, but is not the intended function, that a GUI should provide. In VectorWorks-script "Message" worked perfectly, but in python it does not work, during a script-execution. So there is no "visual" feedback to the user, in order to get an idea, what is happening. best regards P.S. hopping vs.Message will work in VW 2018
  14. Hello Marissa and Pat Many thanks for your considerations and many thanks for the hint with the "Mix2" node. Yes with this approach I got my "challange" managed (see attachmend). Although VW worked for a longtime to process the network. I think it has to do with the n*m list combination that the "Mix2" node is creating - it is obvious that from set theory this matrix of combinations (items of outer loop and elements of inner loop) do the "analog" thing as a nested loop, but in regard of performance procedural nested loop may in certain case be faster. In regard to Pat's considrations, I agree mostly with his arguments. But I have to say that I am yet not very well trained with building Marionettes. I have in the german forum already some times ago suggested to implement the possibility to link Marionette-networks to script palettes. Also I would appreciate to organize Marionettes on a separate type of layer and not on construction layers with fixed scales. But in general I esteem the approach of Marionette to be a complementary scripting method - the possibility for easier interlinking both would be nice . Best regards, CompareObjectsForOverlapping.vwx
  15. Hello I am look for any hint or example how I can create a marionette network to implement a nested loop with standard nodes (otherwise I would be faster to write my owen traditional pyhton script)? My "challenge" is to iterate over a list of objects (ca. 2000 building objects) and test them against a second list of objects (ca. 30 quarter objects) in order to determine in which quarter object each building object is located. - So I create as first the building object list with an appropriate criteria. - Then I crate the quarter object list with its appropriate criteria. - Then I should iterate over the building object list, and for every building object item I should iterate over the entire quarter object list. - Finally for every actual building object item and quarter object item combination I test for overlapping. Many thanks for any hint.
  16. Hello I would like to use the vs command vs.Message in pyhton like I used it in vectorscript. But it seems that vs.Message does not work as expected. As far I can see the Message window is only opened at the end of the called python script. Is there any possibility to make vs.Message to work as it should - the window is opened at the first call to vs.Message and updated on every futher vs.Message call. Otherwise the command is useless. Many thanks in advance and best regards
  17. Hello Josh Thank you very much - finally I went the way you proposed also. I tried also the command "vs.SetAngle" and that is the command I searched for (absolute rotation), but unfortunately this command works only on "pure" 2D Objects but not on 2D Symbols.
  18. Hello I have to rotate 2D objects in vectorscript/python by an individual absolute angle. With vs.HRotate the rotation is executed in relation to the actual angle - so the actual object angle value is added by the angle value set with vs.HRotate ( actual angle is for examble 30d, the angle for rotation is 45d so with HRotate the resulting angle will be 75d - but I want the object to be rotate to the absolute angle of 45d) . Is there any alternative command to set an absolute angle - e.g. set/access the object angle field directly? Many thanks in advance
  19. Hello Josh Thank you very much - your tip did it. Although it is some bit strange that VectorWorks does not document this special case with the nil handle to access the databases/records attached to the document itself. The following python script snippet shows how it works. Maybe it helps others ... import vs vHandle = "" vRecordsNum = vs.NumRecords(vHandle) vs.AlrtDialog("Databases : " + str(vRecordsNum)) for vRecordID in range(1, vRecordsNum+1): vRecordHandle = vs.GetRecord(vHandle, vRecordID) vRecordName = vs.GetName(vRecordHandle) vMessage = "Database : " + str(vRecordID) + " : " + vRecordName + " : " +str(vRecordHandle) vs.AlrtDialog(vMessage) vFieldsNum = vs.NumFields(vRecordHandle) vFieldsName = vRecordName + " : " for vFieldID in range(1, vFieldsNum+1): vFieldsName = vFieldsName + vs.GetFldName(vRecordHandle, vFieldID) + ", " vs.AlrtDialog(vFieldsName)
  20. Hello Raymond Thank you very much for your answer. Yes I am scripting in python, but I have to rely on vs.functions in order to access VW information/data. I do not use worksheets and in this sens I would like only to obtain a list of all databases (not the record instances) that are present in the VW document in order I can generate a generic dialog/script for which the user can select the appropriate database and database-field to operate on (in this case to label or rotate objects arrcording to an database-field value selected by the user at script runtime). best regards
  21. Hello I would like to create a custom dialog where I can select in a pulldown-menu a list of all databases in the actual document. In a second pulldown-menu I woud like to show the corresponding database-fields. What I am missing in the vs function references are the appropriate vs functions to get/retrieve those lists. Do I have missed or overseen something? many thanks in advance.
  22. relume


    Hello In python the behavior of vs.GetPt is very different as in vectroscript. Calling vs.GetPt(callback) in python executes all following statements without waiting for the end of the called callback-function: def callback(pt) vMessage = 'X/Y : ' + str(pt[0]) + '/' + str(pt[1]) vs.AlrtDialog(vMessage) vs.DSelectAll() vs.GetPt(callback) vs.AlrtDialog('the end') This means in this example that the message "the end" is shown before the message "X/Y ..." is shown from the callback-function "callback". Is there any way to get the result of vs.GetPt function back to the calling level where it can be processed successively, as it is some bit "strange" to write "main" code into the callback-function of vs.GetPt? Many thanks
  23. Hello Furthermore "FindObjAtPt_Create" works on the bounding box area and not only on the surface of the object as expected.
  24. Hello I found with trial and error that the command "FindObjAtPt_Create" does not work for Arc-objects. "FindObjectAtPt_Create" does only find Arc-objects if the specified point within specified radius overlaps the left side Arc-boundary line. "left side" of the Arc means that the Arc segment from 180-360 degrees (clockwise) from the insertion point of the Arc are responsive to "FindObjectAtPt_Create". See picture (small red circles = Arc-object is found, small black circles = Arc-object is not found, cross = Arc-insertion point).
  25. Hello Further that the command "FindObjectAtPt_Create" works only for objects on the active layer it works also only correctly if the null point (document origin) of the drawing has not been changed. By moving the null point (document origin) of the drawing, the command "FindObjectAtPt_Create" does find not anymore objects. I do not know if that represent a bug, but I guess so. The above example script should then include an adjustment for the X, Y parameters of the "FindObjectAtPt_Create" command with the document origin: PROCEDURE ObjectInRadius; VAR cnt, i : INTEGER; startContainer : HANDLE; list : LONGINT; loc: VECTOR; vX : REAL; vY : REAL; vXnew : REAL; vYnew : REAL; vXorg : REAL; vYorg : REAL; vObjectHandle : HANDLE; vObjectName : STRING; BEGIN dselectall; startContainer := NIL; GetPt(vX,vY); GetOrigin(vXorg, vYorg); AlrtDialog(Concat('X/Y Org : ', vXorg, '/', vYorg)); vXnew := vXorg+vX; vYnew := vYorg+vY; AlrtDialog(Concat('X/Y; new : ', vX,'/', vY, ' ; ', vXnew,'/', vYnew)); list := FindObjAtPt_Create(startContainer, 0, 1, vXnew, vYnew, 0.5); cnt := FindObjAtPt_GetCount(list)+1; i := 0; WHILE i < cnt DO BEGIN vObjectHandle := FindObjAtPt_GetObj(list, i); vObjectName := GetName(vObjectHandle); SetSelect(vObjectHandle); AlrtDialog(Concat('object : ', i , ' : ', vObjectName, ' : ', vObjectHandle)); i := i + 1; END; END; Run(ObjectInRadius);
  • Create New...