littlewhitecloud / TkTerminal

A terminal emulator widget written in Python using tkinter
MIT License
15 stars 2 forks source link

Add a tag to stop user from editing anything. #27

Open littlewhitecloud opened 1 year ago

littlewhitecloud commented 1 year ago

I was testing the widget and I found we can edit the output and the path. Then the widget became what a mess. I through a simple solution to fix it:

Moosems commented 1 year ago

I had fixed that with the left right up commands...

littlewhitecloud commented 1 year ago

littlewhitecloud commented 1 year ago

But I can still delete things.

littlewhitecloud commented 1 year ago

image image

Moosems commented 1 year ago

There's nothing gone.....

littlewhitecloud commented 1 year ago

6, image

littlewhitecloud commented 1 year ago

Actally, the left right up commands has problem, If I choose the text and press delete, it will still delete.

Moosems commented 1 year ago

So clicking needs a bind.

littlewhitecloud commented 1 year ago

Is there a way to give a readonly tag?

littlewhitecloud commented 1 year ago

So clicking needs a bind.

I prefer use a tag to set the text above it read only.

Moosems commented 1 year ago

There's no built in way but I can create one.

littlewhitecloud commented 1 year ago

There's no built in way but I can create one.

WOW! How?

Moosems commented 1 year ago

Bind all keypresses and button clicks and determine if the end result would be on top of any of the tag ranges. If it is, cancel the action otherwise allow it. Up and down get special treatment.

littlewhitecloud commented 1 year ago

Bind all keypresses and button clicks and determine if the end result would be on top of any of the tag ranges. If it is, cancel the action otherwise allow it. Up and down get special treatment.

Good idea, but bind a lot maybe make the program slow.

Moosems commented 1 year ago

It'll be fast enough :).

Moosems commented 1 year ago

@littlewhitecloud I'm going to do a ton of work tomorrow on the repo (eastern time US) so buckle up :D.

littlewhitecloud commented 1 year ago

@littlewhitecloud I'm going to do a ton of work tomorrow on the repo (eastern time US) so buckle up :D.

So I think We should split it out from the improve pr, create a new one and starting our trip :)

Moosems commented 1 year ago

from tkinter import Tk, Text, Event

root = Tk()
txt = Text(root)
txt.pack()

txt.tag_configure("important")

txt.insert("1.0", "Hello, World!")
txt.tag_add("important", "1.0", "1.5")
# written on phone so there may be syntax errors

def check_important(event: Event) -> None:
    # Things to check:
    # Is the text that would be gone to by typing on the same line and to the right of anything important?
    # Are we selecting stuff? In most terminals, that shouldn't even be allowed.
    # If it's a click event, is the clicked char important?
    # If any of these fail, we should return "break"
    widget = event.widget
    if widget.tag_ranges("sel"):
        widget.tag_remove("sel", "1.0", "end")
    # Determine the action (click or keypress)
    # Keypress check for a few things: is it backspace (check if previous character is a special one, up or down which inserts that line, return creates a new line and runs the code, and all modified ones like control/command-a and blocks those)
    # Clicks check for the index of the click and if it is inside one of the special we just bring it to the start of the non special chars

    important_ranges: list[tuple[str]] = widget.tag_ranges("important")
    if event.type == 4:
        # The type is a click
        click_index: str = widget.index(f"@{event.x},{event.y}).split(".")[1]
        end_line = widget.index("end-1c").split(".")[0]
        check_index = f"{end_line}.{click_index}"
        if "important" in widget.tag_names(check_index):
            # Wants to click on an important char
            # Put the cursor in the first non-important space (Len of working dir)
            ...
        return
    # The type is a keypress
    # Use keysym ("Left", "Up", "Return", "BackSpace", something for contmand-a (keysym and key combo), command-arrow, control-arrow, list is here: https://www.tcl.tk/man/tcl8.6/TkCmd/keysyms.html)
    return_keysym = 65293
    left_keysym = 65361
    right_keysym = 65363
    backspace_keysym = 
    ...

txt.bind("<Key>", check_important, add=True)
txt.bind("<Button-1>", check_important, add=True)

root.mainloop()
Moosems commented 1 year ago

@littlewhitecloud, I am still working on this from my phone but here's an update.

littlewhitecloud commented 1 year ago
# Edit it on iPad, maybe have a lot of typo
self.cursor = 0
self.text.bind(“Left”, self._left)
self.text.bind(“Right”, self._right)
self.text.bind(“Click”, self._click)
# maybe merge them into one function
def _left(self, event):
    self.cursor -= 1
    if self.cursor < 0:
       self.text[“state”] = “readonly”

def _right(self, event):
    self.index += 1
    if self.index > 0:
        self.text[“state”] = “normal”

def _click(self, event):
    self.index = #cursor index
    if self.index < 0 and self.text[“state”] == “normal”:
         self.text[“state”] = “readonly”
    elif self.index > 0 and self.text[“state”] == “readonly”:
         self.text[“state”] = “normal”
littlewhitecloud commented 1 year ago

My form, but still have a lot of logic problem, fix it later.

Moosems commented 1 year ago

Clear also needs to be a special command for typing.

littlewhitecloud commented 1 year ago

find a new and better way to improve it.

    def updates(self, _: Event) -> None:
        """Update cursor"""
        self.cursor = self.text.index("insert")
        if float(self.cursor) < float(self.latest):
            self.text.bind("<KeyPress>", self.eat, True)
            self.text.bind("<KeyPress-BackSpace>", self.eat, True)
        elif float(self.cursor) >= float(self.latest):
            self.text.unbind("<Key>")
            self.text.unbind("<KeyPress-Backspace>")

    def eat(self, _: Event) -> str:
        """Just eat"""
        return "break"
Moosems commented 1 year ago

Mine should be able to be put in a duct allowing for better handling. I'll need to finish the handler but I have a feeling it will work well.

littlewhitecloud commented 1 year ago

Mine should be able to be put in a duct allowing for better handling. I'll need to finish the handler but I have a feeling it will work well.

How long will it take to finish it?

littlewhitecloud commented 1 year ago

If it still take a long time, maybe we should fix it in another pr. Just use mine version as a temp solution. When you are finished, we can remove mine can replace with your solution.

Moosems commented 1 year ago

Yeah. I'd merge the PR and when I have a free week I'll make a big update PR.