diff --git a/src/DPrsStd/DPrsStd_AISPresentationCommands.cxx b/src/DPrsStd/DPrsStd_AISPresentationCommands.cxx
index 84c8392e12..695175641f 100644
--- a/src/DPrsStd/DPrsStd_AISPresentationCommands.cxx
+++ b/src/DPrsStd/DPrsStd_AISPresentationCommands.cxx
@@ -636,7 +636,7 @@ static Standard_Integer DPrsStd_AISMode(Draw_Interpretor& di,
 
 //=======================================================================
 //function : DPrsStd_AISSelMode
-//purpose  : AISSelMode (DOC,entry,[SelMode])
+//purpose  : AISSelMode (DOC,entry,[SelMode1 SelMode2 ...])
 //=======================================================================
 static Standard_Integer DPrsStd_AISSelMode(Draw_Interpretor& di,
                                            Standard_Integer nb,
@@ -645,7 +645,7 @@ static Standard_Integer DPrsStd_AISSelMode(Draw_Interpretor& di,
   TDF_Label L;
   Handle(TDocStd_Document) D;
   Handle(TPrsStd_AISPresentation) prs;
-  if (nb >= 3 && nb <= 4)
+  if (nb >= 3)
   {
     if (!DDocStd::GetDocument(arg[1],D)) 
       return 1;
@@ -653,18 +653,38 @@ static Standard_Integer DPrsStd_AISSelMode(Draw_Interpretor& di,
       return 1;
     if (!L.FindAttribute(TPrsStd_AISPresentation::GetID(), prs))
       return 1;
-    if (nb == 4)
+    if (nb >= 4)
     {
       // Set selection mode.
       Standard_Integer selMode = Draw::Atoi(arg[3]);
       prs->SetSelectionMode(selMode);
+      // Add other selection modes.
+      for (Standard_Integer i = 4; i < nb; i++)
+      {
+        selMode = Draw::Atoi(arg[i]);
+        prs->AddSelectionMode(selMode);
+      }
       TPrsStd_AISViewer::Update(L);
     }
     else if (nb == 3)
     {
       // Print selection mode.
-      Standard_Integer selMode = prs->SelectionMode();
-      di<<selMode;
+      Standard_Integer nbSelModes = prs->GetNbSelectionModes();
+      if (nbSelModes == 1)
+      {
+        Standard_Integer selMode = prs->SelectionMode();
+        di << selMode;
+      }
+      else
+      {
+        for (Standard_Integer i = 1; i <= nbSelModes; i++)
+        {
+          Standard_Integer selMode = prs->SelectionMode(i);
+          di << selMode;
+          if (i < nbSelModes)
+            di << " ";
+        }
+      }
     }
     return 0; 
   }
@@ -756,6 +776,6 @@ void DPrsStd::AISPresentationCommands (Draw_Interpretor& theCommands)
 		   __FILE__, DPrsStd_AISMode, g);
 
   theCommands.Add ("AISSelMode", 
-                   "AISSelMode (DOC, entry, [SelMode])",
+                   "AISSelMode (DOC, entry, [SelMode1 SelMode2 ...])",
 		   __FILE__, DPrsStd_AISSelMode, g);
 }
diff --git a/src/TDataXtd/TDataXtd_Presentation.cxx b/src/TDataXtd/TDataXtd_Presentation.cxx
index b389e603c0..8525767e33 100644
--- a/src/TDataXtd/TDataXtd_Presentation.cxx
+++ b/src/TDataXtd/TDataXtd_Presentation.cxx
@@ -33,7 +33,6 @@ TDataXtd_Presentation::TDataXtd_Presentation()
   myColor                (Quantity_NOC_WHITE),
   myMaterialIndex        (0),
   myMode                 (0),
-  mySelectionMode        (0),
   myTransparency         (0.0),
   myWidth                (0.0),
   myIsDisplayed          (Standard_False),
@@ -280,6 +279,15 @@ void TDataXtd_Presentation::SetMode(const Standard_Integer theMode)
   }
 }
 
