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

Jimp Browser Support #1194

Closed
3 tasks
marvinruder opened this issue Feb 7, 2023 · 33 comments · Fixed by #1285
Closed
3 tasks

Jimp Browser Support #1194

marvinruder opened this issue Feb 7, 2023 · 33 comments · Fixed by #1285
Labels
bug there is a bug in the way jimp behaves help wanted released This issue/pull request has been released.
Milestone

Comments

@marvinruder
Copy link

marvinruder commented Feb 7, 2023

Is your feature request related to a problem? Please describe.
At the moment, some problems arise when attempting to use Jimp in React (similar issues were reported from users of other tools, e.g. React Native). The following are known so far:

Describe the solution you'd like
The issues described above are resolved and Jimp can be used in frontend tools like React using import Jimp from "jimp[/es]"; without a problem.

Describe alternatives you've considered
Using the browser version of Jimp via require("jimp/browser/lib/jimp.js"); const { Jimp } = window; is a possible workaround, but that version is aimed more at using Jimp in plain HTML/JS than by bundling tools such as Webpack, Rollup etc., which should be able to handle jimp or jimp/es properly.

@marvinruder marvinruder added help wanted bug there is a bug in the way jimp behaves labels Feb 7, 2023
@hipstersmoothie hipstersmoothie added this to the V1 milestone Feb 7, 2023
@sergeushenecz
Copy link

image

@hipstersmoothie hipstersmoothie changed the title Support Jimp in React Jimp Browser Support Feb 7, 2023
@crutchcorn
Copy link
Member

It might be worthwhile to explore an option similar to how @wmhilton has done so with isomorphic-git using FS as a property to pass in:

https://isomorphic-git.org/docs/en/fs#docsNav

@wmhilton has even created a browser-first FS package called "LighningFS" that might be a good package to point to for official browser support, alongside an example repo that integrates it:

https://github.com/isomorphic-git/lightning-fs

@crutchcorn
Copy link
Member

Also worth mentioning - @marvinruder you may want to look into the work being done by @danielholmes :

https://github.com/danielholmes/jimp-vite

@suneox
Copy link

suneox commented Feb 8, 2023

It can work well on example, this lib using for node so some related packages don't work you need to use a build for the browser version and then I have resolved this and workaround by loading jimp.js on index.html and defining a global type for Jimp variable

@hipstersmoothie
Copy link
Collaborator

Yeah that one works but we're talking about esm usage rather than bundling. Bundling means we can't tree shake things. Right now our esm breaks browsers

@gabycush
Copy link

