Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add mSLA capabilities #6575

Open
wants to merge 31 commits into
base: master
Choose a base branch
from
Open

Add mSLA capabilities #6575

wants to merge 31 commits into from

Conversation

sn4k3
Copy link

@sn4k3 sn4k3 commented Apr 23, 2024

Background

I'm the creator of UVtools, a software dedicated to help and make resin printing sane (mSLA/DLP) with tons of manipulations and checks.

From the past 4 years I've being deal with many mSLA formats available today, I known them in depth, I'm amazed with the fact that mSLA is far behind FDM in slicing features (In fact I could not believe 4 years ago that mSLA was not gcoded and open like FDM). We are very limited to static file formats that only follow a structure with few or none options. The existing gcode printers in this technology can be counted by hand and the ones that exists suffer from bugs or bad performance.

The bad firmwares are ruining the printers "completely", they never listen to community, never fix bugs that in a normal case takes just 1 day to fix and send the patch firmware online. They really don't care, they just flood the market with models and models of machines that many are very decent on it hardware but the firmware make them a crap machine.
Companies right now are tied to one or two solutions, which are always locking formats and make the best effort to encrypt and make sure no others can be used.

Myself got asked by a board company what could be done to improve the eco-system. I tell them: Well, make the format open-source and run over gcode... A: That's not possible, our hardware is not capable, parse gcode is very hard, run png's is not possible, not economical, can't be made open-source, bla bla bla. All runaround.
The fact is that now they have 4GB boards running linux, is load png still too hard? Is gcode still not possible? 🤦

Then big promises came, open-source boards and format. Guess what? They call themself open-source by just having a repo in github with just a few documentation on the format, which even with the docs we are unsure about the meaning of some fields...

Lies, promises, bad products, and more lies... This is a loop in mSLA with huge lack of vision.

This crappy mindset are ruining the technology and the overall experience. Myself I don't active do nor like resin printing, but I can't just see this and doing nothing when I have to power to change the situation! That lead me to this PR.

What is required run mSLA?

mSLA only need one Z axis, feed image to a screen and lit a UV LED over it. Looping layer by layer and forming a solid piece from cured resin from the lit pixels.
FDM is far more complex to build because it motion system. So now you see another point here, why such simple tech is soo hard to implement? The answer is: Drive the displays! Most displays are held, no datasheets no information how to drive it, require custom FPC = custom board.
However today most LCDs are HDMI! And you guess it, plug HDMI to PC and send image. Easy!

Why Klipper?

I have been told: Why klipper for that? Thats OP for what you want. Why not using something else?
I can't disagree more!

  • I'm a FDM user, I know marlin and klipper and used both. Klipper is very solid and flexible, easy to configure and tune, "no compilation required", well documented, very strong, plugin based, good interfaces, etc.
  • We still need an computer (Pi) because we need to drive the display (4k, 8k, 12k). So why not merge a good Pi and Klipper and have the best of two worlds?
  • Gcode! --> We really need this (Different cure times for supports, better tests, variable layer, dynamic lifts, M600, etc, etc.)
  • People can now convert their HDMI printer into something much better and dump horrible boards and firmwares
  • People can upgrade their LCD's or use other models that fit the frame and have HDMI, eg: RGB to Mono upgrade
  • People can start to configure their heaters and fans
  • People can start to configure their cameras and having timelapses
  • People can start to configure their lame RGB leds
  • People can start to monitor their printer
  • New sensors and improved hardware with new capabilities
  • Custom gcodes and events
  • Remote management
  • More time and confidence
  • Makers can now build their own mSLA!
  • (More could be written, but each user can find it own needs on this)

So is Klipper OP for this!? NO! It's just perfect!

Also I think it's time for klipper to embrace other manufacturing processes, it's a win-win and will make klipper richer in capabilities and features.

Hardware

Right now I'm using:

  • BTT Manta M5P + Pi CM4 4gb
  • UNIZ IBEE printer with all it hardware

The PR / Implementation

Note that I mark this PR as a draft because I wan't it to be review, it's my first time dealing with klipper sources. In fact I did what most said impossible in just 3 days but had my printer displaying the image using klipper in just one day. This alone means klipper perfect :)
So forgive-me If something is not soo well defined.

