pinokiod 3.48.0 → 3.50.0

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.
@@ -13,6 +13,18 @@ body {
13
13
  display: grid;
14
14
  grid-template-rows: var(--row0, 1fr) 6px var(--row1, 1fr);
15
15
  gap: 0px;
16
+ position: relative;
17
+ }
18
+ #dragger {
19
+ -webkit-app-region: drag;
20
+ cursor: drag;
21
+ position: absolute;
22
+ top: 0;
23
+ left: 0;
24
+ right: 0;
25
+ height: 20px;
26
+ width: 100%;
27
+ z-index: 1000000000000;
16
28
  }
17
29
  body iframe {
18
30
  border: none;
@@ -54,8 +66,10 @@ body.resizing {
54
66
  .gutter:hover::before, body.resizing .gutter::before { background: #9e9e9e; }
55
67
  .gutter:focus { outline: none; box-shadow: inset 0 0 0 2px #90caf9; }
56
68
  </style>
69
+ <script src="/window_storage.js"></script>
57
70
  </head>
58
71
  <body class='<%=theme%>'>
72
+ <div id='dragger'></div>
59
73
  <iframe id='row0' data-src="<%=src%>"></iframe>
60
74
  <div id="gutter" class="gutter" tabindex="0" role="separator" aria-orientation="horizontal" aria-label="Resize panels" aria-valuemin="120" aria-valuemax="0" aria-valuenow="0"></div>
61
75
  <iframe id='row1' data-src="<%=src%>"></iframe>
@@ -105,7 +119,7 @@ body.resizing {
105
119
  const total = computeTotal();
106
120
  if (total > 0) {
107
121
  const ratio = clamp(topPx / total, 0, 1);
108
- try { sessionStorage.setItem(splitKey, String(ratio)); } catch (_) {}
122
+ windowStorage.setItem(splitKey, String(ratio));
109
123
  }
110
124
  }
111
125
 
@@ -121,7 +135,7 @@ body.resizing {
121
135
  function restorePaneURL(pane) {
122
136
  const key = urlKeyFor(pane.name);
123
137
  try {
124
- const saved = sessionStorage.getItem(key);
138
+ const saved = windowStorage.getItem(key);
125
139
  const fallback = pane.getAttribute('data-src') || pane.getAttribute('src') || '';
126
140
  const target = (saved && typeof saved === 'string') ? saved : fallback;
127
141
  if (target && pane.src !== target) pane.src = target;
@@ -134,7 +148,7 @@ body.resizing {
134
148
  const cw = pane.contentWindow;
135
149
  if (!cw) return;
136
150
  const notify = () => {
137
- try { sessionStorage.setItem(key, cw.location.href); } catch (_) {}
151
+ windowStorage.setItem(key, cw.location.href);
138
152
  };
139
153
  // Hook SPA navigations
140
154
  const _ps = cw.history.pushState;
@@ -147,7 +161,7 @@ body.resizing {
147
161
  else notify();
148
162
  } catch (err) {
149
163
  // Cross-origin: fall back to saving src only
150
- try { sessionStorage.setItem(key, pane.src); } catch (_) {}
164
+ windowStorage.setItem(key, pane.src);
151
165
  }
152
166
  }
153
167
 
@@ -174,8 +188,9 @@ body.resizing {
174
188
  let overlay = null;
175
189
 
176
190
  function refreshLayout (splitKey) {
177
- let val = sessionStorage.getItem(splitKey)
191
+ let val = windowStorage.getItem(splitKey)
178
192
  let id = splitKey.replace("splitRatio:", "")
193
+ console.log({ id, val })
179
194
  if (val === "1" || val === "0") {
180
195
  if (val === "1") {
181
196
  id_to_hide = id + ".1"
@@ -184,8 +199,24 @@ body.resizing {
184
199
  }
185
200
  const el = document.querySelector(`iframe[name='${id_to_hide}']`)
186
201
  el.remove()
187
- document.body.className = "single"
188
- document.querySelector("#gutter").remove()
202
+ if (document.querySelector("#gutter")) {
203
+ document.querySelector("#gutter").remove()
204
+ }
205
+ let existing_iframe = document.querySelector("iframe")
206
+ if (existing_iframe) {
207
+ debugger
208
+ document.body.className = "single"
209
+ } else {
210
+ if (window.parent) {
211
+ // if all child iframes have been removed, remove self
212
+ window.parent.postMessage({
213
+ e: "close"
214
+ }, "*")
215
+ } else {
216
+ // if this is the top window, everything has been removed, so just redirect to home
217
+ location.href = "/"
218
+ }
219
+ }
189
220
  }
190
221
  }
191
222
 
@@ -267,7 +298,7 @@ body.resizing {
267
298
 
268
299
  // Initialize from saved ratio if available and set ARIA
269
300
  try {
270
- const saved = parseFloat(sessionStorage.getItem(splitKey) || '');
301
+ const saved = parseFloat(windowStorage.getItem(splitKey) || '');
271
302
  console.log({ saved })
272
303
  if (!Number.isNaN(saved) && saved > 0 && saved < 1) {
273
304
  console.log("< 1")
@@ -285,7 +316,7 @@ body.resizing {
285
316
  // Re-apply on window resize to keep ratio
286
317
  window.addEventListener('resize', () => {
287
318
  try {
288
- const saved = parseFloat(sessionStorage.getItem(splitKey) || '');
319
+ const saved = parseFloat(windowStorage.getItem(splitKey) || '');
289
320
  if (!Number.isNaN(saved) && saved > 0 && saved < 1) {
290
321
  applyFromRatio(saved);
291
322
  } else {
@@ -304,11 +335,17 @@ body.resizing {
304
335
 
305
336
  let sourceFrameId = null;
306
337
 
307
- if (event.source === row0.contentWindow) {
338
+ if (row0 && event.source === row0.contentWindow) {
308
339
  sourceFrameId = 'row0';
309
- } else if (event.source === row1.contentWindow) {
340
+ } else if (row1 && event.source === row1.contentWindow) {
310
341
  sourceFrameId = 'row1';
311
342
  }
343
+
344
+ if (!sourceFrameId) {
345
+ windowStorage.removeItem(splitKey)
346
+ location.href = "/"
347
+ return
348
+ }
312
349
 
313
350
  console.log('Message received from iframe:', sourceFrameId);
314
351
 
@@ -317,16 +354,13 @@ body.resizing {
317
354
  console.log({ splitKey })
318
355
  for (let iframe of iframes) {
319
356
  if (event.source === iframe.contentWindow) {
320
- // const splitKey = `splitRatio:${iframe.name}`
321
357
  if (iframe.id === "row0") {
322
358
  // hide row0 => ratio:; 0
323
- // row0.src = "about:blank"
324
- try { sessionStorage.setItem(splitKey, "0"); } catch (_) { console.log("> e", _)}
359
+ windowStorage.setItem(splitKey, "0");
325
360
  refreshLayout(splitKey)
326
361
  } else if (iframe.id === "row1") {
327
362
  // hide row1 => ratio:; 1
328
- // row1.src = "about:blank"
329
- try { sessionStorage.setItem(splitKey, "1"); } catch (_) {console.log(">>> e", _)}
363
+ windowStorage.setItem(splitKey, "1");
330
364
  refreshLayout(splitKey)
331
365
  }
332
366
  console.log('Message from iframe with id:', iframe.id);
@@ -336,6 +370,17 @@ body.resizing {
336
370
  }
337
371
  })
338
372
  })();
373
+ if (document.querySelector("#collapse") && window.windowStorage) {
374
+ document.querySelector("#collapse").addEventListener("click", (e) => {
375
+ document.body.classList.toggle("minimized")
376
+ let frame_key = window.frameElement?.name || "";
377
+ if (document.body.classList.contains("minimized")) {
378
+ windowStorage.setItem(frame_key + ":window_mode", "minimized")
379
+ } else {
380
+ windowStorage.setItem(frame_key + ":window_mode", "full")
381
+ }
382
+ })
383
+ }
339
384
  </script>
340
385
  </body>
341
386
  </html>
@@ -10,6 +10,7 @@
10
10
  <link href="/markdown.css" rel="stylesheet"/>
11
11
  <link href="/noty.css" rel="stylesheet"/>
12
12
  <link href="/style.css" rel="stylesheet"/>
13
+ <link href="/urldropdown.css" rel="stylesheet" />
13
14
  <% if (agent === "electron") { %>
14
15
  <link href="/electron.css" rel="stylesheet"/>
15
16
  <% } %>
@@ -544,12 +545,14 @@ body.dark .gallery-item-timestamp {
544
545
  justify-content: center;
545
546
  }
546
547
 
548
+ /*
547
549
  @media only screen and (max-width: 800px) {
548
550
  body {
549
551
  display: flex !important;
550
552
  flex-direction: row !important;
551
553
  }
552
554
  }
555
+ */
553
556
  @media only screen and (max-width: 768px) {
554
557
  .gallery-grid {
555
558
  grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
@@ -610,6 +613,7 @@ body.dark .gallery-item-timestamp {
610
613
  }
611
614
  }
612
615
  </style>
616
+ <script src="/window_storage.js"></script>
613
617
  <script src="/popper.min.js"></script>
614
618
  <script src="/tippy-bundle.umd.min.js"></script>
615
619
  <script src="/hotkeys.min.js"></script>
@@ -625,6 +629,15 @@ body.dark .gallery-item-timestamp {
625
629
  <script src="/common.js"></script>
626
630
  <script src="/opener.js"></script>
627
631
  <script src="/nav.js"></script>
632
+ <script src="/urldropdown.js"></script>
633
+ <script>
634
+ // Initialize URL Dropdown with empty behavior for screenshots page
635
+ document.addEventListener('DOMContentLoaded', function() {
636
+ initUrlDropdown({
637
+ clearBehavior: 'empty'
638
+ });
639
+ });
640
+ </script>
628
641
  <script src="/report.js"></script>
629
642
  </head>
630
643
  <body class='<%=theme%>' data-agent="<%=agent%>">
@@ -636,11 +649,18 @@ body.dark .gallery-item-timestamp {
636
649
  <header class='navheader grabbable'>
637
650
  <h1>
638
651
  <a class='home' href="/"><img class='icon' src="/pinokio-black.png"></a>
652
+ <button id='collapse' class='btn2' data-tippy-content="toggle fullscreen view"><i class="fa-solid fa-bars"></i></button>
639
653
  <button class='btn2' id='back' data-tippy-content="back"><div><i class="fa-solid fa-chevron-left"></i></div></button>
640
654
  <button class='btn2' id='forward' data-tippy-content="forward"><div><i class="fa-solid fa-chevron-right"></i></div></button>
641
655
  <button class='btn2' id='refresh-page' data-tippy-content="refresh"><div><i class="fa-solid fa-rotate-right"></i></div></button>
642
656
  <button class='btn2' id='screenshot' data-tippy-content="take a screenshot"><i class="fa-solid fa-camera"></i></button>
643
- <form class='urlbar'><input type='url' placeholder='enter a local url'></form>
657
+ <button class='btn2 mobile-link-button' id='mobile-link-button' data-tippy-content="enter url"><i class="fa-solid fa-link"></i></button>
658
+ <form class='urlbar'>
659
+ <div class='url-input-container'>
660
+ <input type='url' placeholder='enter a local url'>
661
+ <div class='url-dropdown' id='url-dropdown'></div>
662
+ </div>
663
+ </form>
644
664
  <a class='btn2' href="/columns" data-tippy-content="split into 2 columns">
645
665
  <div><i class="fa-solid fa-table-columns"></i></div>
646
666
  </a>
@@ -10,6 +10,7 @@
10
10
  <link href="/markdown.css" rel="stylesheet"/>
11
11
  <link href="/noty.css" rel="stylesheet"/>
12
12
  <link href="/style.css" rel="stylesheet"/>
13
+ <link href="/urldropdown.css" rel="stylesheet" />
13
14
  <% if (agent === "electron") { %>
14
15
  <link href="/electron.css" rel="stylesheet"/>
15
16
  <% } %>
@@ -279,12 +280,14 @@ aside .selected {
279
280
  opacity: 1;
280
281
  }
281
282
 
283
+ /*
282
284
  @media only screen and (max-width: 800px) {
283
285
  body {
284
286
  display: flex !important;
285
287
  flex-direction: row !important;
286
288
  }
287
289
  }
290
+ */
288
291
  @media only screen and (max-width: 600px) {
289
292
  aside {
290
293
  width: unset;
@@ -332,6 +335,7 @@ aside .selected {
332
335
  }
333
336
  }
334
337
  </style>
338
+ <script src="/window_storage.js"></script>
335
339
  <script src="/popper.min.js"></script>
336
340
  <script src="/tippy-bundle.umd.min.js"></script>
337
341
  <script src="/hotkeys.min.js"></script>
@@ -347,6 +351,15 @@ aside .selected {
347
351
  <script src="/common.js"></script>
348
352
  <script src="/opener.js"></script>
349
353
  <script src="/nav.js"></script>
354
+ <script src="/urldropdown.js"></script>
355
+ <script>
356
+ // Initialize URL Dropdown with empty behavior for settings page
357
+ document.addEventListener('DOMContentLoaded', function() {
358
+ initUrlDropdown({
359
+ clearBehavior: 'empty'
360
+ });
361
+ });
362
+ </script>
350
363
  <script src="/report.js"></script>
351
364
  </head>
352
365
  <body class='<%=theme%>' data-agent="<%=agent%>">
@@ -358,6 +371,7 @@ aside .selected {
358
371
  <header class='navheader grabbable'>
359
372
  <h1>
360
373
  <a class='home' href="/"><img class='icon' src="/pinokio-black.png"></a>
374
+ <button id='collapse' class='btn2' data-tippy-content="toggle fullscreen view"><i class="fa-solid fa-bars"></i></button>
361
375
  <button class='btn2' id='back' data-tippy-content="back"><div><i class="fa-solid fa-chevron-left"></i></div></button>
362
376
  <button class='btn2' id='forward' data-tippy-content="forward"><div><i class="fa-solid fa-chevron-right"></i></div></button>
363
377
  <button class='btn2' id='refresh-page' data-tippy-content="refresh"><div><i class="fa-solid fa-rotate-right"></i></div></button>
@@ -369,7 +383,13 @@ aside .selected {
369
383
  <% } %>
370
384
  <% }) %>
371
385
  <button class='btn2' id='screenshot' data-tippy-content="take a screenshot"><i class="fa-solid fa-camera"></i></button>
372
- <div class='flexible'></div>
386
+ <button class='btn2 mobile-link-button' id='mobile-link-button' data-tippy-content="enter url"><i class="fa-solid fa-link"></i></button>
387
+ <form class='urlbar'>
388
+ <div class='url-input-container'>
389
+ <input type='url' placeholder='enter a local url'>
390
+ <div class='url-dropdown' id='url-dropdown'></div>
391
+ </div>
392
+ </form>
373
393
  <a class='btn2' href="/columns" data-tippy-content="split into 2 columns">
374
394
  <div><i class="fa-solid fa-table-columns"></i></div>
375
395
  </a>
@@ -711,7 +731,7 @@ document.addEventListener("DOMContentLoaded", async () => {
711
731
  })
712
732
  })
713
733
  }
714
- document.querySelector("form").addEventListener("submit", async (e) => {
734
+ document.querySelector("main form").addEventListener("submit", async (e) => {
715
735
  e.preventDefault()
716
736
  e.stopPropagation()
717
737
  let val = document.querySelector(`[name=home]`).value
@@ -109,12 +109,14 @@ body {
109
109
  .timestamp {
110
110
  color: rgba(0,0,0,0.5);
111
111
  }
112
+ /*
112
113
  @media only screen and (max-width: 800px) {
113
114
  body {
114
115
  display: flex !important;
115
116
  flex-direction: row !important;
116
117
  }
117
118
  }
119
+ */
118
120
  </style>
119
121
  <script src="/hotkeys.min.js"></script>
120
122
  <script src="/sweetalert2.js"></script>
@@ -10,6 +10,7 @@
10
10
  <link href="/markdown.css" rel="stylesheet"/>
11
11
  <link href="/noty.css" rel="stylesheet"/>
12
12
  <link href="/style.css" rel="stylesheet"/>
13
+ <link href="/urldropdown.css" rel="stylesheet" />
13
14
  <% if (agent === "electron") { %>
14
15
  <link href="/electron.css" rel="stylesheet"/>
15
16
  <% } %>
@@ -761,12 +762,14 @@ aside .selected {
761
762
  }
762
763
  }
763
764
 
765
+ /*
764
766
  @media only screen and (max-width: 800px) {
765
767
  body {
766
768
  display: flex !important;
767
769
  flex-direction: row !important;
768
770
  }
769
771
  }
772
+ */
770
773
  @media only screen and (max-width: 600px) {
771
774
  aside {
772
775
  width: unset;
@@ -802,6 +805,7 @@ aside .selected {
802
805
  }
803
806
  }
804
807
  </style>
808
+ <script src="/window_storage.js"></script>
805
809
  <script src="/popper.min.js"></script>
806
810
  <script src="/tippy-bundle.umd.min.js"></script>
807
811
  <script src="/hotkeys.min.js"></script>
@@ -817,6 +821,15 @@ aside .selected {
817
821
  <script src="/common.js"></script>
818
822
  <script src="/opener.js"></script>
819
823
  <script src="/nav.js"></script>
824
+ <script src="/urldropdown.js"></script>
825
+ <script>
826
+ // Initialize URL Dropdown with empty behavior for tools page
827
+ document.addEventListener('DOMContentLoaded', function() {
828
+ initUrlDropdown({
829
+ clearBehavior: 'empty'
830
+ });
831
+ });
832
+ </script>
820
833
  <script src="/report.js"></script>
821
834
  </head>
822
835
  <body class='<%=theme%>' data-agent="<%=agent%>">
@@ -828,11 +841,18 @@ aside .selected {
828
841
  <header class='navheader grabbable'>
829
842
  <h1>
830
843
  <a class='home' href="/"><img class='icon' src="/pinokio-black.png"></a>
844
+ <button id='collapse' class='btn2' data-tippy-content="toggle fullscreen view"><i class="fa-solid fa-bars"></i></button>
831
845
  <button class='btn2' id='back' data-tippy-content="back"><div><i class="fa-solid fa-chevron-left"></i></div></button>
832
846
  <button class='btn2' id='forward' data-tippy-content="forward"><div><i class="fa-solid fa-chevron-right"></i></div></button>
833
847
  <button class='btn2' id='refresh-page' data-tippy-content="refresh"><div><i class="fa-solid fa-rotate-right"></i></div></button>
834
848
  <button class='btn2' id='screenshot' data-tippy-content="take a screenshot"><i class="fa-solid fa-camera"></i></button>
835
- <form class='urlbar'><input type='url' placeholder='enter a local url'></form>
849
+ <button class='btn2 mobile-link-button' id='mobile-link-button' data-tippy-content="enter url"><i class="fa-solid fa-link"></i></button>
850
+ <form class='urlbar'>
851
+ <div class='url-input-container'>
852
+ <input type='url' placeholder='enter a local url'>
853
+ <div class='url-dropdown' id='url-dropdown'></div>
854
+ </div>
855
+ </form>
836
856
  <a class='btn2' href="/columns" data-tippy-content="split into 2 columns">
837
857
  <div><i class="fa-solid fa-table-columns"></i></div>
838
858
  </a>