让 CellDingbat 在 Mathematica 会话之间记住它的状态 [英] Getting CellDingbat to remember its state between Mathematica sessions

查看:25
本文介绍了让 CellDingbat 在 Mathematica 会话之间记住它的状态的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我修改了我笔记本的样式表以包含一个从 StyleData["Item"] 继承的 StyleData["Todo"].它将单元格 dingbat 更改为复选框.在样式表编辑器中:

I have modified my notebook's stylesheet to include a StyleData["Todo"] that inherits from StyleData["Item"]. It changes the cell dingbat to a checkbox. In the stylesheet editor:

Cell[StyleData["ToDo", StyleDefinitions -> StyleData["Item"]], 
  CellDingbat->DynamicModuleBox[{$CellContext`color$$}, 
    CheckboxBox[
    Dynamic[$CellContext`color$$], {RGBColor[1, 0.5, 0],RGBColor[0,Rational[2, 3], 0]},    
    Background -> Dynamic[$CellContext`color$$]], 
    DynamicModuleValues :> {}
  ],
]

问题是复选框的状态在笔记本中使用时不会在 Mathematica 会话之间保存.我认为 DynamicModule[] 可以解决问题.如何让复选框记住其状态?

The problem is that the state of the checkbox, when used in a notebook, is not saved between Mathematica sessions. I thought the DynamicModule[] would do the trick. How do I get the checkbox to remember its state?

编辑

Simon 的解决方案确实保存了复选框的状态,但是当用作 CellDingbat (MacOS X) 时,复选框会被裁剪.将 Simon 的代码放在 CellFrameLabels 选项中可以解决问题,并且还保留默认的项目"CellDingbat.这是我所用的:

Simon's solution does save the state of the checkbox, but the checkbox is clipped when used as a CellDingbat (MacOS X). Putting Simon's code in a CellFrameLabels options does the trick, and also keeps the default "Item" CellDingbat. Here is what I've gone with:

Cell[StyleData["ToDo", StyleDefinitions -> StyleData["Item"]],
 CellFrameLabels->{{
    ButtonBox[
     CheckboxBox[False], ButtonFunction :> (SelectionMove[
        ButtonNotebook[], All, ButtonCell]; 
      With[{$CellContext`new = ReplaceAll[
           Options[
            NotebookSelection[
             ButtonNotebook[]], CellFrameLabels], CheckboxBox[
             Pattern[$CellContext`x, 
              Alternatives[True, False]]] :> CheckboxBox[
             Not[$CellContext`x]]]}, 
        SetOptions[
         NotebookSelection[
          ButtonNotebook[]], $CellContext`new]]; SelectionMove[
        ButtonNotebook[], After, CellContents]), Appearance -> None, 
     Method -> "Preemptive", Evaluator -> Automatic], None}, {
   None, None}},
 MenuSortingValue->1621]

推荐答案

您的代码的问题(我认为)是每次创建新的ToDo"时都不会创建新的 DynamicModule"细胞.所以没有任何地方可以保存每个 Checkbox 的状态.

The problem with your code (I think) is that a new DynamicModule does not get created each time you create a new "ToDo" cell. So there is nowhere that the state of each Checkbox can get saved.

我能想到的为每个待办事项"单元格存储 Checkbox 状态的最简单解决方案是在 第一次覆盖 CellDingbat复选框被激活.(我使用的其他选项是使用 TaggingRules,在待办事项"和待办事项"样式之间切换,等等...)

The simplest solution I could think of for storing the state of the Checkbox for each "ToDo" cell is to overwrite the CellDingbat the first time that the Checkbox is activated. (Other options I played with were using TaggingRules, toggling between "ToDo" and "ToDone" styles, etc...)

但是,即使 CellDingbat 中的普通 Checkbox 也不会存储其状态 - 尝试运行以下命令,然后通过 显示表达式 循环.

However, even a plain Checkbox in a CellDingbat does not store its state - try running the following then cycle the output through a Show Expression cycle.

CellPrint[Cell["test", "Text", CellDingbat -> ToBoxes[Checkbox[]]]]

为了解决这个问题,我使用了 Checkbox 和明确的参数 TrueFalse 包裹在改变状态的按钮中.这是愚蠢且低效的,但它有效!

To get around this, I used Checkbox with the definite argument True or False wrapped up in a button that changes the state. This is stupid and inefficient, but it works!

所以,我的单元格样式代码

So, my code for the cell style

Cell[StyleData["ToDo", StyleDefinitions -> StyleData["Item"]],
 CellDingbat -> ButtonBox[CheckboxBox[False], 
   ButtonFunction :> (SelectionMove[ButtonNotebook[], All, ButtonCell]; 
     With[{$CellContext`new = ReplaceAll[
          Options[NotebookSelection[ButtonNotebook[]], CellDingbat], 
          CheckboxBox[Pattern[$CellContext`x, Alternatives[True, False]]] :> CheckboxBox[Not[$CellContext`x]]]}, 
        SetOptions[NotebookSelection[ButtonNotebook[]], $CellContext`new]]; 
      SelectionMove[ButtonNotebook[], After, CellContents]), 
    Appearance -> None, Method -> "Preemptive", Evaluator -> Automatic]]

我对这个解决方案不满意,但这是我想出的最好的解决方案.一个改进是将按钮功能代码移出单元格,这样就不会为每个选中的 ToDo 单元格重复它.还要让它在没有 ReplaceAll 的情况下运行,这样就不需要内核,并且可以只使用前端来运行该函数.

I'm not happy with this solution, but it's the best I've come up with. An improvement would be to move the button function code out of the cell so that it is not repeated for every checked ToDo cell. Also to make it run without a ReplaceAll so that the kernel is not needed and the function can be run using just the frontend.

这篇关于让 CellDingbat 在 Mathematica 会话之间记住它的状态的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