GCode sample:

MSLA_DISPLAY_VALIDATE RESOLUTION=3840,2400 PIXEL=0.05,0.050

G21;
G90;
M17;
M1401;
G28 Z;
M106 S255;

M1451 F"1.png"; Render image into display (LED is OFF)
G0 Z7.1 F800;
G0 Z0.1 F1000;
G4 P3000;
M1400 S255 P4000 ; Turn LED ON for 4s, if image not render yet, it waits before turn ON for completion
G4 P3000;

M1451 F"2.png";
G0 Z7.2 F800;
G0 Z0.2 F1000;
G4 P3000;
M1400 S255 P4000;
G4 P3000;
...

Image display

The displays are now connected via HDMI on the Pi.
Pi itself let us configure the framebuffer (config.txt) to match the display. So all we need is set correct parameters there.
After I created a [framebuffer_display] module into klipper. Which allow us to configure any framebuffer and send buffers/images over there. See framebuffer_display.py
I created to be generic and mux, so some may use it for other displays and send pics to a HDMI display.
All code is python and it direct address the framebuffer without any external dependencies.

From that I created the [msla_display] which is the keypoint

eg:

# Also compatible with [pwm_tool]
[output_pin msla_uvled]
pin: PA5

[msla_display]
type: Mono
model: TM089CFSP01
framebuffer_index: 0
resolution_x: 3840
resolution_y: 2400
pixel_width: 0.05
pixel_height: 0.05
cache: 1
uvled_output_pin_name: msla_uvled

type, model are just information, not actually used.
All other parameters are used to have sane checks but also provide information about the display which is required.
the cache parameter is a smart-feature to cache next layers so buffer is much more fast to send when time comes.

The most smart approach to exposure an layer is:

  1. Starts new layer
  2. Display image
  3. Do lift/rectract and/or wait times
  4. Turn on UV LED
  5. Wait the exposure time
  6. Turn of UV LED
  7. Loop to 1

In my implementation before UV LED is turn on, it waits for image buffer send to be completed. A smart feature that most of gcode printers does not have, they never know when buffer is actually completed, in consequence UV LED can be lit before image is present. I really can't understand why, why so hard to make it right?
With cache system and direct buffers I manage fast speeds on transfers, not that we really need them, because they way mSLA works with lifts and waits make time to image to complete (In most cases).

Here the results of an 4K buffer, sampled and avg 10 times:

Clear time: 7.285666ms (10 samples)
Send cached buffer: 3.448391ms (10 samples)
Read image from disk + send time: 94.163990ms (10 samples)
Buffer size: 9216000 bytes (8.79 MB)
MSLA_DISPLAY_RESPONSE_TIME AVG=10

So in normal conditions if image is load from disk it took about 94ms, but if cached it took 3.5ms to be rendered to the display. Pretty good.

Some gcode commands where created to:

  • Clear the display: M1450
  • Send image to the display: M1451 F"file.png"
    • When printer is printing, partial path always start at gcode basedir
  • Measure display times
  • Control the UV LED: M1400 S[0-255] P[exposure-ms]
  • Turn UV LED Off: M1401

M1400: Because UV wavelength goes from 100nm-400nm
M1451: Command used by other gcode printers to display the image is M6054, but opt for M1451 to be closer from M1400

Commands are debatable, we should set an standard now.

[virtual_sdcard]

The mSLA requires an image per layer. Some users prints can go up to 4000 layers. Upload folders is a bit messy, the format I think is best it's the Zip file (pngs + gcode)
I had to alter the virtual_sdcard.py with some features:

  • Accept zip and tar files, it will analyze them, if they have one gcode file, they got decompressed and selected to be printed.
  • Archieve is decompressed to a folder other than "gcodes" to not show on file manager. They are extracted to a folder selectable by user, see sdcard_archive_temp_dirname. If same file is printed it compare the hash, if equal no need to extract again. On a different hash it will then remove folder and extract new contents.
  • This also means, a zip with a gcode is now printable

[toolhead.py]

