<div class="gmail_quote">On Tue, May 8, 2012 at 3:10 PM, Dmitry Kazakov <span dir="ltr"><<a href="mailto:dimula73@gmail.com" target="_blank">dimula73@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">

<br><br><div class="gmail_quote"><div>On Mon, May 7, 2012 at 6:19 AM, Sven Langkamp <span dir="ltr"><<a href="mailto:sven.langkamp@gmail.com" target="_blank">sven.langkamp@gmail.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
<div class="gmail_quote"><br><div>Explanation:<br><br>Command: A command is contains basically two things: 1) an id string to identify the command 2) a KisPropertiesConfiguration that contains the parameters<br><br>Command Widget: That's the ui for the command like the current dialog, but closer the filter widgets (and paintop options). It writes the input of the UI into the KisPropertiesConfiguration like we do for filter. Then the command is send to the command switch.<br>



<br>Command switch: This is like a normal network switch. A command comes in and the switch looks at the id and passes it to the command runner that is associated with the id of the command. It's also a big registry for command runners, which are registered by Krita or plugins.<br>



<br>Command runner: The class or plugin that executes the command.<br></div></div></blockquote></div><div><br>Actualy, this fits very well into the idea of the strokes framework. We just need to expand it to cover the usecase of recording as well, because this usecase was taken into account during for its design. [1]<br>


<br>The "command switch" may be a couple of a stroke strategy factory and the registry where it is stored, while the "command runner" is the stroke framework itself.<br><br>To implement the recording based on strokes framework we just need to implement 3+3 factory classes for the strokes we have and for their stroke jobs and write toXML/fromXML methods for the stroke strategies. It's not too difficult. After that the update scheduler would be able to record everything we do.<br>


<br>Although there are two complications. <br><br>The first one is related to the fact that we need to save the contents of QUndoCommand somehow.<br><br>The second one is related to the complex tasks like "Resize Image". Currently, to do this job we use KisProcessingApplicator, which creates all the strokes and stroke jobs for us and eases our lives. This is, of course, cool but the problem is that it creates the jobs (and QUndoCommands) asynchronously in the context of the caller thread. It means that it also fetches the data about the image asynchronously, which may be wrong because some strokes may be changing the image concurrently [2].<br>


<br><br>As a solution for the first  problem we can just add toXML/fromXML methods to all the commands we have and make KisStrokeStrategyUndoCommandBased and its factory fetch this information. This appreach allows us to port all the actions to strokes very easily, but it doesn't handle the first problem in any way. More than that, the saved actions may become too low-level for being dealt in the recording actions editor effectively, so this should be thought over.<br>


<br>The second problem should be dealt in the factories. That is they 
shouldn't allow opening "Resize Image" dialog until all the actions in 
the scheduler are finished. The factories for most of the actions can 
use KisProcessingApplicator internally. <br>

<br><br>[1] - <a href="http://community.kde.org/Krita/Recording_System" target="_blank">http://community.kde.org/Krita/Recording_System</a><br>[2] - See QEXPECT_FAIL comment in the unittest:  KisSelectionManagerTest::testResizeToSelection()<span><font color="#888888"><br>

</font></span></div></div></blockquote><div><br>The commands at I was talking about are not QUndoCommands. It's also not on the same level as the strokes framework.<br><br>QUndoCommand is too low-level. Action might map undo commands that are missing information that is needed for recording e.g. the selection tools use a normal transaction. Beside that I don't want to add xml loading and saving code to every undo command.<br>
<br>Runners are on a much higher level than the strokes framework. For example a possible runner could be the current KisLayerManager.<br><br>For example if you want to scale a layer:<br>1) Dialog saves the values into a KisPropertiesConfiguration of a command, id is set to e.g. "scaleLayer"<br>
2) Command is then send to the "command switch", that looks at the and looks up the runner for id "scaleLayer"<br>3) Command is then send to the KisLayerManager, which reads command id "scaleLayer" from which is knows the function to call and the values to read<br>
4) KisLayerManager reads the values and calls KisLayerManager::scaleLayer<br><br>Recording happens in step 2, when the command goes through the "command switch". Recording can't happen in step 4 as we have just transactions at that point and no information about the original dialog values anymore.<br>

</div></div>