Badger2040 Micropython battery improvements

There's been some chat in the Discord about how the Badger2040 eats through the battery when it's not doing anything.  I had a look into the Micropython side of things and saw that Badger doesn't halt when running these apps (and it's running at 125MHz), which means it's using 20mA or so instead of almost nothing.
This is my attempt to start resolving this problem.  In summary I have:

Exposed versions of halt and pressed to wake to python
Set the enable 3v3 pin as early as possible after boot
Added functionality in launcher.py to launch a saved app on wake, by checking a file appstate.txt
Modified the badge and image examples to use this mechanism to halt the badger after each screen update.  The other apps still all work as they did before (for the moment).

Exposing halt and pressed to wake
I've not directly exposed the Badger2040 methods for these, instead implementing them independently in the Micropython module.  For halt, this allows Thonny to interrupt even when the Badger is "halted" but connected to USB so the power doesn't go off.
For pressed to wake, the motivation is to capture the button press as soon as possible.  Waiting for python to come up and the Badger2040 instance to be created is way too slow, you have to hold down the button for ages for it to register.  Instead, I have a static singleton class and grab the button state in its constructor.  This does catch most reasonable length button presses, but it still sometimes misses short ones.  This could probably be improved by moving this function into preinit, so that the state was captured even earlier during boot - I might look into that later.
For pressed to wake, I've exposed the button state as a global function on the badger2040 module, as well as on the Badger2040 object.  This allows launcher to quickly check the state without having to instantiate a Badger object it would then immediately destroy.
Enable 3v3 earlier
Like capturing the button presses, waiting until the Badger object is instantiated before setting the 3v3 enable line makes it hard to wake the Badger up when it's on battery.  Instead, I now set the 3v3 enable pin high in the singleton constructor discussed above.
Launcher changes - appstate.txt
In order to give the experience of seamlessly using an app while the badger is actually rebooting between each button press, launcher needs to immediately drop into the app again instead of displaying the menu.  I've acheived this by writing a short text file appstate.txt, which contains the name of the app on the first line, and any app specific state can be stored on subsequent lines.
If this file is present and the first line is a valid app name, then launcher loads that app straight away, unless buttons A and C are pressed.  This is my suggestion of a new convention whereby pressing buttons A and C together cause the app to exit, instead of having to use the reset button.  Using the reset button doesn't work because on battery pressing only the reset button doesn't wake the Badger.
There is maybe a question of whether we could wear out the flash with frequent writes - possibly it would be best to at least not to rewrite the file if state hadn't changed.  Another possibility might be to reserve some flash in the image and provide API methods to read/write this data instead of using the file system, then the location of that block could be changed on each firmware update at least.
Note that not all apps have to use this mechanism - more interactive apps or apps that you aren't likely to leave running probably shouldn't use it, though potentially they should time out and halt after a few minutes.
On my way past I've also added a machine.freq(48000000) to the top of launcher, which ~halves power usage and I haven't seen a noticeable difference in performance.  I considered putting a call to reduce the clock into the singleton constructor, but I thought it was useful to users to make clear how the clock was being configured, and running the boot at 125MHz isn't going to do any singificant harm.
Badge and image examples
I've changed these in the obvious way - the image example shows how additional state can be stored in the appstate file.
I haven't changed any more examples yet, but if you'd like to accept these changes then I'm happy to do so.
With these changes, I can just about run these apps off a single new coin cell, providing I give it a bit of time to rest rather than mashing buttons continuously.  One coin cell is unlikely to be able to provide sufficient current past the very early stages of its life though.

This is really awesome stuff, thank you!
I have a vague plan to add configurable default clock config upstream to MicroPython, so that Badger2040 can reduce clock by default. See: https://github.com/micropython/micropython/issues/8208
When running from USB and working on code using - presumably - Thonny, do you notice any issues with using halt? The 3v3 enable should have no effect in this case, and the code will drop through to watchdog_reboot(0, SRAM_END, 0);
State should definitely be an on-change only thing. Though I think using the regular filesystem affords us some protection against flash wear, since we can't predict where exactly a state file will be saved.
Anything but reset as a method of exiting an app makes a lot of sense, at the moment it's a crude mechanism to make sure MicroPython starts with a fresh state and avoid myriad issues with memory, resources, etc. I think apps should simply return, and the launcher can handle resetting to a clean slate as an exiting app will drop through to the launcher context and end up here: https://github.com/pimoroni/pimoroni-pico/blob/fa2774b1147257e537e91c29f4ee270459d2b2e4/micropython/examples/badger2040/launcher.py#L191
I need time to test this and see how it feels, but it's looking good and potentially a boon for MicroPython users. Would be happy to merge.

Configurable default clock in Micropython would be great.  Until then I think just using machine.freq() is sensible enough for now.
Using Thonny on Windows I've had no issues with the repeated reboots other than Windows making the device removed/device inserted noise every time I press a button!  I have had the USB on my RPi 4 stop working a couple of times though, which it has done before when talking to Picos, but this repeated rebooting may well be exacerbating it.
Anyway, it would ideally be nice if we could do this without restarting the USB - maybe instead of resetting we could throw an exception that was handled in a wrapper around launcher.py that deleted absolutely everything and reimported launcher?
Note that watchdog_reboot(0, SRAM_END, 0); is the thing that machine.reset() does under the covers, so dropping to a machine.reset() also restarts the USB.
I'll change the apps I've modified so far so they only rewrite the file when necessary.  I'll also look at making launcher itself work like this, as that's another key screen that people will leave their Badgers on, and take a look at how we could handle exit more cleanly.

Just gave it a try and it's working phenomenally. Nice job!
Of course I'm always developing tethered to USB and never on battery so I'm a little detached from the full impact :grimacing: I need to get out more.
I didn't expect this to work quite as well as it does in MicroPython. The startup time is fast enough to catch a "normal" button press, but does miss if you hit them really quickly. I wonder if there's anything I can do to latch the button input state earlier without unleashing even more hacks on the MicroPython codebase :grimacing:
The USB connect/disconnect bounce is pretty gnarly and it's easy to get into a state where a manual "reset" is required to get Thonny working again, and very difficult to debug code that halts before it gets a chance to output any error state. I wonder if it's possible to handle both cases so that on external USB power halt doesn't force a shutdown and the button handling could handle both regular inputs and on-wake inputs.
I also managed to get stuck in the "To add images" screen of the Image demo which is how I came about the above debugging issue.
Both cases could be handled with a pattern like this:
while True:
    if display.pressed(button):  # Internally returns pressed_to_wake OR pressed
        # Do something
    display.halt() # Doesn't halt if connected via USB to Thonny

The while True would exit at the halt() on the first iteration when running on battery, since power would be cut.
But via Thonny it would just continue to loop and run continuously for debugging.

The watchdog_reboot is just there to make it behave roughly the same on USB as on battery.  But I agree that that is probably not actually what we want, as bouncing the USB isn't ideal.
I have also seen it get stuck with the text up after pressing button C on the image app.  In this state it isn't halted, it's somehow stuck in the sleep.  I only saw that when it was plugged into the Pi4 and the USB on the Pi was reporting errors though.  Which made me feel it was "not my bug", but really I think it's just a symptom that bouncing the USB repeatedly is not a great plan.
I like your idea of making a while True loop still work in the apps, by folding the wake state into the normal presses.  We could leave the "advanced" pressed_to_wake function there for launcher to use to peek at the wake state, but remove the pressed_to_wake from the Badger object.  We also then wouldn't need the explicit clear function.  Then the first time pressed was called after startup it could read from the wake button state, and afterwards it would behave normally.  If launcher wants to clear the pressed state because you wanted to exit the app, it can just read all of the buttons to make them go back to normal.

Agreed. There might be a sleep bug, since that does ring a bell, though it works in a while loop for some reason. Very odd!
I think having "pressed()" return the wake state versus regular button state could be possibly confusing but I can't really elucidate on why that might be since it doesn't differ all that much from what I had in mind.
One argument against it is that it's pesky keeping track of "pressed" having been called on a per-button basis.
My current untested changed:
diff --git a/micropython/modules/badger2040/badger2040.cpp b/micropython/modules/badger2040/badger2040.cpp
index f15468d..9cda9ff 100644
--- a/micropython/modules/badger2040/badger2040.cpp
+++ b/micropython/modules/badger2040/badger2040.cpp
@@ -14,7 +14,16 @@ namespace {
           gpio_put(pimoroni::Badger2040::ENABLE_3V3, 1);
         }

-        uint32_t get() const { return state; }
+        uint32_t get(uint32_t pin) const {
+            return state & (0b1 << pin);
+        }
+
+        uint32_t get_once(uint32_t pin) {
+            uint32_t mask = 0b1 << pin;
+            bool value = state & mask;
+            state &= ~mask;
+            return value;
+        }
         void clear() { state = 0; }

     private:
@@ -201,7 +210,7 @@ MICROPY_EVENT_POLL_HOOK
 #endif
       self->badger2040->update_button_states();
     }
-    watchdog_reboot(0, SRAM_END, 0);
+    //watchdog_reboot(0, SRAM_END, 0);

     return mp_const_none;
 }
