Compare commits

...

21 Commits

Author SHA1 Message Date
Oğuzhan Koral 966f7aaed5 Fix (Collection): fix blender receive 2023-05-29 18:12:02 +03:00
oguzhankoral 51b59fa995 Fix typo on including string 2023-05-29 18:09:48 +03:00
oguzhankoral 0b713736bd Include also detached @elements props to displayValue 2023-05-29 18:06:05 +03:00
oguzhankoral 9e33581c66 Accept also detached @displayValue props 2023-05-29 18:05:29 +03:00
oguzhankoral b97792b596 Check only collection is model or not 2023-05-29 18:04:56 +03:00
Matteo Cominetti c0746f8eff Merge pull request #270 from specklesystems/oguzhan/hash-only-hostname-of-server-url 2023-05-25 18:17:37 +01:00
oguzhankoral a826a9d692 Hash hostname of the serverUrl 2023-05-25 20:09:32 +03:00
Oğuzhan Koral 6d04203d37 Feat (Collections): Eliminate relations for layer info 2023-05-24 15:57:47 +03:00
oguzhankoral 33b2ed8a94 Fix performance penalty 2023-05-24 14:38:27 +03:00
oguzhankoral 4f16da7ad0 Do not extract relations if from revit 2023-05-24 01:16:51 +03:00
oguzhankoral 36f92c7655 Add network object support 2023-05-24 01:00:06 +03:00
oguzhankoral 1d4f5a759e Eliminate relations for model collections 2023-05-23 23:31:02 +03:00
oguzhankoral 28af9bc811 Enable rescue block for to_native 2023-05-23 12:07:48 +03:00
oguzhankoral cf04cd4094 Check view up and direction parallel or not 2023-05-23 11:50:08 +03:00
oguzhankoral 23e9efb28a Pass layer prop through to_native methods 2023-05-23 11:49:51 +03:00
Oğuzhan Koral 57322df29c Fix (Layer): Do not send line_style if none 2023-05-22 13:57:23 +03:00
oguzhankoral fff82d34c6 Do not send line_style if none 2023-05-22 13:56:10 +03:00
Oğuzhan Koral 7211860c21 Chore (Layer): Support line styles for layers 2023-05-22 11:46:52 +03:00
oguzhankoral 9fc69044f8 Support line styles for layers 2023-05-22 11:42:51 +03:00
Oğuzhan Koral 76467c3e81 Fix (Blocks): Eliminate nil block geometries 2023-05-19 19:36:28 +03:00
oguzhankoral 4cfc04e2f3 Eliminate nil block geometries 2023-05-19 19:13:15 +03:00
25 changed files with 293 additions and 76 deletions
@@ -11,6 +11,7 @@ module SpeckleConnector
# @param state [States::State] the current state of the {App::SpeckleConnectorApp}
# @return [States::State] the new updated state object
# rubocop:disable Metrics/AbcSize
# rubocop:disable Metrics/MethodLength
# rubocop:disable Metrics/PerceivedComplexity
# rubocop:disable Metrics/CyclomaticComplexity
def self.update_state(state, data)
@@ -25,7 +26,7 @@ module SpeckleConnector
flat_entities = SketchupModel::Query::Entity.flat_entities(sketchup_model.entities)
comp_flat_entities = flat_entities.grep(Sketchup::ComponentInstance) + flat_entities.grep(Sketchup::Group) +
flat_entities.grep(Sketchup::ComponentDefinition)
flat_entities.grep(Sketchup::ComponentDefinition)
face_edge_flat_entities = flat_entities.grep(Sketchup::Face) + flat_entities.grep(Sketchup::Edge)
# Collect entity ids to clear mappings
@@ -55,6 +56,7 @@ module SpeckleConnector
Events::SelectionEventAction.update_state(state, { clear: true })
end
# rubocop:enable Metrics/AbcSize
# rubocop:enable Metrics/MethodLength
# rubocop:enable Metrics/PerceivedComplexity
# rubocop:enable Metrics/CyclomaticComplexity
end
@@ -6,6 +6,7 @@ module SpeckleConnector
OBJECTS_GIS_POLYGONELEMENT = 'Objects.GIS.PolygonElement'
OBJECTS_BUILTELEMENTS_VIEW3D = 'Objects.BuiltElements.View:Objects.BuiltElements.View3D'
OBJECTS_BUILTELEMENTS_NETWORK = 'Objects.BuiltElements.Network'
OBJECTS_BUILTELEMENTS_REVIT_DIRECTSHAPE = 'Objects.BuiltElements.Revit.DirectShape'
OBJECTS_BUILTELEMENTS_REVIT_LEVEL = 'Objects.BuiltElements.Level:Objects.BuiltElements.Revit.RevitLevel'
@@ -20,4 +21,7 @@ module SpeckleConnector
OBJECTS_OTHER_REVIT_REVITINSTANCE = 'Objects.Other.Revit.RevitInstance'
OBJECTS_OTHER_BLOCKDEFINITION = 'Objects.Other.BlockDefinition'
OBJECTS_OTHER_RENDERMATERIAL = 'Objects.Other.RenderMaterial'
OBJECTS_OTHER_DISPLAYSTYLE = 'Objects.Other.DisplayStyle'
SPECKLE_CORE_MODELS_COLLECTION = 'Speckle.Core.Models.Collection'
end
+27 -14
View File
@@ -13,6 +13,8 @@ require_relative '../speckle_objects/geometry/point'
require_relative '../speckle_objects/geometry/line'
require_relative '../speckle_objects/geometry/mesh'
require_relative '../speckle_objects/built_elements/view3d'
require_relative '../speckle_objects/built_elements/network'
require_relative '../speckle_objects/speckle/core/models/collection'
require_relative '../sketchup_model/dictionary/speckle_entity_dictionary_handler'
module SpeckleConnector
@@ -51,6 +53,7 @@ module SpeckleConnector
DISPLAY_VALUE = OTHER::DisplayValue
VIEW3D = BUILTELEMENTS::View3d
POLYGON_ELEMENT = GIS::PolygonElement
COLLECTION = SpeckleObjects::Speckle::Core::Models::Collection
BASE_OBJECT_PROPS = %w[applicationId id speckle_type totalChildrenCount].freeze
CONVERTABLE_SPECKLE_TYPES = %w[
@@ -64,7 +67,9 @@ module SpeckleConnector
Objects.Other.RenderMaterial
Objects.Other.Instance:Objects.Other.BlockInstance
Objects.BuiltElements.View:Objects.BuiltElements.View3D
Objects.BuiltElements.Network
Objects.GIS.PolygonElement
Speckle.Core.Models.Collection
].freeze
def from_revit
@@ -86,10 +91,13 @@ module SpeckleConnector
def receive_commit_object(obj)
# First create layers on the sketchup before starting traversing
# @Named Views are exception here. It does not mean a layer. But it is anti-pattern for now.
layers_relation = obj['layers_relation']
# layers_relation = obj['layers_relation']
# Create layers and it's folders from layers relation on the model collection.
SpeckleObjects::Relations::Layers.to_native(layers_relation, sketchup_model) if layers_relation && !from_revit
unless from_revit
layers_relation = SpeckleObjects::Relations::Layers.extract_relations(obj)
# Create layers and it's folders from layers relation on the model collection.
SpeckleObjects::Relations::Layers.to_native(layers_relation, sketchup_model) if layers_relation
end
# By default entities to fill is sketchup model's entities.
@entities_to_fill = sketchup_model.entities
@@ -100,7 +108,9 @@ module SpeckleConnector
@entities_to_fill = @branch_definition.entities
end
traverse_commit_object(obj, @entities_to_fill)
default_commit_layer = sketchup_model.layers.layers.find { |layer| layer.display_name == '@Untagged' }
traverse_commit_object(obj, default_commit_layer, @entities_to_fill)
create_levels_from_section_planes
check_hiding_layers_needed
try_create_instance
@@ -230,9 +240,9 @@ module SpeckleConnector
# self-caller method means that call itself according to conditions inside of it.
# rubocop:disable Metrics/CyclomaticComplexity
# rubocop:disable Metrics/PerceivedComplexity
def traverse_commit_object(obj, entities)
def traverse_commit_object(obj, layer, entities)
if convertible_to_native?(obj)
@state = convert_to_native(@state, obj, entities)
@state = convert_to_native(@state, obj, layer, entities)
elsif obj.is_a?(Hash) && obj.key?('speckle_type')
return if ignored_speckle_type?(obj)
@@ -240,23 +250,23 @@ module SpeckleConnector
# puts(">>> Found #{obj['speckle_type']}: #{obj['id']}. Continuing traversal.")
props = obj.keys.filter_map { |key| key unless key.start_with?('_') }
props.each do |prop|
traverse_commit_object(obj[prop], entities)
traverse_commit_object(obj[prop], layer, entities)
end
else
# puts(">>> Found #{obj['speckle_type']}: #{obj['id']} with displayValue.")
@state = convert_to_native(@state, obj, entities)
@state = convert_to_native(@state, obj, layer, entities)
end
elsif obj.is_a?(Hash)
obj.each_value { |value| traverse_commit_object(value, entities) }
obj.each_value { |value| traverse_commit_object(value, layer, entities) }
elsif obj.is_a?(Array)
obj.each { |value| traverse_commit_object(value, entities) }
obj.each { |value| traverse_commit_object(value, layer, entities) }
end
end
# rubocop:enable Metrics/CyclomaticComplexity
# rubocop:enable Metrics/PerceivedComplexity
def speckle_object_to_native(obj)
return DISPLAY_VALUE.method(:to_native) unless obj['displayValue'].nil?
return DISPLAY_VALUE.method(:to_native) unless obj['displayValue'].nil? && obj['@displayValue'].nil?
SPECKLE_OBJECT_TO_NATIVE[obj['speckle_type']]
end
@@ -272,18 +282,21 @@ module SpeckleConnector
OBJECTS_OTHER_REVIT_REVITINSTANCE => REVIT_INSTANCE.method(:to_native),
OBJECTS_OTHER_RENDERMATERIAL => RENDER_MATERIAL.method(:to_native),
OBJECTS_BUILTELEMENTS_VIEW3D => VIEW3D.method(:to_native),
OBJECTS_GIS_POLYGONELEMENT => POLYGON_ELEMENT.method(:to_native)
OBJECTS_BUILTELEMENTS_REVIT_DIRECTSHAPE => BUILTELEMENTS::Revit::DirectShape.method(:to_native),
OBJECTS_BUILTELEMENTS_NETWORK => BUILTELEMENTS::Network.method(:to_native),
OBJECTS_GIS_POLYGONELEMENT => POLYGON_ELEMENT.method(:to_native),
SPECKLE_CORE_MODELS_COLLECTION => COLLECTION.method(:to_native)
}.freeze
# @param state [States::State] state of the speckle application
def convert_to_native(state, obj, entities = sketchup_model.entities)
def convert_to_native(state, obj, layer, entities = sketchup_model.entities)
# store this method as parameter to re-call it inner callstack
convert_to_native = method(:convert_to_native)
# Get 'to_native' method to convert upcoming speckle object to native sketchup entity
to_native_method = speckle_object_to_native(obj)
# Call 'to_native' method by passing this method itself to handle nested 'to_native' conversions.
# It returns updated state and converted entities.
state, converted_entities = to_native_method.call(state, obj, entities, &convert_to_native)
state, converted_entities = to_native_method.call(state, obj, layer, entities, &convert_to_native)
if from_revit
# Create levels as section planes if they exists
create_levels(state, obj)
@@ -33,8 +33,6 @@ module SpeckleConnector
new_speckle_state, model_collection = MODEL_COLLECTION.from_sketchup_model(sketchup_model, speckle_state,
@units, preferences, &convert)
# send only layers that have any object
model_collection[:layers_relation] = SpeckleObjects::Relations::Layers.from_model(sketchup_model)
return new_speckle_state, model_collection
end
@@ -0,0 +1,23 @@
# frozen_string_literal: true
require_relative '../base'
require_relative '../../constants/type_constants'
module SpeckleConnector
module SpeckleObjects
module BuiltElements
# Network object represents scenes on Sketchup.
class Network < Base
SPECKLE_TYPE = OBJECTS_BUILTELEMENTS_NETWORK
def self.to_native(state, network, layer, entities, &convert_to_native)
network['elements'].each do |element|
state = convert_to_native.call(state, element['elements'], layer, entities)
end
return state, []
end
end
end
end
end
@@ -2,9 +2,13 @@
require_relative '../../base'
require_relative '../../other/render_material'
require_relative '../../other/block_instance'
require_relative '../../other/block_definition'
require_relative '../../other/transform'
require_relative '../../../constants/type_constants'
require_relative '../../../sketchup_model/query/entity'
require_relative '../../../sketchup_model/reader/speckle_entities_reader'
require_relative '../../../sketchup_model/dictionary/speckle_schema_dictionary_handler'
module SpeckleConnector
module SpeckleObjects
@@ -30,6 +34,41 @@ module SpeckleConnector
self[:baseGeometries] = base_geometries
end
def self.get_direct_shape_name(direct_shape)
if direct_shape['name'] == ''
direct_shape['applicationId'].to_s
else
"#{direct_shape['name']}::#{direct_shape['applicationId']}"
end
end
# @param state [States::State] state of the application.
def self.to_native(state, direct_shape, layer, entities, &convert_to_native)
direct_shape['geometry'] = direct_shape['baseGeometries']
direct_shape['name'] = get_direct_shape_name(direct_shape)
state, _definitions = Other::BlockDefinition.to_native(
state, direct_shape, layer, entities, &convert_to_native
)
definition = state.sketchup_state.sketchup_model
.definitions[Other::BlockDefinition.get_definition_name(direct_shape)]
instance = entities.add_instance(definition, Geom::Transformation.new)
instance.name = direct_shape['name'] unless direct_shape['name'].nil?
DICTIONARY::SpeckleSchemaDictionaryHandler.set_hash(
instance,
{
name: direct_shape['name'], category: direct_shape['category'], method: 'Direct Shape'
}
)
new_speckle_state = state.speckle_state.with_mapped_entity(instance)
state = state.with_speckle_state(new_speckle_state)
instance.layer = layer unless layer.nil?
return state, [instance, definition]
end
# Collects direct shapes on selection as flat list.
def self.direct_shapes_on_selection(sketchup_model)
flat_selection_with_path = QUERY::Entity.flat_entities_with_path(
@@ -60,7 +60,7 @@ module SpeckleConnector
target = get_camera_target(cam, units)
direction = get_camera_direction(cam, units)
update_properties = get_scene_update_properties(page)
rendering_options = SpeckleObjects::Others::RenderingOptions.to_speckle(page.rendering_options)
rendering_options = SpeckleObjects::Other::RenderingOptions.to_speckle(page.rendering_options)
View3d.new(
page.name, origin, target, direction, SpeckleObjects::Geometry::Vector.new(0, 0, 1, units),
cam.perspective?, cam.fov, units, page.name, update_properties, rendering_options
@@ -71,7 +71,8 @@ module SpeckleConnector
# @param obj [Hash] commit object.
# rubocop:disable Metrics/AbcSize
# rubocop:disable Metrics/CyclomaticComplexity
def self.to_native(state, view, _entities, &_convert_to_native)
# rubocop:disable Metrics/PerceivedComplexity
def self.to_native(state, view, _layer, _entities, &_convert_to_native)
sketchup_model = state.sketchup_state.sketchup_model
return state, [] unless view['speckle_type'] == 'Objects.BuiltElements.View:Objects.BuiltElements.View3D'
@@ -84,8 +85,10 @@ module SpeckleConnector
lens = view['lens'] || 50
origin = SpeckleObjects::Geometry::Point.to_native(origin['x'], origin['y'], origin['z'], origin['units'])
target = SpeckleObjects::Geometry::Point.to_native(target['x'], target['y'], target['z'], target['units'])
view_direction = (origin - target).normalize
up = view_direction.parallel?([0, 0, 1]) ? [0, 1, 0] : [0, 0, 1]
# Set camera position before creating scene on it.
my_camera = Sketchup::Camera.new(origin, target, [0, 0, 1], !view['isOrthogonal'], lens)
my_camera = Sketchup::Camera.new(origin, target, up, !view['isOrthogonal'], lens)
sketchup_model.active_view.camera = my_camera
sketchup_model.pages.add(name)
page = sketchup_model.pages[name]
@@ -93,9 +96,10 @@ module SpeckleConnector
set_rendering_options(page.rendering_options, view['rendering_options']) if view['rendering_options']
return state, [page]
end
# rubocop:enable Metrics/AbcSize
# rubocop:enable Metrics/CyclomaticComplexity
# rubocop:enable Metrics/PerceivedComplexity
# @param page [Sketchup::Page] scene to update -update properties-
def self.set_page_update_properties(page, update_properties)
update_properties.each do |prop, value|
@@ -109,7 +113,7 @@ module SpeckleConnector
next if rendering_options[prop].nil?
rendering_options[prop] = if value.is_a?(Hash)
SpeckleObjects::Others::Color.to_native(value)
SpeckleObjects::Other::Color.to_native(value)
else
value
end
@@ -67,7 +67,7 @@ module SpeckleConnector
# rubocop:disable Metrics/AbcSize
# rubocop:disable Metrics/PerceivedComplexity
# rubocop:disable Metrics/CyclomaticComplexity
def self.to_native(state, line, entities, &_convert_to_native)
def self.to_native(state, line, layer, entities, &_convert_to_native)
if line.key?('value')
values = line['value']
points = values.each_slice(3).to_a.map { |pt| Point.to_native(pt[0], pt[1], pt[2], line['units']) }
@@ -81,7 +81,7 @@ module SpeckleConnector
line_layer_name = SketchupModel::Query::Layer.entity_layer_from_path(line['layer'])
line_layer = state.sketchup_state.sketchup_model.layers.to_a.find { |l| l.display_name == line_layer_name }
edges.each do |edge|
edge.layer = line_layer unless line_layer.nil?
edge.layer = line_layer.nil? ? layer : line_layer
unless line['sketchup_attributes'].nil?
SketchupModel::Dictionary::BaseDictionaryHandler
.attribute_dictionaries_to_native(edge, line['sketchup_attributes']['dictionaries'])
@@ -80,7 +80,7 @@ module SpeckleConnector
# rubocop:disable Metrics/AbcSize
# rubocop:disable Metrics/CyclomaticComplexity
# rubocop:disable Metrics/PerceivedComplexity:
def self.to_native(state, mesh, entities, &convert_to_native)
def self.to_native(state, mesh, layer, entities, &convert_to_native)
model_preferences = state.user_state.preferences[:model]
# Get soft? flag of {Sketchup::Edge} object to understand smoothness of edge.
is_soften = get_soften_setting(mesh, entities)
@@ -105,7 +105,7 @@ module SpeckleConnector
native_mesh.add_polygon(polygon_points)
end
end
state, _materials = Other::RenderMaterial.to_native(state, mesh['renderMaterial'],
state, _materials = Other::RenderMaterial.to_native(state, mesh['renderMaterial'], layer,
entities, &convert_to_native)
# Find and assign material if exist
unless mesh['renderMaterial'].nil?
@@ -157,9 +157,7 @@ module SpeckleConnector
speckle_mesh = Mesh.new(
units: units,
render_material: material.nil? ? nil : Other::RenderMaterial.from_material(material),
vertices: [],
faces: [],
sketchup_attributes: att,
vertices: [], faces: [], sketchup_attributes: att,
layer: SketchupModel::Query::Layer.entity_path(face),
speckle_schema: speckle_schema,
application_id: face.persistent_id
@@ -30,16 +30,13 @@ module SpeckleConnector
end
# Handles polygon element differently from display value.
def self.to_native(state, obj, entities, &convert_to_native)
def self.to_native(state, obj, layer, entities, &convert_to_native)
attributes = get_qgis_attributes(obj)
obj = collect_definition_geometries(obj)
obj['name'] = get_definition_name(obj, attributes)
state, _definitions = Other::BlockDefinition.to_native(
state,
obj,
entities,
&convert_to_native
state, obj, layer, entities, &convert_to_native
)
definition = state.sketchup_state.sketchup_model
@@ -75,7 +75,7 @@ module SpeckleConnector
block_definition = BlockDefinition.new(
units: units,
name: definition.name,
geometry: geometry,
geometry: geometry.compact,
always_face_camera: definition.behavior.always_face_camera?,
sketchup_attributes: att,
speckle_schema: speckle_schema,
@@ -98,7 +98,7 @@ module SpeckleConnector
# rubocop:disable Metrics/PerceivedComplexity
# rubocop:disable Metrics/MethodLength
# rubocop:disable Metrics/AbcSize
def self.to_native(state, definition_obj, _entities, &convert_to_native)
def self.to_native(state, definition_obj, layer, _entities, &convert_to_native)
sketchup_model = state.sketchup_state.sketchup_model
# FIXME: Check later this is a valid check or not. Maybe unnecessary? If necessary document it!
@@ -124,11 +124,11 @@ module SpeckleConnector
if geometry.is_a?(Array)
geometry.each do |obj|
state = convert_to_native.call(state, obj, definition.entities)
state = convert_to_native.call(state, obj, layer, definition.entities)
end
end
if geometry.is_a?(Hash) && !definition_obj['speckle_type'].nil?
state = convert_to_native.call(state, geometry, definition.entities)
state = convert_to_native.call(state, geometry, layer, definition.entities)
end
# puts("definition finished: #{name} (#{application_id})")
# puts(" entity count: #{definition.entities.count}")
@@ -112,7 +112,7 @@ module SpeckleConnector
# @param block [Object] block object that represents Speckle block.
# @param layer [Sketchup::Layer] layer to add {Sketchup::Edge} into it.
# @param entities [Sketchup::Entities] entities collection to add {Sketchup::Edge} into it.
def self.to_native(state, block, entities, &convert_to_native)
def self.to_native(state, block, layer, entities, &convert_to_native)
# is_group = block.key?("is_sketchup_group") && block["is_sketchup_group"]
# something about this conversion is freaking out if nested block geo is a group
# so this is set to false always until I can figure this out
@@ -124,6 +124,7 @@ module SpeckleConnector
state, _definitions = BlockDefinition.to_native(
state,
block_definition,
layer,
entities,
&convert_to_native
)
@@ -133,7 +134,7 @@ module SpeckleConnector
block_layer_name = SketchupModel::Query::Layer.entity_layer_from_path(block['layer'])
block_layer = state.sketchup_state.sketchup_model.layers.to_a.find { |l| l.display_name == block_layer_name }
return add_instance_from_definition(state, block, block_layer, entities, definition, is_group,
return add_instance_from_definition(state, block, block_layer, layer, entities, definition, is_group,
&convert_to_native)
end
@@ -169,18 +170,19 @@ module SpeckleConnector
# rubocop:disable Metrics/CyclomaticComplexity
# rubocop:disable Metrics/PerceivedComplexity
# rubocop:disable Metrics/ParameterLists
def self.add_instance_from_definition(state, block, layer, entities, definition, is_group, &convert_to_native)
def self.add_instance_from_definition(state, block, block_layer, layer, entities, definition, is_group,
&convert_to_native)
t_arr = get_transform_matrix(block)
transform = Other::Transform.to_native(t_arr, block['units'])
instance = if is_group
# rubocop:disable SketchupSuggestions/AddGroup
group = entities.add_group(definition.entities.to_a)
group.layer = layer unless layer.nil?
group.layer = block_layer.nil? ? layer : block_layer
group
# rubocop:enable SketchupSuggestions/AddGroup
else
instance = entities.add_instance(definition, transform)
instance.layer = layer unless layer.nil?
instance.layer = block_layer.nil? ? layer : block_layer
instance
end
@@ -190,7 +192,7 @@ module SpeckleConnector
puts("Failed to create instance for speckle block instance #{block['id']}") if instance.nil?
# Transform already applied to instance unless is group
instance.transformation = transform if is_group
state, _materials = Other::RenderMaterial.to_native(state, block['renderMaterial'],
state, _materials = Other::RenderMaterial.to_native(state, block['renderMaterial'], layer,
entities, &convert_to_native)
# Retrieve material from state
@@ -2,7 +2,7 @@
module SpeckleConnector
module SpeckleObjects
module Others
module Other
# Color object transformations between sketchup and speckle.
class Color
# @param color [Sketchup::Color] color to convert speckle object
@@ -16,9 +16,24 @@ module SpeckleConnector
end
def self.to_native(speckle_color)
return from_int(speckle_color) if speckle_color.is_a?(Numeric)
Sketchup::Color.new(speckle_color['red'], speckle_color['green'],
speckle_color['blue'], speckle_color['alpha'])
end
# @param color [Sketchup::Color] color to convert speckle object
# @return [Numeric] int value of the color
def self.to_int(color)
rgba = color.to_a
[rgba[3] << 24 | rgba[0] << 16 | rgba[1] << 8 | rgba[2]].pack('l').unpack1('l').to_i
end
# @param argb [Numeric] int value of the corresponding color
# @return [Sketchup::Color] sketchup color
def self.from_int(argb)
Sketchup::Color.new((argb >> 16) & 255, (argb >> 8) & 255, argb & 255, (argb >> 24) & 255)
end
end
end
end
@@ -0,0 +1,36 @@
# frozen_string_literal: true
require_relative 'color'
require_relative '../base'
require_relative '../../constants/type_constants'
module SpeckleConnector
module SpeckleObjects
module Other
# DisplayStyle object for layer.
class DisplayStyle < Base
def initialize(name:, color:, line_type:)
super(
speckle_type: OBJECTS_OTHER_DISPLAYSTYLE,
total_children_count: 0,
application_id: nil,
id: nil
)
self[:name] = name
self[:color] = color
self[:linetype] = line_type unless line_type.nil?
end
# @param layer [Sketchup::Layer] layer to get display style.
def self.from_layer(layer)
DisplayStyle.new(
name: '',
color: Color.to_int(layer.color),
line_type: layer.line_style.nil? ? nil : layer.line_style.name
)
end
end
end
end
end
@@ -43,7 +43,7 @@ module SpeckleConnector
# Creates a component definition and instance from a speckle object with a display value
# @param state [States::State] state of the application.
def self.to_native(state, obj, entities, &convert_to_native)
def self.to_native(state, obj, layer, entities, &convert_to_native)
# Switch displayValue with geometry
obj = collect_definition_geometries(obj)
obj['name'] = get_definition_name(obj)
@@ -51,6 +51,7 @@ module SpeckleConnector
state, _definitions = BlockDefinition.to_native(
state,
obj,
layer,
entities,
&convert_to_native
)
@@ -59,19 +60,22 @@ module SpeckleConnector
BlockInstance.find_and_erase_existing_instance(definition, obj['id'], obj['applicationId'])
t_arr = obj['transform']
transform = t_arr.nil? ? Geom::Transformation.new : OTHER::Transform.to_native(t_arr, obj['units'])
transform = t_arr.nil? ? Geom::Transformation.new : Other::Transform.to_native(t_arr, obj['units'])
instance = entities.add_instance(definition, transform)
instance.name = obj['name'] unless obj['name'].nil?
instance.layer = layer unless layer.nil?
# Align instance axes that created from display value. (without any transform)
# BlockInstance.align_instance_axes(instance)
return state, [instance, definition]
end
def self.collect_definition_geometries(obj)
obj['geometry'] = obj['displayValue']
obj['geometry'] = obj['displayValue'] || obj['@displayValue']
if !obj['elements'].nil? && obj['elements'].is_a?(Array)
obj['elements'].each do |element|
elements = obj['elements'] || obj['@elements']
if !elements.nil? && elements.is_a?(Array)
elements.each do |element|
# Mullions is a special case here, they are extracted as base object with @displayValue from revit..
if element['@displayValue'].nil?
obj['geometry'].append(element)
@@ -1,5 +1,6 @@
# frozen_string_literal: true
require_relative 'color'
require_relative '../base'
module SpeckleConnector
@@ -38,10 +39,9 @@ module SpeckleConnector
# @param material [Sketchup::Material] material on the Sketchup.
def self.from_material(material)
rgba = material.color.to_a
RenderMaterial.new(
name: material.name,
diffuse: [rgba[3] << 24 | rgba[0] << 16 | rgba[1] << 8 | rgba[2]].pack('l').unpack1('l'),
diffuse: Other::Color.to_int(material.color),
opacity: material.alpha,
emissive: -16_777_216,
metalness: 0,
@@ -50,7 +50,7 @@ module SpeckleConnector
end
# @param state [States::State] state of the application.
def self.to_native(state, render_material, _entities, &_convert_to_native)
def self.to_native(state, render_material, _layer, _entities, &_convert_to_native)
return state, [] if render_material.nil?
sketchup_model = state.sketchup_state.sketchup_model
@@ -65,7 +65,7 @@ module SpeckleConnector
material = sketchup_model.materials.add(name)
material.alpha = render_material['opacity']
argb = render_material['diffuse']
material.color = Sketchup::Color.new((argb >> 16) & 255, (argb >> 8) & 255, argb & 255, (argb >> 24) & 255)
material.color = Color.from_int(argb)
new_sketchup_state = state.sketchup_state.with_materials(materials.add_material(name, material))
return state.with_sketchup_state(new_sketchup_state), [material]
end
@@ -4,7 +4,7 @@ require_relative 'color'
module SpeckleConnector
module SpeckleObjects
module Others
module Other
# Rendering options for scenes.
class RenderingOptions
# @param options [Sketchup::RenderingOptions] rendering options to convert speckle object
@@ -11,7 +11,8 @@ module SpeckleConnector
SPECKLE_TYPE = 'Speckle.Core.Models.Collection'
# rubocop:disable Metrics/ParameterLists
def initialize(name:, visible:, is_folder:, color: nil, layers_and_folders: [], application_id: nil)
def initialize(name:, visible:, is_folder:, line_style: nil, color: nil, layers_and_folders: [],
application_id: nil)
super(
speckle_type: SPECKLE_TYPE,
total_children_count: 0,
@@ -22,6 +23,7 @@ module SpeckleConnector
self[:color] = color
self[:visible] = visible
self[:is_folder] = is_folder
self[:line_style] = line_style unless line_style.nil?
self[:collectionType] = 'layer'
self[:elements] = layers_and_folders if layers_and_folders.any?
end
@@ -29,25 +31,30 @@ module SpeckleConnector
# @param speckle_layer [Object] speckle layer object.
# @param folder [Sketchup::Layers, Sketchup::LayerFolder] folder to create layers in it.
# @param sketchup_model [Sketchup::Model] sketchup active model.
def self.to_native_layer(speckle_layer, folder, sketchup_model)
layer = sketchup_model.layers.add_layer(speckle_layer['name'])
layer.visible = speckle_layer['visible'] unless speckle_layer['visible'].nil?
layer.color = SpeckleObjects::Others::Color.to_native(speckle_layer['color']) if speckle_layer['color']
layer = sketchup_model.layers.add_layer(speckle_layer[:name])
layer.visible = speckle_layer[:visible] unless speckle_layer[:visible].nil?
layer.color = SpeckleObjects::Other::Color.to_native(speckle_layer[:color]) if speckle_layer[:color]
if speckle_layer[:line_style]
line_style = sketchup_model.line_styles.find { |ls| ls.name == speckle_layer[:line_style] }
layer.line_style = line_style unless line_style.nil?
end
folder.add_layer(layer) if folder.is_a?(Sketchup::LayerFolder)
end
def self.to_native_layer_folder(speckle_layer_folder, folder, sketchup_model)
speckle_layers = speckle_layer_folder['elements'].select { |layer_or_fol| layer_or_fol['elements'].nil? }
speckle_layers = speckle_layer_folder[:elements].select { |layer_or_fol| layer_or_fol[:elements].nil? }
speckle_layers.each do |speckle_layer|
to_native_layer(speckle_layer, folder, sketchup_model)
end
speckle_folders = speckle_layer_folder['elements'].reject { |layer_or_fol| layer_or_fol['elements'].nil? }
speckle_folders = speckle_layer_folder[:elements].reject { |layer_or_fol| layer_or_fol[:elements].nil? }
speckle_folders.each do |speckle_folder|
sub_folder = folder.add_folder(speckle_folder['name'])
sub_folder.visible = speckle_folder['visible'] unless speckle_folder['visible'].nil?
sub_folder = folder.add_folder(speckle_folder[:name])
sub_folder.visible = speckle_folder[:visible] unless speckle_folder[:visible].nil?
to_native_layer_folder(speckle_folder, sub_folder, sketchup_model)
end
end
@@ -71,7 +78,8 @@ module SpeckleConnector
name: layer.display_name,
visible: layer.visible?,
is_folder: false,
color: SpeckleObjects::Others::Color.to_speckle(layer.color),
line_style: layer.line_style.nil? ? nil : layer.line_style.name,
color: SpeckleObjects::Other::Color.to_speckle(layer.color),
application_id: layer.persistent_id
)
end
@@ -22,6 +22,33 @@ module SpeckleConnector
self[:elements] = layers
end
def self.element_to_relation(elements)
elements.collect do |element|
next unless element['speckle_type'] == SPECKLE_CORE_MODELS_COLLECTION
is_folder = element['elements'].any? { |e| e['speckle_type'] == SPECKLE_CORE_MODELS_COLLECTION }
color = element['color'] || element['displayStyle']['color'] unless element['displayStyle'].nil?
Layer.new(
name: element['name'],
visible: element['visible'],
is_folder: is_folder,
color: color,
layers_and_folders: element_to_relation(element['elements'])
)
end.compact
end
def self.extract_relations(commit_obj)
return nil unless commit_obj['speckle_type'] == SPECKLE_CORE_MODELS_COLLECTION
elements = element_to_relation(commit_obj['elements'])
Layers.new(
active: commit_obj['active_layer'],
layers: elements
)
end
def self.to_native(layers_relation, sketchup_model)
folder = sketchup_model.layers
@@ -19,11 +19,11 @@ module SpeckleConnector
return "#{family}-#{type}-#{category}-#{def_obj['elementId']}"
end
def self.to_native(state, definition, entities, &convert_to_native)
def self.to_native(state, definition, layer, entities, &convert_to_native)
definition_name = get_definition_name(definition)
definition['name'] = definition_name
definition['displayValue'] += definition['elements'] unless definition['elements'].nil?
SpeckleObjects::Other::BlockDefinition.to_native(state, definition, entities, &convert_to_native)
SpeckleObjects::Other::BlockDefinition.to_native(state, definition, layer, entities, &convert_to_native)
end
end
end
@@ -16,12 +16,13 @@ module SpeckleConnector
# @param block [Object] block object that represents Speckle block.
# @param layer [Sketchup::Layer] layer to add {Sketchup::Edge} into it.
# @param entities [Sketchup::Entities] entities collection to add {Sketchup::Edge} into it.
def self.to_native(state, block, entities, &convert_to_native)
def self.to_native(state, block, layer, entities, &convert_to_native)
block_definition = block['definition']
state, _definitions = RevitDefinition.to_native(
state,
block_definition,
layer,
entities,
&convert_to_native
)
@@ -29,10 +30,11 @@ module SpeckleConnector
definition = state.sketchup_state.sketchup_model
.definitions[RevitDefinition.get_definition_name(block_definition)]
layer = state.sketchup_state.sketchup_model.layers.to_a.find { |l| l.display_name == block['category'] }
block_layer = state.sketchup_state.sketchup_model.layers.to_a
.find { |l| l.display_name == block['category'] }
return SpeckleObjects::Other::BlockInstance.add_instance_from_definition(
state, block, layer, entities, definition, false, &convert_to_native
state, block, block_layer, layer, entities, definition, false, &convert_to_native
)
end
end
@@ -1,6 +1,7 @@
# frozen_string_literal: true
require_relative '../../../base'
require_relative '../../../../constants/type_constants'
module SpeckleConnector
module SpeckleObjects
@@ -9,15 +10,13 @@ module SpeckleConnector
module Models
# Collection object that collect other speckle objects under it's elements.
class Collection < Base
SPECKLE_TYPE = 'Speckle.Core.Models.Collection'
# @param name [String] name of the collection.
# @param collection_type [String] type of the collection like, layers, categories etc..
# @param elements [Array<Object>] elements of the collection.
# @param application_id [String, nil] id of the collection on the model.
def initialize(name:, collection_type:, elements: [], application_id: nil)
super(
speckle_type: SPECKLE_TYPE,
speckle_type: SPECKLE_CORE_MODELS_COLLECTION,
total_children_count: 0,
application_id: application_id,
id: nil
@@ -26,6 +25,16 @@ module SpeckleConnector
self[:collectionType] = collection_type
self[:elements] = elements
end
def self.to_native(state, collection, layer, entities, &convert_to_native)
collection_type = collection['collectionType']
if collection_type.include?('model')
ModelCollection.to_native(state, collection, layer, entities, &convert_to_native)
else
LayerCollection.to_native(state, collection, layer, entities, &convert_to_native)
end
end
end
end
end
@@ -3,6 +3,7 @@
require_relative 'collection'
require_relative '../../../../sketchup_model/query/layer'
require_relative '../../../other/color'
require_relative '../../../other/display_style'
module SpeckleConnector
module SpeckleObjects
@@ -13,7 +14,8 @@ module SpeckleConnector
class LayerCollection < Collection
SPECKLE_TYPE = 'Speckle.Core.Models.Collection'
# rubocop:disable Metrics/ParameterLists
def initialize(name:, visible:, is_folder:, color: nil, elements: [], application_id: nil)
def initialize(name:, visible:, is_folder:, display_style: nil, color: nil, elements: [],
application_id: nil)
super(
name: name,
collection_type: 'layer',
@@ -23,6 +25,7 @@ module SpeckleConnector
self[:visible] = visible
self[:is_folder] = is_folder
self[:color] = color unless color.nil?
self[:displayStyle] = display_style unless display_style.nil?
end
# rubocop:enable Metrics/ParameterLists
@@ -57,7 +60,7 @@ module SpeckleConnector
name: layer.display_name,
visible: layer.visible?,
is_folder: false,
color: SpeckleObjects::Others::Color.to_speckle(layer.color),
display_style: Other::DisplayStyle.from_layer(layer),
application_id: layer.persistent_id
)
end
@@ -76,7 +79,7 @@ module SpeckleConnector
el[:name] == folder.display_name
end
if collection_candidate.nil?
color = folder.respond_to?(:color) ? SpeckleObjects::Others::Color.to_speckle(folder.color) : nil
color = folder.respond_to?(:color) ? SpeckleObjects::Other::Color.to_speckle(folder.color) : nil
collection_candidate = LayerCollection.new(
name: folder.display_name, visible: folder.visible?,
is_folder: folder.is_a?(Sketchup::LayerFolder), color: color
@@ -90,6 +93,23 @@ module SpeckleConnector
collection
end
# rubocop:enable Metrics/CyclomaticComplexity
# @param state [States::State] state of the Speckle application.
def self.to_native(state, layer_collection, layer_or_folder, entities, &convert_to_native)
sketchup_model = state.sketchup_state.sketchup_model
elements = layer_collection['elements']
name = layer_collection['name']
layer = sketchup_model.layers.find { |l| l.display_name == name }
layer_or_folder = layer if layer
elements.each do |element|
new_state = convert_to_native.call(state, element, layer_or_folder, entities)
state = new_state
end
return state, []
end
end
end
end
@@ -61,6 +61,20 @@ module SpeckleConnector
[direct_shape, [entity]]
end
end
def self.to_native(state, model_collection, layer, entities, &convert_to_native)
elements = model_collection['elements']
elements.each do |element|
new_state = convert_to_native.call(state, element, layer, entities)
state = new_state
end
active_layer = model_collection['active_layer']
state.sketchup_state.sketchup_model.active_layer = active_layer unless active_layer.nil?
return state, []
end
end
end
end
+3 -1
View File
@@ -26,9 +26,11 @@ const SpeckleMetrics = {
.digest('hex')
.toUpperCase()
let serverUrl = new URL(localStorage.getItem('serverUrl'))
let serverId = crypto
.createHash('md5')
.update(localStorage.getItem('serverUrl').toLowerCase())
.update(serverUrl.hostname.toLowerCase())
.digest('hex')
.toUpperCase()