-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcontent.js
More file actions
243 lines (207 loc) · 11.4 KB
/
content.js
File metadata and controls
243 lines (207 loc) · 11.4 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
/**
* GitHub Clone with VS Code Extension
* Adds an "Open with VS Code" button to GitHub repositories in the tab navigation
*/
(function() {
'use strict';
// VS Code icon from Codeberg
const vscodeIconSvg = `<svg viewBox="-1 -1 34 34" aria-hidden="true" width="16" height="16" style="vertical-align: middle; margin-right: 4px;">
<path d="M30.9 3.4 24.3.3a2 2 0 0 0-2.3.4L9.4 12.2 3.9 8c-.5-.4-1.2-.4-1.7 0L.4 9.8c-.5.5-.5 1.4 0 2L5.2 16 .4 20.3c-.5.6-.5 1.5 0 2L2.2 24c.5.5 1.2.5 1.7 0l5.5-4L22 31.2a2 2 0 0 0 2.3.4l6.6-3.2a2 2 0 0 0 1.1-1.8V5.2a2 2 0 0 0-1.1-1.8M24 23.3 14.4 16 24 8.7z" fill="#007ACC"></path>
</svg>`;
// Continuously check for the tab navigation to appear
function waitForCodeDropdown() {
const observer = new MutationObserver((mutations, observer) => {
checkAndAddTabButton();
});
// Observe DOM changes to catch when the elements appear
observer.observe(document.body, {
childList: true,
subtree: true
});
// Also check immediately in case it's already there
checkAndAddTabButton();
// Periodically check for the elements as a fallback
setInterval(() => {
checkAndAddTabButton();
}, 1000);
// Add click listener to the Code button
document.addEventListener('click', (event) => {
// Wait a short time to let the dropdown render
setTimeout(() => {
checkAndAddTabButton();
}, 100);
});
}
// The dropdown button functionality has been removed as requested
// Helper function to get the repository URL
function getRepositoryUrl() {
// Try to get URL from the clone button data - multiple selector attempts for different GitHub UI versions
// First try the new GitHub UI selectors
const clipboardElement = document.querySelector('input[data-autoselect="true"][value], input#clone-with-gh-cli[value]');
if (clipboardElement && clipboardElement.value) {
const clipValue = clipboardElement.value;
// If it's a gh CLI command, extract the repo URL
if (clipValue.startsWith('gh repo clone ')) {
const repoPath = clipValue.replace('gh repo clone ', '');
return `https://github.com/${repoPath}.git`;
}
return clipValue;
}
// Try old UI selectors
const urlElement = document.querySelector('clipboard-copy[value], input[name="cli-clone-url"]');
if (urlElement && urlElement.value) {
return urlElement.value;
}
// Fallback: construct from location
const match = window.location.pathname.match(/\/([^\/]+)\/([^\/]+)/);
if (match) {
const [, owner, repo] = match;
return `https://github.com/${owner}/${repo}.git`;
}
return null;
}
// Add button to the tab navigation (HTTPS/SSH/GitHub CLI row)
function checkAndAddTabButton() {
// Look for the tab navigation - try multiple selectors for different GitHub UI versions
const possibleTabNavs = [
document.querySelector('div[role="tablist"]'),
document.querySelector('.TabNav__TabNavTabList-sc-pwdi4r-1'),
document.querySelector('nav.TabNav'),
document.querySelector('nav[aria-label="Remote URL selector"]')
].filter(Boolean);
// Process each possible tab navigation area
for (const tabNav of possibleTabNavs) {
if (tabNav && !document.querySelector('.vscode-tab-button')) {
console.log('GitHub Clone with VS Code: Found tab navigation', tabNav);
// Get repository URL
const repoUrl = getRepositoryUrl();
if (!repoUrl) {
console.log('GitHub Clone with VS Code: Could not find repository URL for tab button');
continue;
}
// Create VS Code clone URL
const vsCodeUrl = `vscode://vscode.git/clone?url=${encodeURIComponent(repoUrl)}`;
// Find the GitHub CLI button or SSH button to get its styling and position
const tabButtons = Array.from(tabNav.querySelectorAll('button, a, li'));
const referenceButton = tabButtons.find(el =>
el.textContent.trim().includes('GitHub CLI') ||
el.textContent.trim().includes('SSH'));
if (referenceButton) {
console.log('GitHub Clone with VS Code: Found reference button', referenceButton);
// Determine if we're working with the new GitHub UI
const isNewUI = referenceButton.className.includes('prc-') ||
tabNav.className.includes('prc-');
// Create a button of the same type as the reference button
const vsCodeTabButton = document.createElement(referenceButton.tagName);
if (referenceButton.tagName.toLowerCase() === 'button') {
vsCodeTabButton.type = 'button';
vsCodeTabButton.role = 'tab';
vsCodeTabButton.setAttribute('aria-selected', 'false');
vsCodeTabButton.setAttribute('tabindex', '-1');
} else if (referenceButton.tagName.toLowerCase() === 'a') {
vsCodeTabButton.href = '#';
vsCodeTabButton.setAttribute('role', 'tab');
vsCodeTabButton.setAttribute('aria-selected', 'false');
} else if (referenceButton.tagName.toLowerCase() === 'li') {
// For list item, we'll need to create an anchor inside
const anchor = document.createElement('a');
anchor.href = '#';
anchor.className = Array.from(referenceButton.querySelector('a')?.classList || []).join(' ');
vsCodeTabButton.appendChild(anchor);
}
// Apply common classes but add our own identifier
vsCodeTabButton.className = referenceButton.className + ' vscode-tab-button';
// Apply VS Code styling - make it stand out with the VS Code blue
vsCodeTabButton.style.color = '#007ACC';
// Get the right structure based on the UI version
if (isNewUI) {
// Structure for new GitHub UI
if (referenceButton.tagName.toLowerCase() === 'li') {
// If it's a list item, modify the anchor inside
vsCodeTabButton.querySelector('a').innerHTML = `
<span data-component="text" data-content="VS Code">
${vscodeIconSvg} VS Code
</span>
`;
} else {
// For button or direct anchor
vsCodeTabButton.innerHTML = `
<span data-component="buttonContent" data-align="center" class="prc-Button-ButtonContent-HKbr-">
${vscodeIconSvg}
<span data-component="text" class="prc-Button-Label-pTQ3x">VS Code</span>
</span>
`;
}
} else {
// Simpler fallback structure for older GitHub UI
if (referenceButton.tagName.toLowerCase() === 'li') {
vsCodeTabButton.querySelector('a').innerHTML = `${vscodeIconSvg} VS Code`;
} else {
vsCodeTabButton.innerHTML = `${vscodeIconSvg} VS Code`;
}
}
// Add styling including wireframe border
const styleTag = document.createElement('style');
styleTag.textContent = `
.vscode-tab-button {
border: 1px solid #007ACC !important;
border-radius: 10px !important;
margin: 0 2px !important;
padding: 4px 8px !important;
}
.vscode-tab-button[aria-selected="true"] {
border-bottom-color: #007ACC !important;
color: #007ACC !important;
background-color: rgba(0, 122, 204, 0.1) !important;
}
`;
document.head.appendChild(styleTag);
// Insert after the reference button
referenceButton.parentNode.insertBefore(vsCodeTabButton, referenceButton.nextSibling);
// Add click handler to open VS Code
const clickHandler = (e) => {
e.preventDefault();
e.stopPropagation();
// Set this button as selected visually
tabButtons.forEach(btn => {
btn.setAttribute('aria-selected', 'false');
if (btn.classList.contains('selected')) {
btn.classList.remove('selected');
}
});
vsCodeTabButton.setAttribute('aria-selected', 'true');
if (!vsCodeTabButton.classList.contains('selected')) {
vsCodeTabButton.classList.add('selected');
}
// Open VS Code after a small delay to allow visual feedback
setTimeout(() => {
window.location.href = vsCodeUrl;
}, 100);
};
if (referenceButton.tagName.toLowerCase() === 'li') {
vsCodeTabButton.querySelector('a').addEventListener('click', clickHandler);
} else {
vsCodeTabButton.addEventListener('click', clickHandler);
}
console.log('GitHub Clone with VS Code: Added tab button', vsCodeTabButton);
}
}
}
}
// Start observing for tab navigation
waitForCodeDropdown();
// Also add listener for navigation changes (for GitHub's SPA behavior)
window.addEventListener('popstate', () => {
setTimeout(() => {
checkAndAddTabButton();
}, 500);
});
// For navigation within GitHub that doesn't trigger popstate
const pushState = history.pushState;
history.pushState = function() {
pushState.apply(history, arguments);
setTimeout(() => {
checkAndAddTabButton();
}, 500);
};
})();