@linear_non/stellar-libs 1.0.9 → 1.0.10

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@linear_non/stellar-libs",
3
- "version": "1.0.9",
3
+ "version": "1.0.10",
4
4
  "description": "Reusable JavaScript libraries for Non-Linear Studio projects.",
5
5
  "main": "src/index.js",
6
6
  "type": "module",
@@ -16,13 +16,11 @@ export default class SpritePlayer {
16
16
  fileExtension = "png",
17
17
  cache = null,
18
18
  persistent = false,
19
- // alpha options
20
- alpha_path = null, // { mobile: "...", desktop: "..." }
21
- fileAlpha = null, // e.g. "sprite_mask_"
19
+ alpha_path = null, // { mobile, desktop }
20
+ fileAlpha = null,
22
21
  useAlpha = false,
23
22
  }) {
24
23
  const rect = bounds(container)
25
-
26
24
  this.progress = gsap.utils.clamp(0, 1, progress)
27
25
  this.persistent = persistent
28
26
  this.isAlpha = !!useAlpha
@@ -56,8 +54,12 @@ export default class SpritePlayer {
56
54
  const { mobile_path, desktop_path, alpha_path, file_name, fileAlpha, total, file_extension, cache } =
57
55
  this.settings
58
56
 
59
- const originBase = sniffer.isDesktop ? desktop_path : mobile_path
60
- const originAlpha = alpha_path ? (sniffer.isDesktop ? alpha_path.desktop : alpha_path.mobile) : null
57
+ const originBase = sniffer.isDesktop ? desktop_path : mobile_path || desktop_path
58
+ const originAlpha = alpha_path
59
+ ? sniffer.isDesktop
60
+ ? alpha_path.desktop || alpha_path.mobile
61
+ : alpha_path.mobile || alpha_path.desktop
62
+ : null
61
63
 
62
64
  const make = (origin, name) =>
63
65
  new ImageLoader({
@@ -81,6 +83,12 @@ export default class SpritePlayer {
81
83
 
82
84
  this.dom.images = images
83
85
  this.dom.alphaImages = alphaImages
86
+
87
+ if (this.isAlpha && this.dom.alphaImages.length) {
88
+ this.dom.alphaImages = this.dom.alphaImages.map(img => this.toAlphaFromLuma(img))
89
+ }
90
+ if (this.isAlpha && !this.dom.alphaImages.length) this.isAlpha = false
91
+
84
92
  this.frameCount = images.length
85
93
  this.state.loaded = true
86
94
  emitter.emit("sprite:loaded", this)
@@ -104,9 +112,31 @@ export default class SpritePlayer {
104
112
  Object.assign(this.canvas, { width: rect.width, height: rect.height, rect, area, offset })
105
113
  }
106
114
 
115
+ // grayscale -> alpha (returns a canvas)
116
+ toAlphaFromLuma(img) {
117
+ const w = img.naturalWidth || img.width,
118
+ h = img.naturalHeight || img.height
119
+ const c = document.createElement("canvas")
120
+ c.width = w
121
+ c.height = h
122
+ const x = c.getContext("2d")
123
+ x.drawImage(img, 0, 0, w, h)
124
+ const d = x.getImageData(0, 0, w, h)
125
+ const a = d.data
126
+ for (let i = 0; i < a.length; i += 4) {
127
+ const lum = a[i] * 0.2126 + a[i + 1] * 0.7152 + a[i + 2] * 0.0722
128
+ a[i] = 0
129
+ a[i + 1] = 0
130
+ a[i + 2] = 0
131
+ a[i + 3] = lum
132
+ }
133
+ x.putImageData(d, 0, 0)
134
+ return c
135
+ }
136
+
107
137
  drawImageCover(ctx, img, area, offset) {
108
- const iw = img.naturalWidth,
109
- ih = img.naturalHeight
138
+ const iw = img.naturalWidth || img.width
139
+ const ih = img.naturalHeight || img.height
110
140
  const cw = area.width,
111
141
  ch = area.height
112
142
  const ir = iw / ih,
@@ -135,7 +165,8 @@ export default class SpritePlayer {
135
165
  const total = this.frameCount || images.length || 1
136
166
  const index = Math.min(total - 1, Math.round(this.progress * (total - 1)))
137
167
  const base = images[index]
138
- const mask = this.isAlpha ? alphaImages[index] : null
168
+ const hasMasks = this.isAlpha && alphaImages.length === images.length
169
+ const mask = hasMasks ? alphaImages[index] : null
139
170
 
140
171
  ctx.clearRect(0, 0, width, height)
141
172
  if (!base) return
@@ -143,9 +174,10 @@ export default class SpritePlayer {
143
174
  this.drawImageCover(ctx, base, area, offset)
144
175
 
145
176
  if (mask) {
177
+ ctx.save()
146
178
  ctx.globalCompositeOperation = "destination-in"
147
179
  this.drawImageCover(ctx, mask, area, offset)
148
- ctx.globalCompositeOperation = "source-over"
180
+ ctx.restore()
149
181
  }
150
182
  }
151
183
 
@@ -163,7 +195,6 @@ export default class SpritePlayer {
163
195
  setProgress(p) {
164
196
  this.progress = gsap.utils.clamp(0, 1, p)
165
197
  }
166
-
167
198
  show() {
168
199
  this.isVisible = true
169
200
  }
@@ -172,7 +203,6 @@ export default class SpritePlayer {
172
203
  const { ctx, width, height } = this.canvas
173
204
  ctx.clearRect(0, 0, width, height)
174
205
  }
175
-
176
206
  enableAlpha(v = true) {
177
207
  this.isAlpha = !!v
178
208
  }