@roomle/embedding-lib 5.5.0-debug.3 → 5.5.0-debug.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,539 @@
1
+ var C = Object.defineProperty;
2
+ var F = (r, s, e) => s in r ? C(r, s, { enumerable: !0, configurable: !0, writable: !0, value: e }) : r[s] = e;
3
+ var c = (r, s, e) => F(r, typeof s != "symbol" ? s + "" : s, e);
4
+ class y {
5
+ constructor(s, e, o, t) {
6
+ c(this, "_side");
7
+ // for better debugging (who handles message? iframe or website?)
8
+ c(this, "_incomingMessageBus");
9
+ c(this, "_outgoingMessageBus", null);
10
+ c(this, "_execMessage", null);
11
+ this._side = s, this._incomingMessageBus = e, this._outgoingMessageBus = o, this._execMessage = t, this._incomingMessageBus.addEventListener(
12
+ "message",
13
+ this._handleMessage.bind(this)
14
+ );
15
+ }
16
+ setOutgoingMessageBus(s) {
17
+ this._outgoingMessageBus = s;
18
+ }
19
+ setMessageExecution(s) {
20
+ this._execMessage = s;
21
+ }
22
+ sendMessage(s, e = []) {
23
+ return new Promise((o, t) => {
24
+ const n = new MessageChannel();
25
+ n.port1.onmessage = (a) => {
26
+ if (!a || !a.data)
27
+ return n.port1.close(), n.port2.close(), t(
28
+ new Error(
29
+ this._side + " received message but response can not be interpreted"
30
+ )
31
+ );
32
+ let i;
33
+ try {
34
+ i = JSON.parse(a.data);
35
+ } catch (d) {
36
+ return n.port1.close(), n.port2.close(), this._prepareError(d), t(d);
37
+ }
38
+ i.error ? t(i.error) : i.result !== void 0 ? o(i.result) : o(void 0), n.port1.close(), n.port2.close();
39
+ };
40
+ let l = "";
41
+ try {
42
+ l = JSON.stringify({ message: s, args: e });
43
+ } catch {
44
+ return t(
45
+ new Error(
46
+ this._side + ": can not create command because it is not JSON.stringify able"
47
+ )
48
+ );
49
+ }
50
+ if (!this._outgoingMessageBus)
51
+ return t(new Error(this._side + ": outgoing bus not set yet"));
52
+ this._outgoingMessageBus.postMessage(l, "*", [
53
+ n.port2
54
+ ]);
55
+ });
56
+ }
57
+ _handleMessage(s) {
58
+ const e = s.ports && Array.isArray(s.ports) && s.ports.length > 0 ? s.ports[0] : null;
59
+ if (s.data && e)
60
+ try {
61
+ const o = JSON.parse(s.data);
62
+ if (!this._execMessage)
63
+ return e.postMessage(
64
+ JSON.stringify({
65
+ error: this._side + " is not ready to handle messages"
66
+ })
67
+ );
68
+ Array.isArray(o.args) || (o.args = [o.args]);
69
+ const t = this._execMessage(o, s);
70
+ if (t === void 0)
71
+ return;
72
+ t.then(
73
+ (n = {}) => {
74
+ let l, a;
75
+ typeof n == "object" && n !== null && (l = n.error, a = n.result), l ? e.postMessage(
76
+ JSON.stringify({ error: l })
77
+ ) : a !== void 0 ? e.postMessage(
78
+ JSON.stringify({ result: a })
79
+ ) : e.postMessage(
80
+ JSON.stringify({ result: n })
81
+ );
82
+ },
83
+ (n) => {
84
+ e.postMessage(
85
+ JSON.stringify({
86
+ error: this._prepareError(n)
87
+ })
88
+ );
89
+ }
90
+ );
91
+ } catch (o) {
92
+ e.postMessage(
93
+ JSON.stringify({
94
+ error: this._prepareError(o)
95
+ })
96
+ );
97
+ }
98
+ }
99
+ _prepareError(s) {
100
+ if (typeof s == "string") {
101
+ const e = this._side + ": " + s;
102
+ return console.error(e), e;
103
+ }
104
+ return s.message = this._side + ": " + s.message, console.error(s), s.message;
105
+ }
106
+ }
107
+ const p = ".", E = {
108
+ REQUEST_BOOT: "requestBoot",
109
+ SETUP: "setup",
110
+ WEBSITE_READY: "websiteReady"
111
+ }, _ = {
112
+ GET_METHODS: "getMethods",
113
+ RETURN_METHODS: "returnMethods",
114
+ REGISTER_CUSTOM_VIEW: "registerCustomView",
115
+ REGISTER_CUSTOM_VIEW_DONE: "registerCustomViewDone"
116
+ }, U = async (r, s) => {
117
+ if (typeof r != "string")
118
+ throw new Error(
119
+ 'Configurator ID is not a string type: "' + typeof r + '"'
120
+ );
121
+ const e = s.customApiUrl ? s.customApiUrl : "https://api.roomle.com/v2", o = s.overrideTenant || 9, t = e + "/configurators/" + r, n = "roomle_portal_v2", l = "03-" + window.btoa((/* @__PURE__ */ new Date()).toISOString() + ";anonymous;" + n), a = () => {
122
+ const h = {
123
+ apiKey: n,
124
+ currentTenant: o,
125
+ locale: "en",
126
+ language: "en",
127
+ device: 1,
128
+ token: l,
129
+ platform: "web"
130
+ };
131
+ return new Headers(h);
132
+ }, i = new Request(t, {
133
+ method: "GET",
134
+ headers: a(),
135
+ mode: "cors",
136
+ cache: "default"
137
+ }), d = await fetch(i), { configurator: g } = await d.json();
138
+ return g;
139
+ }, B = () => {
140
+ try {
141
+ return window.self !== window.top;
142
+ } catch {
143
+ return !0;
144
+ }
145
+ }, k = ["127.0.0.1", "localhost", "0.0.0.0"], W = () => {
146
+ const r = B();
147
+ let s = window.location.href;
148
+ if (r) {
149
+ if (!document.referrer)
150
+ return null;
151
+ s = document.referrer;
152
+ }
153
+ const { hostname: e } = new URL(s);
154
+ return e;
155
+ }, x = (r) => !!(k.includes(r) || r.endsWith("roomle.com") || r.endsWith("gitlab.io") || r.endsWith("gitlab.com")), M = [
156
+ "language",
157
+ "browserLanguage",
158
+ "userLanguage",
159
+ "systemLanguage"
160
+ ], G = (r = null) => {
161
+ const s = window.navigator;
162
+ if (r)
163
+ return r.substr(0, 2);
164
+ if (Array.isArray(s.languages) && s.languages.length > 0)
165
+ return s.languages[0].substr(0, 2);
166
+ for (let e = 0, o = M.length; e < o; e++) {
167
+ const t = s[M[e]];
168
+ if (t)
169
+ return t.substr(0, 2);
170
+ }
171
+ return "en";
172
+ }, V = (r, s) => {
173
+ const e = JSON.parse(JSON.stringify(r));
174
+ return S(e, s);
175
+ }, S = (r, s) => {
176
+ for (const e in s)
177
+ try {
178
+ s[e].constructor === Object ? r[e] = S(r[e], s[e]) : r[e] = s[e];
179
+ } catch {
180
+ r[e] = s[e];
181
+ }
182
+ return r;
183
+ };
184
+ var J = { BASE_URL: "/", DEV: !1, MODE: "production", PROD: !0, SSR: !1 };
185
+ const $ = {
186
+ mobileLandscape: !0,
187
+ floorMaterialRootTag: "materials_root",
188
+ buttons: {
189
+ renderimage: !0,
190
+ requestproduct: !0,
191
+ requestplan: !0,
192
+ load_product: !0,
193
+ partlist_print: !0
194
+ },
195
+ helpcenter: {
196
+ roomdesigner: !0,
197
+ configurator: !1,
198
+ disable: !1
199
+ },
200
+ firstPersonView: !0,
201
+ saveToIdb: !0,
202
+ featureFlags: {
203
+ mocAr: !0
204
+ },
205
+ rotationSnapDegrees: 10
206
+ }, z = "(idle)", Y = (r) => (O(r), r != null && r.customApiUrl && (r.customApiUrl = decodeURIComponent(r.customApiUrl)), r.shareUrl && (r.deeplink = r.shareUrl.replace(
207
+ Q,
208
+ X
209
+ )), r), O = (r) => {
210
+ if (!r)
211
+ return;
212
+ const s = Object.keys(r);
213
+ for (const e of s) {
214
+ const o = r[e];
215
+ if (!Array.isArray(o) && typeof o == "object" && o !== null && O(o), Array.isArray(o))
216
+ for (const t of o)
217
+ O(t);
218
+ (o === "true" || o === "false") && (r[e] = o === "true");
219
+ }
220
+ }, q = (r, s) => {
221
+ s.configuratorId = r.id;
222
+ const e = r.settings || {};
223
+ return !s.overrideTenant && r.tenant && (s.overrideTenant = r.tenant), V(e, s);
224
+ }, K = () => {
225
+ const r = {
226
+ ...$
227
+ };
228
+ r.locale || (r.locale = G()), r.id === z && delete r.id;
229
+ const s = W();
230
+ return s && x(s) && (r.configuratorId = "demoConfigurator"), r.customApiUrl = J.VITE_RAPI_URL, r.emails = !1, r;
231
+ }, Q = "<CONF_ID>", X = "#CONFIGURATIONID#", R = () => /(android)/i.test(navigator.userAgent);
232
+ class T {
233
+ constructor() {
234
+ c(this, "_messageHandler", null);
235
+ c(this, "isSetupDone", !1);
236
+ c(this, "viewName", "main");
237
+ c(this, "plugins", {});
238
+ c(this, "pluginsLoaded", []);
239
+ c(this, "ui", {
240
+ callbacks: null
241
+ });
242
+ c(this, "extended", {
243
+ callbacks: null
244
+ });
245
+ c(this, "configurator", {
246
+ callbacks: null
247
+ });
248
+ c(this, "analytics", {
249
+ callbacks: {}
250
+ });
251
+ c(this, "global", {
252
+ callbacks: {}
253
+ });
254
+ }
255
+ setMessageHandler(s) {
256
+ this._messageHandler = s;
257
+ }
258
+ handleSetup(s) {
259
+ const { methods: e, callbacks: o } = s;
260
+ e.forEach((t) => {
261
+ const n = t.split(p), l = n[0], a = n[1];
262
+ this[l] || (this[l] = {}), this[l][a] = (function() {
263
+ if (!this._messageHandler) {
264
+ console.error("MessageHandler not set");
265
+ return;
266
+ }
267
+ return this._messageHandler.sendMessage(t, [...arguments]);
268
+ }).bind(this);
269
+ }), o.forEach((t) => {
270
+ const n = t.split(p), l = n[0], a = n[1], i = n[2];
271
+ this[l] || (this[l] = {}), this[l][a] || (this[l][a] = {}), this[l][a][i] = () => {
272
+ };
273
+ }), this.isSetupDone = !0;
274
+ }
275
+ executeMessage({ message: s, args: e }) {
276
+ const o = s.split(p), t = o[0], n = o[1], l = o.length === 3 ? o[2] : null;
277
+ if (l && this[t][n][l]) {
278
+ const a = this[t][n][l](
279
+ ...e
280
+ );
281
+ return a instanceof Promise ? a.then((i) => ({ result: i })) : a !== void 0 ? Promise.resolve({ result: a }) : Promise.resolve({ result: null });
282
+ }
283
+ return Promise.reject('Message "' + s + '" is unkown');
284
+ }
285
+ setupPlugins(s, e, o = "website") {
286
+ for (const t of s)
287
+ typeof t == "string" && t === "dragIn" ? this.pluginsLoaded.push(
288
+ new Promise((n, l) => {
289
+ try {
290
+ import("./drag-in-B_Ab1D0Y.mjs").then(
291
+ ({ DragIn: a }) => {
292
+ const i = new a(e, o);
293
+ i.setInstance(this.ui), i.setViewName(this.viewName), this.plugins.dragIn = i, n();
294
+ }
295
+ );
296
+ } catch (a) {
297
+ l(a);
298
+ }
299
+ })
300
+ ) : t.name && t.loader && this.pluginsLoaded.push(
301
+ new Promise((n, l) => {
302
+ try {
303
+ t.loader().then((a) => {
304
+ const i = new a(e, o);
305
+ i.setInstance(this.ui), i.setViewName(this.viewName), this.plugins[t.name] = i, n();
306
+ });
307
+ } catch (a) {
308
+ l(a);
309
+ }
310
+ })
311
+ );
312
+ }
313
+ }
314
+ const A = () => {
315
+ let r, s;
316
+ return { promise: new Promise((o, t) => {
317
+ r = o, s = t;
318
+ }), resolve: r, reject: s };
319
+ }, N = (r, s, e) => {
320
+ let o = null;
321
+ Object.defineProperty(r, s, {
322
+ get() {
323
+ return o || e;
324
+ },
325
+ set(t) {
326
+ t != null && t.mute ? o = t.value : (console.warn(
327
+ "You override Roomle defined behaviour. To disalbe this warning pass in an object with the following properties"
328
+ ), console.warn("{ mute: true, value: () => void }"), o = t);
329
+ }
330
+ });
331
+ }, v = () => window.innerHeight * 0.01 + "px", L = (r) => {
332
+ r && setTimeout(
333
+ () => r.style.setProperty(I, v()),
334
+ 0
335
+ );
336
+ }, b = "rml-styles", Z = 450, I = "--rml-full-height", u = {
337
+ CONTAINER: "rml-container",
338
+ FILL: "rml-fill",
339
+ POSITION: "rml-pos",
340
+ TRANSITION: "rml-transition",
341
+ ANDROID_HEIGHT: "rml-android-height",
342
+ OVERFLOW_HIDDEN: "rml-overflow-hidden"
343
+ }, w = /* @__PURE__ */ new Map();
344
+ class ee extends T {
345
+ constructor(e, o, t, n, l) {
346
+ super();
347
+ c(this, "_waitForIframe");
348
+ c(this, "_container");
349
+ c(this, "_configuratorSettings");
350
+ c(this, "_initData", {});
351
+ c(this, "_iframe");
352
+ if (!e || typeof e.id != "string")
353
+ throw new Error(
354
+ "Please provide a correct configuratorId, you get the correct ID from your Roomle Contact Person"
355
+ );
356
+ if (w.has(o))
357
+ throw new Error("There is already an instance on this DOM element");
358
+ if (!!!document.getElementById(b)) {
359
+ const g = t.zIndex || 9999999, h = document.createElement("style");
360
+ h.type = "text/css", h.id = b;
361
+ const f = "transition:all ease-in-out " + Z + "ms;", m = ["-webkit-", "-o-"].reduce(
362
+ (P, D) => P += D + f,
363
+ ""
364
+ ) + f, H = v();
365
+ h.innerHTML = `
366
+ .${u.CONTAINER}{${I}:${H};}
367
+ .${u.POSITION}{position:fixed;top:0;left:0;z-index:${g};opacity:0}
368
+ .${u.TRANSITION}{${m}}
369
+ .${u.FILL}{width:100%;height:100%;opacity:1}
370
+ .${u.ANDROID_HEIGHT}{height:calc(var(${I},1vh)*100)}
371
+ .${u.OVERFLOW_HIDDEN}{overflow:hidden}
372
+ `, document.head.appendChild(h);
373
+ }
374
+ this._executeMessage = this._executeMessage.bind(this);
375
+ const i = new y(
376
+ "website",
377
+ window,
378
+ null,
379
+ this._executeMessage
380
+ );
381
+ this.setMessageHandler(i), this._onResize = this._onResize.bind(this), R() && window.addEventListener("resize", this._onResize), this._container = o, this._initData = t, this._configuratorSettings = e;
382
+ const d = this._createIframe();
383
+ this._onUseFullPage = this._onUseFullPage.bind(this), this._onBackToWebsite = this._onBackToWebsite.bind(this), this._waitForIframe = l, this._container.appendChild(d), this._iframe = d, this.setupPlugins(n, this._iframe), w.set(o, !0);
384
+ }
385
+ static createPlanner(e, o, t, n = []) {
386
+ return this._create(
387
+ e,
388
+ o,
389
+ t,
390
+ n
391
+ );
392
+ }
393
+ static async connect(e, o = []) {
394
+ const t = new T();
395
+ t.viewName = e;
396
+ const { resolve: n, promise: l } = A(), { resolve: a, promise: i } = A(), d = ({
397
+ message: f,
398
+ args: m
399
+ }) => {
400
+ if (f === _.REGISTER_CUSTOM_VIEW_DONE) {
401
+ n();
402
+ return;
403
+ }
404
+ if (f === _.RETURN_METHODS) {
405
+ t.handleSetup(m[0]), a();
406
+ return;
407
+ }
408
+ if (t.isSetupDone)
409
+ return t.executeMessage({ message: f, args: m });
410
+ }, g = new y(
411
+ "custom-view",
412
+ window,
413
+ window.parent,
414
+ d
415
+ );
416
+ t.setMessageHandler(g);
417
+ const h = [e];
418
+ return g.sendMessage(
419
+ _.REGISTER_CUSTOM_VIEW,
420
+ h
421
+ ), await l, g.sendMessage(_.GET_METHODS, h), await i, t.setupPlugins(
422
+ o,
423
+ document.body,
424
+ "custom-view"
425
+ ), await Promise.allSettled(t.pluginsLoaded), t;
426
+ }
427
+ /**
428
+ * Method to create a new instance of a Roomle Configurator
429
+ * @param configuratorId the id which identifies your configurator, you will get this ID from your Roomle Contact Person
430
+ * @param container DOM container in which the configurator should be placed
431
+ * @param initData settings with which the configurator should be started
432
+ */
433
+ static createConfigurator(e, o, t, n = []) {
434
+ return this._create(
435
+ e,
436
+ o,
437
+ t,
438
+ n
439
+ );
440
+ }
441
+ /**
442
+ * Method to create a new instance of a Roomle Configurator
443
+ * @deprecated please use "createConfigurator"
444
+ * @param configuratorId the id which identifies your configurator, you will get this ID from your Roomle Contact Person
445
+ * @param container DOM container in which the configurator should be placed
446
+ * @param initData settings with which the configurator should be started
447
+ */
448
+ static create(e, o, t, n) {
449
+ return this._create(
450
+ e,
451
+ o,
452
+ t,
453
+ n
454
+ );
455
+ }
456
+ /**
457
+ * Method to create a new instance of a Roomle Viewer
458
+ * @param configuratorId the id which identifies your configurator, you will get this ID from your Roomle Contact Person
459
+ * @param container DOM container in which the configurator should be placed
460
+ * @param initData settings with which the configurator should be started
461
+ */
462
+ static createViewer(e, o, t, n = []) {
463
+ return this._create(
464
+ e,
465
+ o,
466
+ t,
467
+ n
468
+ );
469
+ }
470
+ static async _create(e, o, t, n) {
471
+ return new Promise(async (l, a) => {
472
+ try {
473
+ const i = S(
474
+ K(),
475
+ Y(t)
476
+ );
477
+ i.featureFlags || (i.featureFlags = {}), typeof i.featureFlags.realPartList != "boolean" && (i.featureFlags.realPartList = !0), typeof i.featureFlags.globalCallbacks != "boolean" && (i.featureFlags.globalCallbacks = !0), typeof i.featureFlags.mocAr != "boolean" && (i.featureFlags.mocAr = !1);
478
+ const d = await U(
479
+ e,
480
+ i
481
+ );
482
+ t = q(d, i);
483
+ const g = new this(
484
+ d,
485
+ o,
486
+ t,
487
+ n,
488
+ l
489
+ );
490
+ return await Promise.allSettled(g.pluginsLoaded), g;
491
+ } catch (i) {
492
+ return a(i);
493
+ }
494
+ });
495
+ }
496
+ teardown() {
497
+ this._container && w.delete(this._container);
498
+ const e = this._container.querySelector("iframe");
499
+ e && this._container.removeChild(e), window.removeEventListener("resize", this._onResize);
500
+ }
501
+ _createIframe() {
502
+ var t;
503
+ const e = document.createElement("iframe");
504
+ let o = ((t = this._configuratorSettings) == null ? void 0 : t.url) || "https://www.roomle.com/t/cp/";
505
+ return this._initData.useLocalRoomle && (o = location.href.replace("embedding.html", "")), location.href.includes("roomle.gitlab.io") && (o = location.href.replace("embedding.html", "index.html")), this._initData.overrideServerUrl && (o = this._initData.overrideServerUrl), e.src = o, e.classList.add(u.CONTAINER), e.classList.add(u.FILL), e;
506
+ }
507
+ _onResize() {
508
+ L(this._iframe);
509
+ }
510
+ _onUseFullPage() {
511
+ this._iframe.classList.add(u.POSITION), document.documentElement.classList.add(u.OVERFLOW_HIDDEN), window.document.body.classList.add(u.OVERFLOW_HIDDEN), R() && (L(this._iframe), this._iframe.classList.add(u.ANDROID_HEIGHT));
512
+ }
513
+ _onBackToWebsite() {
514
+ this._iframe.classList.remove(u.POSITION), this._iframe.classList.remove(u.ANDROID_HEIGHT), document.documentElement.classList.remove(u.OVERFLOW_HIDDEN), window.document.body.classList.remove(u.OVERFLOW_HIDDEN);
515
+ }
516
+ _executeMessage({ message: e, args: o }, t) {
517
+ var n;
518
+ if (t.source && t.source === ((n = this._iframe) == null ? void 0 : n.contentWindow))
519
+ return e === E.REQUEST_BOOT ? this._messageHandler ? (this._messageHandler.setOutgoingMessageBus(t.source), Promise.resolve({ result: this._initData })) : (console.error("MessageHandler not set"), Promise.resolve({ error: "MessageHandler not set" })) : e === E.SETUP ? (this.handleSetup(o[0]), N(
520
+ this.ui.callbacks,
521
+ "onUseFullPage",
522
+ this._onUseFullPage
523
+ ), N(
524
+ this.ui.callbacks,
525
+ "onBackToWebsite",
526
+ this._onBackToWebsite
527
+ ), this._waitForIframe(this), setTimeout(() => {
528
+ if (!this._messageHandler) {
529
+ console.error("MessageHandler not set");
530
+ return;
531
+ }
532
+ this._messageHandler.sendMessage(E.WEBSITE_READY);
533
+ }, 0), Promise.resolve({ result: null })) : this.executeMessage({ message: e, args: o });
534
+ }
535
+ }
536
+ export {
537
+ ee as R,
538
+ A as p
539
+ };
@@ -0,0 +1,8 @@
1
+ var H=Object.defineProperty,A=(r,e,t)=>e in r?H(r,e,{enumerable:!0,configurable:!0,writable:!0,value:t}):r[e]=t,c=(r,e,t)=>A(r,typeof e!="symbol"?e+"":e,t);class b{constructor(e,t,s,i){c(this,"_side"),c(this,"_incomingMessageBus"),c(this,"_outgoingMessageBus",null),c(this,"_execMessage",null),this._side=e,this._incomingMessageBus=t,this._outgoingMessageBus=s,this._execMessage=i,this._incomingMessageBus.addEventListener("message",this._handleMessage.bind(this))}setOutgoingMessageBus(e){this._outgoingMessageBus=e}setMessageExecution(e){this._execMessage=e}sendMessage(e,t=[]){return new Promise((s,i)=>{const o=new MessageChannel;o.port1.onmessage=n=>{if(!n||!n.data)return o.port1.close(),o.port2.close(),i(new Error(this._side+" received message but response can not be interpreted"));let l;try{l=JSON.parse(n.data)}catch(u){return o.port1.close(),o.port2.close(),this._prepareError(u),i(u)}l.error?i(l.error):l.result!==void 0?s(l.result):s(void 0),o.port1.close(),o.port2.close()};let a="";try{a=JSON.stringify({message:e,args:t})}catch{return i(new Error(this._side+": can not create command because it is not JSON.stringify able"))}if(!this._outgoingMessageBus)return i(new Error(this._side+": outgoing bus not set yet"));this._outgoingMessageBus.postMessage(a,"*",[o.port2])})}_handleMessage(e){const t=e.ports&&Array.isArray(e.ports)&&e.ports.length>0?e.ports[0]:null;if(e.data&&t)try{const s=JSON.parse(e.data);if(!this._execMessage)return t.postMessage(JSON.stringify({error:this._side+" is not ready to handle messages"}));Array.isArray(s.args)||(s.args=[s.args]);const i=this._execMessage(s,e);if(i===void 0)return;i.then((o={})=>{let a,n;typeof o=="object"&&o!==null&&(a=o.error,n=o.result),a?t.postMessage(JSON.stringify({error:a})):n!==void 0?t.postMessage(JSON.stringify({result:n})):t.postMessage(JSON.stringify({result:o}))},o=>{t.postMessage(JSON.stringify({error:this._prepareError(o)}))})}catch(s){t.postMessage(JSON.stringify({error:this._prepareError(s)}))}}_prepareError(e){if(typeof e=="string"){const t=this._side+": "+e;return console.error(t),t}return e.message=this._side+": "+e.message,console.error(e),e.message}}const p=".",f={REQUEST_BOOT:"requestBoot",SETUP:"setup",WEBSITE_READY:"websiteReady"},_={GET_METHODS:"getMethods",RETURN_METHODS:"returnMethods",REGISTER_CUSTOM_VIEW:"registerCustomView",REGISTER_CUSTOM_VIEW_DONE:"registerCustomViewDone"},U=async(r,e)=>{if(typeof r!="string")throw new Error('Configurator ID is not a string type: "'+typeof r+'"');const t=e.customApiUrl?e.customApiUrl:"https://api.roomle.com/v2",s=e.overrideTenant||9,i=t+"/configurators/"+r,o="roomle_portal_v2",a="03-"+window.btoa(new Date().toISOString()+";anonymous;"+o),n=()=>{const h={apiKey:o,currentTenant:s,locale:"en",language:"en",device:1,token:a,platform:"web"};return new Headers(h)},l=new Request(i,{method:"GET",headers:n(),mode:"cors",cache:"default"}),u=await fetch(l),{configurator:d}=await u.json();return d},F=()=>{try{return window.self!==window.top}catch{return!0}},x=["127.0.0.1","localhost","0.0.0.0"],B=()=>{const r=F();let e=window.location.href;if(r){if(!document.referrer)return null;e=document.referrer}const{hostname:t}=new URL(e);return t},C=r=>!!(x.includes(r)||r.endsWith("roomle.com")||r.endsWith("gitlab.io")||r.endsWith("gitlab.com")),v=["language","browserLanguage","userLanguage","systemLanguage"],W=(r=null)=>{const e=window.navigator;if(r)return r.substr(0,2);if(Array.isArray(e.languages)&&e.languages.length>0)return e.languages[0].substr(0,2);for(let t=0,s=v.length;t<s;t++){const i=e[v[t]];if(i)return i.substr(0,2)}return"en"},k=(r,e)=>{const t=JSON.parse(JSON.stringify(r));return w(t,e)},w=(r,e)=>{for(const t in e)try{e[t].constructor===Object?r[t]=w(r[t],e[t]):r[t]=e[t]}catch{r[t]=e[t]}return r};var V={BASE_URL:"/",DEV:!1,MODE:"production",PROD:!0,SSR:!1};const G={mobileLandscape:!0,floorMaterialRootTag:"materials_root",buttons:{renderimage:!0,requestproduct:!0,requestplan:!0,load_product:!0,partlist_print:!0},helpcenter:{roomdesigner:!0,configurator:!1,disable:!1},firstPersonView:!0,saveToIdb:!0,featureFlags:{mocAr:!0},rotationSnapDegrees:10},J="(idle)",$=r=>(E(r),r!=null&&r.customApiUrl&&(r.customApiUrl=decodeURIComponent(r.customApiUrl)),r.shareUrl&&(r.deeplink=r.shareUrl.replace(q,Y)),r),E=r=>{if(!r)return;const e=Object.keys(r);for(const t of e){const s=r[t];if(!Array.isArray(s)&&typeof s=="object"&&s!==null&&E(s),Array.isArray(s))for(const i of s)E(i);(s==="true"||s==="false")&&(r[t]=s==="true")}},j=(r,e)=>{e.configuratorId=r.id;const t=r.settings||{};return!e.overrideTenant&&r.tenant&&(e.overrideTenant=r.tenant),k(t,e)},z=()=>{const r={...G};r.locale||(r.locale=W()),r.id===J&&delete r.id;const e=B();return e&&C(e)&&(r.configuratorId="demoConfigurator"),r.customApiUrl=V.VITE_RAPI_URL,r.emails=!1,r},q="<CONF_ID>",Y="#CONFIGURATIONID#",M=()=>/(android)/i.test(navigator.userAgent);class T{constructor(){c(this,"_messageHandler",null),c(this,"isSetupDone",!1),c(this,"viewName","main"),c(this,"plugins",{}),c(this,"pluginsLoaded",[]),c(this,"ui",{callbacks:null}),c(this,"extended",{callbacks:null}),c(this,"configurator",{callbacks:null}),c(this,"analytics",{callbacks:{}}),c(this,"global",{callbacks:{}})}setMessageHandler(e){this._messageHandler=e}handleSetup(e){const{methods:t,callbacks:s}=e;t.forEach(i=>{const o=i.split(p),a=o[0],n=o[1];this[a]||(this[a]={}),this[a][n]=function(){if(!this._messageHandler){console.error("MessageHandler not set");return}return this._messageHandler.sendMessage(i,[...arguments])}.bind(this)}),s.forEach(i=>{const o=i.split(p),a=o[0],n=o[1],l=o[2];this[a]||(this[a]={}),this[a][n]||(this[a][n]={}),this[a][n][l]=()=>{}}),this.isSetupDone=!0}executeMessage({message:e,args:t}){const s=e.split(p),i=s[0],o=s[1],a=s.length===3?s[2]:null;if(a&&this[i][o][a]){const n=this[i][o][a](...t);return n instanceof Promise?n.then(l=>({result:l})):n!==void 0?Promise.resolve({result:n}):Promise.resolve({result:null})}return Promise.reject('Message "'+e+'" is unkown')}setupPlugins(e,t,s="website"){for(const i of e)typeof i=="string"&&i==="dragIn"?this.pluginsLoaded.push(new Promise((o,a)=>{try{import("./drag-in-DKZRYdaz.mjs").then(({DragIn:n})=>{const l=new n(t,s);l.setInstance(this.ui),l.setViewName(this.viewName),this.plugins.dragIn=l,o()})}catch(n){a(n)}})):i.name&&i.loader&&this.pluginsLoaded.push(new Promise((o,a)=>{try{i.loader().then(n=>{const l=new n(t,s);l.setInstance(this.ui),l.setViewName(this.viewName),this.plugins[i.name]=l,o()})}catch(n){a(n)}}))}}const y=()=>{let r,e;return{promise:new Promise((t,s)=>{r=t,e=s}),resolve:r,reject:e}},S=(r,e,t)=>{let s=null;Object.defineProperty(r,e,{get(){return s||t},set(i){i!=null&&i.mute?s=i.value:(console.warn("You override Roomle defined behaviour. To disalbe this warning pass in an object with the following properties"),console.warn("{ mute: true, value: () => void }"),s=i)}})},R=()=>window.innerHeight*.01+"px",N=r=>{r&&setTimeout(()=>r.style.setProperty(I,R()),0)},D="rml-styles",Q=450,I="--rml-full-height",g={CONTAINER:"rml-container",FILL:"rml-fill",POSITION:"rml-pos",TRANSITION:"rml-transition",ANDROID_HEIGHT:"rml-android-height",OVERFLOW_HIDDEN:"rml-overflow-hidden"},O=new Map;class K extends T{constructor(e,t,s,i,o){if(super(),c(this,"_waitForIframe"),c(this,"_container"),c(this,"_configuratorSettings"),c(this,"_initData",{}),c(this,"_iframe"),!e||typeof e.id!="string")throw new Error("Please provide a correct configuratorId, you get the correct ID from your Roomle Contact Person");if(O.has(t))throw new Error("There is already an instance on this DOM element");if(!document.getElementById(D)){const l=s.zIndex||9999999,u=document.createElement("style");u.type="text/css",u.id=D;const d="transition:all ease-in-out "+Q+"ms;",h=["-webkit-","-o-"].reduce((L,P)=>L+=P+d,"")+d,m=R();u.innerHTML=`
2
+ .${g.CONTAINER}{${I}:${m};}
3
+ .${g.POSITION}{position:fixed;top:0;left:0;z-index:${l};opacity:0}
4
+ .${g.TRANSITION}{${h}}
5
+ .${g.FILL}{width:100%;height:100%;opacity:1}
6
+ .${g.ANDROID_HEIGHT}{height:calc(var(${I},1vh)*100)}
7
+ .${g.OVERFLOW_HIDDEN}{overflow:hidden}
8
+ `,document.head.appendChild(u)}this._executeMessage=this._executeMessage.bind(this);const a=new b("website",window,null,this._executeMessage);this.setMessageHandler(a),this._onResize=this._onResize.bind(this),M()&&window.addEventListener("resize",this._onResize),this._container=t,this._initData=s,this._configuratorSettings=e;const n=this._createIframe();this._onUseFullPage=this._onUseFullPage.bind(this),this._onBackToWebsite=this._onBackToWebsite.bind(this),this._waitForIframe=o,this._container.appendChild(n),this._iframe=n,this.setupPlugins(i,this._iframe),O.set(t,!0)}static createPlanner(e,t,s,i=[]){return this._create(e,t,s,i)}static async connect(e,t=[]){const s=new T;s.viewName=e;const{resolve:i,promise:o}=y(),{resolve:a,promise:n}=y(),l=({message:h,args:m})=>{if(h===_.REGISTER_CUSTOM_VIEW_DONE){i();return}if(h===_.RETURN_METHODS){s.handleSetup(m[0]),a();return}if(s.isSetupDone)return s.executeMessage({message:h,args:m})},u=new b("custom-view",window,window.parent,l);s.setMessageHandler(u);const d=[e];return u.sendMessage(_.REGISTER_CUSTOM_VIEW,d),await o,u.sendMessage(_.GET_METHODS,d),await n,s.setupPlugins(t,document.body,"custom-view"),await Promise.allSettled(s.pluginsLoaded),s}static createConfigurator(e,t,s,i=[]){return this._create(e,t,s,i)}static create(e,t,s,i){return this._create(e,t,s,i)}static createViewer(e,t,s,i=[]){return this._create(e,t,s,i)}static async _create(e,t,s,i){return new Promise(async(o,a)=>{try{const n=w(z(),$(s));n.featureFlags||(n.featureFlags={}),typeof n.featureFlags.realPartList!="boolean"&&(n.featureFlags.realPartList=!0),typeof n.featureFlags.globalCallbacks!="boolean"&&(n.featureFlags.globalCallbacks=!0),typeof n.featureFlags.mocAr!="boolean"&&(n.featureFlags.mocAr=!1);const l=await U(e,n);s=j(l,n);const u=new this(l,t,s,i,o);return await Promise.allSettled(u.pluginsLoaded),u}catch(n){return a(n)}})}teardown(){this._container&&O.delete(this._container);const e=this._container.querySelector("iframe");e&&this._container.removeChild(e),window.removeEventListener("resize",this._onResize)}_createIframe(){var e;const t=document.createElement("iframe");let s=((e=this._configuratorSettings)==null?void 0:e.url)||"https://www.roomle.com/t/cp/";return this._initData.useLocalRoomle&&(s=location.href.replace("embedding.html","")),location.href.includes("roomle.gitlab.io")&&(s=location.href.replace("embedding.html","index.html")),this._initData.overrideServerUrl&&(s=this._initData.overrideServerUrl),t.src=s,t.classList.add(g.CONTAINER),t.classList.add(g.FILL),t}_onResize(){N(this._iframe)}_onUseFullPage(){this._iframe.classList.add(g.POSITION),document.documentElement.classList.add(g.OVERFLOW_HIDDEN),window.document.body.classList.add(g.OVERFLOW_HIDDEN),M()&&(N(this._iframe),this._iframe.classList.add(g.ANDROID_HEIGHT))}_onBackToWebsite(){this._iframe.classList.remove(g.POSITION),this._iframe.classList.remove(g.ANDROID_HEIGHT),document.documentElement.classList.remove(g.OVERFLOW_HIDDEN),window.document.body.classList.remove(g.OVERFLOW_HIDDEN)}_executeMessage({message:e,args:t},s){var i;if(s.source&&s.source===((i=this._iframe)==null?void 0:i.contentWindow))return e===f.REQUEST_BOOT?this._messageHandler?(this._messageHandler.setOutgoingMessageBus(s.source),Promise.resolve({result:this._initData})):(console.error("MessageHandler not set"),Promise.resolve({error:"MessageHandler not set"})):e===f.SETUP?(this.handleSetup(t[0]),S(this.ui.callbacks,"onUseFullPage",this._onUseFullPage),S(this.ui.callbacks,"onBackToWebsite",this._onBackToWebsite),this._waitForIframe(this),setTimeout(()=>{if(!this._messageHandler){console.error("MessageHandler not set");return}this._messageHandler.sendMessage(f.WEBSITE_READY)},0),Promise.resolve({result:null})):this.executeMessage({message:e,args:t})}}export{K as R,y as p};
package/index.d.ts CHANGED
@@ -16,9 +16,9 @@ import { PossibleCustomViewsAndMain as PossibleCustomViewsAndMain_2 } from '../.
16
16
  import { RapiId } from '@roomle/web-sdk/lib/definitions/typings/rapi-types';