+//=======================================================================
+//function : GetNbSelectionModes
+//purpose  : Returns the number of selection modes of the attribute.
+//         : It starts with 1 .. GetNbSelectionModes().
+//=======================================================================
+Standard_EXPORT Standard_Integer TDataXtd_Presentation::GetNbSelectionModes() const
+{
+  return mySelectionModes.Extent();
+}
 
 //=======================================================================
 //function : SetSelectionMode
@@ -287,15 +295,31 @@ void TDataXtd_Presentation::SetMode(const Standard_Integer theMode)
 //=======================================================================
 void TDataXtd_Presentation::SetSelectionMode(const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction)
 {
-  if (! myHasOwnSelectionMode || mySelectionMode != theSelectionMode)
+  if (!myHasOwnSelectionMode || GetNbSelectionModes() > 1 ||
+      (GetNbSelectionModes() > 0 && mySelectionModes.First() != theSelectionMode))
   {
     if (theTransaction)
-        Backup();
-    mySelectionMode = theSelectionMode;
+      Backup();
+    mySelectionModes.Clear();
+    mySelectionModes.Append(theSelectionMode);
     myHasOwnSelectionMode = Standard_True;
   }
 }
 
+//=======================================================================
+//function : AddSelectionMode
+//purpose  : 
+//=======================================================================
+void TDataXtd_Presentation::AddSelectionMode(const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction)
+{
+  if (!myHasOwnSelectionMode || !HasSelectionMode(theSelectionMode))
+  {
+    if (theTransaction)
+      Backup();
+    mySelectionModes.Append(theSelectionMode);
+    myHasOwnSelectionMode = Standard_True;
+  }
+}
 
 //=======================================================================
 //function : MaterialIndex
@@ -351,9 +375,16 @@ Standard_Integer TDataXtd_Presentation::Mode() const
 //function : SelectionMode
 //purpose  : 
 //=======================================================================
-Standard_Integer TDataXtd_Presentation::SelectionMode() const
+Standard_Integer TDataXtd_Presentation::SelectionMode(const Standard_Integer index) const
 {
-  return mySelectionMode;
+  Standard_Integer aSelectionMode(0);
+  TColStd_ListOfInteger::Iterator itr(mySelectionModes);
+  for (Standard_Integer i = 1; itr.More() && i <= index; itr.Next(), i++)
+  {
+    if (i == index)
+      aSelectionMode = itr.Value();
+  }
+  return aSelectionMode;
 }
 
 
@@ -437,6 +468,7 @@ void TDataXtd_Presentation::UnsetSelectionMode()
   {
     Backup();
     myHasOwnSelectionMode = Standard_False;
+    mySelectionModes.Clear();
   }
 }
 
@@ -451,7 +483,7 @@ Handle(TDF_Attribute) TDataXtd_Presentation::BackupCopy() const
 
   aCopy->myIsDisplayed   = myIsDisplayed;
   aCopy->myDriverGUID    = myDriverGUID;
-  aCopy->mySelectionMode = mySelectionMode;
+  aCopy->mySelectionModes= mySelectionModes;
   aCopy->myTransparency  = myTransparency;
   aCopy->myColor         = myColor;
   aCopy->myMode          = myMode;
@@ -501,7 +533,7 @@ void TDataXtd_Presentation::Restore(const Handle(TDF_Attribute)& theAttribute)
   myMode = aPresentation->Mode();
 
   myHasOwnSelectionMode = aPresentation->HasOwnSelectionMode();
-  mySelectionMode = aPresentation->SelectionMode();
+  mySelectionModes = aPresentation->mySelectionModes;
 
   myHasOwnTransparency = aPresentation->HasOwnTransparency();
   myTransparency = aPresentation->Transparency();