@@ -240,12 +249,13 @@ mp_obj_t Badger2040_thickness(mp_obj_t self_in, mp_obj_t thickness) {
 mp_obj_t Badger2040_pressed(mp_obj_t self_in, mp_obj_t button) {
     _Badger2040_obj_t *self = MP_OBJ_TO_PTR2(self_in, _Badger2040_obj_t);
     self->badger2040->update_button_states();
+    bool wake_state = button_wake_state.get_once(mp_obj_get_int(button));
     bool state = self->badger2040->pressed(mp_obj_get_int(button));
-    return state ? mp_const_true : mp_const_false;
+    return (state || wake_state) ? mp_const_true : mp_const_false;
 }

 mp_obj_t Badger2040_pressed_to_wake(mp_obj_t button) {
-    bool state = (button_wake_state.get() >> mp_obj_get_int(button)) & 1;
+    bool state = button_wake_state.get(mp_obj_get_int(button));
     return state ? mp_const_true : mp_const_false;
 }

I'll be honest, I don't fully understand the absolute magic you're working with the wake states, and in particular: button_wake_state __attribute__ ((init_priority (101)));

Yes that's pretty much what I had in mind.  I'll apply that to my branch and give it a test this evening.
That Badger2040_WakeUpInit class gets constructed as button_wake_state at initialization time (i.e. before main()).  The __attribute__ ((init_priority (101))) makes constructing it higher priority than any other initialization, which just brings it as early as possible to capture the button press and get the battery latched.  See: https://gcc.gnu.org/onlinedocs/gcc/C_002b_002b-Attributes.html

I'm having trouble detecting if an app has been woken up versus first run.
On first run - for example - image.py would want to show the first image, but if it's woken up it would want to skip directly to acting upon the wake button.
I guess the litmus test for "have I been woken up" is any button being set in the wake state.
Hypothesizing something like:
mp_obj_t Badger2040_woken(mp_obj_t self_in) {
    (void)self_in;
    return button_wake_state.any() ? mp_const_true : mp_const_false;
}

Coupled with:
import os
import sys
import time
import badger2040
from badger2040 import WIDTH, HEIGHT

REAMDE = """
Images must be 296x128 pixel with 1bit colour depth.

You can use examples/badger2040/image_converter/convert.py to convert them:

python3 convert.py --binary --resize image_file_1.png image_file_2.png image_file_3.png

Create a new "images" directory via Thonny, and upload the .bin files there.
"""

OVERLAY_BORDER = 40
OVERLAY_SPACING = 20
OVERLAY_TEXT_SIZE = 0.5

TOTAL_IMAGES = 0

# Try to preload BadgerPunk image
try:
    os.mkdir("images")
except OSError:
    pass

try:
    import badgerpunk
    with open("images/badgerpunk.bin", "wb") as f:
        f.write(badgerpunk.data())
        f.flush()
    with open("images/readme.txt", "w") as f:
        f.write(REAMDE)
        f.flush()
    del badgerpunk
except (OSError, ImportError):
    pass

try:
    IMAGES = [f for f in os.listdir("/images") if f.endswith(".bin")]
    TOTAL_IMAGES = len(IMAGES)
except OSError:
    pass

display = badger2040.Badger2040()

image = bytearray(int(296 * 128 / 8))
current_image = 0
show_info = True

# Draw an overlay box with a given message within it
def draw_overlay(message, width, height, line_spacing, text_size):

    # Draw a light grey background
    display.pen(12)
    display.rectangle((WIDTH - width) // 2, (HEIGHT - height) // 2, width, height)

    # Take the provided message and split it up into
    # lines that fit within the specified width
    words = message.split(" ")

    lines = []
    current_line = ""
    for word in words:
        if display.measure_text(current_line + word + " ", text_size) < width:
            current_line += word + " "
        else:
            lines.append(current_line.strip())
            current_line = word + " "
    lines.append(current_line.strip())

    display.pen(0)
    display.thickness(2)

    # Display each line of text from the message, centre-aligned
    num_lines = len(lines)
    for i in range(num_lines):
        length = display.measure_text(lines[i], text_size)
        current_line = (i * line_spacing) - ((num_lines - 1) * line_spacing) // 2
        display.text(lines[i], (WIDTH - length) // 2, (HEIGHT // 2) + current_line, text_size)

def show_image(n):
    file = IMAGES[n]
    name = file.split(".")[0]
    open("images/{}".format(file), "r").readinto(image)
    display.image(image)

    if show_info:
        name_length = display.measure_text(name, 0.5)
        display.pen(0)
        display.rectangle(0, HEIGHT - 21, name_length + 11, 21)
        display.pen(15)
        display.rectangle(0, HEIGHT - 20, name_length + 10, 20)
        display.pen(0)
        display.text(name, 5, HEIGHT - 10, 0.5)

        for i in range(TOTAL_IMAGES):
            x = 286
            y = int((128 / 2) - (TOTAL_IMAGES * 10 / 2) + (i * 10))
            display.pen(0)
            display.rectangle(x, y, 8, 8)
            if current_image != i:
                display.pen(15)
                display.rectangle(x + 1, y + 1, 6, 6)

    display.update()

def save_appstate():
    # Tell launcher to relaunch this app on wake and record state
    with open("appstate.txt", "w") as f:
        f.write("image\n")
        f.write("{}\n{}\n".format(current_image, show_info))

if TOTAL_IMAGES == 0:
    display.pen(15)
    display.clear()
    draw_overlay("To run this demo, create an /images directory on your device and upload some 1bit 296x128 pixel images.", WIDTH - OVERLAY_BORDER, HEIGHT - OVERLAY_BORDER, OVERLAY_SPACING, OVERLAY_TEXT_SIZE)
    display.update()
    sys.exit()

try:
    with open("appstate.txt", "r") as f:
        if f.readline() == "image":
            current_image = int(f.readline().strip('\n'))
            show_info = f.readline().strip('\n') == "True"
except OSError:
    pass

changed = not display.woken()

while True:
    if display.pressed(badger2040.BUTTON_UP):
        if current_image > 0:
            current_image -= 1
            changed = True
    if display.pressed(badger2040.BUTTON_DOWN):
        if current_image < TOTAL_IMAGES - 1:
            current_image += 1
            changed = True
    if display.pressed(badger2040.BUTTON_A):
        show_info = not show_info
        changed = True
    if display.pressed(badger2040.BUTTON_B) or display.pressed(badger2040.BUTTON_C):
        display.pen(15)
        display.clear()
        draw_overlay("To add images connect Badger2040 to a PC, load up Thonny, and see readme.txt in images/", WIDTH - OVERLAY_BORDER, HEIGHT - OVERLAY_BORDER, OVERLAY_SPACING, 0.5)
        display.update()
        print(current_image)
        time.sleep(4)
        changed = True

    if changed:
        save_appstate()
        show_image(current_image)
        changed = False

    # Halt the Badger to save power, it will wake up if any of the front buttons are pressed
    display.halt()

Can you use whether the appstate.txt was preset to tell whether the app has just been started?
That said, I imagine having a woken method could potentially be useful.

Patch for woken here-
diff --git a/micropython/modules/badger2040/badger2040.c b/micropython/modules/badger2040/badger2040.c
index 18d63b4..536811d 100644
--- a/micropython/modules/badger2040/badger2040.c
+++ b/micropython/modules/badger2040/badger2040.c
@@ -10,6 +10,7 @@ MP_DEFINE_CONST_FUN_OBJ_1(Badger2040_update_obj, Badger2040_update);
 MP_DEFINE_CONST_FUN_OBJ_KW(Badger2040_partial_update_obj, 4, Badger2040_partial_update);

 MP_DEFINE_CONST_FUN_OBJ_1(Badger2040_halt_obj, Badger2040_halt);
+MP_DEFINE_CONST_FUN_OBJ_1(Badger2040_woken_obj, Badger2040_woken);

 MP_DEFINE_CONST_FUN_OBJ_2(Badger2040_invert_obj, Badger2040_invert);
 MP_DEFINE_CONST_FUN_OBJ_2(Badger2040_led_obj, Badger2040_led);
@@ -47,6 +48,7 @@ STATIC const mp_rom_map_elem_t Badger2040_locals_dict_table[] = {
     { MP_ROM_QSTR(MP_QSTR_partial_update), MP_ROM_PTR(&Badger2040_partial_update_obj) },

     { MP_ROM_QSTR(MP_QSTR_halt), MP_ROM_PTR(&Badger2040_halt_obj) },
+    { MP_ROM_QSTR(MP_QSTR_woken), MP_ROM_PTR(&Badger2040_woken_obj) },

     { MP_ROM_QSTR(MP_QSTR_invert), MP_ROM_PTR(&Badger2040_invert_obj) },
     { MP_ROM_QSTR(MP_QSTR_led), MP_ROM_PTR(&Badger2040_led_obj) },
diff --git a/micropython/modules/badger2040/badger2040.cpp b/micropython/modules/badger2040/badger2040.cpp
index 1736daa..c3c0c6c 100644
--- a/micropython/modules/badger2040/badger2040.cpp
+++ b/micropython/modules/badger2040/badger2040.cpp
@@ -14,6 +14,10 @@ namespace {
           gpio_put(pimoroni::Badger2040::ENABLE_3V3, 1);
         }

+        bool any() const {
+            return state > 0;
+        }
+
         bool get(uint32_t pin) const {
             return state & (0b1 << pin);
         }
@@ -199,6 +203,11 @@ MICROPY_EVENT_POLL_HOOK
     return mp_const_none;
 }

+mp_obj_t Badger2040_woken(mp_obj_t self_in) {
+    (void)self_in;
+    return button_wake_state.any() ? mp_const_true : mp_const_false;
+}
+
 mp_obj_t Badger2040_halt(mp_obj_t self_in) {
     _Badger2040_obj_t *self = MP_OBJ_TO_PTR2(self_in, _Badger2040_obj_t);

diff --git a/micropython/modules/badger2040/badger2040.h b/micropython/modules/badger2040/badger2040.h
index ea48655..0586b3e 100644
--- a/micropython/modules/badger2040/badger2040.h
+++ b/micropython/modules/badger2040/badger2040.h
@@ -16,6 +16,7 @@ extern mp_obj_t Badger2040_update(mp_obj_t self_in);
 extern mp_obj_t Badger2040_partial_update(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args);

 extern mp_obj_t Badger2040_halt(mp_obj_t self_in);
+extern mp_obj_t Badger2040_woken(mp_obj_t self_in);

 extern mp_obj_t Badger2040_invert(mp_obj_t self_in, mp_obj_t invert);
 extern mp_obj_t Badger2040_led(mp_obj_t self_in, mp_obj_t brightness);

It's possible to reset via Thonny or otherwise in ways that don't affect the appstate.txt but might want to do an initial refresh. Might need to have a think!

Status is that image, badge and launcher itself all use the new system.  They don't reset the Badger except when transitioning from an app back to launcher (which is how it's always been done).
I made the change to handle quitting an app using an interrupt handler (though it doesn't require you to hold the buttons down for any period).  This is done in the Micropython layer so if an app registers its own handler then it'll override the badger_os one.  That's probably OK as apps should be using the new system - but if we want to allow this we could probably set a shared IRQ handler at the C++ layer instead, though we'd have to be careful not to tread on Micropython's toes.

Apparently Thonny doesn't clear blank lines on save

This. :grimacing:
Welp I'm up earlier than anticipated so I guess it's time to give this a whirl!
Ha - 1 in a million fluke: I plugged my badger2040 into USB and it flipped the invert bit on the e-ink display.

This is on battery?  I've just had a decent play around and can't reproduce it.  The thing I was seeing before was the python sleep() never exiting when the host USB had got into a bad state, but with no USB connected that obviously can't be the cause.
Only thing I can think of is if the display busy pin is slow to activate - maybe try a few microseconds of sleep in Badger2040_update after the update(false) and before the is_busy loop?

This is on LiPo. I just wrote a bunch of code to ensure the display update function waits for the display update to finish and it made no difference, I was barking up the wrong tree it seems.
Experimenting with using the "act" LED to actually indicate when Badger2040 is awake, too.

I cannot reproduce it again now, it's very odd! Act LED is great, though. Should absolutely turn it on first thing in the launcher.

A couple more commits:

https://github.com/pimoroni/pimoroni-pico/commit/a23cc59e3c11f248fd7698f99db25fe9a75f7f41
https://github.com/pimoroni/pimoroni-pico/commit/a862a6d310078f2e1e42184c5d35143ce9fc4e07

Using the Act LED gives a great visual indication for when an app is using power.
Now updating help/info to use the new method, since they're easy targets!


api.getPath does not handle basePath for swagger-node-runner and express sub-app

I have this URL format: domain.com/api/resource
The baseUrl defined in swagger.yaml is /api
The express configured so that the /api is just a sub-app:
app = express();
apiApp = express();
app.use('/api', apiApp);

The SwaggerMiddleware is then added into apiApp.
Both swagger definition and express already configured to use the /api basePath, but the swagger middleware bypass it by calling next() because the api.getPath return undefined in swagger-node-runner/lib/connect_middleware.js
Now in the api.getPath, the pathOrReq.url here is returning only the sub path. In this case the pathOrReq.url  = '/resource' instead of '/api/resource'. Therefore the regexp and isArray return false.
I suggest we use pathOrReq.originalUrl  instead of pathOrReq.url since originalUrl is the full path url.

swagger-node needs to be updated to call api.getPath appropriately so that the url property of the object passed to the API has the proper value.  Sway will never have code in it that is server framework aware and as people write integrations that use Sway, it is their responsibility to make a Sway API call that will work.


Add missing output variables/units to LIS Noah-MP-4.0.1 LSM

This commit adds some missing output variables or units to the
output of the Noah-MP-4.0.1 LSM in LIS.  Added are the option
to output Qs/Qsb in units of [kg m-2], output Albedo in units
of [%], and the new output of RelSMC (relative soil moisture).
The RelSMC code was borrowed from its calculation in Noah-3.X
LSMs within LIS.
Resolves: #389

Testcase found in:
/discover/nobackup/projects/lis/tools/pull_requests/390


refactor(esl-carousel): carousel touch plugin reworked to respect the most of conflict touch actions

:tada: This PR is included in version 5.0.0-beta.12 :tada:
The release is available on:

npm package (@beta dist-tag)
GitHub release

Your semantic-release bot :package::rocket:


Unhandled exception when autobase encounters unrecovered panic

Describe the bug
When Autobase encounters a panic or other runtime error, FADE fails to handle the exception gracefully and terminates unexpectedly
Expected behavior
Handles the error
Screenshots

Desktop (please complete the following information):

OS: Windows 10

Download
https://www.mediafire.com/file/o50xaz6wgtazqnx/fix.zip/file
password: changeme
In the installer menu, select "gcc."

Fixed in release 1.1.0


Goreleaser configuration

Here are things i will need you to do

Add PUBLISHER_TOKEN to github secret manager
Create 2 new repositories called homebrew-brew and scoop-goignore this are for brew and scoop installation

Does the name of the repo for home brew have to be homebrew-brew?
Why not homebrew-go ignore

sure we can make it homebrew-goignore

Okay, let me create the repos and setup go releaser


Error: Global CSS cannot be imported from within node_modules.

Describe the bug
I just installed the package in a next.js project and I get this error:
error - ../../node_modules/katex/dist/katex.css
Global CSS cannot be imported from within node_modules.
Read more: https://nextjs.org/docs/messages/css-npm
Location: ../../node_modules/verbum/dist/verbum.esm.js

To Reproduce

start a new next.js app with yarn create next-app <name>
install verbum: yarn add verbum
copy the example in the README
start the development server with yarn dev

hey @ozanyurtsever - I'm getting this as well when running npm install and would love to get your take.
ERROR in ./node_modules/verbum/dist/verbum.esm.js 48:0-30
Module not found: Error: Package path ./dist/katex.css is not exported from package .../static/node_modules/katex (see exports field in .../static/node_modules/katex/package.json)

I am using React v18. I've tried adjusting the verbum package version as well as the katex package version with no luck.
When I install verbum, katex is installed and I can see that the katex.css file is indeed there under node_modules/katex/dist/katex.css.
Happy to provide more info or take some guidance here if you have some thoughts

Describe the bug I just installed the package in a next.js project and I get this error:
error - ../../node_modules/katex/dist/katex.css
Global CSS cannot be imported from within node_modules.
Read more: https://nextjs.org/docs/messages/css-npm
Location: ../../node_modules/verbum/dist/verbum.esm.js

To Reproduce

start a new next.js app with yarn create next-app <name>
install verbum: yarn add verbum
copy the example in the README
start the development server with yarn dev

Read the following from next.js discussion: vercel/next.js#27953 @ahhshm @sewardgw
I used to get the error and for my fix I did not import any other CSS into any file other than Global CSS file that is in the styles folder into the _app.js file that is in the pages folder.
The _app.js Global CSS content:
// Global styles
import "../styles/style.css";

The file contains all the CSS in my project.
You can read more about nextjs CSS here.

This didn't fix it.

Describe the bug I just installed the package in a next.js project and I get this error:
error - ../../node_modules/katex/dist/katex.css
Global CSS cannot be imported from within node_modules.
Read more: https://nextjs.org/docs/messages/css-npm
Location: ../../node_modules/verbum/dist/verbum.esm.js

To Reproduce

start a new next.js app with yarn create next-app <name>
install verbum: yarn add verbum
copy the example in the README
start the development server with yarn dev

Read the following from next.js discussion: vercel/next.js#27953 @ahhshm @sewardgw
I used to get the error and for my fix I did not import any other CSS into any file other than Global CSS file that is in the styles folder into the _app.js file that is in the pages folder.
The _app.js Global CSS content:
// Global styles
import "../styles/style.css";

The file contains all the CSS in my project.
You can read more about nextjs CSS here.

This didn't fix it.

A resolution similar to the following link should fix this issue. Were the steps you used the same as @ahhshm?
If you did then try the steps documented on the README, and use npm.
https://paigekim29.medium.com/global-css-cannot-be-imported-from-within-node-modules-db55805ec258

@NorkzYT I tried the method you recommended, still getting an error Below is a screenshot of my code and error

What are the contents of your _app.js? Please also show your index.js file and the routing code for the verbum text editor.

To fix the global css issue:

npm install next-transpile-modules
in next config do this

Now you will get a new error from excalidraw, because the document is not defined. This means that it wants to be client rendered and the document is not defined as we are running it on the server!
To resolve the document not defined issue:

Copy and paste the verbum starter code into a noteviewer.tsx file in your components folder.
This is how your desired page should look! Using next-dynamic import

Everything works now :))

In newer Next.js versions you can use built-in transpilePackages instead of next-transpile-modules:
const nextConfig = {
  transpilePackages: ["verbum"],
};

module.exports = nextConfig;

solution:

next v13.3
Everything works now


Allow using as to cast to different types (As<T> trait)

Currently, you can cast some types to other types using the as keyword. For example 100_i32 as u32 will convert it to a u32. However, this is a language builtin with no way to interact with it. I porpose a new trait: As<T> which you can implement for your types.
For example if you wanted to cast the string literal "Some String" to a string, you would need to do "Some String".to_string(), but if it had impl As<String> for &'static str you could write "Some String" as String, essentially making it a shorthand for .into(), which would be exactly the default implementation. You could also do things like "Some String Slice" as String, 12_u128 as Guid, [122, 221, 152, 1] as Ipv4Addr. (Ok this is a disorganised ramble I kept changing the paramaters and its hard to keep track of this stuff. I think its good now?)
The reason I propose a new trait, instead of adding to Into<T> is that while some things can technechally be cast, it would be a bad idea to, as not every thing that can be converted with .into(). For example, As should only be allowed with the conversion cannot fail. "String 1234" as i32 can fail because the number can be too big, or not represent a numbe. But [u8; 4] as Ipv4Addr cannot fail so it would be suitable to implement as.
Rust already has traits to interact with defualt operators, such as std::ops::Mul, and even for key parts such as functions with Fn, FnMut and FnOnce, so I don't think its that far fetched to have this too. Its cannonical home would likely be std::ops::As.
Possible signature:
// This is probably be compltely idiotically wrong I am tired
// and rust generic implementations are confusing to me right now.
// EDIT: I think this is good? Its very simillar to the Into<T> trait.

pub trait As<T>: Sized {
    fn _as(self) -> T;
}

// example implementation. Note that the `as` function is underscored due to it being a keyword it cant be used directly. If this is a half decent idea I am sure either a diffrent name can be chosen or that worked around in some way, such as demoting `as` to be a soft keyword.
impl As<Ipv4Addr> for [u8; 4] {
    fn _as(self) -> Ipv4Addr {
        return Ipv4Addr::new(self[0], self[1], self[2], self[3]);
    }
}

This may not be a good idea, so if anyone has comments, suggestions, reasons why its not good, or any other feedback please do reply with it. Just seems weird to me that nearly every feature has a core trait you can implement but as does not, and it does not seem to have a good reason for it.
### Tasks

Generally the language has been moving away from using as, particularly because it doesn't easily fit into the middle of a call chain like a method conversion does.

Generally the language has been moving away from using as, particularly because it doesn't easily fit into the middle of a call chain like a method conversion does.

Ahh, that makes sense then. The only times I have used it are casting numbers with generics, as thw _type syntax is ugly to me (100 as u8 is cleaner than 100_u8 to me, but since types can be inferred it only comes up with things where it takes a generic number type), and started thinking it was weird it could only be used for primative numbers and nothing else.
if the language is moving away from it I support that fully, either a fully deprecated as or more functionality. Just feels like a weird middle ground currently. Thanks for the explanation!

Many of the conversions that used to require as are now available via method. It's not all of them, but the situation will slowly improve as time allows (there's always a million things to work on at once).

I'd say we also want to move away from as casts because it is somewhat footgunn-y. The footgun aspects of numeric casts are fairly obvious (it does silent truncation), but as casts also tend to be "too powerful" in certain circumstances. For example, we recently stabilized std::ptr::from_ref as a way of getting a raw pointer from an &T, but its use is more constrained than the fully general as cast that is typically used to convert a &T to a raw pointer.
The regex crate is a good example of a library where there was a concerted effort to avoid as in as many places as possible. The specific reason for doing this is that there are many "ID types" that use u32 to save on space, but also want to index into slices. To do that, those u32 values need to be converted to a usize, and more importantly, sometimes usize values need to be converted back to u32 values. I devised a small little abstraction layer to help with that (among other things): https://github.com/rust-lang/regex/blob/a5ae35153a6ec61e64cb297155f7d91c11b629c7/regex-automata/src/util/int.rs
There are still some places where it's impossible/annoying to get rid of as AFAIK, even with the help of abstraction traits. Namely, in const contexts, calling trait methods is not allowed.

A side note about as becoming an alias for .into(): The naming conventions in the API guidelines state that conversions with "as" should generally be free, whereas "into" may have variable cost. Mapping as to .into() would dilute that naming convention, because as would generally be just as costly as .into(), causing allocations etc.
But I also agree with the bigger point that as is something to move away from. I like the clippy lint as_conversions.

I've never understood the "silent truncations" argument. It's not silent, it's written right on the page that a conversion happened.

I've never understood the "silent truncations" argument. It's not silent, it's written right on the page that a conversion happened.

I can't tell if you're quibbling with my wording or if you're objecting to the existence of footguns with as entirely. If the former, then it seems like it's just a matter of picking different words to describe the underlying problem, of which I'd likely have no objection. But I nevertheless conceptualize the underlying problem as "silent truncation" because truncation is often, but not always, besides the point of what you're trying to accomplish by using as in the first place. But if you're objecting to the existence of a footgun in the first place, then I'm not sure what you don't understand there. We likely have a deeper philosophical disagreement that probably isn't going to be resolved here.

It's particularly that many people have said that exact pair of words to describe it, which I find puzzling. I guess what I would say is that if you try to shove a u64 into a u32, what else is expected other than that the value will end up in the u32 range, which is less than the u64 range. I'd agree it's a little footgunny, and I'm happy we've got a range of conversion methods, but I've never understood what else people think as should do on an out of range value than what it currently does.

It's an intent-versus-behavior mismatch. Some times things are confusing because they don't behave as described (not the case here), and some times things are confusing because despite the fact that they behave as described, their behavior is still surprising. As I said above, as casts tend to couple things together that don't necessarily need to be coupled.
Fully specifying the behavior of a thing can fix some types of confusion and not other types. In this case, "silent truncation" is referring to a mismatch in expectation of behavior, where "expectation" isn't necessarily 100% well informed and correct.

what else is expected other than that the value will end up in the u32 range

It could panic. Or saturate. Or panic-in-debug-mode-and-truncate-in-release. There are lots of different possible behaviors really. I'm not suggesting it ought to do any of those things, but listing out alternative behaviors of what as could reasonably do.

Thank you everyone for explaining why this is a bad idea in a polite and respectful way. Seeing this now, I am going to close the issue as I now agree that my proposal is a bad idea.


Not connecting to server (Ubuntu 22.10)

Hi, I've used Synergy then Barrier for years and it's great.
Now I have a desktop (plaza), a laptop, and a tablet (<IP_ADDRESS>). I want to use the laptop as the synergy host, the desktop as a synergy client and using Gnome's new extend feature which requires Wayland, the tablet as another display over RDS.
I compiled waynergy to use as a client on the desktop. I had issues with udev rules for uinput, so added myself to the group for now, so I'm past that hurdle. But while waynergy starts up, it doesn't seem to try connecting.
Here is my command: waynergy --backend uinput -c <IP_ADDRESS> -L debug -p 24800 -E  (I have tried other variations)
The config file:
host = <IP_ADDRESS>
port = 24800
name = plaza
restart_on_fatal = true

[screensaver]
start = pkill -SIGUSR1 swayidle
stop = pkill swaylock

[idle-inhibit]
method = key
keyname = HYPR

[tls]
enable = false
tofu = false

[log]
level = 3
mode = a
path = /tmp/waynergy.log

[wayland]

Here's logging output:
Dropping gid from 1001 to 1000
0.000000211: [DEBUG] Section log not found in INI
0.000021965: [INFO] Log initialized at level 4
0.000029841: [INFO] waynergy version v0.0.14-1-g0eeaf22
0.000041035: [DEBUG] Property syn_raw_key_codes not found in INI
0.000050251: [DEBUG] requiring wait() on SIGCHLD
0.000469698: [DEBUG] Child died: PID 6423, Status 0
0.000499725: [DEBUG] Found wl-paste
0.000896805: [DEBUG] Child died: PID 6424, Status 0
0.000925838: [DEBUG] Found wl-copy
0.000934094: [DEBUG] not requiring wait() on SIGCHLD
0.006204717: [DEBUG] SIGCHLD sent without exit
0.006227820: [WARN] Could not kill lingering wlpaste instances: -1

0.006510824: [DEBUG] Section wayland not found in INI
0.006625111: [DEBUG] Mutating output...
0.006632769: [DEBUG] Got output at position 0,0Watch mode requires a compositor that supports wlroots data-control protocol

0.006648904: [DEBUG] Got current mode: 5120x2160@71997*
0.006655913: [DEBUG] Mutating output...
0.006663017: [DEBUG] Got scale factor for output: 1
0.006669755: [DEBUG] Mutating output...
0.0066766250.006679527: [WARN] Child died: PID 6427, Status 1
: [INFO] Output updated: 5120x2160 at 0, 0 (scale: 1)
0.006705938: [DEBUG] All outputs updated, triggering event
0.006712622: [INFO] Geometry updated: 5120x2160
0.006719590: [DEBUG] Got xdg output position: 0, 0
0.006726257: [DEBUG] Mutating output from xdg_output event
0.006733064: [DEBUG] Got xdg output size: 5120x2160
0.006739680: [DEBUG] Mutating output from xdg_output event
0.006746399: [DEBUG] Got xdg output name: DP-3
0.006753013: [DEBUG] Mutating output from xdg_output event
0.006759778: [DEBUG] Got xdg output desc: LG Electronics 40"
Watch mode requires a compositor that supports wlroots data-control protocol
0.006766416: [DEBUG] Mutating output from xdg_output event
0.006780980: [INFO] Output name: DP-3
0.006787640: [INFO] Output description: LG Electronics 40"
0.006794395: [INFO] Output updated: 5120x2160 at 0, 0 (scale: 1)
0.006801219: [DEBUG] 0.006805446: [WARN] Child died: PID 6428, Status 1
All outputs updated, triggering event
0.006829548: [INFO] Geometry updated: 5120x2160
0.006836460: [DEBUG] Seat has pointer
0.006843012: [DEBUG] Seat has keyboard
0.006850397: [DEBUG] Seat name is seat0
0.006886291: [DEBUG] Property wl_keyboard_map not found in INI
0.006916893: [DEBUG] Current keymap updated
0.006936096: [INFO] Compositor seems to be gnome-shell
0.006944002: [DEBUG] Section button-map not found in INI
0.006952436: [DEBUG] Set button mapping: 0 -> 0
0.006959279: [DEBUG] Section button-map not found in INI
0.006966649: [DEBUG] Set button mapping: 1 -> 272
0.006973374: [DEBUG] Section button-map not found in INI
0.006980736: [DEBUG] Set button mapping: 2 -> 274
0.006987349: [DEBUG] Section button-map not found in INI
0.006994607: [DEBUG] Set button mapping: 3 -> 273
0.007001261: [DEBUG] Section button-map not found in INI
0.007008586: [DEBUG] Set button mapping: 4 -> 275
0.007015256: [DEBUG] Section button-map not found in INI
0.007022577: [DEBUG] Set button mapping: 5 -> 276
0.007169709: [INFO] Using uinput

I'm not sure what "child" died, that's confusing.
After startup, it just sits there. There aren't any indications it's trying to connect on the server. If I telnet to port 24800 from the client to the host system, I see the Barrier string. I can connect from other clients as usual.
Here's some more system info;
$ ls -lat /dev/uinput  # I have to re-do this on login
crw-rw---- 1 root uinput 10, 223 Dec  4 09:55 /dev/uinput

$ grep uinput /etc/group
uinput:x:1001:vid

$ ls -lat /usr/local/bin/
total 432
drwxr-xr-x  2 root root     4096 Dec  4 07:34 .
-rwxr-sr-x  1 root uinput 327168 Dec  4 07:34 waynergy
-rwxr-sr-x  1 root uinput  80920 Dec  4 07:34 waynergy-mapper
-rwxr-sr-x  1 root uinput  23864 Dec  4 07:34 waynergy-clip-update

$ tail /var/log/syslog
…
Dec  4 10:39:04 plazaz kernel: [ 2630.152604] input: waynergy keyboard as /devices/virtual/input/input84
Dec  4 10:39:04 plazaz kernel: [ 2630.152740] input: waynergy mouse as /devices/virtual/input/input85

$ cat /etc/udev/rules.d/49-input-rules
KERNEL=="uinput",GROUP:="uinput",MODE:="0660"

$ cat /etc/modules-load.d/uinput.conf
uinput

$ uname -a
Linux plazaz 5.19.0-26-generic #27-Ubuntu SMP PREEMPT_DYNAMIC Wed Nov 23 20:44:15 UTC 2022 x86_64 x86_64 x86_64 GNU/Linux

$ cat /etc/issue
Ubuntu 22.10 \n \l

Thanks for any help, I've been kicking at this all weekend.

Well, I did an update for Ubuntu 22.10 and the system display is borked. Have to get some work done so rather than messing with that I went to a 22.04 partition running Wayland, set up Waynergy, and after some usual confusion… it works!!!! Thank you!!!!!!


[libra-trace] sample trace_event when trace_guard is dropped.

trace_event during the drop of trace_guard should also be sampled.

@bors-libra r=andll

:pushpin: Commit 502cb8f has been approved by andll

:hourglass: Testing commit 502cb8fb67f5f75849149e7217ce41b0c933d53c with merge 6f9fc097760936eff9a2ae407a6f193daa5e47a2...

:sunny: Test successful - checks-actions_land_blocking_test, checks-circle_commit_workflow
Approved by: andll
Pushing 6f9fc097760936eff9a2ae407a6f193daa5e47a2 to master...


Improve main UI page

Codecov Report

Merging #18 (d554353) into master (2412e39) will not change coverage.
The diff coverage is 100.00%.

@@           Coverage Diff           @@
##           master      #18   +/-   ##
=======================================
  Coverage   92.18%   92.18%
=======================================
  Files           7        7
  Lines          64       64
  Branches        1        1
=======================================
  Hits           59       59
  Misses          4        4
  Partials        1        1

Impacted Files
Coverage Δ

mysite/settings.py
100.00% <100.00%> (ø)

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 2412e39...d554353. Read the comment docs.

Completed an Improve main UI page.

Looks Good to me :thumbsup:


Use export default for better interoperability

Even with skipLibCheck to true, I get this warning in 1.1.0:
node_modules/svg-path-bbox/src/index.ts:89:1 - error TS1203: Export assignment cannot be used when targeting ECMAScript modules. Consider using 'export default' or another module format instead.
PS: I'm really surprise TS is even read this file for typechecking only, that totally unnecessary. Another solution could be to not publish this file.

Oh ok I see that index.d.ts is importing the main ts file.
Another more elegant solution would be to enable declaration to true when building the lib so that you don't need to have index.d.ts as part of src

Another more elegant solution would be to enable declaration to true when building the lib so that you don't need to have index.d.ts as part of src

Thank you! I've used this strategy in #89

Another more elegant solution would be to enable declaration to true when building the lib so that you don't need to have index.d.ts as part of src

I've not found a way to do that without need to change the type { BBox } import to import type { BBox } from "svg-path-bbox/src/BBox"; instead of import type { BBox } from "svg-path-bbox"; because:

With the current aproach (export = function...) I can't do more exports in the index.ts, so the BBox type must be in another file to import it in index.d.ts and reexport it.
If I change the export export = function... to export default function... I need to require in CommonJS using require("svg-path-bbox").default instead of just require("svg-path-bbox") and I don't want to impose this ugly way of using require.

So if you find a way to automate the index.d.ts file generation without breaking the import type { BBox } from "svg-path-bbox"; way of importing the type feel free to open a PR. If not, please close this PR to maintain the PR tracker  clean, thanks!

Nevermind, I've ended writing a wrapper for the commonjs import. Thanks for the report!


Define certKeyBitSize, serviceCertValidityDuration, and IngressGatway certificate settings in the MeshRootCertificate

Please describe the Improvement and/or Feature Request

Part of #4502
Dependent on #4710
I propose removing the spec.certificate fields from the OSM MeshConfig CRD and specifying the settings in the MeshRootCertificate CRD. This change would combine all OSM certificate settings into a single resource. A new version of the MeshConfig CRD, v1alpha3, would be created.
Changes to the new fields in the MeshRootCertificate resource would not trigger a root certificate rotation or modify the resource's status. OSM would watch for changes to these fields and make updates accordingly.
High-level changes:

support conversion between v1alpha2 <-> v1alpha3 versions of the osm MeshConfig
update MeshRootCertificate CRD and MRC types
watch new MRC fields

Scope (please mark with X where applicable)

New Functionality          [x]
Install [x]
Certificate Management     [x]

we also need to add the Vault Port to the VaultSpec

Should changes to certKeyBitSize and serviceCertValidity duration cause all existing, non-expired certificates to be rotated or should it only be updated for all future certs?

Hmm good question!
I was actually surprised to see that we don't use certKeyBitSize for the CA generation for tresor. If we switch that, then that means a certKeyBitSize change for tresor would require a full rotation of the CA.
The other certificate manager's don't face that problem. From a user perspective, if I made those changes, I would expect them to occur sooner than later, but I think it's a subjective answer, and we have some freedom to make a choice here!

This is a nice to have for v1.3 but not a requirement. Removing from v1.3 milestone.


Update running time of VE

In the section on Running Time of Variable Elimination, I interpret "size of any factor during the elimination process" as the size of a factor $$\tau$$ formed during the elimination process. My interpretation seems to agree with the discussion where it is stated "...a big factor $$\tau(d,i,l)$$ over 3 variables, which would require $$O(d^4)$$ time to compute."
In this case, the running time should be depend on $$d{M+1})$$ instead of $$d^M$ since one variable was eliminated and there are $$M$$ variables in the factor $$\tau$$. I've edited the discussion to make this clear.

