{"id":21145,"date":"2024-01-25T12:16:21","date_gmt":"2024-01-25T05:16:21","guid":{"rendered":"https:\/\/www.makeriot2020.com\/?p=21145"},"modified":"2024-01-25T12:16:27","modified_gmt":"2024-01-25T05:16:27","slug":"xiao-rp2040-mouse-ver-3-0","status":"publish","type":"post","link":"https:\/\/www.makeriot2020.com\/index.php\/2024\/01\/25\/xiao-rp2040-mouse-ver-3-0\/","title":{"rendered":"XIAO RP2040 Mouse Ver 3.0"},"content":{"rendered":"\n<figure class=\"wp-block-image size-large\"><img decoding=\"async\" width=\"814\" height=\"1024\" data-src=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-814x1024.jpeg\" alt=\"\" class=\"wp-image-21147 lazyload\" data-srcset=\"https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-814x1024.jpeg 814w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-238x300.jpeg 238w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-768x966.jpeg 768w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478.jpeg 1003w\" data-sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 984px) 61vw, (max-width: 1362px) 45vw, 600px\" src=\"data:image\/svg+xml;base64,PHN2ZyB3aWR0aD0iMSIgaGVpZ2h0PSIxIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjwvc3ZnPg==\" style=\"--smush-placeholder-width: 814px; --smush-placeholder-aspect-ratio: 814\/1024;\" \/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<p>Over the last few months, We have been steadily improving the design of our XIAO RP2040-based mouse device. With this, ver 3.0 all the hardware bugs were finally eliminated, and we also placed the device into its first-ever enclosure.<br><br>Let us take a look at the design<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">The PCB and Schematic<\/h2>\n\n\n\n<figure class=\"wp-block-image size-large\"><img decoding=\"async\" width=\"1024\" height=\"957\" data-src=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_172917-scaled-e1706157982464-1024x957.jpg\" alt=\"\" class=\"wp-image-21156 lazyload\" data-srcset=\"https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_172917-scaled-e1706157982464-1024x957.jpg 1024w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_172917-scaled-e1706157982464-300x280.jpg 300w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_172917-scaled-e1706157982464-768x718.jpg 768w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_172917-scaled-e1706157982464-1200x1122.jpg 1200w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_172917-scaled-e1706157982464.jpg 1442w\" data-sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 1362px) 62vw, 840px\" src=\"data:image\/svg+xml;base64,PHN2ZyB3aWR0aD0iMSIgaGVpZ2h0PSIxIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjwvc3ZnPg==\" style=\"--smush-placeholder-width: 1024px; --smush-placeholder-aspect-ratio: 1024\/957;\" \/><\/figure>\n\n\n\n<p><br>The PCB is a very strange shape, with lots of cut-outs. This is to accommodate the big push buttons that will be mounted in the enclosure, as well as to fit nicely into the mounting area of the enclosure&#8230; This design took quite some time with a pair of callipers and CAD, but all went well, and the shape is perfectly accurate. <\/p>\n\n\n\n<div data-wp-interactive=\"core\/file\" class=\"wp-block-file\"><object data-wp-bind--hidden=\"!state.hasPdfPreview\" hidden class=\"wp-block-file__embed\" data=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/Schematic_RemoteMouse_2024-01-25.pdf\" type=\"application\/pdf\" style=\"width:100%;height:600px\" aria-label=\"Embed of Schematic_RemoteMouse_2024-01-25.\"><\/object><a id=\"wp-block-file--media-a1f616fc-0bec-44ed-84fa-68c015549edf\" href=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/Schematic_RemoteMouse_2024-01-25.pdf\">Schematic_RemoteMouse_2024-01-25<\/a><a href=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/Schematic_RemoteMouse_2024-01-25.pdf\" class=\"wp-block-file__button wp-element-button\" download aria-describedby=\"wp-block-file--media-a1f616fc-0bec-44ed-84fa-68c015549edf\">Download<\/a><\/div>\n\n\n\n<p><br>The schematic is also straight forward, with the only real changes begin to the rotary encoder. In ver 2.0, We connected the encoder to the MCP23008, but for some reason CircuitPython does not seem to like an encoder connected to an IO extender&#8230; That forced us to do some software hack to use the encoder&#8230; I have thus decided to change things around in ver 3.0 and move the encoder back to the native GPIO on the XIAO RP2040<\/p>\n\n\n\n<p>It is also interesting to note that the circuit was initially designed for the XIAO ESP32S3, but due to issues with stock, as well as crazy prices on local parts, we  made a quick turn-around and went back to the RP2040. The ESP32S3 was going to allow us to implement a wireless device, through using ESPNow protocol&#8230; That may still be done in future, but for now, I think we have done enough work on the mouse device for the time being&#8230;<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Manufacturing the PCB and Assembly<\/h2>\n\n\n\n<p>I choose <a href=\"https:\/\/www.pcbway.com\/?from=makeriot2022\" target=\"_blank\" rel=\"noreferrer noopener\">PCBWay<\/a> for my PCB manufacturing. Why? What makes them different from the rest?<br><br><a href=\"https:\/\/www.pcbway.com\/?from=makeriot2022\" target=\"_blank\" rel=\"noreferrer noopener\">PCBWay<\/a>\u2018s business goal is to be the most professional PCB manufacturer for prototyping and low-volume production work in the world. With more than a decade in the business, they are committed to meeting the needs of their customers from different industries in terms of quality, delivery, cost-effectiveness and any other demanding requests. As one of the most experienced PCB manufacturers and SMT Assemblers in China, they pride themselves to be our (the Makers) best business partners, as well as good friends in every aspect of our PCB manufacturing needs. They strive to make our R&amp;D work easy and hassle-free.<br><br>How do they do that?<br><br><strong>PCBWay is NOT a broker. <\/strong>That means that they do all manufacturing and assembly themselves, cutting out all the middlemen, and saving us money.<br><br><strong>PCBWay\u2019s online quoting system<\/strong> gives a very detailed and accurate picture of all costs upfront, including components and assembly costs. This saves a lot of time and hassle.<\/p>\n\n\n\n<p><strong>PCBWay gives you one-on-one customer support,<\/strong> that answers you in 5 minutes ( from the Website chat ), or by email within a few hours ( from your personal account manager). Issues are really resolved very quickly, not that there are many anyway, but, as we are all human, it is nice to know that when a gremlin rears its head, you have someone to talk to who will do his\/her best to resolve your issue as soon as possible.<\/p>\n\n\n\n<p>Find out more <a href=\"https:\/\/www.pcbway.com\/why.html?from=makeriot2022\" target=\"_blank\" rel=\"noreferrer noopener\">here<\/a><\/p>\n\n\n\n<figure class=\"wp-block-image size-full\"><a href=\"https:\/\/www.pcbway.com\/?from=makeriot2022\"><img decoding=\"async\" width=\"600\" height=\"120\" data-src=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/image.png\" alt=\"\" class=\"wp-image-21166 lazyload\" data-srcset=\"https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/image.png 600w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/image-300x60.png 300w\" data-sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 984px) 61vw, (max-width: 1362px) 45vw, 600px\" src=\"data:image\/svg+xml;base64,PHN2ZyB3aWR0aD0iMSIgaGVpZ2h0PSIxIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjwvc3ZnPg==\" style=\"--smush-placeholder-width: 600px; --smush-placeholder-aspect-ratio: 600\/120;\" \/><\/a><\/figure>\n\n\n\n<p><br>Assembly was quite easy, I chose to use a stencil, because the IO Expander chip has a very tiny footprint, as well as a leadless package&#8230; The stencil definitely helps prevent excessive solder paste, as well as saves a lot of time on reworking later&#8230;<\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img decoding=\"async\" width=\"826\" height=\"1024\" data-src=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_173124-scaled-e1706158929594-826x1024.jpg\" alt=\"\" class=\"wp-image-21155 lazyload\" data-srcset=\"https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_173124-scaled-e1706158929594-826x1024.jpg 826w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_173124-scaled-e1706158929594-242x300.jpg 242w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_173124-scaled-e1706158929594-768x952.jpg 768w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_173124-scaled-e1706158929594-1239x1536.jpg 1239w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_173124-scaled-e1706158929594-1200x1487.jpg 1200w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_173124-scaled-e1706158929594.jpg 1442w\" data-sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 984px) 61vw, (max-width: 1362px) 45vw, 600px\" src=\"data:image\/svg+xml;base64,PHN2ZyB3aWR0aD0iMSIgaGVpZ2h0PSIxIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjwvc3ZnPg==\" style=\"--smush-placeholder-width: 826px; --smush-placeholder-aspect-ratio: 826\/1024;\" \/><\/figure>\n\n\n\n<p><\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img decoding=\"async\" width=\"1024\" height=\"576\" data-src=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_175922-1024x576.jpg\" alt=\"\" class=\"wp-image-21151 lazyload\" data-srcset=\"https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_175922-1024x576.jpg 1024w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_175922-300x169.jpg 300w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_175922-768x432.jpg 768w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_175922-1536x864.jpg 1536w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_175922-2048x1152.jpg 2048w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/20240120_175922-1200x675.jpg 1200w\" data-sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 1362px) 62vw, 840px\" src=\"data:image\/svg+xml;base64,PHN2ZyB3aWR0aD0iMSIgaGVpZ2h0PSIxIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjwvc3ZnPg==\" style=\"--smush-placeholder-width: 1024px; --smush-placeholder-aspect-ratio: 1024\/576;\" \/><\/figure>\n\n\n\n<figure class=\"wp-block-image size-large\"><img decoding=\"async\" width=\"647\" height=\"1024\" data-src=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_1092099965149834-e1706159186333-647x1024.jpeg\" alt=\"\" class=\"wp-image-21146 lazyload\" data-srcset=\"https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_1092099965149834-e1706159186333-647x1024.jpeg 647w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_1092099965149834-e1706159186333-189x300.jpeg 189w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_1092099965149834-e1706159186333-768x1216.jpeg 768w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_1092099965149834-e1706159186333-970x1536.jpeg 970w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_1092099965149834-e1706159186333.jpeg 1004w\" data-sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 984px) 61vw, (max-width: 1362px) 45vw, 600px\" src=\"data:image\/svg+xml;base64,PHN2ZyB3aWR0aD0iMSIgaGVpZ2h0PSIxIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjwvc3ZnPg==\" style=\"--smush-placeholder-width: 647px; --smush-placeholder-aspect-ratio: 647\/1024;\" \/><\/figure>\n\n\n\n<p><br>In the picture above, we can clearly see why I had to design the PCB with such an irregular shape. <\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img decoding=\"async\" width=\"814\" height=\"1024\" data-src=\"http:\/\/makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-814x1024.jpeg\" alt=\"\" class=\"wp-image-21147 lazyload\" data-srcset=\"https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-814x1024.jpeg 814w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-238x300.jpeg 238w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478-768x966.jpeg 768w, https:\/\/www.makeriot2020.com\/wp-content\/uploads\/2024\/01\/received_361446036515344-e1706157508478.jpeg 1003w\" data-sizes=\"(max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 984px) 61vw, (max-width: 1362px) 45vw, 600px\" src=\"data:image\/svg+xml;base64,PHN2ZyB3aWR0aD0iMSIgaGVpZ2h0PSIxIiB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciPjwvc3ZnPg==\" style=\"--smush-placeholder-width: 814px; --smush-placeholder-aspect-ratio: 814\/1024;\" \/><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\">Firmware and Coding<\/h2>\n\n\n\n<p>We are still using CircuitPython for the firmware on this device. It is not perfect, but it works, well sort of anyway. What does that mean? Well&#8230; As far as the mouse functions are concerned, clicking, scrolling, moving the pointer &#8211; all of that is works perfectly, and thus allows me to use the device for basic operations every day. Drag and Drop, as well as selecting and or highlighting text DOES NOT work. This seem to be an issue with the HID code in Circuitpython, meaning it doesn&#8217;t seem to be implemented. It is also way beyond my abilities to implement it myself&#8230;<\/p>\n\n\n\n<p>Below is the code.py file, with the boot.py below that<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>\nimport time\nimport board\nimport busio\nfrom rainbowio import colorwheel\nimport neopixel\nimport rotaryio\nimport microcontroller\nfrom digitalio import Direction\nfrom adafruit_mcp230xx.mcp23008 import MCP23008\nimport digitalio\ni2c = busio.I2C(board.SCL, board.SDA)\nmcp = MCP23008(i2c)\n\n\nfrom analogio import AnalogIn\nimport usb_hid\nfrom adafruit_hid.mouse import Mouse\njoyX = board.A0\njoyY = board.A1\nJoyBtn = board.D2\n\nLeftBtn = 0\nCenterBtn = 1\nRightBtn = 2\nUpBtn = 3\nDownBtn = 4\nEncoderBtn = 5\n\n\nmouse = Mouse(usb_hid.devices)\nxAxis = AnalogIn(joyX)\nyAxis = AnalogIn(joyY)\n\n# NEOPIXEL\npixel_pin = board.NEOPIXEL\nnum_pixels = 1\npixels = neopixel.NeoPixel(pixel_pin, num_pixels, brightness=0.1, auto_write=False)\n\nleftbutton = mcp.get_pin(LeftBtn)\nleftbutton.direction = digitalio.Direction.INPUT\nleftbutton.pull = digitalio.Pull.UP\n\ncenterbutton = mcp.get_pin(CenterBtn)\ncenterbutton.direction = digitalio.Direction.INPUT\ncenterbutton.pull = digitalio.Pull.UP\n\nmaint_btn = digitalio.DigitalInOut(JoyBtn)\nmaint_btn.switch_to_input(pull=digitalio.Pull.UP)\n\nrightbutton = mcp.get_pin(RightBtn)\nrightbutton.direction = digitalio.Direction.INPUT\nrightbutton.pull = digitalio.Pull.UP\n\nenc_btn = mcp.get_pin(EncoderBtn)\nenc_btn.direction = digitalio.Direction.INPUT\nenc_btn.pull = digitalio.Pull.UP\n\nscroll_up = mcp.get_pin(UpBtn)\nscroll_up.direction = digitalio.Direction.INPUT\nscroll_up.pull = digitalio.Pull.UP\n\nscroll_down = mcp.get_pin(DownBtn)\nscroll_down.direction = digitalio.Direction.INPUT\nscroll_down.pull = digitalio.Pull.UP\n\n\n\nmousewheel = rotaryio.IncrementalEncoder(board.D6, board.D7, 4)\nlast_position = mousewheel.position\nprint(mousewheel.position)\n\nmove_speed = 3\nenc_down = 0\n\nRED = (255, 0, 0)\nYELLOW = (255, 150, 0)\nGREEN = (0, 255, 0)\nCYAN = (0, 255, 255)\nBLUE = (0, 0, 255)\nPURPLE = (180, 0, 255)\nBLACK = (0, 0, 0)\n\n\nif move_speed == 0:\n    in_min, in_max, out_min, out_max = (0, 65000, -20, 20)\n    filter_joystick_deadzone = (\n        lambda x: int((x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min)\n        if abs(x - 32768) > 500\n        else 0\n    )\nif move_speed == 1:\n    pixels.fill(GREEN)\n    pixels.show()\n    in_min, in_max, out_min, out_max = (0, 65000, -15, 15)\n    filter_joystick_deadzone = (\n        lambda x: int((x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min)\n        if abs(x - 32768) > 500\n        else 0\n    )\nif move_speed == 2:\n    pixels.fill(BLUE)\n    pixels.show()\n    in_min, in_max, out_min, out_max = (0, 65000, -10, 10)\n\n\nfilter_joystick_deadzone = (\n        lambda x: int((x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min)\n        if abs(x - 32768) > 500\n        else 0\n    )\nif move_speed == 3:\n    pixels.fill(PURPLE)\n    pixels.show()\n    in_min, in_max, out_min, out_max = (0, 65000, -8, 8)\n    filter_joystick_deadzone = (\n        lambda x: int((x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min)\n        if abs(x - 32768) > 500\n        else 0\n    )\nif move_speed == 4:\n    pixels.fill(CYAN)\n    pixels.show()\n    in_min, in_max, out_min, out_max = (0, 65000, -5, 5)\n    filter_joystick_deadzone = (\n        lambda x: int((x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min)\n        if abs(x - 32768) > 500\n        else 0\n    )\n\n\npixels.fill(BLACK)\npixels.show()\nwhile True:\n    # Set mouse accelleration ( speed)\n    #print(mousewheel.position)\n    if move_speed == 0:\n        pixels.fill(BLACK)\n        pixels.show()\n        in_min, in_max, out_min, out_max = (0, 65000, -20, 20)\n        filter_joystick_deadzone = (\n            lambda x: int(\n                (x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min\n            )\n            if abs(x - 32768) > 500\n            else 0\n        )\n    if move_speed == 1:\n        pixels.fill(GREEN)\n        pixels.show()\n        in_min, in_max, out_min, out_max = (0, 65000, -15, 15)\n        filter_joystick_deadzone = (\n            lambda x: int(\n                (x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min\n            )\n            if abs(x - 32768) > 500\n            else 0\n        )\n    if move_speed == 2:\n        pixels.fill(BLUE)\n        pixels.show()\n        in_min, in_max, out_min, out_max = (0, 65000, -10, 10)\n        filter_joystick_deadzone = (\n            lambda x: int(\n                (x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min\n            )\n            if abs(x - 32768) > 500\n            else 0\n        )\n    if move_speed == 3:\n        pixels.fill(PURPLE)\n        pixels.show()\n        in_min, in_max, out_min, out_max = (0, 65000, -8, 8)\n        filter_joystick_deadzone = (\n            lambda x: int(\n                (x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min\n            )\n            if abs(x - 32768) > 500\n            else 0\n        )\n    if move_speed == 4:\n        pixels.fill(CYAN)\n        pixels.show()\n        in_min, in_max, out_min, out_max = (0, 65000, -5, 5)\n        filter_joystick_deadzone = (\n            lambda x: int(\n                (x - in_min) * (out_max - out_min) \/ (in_max - in_min) + out_min\n            )\n            if abs(x - 32768) > 500\n            else 0\n        )\n\n    current_position = mousewheel.position\n    position_change = current_position - last_position\n\n    x_offset = filter_joystick_deadzone(xAxis.value) * -1  # Invert axis\n    y_offset = filter_joystick_deadzone(yAxis.value)\n    mouse.move(x_offset, y_offset, 0)\n\n    if enc_btn.value and enc_down == 1:\n        move_speed = move_speed + 1\n        if move_speed > 4:\n            move_speed = 0\n\n        # print (move_speed)\n        enc_down = 0\n\n    if not enc_btn.value:\n        enc_down = 1\n\n    if leftbutton.value:\n        mouse.release(Mouse.LEFT_BUTTON)\n        # pixels.fill(BLACK)\n        # pixels.show()\n    else:\n        mouse.press(Mouse.LEFT_BUTTON)\n        pixels.fill(GREEN)\n        pixels.show()\n\n    if centerbutton.value:\n        mouse.release(Mouse.MIDDLE_BUTTON)\n    else:\n        mouse.press(Mouse.MIDDLE_BUTTON)\n        pixels.fill(YELLOW)\n        pixels.show()\n\n    # Center button on joystick\n    if maint_btn.value:\n        mouse.release(Mouse.LEFT_BUTTON)\n    else:\n        mouse.press(Mouse.LEFT_BUTTON)\n        pixels.fill(GREEN)\n        pixels.show()\n\n    if rightbutton.value:\n        mouse.release(Mouse.RIGHT_BUTTON)\n        # pixels.fill(BLACK)\n        # pixels.show()\n    else:\n        mouse.press(Mouse.RIGHT_BUTTON)\n        pixels.fill(PURPLE)\n        pixels.show()\n\n    if not scroll_up.value:\n        mouse.move(wheel=1)\n        time.sleep(0.25)\n        pixels.fill(BLUE)\n        pixels.show()\n\n    if not scroll_down.value:\n        mouse.move(wheel=-1)\n        time.sleep(0.25)\n        pixels.fill(CYAN)\n        pixels.show()\n\n    if not scroll_up.value and not scroll_down.value:\n        for x in range(4):\n            pixels.fill(RED)\n            pixels.show()\n            time.sleep(0.5)\n            pixels.fill(BLACK)\n            pixels.show()\n            time.sleep(0.5)\n        microcontroller.reset()\n\n\n\n    if position_change > 0:\n        mouse.move(wheel=position_change)\n        #print(current_position)\n        #pixels.fill(BLUE)\n        #pixels.show()\n    elif position_change &lt; 0:\n        mouse.move(wheel=position_change)\n        #print(current_position)\n        #pixels.fill(CYAN)\n        #pixels.show()\n    last_position = current_position\n    pixels.fill(BLACK)\n    pixels.show()\n<\/code><\/pre>\n\n\n\n<p>boot.py<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>import storage\nimport board, digitalio\nimport time\nfrom rainbowio import colorwheel\nimport neopixel\nimport busio\nfrom digitalio import Direction\nfrom adafruit_mcp230xx.mcp23008 import MCP23008\nimport digitalio\ni2c = busio.I2C(board.SCL, board.SDA)\nmcp = MCP23008(i2c)\n\n\n\n#button = digitalio.DigitalInOut(board.D8)\n#button.pull = digitalio.Pull.UP\n\nbutton = mcp.get_pin(6)\nbutton.direction = digitalio.Direction.INPUT\nbutton.pull = digitalio.Pull.UP\n\nRstbutton = mcp.get_pin(7)\nRstbutton.direction = digitalio.Direction.INPUT\nRstbutton.pull = digitalio.Pull.UP\n\n# NEOPIXEL\npixel_pin = board.NEOPIXEL\nnum_pixels = 1\npixels = neopixel.NeoPixel(pixel_pin,num_pixels,brightness=0.2,auto_write=False)\n\nRED = (255, 0, 0)\nYELLOW = (255,150, 0)\nGREEN = (0, 255, 0)\nCYAN = (0, 255, 255)\nBLUE = (0, 0, 255)\nPURPLE = (180, 0, 255)\nBLACK = (0, 0, 0)\n\n# Disable devices only if button is not pressed.\n#usb_hid.enable((), boot_device=2)\nif button.value:\n   pixels.fill(GREEN)\n   pixels.show()\n   storage.disable_usb_drive()\n   usb_cdc.disable()\nelse:\n    pixels.fill(RED)\n    pixels.show()\n    usb_cdc.enable(console=True, data=False)\n    storage.enable_usb_drive()\n\n\ntime.sleep(5)\n# Write your code here :-)<\/code><\/pre>\n","protected":false},"excerpt":{"rendered":"<p>Over the last few months, We have been steadily improving the design of our XIAO RP2040-based mouse device. With this, ver 3.0 all the hardware bugs were finally eliminated, and we also placed the device into its first-ever enclosure. Let us take a look at the design The PCB and Schematic The PCB is a &hellip; <a href=\"https:\/\/www.makeriot2020.com\/index.php\/2024\/01\/25\/xiao-rp2040-mouse-ver-3-0\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> &#8220;XIAO RP2040 Mouse Ver 3.0&#8221;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":21147,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[89,139],"tags":[45,95],"class_list":["post-21145","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-custom-pcb-design","category-rp2040","tag-electronics","tag-raspberry-pi-pico"],"aioseo_notices":[],"_links":{"self":[{"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/posts\/21145","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/comments?post=21145"}],"version-history":[{"count":0,"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/posts\/21145\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/media\/21147"}],"wp:attachment":[{"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/media?parent=21145"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/categories?post=21145"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.makeriot2020.com\/index.php\/wp-json\/wp\/v2\/tags?post=21145"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}