@@ -565,7 +597,7 @@ void TDataXtd_Presentation::Paste(const Handle(TDF_Attribute)& theInto,
 
   if (myHasOwnSelectionMode)
   {
-    anInto->mySelectionMode = mySelectionMode;
+    anInto->mySelectionModes = mySelectionModes;
     anInto->myHasOwnSelectionMode = Standard_True;
   }
   else
@@ -586,3 +618,19 @@ void TDataXtd_Presentation::Paste(const Handle(TDF_Attribute)& theInto,
   anInto->myIsDisplayed = myIsDisplayed;
   anInto->myDriverGUID  = myDriverGUID;
 }
+
+//=======================================================================
+//function : HasSelectionMode
+//purpose  : Checks a list of selection modes.
+//=======================================================================
+Standard_Boolean TDataXtd_Presentation::HasSelectionMode(const Standard_Integer theSelectionMode) const
+{
+  Standard_Boolean ret(Standard_False);
+  TColStd_ListOfInteger::Iterator itr(mySelectionModes);
+  for (; itr.More(); itr.Next())
+  {
+    if (theSelectionMode == itr.Value())
+      ret = Standard_True;
+  }
+  return ret;
+}
diff --git a/src/TDataXtd/TDataXtd_Presentation.hxx b/src/TDataXtd/TDataXtd_Presentation.hxx
index 9911b2462e..2354e058b6 100644
--- a/src/TDataXtd/TDataXtd_Presentation.hxx
+++ b/src/TDataXtd/TDataXtd_Presentation.hxx
@@ -23,6 +23,7 @@
 #include <gp_Pnt.hxx>
 #include <TDF_Attribute.hxx>
 #include <Quantity_NameOfColor.hxx>
+#include <TColStd_ListOfInteger.hxx>
 
 class TDF_Label;
 class gp_Pnt;
@@ -114,13 +115,17 @@ public:
 
   Standard_EXPORT void SetMode(const Standard_Integer theMode);
 
+  //! Returns the number of selection modes of the attribute.
+  //! It starts with 1 .. GetNbSelectionModes().
+  Standard_EXPORT Standard_Integer GetNbSelectionModes() const;
+
   //! Sets selection mode.
   //! If "theTransaction" flag is OFF, modification of the attribute doesn't influence the transaction mechanism
-  //! (the attribute doesn't participate in undo/redo).
+  //! (the attribute doesn't participate in undo/redo because of this modification).
   //! Certainly, if any other data of the attribute is modified (display mode, color, ...),
-  //! the attribute will be included into transaction.
-  //! Obsolete method (may be removed later).
+  //! the attribute will be included into undo/redo.
   Standard_EXPORT void SetSelectionMode(const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction = Standard_True);
+  Standard_EXPORT void AddSelectionMode(const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction = Standard_True);
 
   Standard_EXPORT Standard_Integer MaterialIndex() const;
 
@@ -132,7 +137,7 @@ public:
 
   Standard_EXPORT Standard_Integer Mode() const;
 
-  Standard_EXPORT Standard_Integer SelectionMode() const;
+  Standard_EXPORT Standard_Integer SelectionMode(const int index = 1) const;
 
   Standard_EXPORT void UnsetMaterial();
 
@@ -151,7 +156,7 @@ private:
   Quantity_NameOfColor myColor;
   Standard_Integer myMaterialIndex;
   Standard_Integer myMode;
-  Standard_Integer mySelectionMode;
+  TColStd_ListOfInteger mySelectionModes;
   Standard_Real myTransparency;
   Standard_Real myWidth;
   Standard_Boolean myIsDisplayed;
@@ -161,6 +166,9 @@ private:
   Standard_Boolean myHasOwnWidth;
   Standard_Boolean myHasOwnMode;
   Standard_Boolean myHasOwnSelectionMode;
+
+  //! Checks a list of selection modes.
+  Standard_Boolean HasSelectionMode(const Standard_Integer theSelectionMode) const;
 };
 
 #endif // _TDataXtd_Presentation_HeaderFile
diff --git a/src/TPrsStd/TPrsStd_AISPresentation.cxx b/src/TPrsStd/TPrsStd_AISPresentation.cxx
index 777eb8f042..1c0140ffc9 100644
--- a/src/TPrsStd/TPrsStd_AISPresentation.cxx
+++ b/src/TPrsStd/TPrsStd_AISPresentation.cxx
@@ -569,13 +569,23 @@ void TPrsStd_AISPresentation::UnsetMode()
   }
 }
 