When using the jimp/es import, accessing some built-in Node APIs like fs, path etc. is attempted and the build fails (example: Can't resolve 'fs' in '…/node_modules/@jimp/core/es'). Reproducable in jimp-dev/jimp-react

I'm having this issue too, is a solution in the works or is there a specific suggested workaround?

@Ronkiro
Copy link

Ronkiro commented Mar 1, 2023

My solution for NextJS was to load jimp and import from window, similar approach from the issue's text but not using the library for the browser (it was giving me the error that self is not defined).

Code:

import 'jimp';
const { Jimp } = window as any;

Hope it helps anyone

@angello0926
Copy link

My solution for NextJS was to load jimp and import from window, similar approach from the issue's text but not using the library for the browser (it was giving me the error that self is not defined).

Code:

import 'jimp';
const { Jimp } = window as any;

Hope it helps anyone

This really helps me to get through this issue for now! Struggled for a few hours, thanks!

@MBrunoS
Copy link

MBrunoS commented Apr 8, 2023

I tried all the suggestions, but still couldn't make it work... I'm trying to use Jimp in a Web Worker, with Vite. So, I'm not being able to use the lib.
I'd even help with this bug, but I don't know where to start right now.

@xenova
Copy link

xenova commented Apr 9, 2023

I got Jimp working in the browser/webworker/node/... with this ugly hack:

ES6:

// For some reason, Jimp attaches to self, even in Node.
// https://github.com/jimp-dev/jimp/issues/466
import * as _Jimp from 'jimp';

// @ts-ignore
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

CommonJS:

// For some reason, Jimp attaches to self, even in Node.
// https://github.com/jimp-dev/jimp/issues/466
const _Jimp = require('jimp');

// @ts-ignore
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

@sexnine
Copy link

sexnine commented Apr 9, 2023

@xenova I don't know why this works, but it works.

I've been struggling to get Jimp working on Cloudflare Workers (using SvelteKit) for wayyy too long and you're solution just works.

One thing I noticed using your solution is instantiating a new Jimp instance I have to do new Jimp.default(...) on Node.js but on Cloudflare Workers new Jimp(...) is the only way that works.

I am extremely grateful that you shared your solution, so thanks <3.

@xenova
Copy link

xenova commented Apr 9, 2023

I don't know why this works, but it works.

That's exactly what I thought when I got it working 🤣 ...

One thing I noticed using your solution is instantiating a new Jimp instance I have to do new Jimp.default(...) on Node.js but on Cloudflare Workers new Jimp(...) is the only way that works.

Interesting. I haven't had an issue with creating new Jimp instances with my node.js version... but it's good to know you found a solution!

I am extremely grateful that you shared your solution, so thanks <3.

Happy to help!

@LetMeDream
Copy link

My solution for NextJS was to load jimp and import from window, similar approach from the issue's text but not using the library for the browser (it was giving me the error that self is not defined).

Code:

import 'jimp';
const { Jimp } = window as any;

Hope it helps anyone

Ok but, where is that code supposed to go inside the next Js project? In the component that's gonna use Jimp?

@LetMeDream
Copy link

I got Jimp working in the browser/webworker/node/... with this ugly hack:

ES6:

// For some reason, Jimp attaches to self, even in Node.
// https://github.com/jimp-dev/jimp/issues/466
import * as _Jimp from 'jimp';

// @ts-ignore
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

CommonJS:

// For some reason, Jimp attaches to self, even in Node.
// https://github.com/jimp-dev/jimp/issues/466
const _Jimp = require('jimp');

// @ts-ignore
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

This works in Next JS and apps created using CRA. Not in Vite, tho.

@patrickelectric
Copy link

No luck when using it in a webpage in a typescript project:

[vue warn]: Error in v-on handler (Promise/async): "TypeError: jimp__WEBPACK_IMPORTED_MODULE_7___default(...) is not a function"

found in

---> <VBtn>
       <GenericViewer> at src/components/vehiclesetup/viewers/GenericViewer.vue
         <VehicleViewer> at src/components/vehiclesetup/viewers/VehicleViewer.vue
           <VCard>
             <SetupOverview> at src/components/vehiclesetup/SetupOverview.vue
               <VehicleSetupView> at src/views/VehicleSetupView.vue
                 <VMain>
                   <VApp>
                     <App> at src/App.vue
                       <Root>

w

@Lofavreel
Copy link

Lofavreel commented May 7, 2023

I got Jimp working in the browser/webworker/node/... with this ugly hack:

ES6:

// For some reason, Jimp attaches to self, even in Node.
// https://github.com/jimp-dev/jimp/issues/466
import * as _Jimp from 'jimp';

// @ts-ignore
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

CommonJS:

// For some reason, Jimp attaches to self, even in Node.
// https://github.com/jimp-dev/jimp/issues/466
const _Jimp = require('jimp');

// @ts-ignore
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

Because some were wondering why your proposed workaround works:
I just did a little digging, because I had the same issue. I found this in the @jimp/core/ index.js (in both es and dist); it is before the last three lines of code in those files:

if (process.env.ENVIRONMENT === "BROWSER") {
  // For use in a web browser or web worker
  /* global self */
  let gl;
  if (typeof window !== "undefined" && typeof window === "object") {
    gl = window;
  }
  if (typeof self !== "undefined" && typeof self === "object") {
    gl = self;
  }
  gl.Jimp = Jimp;
  gl.Buffer = Buffer;
}

I don't know why and I don't think I will look into it, but maybe this will give the right person a starting idea on where to look to resolve this issue.

@hipstersmoothie
Copy link
Collaborator

Any help from someone in the community would be appreciated. If you want to submit a PR I'd be happy to Shepard that PR. At the time unfortunately I don't see myself doing this soon.

@jcard0na
Copy link

jcard0na commented May 11, 2023

Just for others usign React, the workaround mentioned on the issue's text worked for me:

export default function App() {
    require("jimp/browser/lib/jimp.js"); 
    const { Jimp } = window
    ...
};

this also worked:

import 'jimp';

export default function App() {
    const { Jimp } = window;
    ...
};

@devenkhatri
Copy link

My solution for NextJS was to load jimp and import from window, similar approach from the issue's text but not using the library for the browser (it was giving me the error that self is not defined).
Code:

import 'jimp';
const { Jimp } = window as any;

Hope it helps anyone

This really helps me to get through this issue for now! Struggled for a few hours, thanks!

Thanks for this suggestion. This worked for me.

@da7a90-backup
Copy link

For Vercel edge the workaround mentioned by @xenova works locally but not on production and even locally you have to set unstable_allowDynamic and point it to the library in node_modules but that doesn't seem to work for some reason when trying to deploy to production.

@sergeushenecz
Copy link

sergeushenecz commented Sep 3, 2023

My solution. Version 0.22.10

import  'jimp/browser/lib/jimp';
const { Jimp } = window;

@meepen
Copy link

meepen commented Nov 2, 2023

none of these work very well for typescript...

@Ronkiro
Copy link

Ronkiro commented Nov 7, 2023

none of these work very well for typescript...

@meepen check my comment #1194 (comment) it may help you

@sameert89
Copy link

sameert89 commented Nov 18, 2023

For react native/expo with hermes engine, this actually works, I cannot understand why it is like that, any insigths would be very helpful.

import * as _Jimp from 'jimp';
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

@Ronkiro
Copy link

Ronkiro commented Dec 6, 2023

@sameert89 React Native newbie here, but it seems that self works like window for RN. This snippet checks if it's existent/accessible, if it is then use it, else use the normal variable. It's similar to the solution i pointed #1194 (comment) and to the one pointed in the first post

@NayamAmarshe
Copy link

none of these work very well for typescript...

Maybe try this:

import "jimp";

const ReactComponent = () => {
  const { Jimp } = window as Window & typeof globalThis & {
    Jimp: typeof import("jimp");
  };
...

@tsgouros
Copy link

tsgouros commented Mar 21, 2024

For react native/expo with hermes engine, this actually works, I cannot understand why it is like that, any insigths would be very helpful.

import * as _Jimp from 'jimp';
const Jimp = (typeof self !== 'undefined') ? (self.Jimp || _Jimp) : _Jimp;

I was very excited to find this comment, since I am also trying to use Jimp in React Native (w/o Expo), but it does not work for me. Or it partly works, in that I can use the constructor to create an object to receive an image:

const jp = new Jimp(256, 256, "#000000", (err, image) => {
  console.log("+++", err);
});

But I can't seem to use that value to access functionality like Jimp.read() which is what I need.

@hipstersmoothie hipstersmoothie mentioned this issue Mar 28, 2024
Merged
@neko-para
Copy link

For those want to use jimp in browser with typescript definition, here's a guide.
First, import browser build. As it pollute into window.Jimp, place doesn't matter.

import 'jimp/browser/lib/jimp.js'

Then, add a dts file

declare var Jimp: typeof import('jimp')

Just use Jimp.xxx.

@vickyRathee
Copy link

@sexnine Can you please prove the example code for Cloudflare? I can't get it work for some reason.

@sexnine
Copy link

sexnine commented Apr 23, 2024

@sexnine Can you please prove the example code for Cloudflare? I can't get it work for some reason.

Are you using Sveltekit on CF workers, or just vanilla workers? Typescript or JS?

I can try to make a quick demo later today :)

@vickyRathee
Copy link

Just a vanilla worker using Typescript. I am trying to resize a puppeteer screenshot and upload to R2 to generate website thumbnail.

This was my code when I was testing with sharp

image

@trungpd1102
Copy link

trungpd1102 commented May 10, 2024

Just a vanilla worker using Typescript. I am trying to resize a puppeteer screenshot and upload to R2 to generate website thumbnail.

This was my code when I was testing with sharp

image

@hipstersmoothie
Copy link
Collaborator

🚀 Issue was released in v1.0.2 🚀

@hipstersmoothie hipstersmoothie added the released This issue/pull request has been released. label Aug 31, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug there is a bug in the way jimp behaves help wanted released This issue/pull request has been released.
Projects
None yet
Development

Successfully merging a pull request may close this issue.