I admit that I had a hard time discovering the [printer] 😅
I have added the property manufacturing_process this is required for others interfaces to adapt. Up now all is related to FDM, so interfaces like mainsail would need to know proper process to adapt interface, eg: For mSLA we want to see current layer image that is printing.

[printer]
manufacturing_process: mSLA
kinematics: cartesian
max_velocity: 300
max_accel: 3000
max_z_velocity: 25
max_z_accel: 150

[printer_stats.py]

Klipper was build around FDM, stats is filament based. Current system is very limited so I rewrote the stats to be universal and more useful. UI's can now render information easier without parse.

  • filament_used: Was kept for compatibility and give time for other backends to adapt, but marked as deprecated in favor of material_used
  • material_type: Based on toolhead.manufacturing_process this is auto set by klipper, eg: filament or resin
  • material_name: This is set by user via SET_PRINT_STATS_INFO, it represents the current printing material, if a material is changed, eg: M600, we can now update it name and display under UI's.
  • material_unit: The material unit, this is set by klipper but can also be set by user, for filament is set to 'mm', for resin is set to 'ml'. If user is not happy he can change with to 'in' using SET_PRINT_STATS_INFO
  • material_total: The total material print will use, set once on print start
  • material_used: The used material so far in the print.
  • info.last_material_used: The last used material, is often the material consumed by last layer.

Syntax:

        Syntax: SET_PRINT_STATS_INFO TOTAL_LAYER=[count]
                                     CURRENT_LAYER=[number]
                                     MATERIAL_NAME=["name"]
                                     MATERIAL_UNIT=[unit]
                                     MATERIAL_TOTAL=[total]
                                     CONSUME_MATERIAL=[amount]

        TOTAL_LAYER: Total layer count
        CURRENT_LAYER: Current printing layer number
        MATERIAL_NAME: Name of the material being used
        MATERIAL_UNIT: Material unit
        MATERIAL_TOTAL: Total material this print will consume
        CONSUME_MATERIAL: Consume material and increment the used material

FDM sample:

Print start: SET_PRINT_STATS_INFO TOTAL_LAYER=1000 MATERIAL_NAME="Generic Orange PLA" MATERIAL_TOTAL=100000
Before layer: SET_PRINT_STATS_INFO LAYER=1
After layer: SET_PRINT_STATS_INFO CONSUME_MATERIAL=100

echo: 100 / 100000 mm -> This is the used material in mm

Advanced:

SET_PRINT_STATS_INFO MATERIAL_NAME="Brand Red PLA" 
M600

Then our M600 macro can be expanded to show the material to insert.

image

Resin sample:

Print start: SET_PRINT_STATS_INFO TOTAL_LAYER=1000 MATERIAL_NAME="Generic ABS-Like" MATERIAL_TOTAL=1000
Before layer: SET_PRINT_STATS_INFO LAYER=1
After layer: SET_PRINT_STATS_INFO CONSUME_MATERIAL=1

echo: 1 / 1000 ml -> This is the used material in ml

image

Laser sample:

Print start: SET_PRINT_STATS_INFO TOTAL_LAYER=1 MATERIAL_NAME="MDF" MATERIAL_TOTAL=10000
On etch/period: SET_PRINT_STATS_INFO CONSUME_MATERIAL=10

echo: 10 / 10000 mm^2 --> This is the etched / cut area

CNC sample:

Print start: SET_PRINT_STATS_INFO TOTAL_LAYER=1 MATERIAL_NAME="MDF" MATERIAL_TOTAL=10000
On cut/period: SET_PRINT_STATS_INFO CONSUME_MATERIAL=10

echo: 10 / 10000 mm^3 --> This is the removed material volume

This are just samples, and uses are not limited to them.
UI's can now render better stats without the need of parse nor if's to display stats to other manufacturing processes.

[display]

  • menu.cfg and display.cfg was adjusted to remove some menus if criteria are not match.
  • Introduce UVLED and UVLED pwr under Control menu.
  • Introduce UVLED glyph, will show when UVLED is ON

2024-05-02-21-08-44-129