+//=======================================================================
+//function : GetNbSelectionModes
+//purpose  : Returns selection mode(s) of the attribute.
+//         : It starts with 1 .. GetNbSelectionModes().
+//=======================================================================
+Standard_Integer TPrsStd_AISPresentation::GetNbSelectionModes() const
+{
+  return getData()->GetNbSelectionModes();
+}
+
 //=======================================================================
 //function : SelectionMode
 //purpose  : 
 //=======================================================================
-Standard_Integer TPrsStd_AISPresentation::SelectionMode() const
+Standard_Integer TPrsStd_AISPresentation::SelectionMode(const Standard_Integer index) const
 {
-  return getData()->SelectionMode();
+  return getData()->SelectionMode(index);
 }
 
 //=======================================================================
@@ -603,13 +613,29 @@ void TPrsStd_AISPresentation::SetSelectionMode(const Standard_Integer theSelecti
     ActivateSelectionMode();
 }
 
+//=======================================================================
+//function : AddSelectionMode
+//purpose  : 
+//=======================================================================
+void TPrsStd_AISPresentation::AddSelectionMode(const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction)
+{
+  if (theTransaction)
+    Backup();
+  getData()->AddSelectionMode (theSelectionMode, theTransaction);
+
+  if (myAIS.IsNull())
+    AISUpdate();
+  else
+    ActivateSelectionMode();
+}
+
 //=======================================================================
 //function : UnsetSelectionMode
 //purpose  : 
 //=======================================================================
 void TPrsStd_AISPresentation::UnsetSelectionMode()
 {
-  getData()->UnsetSelectionMode ();
+  getData()->UnsetSelectionMode();
   AISUpdate();
 }
 
@@ -1006,24 +1032,37 @@ void TPrsStd_AISPresentation::ActivateSelectionMode()
     {
       TColStd_ListOfInteger anActivatedModes;
       aContext->ActivatedModes (myAIS, anActivatedModes);
-      Standard_Boolean isActivated = Standard_False;
-      Standard_Integer aSelectionMode = SelectionMode();
-      if (aSelectionMode == -1)
+      Standard_Integer nbSelModes = GetNbSelectionModes();
+      if (nbSelModes == 1)
       {
-        aContext->Deactivate(myAIS);
+        Standard_Boolean isActivated = Standard_False;
+        Standard_Integer aSelectionMode = SelectionMode();
+        if (aSelectionMode == -1)
+        {
+          aContext->Deactivate(myAIS);
+        }
+        else
+        {
+          for (TColStd_ListIteratorOfListOfInteger aModeIter(anActivatedModes); aModeIter.More(); aModeIter.Next())
+          {
+            if (aModeIter.Value() == aSelectionMode)
+            {
+              isActivated = Standard_True;
+              break;
+            }
+          }
+          if (!isActivated)
+            aContext->Activate(myAIS, aSelectionMode, Standard_False);
+        }
       }
       else
       {
-        for (TColStd_ListIteratorOfListOfInteger aModeIter (anActivatedModes); aModeIter.More(); aModeIter.Next())
+        for (Standard_Integer iSelMode = 1; iSelMode <= nbSelModes; iSelMode++)
         {
-          if (aModeIter.Value() == aSelectionMode)
-          {
-            isActivated = Standard_True;
-            break;
-          }
+          const Standard_Integer aSelectionMode = SelectionMode (iSelMode);
+          aContext->SetSelectionModeActive (myAIS, aSelectionMode, Standard_True/*activate*/,
+                                            iSelMode == 1 ? AIS_SelectionModesConcurrency_Single : AIS_SelectionModesConcurrency_GlobalOrLocal);
         }
-        if (!isActivated)
-          aContext->Activate (myAIS, aSelectionMode, Standard_False);
       }
     } 
   }
