Giter Club home page Giter Club logo

Comments (9)

nolanlawson avatar nolanlawson commented on June 2, 2024 2

BTW here is a simpler solution (IMO):

<emoji-picker></emoji-picker>
<script>
  import { onMount } from 'svelte'
  onMount(() => import('emoji-picker-element/svelte'))
</script>

The <emoji-picker> tag is rendered server-side, but it's only upgraded to a custom element in onMount when the component is imported. I tested it in a minimal SvelteKit app, and it works:

Screenshot from 2023-11-15 07-05-49

from emoji-picker-element.

nolanlawson avatar nolanlawson commented on June 2, 2024 1

Thanks for the explanation. This is the key point I think:

onMount(async () => {
  Picker = await import('emoji-picker-element/svelte');
  // ...
})

onMount only runs in the browser when using Svelte. So this avoids the SSR issue.

I would add something to the README, but I don't necessarily want to put something SvelteKit-specific in there. The advice will vary from container to container (Next, Remix, SolidStart, Vue+Vite, etc.).

from emoji-picker-element.

BigBoulard avatar BigBoulard commented on June 2, 2024 1

BTW here is a simpler solution (IMO):

<emoji-picker></emoji-picker>
<script>
  import { onMount } from 'svelte'
  onMount(() => import('emoji-picker-element/svelte'))
</script>

The <emoji-picker> tag is rendered server-side, but it's only upgraded to a custom element in onMount when the component is imported. I tested it in a minimal SvelteKit app, and it works:

Screenshot from 2023-11-15 07-05-49

To complete the answer, you can listen to events as you do on the JSX part of the code like below:

<emoji-picker on:emoji-click={doSomething} />

from emoji-picker-element.

nolanlawson avatar nolanlawson commented on June 2, 2024 1

Thanks for the feedback. Added a note to the README ^

from emoji-picker-element.

nolanlawson avatar nolanlawson commented on June 2, 2024

I'm not familiar with SvelteKit, but emoji-picker-element is a bog-standard custom element. So you should be able to just import it the way you would import it in any other framework.

The main difference is that emoji-picker-element uses Svelte under the hood, so you're free to do import 'emoji-picker-element/svelte.js' to save some bytes. But it's a very minor performance optimization.

The other consideration is that this project doesn't support SSR, and you probably wouldn't want to SSR it anyway since it makes more sense to lazy-load it from a user interaction, client-side.

I hope that helps! Let me know if anything is unclear from the documentation. 🙇

from emoji-picker-element.

BigBoulard avatar BigBoulard commented on June 2, 2024

Hi @nolanlawson thank you for your response. I just realized that my question was misleading, sorry.
In fact, I'm using sveltekit but I don't need SSR, so my question is not really specific to sveltekit but svelte.

I just tried to install using the npm module cause I don't want to load the library at the application startup using the script tag (and all dependencies are actually managed as npm modules) but it failed I don't know why (I'm not a frontend dev):

pnpm run dev emoji-picker-element

In component.svelte ...

<script>
import 'emoji-picker-element';
...
</script>


<emoji-picker />
requestAnimationFrame is not defined
ReferenceError: requestAnimationFrame is not defined
    at file:///Users/me/dev/project/node_modules/.pnpm/[email protected]/node_modules/emoji-picker-element/picker.js:676:13
    at ModuleJob.run (node:internal/modules/esm/module_job:192:25)
    at async DefaultModuleLoader.import (node:internal/modules/esm/loader:228:24)
    at async nodeImport (file:///Users/me/dev/project/node_modules/.pnpm/[email protected][email protected]/node_modules/vite/dist/node/chunks/dep-bb8a8339.js:56097:17)
    at async ssrImport (file:///Users/me/dev/project/node_modules/.pnpm/[email protected]_terser

from emoji-picker-element.

nolanlawson avatar nolanlawson commented on June 2, 2024

Yep, that's because it only works in client-side rendering, not server-side rendering. I don't know what the mechanism in SvelteKit is to force something to render only client-side, but that's what you would need to do. requestAnimationFrame is only available in the browser, not in Node.js.

from emoji-picker-element.

BigBoulard avatar BigBoulard commented on June 2, 2024

Hi,

about prerendering: https://kit.svelte.dev/docs/page-options#prerender
about SSR: https://kit.svelte.dev/docs/page-options#ssr

I disabled prerendering by adding this file /routes/+layout.js with the code below

export const prerender = false;
export const ssr = false;

From there, It would have been great if I could be able to import like this but there's probably some adaptation to do in the npm package.

import { Picker } from 'emoji-picker-element';
// or this if there was a default export: import Picker from 'emoji-picker-element';
// or something like: import { Picker } from 'emoji-picker-element/svelte';

let picker = new Picker.default({
	locale: 'en'
});
picker.addEventListener('emoji-click', onPickerClick);
emojiPanel.appendChild(picker);

So, in the end, here is what's working. Pretty ugly but it works
I think it would be beneficial if you could adapt this a little bit this snippet and add it as an example to your README.md.

import { onMount } from 'svelte';

let Picker = null; // picker lib
let picker = null; // picker instance

onMount(async () => {
	Picker = await import('emoji-picker-element/svelte');

	picker = new Picker.default({
		locale: 'en'
	});
	picker.addEventListener('emoji-click', onPickerClick);
	emojiPanel.appendChild(picker);
});

function onPickerClick(e) {
	console.log(e.detail);
}
</script>

<div class="emoji-panel" class:hidden={!showEmojiPanel} bind:this={emojiPanel} />

<div class="input-wrapper">
  <input
		type="text"
		class="input-field"
		name="message"
		autocomplete="off"
  />
  <button class="emoji-button" on:click={() => (showEmojiPanel = !showEmojiPanel)}>&#128516;</button>
  <button class="send-button" on:click={send}>Send</button>
</div>

<style>
.emoji-panel {
	position: absolute;
	bottom: 50px;
	right: 80px;
}

 .input-wrapper{
	display: flex;
	align-items: center;
	padding: 10px;
}

.input-field {
	flex-grow: 1;
	border: none;
	outline: none;
	padding: 5px;
	text-align: right;
	width: 100%;
}

.emoji-button {
	background-color: transparent;
	border: none;
	cursor: pointer;
	font-size: 20px;
	margin-left: 10px;
}

.send-button {
	background-color: blue;
	padding: 10px 20px;
	cursor: pointer;
}

</style>

from emoji-picker-element.

Terkwood avatar Terkwood commented on June 2, 2024

This was really helpful. I wish the instructions were printed in the README, because I had to spend about 30 minutes searching around for it. I'm not very skilled as a frontend dev so it was nice to find this explanation in the issue tracker.

from emoji-picker-element.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.