What's missing

  • Stats for mSLA? I'm not sure if klipper does stats for FDM, so this is a question.
  • UI LCD interface (Remove hotend, heatbed and extra menus that are not required for mSLA)
  • Axis freedom: I tried to create a new kinematic with just an Z, but I failed, it complain that require two more axis (YZ), so I guess klipper at the moment is constrained to 3 axis min? To bypass this I use cartesian and end in configure 2 more steppers that are not used. As we only use Z, it prints happy without touch X and Y. Just the home must be issued with G28 Z. I think kinematics should constrain that and not the core as a global rule. There are many applications for few axis and while I search I found other users with same problem. Creating manual_stepper is ugly, break interface and gcodes. Displaying the fake XY is not that bad but...
  • Docs: I would complete the docs when PR is done, without further changes to make.

Breaking changes:

None.

Video

(Sorry for the bad quality.)

Sample print file

https://we.tl/t-l9a9fMftQN

WIP

This is a WIP, looking for ideias, improvements but the implementation is working stable.

@sn4k3
Copy link
Author

sn4k3 commented Apr 23, 2024

Some questions:

  1. Is there events I can listen for print start/end/pause/cancel? Because I want to clear cache on print end event, and right now I only do at print start. But also it's safer to issue a UV LED OFF command in case macro or slicer miss that on print end.
  2. I'm thinking in offer a option to limit the UV LED ON time, why? Because UV LED are powerful, they saturate the heatsink very fast, if on for long periods can damage itself, also wear LCD. Giving the option in seconds to limit the amount of time the LED is ON would be a safe feature, in a normal print we never need more than 30s. So user can configure eg. 60s maximum. If he forget to turn LED OFF, system will do it as a safe-guard. My question: You think this is something I can implement on [output_pin] and benefit other uses, or do it at [msla_display] level?
  3. In mSLA TSMC was introduced to cut time in print, it does two lifts (Slow + Fast) and then retract with (Fast + slow). It need to detach from FEP slow and when done raise a bit more fast. TSMC is a stupid fix, we don't really need it. What we need is Acceleration! So we want to have a slow accel on lift start, but fast accel on stop. Then fast accel on retract start and slow accel on stop. Currently I think it's only possible to set accel in one way. Would be possible to have a second parameter to define the stop accel?

See this code:

M6054 "2.png";
G0 Z7.2 F8; -> Safe lift, detach from fep + refresh resin
G0 Z0.2 F10; -> Retract to cure the layer at 0.2mm pos
G4 P3000; -> Wait to platform settle
M1400 S255; -> led on
G4 P20000; -> 20s
M1400 S0; -> led off
G4 P3000; -> wait for layer to cooldown

What would be optimal:

M6054 "2.png";
SET_VELOCITY_LIMIT ACCEL=5,500 -> Slow detach but fast stop
G0 Z7.2 F8; -> Safe lift, detach from fep + refresh resin
SET_VELOCITY_LIMIT ACCEL=500,5 -> Fast retract but slow stop
G0 Z0.2 F10; -> Retract to cure the layer at 0.2mm pos
G4 P3000; -> Wait to platform settle
M1400 S255; -> led on
G4 P20000; -> 20s
M1400 S0; -> led off
G4 P3000; -> wait for layer to cooldown

You think the SET_VELOCITY_LIMIT can be improved in that way?

sn4k3 added 18 commits April 23, 2024 21:00
- Sync display with UV LED in two-way mode
- Add a response test to measure the UV LED shutter time
- Allow to define the response delay of the UV LED shutter and take it into account when using M1400 Px
- Fix regex for the file path parse from M6054
- Refactorings
- Remove display_width and height from configuration to simplify
- Fix bit_depth not set when 32
- Rename type to pixel_format
- Use locks on framebuffer
- Add more utility functions
- Add `MSLA_DISPLAY_TEST` command
- Add channels information
- Add fill_buffer allow a rgb tuple
- Add M1401 command to turn off the uvled
- Improve image send to allow images smaller than buffer
- Improve get_image_buffer to return more data and allow strip alpha
- Improve raise to gcode.error
- Add utility functions
- Rename some commands
Z axis with self homed xy and allow only to move Z
Instead of using filament schemantic, it now use universal material which can be set by user. It is to provide better and more accurate stats, while allowing material types other than filament.
- Add M1450 to clear the screen
- Change M6054 to M1451 and force the F param
@sn4k3 sn4k3 marked this pull request as ready for review May 3, 2024 01:33
@sn4k3 sn4k3 changed the title [WIP] Add mSLA capabilities Add mSLA capabilities May 3, 2024
Copy link

