npm-noxyai 1.0.8 ā 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/index-noxyai.js +184 -108
- package/index.html +27 -0
- package/package.json +11 -2
- package/reinstall_pip.py +1 -0
- package/script.js +38 -0
- package/server.js +11 -0
- package/snake_game.py +90 -0
- package/style.css +11 -0
- package/tic_tac_toe_local.py +46 -0
package/index-noxyai.js
CHANGED
|
@@ -3,15 +3,31 @@
|
|
|
3
3
|
const fs = require('fs');
|
|
4
4
|
const os = require('os');
|
|
5
5
|
const path = require('path');
|
|
6
|
-
const { spawn } = require('child_process');
|
|
6
|
+
const { spawn } = require('child_process');
|
|
7
7
|
const readline = require('readline');
|
|
8
8
|
|
|
9
9
|
const BASE_URL = 'https://www.noxyai.com';
|
|
10
10
|
const CONFIG_FILE = path.join(os.homedir(), '.noxyai.json');
|
|
11
11
|
|
|
12
|
+
const GOOGLE_KEY = "AIzaSyAXoZgwIaEnXfO3JuKIvR8GzhydqRKPh20";
|
|
13
|
+
const GOOGLE_CX = "33d4204810fae4852";
|
|
14
|
+
|
|
12
15
|
const args = process.argv.slice(2);
|
|
13
16
|
const command = args[0];
|
|
14
17
|
|
|
18
|
+
// --- CONFIG MANAGEMENT ---
|
|
19
|
+
function loadConfig() {
|
|
20
|
+
if (fs.existsSync(CONFIG_FILE)) {
|
|
21
|
+
try { return JSON.parse(fs.readFileSync(CONFIG_FILE, 'utf8')); } catch(e){}
|
|
22
|
+
}
|
|
23
|
+
return { token: null, model: 'auto' };
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
function saveConfig(config) {
|
|
27
|
+
fs.writeFileSync(CONFIG_FILE, JSON.stringify(config, null, 2));
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
// --- UI HELPERS ---
|
|
15
31
|
function printLogo() {
|
|
16
32
|
console.log('\x1b[36m' + `
|
|
17
33
|
āāāā āāā āāāāāāā āāā āāāāāā āāā āāāāāā āāā
|
|
@@ -23,41 +39,38 @@ function printLogo() {
|
|
|
23
39
|
` + '\x1b[0m');
|
|
24
40
|
}
|
|
25
41
|
|
|
26
|
-
|
|
27
|
-
|
|
42
|
+
let spinnerInterval;
|
|
43
|
+
function startSpinner(text) {
|
|
44
|
+
const frames = ['ā ', 'ā ', 'ā ¹', 'ā ø', 'ā ¼', 'ā “', 'ā ¦', 'ā §', 'ā ', 'ā '];
|
|
45
|
+
let i = 0;
|
|
46
|
+
process.stdout.write('\x1b[?25l'); // Hide cursor
|
|
47
|
+
spinnerInterval = setInterval(() => {
|
|
48
|
+
process.stdout.write(`\r\x1b[36m${frames[i]} ${text}\x1b[0m`);
|
|
49
|
+
i = (i + 1) % frames.length;
|
|
50
|
+
}, 80);
|
|
28
51
|
}
|
|
29
52
|
|
|
30
|
-
function
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
return config.token;
|
|
34
|
-
}
|
|
35
|
-
return null;
|
|
53
|
+
function stopSpinner() {
|
|
54
|
+
clearInterval(spinnerInterval);
|
|
55
|
+
process.stdout.write('\r\x1b[K\x1b[?25h'); // Clear line, show cursor
|
|
36
56
|
}
|
|
37
57
|
|
|
38
58
|
function logout() {
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
console.log('You are already logged out.');
|
|
44
|
-
}
|
|
45
|
-
process.exit(0);
|
|
59
|
+
const config = loadConfig();
|
|
60
|
+
config.token = null;
|
|
61
|
+
saveConfig(config);
|
|
62
|
+
console.log('ā
Successfully logged out.');
|
|
46
63
|
}
|
|
47
64
|
|
|
48
65
|
function openBrowser(url) {
|
|
49
66
|
const platform = os.platform();
|
|
50
|
-
if (platform === 'android') {
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
} else if (platform === 'win32') {
|
|
55
|
-
spawn('cmd.exe', ['/c', 'start', '""', url], { stdio: 'ignore' });
|
|
56
|
-
} else {
|
|
57
|
-
spawn('xdg-open', [url], { stdio: 'ignore' });
|
|
58
|
-
}
|
|
67
|
+
if (platform === 'android') spawn('termux-open-url', [url], { stdio: 'ignore' });
|
|
68
|
+
else if (platform === 'darwin') spawn('open', [url], { stdio: 'ignore' });
|
|
69
|
+
else if (platform === 'win32') spawn('cmd.exe', ['/c', 'start', '""', url], { stdio: 'ignore' });
|
|
70
|
+
else spawn('xdg-open', [url], { stdio: 'ignore' });
|
|
59
71
|
}
|
|
60
72
|
|
|
73
|
+
// --- CORE FUNCTIONS ---
|
|
61
74
|
async function login() {
|
|
62
75
|
printLogo();
|
|
63
76
|
console.log('Initializing secure login...\n');
|
|
@@ -73,7 +86,7 @@ async function login() {
|
|
|
73
86
|
rl.question('Press ENTER to automatically open the browser...', () => {
|
|
74
87
|
openBrowser(verificationUrl);
|
|
75
88
|
rl.close();
|
|
76
|
-
|
|
89
|
+
startSpinner('Waiting for authentication...');
|
|
77
90
|
});
|
|
78
91
|
|
|
79
92
|
const pollInterval = setInterval(async () => {
|
|
@@ -88,15 +101,19 @@ async function login() {
|
|
|
88
101
|
|
|
89
102
|
if (data.status === 'success') {
|
|
90
103
|
clearInterval(pollInterval);
|
|
91
|
-
|
|
104
|
+
stopSpinner();
|
|
105
|
+
const config = loadConfig();
|
|
106
|
+
config.token = data.token;
|
|
107
|
+
saveConfig(config);
|
|
92
108
|
|
|
93
109
|
console.clear();
|
|
94
110
|
printLogo();
|
|
95
111
|
console.log('ā
Login successful! Terminal connected.');
|
|
96
|
-
console.log('Type "noxyai
|
|
112
|
+
console.log('Type "noxyai" to start interactive mode.\n');
|
|
97
113
|
process.exit(0);
|
|
98
114
|
} else if (data.error) {
|
|
99
115
|
clearInterval(pollInterval);
|
|
116
|
+
stopSpinner();
|
|
100
117
|
console.error('\nā Login failed: ' + data.error);
|
|
101
118
|
process.exit(1);
|
|
102
119
|
}
|
|
@@ -108,57 +125,55 @@ async function login() {
|
|
|
108
125
|
}
|
|
109
126
|
}
|
|
110
127
|
|
|
111
|
-
// šØ THE FIX: Upgraded to spawn with interactive stdio
|
|
112
128
|
function runTerminalCommand(cmd) {
|
|
113
129
|
return new Promise((resolve, reject) => {
|
|
114
130
|
console.log(`\n\x1b[33mā” Running:\x1b[0m ${cmd}\n`);
|
|
115
|
-
|
|
116
|
-
const child = spawn(cmd, {
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
131
|
+
const isServer = cmd.includes('dev') || cmd.includes('serve') || cmd.includes('host') || cmd.includes('start');
|
|
132
|
+
const child = spawn(cmd, { shell: true, stdio: 'inherit' });
|
|
133
|
+
|
|
134
|
+
if (isServer) {
|
|
135
|
+
console.log(`\x1b[36m[i] Server detected. Running in foreground. Press Ctrl+C to stop.\x1b[0m`);
|
|
136
|
+
setTimeout(() => resolve(), 2500);
|
|
137
|
+
}
|
|
120
138
|
|
|
121
139
|
child.on('close', (code) => {
|
|
122
|
-
if (
|
|
123
|
-
|
|
140
|
+
if (!isServer) {
|
|
141
|
+
if (code !== 0) reject(`Command failed with exit code ${code}`);
|
|
142
|
+
else resolve();
|
|
143
|
+
}
|
|
124
144
|
});
|
|
125
|
-
|
|
126
145
|
child.on('error', (error) => reject(error.message));
|
|
127
146
|
});
|
|
128
147
|
}
|
|
129
148
|
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
149
|
+
function getLocalContext() {
|
|
150
|
+
try {
|
|
151
|
+
const files = fs.readdirSync(process.cwd()).filter(f => !f.startsWith('node_modules') && !f.startsWith('.git')).slice(0, 30);
|
|
152
|
+
return `\n[SYSTEM: You are in ${process.cwd()}. Files here: ${files.join(', ')}]\n`;
|
|
153
|
+
} catch (e) { return ""; }
|
|
154
|
+
}
|
|
136
155
|
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
}
|
|
156
|
+
async function chat(prompt, depth = 0) {
|
|
157
|
+
const config = loadConfig();
|
|
158
|
+
if (!config.token) { console.error('ā Unauthorized: Run "noxyai login"'); return; }
|
|
159
|
+
if (depth > 6) { console.error('\nā Reached max reasoning depth. Stopping.'); return; }
|
|
141
160
|
|
|
142
|
-
const
|
|
161
|
+
const enhancedPrompt = depth === 0 ? getLocalContext() + prompt : prompt;
|
|
162
|
+
|
|
163
|
+
startSpinner(depth === 0 ? 'NoxyAI is thinking...' : 'NoxyAI is analyzing results...');
|
|
143
164
|
|
|
144
165
|
try {
|
|
145
166
|
const res = await fetch(BASE_URL + '/api/io', {
|
|
146
167
|
method: 'POST',
|
|
147
|
-
headers: {
|
|
148
|
-
|
|
149
|
-
'Authorization': 'Bearer ' + token
|
|
150
|
-
},
|
|
151
|
-
body: JSON.stringify({ prompt, model })
|
|
168
|
+
headers: { 'Content-Type': 'application/json', 'Authorization': 'Bearer ' + config.token },
|
|
169
|
+
body: JSON.stringify({ prompt: enhancedPrompt, model: config.model })
|
|
152
170
|
});
|
|
153
171
|
|
|
154
|
-
|
|
155
|
-
const errorText = await res.text();
|
|
156
|
-
console.error('\nā API Error: ' + errorText);
|
|
157
|
-
process.exit(1);
|
|
158
|
-
}
|
|
172
|
+
stopSpinner();
|
|
159
173
|
|
|
160
|
-
if (
|
|
161
|
-
|
|
174
|
+
if (!res.ok) return console.error('\nā API Error: ' + await res.text());
|
|
175
|
+
|
|
176
|
+
console.log(`\nš¤ \x1b[36mNoxyAI (${config.model}):\x1b[0m\n`);
|
|
162
177
|
|
|
163
178
|
const reader = res.body.getReader();
|
|
164
179
|
const decoder = new TextDecoder('utf-8');
|
|
@@ -167,10 +182,7 @@ async function chat(prompt, depth = 0) {
|
|
|
167
182
|
while (true) {
|
|
168
183
|
const { done, value } = await reader.read();
|
|
169
184
|
if (done) break;
|
|
170
|
-
|
|
171
|
-
const chunk = decoder.decode(value, { stream: true });
|
|
172
|
-
const lines = chunk.split('\n');
|
|
173
|
-
|
|
185
|
+
const lines = decoder.decode(value, { stream: true }).split('\n');
|
|
174
186
|
for (const line of lines) {
|
|
175
187
|
if (line.startsWith('data: ')) {
|
|
176
188
|
const data = line.slice(6).trim();
|
|
@@ -186,73 +198,137 @@ async function chat(prompt, depth = 0) {
|
|
|
186
198
|
}
|
|
187
199
|
}
|
|
188
200
|
|
|
189
|
-
console.log('\n\n\x1b[32m[Agent]
|
|
201
|
+
console.log('\n\n\x1b[32m[Agent] Processing actions...\x1b[0m');
|
|
202
|
+
let agentFeedback = "";
|
|
190
203
|
|
|
191
|
-
|
|
204
|
+
// Tool: Read Files
|
|
205
|
+
const readRegex = /<read>([\s\S]*?)<\/read>/g;
|
|
192
206
|
let match;
|
|
207
|
+
while ((match = readRegex.exec(fullResponse)) !== null) {
|
|
208
|
+
const filePath = match[1].trim();
|
|
209
|
+
try {
|
|
210
|
+
const content = fs.readFileSync(filePath, 'utf8');
|
|
211
|
+
console.log(`\x1b[34mš Read file:\x1b[0m ${filePath}`);
|
|
212
|
+
agentFeedback += `\n[FILE: ${filePath}]\n\`\`\`\n${content}\n\`\`\`\n`;
|
|
213
|
+
} catch (err) {
|
|
214
|
+
console.log(`\x1b[31mā Failed to read:\x1b[0m ${filePath}`);
|
|
215
|
+
agentFeedback += `\n[ERROR reading ${filePath}: ${err.message}]\n`;
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
// Tool: Search Web
|
|
220
|
+
const searchRegex = /<search>([\s\S]*?)<\/search>/g;
|
|
221
|
+
while ((match = searchRegex.exec(fullResponse)) !== null) {
|
|
222
|
+
const query = match[1].trim();
|
|
223
|
+
console.log(`\x1b[35mš Searching Web:\x1b[0m ${query}`);
|
|
224
|
+
try {
|
|
225
|
+
const searchRes = await fetch(`https://www.googleapis.com/customsearch/v1?key=${GOOGLE_KEY}&cx=${GOOGLE_CX}&q=${encodeURIComponent(query)}`);
|
|
226
|
+
const searchData = await searchRes.json();
|
|
227
|
+
const snippets = searchData.items ? searchData.items.map(i => `- ${i.title}: ${i.snippet}`).join('\n') : "No results.";
|
|
228
|
+
agentFeedback += `\n[SEARCH RESULTS FOR "${query}"]\n${snippets}\n`;
|
|
229
|
+
} catch (err) {
|
|
230
|
+
agentFeedback += `\n[SEARCH FAILED: ${err.message}]\n`;
|
|
231
|
+
}
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
// Tool: Write Files
|
|
235
|
+
const fileRegex = /<file path="([^"]+)">([\s\S]*?)<\/file>/g;
|
|
193
236
|
while ((match = fileRegex.exec(fullResponse)) !== null) {
|
|
194
|
-
const filePath = match[1];
|
|
195
|
-
const content = match[2];
|
|
196
|
-
|
|
237
|
+
const filePath = match[1], content = match[2];
|
|
197
238
|
const dir = path.dirname(filePath);
|
|
198
239
|
if (!fs.existsSync(dir)) fs.mkdirSync(dir, { recursive: true });
|
|
199
240
|
fs.writeFileSync(filePath, content.trim());
|
|
200
|
-
console.log(`\x1b[32mā
|
|
241
|
+
console.log(`\x1b[32mā Wrote file:\x1b[0m ${filePath}`);
|
|
201
242
|
}
|
|
202
243
|
|
|
244
|
+
// Tool: Execute Commands
|
|
203
245
|
const execRegex = /<execute>([\s\S]*?)<\/execute>/g;
|
|
204
246
|
const commands = [];
|
|
205
|
-
while ((match = execRegex.exec(fullResponse)) !== null)
|
|
206
|
-
|
|
207
|
-
}
|
|
208
|
-
|
|
247
|
+
while ((match = execRegex.exec(fullResponse)) !== null) commands.push(match[1].trim());
|
|
248
|
+
|
|
209
249
|
for (const cmd of commands) {
|
|
210
250
|
try {
|
|
211
251
|
await runTerminalCommand(cmd);
|
|
212
252
|
} catch (err) {
|
|
213
|
-
console.
|
|
214
|
-
|
|
215
|
-
const errorPrompt = `I ran the command "${cmd}" and got this error:\n\n${err}\n\nPlease fix the issue. Use <file> tags to rewrite files or <execute> to run commands.`;
|
|
216
|
-
await chat(errorPrompt, depth + 1);
|
|
217
|
-
return;
|
|
253
|
+
console.log(`\x1b[31mā Command Failed:\x1b[0m ${err}`);
|
|
254
|
+
agentFeedback += `\n[COMMAND ERROR running "${cmd}": ${err}]\n`;
|
|
218
255
|
}
|
|
219
256
|
}
|
|
220
|
-
process.exit(0);
|
|
221
257
|
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
258
|
+
if (agentFeedback) {
|
|
259
|
+
console.log(`\x1b[33mš Sending data back to Agent...\x1b[0m`);
|
|
260
|
+
await chat(`Here are the results of your actions:\n${agentFeedback}\nWhat is the next step? Output <file> or <execute> if ready, or <read>/<search> if you need more info.`, depth + 1);
|
|
261
|
+
return;
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
console.log('\n\x1b[32māāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā\x1b[0m');
|
|
265
|
+
console.log(`\x1b[32m⨠Task Completed!\x1b[0m`);
|
|
266
|
+
console.log('\x1b[32māāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāāā\x1b[0m\n');
|
|
267
|
+
|
|
268
|
+
} catch (error) {
|
|
269
|
+
stopSpinner();
|
|
270
|
+
console.error('\nā Connection error: ' + error.message);
|
|
225
271
|
}
|
|
226
272
|
}
|
|
227
273
|
|
|
228
|
-
function
|
|
274
|
+
function startInteractiveMode() {
|
|
275
|
+
const config = loadConfig();
|
|
276
|
+
const rl = readline.createInterface({ input: process.stdin, output: process.stdout });
|
|
229
277
|
printLogo();
|
|
230
|
-
console.log(`
|
|
231
|
-
\x1b[
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
278
|
+
console.log(`\x1b[33mWelcome to NoxyAI Interactive Mode!\x1b[0m`);
|
|
279
|
+
console.log(`Current Model: \x1b[32m${config.model}\x1b[0m`);
|
|
280
|
+
console.log(`Commands: \x1b[36m/model\x1b[0m (Change Model), \x1b[36m/clear\x1b[0m, \x1b[36m/exit\x1b[0m\n`);
|
|
281
|
+
|
|
282
|
+
function ask() {
|
|
283
|
+
rl.question('\x1b[36mNoxyAI > \x1b[0m', async (input) => {
|
|
284
|
+
const trimmed = input.trim();
|
|
285
|
+
const lower = trimmed.toLowerCase();
|
|
286
|
+
|
|
287
|
+
if (lower === 'exit' || lower === '/exit') {
|
|
288
|
+
process.exit(0);
|
|
289
|
+
}
|
|
290
|
+
else if (lower === '/clear') {
|
|
291
|
+
console.clear();
|
|
292
|
+
printLogo();
|
|
293
|
+
ask();
|
|
294
|
+
}
|
|
295
|
+
else if (lower === '/model') {
|
|
296
|
+
console.log('\n\x1b[33mSelect an AI Model:\x1b[0m');
|
|
297
|
+
console.log(' \x1b[36m1)\x1b[0m Auto (Llama 3.3 70B - Fast/Coding)');
|
|
298
|
+
console.log(' \x1b[36m2)\x1b[0m Qwen3 Next 80B Thinking (Deep Reasoning)');
|
|
299
|
+
console.log(' \x1b[36m3)\x1b[0m GLM 4.7');
|
|
300
|
+
|
|
301
|
+
rl.question('\nEnter number (1-3): ', (choice) => {
|
|
302
|
+
let selected = 'auto';
|
|
303
|
+
if (choice === '2') selected = 'Qwen3';
|
|
304
|
+
if (choice === '3') selected = 'GLM';
|
|
305
|
+
|
|
306
|
+
const currentConfig = loadConfig();
|
|
307
|
+
currentConfig.model = selected;
|
|
308
|
+
saveConfig(currentConfig);
|
|
309
|
+
|
|
310
|
+
console.log(`\n\x1b[32mā Model successfully changed to: ${selected}\x1b[0m\n`);
|
|
311
|
+
ask();
|
|
312
|
+
});
|
|
313
|
+
return; // Pause the main loop while waiting for model choice
|
|
314
|
+
}
|
|
315
|
+
else if (trimmed) {
|
|
316
|
+
await chat(trimmed);
|
|
317
|
+
ask();
|
|
318
|
+
} else {
|
|
319
|
+
ask();
|
|
320
|
+
}
|
|
321
|
+
});
|
|
322
|
+
}
|
|
323
|
+
ask();
|
|
243
324
|
}
|
|
244
325
|
|
|
245
326
|
if (command === 'login') login();
|
|
246
327
|
else if (command === 'logout') logout();
|
|
247
|
-
else if (command === 'help' || command === '--help'
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
if (!prompt) {
|
|
251
|
-
console.error('ā Please provide a prompt. Example: noxyai chat "Create a python script"');
|
|
252
|
-
process.exit(1);
|
|
253
|
-
}
|
|
254
|
-
chat(prompt);
|
|
255
|
-
} else {
|
|
256
|
-
console.error(`ā Unknown command: ${command}`);
|
|
257
|
-
console.log('Run "noxyai help" for a list of commands.');
|
|
328
|
+
else if (command === 'help' || command === '--help') {
|
|
329
|
+
printLogo();
|
|
330
|
+
console.log(`\n \x1b[32mnoxyai\x1b[0m Start Interactive Mode\n \x1b[32mnoxyai chat "<prompt>"\x1b[0m Run single prompt\n`);
|
|
258
331
|
}
|
|
332
|
+
else if (command === 'chat') { chat(args.slice(1).join(' ')).then(() => process.exit(0)); }
|
|
333
|
+
else if (!command) startInteractiveMode();
|
|
334
|
+
else { console.error(`ā Unknown command. Run "noxyai help"`); process.exit(1); }
|
package/index.html
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
<html>
|
|
2
|
+
<head>
|
|
3
|
+
<title>Tic Tac Toe</title>
|
|
4
|
+
<link rel="stylesheet" href="style.css">
|
|
5
|
+
</head>
|
|
6
|
+
<body>
|
|
7
|
+
<h1>Tic Tac Toe</h1>
|
|
8
|
+
<div class="game-board">
|
|
9
|
+
<div class="row">
|
|
10
|
+
<div class="cell" id="cell-0"></div>
|
|
11
|
+
<div class="cell" id="cell-1"></div>
|
|
12
|
+
<div class="cell" id="cell-2"></div>
|
|
13
|
+
</div>
|
|
14
|
+
<div class="row">
|
|
15
|
+
<div class="cell" id="cell-3"></div>
|
|
16
|
+
<div class="cell" id="cell-4"></div>
|
|
17
|
+
<div class="cell" id="cell-5"></div>
|
|
18
|
+
</div>
|
|
19
|
+
<div class="row">
|
|
20
|
+
<div class="cell" id="cell-6"></div>
|
|
21
|
+
<div class="cell" id="cell-7"></div>
|
|
22
|
+
<div class="cell" id="cell-8"></div>
|
|
23
|
+
</div>
|
|
24
|
+
</div>
|
|
25
|
+
<script src="script.js"></script>
|
|
26
|
+
</body>
|
|
27
|
+
</html>
|
package/package.json
CHANGED
|
@@ -1,11 +1,20 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "npm-noxyai",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.10",
|
|
4
4
|
"description": "CLI for NoxyAI",
|
|
5
5
|
"main": "index-noxyai.js",
|
|
6
6
|
"bin": {
|
|
7
7
|
"noxyai": "index-noxyai.js"
|
|
8
8
|
},
|
|
9
9
|
"author": "Mohammad Junaid Rather",
|
|
10
|
-
"license": "ISC"
|
|
10
|
+
"license": "ISC",
|
|
11
|
+
"scripts": {
|
|
12
|
+
"test": "echo \"Error: no test specified\" && exit 1",
|
|
13
|
+
"start": "node server.js"
|
|
14
|
+
},
|
|
15
|
+
"keywords": [],
|
|
16
|
+
"type": "commonjs",
|
|
17
|
+
"dependencies": {
|
|
18
|
+
"express": "^5.2.1"
|
|
19
|
+
}
|
|
11
20
|
}
|
package/reinstall_pip.py
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import pip; pip.uninstall('pip'); import os; os.system('python -m ensurepip')
|
package/script.js
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
let currentPlayer = "X";
|
|
2
|
+
let gameBoard = ["", "", "", "", "", "", "", "", ""];
|
|
3
|
+
|
|
4
|
+
function clickCell(cellId) {
|
|
5
|
+
if (gameBoard[cellId] === "") {
|
|
6
|
+
gameBoard[cellId] = currentPlayer;
|
|
7
|
+
document.getElementById(`cell-${cellId}`).innerText = currentPlayer;
|
|
8
|
+
checkWin();
|
|
9
|
+
currentPlayer = currentPlayer === "X" ? "O" : "X";
|
|
10
|
+
}
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
function checkWin() {
|
|
14
|
+
const winConditions = [
|
|
15
|
+
[0, 1, 2],
|
|
16
|
+
[3, 4, 5],
|
|
17
|
+
[6, 7, 8],
|
|
18
|
+
[0, 3, 6],
|
|
19
|
+
[1, 4, 7],
|
|
20
|
+
[2, 5, 8],
|
|
21
|
+
[0, 4, 8],
|
|
22
|
+
[2, 4, 6]
|
|
23
|
+
];
|
|
24
|
+
|
|
25
|
+
for (let i = 0; i < winConditions.length; i++) {
|
|
26
|
+
const [a, b, c] = winConditions[i];
|
|
27
|
+
if (gameBoard[a] !== "" && gameBoard[a] === gameBoard[b] && gameBoard[b] === gameBoard[c]) {
|
|
28
|
+
alert(`Player ${gameBoard[a]} wins!`);
|
|
29
|
+
return;
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
document.addEventListener("DOMContentLoaded", () => {
|
|
35
|
+
for (let i = 0; i < 9; i++) {
|
|
36
|
+
document.getElementById(`cell-${i}`).addEventListener("click", () => clickCell(i));
|
|
37
|
+
}
|
|
38
|
+
});
|
package/server.js
ADDED
package/snake_game.py
ADDED
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import pygame
|
|
2
|
+
import sys
|
|
3
|
+
import time
|
|
4
|
+
import random
|
|
5
|
+
|
|
6
|
+
# Direction Constants
|
|
7
|
+
UP = 1
|
|
8
|
+
RIGHT = 2
|
|
9
|
+
DOWN = 3
|
|
10
|
+
LEFT = 4
|
|
11
|
+
|
|
12
|
+
class SnakeGame:
|
|
13
|
+
def __init__(self, width=800, height=600):
|
|
14
|
+
self.width = width
|
|
15
|
+
self.height = height
|
|
16
|
+
self.snake = [(200, 200), (220, 200), (240, 200)]
|
|
17
|
+
self.direction = RIGHT
|
|
18
|
+
self.apple = self.set_new_apple()
|
|
19
|
+
self.score = 0
|
|
20
|
+
pygame.init()
|
|
21
|
+
self.display = pygame.display.set_mode((width, height))
|
|
22
|
+
self.font = pygame.font.Font(None, 36)
|
|
23
|
+
|
|
24
|
+
def set_new_apple(self):
|
|
25
|
+
while True:
|
|
26
|
+
x = random.randint(0, self.width - 20) // 20 * 20
|
|
27
|
+
y = random.randint(0, self.height - 20) // 20 * 20
|
|
28
|
+
apple = (x, y)
|
|
29
|
+
if apple not in self.snake:
|
|
30
|
+
return apple
|
|
31
|
+
|
|
32
|
+
def play(self):
|
|
33
|
+
clock = pygame.time.Clock()
|
|
34
|
+
while True:
|
|
35
|
+
for event in pygame.event.get():
|
|
36
|
+
if event.type == pygame.QUIT:
|
|
37
|
+
pygame.quit()
|
|
38
|
+
sys.exit()
|
|
39
|
+
elif event.type == pygame.KEYDOWN:
|
|
40
|
+
if event.key == pygame.K_UP and self.direction != DOWN:
|
|
41
|
+
self.direction = UP
|
|
42
|
+
elif event.key == pygame.K_DOWN and self.direction != UP:
|
|
43
|
+
self.direction = DOWN
|
|
44
|
+
elif event.key == pygame.K_LEFT and self.direction != RIGHT:
|
|
45
|
+
self.direction = LEFT
|
|
46
|
+
elif event.key == pygame.K_RIGHT and self.direction != LEFT:
|
|
47
|
+
self.direction = RIGHT
|
|
48
|
+
|
|
49
|
+
head = self.snake[-1]
|
|
50
|
+
if self.direction == UP:
|
|
51
|
+
new_head = (head[0], head[1] - 20)
|
|
52
|
+
elif self.direction == DOWN:
|
|
53
|
+
new_head = (head[0], head[1] + 20)
|
|
54
|
+
elif self.direction == LEFT:
|
|
55
|
+
new_head = (head[0] - 20, head[1])
|
|
56
|
+
elif self.direction == RIGHT:
|
|
57
|
+
new_head = (head[0] + 20, head[1])
|
|
58
|
+
|
|
59
|
+
self.snake.append(new_head)
|
|
60
|
+
if self.apple == new_head:
|
|
61
|
+
self.apple = self.set_new_apple()
|
|
62
|
+
self.score += 1
|
|
63
|
+
else:
|
|
64
|
+
self.snake.pop(0)
|
|
65
|
+
|
|
66
|
+
if (new_head[0] < 0 or new_head[0] >= self.width or
|
|
67
|
+
new_head[1] < 0 or new_head[1] >= self.height or
|
|
68
|
+
new_head in self.snake[:-1]):
|
|
69
|
+
break
|
|
70
|
+
|
|
71
|
+
self.display.fill((0, 0, 0))
|
|
72
|
+
for pos in self.snake:
|
|
73
|
+
pygame.draw.rect(self.display, (0, 255, 0), (pos[0], pos[1], 20, 20))
|
|
74
|
+
pygame.draw.rect(self.display, (255, 0, 0), (self.apple[0], self.apple[1], 20, 20))
|
|
75
|
+
text = self.font.render(f'Score: {self.score}', True, (255, 255, 255))
|
|
76
|
+
self.display.blit(text, (10, 10))
|
|
77
|
+
pygame.display.flip()
|
|
78
|
+
clock.tick(10)
|
|
79
|
+
|
|
80
|
+
time.sleep(1)
|
|
81
|
+
self.display.fill((0, 0, 0))
|
|
82
|
+
text = self.font.render('Game Over', True, (255, 255, 255))
|
|
83
|
+
self.display.blit(text, (self.width // 2 - 50, self.height // 2 - 18))
|
|
84
|
+
pygame.display.flip()
|
|
85
|
+
time.sleep(2)
|
|
86
|
+
pygame.quit()
|
|
87
|
+
|
|
88
|
+
if __name__ == '__main__':
|
|
89
|
+
game = SnakeGame()
|
|
90
|
+
game.play()
|
package/style.css
ADDED
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import tkinter as tk
|
|
2
|
+
from tkinter import messagebox
|
|
3
|
+
|
|
4
|
+
class TicTacToe:
|
|
5
|
+
def __init__(self):
|
|
6
|
+
self.window = tk.Tk()
|
|
7
|
+
self.window.title("Tic Tac Toe")
|
|
8
|
+
self.window.geometry("300x300")
|
|
9
|
+
self.player_turn = "X"
|
|
10
|
+
|
|
11
|
+
self.buttons = []
|
|
12
|
+
for i in range(3):
|
|
13
|
+
row = []
|
|
14
|
+
for j in range(3):
|
|
15
|
+
button = tk.Button(self.window, command=lambda row=i, column=j: self.click(row, column), height=3, width=6)
|
|
16
|
+
button.grid(row=i, column=j)
|
|
17
|
+
row.append(button)
|
|
18
|
+
self.buttons.append(row)
|
|
19
|
+
|
|
20
|
+
def click(self, row, column):
|
|
21
|
+
if self.buttons[row][column]['text'] == "":
|
|
22
|
+
self.buttons[row][column]['text'] = self.player_turn
|
|
23
|
+
if self.check_win():
|
|
24
|
+
messagebox.showinfo("Game Over", f"Player {self.player_turn} wins!")
|
|
25
|
+
self.window.quit()
|
|
26
|
+
self.player_turn = "O" if self.player_turn == "X" else "X"
|
|
27
|
+
|
|
28
|
+
def check_win(self):
|
|
29
|
+
for row in self.buttons:
|
|
30
|
+
if row[0]['text'] == row[1]['text'] == row[2]['text'] != "":
|
|
31
|
+
return True
|
|
32
|
+
for column in range(3):
|
|
33
|
+
if self.buttons[0][column]['text'] == self.buttons[1][column]['text'] == self.buttons[2][column]['text'] != "":
|
|
34
|
+
return True
|
|
35
|
+
if self.buttons[0][0]['text'] == self.buttons[1][1]['text'] == self.buttons[2][2]['text'] != "":
|
|
36
|
+
return True
|
|
37
|
+
if self.buttons[0][2]['text'] == self.buttons[1][1]['text'] == self.buttons[2][0]['text'] != "":
|
|
38
|
+
return True
|
|
39
|
+
return False
|
|
40
|
+
|
|
41
|
+
def run(self):
|
|
42
|
+
self.window.mainloop()
|
|
43
|
+
|
|
44
|
+
if __name__ == "__main__":
|
|
45
|
+
game = TicTacToe()
|
|
46
|
+
game.run()
|