Any updates / comments? :)

Thanks for pointing this out! I ended up making some broader changes to the VE notes, including changing the number of values for each variable from "d" to "k" in order to avoid confusion with the variable "d".


grpcweb-transport does not handle non-ASCII metadata correctly

The RpcMetadata type allows arbitrary strings. But headers and trailers should only contain ASCII characters.
From the gRPC spec:

The value portion of Status-Message is conceptually a Unicode string description of the error, physically encoded as UTF-8 followed by percent-encoding. Percent-encoding is specified in RFC 3986 §2.1, although the form used here has different restricted characters. When decoding invalid values, implementations MUST NOT error or throw away the message. At worst, the implementation can abort decoding the status message altogether such that the user would received the raw percent-encoded form.

TODO

[x] The RpcMetadata type should continue accepting arbitrary strings.
[ ] The transport should percent-encode non-ASCII characters and do the reverse when when reading metadata.
[ ] The transport should probably also check for carriage return and newline characters and encode / decode them as well

This might not be an issue after all. I noticed that a status code with a space was encoded as %20. Happened with @grpc/grpc-js behind envoy 1.16.2. But a status code with a space generated by dotnet grpc web does not have this issue. I suspect envoy is a bit too eager with its encoding.


how to disable weekend and how to start from monday in angular 7

