antigravity-rtl-patcher 3.0.2 → 3.0.3

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": "antigravity-rtl-patcher",
3
- "version": "3.0.2",
3
+ "version": "3.0.3",
4
4
  "description": "Advanced RTL and Persian/Arabic typography patcher for Antigravity with customizable UI",
5
5
  "main": "src/patcher.js",
6
6
  "bin": {
@@ -13,9 +13,7 @@ win.webContents.on('console-message', (event, ...args) => {
13
13
  const configData = message.substring(16);
14
14
  const configPath = require('path').join(require('os').homedir(), '.antigravity-rtl.json');
15
15
  require('fs').writeFileSync(configPath, configData, 'utf8');
16
- } catch (err) {
17
- console.error('[RTL] Config save failed:', err);
18
- }
16
+ } catch (err) {}
19
17
  }
20
18
  });
21
19
 
@@ -38,52 +36,199 @@ win.webContents.on('dom-ready', () => {
38
36
  window.__RTL_LOADED__ = true;
39
37
 
40
38
  let rtlEnabled = ${rtlConfig.enabled};
39
+ let panelVisible = false;
41
40
 
42
41
  const CSS = \`
43
- p, h1, h2, h3, h4, h5, h6, ul, ol, li, div, span {
44
- unicode-bidi: plaintext;
45
- text-align: start;
42
+ /* RTL Styles */
43
+ body.rtl-active p,
44
+ body.rtl-active h1, body.rtl-active h2, body.rtl-active h3,
45
+ body.rtl-active h4, body.rtl-active h5, body.rtl-active h6,
46
+ body.rtl-active ul, body.rtl-active ol, body.rtl-active li,
47
+ body.rtl-active div:not(#rtl-panel):not(.rtl-ui),
48
+ body.rtl-active span:not(.rtl-ui) {
49
+ direction: rtl !important;
50
+ text-align: right !important;
51
+ unicode-bidi: plaintext !important;
46
52
  }
47
53
 
48
- [dir="rtl"] ul, [dir="rtl"] ol {
54
+ body.rtl-active [dir="rtl"] ul,
55
+ body.rtl-active [dir="rtl"] ol {
49
56
  padding-left: 0 !important;
50
57
  padding-right: 1.5rem !important;
51
58
  }
52
59
 
53
- pre, code, pre *, code * {
54
- unicode-bidi: isolate !important;
60
+ body.rtl-active pre,
61
+ body.rtl-active code,
62
+ body.rtl-active pre *,
63
+ body.rtl-active code * {
55
64
  direction: ltr !important;
56
65
  text-align: left !important;
66
+ unicode-bidi: isolate !important;
57
67
  }
58
68
 
59
- #rtl-toggle-btn {
69
+ /* Panel Container */
70
+ #rtl-trigger {
60
71
  position: fixed;
61
72
  bottom: 20px;
62
73
  right: 20px;
63
- z-index: 999999;
74
+ z-index: 999998;
64
75
  width: 50px;
65
76
  height: 50px;
66
77
  border-radius: 50%;
67
- background: rgba(60, 60, 60, 0.9);
68
- border: 2px solid rgba(100, 100, 100, 0.5);
78
+ background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
79
+ border: none;
69
80
  color: white;
70
81
  cursor: pointer;
71
82
  display: flex;
72
83
  align-items: center;
73
84
  justify-content: center;
74
85
  font-size: 24px;
75
- transition: all 0.3s;
76
- box-shadow: 0 2px 10px rgba(0,0,0,0.3);
86
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
87
+ box-shadow: 0 4px 12px rgba(102, 126, 234, 0.4);
88
+ }
89
+
90
+ #rtl-trigger:hover {
91
+ transform: scale(1.1) rotate(180deg);
92
+ box-shadow: 0 6px 20px rgba(102, 126, 234, 0.6);
93
+ }
94
+
95
+ #rtl-trigger.active {
96
+ background: linear-gradient(135deg, #f093fb 0%, #f5576c 100%);
97
+ box-shadow: 0 4px 12px rgba(245, 87, 108, 0.4);
98
+ }
99
+
100
+ #rtl-panel {
101
+ position: fixed;
102
+ bottom: 80px;
103
+ right: 20px;
104
+ z-index: 999999;
105
+ width: 300px;
106
+ background: rgba(255, 255, 255, 0.95);
107
+ backdrop-filter: blur(10px);
108
+ border-radius: 16px;
109
+ box-shadow: 0 8px 32px rgba(0, 0, 0, 0.2);
110
+ opacity: 0;
111
+ transform: translateY(20px) scale(0.9);
112
+ pointer-events: none;
113
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
114
+ overflow: hidden;
115
+ }
116
+
117
+ #rtl-panel.visible {
118
+ opacity: 1;
119
+ transform: translateY(0) scale(1);
120
+ pointer-events: auto;
121
+ }
122
+
123
+ @media (prefers-color-scheme: dark) {
124
+ #rtl-panel {
125
+ background: rgba(30, 30, 40, 0.95);
126
+ color: #e0e0e0;
127
+ }
128
+ }
129
+
130
+ .rtl-panel-header {
131
+ padding: 20px;
132
+ background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
133
+ color: white;
134
+ text-align: center;
135
+ font-weight: 600;
136
+ font-size: 16px;
137
+ }
138
+
139
+ .rtl-panel-body {
140
+ padding: 24px;
141
+ }
142
+
143
+ .rtl-row {
144
+ display: flex;
145
+ align-items: center;
146
+ justify-content: space-between;
147
+ margin-bottom: 16px;
148
+ }
149
+
150
+ .rtl-label {
151
+ font-size: 14px;
152
+ font-weight: 500;
153
+ color: #333;
154
+ }
155
+
156
+ @media (prefers-color-scheme: dark) {
157
+ .rtl-label {
158
+ color: #e0e0e0;
159
+ }
160
+ }
161
+
162
+ /* Toggle Switch */
163
+ .rtl-switch {
164
+ position: relative;
165
+ width: 52px;
166
+ height: 28px;
167
+ background: #ddd;
168
+ border-radius: 14px;
169
+ cursor: pointer;
170
+ transition: background 0.3s;
171
+ }
172
+
173
+ .rtl-switch.active {
174
+ background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
175
+ }
176
+
177
+ .rtl-switch::after {
178
+ content: '';
179
+ position: absolute;
180
+ width: 22px;
181
+ height: 22px;
182
+ background: white;
183
+ border-radius: 50%;
184
+ top: 3px;
185
+ left: 3px;
186
+ transition: transform 0.3s;
187
+ box-shadow: 0 2px 4px rgba(0, 0, 0, 0.2);
188
+ }
189
+
190
+ .rtl-switch.active::after {
191
+ transform: translateX(24px);
192
+ }
193
+
194
+ .rtl-panel-footer {
195
+ padding: 16px 24px;
196
+ border-top: 1px solid rgba(0, 0, 0, 0.1);
197
+ display: flex;
198
+ justify-content: center;
199
+ }
200
+
201
+ @media (prefers-color-scheme: dark) {
202
+ .rtl-panel-footer {
203
+ border-top: 1px solid rgba(255, 255, 255, 0.1);
204
+ }
77
205
  }
78
206
 
79
- #rtl-toggle-btn:hover {
80
- background: rgba(80, 80, 80, 0.95);
81
- transform: scale(1.1);
207
+ .rtl-github-btn {
208
+ display: flex;
209
+ align-items: center;
210
+ gap: 8px;
211
+ padding: 10px 20px;
212
+ background: #24292e;
213
+ color: white;
214
+ border: none;
215
+ border-radius: 8px;
216
+ cursor: pointer;
217
+ font-size: 13px;
218
+ font-weight: 500;
219
+ text-decoration: none;
220
+ transition: all 0.2s;
221
+ }
222
+
223
+ .rtl-github-btn:hover {
224
+ background: #1a1f23;
225
+ transform: translateY(-2px);
226
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.2);
82
227
  }
83
228
 
84
- #rtl-toggle-btn.active {
85
- background: rgba(70, 130, 180, 0.9);
86
- border-color: rgba(70, 130, 180, 0.8);
229
+ .rtl-github-icon {
230
+ width: 18px;
231
+ height: 18px;
87
232
  }
88
233
  \`;
89
234
 
@@ -92,96 +237,81 @@ win.webContents.on('dom-ready', () => {
92
237
  styleEl.textContent = CSS;
93
238
  document.head.appendChild(styleEl);
94
239
 
95
- function detectRTL(text) {
96
- if (!text || text.trim().length === 0) return false;
97
- const cleaned = text.replace(/[\\u200B-\\u200F\\uFEFF]/g, '').trim();
98
- if (cleaned.length === 0) return false;
99
-
100
- const firstChar = cleaned.match(/[A-Za-z\\u0600-\\u06FF\\u0750-\\u077F\\u08A0-\\u08FF\\uFB50-\\uFDFF\\uFE70-\\uFEFF]/);
101
- if (!firstChar) return false;
102
-
103
- return /[\\u0600-\\u06FF\\u0750-\\u077F\\u08A0-\\u08FF\\uFB50-\\uFDFF\\uFE70-\\uFEFF]/.test(firstChar[0]);
240
+ // Apply RTL class if enabled
241
+ if (rtlEnabled) {
242
+ document.body.classList.add('rtl-active');
104
243
  }
105
244
 
106
- function updateDirections() {
107
- if (!rtlEnabled) return;
108
-
109
- document.querySelectorAll('[contenteditable="true"], [contenteditable="true"] p, textarea').forEach(el => {
110
- const text = el.tagName === 'TEXTAREA' ? el.value : el.textContent;
111
- const cleaned = text.replace(/[\\u200B-\\u200F\\uFEFF]/g, '').trim();
112
-
113
- if (cleaned.length > 0) {
114
- const dir = detectRTL(cleaned) ? 'rtl' : 'ltr';
115
- if (el.getAttribute('dir') !== dir) {
116
- el.setAttribute('dir', dir);
117
- }
118
- } else {
119
- if (el.hasAttribute('dir')) el.removeAttribute('dir');
120
- }
121
- });
122
-
123
- document.querySelectorAll('.prose > *, [data-testid="chat-message"] > *, .markdown-body > *, .leading-relaxed > *').forEach(el => {
124
- if (el.tagName === 'PRE' || el.tagName === 'CODE') return;
125
-
126
- const text = el.textContent.replace(/[\\u200B-\\u200F\\uFEFF]/g, '').trim();
127
- if (text) {
128
- const dir = detectRTL(text) ? 'rtl' : 'ltr';
129
- if (el.getAttribute('dir') !== dir) {
130
- el.setAttribute('dir', dir);
131
- }
132
- }
133
- });
134
- }
245
+ // Create UI
246
+ const trigger = document.createElement('button');
247
+ trigger.id = 'rtl-trigger';
248
+ trigger.className = rtlEnabled ? 'active rtl-ui' : 'rtl-ui';
249
+ trigger.innerHTML = '';
250
+ trigger.title = 'RTL Settings';
135
251
 
136
- document.body.addEventListener('input', updateDirections, { capture: true });
137
- const observer = new MutationObserver(updateDirections);
138
- observer.observe(document.body, { childList: true, subtree: true });
139
- setInterval(updateDirections, 500);
252
+ const panel = document.createElement('div');
253
+ panel.id = 'rtl-panel';
254
+ panel.className = 'rtl-ui';
255
+ panel.innerHTML = \`
256
+ <div class="rtl-panel-header rtl-ui">
257
+ Antigravity Smart RTL
258
+ </div>
259
+ <div class="rtl-panel-body rtl-ui">
260
+ <div class="rtl-row rtl-ui">
261
+ <span class="rtl-label rtl-ui">RTL Mode</span>
262
+ <div class="rtl-switch \${rtlEnabled ? 'active' : ''} rtl-ui" id="rtl-toggle"></div>
263
+ </div>
264
+ </div>
265
+ <div class="rtl-panel-footer rtl-ui">
266
+ <a href="https://github.com/VaFa1726/antigravity-rtl-patcher" target="_blank" class="rtl-github-btn rtl-ui">
267
+ <svg class="rtl-github-icon rtl-ui" viewBox="0 0 16 16" fill="currentColor">
268
+ <path d="M8 0C3.58 0 0 3.58 0 8c0 3.54 2.29 6.53 5.47 7.59.4.07.55-.17.55-.38 0-.19-.01-.82-.01-1.49-2.01.37-2.53-.49-2.69-.94-.09-.23-.48-.94-.82-1.13-.28-.15-.68-.52-.01-.53.63-.01 1.08.58 1.23.82.72 1.21 1.87.87 2.33.66.07-.52.28-.87.51-1.07-1.78-.2-3.64-.89-3.64-3.95 0-.87.31-1.59.82-2.15-.08-.2-.36-1.02.08-2.12 0 0 .67-.21 2.2.82.64-.18 1.32-.27 2-.27.68 0 1.36.09 2 .27 1.53-1.04 2.2-.82 2.2-.82.44 1.1.16 1.92.08 2.12.51.56.82 1.27.82 2.15 0 3.07-1.87 3.75-3.65 3.95.29.25.54.73.54 1.48 0 1.07-.01 1.93-.01 2.2 0 .21.15.46.55.38A8.013 8.013 0 0016 8c0-4.42-3.58-8-8-8z"/>
269
+ </svg>
270
+ Star on GitHub
271
+ </a>
272
+ </div>
273
+ \`;
140
274
 
141
- document.addEventListener('keydown', (e) => {
142
- if (e.altKey && e.code === 'KeyR') {
143
- e.preventDefault();
144
- toggleRTL();
145
- }
146
- }, { capture: true });
275
+ document.body.appendChild(trigger);
276
+ document.body.appendChild(panel);
147
277
 
148
- const btn = document.createElement('button');
149
- btn.id = 'rtl-toggle-btn';
150
- btn.className = rtlEnabled ? 'active' : '';
151
- btn.innerHTML = '⇄';
152
- btn.title = 'Toggle RTL (Alt+R)';
278
+ // Event handlers
279
+ trigger.addEventListener('click', (e) => {
280
+ e.stopPropagation();
281
+ panelVisible = !panelVisible;
282
+ panel.classList.toggle('visible', panelVisible);
283
+ });
153
284
 
154
- btn.addEventListener('click', toggleRTL);
285
+ document.addEventListener('click', (e) => {
286
+ if (!e.target.classList.contains('rtl-ui')) {
287
+ panelVisible = false;
288
+ panel.classList.remove('visible');
289
+ }
290
+ });
155
291
 
156
- function toggleRTL() {
292
+ document.getElementById('rtl-toggle').addEventListener('click', () => {
157
293
  rtlEnabled = !rtlEnabled;
158
294
 
295
+ const toggle = document.getElementById('rtl-toggle');
296
+ toggle.classList.toggle('active', rtlEnabled);
297
+ trigger.classList.toggle('active', rtlEnabled);
298
+
159
299
  if (rtlEnabled) {
160
- btn.classList.add('active');
161
- if (!document.getElementById('rtl-main-style')) {
162
- document.head.appendChild(styleEl);
163
- }
164
- updateDirections();
300
+ document.body.classList.add('rtl-active');
165
301
  } else {
166
- btn.classList.remove('active');
167
- if (styleEl.parentNode) {
168
- styleEl.parentNode.removeChild(styleEl);
169
- }
170
- document.querySelectorAll('[dir]').forEach(el => {
171
- if (!el.closest('#rtl-toggle-btn')) {
172
- el.removeAttribute('dir');
173
- }
174
- });
302
+ document.body.classList.remove('rtl-active');
175
303
  }
176
304
 
177
305
  console.log('RTL_CONFIG_SAVE:' + JSON.stringify({ enabled: rtlEnabled }));
178
- }
179
-
180
- document.body.appendChild(btn);
306
+ });
181
307
 
182
- if (rtlEnabled) {
183
- updateDirections();
184
- }
308
+ // Keyboard shortcut
309
+ document.addEventListener('keydown', (e) => {
310
+ if (e.altKey && e.code === 'KeyR') {
311
+ e.preventDefault();
312
+ document.getElementById('rtl-toggle').click();
313
+ }
314
+ });
185
315
  })();
186
316
  `).catch(err => console.error('[RTL] Injection failed:', err));
187
317