Add dimensions in sketchup using ruby

Hi All,

Please help me for add dimensions for each definition on sketchup.

This is my input:

Output:

Anyone please help me for add dimensions for each panels.

Thanks,
Siva S

  1. You need to be more specific about what you need help with. We are glad to answer specific coding questions, but will not just code up an entire solution for you.

  2. Start learning Ruby coding by doing simple tasks first, and slowly learn more difficult tasks a bit at a time.

  3. Whenever you have questions about a specific model, post that model in the forum along with the question. (There is no way, in this universe, anyone can help you in this case without the model.)

  4. A general pointer in the correct direction is, … you must name your model group or component objects in order for code to “find” them in the model’s entities collection, in order to do operations on these objects. (Such as paint them with a material, or attach dimensions to them.)

1 Like

It’d be cool if there was a plugin where you could select groups/components from a list, then it’d generate a list with their x y z dimensions. It wouldn’t add dimensions, but you’d still get their dimensions. I have a feeling there’re already plugins that do that though…

You mean like the CutList extension from the Extension Warehouse? It’ll do what you suggest for a selection or for the whole model.

1 Like

Most CAD systems show the overall X Y and Z dimensions of selected components in the equivalent of the SketchUp “entity” dialog and allow you to change them directly,
This is only one of a dozen extremely useful basic and standard CAD functions inexplicably missing from SketchUp.
That’s why I developed the extension “2DXY SlickMoves”. One of its functions is “resize” which shows the x y and z dimensions of one or more selected components and/or groups. (If more than one, the range of each dimension is shown.) Then you can optionally resize all selected object’s x, y and/or z values by entering absolute values, increments (+or-) or factors (*or/)

Here is link to demo video. 2DXY SlickMoves Demonstration - YouTube

It seems like most of the replies, except @DanRathbun’s, missed your original question, which was how to do this using Ruby - and even he didn’t really steer you very much. You need to look at the method Entities#add_dimension_linear. In it, you specify two end points (best as start and end of the edge you want to dimension) and an offset from that edge where you want the dimension placed. But as Dan wrote, you will get much better help if you give an example of an attempt at code and ask where you are going wrong than if you seemingly ask for someone to write it for you.

Having done similar things before, I can tell you that when you place more than a very small number of dimensions, the offsets come to be the crucial aspect. Such annotations must be placed carefully or they can overlap each other or obscure (or be obscured by) other model contents. There’s an element of art in placing them so that they look good and are easy to read.

2 Likes

Amen! To be blunt, if a poster puts in not much effort at all, (not even a forum search,) then they should expect the same return.

Okay,

model = Sketchup.active_model
entities = model.entities
entities.each { |entity|
	defn = entity.definition
  if entity.class == Sketchup::ComponentInstance
  	bbox = defn.bounds
  elsif entity.class == Sketchup::Group
  	bbox = entity.local_bounds
  end
  name = entity.definition.name
  w = bbox.width.to_l.to_s
  h = bbox.height.to_l.to_s
  d = bbox.depth.to_l.to_s
  puts name + " " + w + " " + h + " " + d  
}

Now, I got width, height and depth for each components. Can you please help me for get minimum and maximum origin’s.

Some tidbits …


This is the model’s top level collection of entities …
entities = model.entities

This is what entities context the user is within …
entities = model.active_entities


This is calling 2 methods, the .class() method, and then the .==() method …

if entity.class == Sketchup::ComponentInstance

This calls 1 method …

if entity.is_a?(Sketchup::ComponentInstance)


These both get the instance object’s definition’s untransformed bounding box …

bbox = defn.bounds
… and …
bbox = group.local_bounds

What you really want is the definition bounds, BUT scaled to match each instance’s scaling property from their individual transformation, but unrotated. So you’ll need to apply some math as @Aerilius spoke of in this other topic thread. And you’ll need to extract the scaling from a Geom::Transformation object. (We’ve covered this many times here in the forums. See next post …)


This gets the definition name, which is just going to be the same for all objects …
name = entity.definition.name

Group and Component Instances ALSO has a individual instance name attribute …
name = entity.name


w = bbox.width.to_l

Calling #to_l is unneeded because Geom::BoundingBox#width and #height and #depth all return Length class objects.

Calling Length#to_s on the result is also unneeded if you use String interpolation.

Ie, this statement is using String concatenation, and is inefficient as it creates 9 string objects …

puts name + " " + w + " " + h + " " + d

(You have the 3 literal String objects, and then each call to String#+() creates another new String object.)

This is better …

puts "#{name} : #{w} x #{h} x #{d}"

… or to format the lengths to 3 decimal places …

puts format( "%s : %.3d x %.3d x %.3d", name, w, h, d )

* NOTE: All internal lengths in SketchUp are in inches.

Here are a few past topics where you’ll find more information …

The origin of a group or instance, is a property of it’s transformation …


To determine a min or max, firstly collect objects into an array of hashes with the object’s reference as the key and origin as the value …

ori_ary = entities.grep(Sketchup::ComponentInstance).map do |inst|
  { :obj => inst, :origin => inst.transformation.origin }
end

The origin returned will be a Geom::Point3d object.


secondly the Enumerable module is mixed into most Ruby collections, … so use it’s #min and #max methods.

Something similar to …

min = ori_ary.min {|a,b|
  a[:origin].distance(ORIGIN) <=> b[:origin].distance(ORIGIN) 
}

Above, we use the Geom::Point3d#distance() method, and the global ORIGIN point3d object as it’s argument, for comparison within the #min and #max blocks.


ADD: I don’t know why I’m thinking you need to build a hash. You can just do this …

closest = entities.grep(Sketchup::ComponentInstance).min do |a,b|
  a.transformation.origin.distance(ORIGIN) <=> b.transformation.origin.distance(ORIGIN) 
end

… and …

furthest = entities.grep(Sketchup::ComponentInstance).max do |a,b|
  a.transformation.origin.distance(ORIGIN) <=> b.transformation.origin.distance(ORIGIN) 
end

you can use a plugin called auto magic dimension for the extension store