diff --git a/src/TPrsStd/TPrsStd_AISPresentation.hxx b/src/TPrsStd/TPrsStd_AISPresentation.hxx
index 6d5ddd22df..a9dee8baea 100644
--- a/src/TPrsStd/TPrsStd_AISPresentation.hxx
+++ b/src/TPrsStd/TPrsStd_AISPresentation.hxx
@@ -155,19 +155,23 @@ public:
   Standard_EXPORT Standard_Boolean HasOwnMode() const;
   
   Standard_EXPORT void UnsetMode();
-  
-  Standard_EXPORT Standard_Integer SelectionMode() const;
+
+  //! Returns selection mode(s) of the attribute.
+  //! It starts with 1 .. GetNbSelectionModes().
+  Standard_EXPORT Standard_Integer GetNbSelectionModes() const;
+  Standard_EXPORT Standard_Integer SelectionMode(const int index = 1) const;
 
   //! Sets selection mode.
   //! If "theTransaction" flag is OFF, modification of the attribute doesn't influence the transaction mechanism
-  //! (the attribute doesn't participate in undo/redo).
+  //! (the attribute doesn't participate in undo/redo because of this modification).
   //! Certainly, if any other data of the attribute is modified (display mode, color, ...),
-  //! the attribute will be included into transaction.
-  //! Obsolete method (may be removed later).
-  Standard_EXPORT void SetSelectionMode (const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction = Standard_True);
-  
+  //! the attribute will be included into undo/redo.
+  Standard_EXPORT void SetSelectionMode(const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction = Standard_True);
+  Standard_EXPORT void AddSelectionMode(const Standard_Integer theSelectionMode, const Standard_Boolean theTransaction = Standard_True);
+
   Standard_EXPORT Standard_Boolean HasOwnSelectionMode() const;
   
+  //! Clears all selection modes of the attribute.
   Standard_EXPORT void UnsetSelectionMode();
   
   Standard_EXPORT const Standard_GUID& ID() const Standard_OVERRIDE;
diff --git a/tests/caf/presentation/N1 b/tests/caf/presentation/N1
new file mode 100644
index 0000000000..67f9a7b85a
--- /dev/null
+++ b/tests/caf/presentation/N1
@@ -0,0 +1,78 @@
+#INTERFACE CAF
+# Presentation attributes
+#
+# Testing attribute: TPrsStd_AISPresentation
+#
+# Testing command:   AISSelMode
+#
+
+puts "caf003-N1"
+
+# Close/Open transaction
+NewCommand D
+
+# Set a shape
+box aBox1 100 200 300
+set aLabel 0:2
+SetShape D ${aLabel} aBox1
+
+# Initialize 3D viewer
+AISInitViewer D
+
+# Add AISPresentation attribute with parameter NS
+AISSet D ${aLabel} NS
+
+# Display presentation of NamedShape in the viewer
+AISDisplay D ${aLabel}
+
+# Close/Open transaction
+NewCommand D
+
+# Get default selection mode
+set aSelMode1 [AISSelMode D ${aLabel}]
+if { ${aSelMode1} != 0 } {
+	puts "Default selection mode is not 0"
+        return
+}
+
+# Set selection mode = 2
+AISSelMode D ${aLabel} 2
+set aSelMode2 [AISSelMode D ${aLabel}]
+if { ${aSelMode2} != 2 } {
+	puts "Selection mode is not 2"
+        return
+}
+
+# Close/Open transaction
+NewCommand D
+
+# Set selection mode = 2 4
+AISSelMode D ${aLabel} 2 4
+set aSelMode3 [AISSelMode D ${aLabel}]
+if { ${aSelMode3} != "2 4" } {
+	puts "Selection mode is not 2 4"
+        return
+}
+
+# Close/Open transaction
+NewCommand D
+
+# Undo
+Undo D
+
+set aSelMode4 [AISSelMode D ${aLabel}]
+if { ${aSelMode4} != 2 } {
+	puts "Selection mode after undo is not 2"
+        return
+}
+
+# Redo
+Redo D
+
+set aSelMode5 [AISSelMode D ${aLabel}]
+if { ${aSelMode5} != "2 4" } {
+	puts "Selection mode after redo is not 2 4"
+        return
+}
+
+puts "AISSelMode command: OK"