Message Boards Message Boards

Avoid SelectionMove inconsistency?

Posted 6 years ago

I believe there is a bug in SelectionMove when it is used to select a CellGroup. The bug is two-fold: not only SelectionMove fails to perform the operation, but also it doesn't return $Failed is it should according to the Documentation:

SelectionMove returns $Failed if it cannot move the selection in the way you request.

Suppose we have a Notebook containing a CellGroup. Then we can paste the following cell after this CellGroup and evaluate it in order to select the previous CellGroup:

SelectionMove[PreviousCell[], All, CellGroup]

This works in the latest version of Mathematica if PreviousCell[] is indeed a member of a CellGroup. But what if it is not? In this case this piece of code just does nothing AND nothing is returned as output, the latter directly contradicts the cited Documentation statement.

The described behavior is also inconsistent with other cases, for example

SelectionMove[EvaluationCell[], Previous, CellGroup]

selects the previous cell (which isn't a member of a CellGroup). Why then the same approach fail to work with PreviousCell[]?

The fact that SelectionMove doesn't return $Failed when it is unable to perform the requested operation is very unfortunate because it makes programming much more difficult: we must check whether selection is moved after EVERY call to SelectionMove, but there is no universal way to do this. In the best case it complicates code a lot and is very inefficient. In the worst case it makes it impossible to perform some simple tasks, as a bright example consider this StackExchange question:

The problem raised in this question is so simple that it is hard to believe it can't be solved reliably: we need just to move the selection after the input cell OR after the CellGroup containing output generated by this cell, and print new cell without scrolling using NotebookWrite (CellPrint always scrolls, hence it cannot be used in this case). But careful investigation showed that it is currently impossible to do this in an efficient way mainly due to the described bug.

My main question is:
Is it possible to check in an efficient and reliable way, whether SelectionMove has failed or not?

Reported to the support as [CASE:3968507].

POSTED BY: Alexey Popkov
4 Replies
Posted 6 years ago

By request from the support I've prepared a Notebook demonstrating both the issues, which as I believe worth posting here. The problems (bugs?) are:

  1. SelectionMove doesn't return $Failed when it fails to move selection in the requested way (second and fourth input cells in the Notebook). This directly contradicts the Documentation statement cited at the beginning of my previous post.

  2. It isn't clear why SelectionMove can't select a standalone previous cell when it starts directly from PreviousCell[] (see second input cell in the Notebook), but is able to do this when it starts from EvaluationCell[] (see fifth input cell in the Notebook). How this difference could be explained? Isn't it an inconsistency?

The motivation for the second point is that I need a way to select either a certain single cell (if the cell is standalone, i.e. not a member of a cell group) or the whole cell group (if the cell is a member of this group) having only CellObject of the cell. The simplest example is given as third and fourth input cells in the Notebook: the code in the third cell correctly selects the surrounding cell group, but the code in the fourth cell does nothing and also doesn't tell me that it failed to select the fourth input cell. I should stress that I do not know beforehand whether the cell is inside of a cell group, or not (and have no idea how to obtain this information in an efficient way). Since SelectionMove doesn't return $Failed (as it should according to the docs), I don't know whether it failed or not. Is there an efficient way to find it out?

Please find the Notebook attached to the post.

Attachments:
POSTED BY: Alexey Popkov
Posted 5 years ago

The first of the described bugs seems to be fixed in version 12.0: now SelectionMove returns $Failed when it can't move the selection. But inconsistent behavior of SelectionMove[PreviousCell[], All, CellGroup] as compared to SelectionMove[EvaluationCell[], Previous, CellGroup] when previous cell isn't a member of a CellGroup is still here: in the first case SelectionMove fails, in the second it successfully selects the previous cell.

POSTED BY: Alexey Popkov
Posted 4 years ago

Further investigation shows that while in version 12.0 SelectionMove returns $Failed when it can't move the selection in the cases described in the original question, it still doesn't work properly in some other cases. For example, consider the case of evaluation of a standalone Cell containing the following code:

SelectionMove[EvaluationCell[], After, GeneratedCell, AutoScroll -> False]

If this Cell has no any Cell immediately after it, the visual insertion point in the Notebook just disappears! And SelectionMove doesn't return $Failed as it should according to the Documentation.

If after this Cell we have another input Cell in the Notebook, the insertion point unexpectedly is moved after the next input Cell. The latter isn't a GeneratedCell, so this behavior is wrong. This happens even if after the next input Cell we have a GeneratedCell.

Reported to the support as [CASE:4326002].

POSTED BY: Alexey Popkov
Posted 2 years ago

I notice that some changes in the behavior of SelectionMove occurred on the transition from version 12.3.1 to 13.0.0.

  1. Changed the behavior of SelectionMove[EvaluationCell[], Previous, CellGroup]. Now it selects the previous CellGroup, even if between the previous CellGroup and the EvaluationCell[] present several cells which aren't a member of a CellGroup. Here is a screenshot of a version 13.0.0 Notebook right after "Evaluate Notebook":

    screenshot

    And here is what happens in version 12.3.1:

    SCREENSHOT2

    The new behavior is more consistent. So the inconsistency described in the question is finally fixed in version 13.0.0.

  2. In the same way changed the behavior of SelectionMove[PreviousCell[], Previous, CellGroup]. Now it selects the CellGroup before the PreviousCell[] even if PreviousCell[] is a member of a CellGroup itself. Here is a screenshot of a version 13.0.0 Notebook right after "Evaluate Notebook":

    screenshot3

    And here is what happens in version 12.3.1:

    screenshot4

So this aspect of the behavior of SelectionMove is finally fixed in version 13.0.0.

POSTED BY: Updating Name
Reply to this discussion
Community posts can be styled and formatted using the Markdown syntax.
Reply Preview
Attachments
Remove
or Discard

Group Abstract Group Abstract