Apologies, I am not a programmer but wondered if someone knew a way to close the Component Option and Component Attribute windows using a ruby script. It will be added to another piece of script where the resulting function falls over with these windows open. It would prevent this happening in the case where the windows are left open accidentally.
This is not possible. But you can use the SketchUp Ruby API to open the components inspector and the preferences window (which I think you meant by āoptionsā). But they neither toggle, nor can you hide them programmatically.
This sounds rather the other piece of script tries to solve a problem the wrong (unsafe) way, or it tries to achieve something that is not possible to do.
Why not explain what you want to achieve on a higher abstract level to get several suggested solutions, than asking for implementation steps of your specific approach?
thanks for the reply. I mean the āComponent Optionā and āComponent Attributeā windows. Apologies for the confusion. Is this also the case for these windows?
In general, you cannot easily interact with or use/modify other tools/windows if they are not your own. The API is more focussed on automating geometry creation or building new tools, than a macro language for automating the user interface.
All true, ā¦ however there are some public instance methods can can be used with disclaimer.
DISCLAIMER: Use at own risk. The Dynamic Components extension is a Trimble internal extension (that is almost part of the core.) Itās internal functionality and method names could change at any time without warning. This could cause your code āin the wildā to fail, resulting in you needing to patch your code and re-release it.
module AuthorNamespace
module ThisPlugin # defined only if DC extension is pre-loaded !
extend self
DC ||= $dc_observers.get_latest_class
# Test whether the DC Component Attributes dialog is open.
def component_attributes_dialog_open?
DC.manager_dialog_is_visible()
end
# Test whether the DC Component Options dialog is open.
def component_options_dialog_open?
DC.configure_dialog_is_visible()
end
# Closes the DC Component Attributes dialog.
def close_component_attributes_dialog
DC.close_manager_dialog()
end
# Closes the DC Component Options dialog.
def close_component_options_dialog
DC.close_configure_dialog()
end
# Refreshes the DC Component Attributes dialog.
def refresh_component_attributes_dialog
DC.refresh_manager_dialog()
end
# Refreshes the DC Component Options dialog.
def refresh_component_options_dialog
DC.refresh_configure_dialog()
end
# Refreshes both dialogs, clearing the highlight if arg is true.
def refresh_dynamic_component_dialogs(clear_highlight = false)
DC.refresh_dialogs(clear_highlight)
end
# Opens the DC Component Attributes dialog.
def show_component_attributes_dialog
model = Sketchup.active_model
entity = model.selection.empty? ? model : model.selection[0]
DC.show_manager_dialog(entity)
end
# Opens the DC Component Options dialog.
def show_component_options_dialog
DC.show_configure_dialog()
end
# --------------------
# A block form method that closes the DC dialog windows,
# evaluates the given block (passing in any arguments,)
# then restores the dialogs if they were previously open.
def do_with_DC_dialogs_closed(*args)
return nil unless block_given?
atts_was_open = component_attributes_dialog_open?
opts_was_open = component_options_dialog_open?
close_component_attributes_dialog() if atts_was_open
close_component_options_dialog() if opts_was_open
#
result = yield *args # eval the block
#
show_component_attributes_dialog() if atts_was_open
show_component_options_dialog() if opts_was_open
return result
end
end if defined?($dc_observers)
end
Using local method wrappers would allow adapting the DC method calls if they change in future releases, using conditional statements that āduck-typeā the DC observer instance using #respond_to?().
Thanks DanRathbun. Iām not writing a plugin, Iām using a script that Eneroth3 posted to select all child instances. Itās a work around for an issue discussed here:
Aerillus, I agree the script is not strictly safe but it solves my problem until Trimble rectify the issue. If the component option and component attribute windows are accidentally left open it throws up an alert āMerging multiple items might be slow. Do you want to continueā. This requires each instance to be either OKād or cancelled, in the case of my drawings too many times. I tend to force quit at this point.
I was hoping to add a few lines to the script to force these windows shut if they are left open. Iām not sure if this is possible with what you have very kindly posted DanRathbun but that is the aim.
ā¦ I wasnāt entirely aware that he was using someone elseās code.
Well all of what I posted is needed. Itās not āa few linesā.
BUT ā¦ I also added near the end, a block form method that will do what you wish (provided all the dialog control methods are added.) The method name is ādo_with_DC_dialogs_closedā and youād use it to wrap calls to Enerothās code.
# within the plugin module ...
do_with_DC_dialogs_closed {
# call the code / methods to perform whilst DC dialogs are closed
}
Of course, in the example, youād either add the methods I defined into Enerothās module, or rename the two nested moduleās to something of your own unique names. Ie "AuthorNamespace" and "ThisPlugin" are just place holder names.
If adding all the wrapper methods are too confusing, you can āliftā some code from the ādo_with_DC_dialogs_closedā method, and replace calls to the āwrapperā methods with direct calls to the DC object ā¦
DC ||= $dc_observers.get_latest_class
atts_was_open = DC.manager_dialog_is_visible()
opts_was_open = DC.configure_dialog_is_visible()
DC.close_manager_dialog() if atts_was_open
DC.close_configure_dialog() if opts_was_open
#
# call Eneroth's code HERE
#
model = Sketchup.active_model
entity = model.selection.empty? ? model : model.selection[0]
DC.show_manager_dialog(entity) if atts_was_open
DC.show_configure_dialog() if opts_was_open
ā¦ but again, if these DC method names or functionality change, your āworkaroundā will break and need to be updated.
Thank you @DanRathbun and @eneroth3. This combined code worked for me. I removed the re-opening as this was causing an issue for drawings with many components. Thanks again
DC ||= $dc_observers.get_latest_class
atts_was_open = DC.manager_dialog_is_visible()
opts_was_open = DC.configure_dialog_is_visible()
DC.close_manager_dialog() if atts_was_open
DC.close_configure_dialog() if opts_was_open
def select_children(instance)
children = instance.definition.entities.select { |e| e.respond_to?(:definition) }
instance.model.selection.add(children)
children.each { |c| select_children(c) }
end
select_children(Sketchup.active_model.selection.first)
model = Sketchup.active_model
entity = model.selection.empty? ? model : model.selection[0]
Just in summary for anyone that might stumble across this. The code solves an issue where generate report does not see copied components. It allows you to select all child components within a component including copies. Selecting ācurrent selectionā in the report window will now include copied components.
This will be cleaner for you, and will not create constants nor methods globally ā¦
module SBJ
module SelectAllCopiedDynamicSubComponents
extend self
DC ||= $dc_observers.get_latest_class
@@loaded = false unless defined?(@@loaded)
def select_children(instance) # recursive method
children = instance.definition.entities.select { |e| e.respond_to?(:definition) }
instance.model.selection.add(children)
children.each { |c| select_children(c) }
end
def select_DC_children_command(instance)
return if instance.nil? # selection was empty
atts_was_open = DC.manager_dialog_is_visible()
opts_was_open = DC.configure_dialog_is_visible()
DC.close_manager_dialog() if atts_was_open
DC.close_configure_dialog() if opts_was_open
select_children(instance)
end
if not @@loaded
# Create a menu item so a shortcut keychord can be used ...
topmenu = UI.menu('Plugins')
item = topmenu.add_item("Select DC Children") {
select_DC_children_command(Sketchup.active_model.selection.first)
}
topmenu.set_validation_proc(item) {
Sketchup.active_model.selection.empty? ? MF_DISABLED : MF_ENABLED
}
@@loaded = true
end
end
end
Allows setting a shortcut keychord once the menu item is created.