diff options
Diffstat (limited to 'src/libs/client')
-rw-r--r-- | src/libs/client/ClientStore.cpp | 37 | ||||
-rw-r--r-- | src/libs/client/ClientStore.hpp | 3 | ||||
-rw-r--r-- | src/libs/client/DeprecatedLoader.cpp | 15 | ||||
-rw-r--r-- | src/libs/client/OSCClientReceiver.cpp | 40 | ||||
-rw-r--r-- | src/libs/client/OSCClientReceiver.hpp | 3 | ||||
-rw-r--r-- | src/libs/client/OSCEngineSender.cpp | 38 | ||||
-rw-r--r-- | src/libs/client/OSCEngineSender.hpp | 9 | ||||
-rw-r--r-- | src/libs/client/ObjectModel.cpp | 10 | ||||
-rw-r--r-- | src/libs/client/ObjectModel.hpp | 7 | ||||
-rw-r--r-- | src/libs/client/PatchModel.cpp | 20 | ||||
-rw-r--r-- | src/libs/client/PatchModel.hpp | 14 | ||||
-rw-r--r-- | src/libs/client/SigClientInterface.hpp | 12 | ||||
-rw-r--r-- | src/libs/client/ThreadedSigClientInterface.hpp | 15 |
13 files changed, 93 insertions, 130 deletions
diff --git a/src/libs/client/ClientStore.cpp b/src/libs/client/ClientStore.cpp index 39908eb5..1fb00eea 100644 --- a/src/libs/client/ClientStore.cpp +++ b/src/libs/client/ClientStore.cpp @@ -43,13 +43,12 @@ ClientStore::ClientStore(SharedPtr<EngineInterface> engine, SharedPtr<SigClientI emitter->signal_new_node.connect(sigc::mem_fun(this, &ClientStore::new_node_event)); emitter->signal_new_port.connect(sigc::mem_fun(this, &ClientStore::new_port_event)); emitter->signal_polyphonic.connect(sigc::mem_fun(this, &ClientStore::polyphonic_event)); - emitter->signal_patch_enabled.connect(sigc::mem_fun(this, &ClientStore::patch_enabled_event)); - emitter->signal_patch_disabled.connect(sigc::mem_fun(this, &ClientStore::patch_disabled_event)); emitter->signal_patch_polyphony.connect(sigc::mem_fun(this, &ClientStore::patch_polyphony_event)); emitter->signal_patch_cleared.connect(sigc::mem_fun(this, &ClientStore::patch_cleared_event)); emitter->signal_connection.connect(sigc::mem_fun(this, &ClientStore::connection_event)); emitter->signal_disconnection.connect(sigc::mem_fun(this, &ClientStore::disconnection_event)); emitter->signal_variable_change.connect(sigc::mem_fun(this, &ClientStore::variable_change_event)); + emitter->signal_property_change.connect(sigc::mem_fun(this, &ClientStore::property_change_event)); emitter->signal_port_value.connect(sigc::mem_fun(this, &ClientStore::port_value_event)); emitter->signal_port_activity.connect(sigc::mem_fun(this, &ClientStore::port_activity_event)); } @@ -453,24 +452,6 @@ ClientStore::polyphonic_event(const Path& path, bool polyphonic) void -ClientStore::patch_enabled_event(const Path& path) -{ - SharedPtr<PatchModel> patch = PtrCast<PatchModel>(object(path)); - if (patch) - patch->enable(); -} - - -void -ClientStore::patch_disabled_event(const Path& path) -{ - SharedPtr<PatchModel> patch = PtrCast<PatchModel>(object(path)); - if (patch) - patch->disable(); -} - - -void ClientStore::patch_polyphony_event(const Path& path, uint32_t poly) { SharedPtr<PatchModel> patch = PtrCast<PatchModel>(object(path)); @@ -522,6 +503,22 @@ ClientStore::variable_change_event(const Path& subject_path, const string& predi } } + +void +ClientStore::property_change_event(const Path& subject_path, const string& predicate, const Atom& value) +{ + SharedPtr<ObjectModel> subject = object(subject_path); + + if (!value.is_valid()) { + cerr << "ERROR: property '" << predicate << "' has no type" << endl; + } else if (subject) { + subject->set_property(predicate, value); + } else { + cerr << "WARNING: property for unknown object " << subject_path + << " lost. Client must refresh!" << endl; + } +} + void ClientStore::port_value_event(const Path& port_path, const Raul::Atom& value) diff --git a/src/libs/client/ClientStore.hpp b/src/libs/client/ClientStore.hpp index d71067d6..e1b3adaa 100644 --- a/src/libs/client/ClientStore.hpp +++ b/src/libs/client/ClientStore.hpp @@ -101,11 +101,10 @@ private: void new_node_event(const Path& path, const string& plugin_uri, bool polyphonic); void new_port_event(const Path& path, uint32_t index, const string& data_type, bool is_output); void polyphonic_event(const Path& path, bool polyphonic); - void patch_enabled_event(const Path& path); - void patch_disabled_event(const Path& path); void patch_polyphony_event(const Path& path, uint32_t poly); void patch_cleared_event(const Path& path); void variable_change_event(const Path& subject_path, const string& predicate, const Atom& value); + void property_change_event(const Path& subject_path, const string& predicate, const Atom& value); void port_value_event(const Path& port_path, const Raul::Atom& value); void port_activity_event(const Path& port_path); void connection_event(const Path& src_port_path, const Path& dst_port_path); diff --git a/src/libs/client/DeprecatedLoader.cpp b/src/libs/client/DeprecatedLoader.cpp index 42f2f5fc..3ed6bc5f 100644 --- a/src/libs/client/DeprecatedLoader.cpp +++ b/src/libs/client/DeprecatedLoader.cpp @@ -359,7 +359,7 @@ DeprecatedLoader::load_patch(const Glib::ustring& filename, // _engine->set_variable(subject, i->first, i->second); if (!existing) - _engine->enable_patch(path); + _engine->set_property(path, "ingen:enabled", (bool)true); _load_path_translations.clear(); @@ -459,23 +459,24 @@ DeprecatedLoader::load_node(const Path& parent, xmlDocPtr doc, const xmlNodePtr bool is_port = false; if (plugin_type == "Internal") { + // FIXME: indices if (plugin_label == "audio_input") { - _engine->new_port(path, "ingen:AudioPort", false); + _engine->new_port(path, 0, "ingen:AudioPort", false); is_port = true; } else if (plugin_label == "audio_output") { - _engine->new_port(path, "ingen:AudioPort", true); + _engine->new_port(path, 0, "ingen:AudioPort", true); is_port = true; } else if (plugin_label == "control_input") { - _engine->new_port(path, "ingen:ControlPort", false); + _engine->new_port(path, 0, "ingen:ControlPort", false); is_port = true; } else if (plugin_label == "control_output" ) { - _engine->new_port(path, "ingen:ControlPort", true); + _engine->new_port(path, 0, "ingen:ControlPort", true); is_port = true; } else if (plugin_label == "midi_input") { - _engine->new_port(path, "ingen:MIDIPort", false); + _engine->new_port(path, 0, "ingen:MIDIPort", false); is_port = true; } else if (plugin_label == "midi_output" ) { - _engine->new_port(path, "ingen:MIDIPort", true); + _engine->new_port(path, 0, "ingen:MIDIPort", true); is_port = true; } else { cerr << "WARNING: Unknown internal plugin label \"" << plugin_label << "\"" << endl; diff --git a/src/libs/client/OSCClientReceiver.cpp b/src/libs/client/OSCClientReceiver.cpp index 091b921b..6087736f 100644 --- a/src/libs/client/OSCClientReceiver.cpp +++ b/src/libs/client/OSCClientReceiver.cpp @@ -145,8 +145,6 @@ OSCClientReceiver::setup_callbacks() lo_server_thread_add_method(_st, "/ingen/plugin", "ssss", plugin_cb, this); lo_server_thread_add_method(_st, "/ingen/new_patch", "si", new_patch_cb, this); lo_server_thread_add_method(_st, "/ingen/destroyed", "s", destroyed_cb, this); - lo_server_thread_add_method(_st, "/ingen/patch_enabled", "s", patch_enabled_cb, this); - lo_server_thread_add_method(_st, "/ingen/patch_disabled", "s", patch_disabled_cb, this); lo_server_thread_add_method(_st, "/ingen/patch_polyphony", "si", patch_polyphony_cb, this); lo_server_thread_add_method(_st, "/ingen/patch_cleared", "s", patch_cleared_cb, this); lo_server_thread_add_method(_st, "/ingen/object_renamed", "ss", object_renamed_cb, this); @@ -158,6 +156,7 @@ OSCClientReceiver::setup_callbacks() lo_server_thread_add_method(_st, "/ingen/polyphonic", "sT", polyphonic_cb, this); lo_server_thread_add_method(_st, "/ingen/polyphonic", "sF", polyphonic_cb, this); lo_server_thread_add_method(_st, "/ingen/set_variable", NULL, set_variable_cb, this); + lo_server_thread_add_method(_st, "/ingen/set_property", NULL, set_property_cb, this); lo_server_thread_add_method(_st, "/ingen/set_port_value", "sf", set_port_value_cb, this); lo_server_thread_add_method(_st, "/ingen/set_voice_value", "sif", set_voice_value_cb, this); lo_server_thread_add_method(_st, "/ingen/port_activity", "s", port_activity_cb, this); @@ -193,22 +192,6 @@ OSCClientReceiver::_destroyed_cb(const char* path, const char* types, lo_arg** a int -OSCClientReceiver::_patch_enabled_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) -{ - patch_enabled((const char*)&argv[0]->s); - return 0; -} - - -int -OSCClientReceiver::_patch_disabled_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) -{ - patch_disabled((const char*)&argv[0]->s); - return 0; -} - - -int OSCClientReceiver::_patch_polyphony_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) { patch_polyphony((const char*)&argv[0]->s, argv[1]->i); @@ -301,7 +284,7 @@ OSCClientReceiver::_polyphonic_cb(const char* path, const char* types, lo_arg** } -/** Notification of a new or updated piece of variable. +/** Notification of a new or updated variable. */ int OSCClientReceiver::_set_variable_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) @@ -320,6 +303,25 @@ OSCClientReceiver::_set_variable_cb(const char* path, const char* types, lo_arg* } +/** Notification of a new or updated property. + */ +int +OSCClientReceiver::_set_property_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) +{ + if (argc != 3 || types[0] != 's' || types[1] != 's') + return 1; + + const char* obj_path = &argv[0]->s; + const char* key = &argv[1]->s; + + Atom value = AtomLiblo::lo_arg_to_atom(types[2], argv[2]); + + set_property(obj_path, key, value); + + return 0; +} + + int OSCClientReceiver::_set_port_value_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) { diff --git a/src/libs/client/OSCClientReceiver.hpp b/src/libs/client/OSCClientReceiver.hpp index 564e39a9..9950df7d 100644 --- a/src/libs/client/OSCClientReceiver.hpp +++ b/src/libs/client/OSCClientReceiver.hpp @@ -86,8 +86,6 @@ private: LO_HANDLER(plugin_list_end); LO_HANDLER(new_patch); LO_HANDLER(destroyed); - LO_HANDLER(patch_enabled); - LO_HANDLER(patch_disabled); LO_HANDLER(patch_polyphony); LO_HANDLER(patch_cleared); LO_HANDLER(object_renamed); @@ -97,6 +95,7 @@ private: LO_HANDLER(new_port); LO_HANDLER(polyphonic); LO_HANDLER(set_variable); + LO_HANDLER(set_property); LO_HANDLER(set_port_value); LO_HANDLER(set_voice_value); LO_HANDLER(port_activity); diff --git a/src/libs/client/OSCEngineSender.cpp b/src/libs/client/OSCEngineSender.cpp index 5f2db7ad..d235e7a9 100644 --- a/src/libs/client/OSCEngineSender.cpp +++ b/src/libs/client/OSCEngineSender.cpp @@ -140,9 +140,11 @@ OSCEngineSender::new_patch(const string& path, void OSCEngineSender::new_port(const string& path, + uint32_t index, const string& data_type, bool is_output) { + // FIXME: use index send("/ingen/new_port", "issi", next_id(), path.c_str(), @@ -264,26 +266,6 @@ OSCEngineSender::set_polyphonic(const string& path, bool poly) void -OSCEngineSender::enable_patch(const string& patch_path) -{ - send("/ingen/enable_patch", "is", - next_id(), - patch_path.c_str(), - LO_ARGS_END); -} - - -void -OSCEngineSender::disable_patch(const string& patch_path) -{ - send("/ingen/disable_patch", "is", - next_id(), - patch_path.c_str(), - LO_ARGS_END); -} - - -void OSCEngineSender::connect(const string& src_port_path, const string& dst_port_path) { @@ -415,7 +397,6 @@ OSCEngineSender::set_variable(const string& obj_path, const string& predicate, const Raul::Atom& value) { - lo_message m = lo_message_new(); lo_message_add_int32(m, next_id()); lo_message_add_string(m, obj_path.c_str()); @@ -424,6 +405,21 @@ OSCEngineSender::set_variable(const string& obj_path, send_message("/ingen/set_variable", m); } + +void +OSCEngineSender::set_property(const string& obj_path, + const string& predicate, + const Raul::Atom& value) +{ + lo_message m = lo_message_new(); + lo_message_add_int32(m, next_id()); + lo_message_add_string(m, obj_path.c_str()); + lo_message_add_string(m, predicate.c_str()); + Raul::AtomLiblo::lo_message_add_atom(m, value); + send_message("/ingen/set_property", m); +} + + // Requests // diff --git a/src/libs/client/OSCEngineSender.hpp b/src/libs/client/OSCEngineSender.hpp index d32a4849..985e1db3 100644 --- a/src/libs/client/OSCEngineSender.hpp +++ b/src/libs/client/OSCEngineSender.hpp @@ -81,6 +81,7 @@ public: uint32_t poly); void new_port(const string& path, + uint32_t index, const string& data_type, bool is_output); @@ -105,10 +106,6 @@ public: void set_polyphonic(const string& path, bool poly); - void enable_patch(const string& patch_path); - - void disable_patch(const string& patch_path); - void connect(const string& src_port_path, const string& dst_port_path); @@ -146,6 +143,10 @@ public: const string& predicate, const Raul::Atom& value); + void set_property(const string& obj_path, + const string& predicate, + const Raul::Atom& value); + // Requests // void ping(); diff --git a/src/libs/client/ObjectModel.cpp b/src/libs/client/ObjectModel.cpp index e83b9fe1..c807797e 100644 --- a/src/libs/client/ObjectModel.cpp +++ b/src/libs/client/ObjectModel.cpp @@ -56,16 +56,6 @@ ObjectModel::get_variable(const string& key) const void -ObjectModel::add_variable(const Variables& data) -{ - for (Variables::const_iterator i = data.begin(); i != data.end(); ++i) { - _variables[i->first] = i->second; - signal_variable.emit(i->first, i->second); - } -} - - -void ObjectModel::set_polyphonic(bool polyphonic) { _polyphonic = polyphonic; diff --git a/src/libs/client/ObjectModel.hpp b/src/libs/client/ObjectModel.hpp index dbd188a3..460d7d9d 100644 --- a/src/libs/client/ObjectModel.hpp +++ b/src/libs/client/ObjectModel.hpp @@ -62,8 +62,12 @@ public: const Atom& get_variable(const string& key) const; void set_variable(const string& key, const Atom& value) { _variables[key] = value; signal_variable.emit(key, value); } + + void set_property(const string& key, const Atom& value) + { _properties[key] = value; signal_property.emit(key, value); } const Variables& variables() const { return _variables; } + const Variables& properties() const { return _properties; } const Path path() const { return _path; } const Symbol symbol() const { return _path.name(); } SharedPtr<ObjectModel> parent() const { return _parent; } @@ -75,6 +79,7 @@ public: sigc::signal<void, SharedPtr<ObjectModel> > signal_new_child; sigc::signal<void, SharedPtr<ObjectModel> > signal_removed_child; sigc::signal<void, const string&, const Atom&> signal_variable; + sigc::signal<void, const string&, const Atom&> signal_property; sigc::signal<void, bool> signal_polyphonic; sigc::signal<void> signal_destroyed; sigc::signal<void> signal_renamed; @@ -89,7 +94,6 @@ protected: virtual void add_child(SharedPtr<ObjectModel> c) {} virtual bool remove_child(SharedPtr<ObjectModel> c) { return true; } - void add_variable(const Variables& data); void set_polyphonic(bool); virtual void set(SharedPtr<ObjectModel> model); @@ -99,6 +103,7 @@ protected: SharedPtr<ObjectModel> _parent; Variables _variables; + Variables _properties; }; diff --git a/src/libs/client/PatchModel.cpp b/src/libs/client/PatchModel.cpp index 20a47406..38019eda 100644 --- a/src/libs/client/PatchModel.cpp +++ b/src/libs/client/PatchModel.cpp @@ -160,23 +160,11 @@ PatchModel::remove_connection(const string& src_port_path, const string& dst_por } -void -PatchModel::enable() -{ - if (!_enabled) { - _enabled = true; - signal_enabled.emit(); - } -} - - -void -PatchModel::disable() +bool +PatchModel::enabled() const { - if (_enabled) { - _enabled = false; - signal_disabled.emit(); - } + Variables::const_iterator i = _properties.find("ingen:enabled"); + return (i != _properties.end() && i->second.type() == Atom::BOOL && i->second.get_bool()); } diff --git a/src/libs/client/PatchModel.hpp b/src/libs/client/PatchModel.hpp index 62b9db44..e39ee2f7 100644 --- a/src/libs/client/PatchModel.hpp +++ b/src/libs/client/PatchModel.hpp @@ -48,10 +48,10 @@ public: SharedPtr<ConnectionModel> get_connection(const string& src_port_path, const string& dst_port_path) const; - size_t poly() const { return _poly; } - bool enabled() const { return _enabled; } - uint32_t internal_polyphony() const { return _poly; } - bool polyphonic() const; + size_t poly() const { return _poly; } + uint32_t internal_polyphony() const { return _poly; } + bool enabled() const; + bool polyphonic() const; /** "editable" = arranging,connecting,adding,deleting,etc * not editable (control mode) you can just change controllers (performing) @@ -71,8 +71,6 @@ public: sigc::signal<void, SharedPtr<NodeModel> > signal_removed_node; sigc::signal<void, SharedPtr<ConnectionModel> > signal_new_connection; sigc::signal<void, SharedPtr<ConnectionModel> > signal_removed_connection; - sigc::signal<void> signal_enabled; - sigc::signal<void> signal_disabled; sigc::signal<void, uint32_t> signal_polyphony; sigc::signal<void, bool> signal_editable; @@ -81,15 +79,12 @@ private: PatchModel(const Path& patch_path, size_t internal_poly) : NodeModel("ingen:Patch", patch_path, false) // FIXME - , _enabled(false) , _poly(internal_poly) , _editable(true) { } void poly(size_t p) { _poly = p; signal_polyphony.emit(p); } - void enable(); - void disable(); void clear(); void add_child(SharedPtr<ObjectModel> c); bool remove_child(SharedPtr<ObjectModel> c); @@ -98,7 +93,6 @@ private: void remove_connection(const string& src_port_path, const string& dst_port_path); Connections _connections; - bool _enabled; uint32_t _poly; bool _editable; }; diff --git a/src/libs/client/SigClientInterface.hpp b/src/libs/client/SigClientInterface.hpp index 6463bf3a..6318f440 100644 --- a/src/libs/client/SigClientInterface.hpp +++ b/src/libs/client/SigClientInterface.hpp @@ -57,8 +57,6 @@ public: sigc::signal<void, string, string, bool> signal_new_node; sigc::signal<void, string, uint32_t, string, bool> signal_new_port; sigc::signal<void, string, bool> signal_polyphonic; - sigc::signal<void, string> signal_patch_enabled; - sigc::signal<void, string> signal_patch_disabled; sigc::signal<void, string, uint32_t> signal_patch_polyphony; sigc::signal<void, string> signal_patch_cleared; sigc::signal<void, string, string> signal_object_renamed; @@ -66,6 +64,7 @@ public: sigc::signal<void, string, string> signal_connection; sigc::signal<void, string, string> signal_disconnection; sigc::signal<void, string, string, Raul::Atom> signal_variable_change; + sigc::signal<void, string, string, Raul::Atom> signal_property_change; sigc::signal<void, string, Raul::Atom> signal_port_value; sigc::signal<void, string, uint32_t, Raul::Atom> signal_voice_value; sigc::signal<void, string> signal_port_activity; @@ -125,12 +124,6 @@ protected: void object_destroyed(const string& path) { if (_enabled) signal_object_destroyed.emit(path); } - void patch_enabled(const string& path) - { if (_enabled) signal_patch_enabled.emit(path); } - - void patch_disabled(const string& path) - { if (_enabled) signal_patch_disabled.emit(path); } - void patch_polyphony(const string& path, uint32_t poly) { if (_enabled) signal_patch_polyphony.emit(path, poly); } @@ -145,6 +138,9 @@ protected: void set_variable(const string& path, const string& key, const Raul::Atom& value) { if (_enabled) signal_variable_change.emit(path, key, value); } + + void set_property(const string& path, const string& key, const Raul::Atom& value) + { if (_enabled) signal_property_change.emit(path, key, value); } void set_port_value(const string& port_path, const Raul::Atom& value) { if (_enabled) signal_port_value.emit(port_path, value); } diff --git a/src/libs/client/ThreadedSigClientInterface.hpp b/src/libs/client/ThreadedSigClientInterface.hpp index ccdbf318..291df426 100644 --- a/src/libs/client/ThreadedSigClientInterface.hpp +++ b/src/libs/client/ThreadedSigClientInterface.hpp @@ -56,14 +56,13 @@ public: , new_port_slot(signal_new_port.make_slot()) , polyphonic_slot(signal_polyphonic.make_slot()) , connection_slot(signal_connection.make_slot()) - , patch_enabled_slot(signal_patch_enabled.make_slot()) - , patch_disabled_slot(signal_patch_disabled.make_slot()) , patch_polyphony_slot(signal_patch_polyphony.make_slot()) , patch_cleared_slot(signal_patch_cleared.make_slot()) , object_destroyed_slot(signal_object_destroyed.make_slot()) , object_renamed_slot(signal_object_renamed.make_slot()) , disconnection_slot(signal_disconnection.make_slot()) , variable_change_slot(signal_variable_change.make_slot()) + , property_change_slot(signal_property_change.make_slot()) , port_value_slot(signal_port_value.make_slot()) , port_activity_slot(signal_port_activity.make_slot()) , program_add_slot(signal_program_add.make_slot()) @@ -115,12 +114,6 @@ public: void object_destroyed(const string& path) { push_sig(sigc::bind(object_destroyed_slot, path)); } - void patch_enabled(const string& path) - { push_sig(sigc::bind(patch_enabled_slot, path)); } - - void patch_disabled(const string& path) - { push_sig(sigc::bind(patch_disabled_slot, path)); } - void patch_polyphony(const string& path, uint32_t poly) { push_sig(sigc::bind(patch_polyphony_slot, path, poly)); } @@ -135,6 +128,9 @@ public: void set_variable(const string& path, const string& key, const Raul::Atom& value) { push_sig(sigc::bind(variable_change_slot, path, key, value)); } + + void set_property(const string& path, const string& key, const Raul::Atom& value) + { push_sig(sigc::bind(property_change_slot, path, key, value)); } void set_port_value(const string& port_path, const Raul::Atom& value) { push_sig(sigc::bind(port_value_slot, port_path, value)); } @@ -172,14 +168,13 @@ private: sigc::slot<void, string, uint32_t, string, bool> new_port_slot; sigc::slot<void, string, bool> polyphonic_slot; sigc::slot<void, string, string> connection_slot; - sigc::slot<void, string> patch_enabled_slot; - sigc::slot<void, string> patch_disabled_slot; sigc::slot<void, string, uint32_t> patch_polyphony_slot; sigc::slot<void, string> patch_cleared_slot; sigc::slot<void, string> object_destroyed_slot; sigc::slot<void, string, string> object_renamed_slot; sigc::slot<void, string, string> disconnection_slot; sigc::slot<void, string, string, Raul::Atom> variable_change_slot; + sigc::slot<void, string, string, Raul::Atom> property_change_slot; sigc::slot<void, string, Raul::Atom> port_value_slot; sigc::slot<void, string, uint32_t, Raul::Atom> voice_value_slot; sigc::slot<void, string> port_activity_slot; |