Unresponsive webviews initially outside of viewport in SingleChildScrollView on real android devices w/ Android 12+

huangapple go评论75阅读模式
英文:

Unresponsive webviews initially outside of viewport in SingleChildScrollView on real android devices w/ Android 12+

问题

以下是您提供的代码的翻译部分:

我试图在`SingleChildScrollView`内显示具有相当长文本和多个iframe的文章。我使用[`flutter_html`](https://pub.dev/packages/flutter_html)来显示内容。

main.dart:
```dart
import 'package:flutter/material.dart';
import 'package:flutter_html/flutter_html.dart';
import 'package:issue/extension.dart';

void main() {
  runApp(const MyApp());
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
        useMaterial3: true,
      ),
      home: const MyHomePage(title: 'Flutter Demo Home Page'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key, required this.title});
  final String title;

  @override
  State<MyHomePage> createState() => _MyHomePageState();
}

// ... 继续阅读以下代码,不再重复翻译 ...
要自定义呈现iframes,我创建了一个自定义扩展(我不仅需要它来呈现YouTube视频,还需要呈现嵌入式内容,如TikTok视频、推文和Instagram帖子。为简单起见,其他部分未包含在帖子中。)。该扩展在[`InAppWebView`](https://inappwebview.dev/docs/webview/in-app-webview)中呈现特定链接。

extension.dart:
```dart
import 'package:flutter/foundation.dart';
import 'package:flutter/gestures.dart';
import 'package:flutter_html/flutter_html.dart';

import 'package:flutter/widgets.dart';
import 'package:flutter_inappwebview/flutter_inappwebview.dart';

class CustomIFrameHtmlExtension extends HtmlExtension {
  BuildContext buildContext;

  CustomIFrameHtmlExtension(
      {required this.buildContext});

  @override
  Set<String> get supportedTags => {"iframe"};

  // ... 继续阅读以下代码,不再重复翻译 ...
以下是您的`pubspec.yaml`文件:

```yaml
name: issue
description: A new Flutter project.

publish_to: 'none' # Remove this line if you wish to publish to pub.dev

version: 1.0.0+1

environment:
  sdk: '>=3.0.5 <4.0.0'

dependencies:
  flutter:
    sdk: flutter

  cupertino_icons: ^1.0.2
  http: ^1.0.0
  flutter_html: 3.0.0-beta.2
  flutter_inappwebview: ^6.0.0-beta.19

dev_dependencies:
  flutter_test:
    sdk: flutter

  flutter_lints: ^2.0.0

flutter:
  uses-material-design: true

请注意,我只翻译了您提供的代码的一部分。如果您需要更多翻译或有其他问题,请随时提出。

英文:

I am trying to display articles with rather long text and several iframes in them inside a SingleChildScrollView. I use flutter_html to display the content.

main.dart:

import 'package:flutter/material.dart';
import 'package:flutter_html/flutter_html.dart';
import 'package:issue/extension.dart';

void main() {
  runApp(const MyApp());
}

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
        useMaterial3: true,
      ),
      home: const MyHomePage(title: 'Flutter Demo Home Page'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key, required this.title});
  final String title;

  @override
  State<MyHomePage> createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  final String? html = """
    \n\n\n<p>Cannes Lions Uluslararası Yaratıcılık Festivali, dünyanın dört bir yanından yaratıcı isimleri 70’inci kez bir araya getirdi. 19-23 Haziran tarihleri arasında düzenlenen festivali yerinden takip edenler arasında Accenture Ortadoğu CMO’su Ebru Tuygun da vardı. Tuygun,  için kaleme aldı.</p>\n<div style="margin: 15px auto; padding: 10px; background: #eee;">\n<div class="Block-advert Block-advert__border Block-advert__border--gray">\n<p class="paragraph-12"></p>\n                </div>
    <iframe title="Korean National Police Agency - Knock Knock (case study) Glass Lions Grand Prix Cannes Lions 2023" width="500" height="281" src="https://www.youtube.com/embed/fcUIc4oTiUI?feature=oembed" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe>\n<h2>Cannes Lions’ın 70. yılında öne çıkan trendler</h2>\n<p>Yaratıcılığın sınırlarını zorlayan, pazarlama ve reklamcılığı yeniden tanımlayan yenilikçi fikirlerin paylaşıldığı Cannes Lions Uluslararası Yaratıcılık Festivali bu sene 70’inci yılını kutladı. Pazarlama ve reklamcılık dünyasının Oscarları olarak da kabul edilen Cannes Lions, dünyanın dört bir yanından gelen yaratıcı dünyanın duayenlerini bir araya getirirken ödül kazanan projeleri izlemek, reklam kampanyaların mutfağından ortaya çıkış hikâyelerini dinlemek ve potansiyel işbirlikleri geliştirmek için çeşitli yaratıcı etkinliklere katılmak muazzam bir deneyimdi. 19-23 Haziran haftası boyunca dünyanın önde gelen marka ve reklam dünyasının yöneticileri önümüzdeki dönemde pazarı etkileyecek ve sektöre yön verecek ilham verici konuşmalar, atölye çalışmaları ve etkinlikler gerçekleştirdiler.</p>\n<h4>Cannes Lions 2023’te gözlemlediğim öne çıkan trendler</h4>\n<ul>\n<li>Yapay zekâ devrimi</li>\n<li>Çeşitlilik, Eşitlik ve Kapsayıcılık (ÇEK) yol haritası</li>\n<li>Sürdürülebilir ve amaç odaklı pazarlama (purpose-led marketing)</li>\n<li>CMO-CFO işbirliği</li>\n<li>Yaratıcı hikâye anlatımı</li>\n</ul>\n<h2><span style="color: #ff0000;">Yapay zekâ devrimi</span></h2>\n<p>Her yıl Cannes Lions Uluslararası Yaratıcılık Festivali’ndeki sohbetlere hâkim olan birkaç konu vardır. Yapay zekâ bu yıl hemen hemen her etkinlikte gündeme geldi. Özellikle içerik oluşturmada verimliliği artırması, zaman kazandırması ve daha fazla yaratıcılığa yer vermesi hususlarında teknolojinin nasıl daha etkili kullanılabileceği tartışılırken yapây zekanın yeni bir yaratıcılık çağını başlattığı konuşuldu.</p>\n<p>Yapay zekânın yaratıcılık üzerindeki gelecekteki etkileri çok büyük ve sektörü güçlendirmek için büyük bir fırsat sunuyor. Yapay zekâ patlaması şimdiden toplumu yeniden şekillendiriyor, yenilik ve yaratıcılığın yeni sınırlarına ilham veriyor ve tüketici deneyiminde devrim yaratıyor. “ChatGPT, DALL·E ve Yaratıcılığın Geleceği” başlıklı oturumdaki konuşmasıyla OpenAI COO’su Brad Lightcap de özellikle bu konuların altını çizdi.</p>\n<p>Cannes Lions’ta ödül kazananlara bakarsak, teknoloji ve yapay zekâyı insanlığın yararı ve tüketicinin faydası yönünde kullanan projelerin öne çıktığını görebiliriz. Sevdiğim en iyi örnekler;</p>\n<h4><span style="color: #000000;">Glass: The Lion for Change’in “tık tık” Grand Prix kazananı Knock Knock</span></h4>\n<p>Tecavüz oranların oldukça yükseldiği Seul’da zor durumda kalan kadınların sessiz kalmamaları ve tek ‘tık’la polise haber vermelerini sağlayan bir uygulama.</p>\n<div class="mali">\n<div class="Block-single-details__content--video"></div>\n</div>\n<p><strong>Ajans:</strong> Cheil Worldwide Seul<br />\n<strong>Reklamveren:</strong> Korean National Police Agency</p>\n<h4><span style="color: #000000;">Titanium Lions’ta Grand Prix kazanan The First Digital Nation</span></h4>\n<p>İklim şartlarından dolayı yok olmaya yüz tutmuş bir ülkenin uluslararası dünyada statüsünü kaybetmemesi ve ülke haklarını koruyabilmesi için metaverse’te kurulan ilk dijital ülkenin hikâyesi.</p>\n<div class="mali">\n<div class="Block-single-details__content--video"><iframe title="Government of Tuvalu - The First Digital Nation (case study) Titanium Grand Prix Cannes Lions 2023" width="500" height="281" src="https://www.youtube.com/embed/b7QKboSOxUw?feature=oembed" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe></div>\n</div>\n<p><strong>Ajans:</strong> The Monkeys/Accenture Song<br />\n<strong>Reklamveren:</strong> Tuvalu</p>\n<h4><span style="color: #000000;">Creative Effectiveness Lions’ta Grand Prix kazanan Shah Rukh Khan-My-Ad</span></h4>\n<p>Küçük işletmelerin ekonomiye katılabilmelerini sağlayan reklamlarında Hindistan’dan çıkan, dünyada da oldukça büyük şöhrete sahip Shah Ruh Khan’i reklamlarında kullanmasını sağlayan dijital uygulamanın hikâyesi.</p>\n<div class="mali">\n<div class="Block-single-details__content--video"><iframe title="Cadbury - Shah Rukh Khan-My-Ad (case study) Creative Effectiveness Grand Prix Cannes Lions 2023" width="500" height="281" src="https://www.youtube.com/embed/US_1qLyOmUc?feature=oembed" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe></div>\n</div>\n<p><strong>Ajans:</strong> Ogilvy, Mumbai<br />\n<strong>Reklamveren:</strong> Mondelēz</p>\n<p>Carlton Rooftop’taki Cannes Lions LinkedIn Sahnesi’nde ele alınan, LinkedIn’in Ipsos ile birlikte yayınladığı <strong>‘<a href="https://business.linkedin.com/content/dam/me/business/en-us/amp/marketing-solutions/images/lms-state-of-b2b-marketing/pdf/the-b2b-benchmark-report-2023-final.pdf" target="_blank" rel="nofollow noopener">The B2B Marketing Benchmark</a>“</strong> başlıklı son araştırmasında da yapay zekânın iş dünyasını nasıl etkilediği öne çıkıyor. Yine aynı araştırmaya göre, “Yapay zekâ senin yerini almayacak; yapay zekâ kullanan biri alacak” gerçeğini kabul etmemiz ve benimsememiz gerekiyor.</p>\n<p>Pazarlama liderlerinin teknolojinin hızıyla başa çıkabilmeleri ve markalarını farklılaştırabilmeleri için yapay zekânın müşterileri, içerik sağlayıcıları, teknoloji uzmanları ve kurum çalışanları için ne anlama geldiğini anlamaları gerekiyor. Birkaç yıl önce Cannes Lions CMO Accelerator programında tanıştığım ve Palais’de konuşmacı olan NYU Profesörü Scott Galloway’in de dediği gibi, “Bu teknolojiyi (yapay zekâ) anlayan en yetenekli insanlar daha fazla para kazanacak. Ve onu anlamayan, sadece sinirlenen ve öğrenmek istemeyen insanlar daha az para kazanacak. Bu kadar basit.”</p>\n<p>Ünlü podcast programı Pivot’un Cannes Lions’ın ana sahnesinden canlı yayınlanan bölümünde, Scott Galloway’e yer verip yapay zekâ, Tesla, Meta ve diğer önemli oyuncular hakkında son gelişmeler paylaşıldı. Dinlemek isterseniz <strong><a href="https://podcasts.apple.com/ae/podcast/teslas-rising-value-metas-ai-and-Twitters-ad-problem/id1073226719?i=1000618079404" target="_blank" rel="nofollow noopener">buraya</a></strong> bağlantıyı ekliyorum.</p>\n<p></p>\n<h2><span style="color: #ff0000;">Çeşitlilik, Eşitlik ve Kapsayıcılık (ÇEK) yol haritası: Temsilin ötesinde yaratıcı düşünceyi dönüştürmek</span></h2>\n<p>Cannes Lions’ta birçok konuşmada öne çıkan diğer bir başlık “Çeşitlilik, Eşitlik ve Kapsayıcılık”tı. Cannes Lions’ta bu sene Afro-Amerikalıların sayısının oldukça fazla olması çok sevindiriciydi. Onların hem konuşmalarda hem de ödüllerde öne çıkmaları önemli gündemlerden biriydi. Yaratıcı çalışmalarda tüm din, dil, ırk ve cinsiyet ayrımcılığının sonlandırılmasının, üretim aşamasında bu tarz hassasiyetlere önem verilmesinin altı çizildi.</p>\n<p>
  """;
  final _scaffoldKey = GlobalKey<ScaffoldState>();

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      key: _scaffoldKey,
      appBar: AppBar(
        backgroundColor: Theme.of(context).colorScheme.inversePrimary,
        title: Text(widget.title),
      ),
      body: SingleChildScrollView(
          child: Padding(
            padding: const EdgeInsets.all(8.0),
            child: Html(extensions: [
              CustomIFrameHtmlExtension(buildContext: context)
            ], style: {
              "iframe": Style(
                height: Height.auto(),
                width: Width(MediaQuery.of(context).size.width * 0.85),
              ),
            }, data: html),
          )),
    );
  }
}

To custom render the iframes I create a custom extension (I need this not just for youtube videos but also to render embeds like tiktok videos, tweets, and instagram posts. The rest are not included in the post for simplicty's sake.). Which renders the specific links within InAppWebView.

extension.dart:

import 'package:flutter/foundation.dart';
import 'package:flutter/gestures.dart';
import 'package:flutter_html/flutter_html.dart';

import 'package:flutter/widgets.dart';
import 'package:flutter_inappwebview/flutter_inappwebview.dart';

class CustomIFrameHtmlExtension extends HtmlExtension {
  BuildContext buildContext;

  CustomIFrameHtmlExtension(
      {required this.buildContext});

  @override
  Set<String> get supportedTags => {"iframe"};

  final Set<Factory<OneSequenceGestureRecognizer>> gestureRecognizers = {
    Factory(() => EagerGestureRecognizer()),
  };
  final UniqueKey _key = UniqueKey();
  InAppWebViewController? webViewController;
  InAppWebViewSettings settings =
      InAppWebViewSettings(iframeAllowFullscreen: true);

  @override
  InlineSpan build(ExtensionContext context) {
    return WidgetSpan(
      child: Builder(
        builder: (child) {
          context;
          final String url = context.element!.attributes["src"]!;

          return Center(
            child: SizedBox(
              width: MediaQuery.of(buildContext).size.width * 0.85,
              height: double.parse(context.element!.attributes["height"]!),
              child: InAppWebView(
                onWebViewCreated: (controller) async {
                  webViewController = controller;
                },
                onPermissionRequest: (controller, request) async {
                  return PermissionResponse(
                      resources: request.resources,
                      action: PermissionResponseAction.GRANT);
                },
                initialSettings: settings,
                key: _key,
                initialUrlRequest: URLRequest(url: WebUri.uri(Uri.parse(url))),
                gestureRecognizers: gestureRecognizers,
              ),
            ),
          );
        },
      ),
    );
  }
}

If these webviews(regardless of the site) are rendered at the start of the page(in view port) such that they don't need to be scrolled down to, they work fine.

Issue:
When they are further down the page so that you have to scroll to view them, they are unresponsive but only on a real device. All of them work fine on both IOS and Android simulators. The real devices I have tested this with are Android 12 and 13. Android Simulator is also Android 13.
I have also tested with an Android 9 device which this works fine with.

Here's my pubspec.yaml:

name: issue
description: A new Flutter project.

publish_to: 'none' # Remove this line if you wish to publish to pub.dev

version: 1.0.0+1

environment:
  sdk: '>=3.0.5 <4.0.0'

dependencies:
  flutter:
    sdk: flutter

  cupertino_icons: ^1.0.2
  http: ^1.0.0
  flutter_html: 3.0.0-beta.2
  flutter_inappwebview: ^6.0.0-beta.19

dev_dependencies:
  flutter_test:
    sdk: flutter

  flutter_lints: ^2.0.0

flutter:
  uses-material-design: true

The two code snippets I've posted should be enough to reproduce the issue.
Can anyone help me understand why this would happen?

答案1

得分: 0

这似乎是与 flutter_html 包相关的问题。当我在滚动视图内放置了多个 webview 而没有 HTML 小部件时,它们似乎可以正常工作。

我发现 flutter_widget_from_html 在这种情况下是一个更好的选择,至少在这个案例中是这样。

英文:

This seems to be an issue with the flutter_html package. When I placed several webviews without an HTML widget they seemed to work fine inside a scrollview.

I found flutter_widget_from_html to be a better alternative, at least in this case.

huangapple
  • 本文由 发表于 2023年7月6日 21:12:30
  • 转载请务必保留本文链接:https://go.coder-hub.com/76629227.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定