scrapped html package and js, now using web

This commit is contained in:
Juan Marulanda De Los Rios 2025-05-14 21:52:21 -04:00
parent 7a1e735f11
commit 9fff611ac0
3 changed files with 167 additions and 145 deletions

View File

@ -12,8 +12,10 @@ import 'package:http/http.dart' as http;
import 'dart:convert';
import 'dart:ui_web' as ui;
import 'augment.dart';
import 'dart:html' as html;
import 'dart:js' as js;
// import 'dart:html' as html;
// import 'dart:js' as js;
import 'package:web/web.dart' as web;
import 'dart:js_interop' as js;
class ApiService {
static String ip = "";
@ -343,76 +345,77 @@ class ApiService {
return AttachmentResponse(name: "error", data: Uint8List(0));
}
Future<List<Map<String, dynamic>>> getMarkerPosition() async {
//this is so we can put a widget right below each email, but the way how the email content is generated
//leads to problems as for a) the html is added one right after the other in one iframe, b)
// if it was multiple iframes then the scrolling to jump would not work as expected
//TODO: MOVE THIS INTO WEB
// Future<List<Map<String, dynamic>>> getMarkerPosition() async {
// //this is so we can put a widget right below each email, but the way how the email content is generated
// //leads to problems as for a) the html is added one right after the other in one iframe, b)
// // if it was multiple iframes then the scrolling to jump would not work as expected
print("marker called");
// JavaScript code embedded as a string
String jsCode = '''
(async function waitForIframeAndMarkers() {
try {
return await new Promise((resolve) => {
const interval = setInterval(() => {
console.log("⏳ Checking for iframe...");
var iframe = document.getElementsByTagName('iframe')[0];
if (iframe && iframe.contentDocument) {
console.log("✅ Iframe found!");
var iframeDoc = iframe.contentDocument || iframe.contentWindow.document;
var markers = iframeDoc.querySelectorAll('[id^="JuanBedarramarker"]');
if (markers.length > 0) {
console.log(` Found markers in the iframe.`);
var positions = [];
markers.forEach((marker) => {
var rect = marker.getBoundingClientRect();
positions.push({
id: marker.id,
x: rect.left + window.scrollX,
y: rect.top + window.scrollY,
});
});
console.log("📌 Marker positions:", positions);
clearInterval(interval);
resolve(JSON.stringify(positions)); // Ensure proper JSON string
} else {
console.log("❌ No markers found yet.");
}
} else {
console.log("❌ Iframe not found or not loaded yet.");
}
}, 200);
});
} catch (error) {
console.error("JS Error:", error);
throw error; // Propagate error to Dart
}
})();
''';
// print("marker called");
// // JavaScript code embedded as a string
// String jsCode = '''
// (async function waitForIframeAndMarkers() {
// try {
// return await new Promise((resolve) => {
// const interval = setInterval(() => {
// console.log("⏳ Checking for iframe...");
// var iframe = document.getElementsByTagName('iframe')[0];
// if (iframe && iframe.contentDocument) {
// console.log("✅ Iframe found!");
// var iframeDoc = iframe.contentDocument || iframe.contentWindow.document;
// var markers = iframeDoc.querySelectorAll('[id^="JuanBedarramarker"]');
// if (markers.length > 0) {
// console.log(` Found markers in the iframe.`);
// var positions = [];
// markers.forEach((marker) => {
// var rect = marker.getBoundingClientRect();
// positions.push({
// id: marker.id,
// x: rect.left + window.scrollX,
// y: rect.top + window.scrollY,
// });
// });
// console.log("📌 Marker positions:", positions);
// clearInterval(interval);
// resolve(JSON.stringify(positions)); // Ensure proper JSON string
// } else {
// console.log("❌ No markers found yet.");
// }
// } else {
// console.log("❌ Iframe not found or not loaded yet.");
// }
// }, 200);
// });
// } catch (error) {
// console.error("JS Error:", error);
// throw error; // Propagate error to Dart
// }
// })();
// ''';
try {
// Execute the JavaScript code using eval
final result = await js.context.callMethod('eval', [jsCode]);
// try {
// // Execute the JavaScript code using eval
// // final result = await js.context.callMethod('eval', [jsCode]);
if (result != null && result is String) {
print("Result received: $result");
// if (result != null && result is String) {
// print("Result received: $result");
// Parse the JSON string returned by JavaScript into a Dart list of maps
final List<dynamic> parsedResult = jsonDecode(result);
var positions = List<Map<String, dynamic>>.from(parsedResult);
print("positions put on");
print(positions);
return positions;
} else {
print("result is null or not a string");
}
} catch (e, stackTrace) {
print("Error executing JavaScript: $e");
print(stackTrace);
}
// // Parse the JSON string returned by JavaScript into a Dart list of maps
// final List<dynamic> parsedResult = jsonDecode(result);
// var positions = List<Map<String, dynamic>>.from(parsedResult);
// print("positions put on");
// print(positions);
// return positions;
// } else {
// print("result is null or not a string");
// }
// } catch (e, stackTrace) {
// print("Error executing JavaScript: $e");
// print(stackTrace);
// }
return [];
}
// return [];
// }
}
class EmailView extends StatefulWidget {
@ -455,10 +458,12 @@ class _EmailViewState extends State<EmailView> {
@override
void initState() {
super.initState();
String currentContent = widget.emailContent;
String currentContent = widget
.emailContent; //html of the email/ actually entire thread, gives me little space to play in between
// i wonder if the other attributes change? because if so i have to add like some zooms in and out of the emails, as in collapse
viewTypeId = "iframe-${DateTime.now().millisecondsSinceEpoch}";
_registerViewFactory(currentContent);
_markerPositionsFuture = ApiService().getMarkerPosition();
// _markerPositionsFuture = ApiService().getMarkerPosition();
}
void _registerViewFactory(String currentContent) {
@ -466,11 +471,20 @@ class _EmailViewState extends State<EmailView> {
viewTypeId = 'iframe-${DateTime.now().millisecondsSinceEpoch}';
ui.platformViewRegistry.registerViewFactory(
viewTypeId,
(int viewId) => html.IFrameElement()
..width = '100%'
..height = '100%'
..srcdoc = currentContent
..style.border = 'none');
(int viewId) => web.HTMLDivElement()
..id = 'new-web'
..innerHTML = currentContent as js.JSAny);
// DivElement div = HTMLDivElement()
// ..id =
// ui.platformViewRegistry.registerViewFactory(
// viewTypeId,
// (int viewId) => html.IFrameElement()
// ..width = '100%'
// ..height = '100%'
// ..srcdoc = currentContent
// ..style.border = 'none');
});
}
@ -502,7 +516,7 @@ class _EmailViewState extends State<EmailView> {
// <h1>Welcome to My Website</h1>
// <p>This is a simple HTML page.</p>
// <h2>What is HTML?</h2>
// <p>HTML (HyperText Markup Language) is the most basic building block of the Web. It defines the meaning and structure of web content. Other technologies besides HTML are generally used to describe a web page's appearance/presentation (CSS) or functionality/behavior (JavaScript).</p>
// <p>HTML (HyperText Markup Language) is the most basic building~ block of the Web. It defines the meaning and structure of web content. Other technologies besides HTML are generally used to describe a web page's appearance/presentation (CSS) or functionality/behavior (JavaScript).</p>
// <h3>Here's a simple list:</h3>
// <ul>
// <li>HTML elements are the building blocks of HTML pages</li>
@ -562,48 +576,48 @@ class _EmailViewState extends State<EmailView> {
),
// Overlay widgets dynamically based on marker positions
FutureBuilder<List<Map<String, dynamic>>>(
future: _markerPositionsFuture,
builder: (context, snapshot) {
print("FutureBuilder state: ${snapshot.connectionState}");
if (snapshot.connectionState == ConnectionState.waiting) {
return Center(child: CircularProgressIndicator());
}
if (snapshot.hasError) {
print("Error in FutureBuilder: ${snapshot.error}");
return Center(child: Text('error loading markers'));
}
if (snapshot.hasData && snapshot.data != null) {
final markers = snapshot.data!;
return Stack(
children: markers.map((marker) {
return Positioned(
left: marker['x'].toDouble(),
top: marker['y'].toDouble(),
child: GestureDetector(
onTap: () {
print('Tapped on ${marker['id']}');
},
child: Container(
width: 50,
height: 50,
color: Colors.red,
child: Center(
child: Text(
marker['id'],
style: TextStyle(color: Colors.white),
),
),
),
),
);
}).toList(),
);
}
// FutureBuilder<List<Map<String, dynamic>>>(
// future: _markerPositionsFuture,
// builder: (context, snapshot) {
// print("FutureBuilder state: ${snapshot.connectionState}");
// if (snapshot.connectionState == ConnectionState.waiting) {
// return Center(child: CircularProgressIndicator());
// }
// if (snapshot.hasError) {
// print("Error in FutureBuilder: ${snapshot.error}");
// return Center(child: Text('error loading markers'));
// }
// if (snapshot.hasData && snapshot.data != null) {
// final markers = snapshot.data!;
// return Stack(
// children: markers.map((marker) {
// return Positioned(
// left: marker['x'].toDouble(),
// top: marker['y'].toDouble(),
// child: GestureDetector(
// onTap: () {
// print('Tapped on ${marker['id']}');
// },
// child: Container(
// width: 50,
// height: 50,
// color: Colors.red,
// child: Center(
// child: Text(
// marker['id'],
// style: TextStyle(color: Colors.white),
// ),
// ),
// ),
// ),
// );
// }).toList(),
// );
// }
return SizedBox.shrink(); // No markers found
},
),
// return SizedBox.shrink(); // No markers found
// },
// ),
// Red widget overlay
// Positioned(
// left: 8, // Adjust based on your desired position

View File

@ -1,4 +1,5 @@
import 'dart:html' as html;
import 'package:web/web.dart' as web;
import 'dart:io';
import 'structs.dart';
import 'package:file_saver/file_saver.dart';

View File

@ -6,8 +6,9 @@ import 'package:crab_ui/structs.dart';
import 'package:flutter/material.dart';
import 'package:pdfrx/pdfrx.dart';
import 'package:pointer_interceptor/pointer_interceptor.dart';
import 'dart:html' as html;
import 'dart:js' as js;
// import 'dart:html' as html;
// import 'dart:js' as js;
import 'package:web/web.dart' as web;
import 'package:pointer_interceptor/pointer_interceptor.dart';
import 'attachmentWidget.dart';
@ -326,7 +327,8 @@ class AugmentClasses {
groupValue: selectedFolder,
onChanged: (String? value) {
setState(() {
selectedFolder = value; // Update the selected folder
selectedFolder =
value; // Update the selected folder
});
},
);
@ -352,8 +354,8 @@ class AugmentClasses {
print("Selected folder: $selectedFolder");
// Store the selected folder or perform any action
// ApiService.currFolder = selectedFolder!;
ApiService()
.moveEmail(ApiService.currFolder, ApiService.currThreadID, selectedFolder!);
ApiService().moveEmail(ApiService.currFolder,
ApiService.currThreadID, selectedFolder!);
_overlayEntry?.remove();
} else {
print("No folder selected");
@ -512,7 +514,7 @@ class AugmentClasses {
console.log('Iframe not found or not loaded.');
}
''';
js.context.callMethod('eval', [js_code]);
// js.context.callMethod('eval', [js_code]);
}
static void invisibility(String htmlClass) {}
@ -520,7 +522,7 @@ class AugmentClasses {
static Future<void> JumpButton(BuildContext context) async {
// FocusNode textFieldFocusNode = FocusNode();
AugmentClasses.disableIframePointerEvents();
// AugmentClasses.disableIframePointerEvents();
await showDialog(
barrierDismissible: true,
// barrierColor: Colors.yellow,
@ -602,7 +604,7 @@ class AugmentClasses {
],
),
).then((_) {
AugmentClasses.enableIframePointerEvents();
// AugmentClasses.enableIframePointerEvents();
});
}
@ -612,7 +614,7 @@ class AugmentClasses {
bool blankLines = false;
bool numbering = false;
bool statementSignatures = false;
AugmentClasses.disableIframePointerEvents();
// AugmentClasses.disableIframePointerEvents();
await showDialog(
context: context,
builder: (context) => Container(
@ -723,7 +725,7 @@ class AugmentClasses {
ElevatedButton(onPressed: () {}, child: Text('OK')),
ElevatedButton(
onPressed: () {
AugmentClasses.disableIframePointerEvents();
// AugmentClasses.disableIframePointerEvents();
Navigator.of(context).pop();
},
child: Text('Cancel')),
@ -737,7 +739,7 @@ class AugmentClasses {
),
),
)).then((_) {
AugmentClasses.enableIframePointerEvents(); // may be useless?
// AugmentClasses.enableIframePointerEvents(); // may be useless?
});
}
@ -747,7 +749,7 @@ class AugmentClasses {
//idea is to search in file, extract the <p> tags that contain these
//words and highlight, then when zoom, you just jump to that paragraph
AugmentClasses.disableIframePointerEvents();
// AugmentClasses.disableIframePointerEvents();
await showDialog(
context: context,
builder: (context) => Container(
@ -775,22 +777,27 @@ class AugmentClasses {
)))));
}
static void disableIframePointerEvents() {
//pretty sure these dont work
final iframes = html.document.getElementsByTagName('iframe');
for (var iframe in iframes) {
if (iframe is html.Element) {
iframe.style.pointerEvents = 'none'; // Disable pointer events
}
}
}
// static void disableIframePointerEvents() {
// //pretty sure these dont work
// // final iframes = html.document.getElementsByTagName('iframe');
// final iframes = web.document.getElementsByTagName('iframe');
// for (var iframe in iframes) {
// // if (iframe is html.Element) {
// // iframe.style.pointerEvents = 'none'; // Disable pointer events
// if (iframe is web.Element) {
// iframe.
// }
// }
// }
static void enableIframePointerEvents() {
final iframes = html.document.getElementsByTagName('iframe');
for (var iframe in iframes) {
if (iframe is html.Element) {
iframe.style.pointerEvents = 'auto'; // Re-enable pointer events
}
}
}
// static void enableIframePointerEvents() {
// // final iframes = html.document.getElementsByTagName('iframe');
// final iframes = html.document.getElementsByTagName('iframe');
// for (var iframe in iframes) {
// if (iframe is html.Element) {
// iframe.style.pointerEvents = 'auto'; // Re-enable pointer events
// }
// }
// }
}