fio :как написать 2X емкость пользователя?

Ты!!! Мне удалось написать скрипт на Python, который возвращает мне нагрузку на новое виртуальное устройство :-D Теперь я могу использовать его с Gimp/Krita/... Осталось только написать правильный драйвер C и загрузить прямо в ядре... Если у вас есть идеи, дайте мне знать!

Доказательство:

enter image description here

Таким образом, идея скрипта состоит в том, чтобы прочитать ввод из файла событий графического планшета, а затем создать хорошие события (не более BTN_LEFT, а BTN_TOUCHвместо этого... см. мой другой вопрос/ответ здесь для более подробной информации ).

Чтобы запустить скрипт (, см. ниже ), сохраните его в папке combine_both.pyи сделайте его исполняемым/установите deps:

$ chmod +x combine_both.py
$ sudo pip3 install libevdev

Затем проверьте доступные устройства ввода:

$ xinput list

Это должно дать вам несколько записей, среди них одна запись типа

VEIKK.INC A30 Mouse                       id=12   [slave  pointer  (2)]

Обратите внимание на идентификатор (, отмеченный как позже ), а также идентификатор указателя виртуального ядра:

Virtual core pointer                          id=2    [master pointer  (3)]

Затем вам нужно знать, какой /dev/input/eventXфайл выбрать, проще всего запустить sudo evtestи прочитать имя файла, соответствующего VEIKK.INC A30 Mouse. Затем запустите скрипт с этим файлом в качестве аргумента, как в:

sudo./combine_both.py /dev/input/event7

Этот скрипт должен выводить информацию, когда вы пытаетесь щелкнуть или переместить устройство. Кроме того, в xinput listтакже должно быть указано это устройство с именем Tablet alone Pen (0)и идентификатором , а xinput test должно дать вам что-то вроде (обратите внимание на 3 столбца для x/y/давления):

$ xinput test 21
[...]
motion a[0]=4151295 a[1]=4151295 a[2]=241 
motion a[0]=4060671 a[1]=4060671 a[2]=226 
motion a[0]=3969535 a[1]=3969535 a[2]=211 
motion a[0]=3878399 a[1]=3878399 a[2]=196 
motion a[0]=3787775 a[1]=3787775 a[2]=181 
motion a[0]=3696639 a[1]=3696639 a[2]=166 
motion a[0]=3605503 a[1]=3605503 a[2]=151 
motion a[0]=3514879 a[1]=3514879 a[2]=137 
motion a[0]=3423743 a[1]=3423743 a[2]=122 
motion a[0]=3332607 a[1]=3332607 a[2]=107 
motion a[0]=3241983 a[1]=3241983 a[2]=92 
motion a[0]=3150847 a[1]=3150847 a[2]=77 
motion a[0]=3059711 a[1]=3059711 a[2]=62 
motion a[0]=2969087 a[1]=2969087 a[2]=47 
motion a[0]=2877951 a[1]=2877951 a[2]=32 
motion a[0]=2650623 a[1]=2650623 a[2]=17 
button release 1

Теперь, чтобы заставить его работать с Gimp/Krita, вы хотите отключить настоящую мышь (, иначе у вас будут конфликты между настоящим и поддельным планшетом ), с

xinput float 

и когда вы закончите, вы можете снова подключить реальное устройство с помощью

xinput reattach  

В gimp не забудьте настроить Tablet alone Pen (0)на mode=screenв Edit/input devicesи убедитесь, что реальный планшет VEIKK.INC A30 Mouseотключен. Наконец, выбрал хорошую динамику, например Pencil Genericдля теста!

Наслаждайтесь!(и я дам вам знать, если в какой-то момент напишу драйвер C)

Скрипт:

#!/usr/bin/env python3
import sys
import libevdev
import datetime
import time


def print_capabilities(l):
    v = l.driver_version
    print("Input driver version is {}.{}.{}".format(v >> 16, (v >> 8) & 0xff, v & 0xff))
    id = l.id
    print("Input device ID: bus {:#x} vendor {:#x} product {:#x} version {:#x}".format(
        id["bustype"],
        id["vendor"],
        id["product"],
        id["version"],
    ))
    print("Input device name: {}".format(l.name))
    print("Supported events:")

    for t, cs in l.evbits.items():
        print("  Event type {} ({})".format(t.value, t.name))

        for c in cs:
            if t in [libevdev.EV_LED, libevdev.EV_SND, libevdev.EV_SW]:
                v = l.value[c]
                print("    Event code {} ({}) state {}".format(c.value, c.name, v))
            else:
                print("    Event code {} ({})".format(c.value, c.name))

            if t == libevdev.EV_ABS:
                a = l.absinfo[c]
                print("       {:10s} {:6d}".format('Value', a.value))
                print("       {:10s} {:6d}".format('Minimum', a.minimum))
                print("       {:10s} {:6d}".format('Maximum', a.maximum))
                print("       {:10s} {:6d}".format('Fuzz', a.fuzz))
                print("       {:10s} {:6d}".format('Flat', a.flat))
                print("       {:10s} {:6d}".format('Resolution', a.resolution))

    print("Properties:")
    for p in l.properties:
        print("  Property type {} ({})".format(p.value, p.name))