Thank you for your contribution to Klipper. Unfortunately, a reviewer has not assigned themselves to this GitHub Pull Request. All Pull Requests are reviewed before merging, and a reviewer will need to volunteer. Further information is available at: https://www.klipper3d.org/CONTRIBUTING.html

There are some steps that you can take now:

  1. Perform a self-review of your Pull Request by following the steps at: https://www.klipper3d.org/CONTRIBUTING.html#what-to-expect-in-a-review
    If you have completed a self-review, be sure to state the results of that self-review explicitly in the Pull Request comments. A reviewer is more likely to participate if the bulk of a review has already been completed.
  2. Consider opening a topic on the Klipper Discourse server to discuss this work. The Discourse server is a good place to discuss development ideas and to engage users interested in testing. Reviewers are more likely to prioritize Pull Requests with an active community of users.
  3. Consider helping out reviewers by reviewing other Klipper Pull Requests. Taking the time to perform a careful and detailed review of others work is appreciated. Regular contributors are more likely to prioritize the contributions of other regular contributors.

Unfortunately, if a reviewer does not assign themselves to this GitHub Pull Request then it will be automatically closed. If this happens, then it is a good idea to move further discussion to the Klipper Discourse server. Reviewers can reach out on that forum to let you know if they are interested and when they are available.

Best regards,
~ Your friendly GitIssueBot

PS: I'm just an automated script, not a human being.

@KevinOConnor
Copy link
Collaborator

Interesting, thanks.

I'm curious what your long-term plans are for this work. Are you still working on it? Are there users utilizing this system today?

I didn't see your questions earlier because of the many earlier updates to the PR. I'll try to answer them:

Is there events I can listen for print start/end/pause/cancel?

Unfortunately that is difficult to do with g-code because there isn't an explicit "start of print" nor "end of print" command in g-code. The closest equivalent would be the events generated from the idle_timeout module (see the send_event() calls in klippy/extras/idle_timeout.py ).

You think this is something I can implement on [output_pin] and benefit other uses, or do it at [msla_display] level?

That sounds like you'll want to implement in a module. You could also look at klippy/extras/pwm_tool.py - as that has emergency cutoff code in it. (Should the host disconnect from the mcu while the gpio is enabled, the mcu will know to transition to an error state and turn off the gpio.)

Would be possible to have a second parameter to define the stop accel?