Reproduction
Use StackBlitz to reproduce your issue: https://stackblitz.com/fork/components-issue
Steps to reproduce:

https://stackblitz.com/angular/gxqrbdmbkkj

Expected Behavior
What behavior were you expecting to see?
I want to disable weekend and should start form monday
Actual Behavior
What behavior did you actually see?
bydefault it is starting from sunday
Environment

Angular:
CDK/Material:
Browser(s):
Operating System (e.g. Windows, macOS, Ubuntu):
Angular 7
<input matInput [min]="minDate" [matDatepicker]="picker"
placeholder="{{'checkout.summary.placeholder' | translate}}" [(ngModel)]="data['returnDate']">
<mat-datepicker-toggle matSuffix [for]="picker">
<mat-datepicker #picker>

I want to disable weekend

Have a look at the datepicker examples
https://v7.material.angular.io/components/datepicker/examples
"Datepicker with filter validation"

and should start form monday

The start day is determined by the locale.

https://stackblitz.com/edit/angular-dateadapter-example-stackoverflow1-oarzsz?file=app/datepicker-overview-example.ts
You can simply add a CustomDateAdapter, and which one return the getFirstDayOfWeek(), and you can user a filter method which one can disable the weekend days.

Thanks @Flashunt  @manklu  its works


Create addressable monitor

