sketchucation logo sketchucation
    • Login
    Oops, your profile's looking a bit empty! To help us tailor your experience, please fill in key details like your SketchUp version, skill level, operating system, and more. Update and save your info on your profile page today!
    πŸ«› Lightbeans Update | Metallic and Roughness auto-applied in SketchUp 2025+ Download

    How to use Ruby API

    Scheduled Pinned Locked Moved Developers' Forum
    28 Posts 5 Posters 1.5k Views 5 Watching
    Loading More Posts
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes
    Reply
    • Reply as topic
    Log in to reply
    This topic has been deleted. Only users with topic management privileges can see it.
    • honoluludesktopH Offline
      honoluludesktop
      last edited by

      OK, now I can locate components, their name, and groups. How do I use the API to get information of the faces within a component, or group?

      
      module WMY_putdxf
       def WMY_putdxf.main #main proc
         .
         model = Sketchup.active_model # make db of active model
         entities = model.active_entities
         selection = model.selection # make db of selections
      
         if model.selection.empty? 
             entities = model.active_entities    
         else 
            entities = model.selection    
         end #endif
      
         entities.each do |e| # do loop through database and 
                              # place entities in type array
           if e.is_a? Sketchup;;ComponentInstance
                stuff= e.definition.name
                WMY_putdxf.get_faces(stuff) #call procedure/function
           end #endif
         end #end loop
         .
      

      And:

      
          def WMY_putdxf.get_faces (stuff)# procedure or method
              # UI.messagebox(stuff)# used this to test 
              # if component instance is selected
              # How do I use API to get component's face info
                  	
          end
      

      Btw, please advise if I have redundant coding:-), or if my qusetions don't make sense.

      1 Reply Last reply Reply Quote 0
      • thomthomT Offline
        thomthom
        last edited by

        group.entities

        component_instance.definition.entities

        That will give you a collection of the entities they contain - like model.entities.

        Thomas Thomassen β€” SketchUp Monkey & Coding addict
        List of my plugins and link to the CookieWare fund

        1 Reply Last reply Reply Quote 0
        • honoluludesktopH Offline
          honoluludesktop
          last edited by

          OK, so now all I have to do is search the new collection for faces? Lets see if I can figure that out:-)

          1 Reply Last reply Reply Quote 0
          • TIGT Offline
            TIG Moderator
            last edited by

            This makes a 'list' called faces of all of the faces inside the group...

            
            faces=[] 
            ### *** note how the list must be defined outside of the {...} block
            group.entities.each{|e|faces<<e if e.class==Sketchup;;Face}
            
            

            This approach can be adjusted to suit any type of 'entities' list and any type of 'class' of thing you want to extract from it - faces, edges, cpoints, clines, text...
            Then of course you can loop through you faces for say a particular material (or any other property)...

            
            red_faces=[] ### ***
            faces.each{|f|red_faces<<f if f.material.name=="Red"}
            
            

            red_faces now contains all of the group's faces that are "Red" etc etc...

            PS: Note that the .entities method returns all of the entities associated with the specified object - i.e. model/group/definition... There is another list of entities: model.active_entities that applies to the current set of entities available in the present edit session - this could equivalent ot the model.entities or if you are editing a group or component-definition the available entities within that - e.g. group.entities...

            TIG

            1 Reply Last reply Reply Quote 0
            • honoluludesktopH Offline
              honoluludesktop
              last edited by

              OK, I put:

              
                 if e.is_a? Sketchup;;ComponentInstance
                     name=e.definition.name#e.typename
                     faces=e.definition.entities
                     WMY_putdxf.get_faces(name,faces)
                 end
              
              

              And:

                
              def WMY_putdxf.get_faces(name,faces)# procedure or method
                 faces.each do |e|
                   info = e.typename
                   if e.is_a? Sketchup;;Face
                     UI.messagebox(name+"; "+info)
                   end #endif
                 end #end do
              end #end method
              
              

              So, you declare a array=[], but a collection (something like an array) makes itself?
              OK, how do I make a collection of the geometric imformation inside each face so that I can access it later? Wild guess to start below:

                
              def WMY_putdxf.get_faces(name,faces)# procedure or method
                 faces.each do |e| #why do we use e; can I use f?
                   info = e.typename
                   if e.is_a? Sketchup;;Face
              
                      facegeo=e.something #get face geo collection goes here?
              
                   end #endif
                 end #end do
              end #end method
              
              
              1 Reply Last reply Reply Quote 0
              • TIGT Offline
                TIG Moderator
                last edited by

                @honoluludesktop said:

                OK, I put:

                I USE CAPITALS FOR EASE OF READING ONLY !!!

                
                >    if e.is_a? Sketchup;;ComponentInstance
                >        name=e.definition.name#e.typename### NAME IS THE 'NAME' - LIKE 'BED' TYPENAME IS THE CLASS/KIND_OF ETC
                >        faces=e.definition.entities### THERE WILL BE MORE THAN FACES IN ENTITIES - AT LEAST EDGES TO FORM THE FACES
                >        WMY_putdxf.get_faces(name,faces)### IF YOU WANT TO PASS THE DEFINITION THEN PASS E.DEFINITION NOT ITS 'NAME'
                >        ### REMEMBER THAT 'FACES' IS 'ENTITIES' THAT WILL INCLUDE FACES BUT NOT JUST FACES ALONE...
                >    end
                > 
                

                And:

                  
                > ### START DEF WITH lowercase LETTERS !!! wmy_putdxf etc
                > ### THIS GETS YOU NOTHING EXCEPT A MESSAGE LISTING THE DEF'S NAME AND EACH FACE IN TURN...
                > def WMY_putdxf.get_faces(name,faces)# procedure or method
                >    faces.each do |e|
                >      info = e.typename
                >      if e.is_a? Sketchup;;Face
                >        UI.messagebox(name+"; "+info)
                >      end #endif
                >    end #end do
                > end #end method
                > 
                

                So, you declare a array=[], but a collection (something like an array) makes itself?
                AN ARRAY FACES=[] IS A LIST
                OK, how do I make a collection of the geometric imformation inside each face so that I can access it later? Wild guess to start below:

                  ### REMEMBER THE lowercase LETTERS TA THE START
                > def WMY_putdxf.get_faces(name,faces)# procedure or method
                >    faces.each do |e| #why do we use e; can I use f? ### CAN USE ANY VARIBALE 'E' IS OFTEN USED FOR 'EntitY'
                >      info = e.typename
                >      if e.is_a? Sketchup;;Face
                > 
                >         facegeo=e.something #get face geo collection goes here?
                > 
                >      end #endif
                >    end #end do
                > end #end method
                > 
                

                HERE IS MY GET FACE VERSION...

                
                if object.class==Sketchup;;ComponentInstance
                  faces=[]
                  object.definition.entities.each{|entity|
                    faces<< entity if entity.class==Sketchup;;Face
                  }
                  ### now do stuff to these faces...
                end#if
                
                

                Done with sub-defs or anything... Tests if the object is an Instance and if so make an Array [list] of its Definition's Entities' Faces to process...

                TIG

                1 Reply Last reply Reply Quote 0
                • honoluludesktopH Offline
                  honoluludesktop
                  last edited by

                  Thanks guys. Will work on this later tonight after I get home. About the lowercase, if the def is inside a module, will it make a difference?

                  This runs ok on my system:

                  
                  require 'sketchup.rb'
                   
                  module WMY_putdxf
                   
                    def WMY_putdxf.main
                   
                      model = Sketchup.active_model # make db of active model
                  	entities = model.active_entities
                      selection = model.selection # make db of selections
                  	
                     if model.selection.empty? 
                         entities = model.active_entities    
                     else 
                        entities = model.selection    
                     end
                  	 
                   	# test if selection made
                      entities.each do |e| # do loop through database and place entities in type array
                  	    if e.is_a? Sketchup;;ComponentInstance
                  			#comp_file_name=e.definition.name
                  			name=e.definition.name#e.typename
                  			faces=e.definition.entities
                  			WMY_putdxf.get_faces(name,faces)
                  		end
                  	end
                   
                    end # .main method
                    
                    def WMY_putdxf.get_faces(name,faces)# procedure or method
                  
                  	faces.each do |e|
                  	   info = e.typename
                  	   if e.is_a? Sketchup;;Face
                  			UI.messagebox(name+"; "+info)
                  	   end #ednif
                  	end #end do
                      
                    end
                       
                  end # WMY_putdxf module
                    
                  #----------------menu------------------
                  if !file_loaded?(__FILE__) #_FILE_  permits renaming the file
                    UI.menu("Plugins").add_item("Yet Another Test") { WMY_putdxf.main }
                  end
                   
                  file_loaded(__FILE__)
                  

                  But with WMY_ as wmy_ this error message:

                  Error Loading File yet_another_script.rb
                  C:/PROGRA~1/Google/GO2494~1/Plugins/yet_another_script.rb:3: class/module name must be CONSTANT

                  Sorry for the uneven indenting, when I copy from notepad++ and paste, the indent spacing changes.

                  1 Reply Last reply Reply Quote 0
                  • Chris FullmerC Offline
                    Chris Fullmer
                    last edited by

                    module names always must start with a capital letter. methods do not start with a cap. Classes start with a cap. That is the basic rule. Constants are variables that start with a capital letter, and should remain constant - like Pi.

                    Chris

                    Lately you've been tan, suspicious for the winter.
                    All my Plugins I've written

                    1 Reply Last reply Reply Quote 0
                    • thomthomT Offline
                      thomthom
                      last edited by

                      @chris fullmer said:

                      module names always must start with a capital letter. methods do not start with a cap. Classes start with a cap. That is the basic rule. Constants are variables that start with a capital letter, and should remain constant - like Pi.

                      Chris

                      Normal convention is to type constants in all caps.

                      Thomas Thomassen β€” SketchUp Monkey & Coding addict
                      List of my plugins and link to the CookieWare fund

                      1 Reply Last reply Reply Quote 0
                      • TIGT Offline
                        TIG Moderator
                        last edited by

                        Sorry for the confusion 😳 - I didn't realise there was an enclosing module / class. They need initial CAPITAL letter; whereas defs and variables need lowercase. Consonants ion caps e.g. ORIGIN...

                        TIG

                        1 Reply Last reply Reply Quote 0
                        • honoluludesktopH Offline
                          honoluludesktop
                          last edited by

                          OK I am stuck again. Problem is with the last box of code below:

                          This is the main proc, methods below are at the bottom of the code in this section:

                          
                          model = Sketchup.active_model
                          entities = model.active_entities
                          selection = model.selection
                          
                          if model.selection.empty?
                            entities = model.active_entities
                          else
                            entities = model.selection
                          end
                          
                          entities.each do |e|
                            if e.is_a? Sketchup;;ComponentInstance
                              the_name=e.definition.name
                              stuff=e.definition.entities
                              counter=0
                              faces=[]
                              stuff.each do |e|
                                if e.is_a? Sketchup;;Face
                                  counter=counter+1
                                  faces.push e
                                end ###if
                              end ###loop
                              points=[]
                              add_face_vert_to_file(faces,points)
                              make_comp_face_file(the_name,faces,counter,model,points)
                            end ###if
                          end ###loop
                          
                          

                          Method to make a collection of face.vertices

                          
                          ###make vertices file of faces in component
                          def add_face_vert_to_file(faces,points)
                            faces.each do |e|
                              points.push e.vertices
                            end ###end loop
                          end
                          
                          

                          Method to make empty text file, then (where I fail) to take the face.vertices and copy them as string to the text file.

                          
                          ###create file ComponentName.txt
                          def make_comp_face_file(the_name,faces,counter,model,points)
                            the_line=the_name+" ",counter," faces"
                            UI.messagebox(the_line)
                            model_filename = File.basename(model.path)
                            path=File.dirname(model.path)+"\\"
                            out_name=the_name+".txt"
                            out_path=path+out_name
                            $mesh_file=File.new(out_path,"w")
                          
                            #HERE is problem code. How do I take the collection
                            #of face.vertices and copy as strings to the text file.
                            points.each do |e|
                              $mesh_file.puts(e.x.to_s)
                              $mesh_file.puts(e.y.to_s)
                              $mesh_file.puts(e.z.to_s)
                            end ###loop
                          end
                          
                          

                          Am writing with the Web Console, and having some problems. Saving seems to drop characters, and the indents are gone. Any ideas?

                          1 Reply Last reply Reply Quote 0
                          • TIGT Offline
                            TIG Moderator
                            last edited by

                            
                            points.each do |e|
                                $mesh_file.puts(e.x.to_s)
                                $mesh_file.puts(e.y.to_s)
                                $mesh_file.puts(e.z.to_s)
                            end ###loop
                            
                            

                            Adds x/y/z into file on separate lines...
                            to test if it's at least getting the points values use plain puts so it appears in the console

                            
                            points.each do |e|
                                puts(e.x.to_s)
                                puts(e.y.to_s)
                                puts(e.z.to_s)
                            end ###loop
                            
                            

                            To write an xyz line use

                            
                            points.each do |e|
                                $mesh_file.puts(e.x.to_s+","+e.y.to_s+","+e.z.to_s)
                            end ###loop
                            
                            

                            Does

                            $mesh_file=File.new(out_path,"w")
                            

                            actually make the file ?
                            You need to open the file for writing AND then close it after you are done writing to it.

                            $mesh_file.close
                            

                            perhaps it's still open and so a second [separate] attempt to write to it fails...

                            TIG

                            1 Reply Last reply Reply Quote 0
                            • Chris FullmerC Offline
                              Chris Fullmer
                              last edited by

                              @thomthom said:

                              Normal convention is to type constants in all caps.

                              Oh yeah! I rarely intialize them. Thanks Thom,

                              Chris

                              Lately you've been tan, suspicious for the winter.
                              All my Plugins I've written

                              1 Reply Last reply Reply Quote 0
                              • honoluludesktopH Offline
                                honoluludesktop
                                last edited by

                                TIG, Just got up, and finished reading at your post. Thanks I think I understand, and have a lot to work with.

                                $mesh_file=File.new(out_path,"w")

                                Made a 0 byte file that I can see in "My Computer". I assumed it was open, guess it wasn't:-). Looks like a lot of stuff to work on later today. Good advice about using "puts" to check output. I use the messagebox a lot but that is slow.

                                puts(e.x.to_s) prints Sketchup::Vertex:0xea24668 ?-(, Crossed this bridge once before, but don't recall how to get output as a number.

                                1 Reply Last reply Reply Quote 0
                                • Chris FullmerC Offline
                                  Chris Fullmer
                                  last edited by

                                  puts(e.x.to_s) should return a numerical "x" position if e is a Point3d object. if e is a vertex, it should return an error. If e is a vertex, you can do e.position.x and that will return the x position of the vertex.

                                  That sounded confusing to me. A few more lines of your code and I could give a slightly more complete example.

                                  Great job so far!

                                  Chris

                                  Lately you've been tan, suspicious for the winter.
                                  All my Plugins I've written

                                  1 Reply Last reply Reply Quote 0
                                  • honoluludesktopH Offline
                                    honoluludesktop
                                    last edited by

                                    "oops: - I" πŸ™‚ A little slow this morning, didn't get it until now. Thanks guys, lets see how far I can get with what I have before I, OOPS:-(, need help getting off the floor. Might not take too long.

                                    Tig, I can now open, write to, and close files:-)

                                    Chris above here is where I stumbled on the code.

                                    It occurred to me that a "method", a "function" in other languages (I missed this one), was in my day know as a "procedure", having evolved from a "[C}all". Before this I did a Basic "sub routine", itself born out of "jump xxxx:xxxx, where xxxx:xxxx began a set of instruction that ended in "return". Before "Buddha" it was all 1111's and 0000's πŸ™‚

                                    1 Reply Last reply Reply Quote 0
                                    • honoluludesktopH Offline
                                      honoluludesktop
                                      last edited by

                                      Help! How do I get a number that repersents the location of a face vertices? The following is setup for Web Console. When I output to UI.messagebox(e.vertices), I get:

                                      #Sketchup::Vertex:0xfc83800#Sketchup::Vertex:0xfc837e8#Sketchup::Vertex:0xfc837d0

                                      The main proc is at the bottom, and the methods are above it.

                                      
                                      model = Sketchup.active_model
                                      entities = model.active_entities
                                      selection = model.selection
                                      
                                      ### Test is selection made
                                      if model.selection.empty?
                                        entities = model.active_entities
                                      else
                                        entities = model.selection
                                      end
                                      
                                      ###create file ComponentName.txt
                                      def make_comp_face_file(the_name,faces,counter,model)
                                        the_line=the_name+" ",counter," faces"
                                        UI.messagebox(the_line)
                                        model_filename = File.basename(model.path)
                                        path=File.dirname(model.path)+"\\"
                                        out_name=the_name+".txt"
                                        out_path=path+out_name
                                      end
                                      
                                      ###make vertices collection of faces in component
                                      def add_face_vertices_collect(faces,points)
                                        faces.each do |e|
                                          points.push e.outer_loop
                                        end ### loop
                                      end
                                      
                                      ###make 3dpoint from vertex HELP HERE!!!! I think
                                      def print_vertices_collect(points)
                                        points.each do |e|
                                          UI.messagebox(e.vertices)       ###puts to test will be 
                                          ###$points_file.puts(e.vertices)###put here when works
                                        end
                                      end
                                      
                                      ###Get su;;component collection
                                      entities.each do |e|
                                        if e.is_a? Sketchup;;ComponentInstance
                                          the_name=e.definition.name
                                          stuff=e.definition.entities
                                          faces=[]
                                          counter=0
                                          ###Locate faces in each component and make faces collection
                                          stuff.each do |e|
                                      	if e.is_a? Sketchup;;Face
                                      	  counter=counter+1
                                      	  faces.push e
                                      	end ###if
                                          end ###loop
                                          make_comp_face_file(the_name,faces,counter,model)####Have to
                                          points=[]
                                          add_face_vertices_collect(faces,points)          ####nest these
                                          print_vertices_collect(points)                   ####later
                                          $points_file.close
                                        end ###if
                                      end ###loop
                                      
                                      
                                      1 Reply Last reply Reply Quote 0
                                      • J Offline
                                        Jim
                                        last edited by

                                        The Vertex entity has a position.

                                        
                                        point = vertex.position
                                        
                                        

                                        The position will be relative to parent container, and not relative the SketchUp axes.

                                        Hi

                                        1 Reply Last reply Reply Quote 0
                                        • TIGT Offline
                                          TIG Moderator
                                          last edited by

                                          
                                          ### points>>>vertices
                                          vertices.each do |vertex|
                                            $points_file.puts(vertex.vertices.point.to_a)
                                            ### FILE of VERTICES POINTS AS AN ARRAY ONE PER LINE...
                                          end
                                          
                                          

                                          TIG

                                          1 Reply Last reply Reply Quote 0
                                          • honoluludesktopH Offline
                                            honoluludesktop
                                            last edited by

                                            Hi guys, Thanks for your help. I stumbled on e.vertices.x.position after starting over. Now how do I read the SU Ruby API to make this easier to understand?-(

                                            
                                            model = Sketchup.active_model
                                            entities = model.entities
                                            selection = model.selection
                                            
                                            if model.selection.empty?
                                            	entities = model.active_entities
                                            else
                                            	entities = model.selection
                                            end
                                            
                                            entities.each do |e|
                                            	if e.is_a? Sketchup;;ComponentInstance
                                            		ci_name=e.definition.name
                                            		#UI.messagebox(ci_name)
                                            		ci_collection=e.definition.entities
                                            		#UI.messagebox(ci_collection)
                                            		ci_collection.each do |e|
                                            			ci_faces_collection=[]
                                            			if e.is_a? Sketchup;;Face
                                            				ci_faces_collection.push e
                                            				ci_faces_collection.each do |e|
                                            					faces_vertices_collection=[]
                                            					if e.vertices
                                            						faces_vertices_collection.push e
                                            						puts(e.vertices.x.position)
                                            					end
                                            				end
                                            			end
                                            		end
                                            	end 
                                            end
                                            
                                            
                                            
                                            1 Reply Last reply Reply Quote 0
                                            • 1
                                            • 2
                                            • 2 / 2
                                            • First post
                                              Last post
                                            Buy SketchPlus
                                            Buy SUbD
                                            Buy WrapR
                                            Buy eBook
                                            Buy Modelur
                                            Buy Vertex Tools
                                            Buy SketchCuisine
                                            Buy FormFonts

                                            Advertisement