This file is indexed.

/usr/share/pyspread/src/model/unredo.py is in pyspread 0.3.3-1.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
#!/usr/bin/env python
# -*- coding: utf-8 -*-

# Copyright Martin Manns
# Distributed under the terms of the GNU General Public License

# --------------------------------------------------------------------
# pyspread is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# pyspread is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with pyspread.  If not, see <http://www.gnu.org/licenses/>.
# --------------------------------------------------------------------

"""

UnRedo
======

UnRedo contains the UnRedo class that manages undo and redo operations.

"""

from src.config import config


class UnRedo(object):
    """Undo/Redo framework class.

    For each undo-able operation, the undo/redo framework stores the
    undo operation and the redo operation. For each step, a 4-tuple of:
    1) the function object that has to be called for the undo operation
    2) the undo function parameters as a list
    3) the function object that has to be called for the redo operation
    4) the redo function parameters as a list
    is stored.

    One undo step in the application can comprise of multiple operations.
    Undo steps are separated by the string "MARK".

    The attributes should only be written to by the class methods.

    Attributes
    ----------
    undolist: List
    \t
    redolist: List
    \t
    active: Boolean
    \tTrue while an undo or a redo step is executed.

    """

    def __init__(self):
        """[(undofunc, [undoparams, ...], redofunc, [redoparams, ...]),
        ..., "MARK", ...]
        "MARK" separartes undo/redo steps

        """

        self.undolist = []
        self.redolist = []
        self.active = False

    def mark(self):
        """Inserts a mark in undolist and empties redolist"""

        if self.undolist and self.undolist[-1] != "MARK":
            self.undolist.append("MARK")

    def undo(self):
        """Undos operations until next mark and stores them in the redolist"""

        self.active = True

        while self.undolist and self.undolist[-1] == "MARK":
            self.undolist.pop()

        if self.redolist and self.redolist[-1] != "MARK":
            self.redolist.append("MARK")

        while self.undolist:
            step = self.undolist.pop()
            self.redolist.append(step)
            if step == "MARK":
                break
            step[0](*step[1])

        self.active = False

    def redo(self):
        """Redos operations until next mark and stores them in the undolist"""

        self.active = True

        while self.redolist and self.redolist[-1] == "MARK":
            self.redolist.pop()

        if self.undolist and self.undolist[-1] != "MARK":
            self.undolist.append("MARK")

        while self.redolist:
            step = self.redolist.pop()
            if step == "MARK":
                break
            self.undolist.append(step)
            step[2](*step[3])

        self.active = False

    def reset(self):
        """Empties both undolist and redolist"""

        self.__init__()

    def append(self, undo_operation, operation):
        """Stores an operation and its undo operation in the undolist

        undo_operation: (undo_function, [undo_function_attribute_1, ...])
        operation: (redo_function, [redo_function_attribute_1, ...])

        """

        if self.active:
            return False

        # If the lists grow too large they are emptied
        if len(self.undolist) > config["max_unredo"] or \
           len(self.redolist) > config["max_unredo"]:
            self.reset()

        # Check attribute types
        for unredo_operation in [undo_operation, operation]:
            iter(unredo_operation)
            assert len(unredo_operation) == 2
            assert hasattr(unredo_operation[0], "__call__")
            iter(unredo_operation[1])

        if not self.active:
            self.undolist.append(undo_operation + operation)

# End of class UnRedo