This was discussed on Discourse. It's possible, but I'd guess it would be simpler to break up the moves and change acceleration between move segments (as you've indicated on Discourse).

I also have a few high-level questions:

  1. I'm curious why you plan to use G1 and M6054 style g-code commands? I understand the desire for an open text-based format, but I'd have thought more verbose commands something like MOVE_AND_DISPLAY_PICTURE HEIGHT=2.300 FILE="2.png" would be possible.
  2. Is there readily available hardware that this code can run on today? That is, can many users buy off-the-shelf hardware and use this support on it, or would users be required to build a printer from scratch.
  3. What software will be used to produce the gcode/png/zip files that are proposed here? Is that software readily available today.
  4. I understand from your description that mSLA firmware is often proprietary. Are there any other popular open source mSLA firmwares at all? Or, is this goal for this to be the basis for the first popular open source mSLA firmware. (Excuse my ignorance here - I have no experience at all with resin based printers.)

Thanks again,
-Kevin

@sn4k3
Copy link
Author

sn4k3 commented Jun 11, 2024

I'm curious what your long-term plans are for this work.

I plan to maintain it and work with community to attend and lead mSLA forward. Klipper has everything to drive mSLA, only the display image part is missing. I also made it to support other techs and not be "filament" specific. I think Klipper core should go in this direction, abstract rather than specific.

Are you still working on it?

No, I find this PR very stable and everything is ready to be used. I'm printing with confidence and without any failure so far. But will be optimal to have another set of eyes on the code.

Are there users utilizing this system today?

Just me. I converted my printer and throw it a Manta M5P + CM4 to make this proof of concept. Currently printing with it using mainsail.

2024-05-11-18-38-19-895

The Athenna printers (Runs nanoDLP with klipper) also had they sync problem with image and exposure time, they looked my PR and adopted the concept and rewrite my M1400

This was discussed on Discourse. It's possible, but I'd guess it would be simpler to break up the moves and change acceleration between move segments (as you've indicated on Discourse).

Yes, topic was open by me. Is true that 4xG1+SET_VELOCITY does optimize (1s less in my tests) however in future would be a nice to have this and benefit other systems. However not critical for PR.

I'm curious why you plan to use G1 and M6054 style g-code commands? I understand the desire for an open text-based format, but I'd have thought more verbose commands something like MOVE_AND_DISPLAY_PICTURE HEIGHT=2.300 FILE="2.png" would be possible.

mSLA requires lifts before exposure next layer. Here a normal sequence for print layer 1:

;LAYER_START:0
;PositionZ:0.05mm
SET_PRINT_STATS_INFO CURRENT_LAYER=1
BEFORE_LAYER_CHANGE LAYER=1 HEIGHT=0.05 PIXELS=189274 BOUNDS=81.75,46.15,25.2,28.85 AREA=473.185 VOLUME=23.659 MATERIALML=0.0237
M73 P0 R69.88;Set print progress
M1451 F"1.png";Show image
M204 S5;Set acceleration
G1 Z4.05 F600;Z Lift (1)
M204 S100;Set acceleration
G1 Z6.05 F600;Z Lift (2)
G1 Z1.55 F600;Retract (1)
M204 S5;Set acceleration
G1 Z0.05 F600;Retract (2)
G4 P3000;Wait before cure
M1400 S255 P30000;Exposure for 30s
G4 P3000;Wait after cure
SET_PRINT_STATS_INFO CONSUME_MATERIAL=0.0237
AFTER_LAYER_CHANGE
;LAYER_END

You can notice the 4xG1 to perform the lift and retract to detach model from FEP and refresh the resin under it.
However this is all setup by user preference, they can opt for just 1 simple lift rather than my optimization with two lifts.
There are also situations where we don't want to lift, eg: Cure supports at one exposure time, cure model at other exposure time. Between this two images changes we don't want to lift because they are same layer.
Another point is multiple exposure tests and models.
There are also users using mSLA printers to fabricate PCBs with high precision.

Regarding that I think MOVE_AND_DISPLAY_PICTURE is very limited and an extra command that slicers will skip. For that be usable it would need to accept optional HEIGHT1/2 and SPEED1/2, ACCEL1/2, WAIT, and whatever comes next to implement.

I think we should stay with standalone commands for best compatibility and customizable.

Here the parameters users can adjust per layer:

image

Is there readily available hardware that this code can run on today? That is, can many users buy off-the-shelf hardware and use this support on it, or would users be required to build a printer from scratch.

Any FDM board and a Pi will do it. I have written step by step guide for who want to convert their printer to this firmware: https://github.com/sn4k3/klipper-msla

In my case I have used a Manta M5P + CM4 to make my UNIZ IBEE klipper based.

What software will be used to produce the gcode/png/zip files that are proposed here? Is that software readily available today.

No slicer so far is able to output this zip format with klipper flavor. The current slicers can output zip but with CWS gcode norm.
However my software (UVtools) can use any slicer and convert to klipper format.
It's a workflow some users already use, They use PrusaSlicer to slice .sl1 and UVtools to convert to their target printer/format.

image

Here a sample sliced file, PrusaSlicer (SL1) -> UVtools -> Klipper zip

I understand from your description that mSLA firmware is often proprietary. Are there any other popular open source mSLA firmwares at all? Or, is this goal for this to be the basis for the first popular open source mSLA firmware. (Excuse my ignorance here - I have no experience at all with resin based printers.)

There are no popular open-source mSLA firmwares. This is the problem :)
Well we have the Prusa SL1 but is not popular along mSLA, also it's a downgrade comparing to FDM none control over printing, it does all internally. So you have no chance to make your custom moves.
There are "open-spec" formats, gcode formats, but none is truly open-source.
Most consumer printers uses CTB ecosystem. Other share is held by Anycubic then Creality and now Elegoo. None listen to community nor have good firmware, most still not able to control layers individual, lots of problems which I'm tired to patch with my software.
There's also the nanoDLP which use klipper but it's a close-source propertary product and have it problems.
You can read more about this bad experiences on my repo (One just came today, one didn't even follow own spec) and also the "war" with formats: sn4k3/UVtools#319 and sn4k3/UVtools#442

Working with all these formats over years it's an experience I don't wish for anyone. I wonder why is so hard to write a good firmware?

This PR aims to free users from all crappy firmwares monopoly and revindicate the machines under their control. And most important, having the first all-in and good open-source mSLA firmware that allow you to tune and add features to your printer like we do with FDM.

@stisa
Copy link

stisa commented Jul 5, 2024

Very interesting PR! It has always seemed strange to me that mSLA, which is a motor, a screen and an LED is less open source than multiple motors working together.
I am working on something similar but doing the image loading/displaying in a separate python script sending gcode commands to klipper for movement/pin handling, would be interesting to have everything handled in klipper directly.

Does this support mono lcds that report lower resolution on one axis (eg, 2560x540 instead of 2560x1440 like the DXQ608)?
Also, have you thought about using multi-slice tiff files instead of a folder of pngs? This would reduce the number of files to 2, tiff+gcode, which can then either be zipped (or not). You can load a tiff as a 3D array (xy+layers) and then just blit the layer onto the framebuffer (eg. using numpy.memmap for the framebuffer)

@sn4k3
Copy link
Author

sn4k3 commented Jul 5, 2024

Very interesting PR! It has always seemed strange to me that mSLA, which is a motor, a screen and an LED is less open source than multiple motors working together.

The hardest part was always the main LCD which was required custom hardware and know how to address data lines. Not anymore with HDMI interface. That constrained the tech so far. But yeah removing lcd from equation the mSLA is much easier to program compared with FDM.

I am working on something similar but doing the image loading/displaying in a separate python script sending gcode commands to klipper for movement/pin handling.

nanoDLP work similar to that, but that is not optimal, you "lose" sync

Does this support mono lcds that report lower resolution on one axis (eg, 2560x540 instead of 2560x1440 like the DXQ608)?

It support any HDMI LCD as long you can configure it right (framebuffer) up to a limit of resolution. The auto kms driver won't work well in most case with this mono lcds.
This fork also allow to use any lcd in other uses and send bitmaps to an LCD, for example you can draw in LCD for FDM printers too from gcode.

Also, have you thought about using multi-slice tiff files instead of a folder of pngs? This would reduce the number of files to 2, tiff+gcode, which can then either be zipped (or not). You can load a tiff as a 3D array (xy+layers) and then just blit the layer onto the framebuffer (eg. using numpy.memmap for the framebuffer)

Why overcomplicate? The simpler the best. Having multiple files is best than single array, it also allow faster pre-process of image. IMO handling +/- 2gb TIFF is only desvantagens and more "lock" prompt.

@Sugaroverdose
Copy link

@sn4k3 Is there any further discussion happens anywhere or it's stuck at PoC?

it would be nice if you'd add information disclosed here into https://github.com/sn4k3/klipper-msla those readme doesn't really makes sense without everything said here, from perspective of a random person who would love to have klipper on msla printer, explanation around screen is lackluster(it's actually makes think that it's more complex than it is in reality due to folder with bunch of files which the only currently tested screen sends you to) and zero info on how to actually print doesn't encurage as well

@sn4k3
Copy link
Author

sn4k3 commented Oct 5, 2024

No discussion outside this PR as far I know. I guess is dependent on reviewers and people who can implement this to test out. As Klipper is mainly FDM something outside that scope might take extra time and effort to get merged.

Most information here (apart from new modules documentation which completes the klipper docs) don't really matter for end user, most stuff is PR related and how code was implemented. But fell free to point out what you find useful to have in klipper-msla and I will complete.

About the folder with bunch of files I guess you talking about the macros I built for mSLA? They are completely optional, klipper alone will work out of the box BUT just like FDM klipper without macros are lackluster, for example you still need macros for filament change and other optimal procedures. As so my macros implement that useful extra functions which I recommend but again are optional and not dependent on.

About complexity is not near as complex as FDM huge configurations, you only need to configure an output pin for UVLED and add an display.
The trick rely then on configuring the framebuffer of LCD on Pi config file, which there is a database with those around, I would like to add more display's to my repo list but I only have one tested under my machine and I only want to add confirmed values. Note that any display will work as long you can use HDMI or DSI with them. That said this fork is only usable with machines that uses HDMI already OR machines where you can buy the converter board.
Also note that Pi have the auto detect driver but most wont work because these displays are Mono and with RGB configuration to compress resolution, that is the reason we need to configure the framebuffer values manually.
For the lack of documentation around displays is always possible to spoof those values via software and a PC or a dedicated hardware in between.

The klipper-msla repo is currently the step by step guide I have build to help people setup things which does not differ from klipper logic and only requires the use of two modules into your klipper printer config file. After that it will print just like any other FDM printer, you can access to webui select file and print. To slice a file you can use PrusaSlicer with my printer profile sample, then you send to UVtools and it will auto convert to klipper file (.zip). That zip is what you upload to your printer and select to print, then it will start and print.

For people not into DIY I would say this can be harder, because they may not be used into tinker with custom boards and set up a klipper. But for who comes from FDM costum builds with klipper, this will be just as easy.

I have been using klipper into my printer now and I can say that everything was improved, in fact I had no failure prints since then using the same slicing parameters. For example, where because a PAUSE would cause a horizontal line on model 100% of the times, now its history, pauses are perfect and don't create lines any more. The precision of exposure also vastly improved.

If you have any questions or require help to implement into your machine fell free to contact me.

@Sugaroverdose
Copy link

Sugaroverdose commented Oct 6, 2024

@sn4k3 i didn't mean that kind of stranger, yet i really appreciate that you've tried to explain as much as possible.
i've meant a person who knows enough, but got link into your instructions for example on Reddit(that's exactly where i found it), read it and didn't get multiple things, since i already have a printer(just for a wider context: i have halot mage and almost all required hardware for it to be swapped to klipper, the only lacking thing is microhdmi->hdmi adapter, funnily enough), so i just started to search for anything related to those repo and happily ended up finding this PR, which answered on all of the questions i had, that's why i recommended to expand those manual with info provided here, so ppl who would like to get aftermarket firmware(or specifically klipper) would actually understand that it's not that hard even if your printer isn't listed.

First and foremost: "what i'm going to do after installation" - there's no answer to that question in those guide, but it is here, even in your reply, specifically:

To slice a file you can use PrusaSlicer with my printer profile sample, then you send to UVtools and it will auto convert to klipper file (.zip). That zip is what you upload to your printer and select to print, then it will start and print.

as well as more info which you provided here, like available settings, which you posted earlier

Secondly: screen/display - it is not explained how exactly it is used, but have config file with sketchy lines like screen model number(as said here - it's pretty much equals to comment and those field doing nothing, but there's nothing about this on the guide page) which correlates with .bin and .data files in "display database" and it leads to assumption that it might require to contact vendor to get those files(yes, it is my mistake to even peek there, but having questions without answer leads to f-around and find out learning method), with info provided here it is clear that you basically need driver board which can handle display and configure it like any other hdmi screen, but taking into consideration details like horizontal resolution(which you touched in you response as well)

I believe that this PR is huge for msla community, but because of unclear level of complexity(which is pretty low, if we talk about printers without fancy stuff like tilting bed, which might require more work like adding "firmware retraction" gcode instead of using plain Z movement) in guide it does not get enough attention
I'll try to describe it in guide repo issues, so this topic wouldn't mess PR with unrelated talks

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants