sketchucation logo sketchucation
    • Login
    πŸ€‘ SketchPlus 1.3 | 44 Tools for $15 until June 20th Buy Now

    Plugin select only one instance + count instances

    Scheduled Pinned Locked Moved Plugins
    5 Posts 2 Posters 455 Views 2 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.
    • S Offline
      sb1305
      last edited by

      Hi guys,

      I am new here and I was wondering if somebody could help me with my problem.
      I have used Sketchup for some years, but I have just started working with Ruby.

      So here is my problem:

      "select only one instance of each component"
      I made a big model with many different components, some of them are more than once in the model and now I want to select the components and copy them next to the model to create a kind of library of all the different components, but I only want to select one of each component and I don't want to select every single one by hand.
      Is there maybe an already existing plugin, that can select only one instance of each component? Or can anyone help me to write that in ruby?

      "text-tag: number of instances"
      And after I copied the elements I would like to put a text tag next to them saying how many instances there are in total, of course minus the copy I just created and I don't want to do that by hand as well. So I want the entity info "solid component(65 in model)" for example as a text-tag. Is there maybe an existing plugin or can anyone help me to write that in ruby?
      And it would also be great to do that by selecting all, so it will create a text tag with the number for every single element in the selection.

      I hope you can help me with that.
      Thank you very much!

      Simon

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

        To find components iterate the definitions...

        require('sketchup.rb')
        module TIG
        	def TIG.composer()
        		model=Sketchup.active_model
        		ents=model.entities
        		ds=[] # component definitions
        		model.definitions.each{|d|
        			next if d.image? || d.group?
        			next unless d.instances[0]
        			ds << d
        		}
        		return unless ds[0]
        		model.start_operation('Composer', true)
        		pt=model.bounds.max
        		pt.z=0
        		pt.offset!([120,0,0])
        		# first point to add instance 10' away adjust as desired
        		ds.each{|d|
        			n=d.name
        			c=d.instances.length
        			t=Geom;;Transformation.new(pt)
        			i=ents.add_instance(d, t)
        			pt.x=i.bounds.max.x+120 # point for next instance
        			ents.add_text("#{n}\nInstances=#{c}", i.bounds.max, [6,6,12])
        		}
        		model.commit_operation
        	end
        end
        

        Usage TIG.composer
        You can use this for the basis of many processes...

        TIG

        1 Reply Last reply Reply Quote 0
        • S Offline
          sb1305
          last edited by

          Thank you so much. That helped a lot.

          1 Reply Last reply Reply Quote 0
          • S Offline
            sb1305
            last edited by

            Hi TIG, so I have some more questions about the code.

            "select only one instance of the components in selection"
            The code runs for all the components in the model, right?
            How can I run it for only the ones I select?
            it would be good to have a code that only selects one instance of each component of my selection.

            "text-tag: number of instances"
            And the text tag which says how many instances there are, can I also use that separated from the copying, so that I can put a text-tag only on components that I select somewhere in my library or in the model?

            "order of components"
            And another thing, what is the order the components come in? I don't find that in the code, do I?

            Sorry for all the questions, I would really like to understand the code and work on it, but I have just started doing this.

            Thank you so much,

            Simon

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

              @sb1305 said:

              Hi TIG, so I have some more questions about the code.

              "select only one instance of the components in selection"
              The code runs for all the components in the model, right?
              How can I run it for only the ones I select?
              it would be good to have a code that only selects one instance of each component of my selection.

              "text-tag: number of instances"
              And the text tag which says how many instances there are, can I also use that separated from the copying, so that I can put a text-tag only on components that I select somewhere in my library or in the model?

              "order of components"
              And another thing, what is the order the components come in? I don't find that in the code, do I?

              Sorry for all the questions, I would really like to understand the code and work on it, but I have just started doing this.

              Thank you so much,

              Simon
              Replace:

              ds=[] # component definitions
                    model.definitions.each{|d|
                       next if d.image? || d.group?
                       next unless d.instances[0]
                       ds << d
                    }
              

              with something to process the selection instead - a bit more convoluted!

              ss=model.selection.grep(Sketchup;;ComponentInstance)
              ds=[]
              ss.each{|e| ds << e.definition }
              ds.uniq!
              

              Now you have a 'list' of just the definitions relating to selected component-instances [.uniq! ensures there are no repeats]... Process that 'ds' 'array' as before...

              To make a text_adder() create another method [def]... In it do something like

              pt=model.bounds.max
              pt.z=0
              pt.offset!([120,0,0])
              (model.selection.grep(Sketchup;;ComponentInstance).uniq).each{|e|
                d=e.definition
                n=d.name
                c=d.instances.length
                t=Geom;;Transformation.new(pt)
                i=ents.add_instance(d, t)
                pt.x=i.bounds.max.x+120 # point for next instance
                ents.add_text("#{n}\nInstances=#{c}", i.bounds.max, [6,6,12])
              }
              

              If you want to not count the one you have in your 'Library' then change c=d.instances.length to c=d.instances.length-1 etc...
              remember to wrap it in a namespace/module as the ' composer' example, and use model_start_op...commit so it's one-step undo-able...

              The order of the components in the earlier post comes from the order in the definitions list, which is 'chronological', so if you made 'zebra' before 'aardvark' that's the order in which they are found.
              The order in a selection is not easily possible to determine, you can try picking in the desired order [holding Ctrl to add to the selection...]...
              If you want to get the results in sorted 'name' order, then you need to add in an extra step or two...The code outlined earlier...

              ss=model.selection.grep(Sketchup;;ComponentInstance)
              ds=[]
              ss.each{|e| ds << e.definition }
              ds.uniq!
              

              needs to become something like ...

              ss=model.selection.grep(Sketchup;;ComponentInstance)
              ns=[]
              ss.each{|e| ns << e.definition.name }
              ns.uniq.sort!
              ### sorted names...
              ds=[]
              ns.each{|n| ds << model.definitions[n] }
              ### NOW process 'ds' which is a list of definitions sorted by name... 
              

              You can make a similar change to the 'whole of the definitions' version too.
              Ruby's 'sort' is 'case sensitive' - you can make it case 'insensitive' using a method [wrapped] like this

              def self.sort_by(a)
                return unless a.is_a?(Array)
                return a.sort_by{|w|[w.downcase, w]}
              end
              

              You then replace the line ns.uniq.sort!
              with this:
              ns.uniq! ns=self.sort_by(ns)
              πŸ€“

              TIG

              1 Reply Last reply Reply Quote 0
              • 1 / 1
              • First post
                Last post
              Buy SketchPlus
              Buy SUbD
              Buy WrapR
              Buy eBook
              Buy Modelur
              Buy Vertex Tools
              Buy SketchCuisine
              Buy FormFonts

              Advertisement