ketcher-react 3.9.0-rc.1 → 3.9.0-rc.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cjs/index.js CHANGED
@@ -44,7 +44,6 @@ var _ = require('lodash');
44
44
  var _taggedTemplateLiteral = require('@babel/runtime/helpers/taggedTemplateLiteral');
45
45
  var styled = require('@emotion/styled');
46
46
  var react = require('@emotion/react');
47
- var KN = require('w3c-keyname');
48
47
  var require$$0$3 = require('util');
49
48
  var ReactDOM = require('react-dom');
50
49
  var reactRedux = require('react-redux');
@@ -122,7 +121,6 @@ var _toConsumableArray__default = /*#__PURE__*/_interopDefaultLegacy(_toConsumab
122
121
  var ___default = /*#__PURE__*/_interopDefaultLegacy(_);
123
122
  var _taggedTemplateLiteral__default = /*#__PURE__*/_interopDefaultLegacy(_taggedTemplateLiteral);
124
123
  var styled__default = /*#__PURE__*/_interopDefaultLegacy(styled);
125
- var KN__namespace = /*#__PURE__*/_interopNamespace(KN);
126
124
  var require$$0__default = /*#__PURE__*/_interopDefaultLegacy(require$$0$3);
127
125
  var ReactDOM__default = /*#__PURE__*/_interopDefaultLegacy(ReactDOM);
128
126
  var CFB__namespace = /*#__PURE__*/_interopNamespace(CFB);
@@ -2854,7 +2852,7 @@ var toolActions = (_toolActions = {
2854
2852
  }
2855
2853
  },
2856
2854
  'charge-plus': {
2857
- shortcut: '+',
2855
+ shortcut: ['Equal', 'Shift+Equal', 'NumpadAdd'],
2858
2856
  title: 'Charge Plus',
2859
2857
  action: {
2860
2858
  tool: 'charge',
@@ -2865,7 +2863,7 @@ var toolActions = (_toolActions = {
2865
2863
  }
2866
2864
  },
2867
2865
  'charge-minus': {
2868
- shortcut: '-',
2866
+ shortcut: ['Minus', 'NumpadSubtract'],
2869
2867
  title: 'Charge Minus',
2870
2868
  action: {
2871
2869
  tool: 'charge',
@@ -3902,7 +3900,7 @@ var zoom = {
3902
3900
  }
3903
3901
  },
3904
3902
  'zoom-out': {
3905
- shortcut: ['Ctrl+_', 'Ctrl+-'],
3903
+ shortcut: ['Mod+Minus', 'Mod+NumpadSubtract'],
3906
3904
  title: 'Zoom Out',
3907
3905
  enabledInViewOnly: true,
3908
3906
  disabled: function disabled(editor) {
@@ -3924,7 +3922,7 @@ var zoom = {
3924
3922
  }
3925
3923
  },
3926
3924
  'zoom-in': {
3927
- shortcut: ['Ctrl+=', 'Ctrl++'],
3925
+ shortcut: ['Mod+Equal', 'Mod+NumpadAdd'],
3928
3926
  title: 'Zoom In',
3929
3927
  enabledInViewOnly: true,
3930
3928
  disabled: function disabled(editor) {
@@ -3955,7 +3953,7 @@ var zoom = {
3955
3953
 
3956
3954
  var openHelpLink = function openHelpLink() {
3957
3955
  var _window$open;
3958
- return (_window$open = window.open("https://github.com/epam/ketcher/blob/".concat("v3.9.0-rc.1\n", "/documentation/help.md#ketcher-overview"))) === null || _window$open === void 0 ? void 0 : _window$open.focus();
3956
+ return (_window$open = window.open("https://github.com/epam/ketcher/blob/".concat("v3.9.0-rc.2\n", "/documentation/help.md#ketcher-overview"))) === null || _window$open === void 0 ? void 0 : _window$open.focus();
3959
3957
  };
3960
3958
  var help = {
3961
3959
  help: {
@@ -8916,7 +8914,7 @@ var Dialog = function Dialog(props) {
8916
8914
  }
8917
8915
  };
8918
8916
  var keyDown = function keyDown(event) {
8919
- var key = KN__namespace.keyName(event);
8917
+ var key = event.key;
8920
8918
  var active = document.activeElement;
8921
8919
  var activeTextarea = active && active.tagName === 'TEXTAREA';
8922
8920
  if (key === 'Escape' || key === 'Enter' && !activeTextarea) {
@@ -20416,8 +20414,8 @@ function keyHandle(dispatch, getState, hotKeys, event) {
20416
20414
  var hoveredItem = getHoveredItem(render.ctab);
20417
20415
  if (key && key.length === 1 && !hoveredItem) {
20418
20416
  var currentlyPressedKeys = selectAbbreviationLookupValue(state);
20419
- var isShortcutKey = shortcutKeys.includes(key === null || key === void 0 ? void 0 : key.toLowerCase());
20420
- var isTheSameKey = key === currentlyPressedKeys;
20417
+ var isShortcutKey = shortcutKeys.includes(key.toLowerCase());
20418
+ var isTheSameKey = key.toLowerCase() === currentlyPressedKeys;
20421
20419
  var isAbbreviationLookupShown = (!isTheSameKey || !isShortcutKey) && currentlyPressedKeys;
20422
20420
  if (isAbbreviationLookupShown) {
20423
20421
  dispatch(showAbbreviationLookup(event.key));
@@ -20435,7 +20433,7 @@ function keyHandle(dispatch, getState, hotKeys, event) {
20435
20433
  dispatch(initAbbreviationLookup(event.key));
20436
20434
  }
20437
20435
  }
20438
- if (key && key.length === 1 && key.match('/')) {
20436
+ if (key === 'Slash') {
20439
20437
  var hotkeyDialogTypes = {
20440
20438
  atoms: configWithNonViewOnlyActionsDisabled['atom-props'].action,
20441
20439
  bonds: configWithNonViewOnlyActionsDisabled['bond-props'].action
@@ -25641,11 +25639,35 @@ var Editor$3 = function () {
25641
25639
  }
25642
25640
  return false;
25643
25641
  }
25642
+ }, {
25643
+ key: "isMinimalViableStructure",
25644
+ value: function isMinimalViableStructure() {
25645
+ var _this = this;
25646
+ var nonLeavingAtoms = this.struct().atoms.filter(function (atomId) {
25647
+ assert_1(_this.monomerCreationState);
25648
+ return Array.from(_this.monomerCreationState.assignedAttachmentPoints.values()).every(function (atomPair) {
25649
+ return atomPair[1] !== atomId;
25650
+ });
25651
+ });
25652
+ if (nonLeavingAtoms.size < 2) {
25653
+ return false;
25654
+ }
25655
+ var nonLeavingAtomBonds = this.struct().bonds.filter(function (_, bond) {
25656
+ return nonLeavingAtoms.has(bond.begin) && nonLeavingAtoms.has(bond.end);
25657
+ });
25658
+ if (nonLeavingAtomBonds.size < 1) {
25659
+ return false;
25660
+ }
25661
+ var simpleSingleBonds = nonLeavingAtomBonds.filter(function (_, bond) {
25662
+ return bond.type === ketcherCore.Bond.PATTERN.TYPE.SINGLE && bond.stereo === ketcherCore.Bond.PATTERN.STEREO.NONE;
25663
+ });
25664
+ return simpleSingleBonds.size >= 1;
25665
+ }
25644
25666
  }, {
25645
25667
  key: "openMonomerCreationWizard",
25646
25668
  value: function openMonomerCreationWizard() {
25647
25669
  var _selection$atoms2,
25648
- _this = this;
25670
+ _this2 = this;
25649
25671
  var currentStruct = this.render.ctab.molecule;
25650
25672
  var selection = this.selection();
25651
25673
  assert_1(selection);
@@ -25657,7 +25679,7 @@ var Editor$3 = function () {
25657
25679
  return a - b;
25658
25680
  }).forEach(function (atomId, i) {
25659
25681
  originalToSelectedAtomsIdMap.set(atomId, i);
25660
- _this.selectedToOriginalAtomsIdMap.set(i, atomId);
25682
+ _this2.selectedToOriginalAtomsIdMap.set(i, atomId);
25661
25683
  });
25662
25684
  var assignedAttachmentPoints = new Map();
25663
25685
  var sideTerminalSGroupAtoms = this.terminalRGroupAtoms.filter(function (_ref) {
@@ -25726,10 +25748,10 @@ var Editor$3 = function () {
25726
25748
  pp: leavingAtom.pp
25727
25749
  });
25728
25750
  var selectedStructLeavingAtomId = selectedStruct.atoms.add(selectedStructLeavingAtom);
25729
- _this.selectedToOriginalAtomsIdMap.set(selectedStructLeavingAtomId, atomId);
25751
+ _this2.selectedToOriginalAtomsIdMap.set(selectedStructLeavingAtomId, atomId);
25730
25752
  var selectedStructAttachmentAtomId = originalToSelectedAtomsIdMap.get(attachmentAtomId);
25731
25753
  assert_1(selectedStructAttachmentAtomId !== undefined);
25732
- _this.selectedToOriginalAtomsIdMap.set(selectedStructAttachmentAtomId, attachmentAtomId);
25754
+ _this2.selectedToOriginalAtomsIdMap.set(selectedStructAttachmentAtomId, attachmentAtomId);
25733
25755
  var newBond = new ketcherCore.Bond({
25734
25756
  type: ketcherCore.Bond.PATTERN.TYPE.SINGLE,
25735
25757
  begin: selectedStructAttachmentAtomId,
@@ -25823,7 +25845,7 @@ var Editor$3 = function () {
25823
25845
  }, {
25824
25846
  key: "assignConnectionPointAtom",
25825
25847
  value: function assignConnectionPointAtom(atomId) {
25826
- var _this2 = this;
25848
+ var _this3 = this;
25827
25849
  assert_1(this.monomerCreationState);
25828
25850
  var potentialLeavingAtoms = this.monomerCreationState.potentialAttachmentPoints.get(atomId);
25829
25851
  var leavingAtomId;
@@ -25832,7 +25854,7 @@ var Editor$3 = function () {
25832
25854
  return a - b;
25833
25855
  }).reduce(function (acc, currentAtomId) {
25834
25856
  var _Elements$get;
25835
- var atom = _this2.struct().atoms.get(currentAtomId);
25857
+ var atom = _this3.struct().atoms.get(currentAtomId);
25836
25858
  assert_1(atom);
25837
25859
  var atomicNumber = (_Elements$get = ketcherCore.Elements.get(atom.label)) === null || _Elements$get === void 0 ? void 0 : _Elements$get.number;
25838
25860
  if (atomicNumber !== undefined) {
@@ -25888,14 +25910,16 @@ var Editor$3 = function () {
25888
25910
  assert_1(_.isNumber(originalLeavingAtomId));
25889
25911
  var originalLeavingAtom = this.originalStruct.atoms.get(originalLeavingAtomId);
25890
25912
  assert_1(originalLeavingAtom);
25891
- originalLeavingAtom.rglabel = null;
25892
- originalLeavingAtom.label = leavingAtom.label;
25893
- this.originalStruct.calcImplicitHydrogen(originalLeavingAtomId);
25913
+ if (originalLeavingAtom.rglabel !== null) {
25914
+ originalLeavingAtom.rglabel = null;
25915
+ originalLeavingAtom.label = leavingAtom.label;
25916
+ this.originalStruct.calcImplicitHydrogen(originalLeavingAtomId);
25917
+ }
25894
25918
  }
25895
25919
  }, {
25896
25920
  key: "saveNewMonomer",
25897
25921
  value: function saveNewMonomer(data) {
25898
- var _this3 = this,
25922
+ var _this4 = this,
25899
25923
  _this$originalSelecti;
25900
25924
  if (!this.monomerCreationState) {
25901
25925
  throw new Error('Monomer creation wizard is not active, cannot save new monomer');
@@ -25952,25 +25976,25 @@ var Editor$3 = function () {
25952
25976
  this.monomerCreationState.assignedAttachmentPoints.forEach(function (_ref11) {
25953
25977
  var _ref12 = _slicedToArray__default["default"](_ref11, 2),
25954
25978
  leavingAtomId = _ref12[1];
25955
- return _this3.cleanupAttachmentPoint(leavingAtomId);
25979
+ return _this4.cleanupAttachmentPoint(leavingAtomId);
25956
25980
  });
25957
25981
  this.monomerCreationState.potentialAttachmentPoints.forEach(function (leavingAtomIds) {
25958
25982
  return Array.from(leavingAtomIds.values()).forEach(function (leavingAtomId) {
25959
- return _this3.cleanupAttachmentPoint(leavingAtomId);
25983
+ return _this4.cleanupAttachmentPoint(leavingAtomId);
25960
25984
  });
25961
25985
  });
25962
25986
  this.closeMonomerCreationWizard();
25963
25987
  (_this$originalSelecti = this.originalSelection.atoms) === null || _this$originalSelecti === void 0 || _this$originalSelecti.forEach(function (atomId) {
25964
- var atom = _this3.render.ctab.molecule.atoms.get(atomId);
25988
+ var atom = _this4.render.ctab.molecule.atoms.get(atomId);
25965
25989
  if (atom) {
25966
25990
  atom.fragment = -1;
25967
25991
  }
25968
25992
  });
25969
25993
  var sGroupAttachmentPoints = ketcherCore.MacromoleculesConverter.convertMonomerAttachmentPointsToSGroupAttachmentPoints(monomer, this.selectedToOriginalAtomsIdMap);
25970
25994
  sGroupAttachmentPoints.forEach(function (ap) {
25971
- _this3.render.ctab.molecule.bonds.forEach(function (bond) {
25972
- var _this3$originalSelect, _this3$originalSelect2;
25973
- if ((bond.begin === ap.atomId || bond.end === ap.atomId) && (!((_this3$originalSelect = _this3.originalSelection.atoms) !== null && _this3$originalSelect !== void 0 && _this3$originalSelect.includes(bond.begin)) || !((_this3$originalSelect2 = _this3.originalSelection.atoms) !== null && _this3$originalSelect2 !== void 0 && _this3$originalSelect2.includes(bond.end)))) {
25995
+ _this4.render.ctab.molecule.bonds.forEach(function (bond) {
25996
+ var _this4$originalSelect, _this4$originalSelect2;
25997
+ if ((bond.begin === ap.atomId || bond.end === ap.atomId) && (!((_this4$originalSelect = _this4.originalSelection.atoms) !== null && _this4$originalSelect !== void 0 && _this4$originalSelect.includes(bond.begin)) || !((_this4$originalSelect2 = _this4.originalSelection.atoms) !== null && _this4$originalSelect2 !== void 0 && _this4$originalSelect2.includes(bond.end)))) {
25974
25998
  bond.beginSuperatomAttachmentPointNumber = ap.attachmentPointNumber;
25975
25999
  }
25976
26000
  });
@@ -26039,6 +26063,7 @@ var Editor$3 = function () {
26039
26063
  }, {
26040
26064
  key: "removeAttachmentPoint",
26041
26065
  value: function removeAttachmentPoint(name) {
26066
+ var _this5 = this;
26042
26067
  assert_1(this.monomerCreationState);
26043
26068
  var atomPair = this.monomerCreationState.assignedAttachmentPoints.get(name);
26044
26069
  assert_1(atomPair);
@@ -26055,8 +26080,18 @@ var Editor$3 = function () {
26055
26080
  var action = ketcherCore.fromOneBondDeletion(this.render.ctab, preservedBondId).mergeWith(ketcherCore.fromOneAtomDeletion(this.render.ctab, preservedLeavingAtomId));
26056
26081
  this.update(action, true);
26057
26082
  }
26083
+ this.preservedConnectionPointData["delete"](attachmentAtomId);
26084
+ } else {
26085
+ var leavingAtoms = this.findPotentialLeavingAtoms(attachmentAtomId);
26086
+ var leavingAtomIdsSet = new Set();
26087
+ leavingAtoms.forEach(function (atom) {
26088
+ var atomId = _this5.struct().atoms.keyOf(atom);
26089
+ if (atomId !== null) {
26090
+ leavingAtomIdsSet.add(atomId);
26091
+ }
26092
+ });
26093
+ this.monomerCreationState.potentialAttachmentPoints.set(attachmentAtomId, leavingAtomIdsSet);
26058
26094
  }
26059
- this.preservedConnectionPointData["delete"](attachmentAtomId);
26060
26095
  this.monomerCreationState.assignedAttachmentPoints["delete"](name);
26061
26096
  this.monomerCreationState = Object.assign({}, this.monomerCreationState);
26062
26097
  this.render.update(true);
@@ -26105,7 +26140,7 @@ var Editor$3 = function () {
26105
26140
  }, {
26106
26141
  key: "findPotentialLeavingAtoms",
26107
26142
  value: function findPotentialLeavingAtoms(attachmentAtomId) {
26108
- var _this4 = this;
26143
+ var _this6 = this;
26109
26144
  var bondsToOutside = this.struct().bonds.filter(function (_, bond) {
26110
26145
  return attachmentAtomId === bond.begin && attachmentAtomId !== bond.end || attachmentAtomId === bond.end && attachmentAtomId !== bond.begin;
26111
26146
  });
@@ -26115,7 +26150,7 @@ var Editor$3 = function () {
26115
26150
  return;
26116
26151
  }
26117
26152
  var atomIdToUse = attachmentAtomId === bond.begin ? bond.end : bond.begin;
26118
- var atom = _this4.struct().atoms.get(atomIdToUse);
26153
+ var atom = _this6.struct().atoms.get(atomIdToUse);
26119
26154
  assert_1(atom);
26120
26155
  if (atom.neighbors.length === 1) {
26121
26156
  potentialLeavingAtoms.push(atom);
@@ -26126,15 +26161,15 @@ var Editor$3 = function () {
26126
26161
  }, {
26127
26162
  key: "subscribeToChangeEventInMonomerCreationWizard",
26128
26163
  value: function subscribeToChangeEventInMonomerCreationWizard() {
26129
- var _this5 = this;
26164
+ var _this7 = this;
26130
26165
  if (this.changeEventSubscriber) {
26131
26166
  return;
26132
26167
  }
26133
26168
  var handleChangeEvent = function handleChangeEvent(data) {
26134
- if (!_this5.isMonomerCreationWizardActive || data.length === 0) {
26169
+ if (!_this7.isMonomerCreationWizardActive || data.length === 0) {
26135
26170
  return;
26136
26171
  }
26137
- _this5.collectChangesForMonomerCreationStateInvalidation(data);
26172
+ _this7.collectChangesForMonomerCreationStateInvalidation(data);
26138
26173
  };
26139
26174
  this.changeEventSubscriber = this.subscribe('change', handleChangeEvent);
26140
26175
  }
@@ -26177,7 +26212,7 @@ var Editor$3 = function () {
26177
26212
  }, {
26178
26213
  key: "invalidateMonomerCreationWizardState",
26179
26214
  value: function invalidateMonomerCreationWizardState(changesMap) {
26180
- var _this6 = this;
26215
+ var _this8 = this;
26181
26216
  if (!this.monomerCreationState) {
26182
26217
  return;
26183
26218
  }
@@ -26191,7 +26226,7 @@ var Editor$3 = function () {
26191
26226
  switch (operation) {
26192
26227
  case ketcherCore.OperationType.ATOM_DELETE:
26193
26228
  {
26194
- var attachmentPointsToInvalidate = Array.from(_this6.monomerCreationState.assignedAttachmentPoints.entries()).filter(function (_ref13) {
26229
+ var attachmentPointsToInvalidate = Array.from(_this8.monomerCreationState.assignedAttachmentPoints.entries()).filter(function (_ref13) {
26195
26230
  var _ref14 = _slicedToArray__default["default"](_ref13, 2),
26196
26231
  atomPair = _ref14[1];
26197
26232
  return ids.has(atomPair[0]) || ids.has(atomPair[1]);
@@ -26207,18 +26242,39 @@ var Editor$3 = function () {
26207
26242
  attachmentAtomId = _atomPair4[0],
26208
26243
  leavingAtomId = _atomPair4[1];
26209
26244
  if (ids.has(attachmentAtomId)) {
26210
- var _this6$monomerCreatio;
26211
- (_this6$monomerCreatio = _this6.monomerCreationState) === null || _this6$monomerCreatio === void 0 || _this6$monomerCreatio.assignedAttachmentPoints["delete"](attachmentPointName);
26245
+ var _this8$monomerCreatio;
26246
+ (_this8$monomerCreatio = _this8.monomerCreationState) === null || _this8$monomerCreatio === void 0 || _this8$monomerCreatio.assignedAttachmentPoints["delete"](attachmentPointName);
26212
26247
  } else if (ids.has(leavingAtomId)) {
26213
- var potentialLeavingAtoms = _this6.findPotentialLeavingAtoms(attachmentAtomId);
26248
+ var potentialLeavingAtoms = _this8.findPotentialLeavingAtoms(attachmentAtomId);
26214
26249
  if (potentialLeavingAtoms.length === 0) {
26215
- var _this6$monomerCreatio2;
26216
- (_this6$monomerCreatio2 = _this6.monomerCreationState) === null || _this6$monomerCreatio2 === void 0 || _this6$monomerCreatio2.assignedAttachmentPoints["delete"](attachmentPointName);
26250
+ var _this8$monomerCreatio2;
26251
+ (_this8$monomerCreatio2 = _this8.monomerCreationState) === null || _this8$monomerCreatio2 === void 0 || _this8$monomerCreatio2.assignedAttachmentPoints["delete"](attachmentPointName);
26217
26252
  } else {
26218
- var _this6$monomerCreatio3;
26219
- var newLeavingAtomId = _this6.struct().atoms.keyOf(potentialLeavingAtoms[0]);
26253
+ var _this8$monomerCreatio3;
26254
+ var newLeavingAtomId = _this8.struct().atoms.keyOf(potentialLeavingAtoms[0]);
26220
26255
  assert_1(newLeavingAtomId !== null);
26221
- (_this6$monomerCreatio3 = _this6.monomerCreationState) === null || _this6$monomerCreatio3 === void 0 || _this6$monomerCreatio3.assignedAttachmentPoints.set(attachmentPointName, [attachmentAtomId, newLeavingAtomId]);
26256
+ (_this8$monomerCreatio3 = _this8.monomerCreationState) === null || _this8$monomerCreatio3 === void 0 || _this8$monomerCreatio3.assignedAttachmentPoints.set(attachmentPointName, [attachmentAtomId, newLeavingAtomId]);
26257
+ }
26258
+ }
26259
+ });
26260
+ var potentialAttachmentPointsToInvalidate = Array.from(_this8.monomerCreationState.potentialAttachmentPoints.entries());
26261
+ potentialAttachmentPointsToInvalidate.forEach(function (_ref17) {
26262
+ var _ref18 = _slicedToArray__default["default"](_ref17, 2),
26263
+ attachmentAtomId = _ref18[0],
26264
+ leavingAtomIds = _ref18[1];
26265
+ if (ids.has(attachmentAtomId)) {
26266
+ var _this8$monomerCreatio4;
26267
+ (_this8$monomerCreatio4 = _this8.monomerCreationState) === null || _this8$monomerCreatio4 === void 0 || _this8$monomerCreatio4.potentialAttachmentPoints["delete"](attachmentAtomId);
26268
+ } else {
26269
+ var updatedLeavingAtomIds = new Set(Array.from(leavingAtomIds).filter(function (id) {
26270
+ return !ids.has(id);
26271
+ }));
26272
+ if (updatedLeavingAtomIds.size === 0) {
26273
+ var _this8$monomerCreatio5;
26274
+ (_this8$monomerCreatio5 = _this8.monomerCreationState) === null || _this8$monomerCreatio5 === void 0 || _this8$monomerCreatio5.potentialAttachmentPoints["delete"](attachmentAtomId);
26275
+ } else {
26276
+ var _this8$monomerCreatio6;
26277
+ (_this8$monomerCreatio6 = _this8.monomerCreationState) === null || _this8$monomerCreatio6 === void 0 || _this8$monomerCreatio6.potentialAttachmentPoints.set(attachmentAtomId, updatedLeavingAtomIds);
26222
26278
  }
26223
26279
  }
26224
26280
  });
@@ -26231,24 +26287,40 @@ var Editor$3 = function () {
26231
26287
  try {
26232
26288
  var _loop2 = function _loop2() {
26233
26289
  var id = _step3.value;
26234
- var bond = _this6.struct().bonds.get(id);
26290
+ var bond = _this8.struct().bonds.get(id);
26235
26291
  assert_1(bond);
26236
- var attachmentPointWithBond = Array.from(_this6.monomerCreationState.assignedAttachmentPoints.entries()).find(function (_ref17) {
26237
- var _ref18 = _slicedToArray__default["default"](_ref17, 2),
26238
- atomPair = _ref18[1];
26292
+ var attachmentPointWithBond = Array.from(_this8.monomerCreationState.assignedAttachmentPoints.entries()).find(function (_ref19) {
26293
+ var _ref20 = _slicedToArray__default["default"](_ref19, 2),
26294
+ atomPair = _ref20[1];
26239
26295
  return bond.begin === atomPair[0] && bond.end === atomPair[1] || bond.begin === atomPair[1] && bond.end === atomPair[0];
26240
26296
  });
26241
- if (!attachmentPointWithBond) {
26242
- return 1;
26297
+ if (attachmentPointWithBond) {
26298
+ if (bond.type !== ketcherCore.Bond.PATTERN.TYPE.SINGLE || bond.stereo !== ketcherCore.Bond.PATTERN.STEREO.NONE) {
26299
+ _this8.monomerCreationState.problematicAttachmentPoints.add(attachmentPointWithBond[0]);
26300
+ } else {
26301
+ _this8.monomerCreationState.problematicAttachmentPoints["delete"](attachmentPointWithBond[0]);
26302
+ }
26243
26303
  }
26244
26304
  if (bond.type !== ketcherCore.Bond.PATTERN.TYPE.SINGLE || bond.stereo !== ketcherCore.Bond.PATTERN.STEREO.NONE) {
26245
- _this6.monomerCreationState.problematicAttachmentPoints.add(attachmentPointWithBond[0]);
26246
- } else {
26247
- _this6.monomerCreationState.problematicAttachmentPoints["delete"](attachmentPointWithBond[0]);
26305
+ _this8.monomerCreationState.potentialAttachmentPoints.forEach(function (leavingAtomIds, attachmentAtomId) {
26306
+ var updatedLeavingAtomIds = new Set(leavingAtomIds);
26307
+ var bondFromAttachmentAtom = bond.begin === attachmentAtomId && leavingAtomIds.has(bond.end);
26308
+ var bondToAttachmentAtom = bond.end === attachmentAtomId && leavingAtomIds.has(bond.begin);
26309
+ if (bondFromAttachmentAtom || bondToAttachmentAtom) {
26310
+ updatedLeavingAtomIds["delete"](bondFromAttachmentAtom ? bond.end : bond.begin);
26311
+ }
26312
+ if (updatedLeavingAtomIds.size === 0) {
26313
+ var _this8$monomerCreatio7;
26314
+ (_this8$monomerCreatio7 = _this8.monomerCreationState) === null || _this8$monomerCreatio7 === void 0 || _this8$monomerCreatio7.potentialAttachmentPoints["delete"](attachmentAtomId);
26315
+ } else {
26316
+ var _this8$monomerCreatio8;
26317
+ (_this8$monomerCreatio8 = _this8.monomerCreationState) === null || _this8$monomerCreatio8 === void 0 || _this8$monomerCreatio8.potentialAttachmentPoints.set(attachmentAtomId, updatedLeavingAtomIds);
26318
+ }
26319
+ });
26248
26320
  }
26249
26321
  };
26250
26322
  for (_iterator3.s(); !(_step3 = _iterator3.n()).done;) {
26251
- if (_loop2()) continue;
26323
+ _loop2();
26252
26324
  }
26253
26325
  } catch (err) {
26254
26326
  _iterator3.e(err);
@@ -26264,23 +26336,44 @@ var Editor$3 = function () {
26264
26336
  try {
26265
26337
  var _loop3 = function _loop3() {
26266
26338
  var id = _step4.value;
26267
- var bond = _this6.struct().bonds.get(id);
26339
+ var bond = _this8.struct().bonds.get(id);
26268
26340
  assert_1(bond);
26269
- var attachmentPointWithBondToLeavingAtom = Array.from(_this6.monomerCreationState.assignedAttachmentPoints.entries()).find(function (_ref19) {
26270
- var _ref20 = _slicedToArray__default["default"](_ref19, 2),
26271
- _ref20$ = _slicedToArray__default["default"](_ref20[1], 2),
26272
- leavingAtomId = _ref20$[1];
26341
+ var attachmentPointWithBondToLeavingAtom = Array.from(_this8.monomerCreationState.assignedAttachmentPoints.entries()).find(function (_ref21) {
26342
+ var _ref22 = _slicedToArray__default["default"](_ref21, 2),
26343
+ _ref22$ = _slicedToArray__default["default"](_ref22[1], 2),
26344
+ leavingAtomId = _ref22$[1];
26273
26345
  return bond.begin === leavingAtomId || bond.end === leavingAtomId;
26274
26346
  });
26275
- if (!attachmentPointWithBondToLeavingAtom) {
26276
- return 1;
26347
+ if (attachmentPointWithBondToLeavingAtom) {
26348
+ var _attachmentPointWithB = _slicedToArray__default["default"](attachmentPointWithBondToLeavingAtom, 1),
26349
+ attachmentPointName = _attachmentPointWithB[0];
26350
+ _this8.monomerCreationState.assignedAttachmentPoints["delete"](attachmentPointName);
26351
+ }
26352
+ if (bond.type === ketcherCore.Bond.PATTERN.TYPE.SINGLE && bond.stereo === ketcherCore.Bond.PATTERN.STEREO.NONE) {
26353
+ if (_this8.monomerCreationState.potentialAttachmentPoints.has(bond.begin)) {
26354
+ var leavingAtomIds = _this8.monomerCreationState.potentialAttachmentPoints.get(bond.begin);
26355
+ assert_1(leavingAtomIds);
26356
+ var endAtom = _this8.struct().atoms.get(bond.end);
26357
+ if (endAtom && endAtom.neighbors.length === 1) {
26358
+ var updatedLeavingAtomIds = new Set(leavingAtomIds);
26359
+ updatedLeavingAtomIds.add(bond.end);
26360
+ _this8.monomerCreationState.potentialAttachmentPoints.set(bond.begin, updatedLeavingAtomIds);
26361
+ }
26362
+ }
26363
+ if (_this8.monomerCreationState.potentialAttachmentPoints.has(bond.end)) {
26364
+ var _leavingAtomIds = _this8.monomerCreationState.potentialAttachmentPoints.get(bond.end);
26365
+ assert_1(_leavingAtomIds);
26366
+ var beginAtom = _this8.struct().atoms.get(bond.begin);
26367
+ if (beginAtom && beginAtom.neighbors.length === 1) {
26368
+ var _updatedLeavingAtomIds = new Set(_leavingAtomIds);
26369
+ _updatedLeavingAtomIds.add(bond.begin);
26370
+ _this8.monomerCreationState.potentialAttachmentPoints.set(bond.end, _updatedLeavingAtomIds);
26371
+ }
26372
+ }
26277
26373
  }
26278
- var _attachmentPointWithB = _slicedToArray__default["default"](attachmentPointWithBondToLeavingAtom, 1),
26279
- attachmentPointName = _attachmentPointWithB[0];
26280
- _this6.monomerCreationState.assignedAttachmentPoints["delete"](attachmentPointName);
26281
26374
  };
26282
26375
  for (_iterator4.s(); !(_step4 = _iterator4.n()).done;) {
26283
- if (_loop3()) continue;
26376
+ _loop3();
26284
26377
  }
26285
26378
  } catch (err) {
26286
26379
  _iterator4.e(err);
@@ -26655,6 +26748,17 @@ var Editor$3 = function () {
26655
26748
  }
26656
26749
  return visited.size === atomIds.length;
26657
26750
  }
26751
+ }, {
26752
+ key: "isStructureImpure",
26753
+ value: function isStructureImpure(struct) {
26754
+ var atoms = struct.atoms,
26755
+ sgroups = struct.sgroups,
26756
+ rgroups = struct.rgroups,
26757
+ functionalGroups = struct.functionalGroups;
26758
+ return sgroups.size > 0 || rgroups.size > 0 || functionalGroups.size > 0 || Array.from(atoms.values()).some(function (atom) {
26759
+ return ketcherCore.genericsList.includes(atom.label);
26760
+ });
26761
+ }
26658
26762
  }]);
26659
26763
  return Editor;
26660
26764
  }();
@@ -26730,10 +26834,10 @@ function domEventSetup(editor, clientArea) {
26730
26834
  eventName: 'mouseover',
26731
26835
  toolEventHandler: 'mouseover'
26732
26836
  }];
26733
- trackedDomEvents.forEach(function (_ref21) {
26734
- var target = _ref21.target,
26735
- eventName = _ref21.eventName,
26736
- toolEventHandler = _ref21.toolEventHandler;
26837
+ trackedDomEvents.forEach(function (_ref23) {
26838
+ var target = _ref23.target,
26839
+ eventName = _ref23.eventName,
26840
+ toolEventHandler = _ref23.toolEventHandler;
26737
26841
  editor.event[eventName] = new subscription.DOMSubscription();
26738
26842
  var subs = editor.event[eventName];
26739
26843
  target.addEventListener(eventName, function () {
@@ -29439,9 +29543,11 @@ var useAttachmentPointSelectsData = function useAttachmentPointSelectsData(edito
29439
29543
  leavingAtomId = _atomPair[1];
29440
29544
  var attachmentAtom = editor.struct().atoms.get(attachmentAtomId);
29441
29545
  assert_1(attachmentAtom);
29442
- var attachmentPointNameOptionsLength = Math.max.apply(Math, _toConsumableArray__default["default"](Array.from(assignedAttachmentPoints.keys()).map(function (name) {
29546
+ var usedNumbers = Array.from(assignedAttachmentPoints.keys()).map(function (name) {
29443
29547
  return ketcherCore.getAttachmentPointNumberFromLabel(name);
29444
- })));
29548
+ });
29549
+ var maxUsedNumber = Math.max.apply(Math, _toConsumableArray__default["default"](usedNumbers));
29550
+ var attachmentPointNameOptionsLength = maxUsedNumber <= 3 ? 3 : Math.min(maxUsedNumber, 8);
29445
29551
  var nameOptions = Array.from({
29446
29552
  length: attachmentPointNameOptionsLength
29447
29553
  }).map(function (_, i) {
@@ -29601,7 +29707,9 @@ var NotificationMessages = {
29601
29707
  noAttachmentPoints: 'The monomer must have at least one attachment point.',
29602
29708
  incorrectAttachmentPointsOrder: 'Attachment point numbers must be in order, but R1 and R2 may be skipped.',
29603
29709
  creationSuccessful: 'The monomer was successfully added to the library.',
29604
- incontinuousStructure: 'All monomers must have a continuous structure.'
29710
+ incontinuousStructure: 'All monomers must have a continuous structure.',
29711
+ notMinimalViableStructure: 'Minimal monomer structure is two atoms connected via a single bond.',
29712
+ impureStructure: 'Monomer structure cannot contain S-groups, R-groups, special atoms, or any other query properties.'
29605
29713
  };
29606
29714
  var NotificationTypes = {
29607
29715
  defaultAttachmentPoints: 'info',
@@ -29612,7 +29720,9 @@ var NotificationTypes = {
29612
29720
  noAttachmentPoints: 'error',
29613
29721
  incorrectAttachmentPointsOrder: 'error',
29614
29722
  creationSuccessful: 'info',
29615
- incontinuousStructure: 'error'
29723
+ incontinuousStructure: 'error',
29724
+ notMinimalViableStructure: 'error',
29725
+ impureStructure: 'error'
29616
29726
  };
29617
29727
  var MonomerCreationExternalNotificationAction = 'MonomerCreationExternalNotification';
29618
29728
 
@@ -29867,6 +29977,21 @@ var validateAttachmentPoints = function validateAttachmentPoints(attachmentPoint
29867
29977
  };
29868
29978
  var validateStructure = function validateStructure(editor) {
29869
29979
  var notifications = new Map();
29980
+ var isStructureImpure = Editor$3.isStructureImpure(editor.struct());
29981
+ if (isStructureImpure) {
29982
+ notifications.set('impureStructure', {
29983
+ type: 'error',
29984
+ message: NotificationMessages.impureStructure
29985
+ });
29986
+ }
29987
+ var isMinimalViableStructure = editor.isMinimalViableStructure();
29988
+ if (!isMinimalViableStructure) {
29989
+ notifications.set('notMinimalViableStructure', {
29990
+ type: 'error',
29991
+ message: NotificationMessages.notMinimalViableStructure
29992
+ });
29993
+ return notifications;
29994
+ }
29870
29995
  var isStructureContinuous = Editor$3.isStructureContinuous(editor.struct());
29871
29996
  if (!isStructureContinuous) {
29872
29997
  notifications.set('incontinuousStructure', {
@@ -36704,6 +36829,11 @@ var TemplateDialog = function TemplateDialog(props) {
36704
36829
  onTabChange(initialTab);
36705
36830
  }
36706
36831
  }, [initialTab, onTabChange]);
36832
+ React.useEffect(function () {
36833
+ if (isMonomerCreationWizardActive && tab === TemplateTabs.FunctionalGroupLibrary) {
36834
+ onTabChange(TemplateTabs.TemplateLibrary);
36835
+ }
36836
+ }, [isMonomerCreationWizardActive, tab, onTabChange]);
36707
36837
  var handleAccordionChange = function handleAccordionChange(accordion) {
36708
36838
  return function (_, isExpanded) {
36709
36839
  setExpandedAccordions(isExpanded ? [].concat(_toConsumableArray__default["default"](expandedAccordions), [accordion]) : _toConsumableArray__default["default"](expandedAccordions).filter(function (expandedAccordion) {
@@ -37911,12 +38041,12 @@ var AbbreviationLookup = function AbbreviationLookup(_ref) {
37911
38041
  });
37912
38042
  },
37913
38043
  renderOption: function renderOption(props, option) {
37914
- return jsxRuntime.jsx("li", _objectSpread$2(_objectSpread$2({}, props), {}, {
38044
+ return React.createElement("li", _objectSpread$2(_objectSpread$2({}, props), {}, {
37915
38045
  title: option.label,
37916
- children: jsxRuntime.jsx("div", {
37917
- className: classes.optionItemContent,
37918
- children: highlightOptionLabel(option, loweredLookupValue)
37919
- })
38046
+ key: option.label
38047
+ }), jsxRuntime.jsx("div", {
38048
+ className: classes.optionItemContent,
38049
+ children: highlightOptionLabel(option, loweredLookupValue)
37920
38050
  }));
37921
38051
  },
37922
38052
  "data-testid": ABBREVIATION_LOOKUP_TEST_ID
@@ -38194,8 +38324,8 @@ var KetcherBuilder = function () {
38194
38324
  cleanup = initApp(prevKetcherId, ketcherId, element, appRoot, staticResourcesUrl, {
38195
38325
  buttons: buttons || {},
38196
38326
  errorHandler: errorHandler || null,
38197
- version: "3.9.0-rc.1" ,
38198
- buildDate: "2025-10-02T16:45:46" ,
38327
+ version: "3.9.0-rc.2" ,
38328
+ buildDate: "2025-10-16T18:57:23" ,
38199
38329
  buildNumber: '',
38200
38330
  customButtons: customButtons || []
38201
38331
  }, structService, resolve, togglerComponent);
@@ -38490,7 +38620,7 @@ var ModeControl = function ModeControl(_ref3) {
38490
38620
  function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
38491
38621
  function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty__default["default"](e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
38492
38622
  var MacromoleculesEditorComponent = React.lazy(function () {
38493
- return Promise.resolve().then(function () { return require('./index.modern-798ecc56.js'); });
38623
+ return Promise.resolve().then(function () { return require('./index.modern-bddb9120.js'); });
38494
38624
  });
38495
38625
  var Editor = function Editor(props) {
38496
38626
  var _useState = React.useState(false),