def print_event(e):
        print("Event: time {}.{:06d}, ".format(e.sec, e.usec), end='')
        if e.matches(libevdev.EV_SYN):
            if e.matches(libevdev.EV_SYN.SYN_MT_REPORT):
                print("++++++++++++++ {} ++++++++++++".format(e.code.name))
            elif e.matches(libevdev.EV_SYN.SYN_DROPPED):
                print(">>>>>>>>>>>>>> {} >>>>>>>>>>>>".format(e.code.name))
            else:
                print("-------------- {} ------------".format(e.code.name))
        else:
            print("type {:02x} {} code {:03x} {:20s} value {:4d}".format(e.type.value, e.type.name, e.code.value, e.code.name, e.value))


class Tablet():
    def __init__(self, tablet_name):
        self.tablet_name = tablet_name

    def __enter__(self):
        self.dev = libevdev.Device()
        self.dev.name = "Tablet alone"
        ### NB: all the following information needs to be enabled
        ### in order to recognize the device as a tablet.
        # Say that the device will send "absolute" values
        self.dev.enable(libevdev.INPUT_PROP_DIRECT)
        # Say that we are using the pen (not the erasor), and should be set to 1 when we are at proximity to the device.
        # See http://www.infradead.org/~mchehab/kernel_docs_pdf/linux-input.pdf page 9 (=13) and guidelines page 12 (=16), or the https://github.com/linuxwacom/input-wacom/blob/master/4.5/wacom_w8001.c (rdy=proximity)
        self.dev.enable(libevdev.EV_KEY.BTN_TOOL_PEN)
        self.dev.enable(libevdev.EV_KEY.BTN_TOOL_RUBBER)
        # Click
        self.dev.enable(libevdev.EV_KEY.BTN_TOUCH)
        # Press button 1 on pen
        self.dev.enable(libevdev.EV_KEY.BTN_STYLUS)
        # Press button 2 on pen, see great doc
        self.dev.enable(libevdev.EV_KEY.BTN_STYLUS2)
        # Send absolute X coordinate
        self.dev.enable(libevdev.EV_ABS.ABS_X,
                        libevdev.InputAbsInfo(minimum=0, maximum=32767, resolution=100))
        # Send absolute Y coordinate
        self.dev.enable(libevdev.EV_ABS.ABS_Y,
                        libevdev.InputAbsInfo(minimum=0, maximum=32767, resolution=100))
        # Send absolute pressure
        self.dev.enable(libevdev.EV_ABS.ABS_PRESSURE,
                        libevdev.InputAbsInfo(minimum=0, maximum=8191))
        # Use to confirm that we finished to send the informations
        # (to be sent after every burst of information, otherwise
        # the kernel does not proceed the information)
        self.dev.enable(libevdev.EV_SYN.SYN_REPORT)
        # Report buffer overflow
        self.dev.enable(libevdev.EV_SYN.SYN_DROPPED)
        self.uinput = self.dev.create_uinput_device()
        print("New device at {} ({})".format(self.uinput.devnode, self.uinput.syspath))
        # Sleep for a bit so udev, libinput, Xorg, Wayland,...
        # all have had a chance to see the device and initialize
        # it. Otherwise the event will be sent by the kernel but
        # nothing is ready to listen to the device yet. And it
        # will never be detected in the futur ;-)
        time.sleep(1)
        # self.simulate_first_click()
        self.reset_state()
        return self

    def __exit__(self, type, value, traceback):
        pass

    def reset_state(self):
        self.is_away = True
        self.is_touching = False
        self.pressed_button_1 = False
        self.pressed_button_2 = False
        self.lastmodif = datetime.datetime.now()

    def send_events(self, events, is_away=False):
        self.lastmodif = datetime.datetime.now()
        self.is_away = is_away
        self.uinput.send_events(events)

    def simulate_first_click(self):
        """Useful only the first time to make sure
        xinput detected the input"""
        # Reports that the PEN is close to the surface
        # Important to make sure xinput can detect (and list)
        # the pen. Otherwise, it won't write anything in gimp.
        self.uinput.send_events([
            libevdev.InputEvent(libevdev.EV_KEY.BTN_TOUCH,
                                value=0),
            libevdev.InputEvent(libevdev.EV_KEY.BTN_TOOL_PEN,
                                value=1),
            libevdev.InputEvent(libevdev.EV_SYN.SYN_REPORT,
                                value=0),
        ])
        # Says that the pen it out of range of the tablet. Useful
        # to make sure you can move your mouse, and to avoid
        # strange things during the first draw.
        self.uinput.send_events([
            libevdev.InputEvent(libevdev.EV_KEY.BTN_TOUCH,
                                value=0),
            libevdev.InputEvent(libevdev.EV_KEY.BTN_TOOL_PEN,
                                value=0),
            libevdev.InputEvent(libevdev.EV_SYN.SYN_REPORT,
                                value=0),
        ])


    def send_state_no_pos(self, is_away=False):
        self.lastmodif = datetime.datetime.now()
        self.is_away = is_away
        print("Away: {}, Touching: {}".format(self.is_away, self.is_touching))
        self.uinput.send_events([
            libevdev.InputEvent(libevdev.EV_KEY.BTN_TOUCH,
                                value=1 if self.is_touching else 0),
            libevdev.InputEvent(libevdev.EV_KEY.BTN_TOOL_PEN,
                                value=1 if not self.is_away else 0),
            libevdev.InputEvent(libevdev.EV_KEY.BTN_STYLUS,
                                value=1 if self.pressed_button_1 else 0),
            libevdev.InputEvent(libevdev.EV_KEY.BTN_STYLUS2,
                                value=1 if self.pressed_button_2 else 0),
            libevdev.InputEvent(libevdev.EV_SYN.SYN_REPORT,
                                value=0),
        ])


    def touch_press(self):
        self.is_touching = True
        self.send_state_no_pos()

    def touch_release(self):
        self.is_touching = False
        self.send_state_no_pos()

    def button_1_press(self):
        self.pressed_button_1 = True
        self.send_state_no_pos()

    def button_1_release(self):
        self.pressed_button_1 = False
        self.send_state_no_pos()

    def button_2_press(self):
        self.pressed_button_2 = True
        self.send_state_no_pos()

    def button_2_release(self):
        self.pressed_button_2 = False
        self.send_state_no_pos()

    def move_x(self, abs_x):
        self.send_events([
            libevdev.InputEvent(libevdev.EV_ABS.ABS_X,
                                value=abs_x),
            libevdev.InputEvent(libevdev.EV_SYN.SYN_REPORT,
                                value=0),
        ])

    def move_y(self, abs_y):
        self.send_events([
            libevdev.InputEvent(libevdev.EV_ABS.ABS_Y,
                                value=abs_y),
            libevdev.InputEvent(libevdev.EV_SYN.SYN_REPORT,
                                value=0),
        ])

    def change_pressure(self, pressure):
        self.send_events([
            libevdev.InputEvent(libevdev.EV_ABS.ABS_PRESSURE,
                                value=pressure),
            libevdev.InputEvent(libevdev.EV_SYN.SYN_REPORT,
                                value=0),
        ])

    def handle_event(self, e):
        if e.matches(libevdev.EV_ABS.ABS_PRESSURE):
            self.change_pressure(e.value)
        elif e.matches(libevdev.EV_ABS.ABS_X):
            self.move_x(e.value)
        elif e.matches(libevdev.EV_ABS.ABS_Y):
            self.move_y(e.value)
        elif e.matches(libevdev.EV_KEY.BTN_LEFT):
            if e.value == 1:
                self.touch_press()
            else:
                self.touch_release()
        elif e.matches(libevdev.EV_SYN.SYN_REPORT):
            pass
        else:
            print("Unkown event:")
            print_event(e)