17
17
  import { UiInitData } from '../../../src/configurator/embedding/types';
18
18
 
19
- declare interface AvailablePlugins {
20
- dragIn?: DragIn;
21
- }
19
+ declare type AvailablePlugins = {
20
+ [K in keyof PluginMap]?: InstanceType<PluginMap[K]>;
21
+ };
22
22
 
23
23
  declare class Connector<SdkType, SdkCallbacks> implements RoomleEmbeddingApiKeys {
24
24
  protected _messageHandler: Nullable<MessageHandler>;
@@ -47,11 +47,11 @@ declare class Connector<SdkType, SdkCallbacks> implements RoomleEmbeddingApiKeys
47
47
  }
48
48
 
49
49
  declare class DragIn extends EmbeddingPlugin {
50
- private _mainDomElement;
51
50
  private _currentDrag;
52
51
  private _currentTouch;
53
52
  private _firefoxDragPosition;
54
53
  private _readyForDragUpdates;
54
+ private _clientRect;
55
55
  options: {
56
56
  dragInOverlapX?: number;
57
57
  dragInOverlapY?: number;
@@ -63,9 +63,9 @@ declare class DragIn extends EmbeddingPlugin {
63
63
  private _injectStyles;
64
64
  private _initializeDragGhost;
65
65
  private _initReadyForDragUpdates;
66
- constructor(iframe: HTMLIFrameElement | HTMLBodyElement);
66
+ constructor(iframe: HTMLIFrameElement | HTMLBodyElement, mode: EmbeddingPluginMode);
67
67
  setInstance(instance: ExposedApi): void;
68
- setMode(mode: EmbeddingPluginMode): void;
68
+ private _initDom;
69
69
  private _firefoxFallback;
70
70
  dragStart(id: RapiId, event: DragEvent | TouchEvent, type?: string): Promise<void>;
71
71
  /** MUST NOT BE ASYNC, OTHERWISE ACCESS TO event.clientX could be wrong */
@@ -77,22 +77,31 @@ declare class DragIn extends EmbeddingPlugin {
77
77
  dispose(): void;
78
78
  }
79
79
 
80
- declare abstract class EmbeddingPlugin {
80
+ declare class EmbeddingPlugin {
81
+ protected _mainDomElement: HTMLIFrameElement | HTMLBodyElement;
81
82
  protected _instance: Nullable_2<ExposedApi>;
82
83
  protected _mode: EmbeddingPluginMode;
83
84
  protected _viewName: PossibleCustomViewsAndMain_2;
85
+ constructor(iframe: HTMLIFrameElement | HTMLBodyElement, mode: EmbeddingPluginMode);
84
86
  setInstance(instance: ExposedApi): void;
85
- setMode(mode: EmbeddingPluginMode): void;
86
87
  setViewName(viewName: PossibleCustomViewsAndMain_2): void;
87
88
  }
88
89
 
89
90
  declare type EmbeddingPluginMode = 'website' | 'custom-view';
90
91
 
92
+ declare type PluginConstructors = {
93
+ [K in keyof PluginMap]: PluginMap[K];
94
+ };
95
+
91
96
  declare type PluginDefinitions = Array<keyof AvailablePlugins | {
92
97
  name: keyof AvailablePlugins;
93
- loader: () => Promise<any>;
98
+ loader: () => Promise<PluginConstructors[keyof PluginConstructors]>;
94
99
  }>;
95
100
 
101
+ declare interface PluginMap {
102
+ dragIn: typeof DragIn;
103
+ }
104
+
96
105
  declare type RoomleConfiguratorApi = RoomleEmbeddingApi<default_2, default_4>;
97
106
 
98
107
  declare class RoomleEmbeddingApi<SdkType, SdkCallbacks> extends Connector<SdkType, SdkCallbacks> {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@roomle/embedding-lib",
3
- "version": "5.5.0-debug.3",
3
+ "version": "5.5.0-debug.5",
4
4
  "description": "This is a small library which can be used to communicate with the Roomle Configurator",
5
5
  "type": "module",
6
6
  "main": "./roomle-embedding-lib.umd.js",