목차

  1. 사용된 기능 설명
  2. 사용 예시

 

 

 

✅ 사용된 기능 설명

  • 캐스케이드 연산자(..) : 같은 객체에 여러 메서드를 "연쇄적으로" 호출할 때 사용 (ex. controller.setA(); controller.setB(); ...)
  • WebViewWidget : 실제 웹뷰 화면을 보여주는 위젯

 

 

✅ 사용 예시

 

1️⃣ pubspec.yaml 설정

 

 

2️⃣ main.dart 작성

  1. import 추가
  2. initState() 메소드 작성
  3. build 작성

 

 

3️⃣ 테스트

 

 

✔️ 사용된 코드

import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
import 'package:webview_flutter_android/webview_flutter_android.dart';
import 'package:webview_flutter_wkwebview/webview_flutter_wkwebview.dart';

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

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

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: ThemeData(primarySwatch: Colors.blue),
      home: const HomePage(),
    );
  }
}

class HomePage extends StatefulWidget {
  const HomePage({super.key});

  @override
  State<HomePage> createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {

  // WebView를 제어하는 객체의 변수 선언
  late final WebViewController _controller;

  @override
  void initState() {  // WebViewController 초기화 및 설정 작업 수행
    super.initState();

    // WebView 컨트롤러 생성 시 플랫폼 별(WebKit(iOS) / Android) 설정을 담는 객체
    late final PlatformWebViewControllerCreationParams params;

    if (WebViewPlatform.instance is WebKitWebViewPlatform) {
      params = WebKitWebViewControllerCreationParams(
        allowsInlineMediaPlayback: true,  // 동영상 등을 인라인 재생 허용
        mediaTypesRequiringUserAction: const <PlaybackMediaTypes>{},  // 사용자 제스처 없이도 자동 재생 허용
      );
    } else {
      params = const PlatformWebViewControllerCreationParams();
    }
    final WebViewController controller =
      WebViewController.fromPlatformCreationParams(params);

    controller
      ..setJavaScriptMode(JavaScriptMode.unrestricted)  // 웹뷰에서 자바스크립트 실행 허용 여부 설정 / unrestricted: 모든 JS 실행 허용
      ..setBackgroundColor(const Color(0x00000000))     // 캐스케이드 연산자(..) : 같은 객체에 여러 메서드를 "연쇄적으로" 호출할 때 사용 (ex. controller.setA(); controller.setB(); ...)
      ..setNavigationDelegate(  // 네비게이션 이벤트(페이지 로드, 에러, 진행률 등)를 처리하는 콜백 지정
        NavigationDelegate(
          onProgress: (int progress) {
            debugPrint('WebView is loading (progress : $progress%)');
          },
          onPageStarted: (String url) {
            debugPrint('Page started loading: $url');
          },
          onPageFinished: (String url) {
            debugPrint('Page finished loading: $url');
          },
          onWebResourceError: (WebResourceError error) {
            debugPrint('''
              Page resource error:
                code: ${error.errorCode}
                description: ${error.description}
                errorType: ${error.errorType}
                isForMainFrame: ${error.isForMainFrame}
            ''');
          },
          onNavigationRequest: (NavigationRequest request) {
            debugPrint('allowing navigation to ${request.url}');
            return NavigationDecision.navigate;
          },
        ),
      )
      ..addJavaScriptChannel(
        'Toaster',
        onMessageReceived: (JavaScriptMessage message) {
          ScaffoldMessenger.of(context).showSnackBar(
            SnackBar(content: Text(message.message)),
          );
        },
      )
      ..loadRequest(Uri.parse('https://flutter.dev/'));     // loadRequest : 초기 로드할 URL 지정
    if (controller.platform is AndroidWebViewController) {  // 플랫폼이 Android일 경우에만 실행
      AndroidWebViewController.enableDebugging(true);       // WebView에서 크롬 개발자 도구를 사용한 디버깅 허용
      (controller.platform as AndroidWebViewController)
          .setMediaPlaybackRequiresUserGesture(false);      // 동영상/오디오 재생 시 사용자 제스처 없이 자동 재생 허용
    }
    _controller = controller;
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: SafeArea(
        bottom: false,
        child: WebViewWidget( // WebViewWidget : 실제 웹뷰 화면을 보여주는 위젯
          controller: _controller
        ),
      ),
    );
  }
}

+ Recent posts