目的
perplexity.aiの検索はかなり使えるのだけど、例えばpdfとしてメールしたい場合、検索窓やフッターが各ページについてしまう。なんとかしたい。
code
tampermonkey.script
// ==UserScript==
// @name Custom Menu and PDF Link
// @namespace http://tampermonkey.net/
// @version 0.1
// @description Adds a PDF link to the menu and empties elements when clicked
// @match https://www.perplexity.ai/search/*
// @grant none
// @require https://code.jquery.com/jquery-3.6.0.min.js
// ==/UserScript==
(function() {
'use strict';
// Wait for the menu element to be available in the DOM
var checkMenu = setInterval(function() {
var menu = document.querySelector('div.items-center.relative.space-y-xs.w-full');
if (menu) {
clearInterval(checkMenu);
addPDFLink(menu);
}
}, 100);
function addPDFLink(menu) {
// Create the PDF link element
var pdfLink = document.createElement('div');
pdfLink.innerHTML = `
<div class="relative gap-x-sm w-full px-two justify-center border-borderMain/50 ring-borderMain/50 divide-borderMain/50 dark:divide-borderMainDark/50 dark:ring-borderMainDark/50 dark:border-borderMainDark/50 bg-transparent">
<div class="px-xs overflow-hidden transition duration-300 relative">
<a id="pdfLink" class="md:hover:bg-offsetPlus text-textOff dark:text-textOffDark md:hover:text-textMain dark:md:hover:bg-offsetPlusDark dark:md:hover:text-textMainDark py-md font-sans focus:outline-none outline-none outline-transparent transition duration-300 ease-in-out font-sans select-none items-center relative group/button justify-start rounded cursor-point active:scale-95 origin-center whitespace-nowrap flex w-full text-base px-md font-medium h-10" href="#" style="-webkit-tap-highlight-color: transparent;">
<div class="flex items-center leading-none justify-left w-full gap-xs">
<svg aria-hidden="true" focusable="false" data-prefix="far" data-icon="file-pdf" class="svg-inline--fa fa-file-pdf fa-fw fa-1x" role="img" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 384 512">
<path fill="currentColor" d="M369.9 97.9L286 14C277 5 264.8-.1 252.1-.1H48C21.5 0 0 21.5 0 48v416c0 26.5 21.5 48 48 48h288c26.5 0 48-21.5 48-48V131.9c0-12.7-5.1-25-14.1-34zM262.2 90.2c-1.3-1.3-2.6-2.5-4-3.5 -4.1-2.3-8.2-3.1-12.1-3.1H128c-8.8 0-16 7.2-16 16v154.4c0 3.4.8 6.5 2.4 9.2 1.6 2.7 4.1 4.6 6.7 5.9 5.5 2.9 12 2.9 17.5 0 2.6-1.3 5.1-3.2 6.7-5.9 1.6-2.7 2.4-5.8 2.4-9.2V128h96v64c0 8.8 7.2 16 16 16h16c8.8 0 16-7.2 16-16v-64c0-8.8-7.2-16-16-16h-16.8c-12.2 0-22.1 9.5-23.4 21.4zM384 448c0 17.6-14.4 32-32 32H48c-17.6 0-32-14.4-32-32V48c0-17.6 14.4-32 32-32h176v104c0 13.3 10.7 24 24 24h104v304z"></path>
</svg>
<div class="text-align-center relative">PDF</div>
</div>
</a>
</div>
</div>
`;
// Insert the PDF link as the third item in the menu
menu.insertBefore(pdfLink, menu.children[2]);
// Add click event listener to the PDF link
document.getElementById('pdfLink').addEventListener('click', function(e) {
e.preventDefault();
$(document).ready(function() {
$("div.fixed.bottom-0").empty();
$("span.grow.block").empty();
});
});
}
})();
解説(DBRX-instructに作ってもらって、DeepL翻訳)
-
(function() { ... })();
- これは即時呼び出し関数式(IIFE)です。これは関数を定義してすぐに呼び出すものです。これはコードをカプセル化し、グローバルスコープに影響を与えないようにするために使われます。 -
use strict';
- コードをストリクトモードにするディレクティブです。ストリクトモードは、より多くの例外を投げたり、非ストリクトモードでは許可されている特定の動作を禁止したりすることで、「安全な」JavaScriptを書きやすくします。 -
var checkMenu = setInterval(function() { ... }, 100);
- この行はcheckMenu
という変数を作成し、その変数にsetInterval
関数の値を代入します。setInterval
関数は2つの引数を取る。繰り返し実行する関数と、各実行の間に待つミリ秒数である。この場合、関数はメニュー要素がDOMで利用可能かどうかをチェックし、利用可能であればインターバルをクリアしてaddPDFLink
関数を呼び出します。間隔は100ミリ秒に設定されている。 -
function addPDFLink(menu) { ... }
- この行はaddPDFLink
という関数を定義しています。この関数は新しいdiv
要素を作成し、そのinnerHTML
プロパティにPDFリンクのHTMLコードを設定します。そして、PDFリンクをメニューの3番目の項目として挿入します。 -
document.getElementById('pdfLink').addEventListener('click', function(e) { .... });
- この行は、PDFリンクにクリックイベントリスナーを追加します。リンクがクリックされると、この関数はデフォルトの動作(リンクのhref
属性に移動する)を阻止し、div.fixed.bottom-0
とspan.grow.block
要素を空にします。 -
$(document).ready(function() { ... });
- この行はjQuery関数で、関数内のコードを実行する前にDOMが完全にロードされるのを待ちます。この場合、div.fixed.bottom-0
とspan.grow.block
要素を空にしています。
課題
- いったん作ったページを再度読み込まないとうまく動かない。キャッシュの影響かもしれない。
-
.empty()
にしているので不可逆。エレメントを不可視にするだけでいいかも
まとめ
生成AIに投げて、SVG画像が作ってもらって開発者ツールで無理やりはめて、はまったのを見えてからは早かった。
DBRXも結構使える。片言英語でなんとかなったし。