def main(args):
    path = args[1]
    try:
        with Tablet("Tablet alone") as tablet:
            ### Read the events from real graphics tablet
            with open(path, "rb") as fd:
                l = libevdev.Device(fd)
                print_capabilities(l)
                print("################################\n"
                      "#      Waiting for events      #\n"
                      "################################")
                while True:
                    try:
                        ev = l.events()
                        for e in ev:
                            print_event(e)
                            tablet.handle_event(e)
                    except libevdev.EventsDroppedException:
                        for e in l.sync():
                            print_event(e)
                            tablet.handle_event(e)
    except KeyboardInterrupt:
        pass
    except IOError as e:
        import errno
        if e.errno == errno.EACCES:
            print("Insufficient permissions to access {}".format(path))
        elif e.errno == errno.ENOENT:
            print("Device {} does not exist".format(path))
        else:
            raise e
    except OSError as e:
        print(e)


if __name__ == "__main__":
    if len(sys.argv) != 2:
        print("Usage: sudo {} /dev/input/eventX".format(sys.argv[0]))
        print(" $ sudo evtest")
        print("can help you to know which file to use.")
        sys.exit(1)
    main(sys.argv)

0
11.07.2020, 18:51
1 ответ

Вы не сможете получить доступ ко всему пространству SSD, так как у вас есть файловая система поверх него, которая, в свою очередь, может иметь ограничения на пространство, доступное для файлов. Вам нужно будет посмотреть на фактическое доступное пространство с помощью чего-то вроде dfи работать с этим числом (, и даже некоторые из них могут быть недоступны, поэтому вам может потребоваться использовать что-то меньшее ).

Если вам на самом деле не нужны четыре задания, вы можете обойтись созданием одного файла с помощью fill_fs=1, а затем использовать loops=2...

Предупреждение:Из этого следует, что запуск вашей основной файловой системы (, которая используется для журналов и т. д. )из-за нехватки места, плохо влияет на работоспособность вашей системы...

0
18.03.2021, 23:20

Теги

Похожие вопросы