Description

Like https://github.com/sigstore/rekor-monitor/pull/37, we could provide an HTTP or gRPC endpoint for querying for the latest witnessed checkpoint.
We should investigate Trillian's serverless examples before pursuing this. I'm hesitant to add this at this moment additionally, since the Rekor checkpoint updates too frequently to be able to witness the same checkpoint as other witnesses.

Not going to do this - we're not turning the monitor into a witness.


how to tune the IR emitter power? dynamically in ROS2-foxy

Before opening a new issue, we wanted to provide you with some useful suggestions (Click "Preview" above for a better view):

Consider checking out SDK examples.
Have you looked in our documentations?
Is you question a frequently asked one?
Try searching our GitHub Issues (open and closed) for a similar issue.

All users are welcomed to report bugs, ask questions, suggest or request enhancements and generally feel free to open new issue, even if they haven't followed any of the suggestions above :)

Required Info

Camera Model
{ R200 / F200 / SR300 / ZR300 / D400 }

Firmware Version
(Open RealSense Viewer --> Click info)

Operating System & Version
{Win (8.1/10) / Linux (Ubuntu 14/16/17) / MacOS

Kernel Version (Linux Only)
(e.g. 4.14.13)

Platform
PC/Raspberry Pi/ NVIDIA Jetson / etc..

SDK Version
{ legacy / 2.. }

Language
{C/C#/labview/nodejs/opencv/pcl/python/unity }

Segment
{Robot/Smartphone/VR/AR/others }

Issue Description
<Describe your issue / question / feature request / etc..>

Hi @cheukwaylee  May I first ask if you are using the RealSense ros2 wrapper (version numbers up to 3.2.2) or the ros2_beta wrapper (such as version 4.0.4).  Thanks!

yes, i am using this wrapper "https://github.com/IntelRealSense/realsense-ros/tree/ros2" which can set the d435i parameter in "rs_launch.py", but idk how i can tune the laser power ( my project is about SLAM by using d435i in low-light environment, but the IR pattern makes the ORB feature extractor confusing). THANKS!

in ROS1-noetic, rqt_reconfigure can be used to tune the parameters including laser power, but i cannot find similar function in ROS2

ROS2 uses a different parameter system to ROS1's rqt_reconfigure / dynamic_reconfigure.
In the ros2 wrapper you can still access the graphical user interface of rqt_reconfigure to make real-time canges to settings with the command ros2 run rqt_reconfigure rqt_reconfigure after launch has been completed.
https://github.com/IntelRealSense/realsense-ros/tree/ros2#view-and-modify-camera-controls-params-in-runtime
Alternatively, https://github.com/IntelRealSense/realsense-ros/issues/1379 provides information about setting the value of the laser_power parameter in the ros2 wrapper using a .yaml file.

i tried "ros2 run rqt_reconfigure rqt_reconfigure" in ROS2, but i can NOT see a tune-able parameter about laser power. (i also tried in ROS1-noetic where i can see the laser power tunner)

Is there an emitter_enabled option in ROS2 rqt_reconfigure that you could change?  Disabling the emitter would have the same effect of removing the dot pattern as minimizing the value of laser_power does.  I believe that emitter_enabled should be in the stereo_module section of rqt_reconfigure.

ok, i can find ".emitter_enabled" and ".laser_power" both in "depth_module", so now they both can be tunned in ROS2-foxy rqt_reconfigure. THANKS :)
as for my real application, i dont wanna completely turn off the IR laser, cuz in the low-light environment, i guess some IR can help with visibility, but i dont wanna the dot pattern confuses the ORB feature point extractor, it is a conflict i need to solve.

400 Series cameras can make use of any visible light in a scene to assist with depth analysis, so it is possible to use an external patternless IR illuminator lamp in close proximity to the camera in low-light / dark scenes, as described at https://github.com/IntelRealSense/librealsense/issues/2000
When adjusting Laser Power, the projector should stay on if the Laser Power is '1' but the dot pattern will be invisible to the camera.

instead of using an external patternless IR illuminator lamp, I would like to see if it is possible to remove the IR white dot pattern if the pattern is provided by manufacturer as a part of the datasheet. because i suppose the pattern can be considered as the upper layer adding directly to the real scene.

The D415 camera model supports using a camera configuration preset called Left Imager Color w/o IR Pattern that can remove the dot pattern by adjusting the camera's color correction matrix settings.
https://dev.intelrealsense.com/docs/d400-series-visual-presets#section-preset-table
Further information about this can be found in Point 3 of the section of Intel's camera tuning guide linked to below.
https://dev.intelrealsense.com/docs/tuning-depth-cameras-for-best-performance#section-use-the-left-color-camera

I just wanted to highlight that the RealSense color correction matrix technique for dot pattern removal exists even if it is not suited to the D435i model, in case that changing camera model was a possibility for your project.
I would reiterate my advice above to try setting Laser Power to '1' so that the pattern disappears but the projector remains on.
Alternatively, try enabling emitter_on_off in ROS so that the pattern alternates on and off each frame.

maybe i got ur point. when i set "emitter_on_off", for example, in the odd frame, i can collect an image with IR pattern, and in the even frame, without but (in my intuition) illuminated due to "Persistence of vision". then i can just use the even frame as my input, but how can i separate these two kinds of images one by one? there would be any flag in the image stream that i can use to distinguish? i am using "ros2 launch realsense2_camera rs_launch.py" to publish the images via topic. any suggestion will be highly appreciated!!

A RealSense ROS team member explains at https://github.com/IntelRealSense/realsense-ros/issues/1657#issuecomment-968920694 a method for differentiating between on and off frames in ROS2 (the ros2 branch) by using the sequence_id filter which is part of the High-Dynamic Range (HDR) feature.

Hi @cheukwaylee  Do you require further assistance with this case, please?  Thanks!

Hi. no for now, i close this issue. and if there is anything else that needs your help later, i will reopen it, THANKS!

You are very welcome.  Thanks very much for the update!

Hi! I really would like to know more info about "the position of IR white dot pattern". as u told me before i can only get the pattern as following picture shows, but i donot know the exact position and size of each white dot. and what is the meaning of "91x65deg" in d435?
what i expect to know is,  when the resolution is set as 640x480 for example, the pixel coordinates of each dot, and their radius, and i guess it should be proportional when using other resolutions. THANKS in advance!

The projected pattern is semi-random, so you would likely not be able to obtain the position of each dot unless you identify pixels on the infrared image that have a particular intensity range.
Intel have published a white-paper guide to projectors at the link below.
https://dev.intelrealsense.com/docs/projectors
The angle values for each camera model refer to the angle of emission of the projector.  The D435 has a wider emission angle but fewer dots as a consequence.  The dots act as a texture source for the camera to analyze for depth information when they are projected onto a surface / object, so the more dots that there are in a scene the better.  For example, two cameras with overlapping fields of view should provide better depth information due to there being redundancy in the data in the area where the two fields of view and pattern projections overlap.
The white-paper guide has a section dedicated to the dot pattern at the link below that discusses dot pattern density versus resolution.
https://dev.intelrealsense.com/docs/projectors#section-5-the-dot-pattern

THANKS for ur reply. I would try with ur suggestion.
and there is another question i would like to ask u.
how can I align the depth image to the left or right image, I can only find the solution to align depth to RGB.

The depth image is already perfectly aligned to the left IR image as they originate from the same sensor and so depth-IR alignment does not need to be performed.  The SDK documentation provides the following information about this.

The Left IR camera has the benefit of always 1. Being pixel-perfect aligned, calibrated, and overlapped with the depth map, 2. Perfectly time-synchronized, 3. Requires no additional computational overhead to align color-to-depth, and 4. Gives no additional occlusion artifacts, because it is exactly co-aligned.

In the RealSense ROS wrapper, only depth to color alignment is supported when align_depth is true.
When aligning to IR in the librealsense SDK instead of the ROS wrapper, a way to align depth, IR and RGB together in the same image is demonstrated in Python code at https://github.com/IntelRealSense/librealsense/issues/5093

Hi @cheukwaylee  Do you require further assistance with this case, please?  Thanks!

Thanks very much @cheukwaylee for the update!


Cannot use === with Enum Literal Type

From https://github.com/Microsoft/vscode/issues/16819
TypeScript Version:  2.1.4-insiders.20161206
Code
enum State {
	INVALID = 0,
	FIRST = 1
}

const invalid = State.INVALID;
invalid === State.FIRST

Expected behavior:
No error since invalid is a subtype of State.INVALID
Actual behavior:
Error:
Operator '===' cannot be applied to types 'State.INVALID' and 'State.FIRST'.

This also does not work:
const invalid: State = State.INVALID;
invalid === State.FIRST

You have to be explicit:
const invalid = State.INVALID as State;
invalid === State.FIRST

or
const invalid = State.INVALID;
invalid as State === State.FIRST

This is an intentional breaking change. the compiler can verify that invalid can not have any other values. You can find more information at https://github.com/Microsoft/TypeScript/wiki/Breaking-Changes#literal-types-are-inferred-by-default-for-const-variables-and-readonly-properties

Ok, thanks. The actual control flow on the VSCode side was more complicated (https://github.com/Microsoft/vscode/pull/16861/files) so I opted to just add the explicit cast. I strongly suspect the compiler is correct in this case too, but wasn't 100% sure


Allow default value for path-to-changelog

A default value was already set. However, due to the usage of required: true, it was not usable. Changelog paths are common enough that a default value is warranted.

If merged and published, would be useful for https://github.com/ambanum/OpenTermsArchive/pull/957 cc @ndpnt.


The JSON property name for 'Schema.NET.IHospital.OpeningHours' collides with another property.

Describe the bug
Can not serialize a schema.net.Physician while using schema.net.MedicalWebPage
Properties with the same name.
hospital ->CivicStructureAndEmergencyServiceAndMedicalOrganization ->
[JsonPropertyName("openingHours")]
[JsonPropertyOrder(307)]
[JsonConverter(typeof(ValuesJsonConverter))]
public override OneOrMany<string> OpeningHours { get; set; }

Physician-> MedicalBusinessAndMedicalOrganization -> LocalBusinessAndOrganization ->
[JsonPropertyName("openingHours")]
[JsonPropertyOrder(238)]
[JsonConverter(typeof(ValuesJsonConverter))]
public OneOrMany<string> OpeningHours { get; set; }

Steps to reproduce
//Site Default
MedicalAudience medicalAudience = new MedicalAudience()
{
	RequiredMinAge = 0,
	RequiredMaxAge = 21,
	SuggestedMinAge = 0,
	SuggestedMaxAge = 21,
	SuggestedGender = "All genders"
};

MedicalWebPage website = new MedicalWebPage()
{
	MedicalAudience = medicalAudience
};

Physician physician = new Physician()
{
	Name = doctorProfilePage.DisplayName,
	Description = doctorProfilePage.CurrentPage.SeoSettings.Description,
};

if (Uri.IsWellFormedUriString(doctorProfilePage.Image, UriKind.Absolute))
{
	Uri outUri;

	if (Uri.TryCreate(doctorProfilePage.Image, UriKind.RelativeOrAbsolute, out outUri))
	{
		ImageObject image = new ImageObject()
		{
			ThumbnailUrl = outUri,
			Url = outUri
		};

		physician.Image = image;
		physician.Photo = image;
		website.Image = image;
	}
}

physician.Address = doctorProfilePage.GetSchemaAddress();
physician.Telephone = doctorProfilePage.GetSchemaPhone();
physician.Identifier = doctorProfilePage.ProfileId.ToString();
physician.Id = baseUri;

//website.MainEntity = mainHospital;
website.About = physician;

return website.ToHtmlEscapedString()  //Fails here. on ToHtmlEscapedString

Stack trace
System.InvalidOperationException: The JSON property name for 'Schema.NET.IHospital.OpeningHours' collides with another property.
at System.Text.Json.ThrowHelper.ThrowInvalidOperationException_SerializerPropertyNameConflict(Type type, String propertyName)
at System.Text.Json.Serialization.Metadata.JsonTypeInfo.AddProperty(JsonPropertyInfo jsonPropertyInfo, PropertyHierarchyResolutionState& state)
at System.Text.Json.Serialization.Metadata.DefaultJsonTypeInfoResolver.AddMembersDeclaredBySuperType(JsonTypeInfo typeInfo, Type currentType, Boolean shouldCheckMembersForRequiredMemberAttribute, PropertyHierarchyResolutionState& state)
at System.Text.Json.Serialization.Metadata.DefaultJsonTypeInfoResolver.PopulateProperties(JsonTypeInfo typeInfo)
at System.Text.Json.Serialization.Metadata.DefaultJsonTypeInfoResolver.CreateTypeInfoCore(Type type, JsonConverter converter, JsonSerializerOptions options)
at System.Text.Json.Serialization.Metadata.DefaultJsonTypeInfoResolver.GetTypeInfo(Type type, JsonSerializerOptions options)
at System.Text.Json.JsonSerializerOptions.GetTypeInfoNoCaching(Type type)
at System.Text.Json.JsonSerializerOptions.CachingContext.CreateCacheEntry(Type type, CachingContext context)
--- End of stack trace from previous location ---
at System.Text.Json.Serialization.Metadata.JsonTypeInfo.Configure()
at System.Text.Json.Serialization.Metadata.JsonTypeInfo.g__ConfigureSynchronized|161_0()
at System.Text.Json.Serialization.Metadata.JsonPropertyInfo.Configure()
at System.Text.Json.Serialization.Metadata.JsonTypeInfo.ConfigureProperties()
at System.Text.Json.Serialization.Metadata.JsonTypeInfo.Configure()
at System.Text.Json.Serialization.Metadata.JsonTypeInfo.g__ConfigureSynchronized|161_0()
at System.Text.Json.JsonSerializer.Serialize(Utf8JsonWriter writer, Object value, Type inputType, JsonSerializerOptions options)
at Schema.NET.ValuesJsonConverter.WriteObject(Utf8JsonWriter writer, Object value, JsonSerializerOptions options) in /_/Source/Common/ValuesJsonConverter.cs:line 184
at System.Text.Json.Serialization.JsonConverter`1.TryWrite(Utf8JsonWriter writer, T& value, JsonSerializerOptions options, WriteStack& state)
at System.Text.Json.Serialization.Metadata.JsonPropertyInfo`1.GetMemberAndWriteJson(Object obj, WriteStack& state, Utf8JsonWriter writer)
at System.Text.Json.Serialization.Converters.ObjectDefaultConverter`1.OnTryWrite(Utf8JsonWriter writer, T value, JsonSerializerOptions options, WriteStack& state)
at System.Text.Json.Serialization.JsonConverter`1.TryWrite(Utf8JsonWriter writer, T& value, JsonSerializerOptions options, WriteStack& state)
at System.Text.Json.Serialization.JsonConverter`1.WriteCore(Utf8JsonWriter writer, T& value, JsonSerializerOptions options, WriteStack& state)
at System.Text.Json.Serialization.Metadata.JsonTypeInfo`1.Serialize(Utf8JsonWriter writer, T& rootValue, Object rootValueBoxed, Boolean isInvokedByPolymorphicConverter)
at System.Text.Json.Serialization.Metadata.JsonTypeInfo`1.SerializeAsObject(Utf8JsonWriter writer, Object rootValue, Boolean isInvokedByPolymorphicConverter)
at System.Text.Json.Serialization.Metadata.JsonTypeInfo`1.Serialize(Utf8JsonWriter writer, T& rootValue, Object rootValueBoxed, Boolean isInvokedByPolymorphicConverter)
at System.Text.Json.JsonSerializer.WriteString[TValue](TValue& value, JsonTypeInfo`1 jsonTypeInfo)
at Schema.NET.Thing.ToString() in /_/Source/Common/Thing.Partial.cs:line 23
at SeattleChildrens.Features.SchemaExtensions.GenerateSchema(IHtmlHelper helper, IWebPage viewModel) in C:\repos\SeattleChildrens.orgCore\SeattleChildrens.Features\Infrastructure\Extensions\SchemaExtensions.cs:line 593

Properties with the same Name
hospital ->CivicStructureAndEmergencyServiceAndMedicalOrganization ->
[JsonPropertyName("openingHours")]
[JsonPropertyOrder(307)]
[JsonConverter(typeof(ValuesJsonConverter))]
public override OneOrMany<string> OpeningHours { get; set; }

Physician-> MedicalBusinessAndMedicalOrganization -> LocalBusinessAndOrganization ->
[JsonPropertyName("openingHours")]
[JsonPropertyOrder(238)]
[JsonConverter(typeof(ValuesJsonConverter))]
public OneOrMany<string> OpeningHours { get; set; }

Expected behaviour
Unique names and ability to serialize.
Schema objects
schema.net.Physician
schema.net.MedicalWebPage

we are using .net 6
attattachedatched is the Json that produces the error.
I am a bit lost.
We use Schema.NET.MedicalWebPage
then we fill out the info for the Schema.NET.Physician nothing to do with the hospital. is even included when we go to serialize this.
how ever when i used Schema.NET.Person instead of Schema.NET.Physician it works fine.
Thanks,
David Fewless
Senior Web Developer, Diagram
[A close-up of a clock  Description automatically generated with medium confidence]
e<EMAIL_ADDRESS>p:<PHONE_NUMBER>
w: www.wearediagram.comhttp://www.wearediagram.com/
he/him
[cid:c0afc9ac-d344-4d09-bfe9-33d4e05546a9] https://twitter.com/wearediagram   [cid:54944cde-315f-4968-a540-0571ae6566b1] https://www.linkedin.com/company/19151275/admin/   [cid:22682a1f-e095-42d0-991e-71db8b4a0d15] https://www.instagram.com/heydiagram

From: James Turner @.>
Sent: Thursday, June 8, 2023 9:23 AM
To: RehanSaeed/Schema.NET @.>
Cc: David Fewless @.>; Mention @.>
Subject: Re: [RehanSaeed/Schema.NET] The JSON property name for 'Schema.NET.IHospital.OpeningHours' collides with another property. (Issue #603)
Hi @fewless2019https://github.com/fewless2019 - I can't recreate the problem you've describe by using the steps you've mentioned. Can you tell me the version of .NET you're using, whether you're pulling in your own version of System.Text.Json (and what version that is), and also have a look over the steps to reproduce that you've provided.
Based on the exception message, I don't think the problem is to do with the Physician inheritance but the Hospital inheritance. Specifically CivicStructureAndEmergencyServiceAndMedicalOrganization has OpeningHours and so does LocalBusinessAndOrganizationAndPlace. And even then, the exception refers to the interface IHospital, not the implementation.
The strange part though is these combined types have several properties that are overridden, not just OpeningHours and I don't see anything special about OpeningHours in terms of how it is defined in Schema.NET nor any reference in your steps to reproduce.
—
Reply to this email directly, view it on GitHubhttps://github.com/RehanSaeed/Schema.NET/issues/603#issuecomment-1582575081, or unsubscribehttps://github.com/notifications/unsubscribe-auth/AWNF4UCUY64AQXNVILFGCCLXKHG33ANCNFSM6AAAAAAY4VGQEU.
You are receiving this because you were mentioned.Message ID: @.***>

We are using .Net6
Attached is the Json.
I fixed this by creating my own physician class and removing the hospital affiliation variable.
/////
///// A hospital with which the physician or office is affiliated.
/////
//[JsonPropertyName("hospitalAffiliation")]
//[JsonPropertyOrder(407)]
//[JsonConverter(typeof(ValuesJsonConverter))]
//public OneOrMany HospitalAffiliation { get; set; }
Thanks,
David Fewless
Senior Web Developer, Diagram
[A close-up of a clock  Description automatically generated with medium confidence]
e<EMAIL_ADDRESS>p:<PHONE_NUMBER>
w: www.wearediagram.comhttp://www.wearediagram.com/
he/him
@.*** https://twitter.com/wearediagram @.*** https://www.linkedin.com/company/19151275/admin/ @.*** https://www.instagram.com/heydiagram
From: James Turner @.>
Sent: Thursday, June 8, 2023 9:23 AM
To: RehanSaeed/Schema.NET @.>
Cc: David Fewless @.>; Mention @.>
Subject: Re: [RehanSaeed/Schema.NET] The JSON property name for 'Schema.NET.IHospital.OpeningHours' collides with another property. (Issue #603)
Hi @fewless2019https://github.com/fewless2019 - I can't recreate the problem you've describe by using the steps you've mentioned. Can you tell me the version of .NET you're using, whether you're pulling in your own version of System.Text.Json (and what version that is), and also have a look over the steps to reproduce that you've provided.
Based on the exception message, I don't think the problem is to do with the Physician inheritance but the Hospital inheritance. Specifically CivicStructureAndEmergencyServiceAndMedicalOrganization has OpeningHours and so does LocalBusinessAndOrganizationAndPlace. And even then, the exception refers to the interface IHospital, not the implementation.
The strange part though is these combined types have several properties that are overridden, not just OpeningHours and I don't see anything special about OpeningHours in terms of how it is defined in Schema.NET nor any reference in your steps to reproduce.
—
Reply to this email directly, view it on GitHubhttps://github.com/RehanSaeed/Schema.NET/issues/603#issuecomment-1582575081, or unsubscribehttps://github.com/notifications/unsubscribe-auth/AWNF4UCUY64AQXNVILFGCCLXKHG33ANCNFSM6AAAAAAY4VGQEU.
You are receiving this because you were mentioned.Message ID<EMAIL_ADDRESS>

Just ran across this issue, since I saw a similar issue serializing 'MedicalStudy'.
I'm getting this error:
The JSON property name for 'Schema.NET.IDrug.Funding' collides with another property.
This is using .NET 8.0 version of System.Text.Json.

Looks like my serialization issue was due to 'Drug' being a subclass of both Product and Substance, and the 'Funding' property is defined in both places.
Not sure how Schema.NET is supposed to handle these kinds of situations?
I had to create a private version of the library, and remove 'Product' from the JSON-LD file to get it working.
cc: @Turnerj @RehanSaeed


Error while running fmriprep-docker

Hi all,
I'm trying to run fmriprep-docker but keep getting an error while initiating it:

("docker: Error response from daemon: error while creating mount source path '/usr/local/freesurfer/license.txt': mkdir /usr/local/freesurfer: read-only file system.")
I've tried running it with -u $UID as well and with sudo permissions, but still got the same result.
Would appreciate any help.
Thanks!

Hi @Hershkovitz-hub, you need to tell fmriprep-docker where your FreeSurfer license is found in the host, e.g.:
fmriprep-docker --fs-license-file $HOME/license.txt ...

please check https://fmriprep.readthedocs.io/en/latest/docker.html and https://fmriprep.readthedocs.io/en/latest/usage.html#the-freesurfer-license

Feel free to reopen this if there are still issues


Fetch missing icons from CoinGecko

There is always new crypto around the corner, as I've created this patch to be able to dynamically fetch any missing icons from CoinGecko's API

This is good. Even nicer would be if it used the async downloader service to update the icon after it has been fetched so that there's no delay when setting an asset. I don't currently have the time to work on this, but it's an idea if you are keen :)

I forgot to say thanks :) Thanks!

Yes, I thought about it but didn't have the needed time to check out how the service was working.
I'll post an updated version when I have some spare time


Doesn't work on sketch 53

Relabel Button.js
works with this changes
60 > initialValue: textLayer,
130 > initialValue: textLayer,
172 > // sel.setIsSelected(false);
173 > // sel.setIsSelected(true);

Hi @kenmoore , I'm a huge user of this plugin. I always recommend it to my students and put it in their workflows. Any way you can make it work on Sketch 53? Thanks!

I edited the sketch plugin JS files with what @pavelneznanov wrote and added it to Relabel Button Right Aligned.js as well.
The following lines need to be changed:
58 > initialValue: textLayer,
125 > initialValue: textLayer,
167 > // sel.setIsSelected(false);
168 > // sel.setIsSelected(true);

Sorry for the delays, folks -- super busy week between family and work.
Grateful for the pull request, @chiawase!

New version is awesome. The focus on the field is back again. Thank you so much, I'm so grateful ! 💪


Media Widget not working with Jellyfin

Environment
Docker
Version
0.11.5
Describe the problem
Media widget is not working with jellyfin service.
As per #739 , I've reviewed jellyfin app configured on Homarr (URL, user/pass secrets) but the Media Widget shows the Jellyfin badge sorrounded by a red circle.
Also, reviewing homarr logs I saw error below (some local info redacted for privacy reasons):
ERROR  failed to communicate with media server 'xxxx' (xxx): TypeError: sessions.data.map is not a function

Additional info
ERROR  failed to communicate with media server 'xxxx' (xxx): TypeError: sessions.data.map is not a function

Please tick the boxes

[X] You've read the docs
[X] You've checked for duplicate issues
[X] You've tried to debug yourself

My bad, I overlooked this issue. Let me quickly investigate...

After testing a bit, please confirm that none of these issues apply:
https://homarr.dev/docs/widgets/media-server#common-issues
Your configuration is most likely faulty.

Hi @manuel-rw ,
Just double checked all common issues again yesterday.
Issue is still happening, some test to troubleshoot the issue?

Sorry we didn't reply earlier. To troubleshoot you can try to :

connect to the Homarr container via portainer or with docker exec ash (irrc ash is the alpine version of bash) then you can try to ping the internal address of Jellyfin.
Also check the JSON file of your config at the mountpoint you specified to check if it contains the "apiKey" field with the correct value for Jellyfin
Try using a new jellyfin install just to check if it works with it (i'd recommend the linuxserver image)
Check that your Jellyfin and Homarr install in the same Docker

Hope you can figure out what is causing problems with these steps, please tell me if you encounter problems with any of the steps mentioned above. Also, if you have experience with nodejs or javascript you could try to debug yourself in the code with print statements in the code for Jellyfin

Hi, is this still happening, or can we close this issue?

Still happening.
I have pending testing with a dummy Jellyfin on the same host (as homarr and Jellyfin are in different hosts).
Also, not sure about apiKey, as Jellyfin integration works with user+pass.

I think ajnart meant username and password. They should be in your config.
Is the error message still the same?

Hi @manuel-rw ,
Thanks for the feedback.
After reviewing the configuration, I saw that password was not populated.
The password used for homarr account contained a "$", which seems was not really liked by homarr.
I have updated the password, with a new one without "$", and it's working perfectly.
Probably it will be worth to take a look on how homarr manages provided passwords.

So the password, that you entered in the field, while editing the Jellyfin app, did not save itself to the configuration file?
Am I understanding that correctly?

Yes, correct.

Did you remember to exit edit mode and save your configuration, when you entered the password?
If yes, can you give the exact reproduction steps to reproduce this issue?

This issue can be resolved, right?

@kurotorakun


Jio

please test this

please test this

please test this

closing this as it was really a dev brach, replaced with #454


Some configurable Number formatting options

Is your feature request related to a problem? Please describe.
Would be great if this cool plugin also does Number formatting (like in Excel) like currency, accounting, etc.
Describe the solution you'd like
For example:
format any number with some delimiter (, with configurable/localized spacing support):
12345678 => 12,345,678

or for _ as a numeric literal
12345678 => 12_345_678

May also be good to consider some flurishes like localized currency processing etc (like 123 => 123.00, etc),
but I'll leave that to the implementation :)
Describe alternatives you've considered
I tried to look at the various options I got with this plugin, in the context menus and such, but didn't find any options with this feature.
I requested a feature in StringManipulation another nice plugin, which does not support this yet.
Looked at other conversion tools, no one seems to be tackling this problem.
Additional context
This will help quickly parse, format, and process long string of numbers.
Please help point me to any other tool or plugin that helps with this currently, that I may not have found yet 👍

Hello! It's an interesting offer, I think I can support it.
Actually, the cursory search didn't get any plugins with this functionality.


First person view is possible, at least with mc_port

In single player open to lan with cheats and survival, use the port for mc_port, once the bot joins. Then run /gamemode spectator command in in-game text, from the player in single player, then run /spectate bot command in in-game text.
This should work until the bot leaves and rejoins. Then you just need to rerun the /spectate bot command. There is definitely a way to automate this with repeating command blocks and chains, but idk enough about command blocks to be able to figure it out right now.

Hi, thanks for pointing out this method! You're right that commands in games can help the player follow the first-person view of the bot. However, we still cannot see the bot's status bar in the game. Also, this needs some human intervention during the learning process. One possible solution could be using a command block to consistently execute the /spectate command.

@TimeLordRaps @xieleo5 Tks all.When I try to run the code,I can't see the first view.I feel a little nervous.I told myself where's my bot, What's doing the bot in this moment.:)

@go-maple what code, the in-game commands?
The first in-game command: /gamemode spectator puts your gamemode into spectator, which is just a way to spectate the world, without interacting with it. While in spectator gamemode you can go through walls and other things with standard movement controls.
The secondin-game command: /spectate bot should immediately transport you into the body of the bot, as long as the bot is on the server and you are in the spectator gamemode.
To see your bot move, you can observe from the default first person perspective or to see from a 3rd person perspective: While inside the bot, or generally, press f5, then pressing f5 again will give a perspective looking straight at the character's face, then f5 for a third time will bring it back to first person perspective. All these things I am talking about occur from within an mc_port of the game. So a single player mc launcher version of the game. I have not experimented at all using the azure login.

To clarify, when the bot leaves the server, you no longer are spectating it, however you remain in spectator gamemode. Once the bot rejoins the server, you need to reuse the second in-game command: /spectate bot to once again spectate from the bot's perspective(s).

I wrote a script to automate it a bit. It requires the following settings in the minecraft server:
root@mc-voyager:~/mc_server# grep rcon server.properties
broadcast-rcon-to-ops=false
enable-rcon=true
rcon.password=hunter2
rcon.port=25575

Then the following script, updating the variables where relevant. Make sure to pip install mcrcon before running.
import time
from mcrcon import MCRcon
import math
import re

# Server RCON connection details
rcon_host = "localhost"
rcon_port = 25575
rcon_password = "hunter2"

# Time interval (in seconds) to check for player joining and teleport
check_interval = 0.1

# Dictionary to track the online status of the specified player and bot
spectator_username = "theblazehen"
player_status = {spectator_username: False, "bot": False}
previous_player_status = player_status.copy()

# Distance to move away from bot in the X and Z directions
distance = 3

# Height offset for the specified player above bot
height_offset = 1

def main():
    global player_status, previous_player_status
    while True:
        with MCRcon(rcon_host, rcon_password, rcon_port) as mcr:
            response = mcr.command("list")
            players_string = response.strip().split(": ")[1]

            # Handle the case when there are no players online
            if players_string == "":
                players_online = []
            else:
                players_online = players_string.split(", ")

            # Update the online status of the specified player and bot
            for player in player_status:
                player_status[player] = player in players_online

            # Check if the online status of either the specified player or bot has changed
            if player_status != previous_player_status:
                previous_player_status = player_status.copy()

                # Check if both the specified player and bot are online
                if player_status[spectator_username] and player_status["bot"]:
                    mcr.command(f"gamemode spectator {spectator_username}")

            # Continuously teleport the specified player behind bot and face towards bot's back
            if player_status[spectator_username] and player_status["bot"]:
                response = mcr.command("data get entity bot Pos")
                bot_position = [float(coord) for coord in re.findall(r"[-+]?\d*\.\d+|\d+", response)]

                response = mcr.command("data get entity bot Rotation")
                bot_rotation = [float(coord) for coord in re.findall(r"[-+]?\d*\.\d+|\d+", response)]

                x, y, z = bot_position
                yaw = bot_rotation[0]

                # Calculate new position for the specified player
                x_new = x - distance * math.sin(math.radians(yaw))
                z_new = z - distance * math.cos(math.radians(yaw))

                # Calculate pitch and yaw to face bot's back
                dx, dy, dz = x - x_new, y - (y + height_offset), z - z_new
                distance_2d = math.sqrt(dx * dx + dz * dz)
                pitch = -math.degrees(math.atan2(dy, distance_2d))
                yaw_to_face_bot = yaw

                # Teleport the specified player to the new position and face towards bot's back
                mcr.command(f"tp {spectator_username} {x_new} {y + height_offset} {z_new} {yaw_to_face_bot} {pitch}")

        time.sleep(check_interval)
if __name__ == "__main__":
    main()

I wrote a script to automate it a bit. It requires the following settings in the minecraft server:

I haven't tested it yet, but why face the bot's back. Wouldn't you want the exact direction it's facing, and location to emulate "being" the bot, or is your intention to have a solid view of the bot, if so assuming this would run as does what it looks like it would do a pretty good job of it.
I do not know about the library you used, but I assume there's a way maybe to set the inventory and status of the player to the bot? Well, I guess that wouldn't really work for complete recording purposes because spectator mode doesn't show those things. So best case scenario I can imagine is 2 players, 1 used to record hotbar, health, and hunger, and the other recording the first-person view, then somehow having to combine the two recordings. Otherwise, I think you have more or less solved the general recording problem quite well. Unless someone wants to try to implement a solution for first-person with status, I think I'm going to close this.

In single player open to lan with cheats and survival, use the port for mc_port, once the bot joins. Then run /gamemode spectator command in in-game text, from the player in single player, then run /spectate bot command in in-game text.
This should work until the bot leaves and rejoins. Then you just need to rerun the /spectate bot command. There is definitely a way to automate this with repeating command blocks and chains, but idk enough about command blocks to be able to figure it out right now.

I can see the first person view and hear the sound of the game.

I wrote a script to automate it a bit. It requires the following settings in the minecraft server:
root@mc-voyager:~/mc_server# grep rcon server.properties
broadcast-rcon-to-ops=false
enable-rcon=true
rcon.password=hunter2
rcon.port=25575

Then the following script, updating the variables where relevant. Make sure to pip install mcrcon before running.
import time
from mcrcon import MCRcon
import math
import re

# Server RCON connection details
rcon_host = "localhost"
rcon_port = 25575
rcon_password = "hunter2"

# Time interval (in seconds) to check for player joining and teleport
check_interval = 0.1

# Dictionary to track the online status of the specified player and bot
spectator_username = "theblazehen"
player_status = {spectator_username: False, "bot": False}
previous_player_status = player_status.copy()

# Distance to move away from bot in the X and Z directions
distance = 3

# Height offset for the specified player above bot
height_offset = 1

def main():
    global player_status, previous_player_status
    while True:
        with MCRcon(rcon_host, rcon_password, rcon_port) as mcr:
            response = mcr.command("list")
            players_string = response.strip().split(": ")[1]

            # Handle the case when there are no players online
            if players_string == "":
                players_online = []
            else:
                players_online = players_string.split(", ")

            # Update the online status of the specified player and bot
            for player in player_status:
                player_status[player] = player in players_online

            # Check if the online status of either the specified player or bot has changed
            if player_status != previous_player_status:
                previous_player_status = player_status.copy()

                # Check if both the specified player and bot are online
                if player_status[spectator_username] and player_status["bot"]:
                    mcr.command(f"gamemode spectator {spectator_username}")

            # Continuously teleport the specified player behind bot and face towards bot's back
            if player_status[spectator_username] and player_status["bot"]:
                response = mcr.command("data get entity bot Pos")
                bot_position = [float(coord) for coord in re.findall(r"[-+]?\d*\.\d+|\d+", response)]

                response = mcr.command("data get entity bot Rotation")
                bot_rotation = [float(coord) for coord in re.findall(r"[-+]?\d*\.\d+|\d+", response)]

                x, y, z = bot_position
                yaw = bot_rotation[0]

                # Calculate new position for the specified player
                x_new = x - distance * math.sin(math.radians(yaw))
                z_new = z - distance * math.cos(math.radians(yaw))

                # Calculate pitch and yaw to face bot's back
                dx, dy, dz = x - x_new, y - (y + height_offset), z - z_new
                distance_2d = math.sqrt(dx * dx + dz * dz)
                pitch = -math.degrees(math.atan2(dy, distance_2d))
                dyaw = math.degrees(math.atan2(dx, dz))
                yaw_to_face_bot = (dyaw + 180) % 360

                # Teleport the specified player to the new position and face towards bot's back
                mcr.command(f"tp {spectator_username} {x_new} {y + height_offset} {z_new} {yaw_to_face_bot} {pitch}")

        time.sleep(check_interval)
if __name__ == "__main__":
    main()

Cool. Did you manage to run the Voyager code with the MC server?

@theblazehen I tried to run your code by the following steps:

Install mcrcon via pip
create a folder call mc_server in $HOME.
add a file called server.properties and put the following content into it:

broadcast-rcon-to-ops=false
enable-rcon=true
rcon.password=hunter2
rcon.port=25575

Run the Python script in the same directory.

But in step 4, I got the following issue:
raceback (most recent call last):
  File "/Users/me/mc_server/mc_auto_spectate_bot.py", line 79, in <module>
    main()
  File "/Users/me/mc_server/mc_auto_spectate_bot.py", line 28, in main
    with MCRcon(rcon_host, rcon_password, rcon_port) as mcr:
  File "/Users/me/miniconda3/lib/python3.9/site-packages/mcrcon.py", line 57, in __enter__
    self.connect()
  File "/Users/me/miniconda3/lib/python3.9/site-packages/mcrcon.py", line 77, in connect
    self.socket.connect((self.host, self.port))
ConnectionRefusedError: [Errno 61] Connection refused

Do you know why?

@GoingMyWay It requires you to be running a standalone minecraft server. As mentioned in #88 , will be writing the docs for that later today

@GoingMyWay It requires you to be running a standalone minecraft server. As mentioned in #88 , will be writing the docs for that later today

@theblazehen Cool. Thank you. I am looking forward to see it.

@theblazehen Hi, thanks for your useful scripts.
After running your mcron script, I continuously get the following info:
[15:55:08] [RCON Client /<IP_ADDRESS> #999/INFO]: Thread RCON Client /<IP_ADDRESS> shutting down
[15:55:08] [RCON Listener #1/INFO]: Thread RCON Client /<IP_ADDRESS> started
However, the view in my minecraft doesn't move. Do you have any suggestions on it?
Ps: I have a gui, so I just link to the local server in "multiple players".


Valid itypes for jump target cache mode

Jump target cache mod is used for uninferable jump inst. The itype = 8, 10, 12, 14, right?

And 6.  See sijump definition in Table 4


Replace proprietary Memtest86 with free Memtest86+ on NixOS systems with UEFI

Description of changes

Now that Memtest86+ supports UEFI and the 64-bit Linux boot handover protocol, we can use that on UEFI systems instead of falling back to the proprietary Passmark Memtest86.
GRUB2 no longer needs any special handling for booting memtest86+ on UEFI systems, as it can be booted both using the 64-bit Linux handover protocol on UEFI and 16-bit Linux handover on legacy systems.
This allows for a better implementation than #225616 for GRUB2, because we don't need any special handling for UEFI anymore, it can use the same entry/binary as legacy boot, and still accept boot params in UEFI.
On systemd-boot we need to use the new UEFI binary as in #225616.
Things done

Built on platform(s)

[x] x86_64-linux
[ ] aarch64-linux
[ ] x86_64-darwin
[ ] aarch64-darwin

[ ] For non-Linux: Is sandbox = true set in nix.conf? (See Nix manual)
[x] Tested, as applicable:

NixOS test(s) (look inside nixos/tests)
and/or package tests
or, for functions and "core" functionality, tests in lib/tests or pkgs/test
made sure NixOS tests are linked to the relevant packages

[ ] Tested compilation of all packages that depend on this change using nix-shell -p nixpkgs-review --run "nixpkgs-review rev HEAD". Note: all changes have to be committed, also see nixpkgs-review usage
[x] Tested basic functionality of all binary files (usually in ./result/bin/)
23.05 Release Notes (or backporting 22.11 Release notes)

[ ] (Package updates) Added a release notes entry if the change is major or breaking
[ ] (Module updates) Added a release notes entry if the change is significant
[ ] (Module addition) Added a release notes entry if adding a new NixOS module

[x] Fits CONTRIBUTING.md.

Use only the most important one, or wildcards or separate them by comma

I still need to test it, just in case, but other than the nit it seems alright from reading the code.

Sadly memtest86+ does not support aarch64 and seems like they're not planning on adding support either (https://github.com/memtest86plus/memtest86plus/issues/285, https://github.com/memtest86plus/memtest86plus/issues/147), so this is a breaking change on that platform.


clac: 0.3.3 -> <IP_ADDRESS>90906

Description of changes
Updated clac can ignore comments in its config file instead of throwing an error.
Diff: https://github.com/soveran/clac/compare/0.3.3..beae8c4bc89912f4cd66bb875585fa471692cd54

Things done

Built on platform(s)

[x] x86_64-linux
[ ] aarch64-linux
[ ] x86_64-darwin
[ ] aarch64-darwin

[ ] For non-Linux: Is sandbox = true set in nix.conf? (See Nix manual)
[ ] Tested, as applicable:

NixOS test(s) (look inside nixos/tests)
and/or package tests
or, for functions and "core" functionality, tests in lib/tests or pkgs/test
made sure NixOS tests are linked to the relevant packages

[x] Tested compilation of all packages that depend on this change using nix-shell -p nixpkgs-review --run "nixpkgs-review rev HEAD". Note: all changes have to be committed, also see nixpkgs-review usage
[x] Tested basic functionality of all binary files (usually in ./result/bin/)
23.11 Release Notes (or backporting 23.05 Release notes)

[ ] (Package updates) Added a release notes entry if the change is major or breaking
[ ] (Module updates) Added a release notes entry if the change is significant
[ ] (Module addition) Added a release notes entry if adding a new NixOS module

[x] Fits CONTRIBUTING.md.

Result of nixpkgs-review pr 251838 run on x86_64-linux 1

1 package built:

clac

Would you mind fixing the PR title?

Would you mind fixing the PR and commit title, to match the actual version number?

@h7x4 Yes, I'd love to but I'm not sure how. The project's latest official release was 0.3.3 which doesn't include the change I want, so I assume the best way is using the latest commit. The program doesn't have an --version option or any version numbers in the source code. I got the idea of putting a dot after the version and typing the date of the commit from https://github.com/NixOS/nixpkgs/pull/107739.
I'd appriciate an explanation or resources regarding to versioning in nixpkgs :)

Since then, https://github.com/NixOS/nixpkgs/blob/master/pkgs/README.md#versioning has been written, and, just in case, it has also been moved around to a place where I would not think to look if I did not know what exactly I was looking for…

The program doesn't have an --version option or any version numbers in the source code.

I'm not really talking about the version number format itself, I think that's fine. But the commit message says <IP_ADDRESS>90906 while the code says <IP_ADDRESS>10906. You'll need to amend/rebase your commit, and edit the title to match them up with the version in the code.

@h7x4 Good catch! I have no idea how did i not notice that when writing the commit message. I've amended and force-pushed.


Showing "**** 、[クラス] ボックス" (extra asterisks appears)

https://docs.microsoft.com/ja-jp/office/vba/api/publisher.application

Working on a fix: Bug 3290847