A Wechat Camera Picker For Flutter

reactive_wechat_camera_picker

Wrapper around wechat_camera_picker to use with reactive_forms

Docs in progress. See example folder for sample.

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add reactive_wechat_camera_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  reactive_wechat_camera_picker: ^0.0.1

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:reactive_wechat_camera_picker/reactive_wechat_camera_picker.dart'; 

example/lib/main.dart

import 'package:flutter/material.dart';
import 'package:reactive_wechat_camera_picker/reactive_wechat_camera_picker.dart';
import 'package:reactive_forms/reactive_forms.dart';
import 'package:reactive_wechat_camera_picker_example/selected_asset_view.dart';

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

class MyApp extends StatelessWidget {
  const MyApp({Key? key}) : super(key: key);

  FormGroup buildForm() => fb.group({
        'input': FormControl<AssetEntity>(value: null),
      });

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      theme: ThemeData(
        primarySwatch: Colors.blue,
        visualDensity: VisualDensity.adaptivePlatformDensity,
      ),
      home: Scaffold(
        appBar: AppBar(),
        body: SafeArea(
          child: SingleChildScrollView(
            physics: const BouncingScrollPhysics(),
            padding: const EdgeInsets.symmetric(
              horizontal: 20.0,
              vertical: 20.0,
            ),
            child: ReactiveFormBuilder(
              form: buildForm,
              builder: (context, form, child) {
                return Column(
                  children: [
                    ReactiveWechatCameraPicker<AssetEntity>(
                      formControlName: 'input',
                      imagePickerBuilder: (pick, image, _) {
                        return Column(
                          children: [
                            if (image != null)
                              SelectedAssetView(
                                asset: image,
                                isDisplayingDetail: ValueNotifier(true),
                                onRemoveAsset: () {},
                              ),
                            ElevatedButton(
                              onPressed: pick,
                              child: const Text('Pick'),
                            ),
                          ],
                        );
                      },
                    ),
                    ElevatedButton(
                      child: const Text('Submit'),
                      onPressed: () {
                        if (form.valid) {
                          debugPrint(form.value.toString());
                        }
                      },
                    ),
                  ],
                );
              },
            ),
          ),
        ),
      ),
    );
  }
} 

Download Details:

Author: artflutter

Source Code: https://github.com/artflutter/reactive_forms_widgets/tree/master/packages/reactive_wechat_camera_picker

#flutter #Picker #camera 

A Wechat Camera Picker For Flutter

A Flutter Multimedia Picker Packages

image_pickers支持本地图片多选,本地视频多选,支持将网络图片保存到相册,支持截图保存到相册,支持将网络视频保存到相册,支持预览视频和预览图片功能,支持主题颜色设置

image pickers support multi-selection of local pictures, multi-selection of local videos, support for saving network pictures to albums, support for saving screenshots to albums, support for saving network videos to albums, support for preview videos and preview images, and support for theme color settings

Supported Platforms

  • Android
  • iOS

iOS : platform :ios, '10.0'

Android: minSdkVersion 19 targetSdkVersion 29 compileSdkVersion 29

多选图片时 cropConfig 字段无效 The cropConfig field is invalid when multiple images are selected

How to Use

# add this line to your dependencies
image_pickers: ^2.0.0+2
import 'package:image_pickers/image_pickers.dart';


///选择多张图片 Select multiple images
Future<void> selectImages() async {
    List<Media> _listImagePaths = await ImagePickers.pickerPaths(
              galleryMode: GalleryMode.image,
              selectCount: 2,
              showGif: false,
              showCamera: true,
              compressSize: 500,
              uiConfig: UIConfig(uiThemeColor: Color(0xffff0f50)),
              cropConfig: CropConfig(enableCrop: false, width: 2, height: 1));
  }

/// 或者 or
ImagePickers.pickerPaths().then((List medias){
      /// medias 照片路径信息 Photo path information
    });

///选择多个视频 Select multiple videos
Future<void> selectVideos() async {
   List<Media> _listVideoPaths = await ImagePickers.pickerPaths(
          galleryMode: GalleryMode.video,
          selectCount: 5,
        );
  }
///直接打开相机拍摄图片 Open the camera directly to take a picture
ImagePickers.openCamera().then((Media? media){
    /// media 包含照片路径信息 Include photo path information
    /// 未拍照返回 media = null
    if(media != null){
        
    }
  });

///直接打开相机拍摄视频 Open the camera directly to shoot the video
ImagePickers.openCamera(cameraMimeType: CameraMimeType.video).then((media){
    /// media 包含视频路径信息 Contains video path information
    /// 未拍摄视频返回 media = null
    if(media != null){
            
    }
  });

///预览图片 Preview picture
ImagePickers.previewImage(_listImagePaths[index].path);
///预览多张图片 Preview multiple pictures
ImagePickers.previewImagesByMedia(_listImagePaths,index);
///预览多张图片 Preview multiple pictures
ImagePickers.previewImages(paths,index);

///预览视频 Preview video
ImagePickers.previewVideo(_listVideoPaths[index].path);
///保存图片到图库 Save image to gallery
ImagePickers.saveImageToGallery("http://i1.sinaimg.cn/ent/d/2008-06-04/U105P28T3D2048907F326DT20080604225106.jpg");
/// 保存截图图片 ByteData 到图库 Save screenshot image ByteData to gallery
RenderRepaintBoundary boundary = globalKey.currentContext.findRenderObject();
ui.Image image = await boundary.toImage(pixelRatio: 3);
ByteData byteData = await image.toByteData(format: ui.ImageByteFormat.png);
Uint8List data = byteData.buffer.asUint8List();

String dataImagePath = await ImagePickers.saveByteDataImageToGallery(data,);

///保存视频到图库 Save video to gallery
ImagePickers.saveVideoToGallery("http://xxxx/xx/xx.mp4");

iOS

Add the following entry to your Info.plist file, located in /Info.plist : <key>NSAppTransportSecurity</key> <dict> <key>NSAllowsArbitraryLoads</key> <true/> </dict> <key>NSMicrophoneUsageDescription</key> <string>...</string> <key>NSPhotoLibraryAddUsageDescription</key> <string>...</string> <key>NSCameraUsageDescription</key> <string>...</string> <key>NSPhotoLibraryUsageDescription</key> <string>...</string>

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add image_pickers

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  image_pickers: ^2.0.0+2

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:image_pickers/image_pickers.dart'; 

example/lib/main.dart

import 'dart:io';
import 'dart:typed_data';

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'dart:async';

import 'package:flutter/services.dart';
import 'package:image_pickers/image_pickers.dart';
import 'dart:ui' as ui;

void main() => runApp(MyApp());

class MyApp extends StatefulWidget {
  @override
  _MyAppState createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  GalleryMode _galleryMode = GalleryMode.image;
  GlobalKey? globalKey;
  @override
  void initState() {
    super.initState();
    globalKey = GlobalKey();
  }

  List<Media> _listImagePaths = [];
  List<Media> _listVideoPaths = [];
  String? dataImagePath = "";

  Future<void> selectImages() async {
    try {
      _galleryMode = GalleryMode.image;
      _listImagePaths = await ImagePickers.pickerPaths(
          galleryMode: _galleryMode,
          showGif: true,
          selectCount: 2,
          showCamera: true,
          cropConfig :CropConfig(enableCrop: true,height: 1,width: 1),
          compressSize: 500,
          uiConfig: UIConfig(uiThemeColor: Color(0xffff0000),
          ),

      );
      print(_listImagePaths.length);
      if(_listImagePaths.length > 0){
        _listImagePaths.forEach((media){
          print(media.path.toString());
        });
      }
      setState(() {

      });
    } on PlatformException {}
  }

  Future<void> selectVideos() async {
    try {
      _galleryMode = GalleryMode.video;
      _listVideoPaths = await ImagePickers.pickerPaths(
        galleryMode: _galleryMode,
        selectCount: 2,
        showCamera: true,
      );
      setState(() {

      });
      print(_listVideoPaths);
    } on PlatformException {}
  }

  @override
  Widget build(BuildContext context) {
    return RepaintBoundary(
      key: globalKey,
      child: MaterialApp(
        theme: ThemeData(
          backgroundColor: Colors.white,
          primaryColor: Colors.white,
        ),

        home: Scaffold(
          appBar: AppBar(
            title: const Text('多图选择'),
          ),
          body: SingleChildScrollView(
            physics: BouncingScrollPhysics(),
            child: Column(
              children: <Widget>[
                GridView.builder(
                    physics: NeverScrollableScrollPhysics(),
                    itemCount: _listImagePaths.length,
                    shrinkWrap: true,
                    gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
                        crossAxisCount: 3,
                        mainAxisSpacing: 20.0,
                        crossAxisSpacing: 10.0,
                        childAspectRatio: 1.0),
                    itemBuilder: (BuildContext context, int index) {
                      return GestureDetector(
                        onTap: (){
//                        ImagePickers.previewImage(_listImagePaths[index].path);

//                      List<String> paths = [];
//                        _listImagePaths.forEach((media){
//                          paths.add(media.path);
//                        });
//
//                        ImagePickers.previewImages(paths,index);

                          ImagePickers.previewImagesByMedia(_listImagePaths,index);
                        },
                        child: Image.file(
                          File(
                            _listImagePaths[index].path!,
                          ),
                          fit: BoxFit.cover,
                        ),
                      );
                    }),
                ElevatedButton(
                  onPressed: () {
                    selectImages();
                  },
                  child: Text("选择图片"),
                ),
                ElevatedButton(
                  onPressed: () async {
                    ImagePickers.openCamera(cropConfig: CropConfig(enableCrop: false, width: 2, height: 3)).then((Media? media){
                      _listImagePaths.clear();
                      if(media != null){
                        _listImagePaths.add(media);
                      }
                      setState(() {

                      });
                    });
                  },
                  child: Text("拍照"),
                ),
                ElevatedButton(
                  onPressed: () {
                    ImagePickers.openCamera(cameraMimeType: CameraMimeType.video).then((media){
                      _listVideoPaths.clear();
                      if(media != null){
                      print(media.path);
                      _listVideoPaths.add(media);
                      }
                      setState(() {

                      });
                    });
                  },
                  child: Text("拍视频"),
                ),
                GridView.builder(
                    physics: NeverScrollableScrollPhysics(),
                    itemCount: _listVideoPaths.length,
                    shrinkWrap: true,
                    gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
                        crossAxisCount: 3,
                        mainAxisSpacing: 20.0,
                        crossAxisSpacing: 10.0,
                        childAspectRatio: 1.0),
                    itemBuilder: (BuildContext context, int index) {
                      return GestureDetector(
                        onTap: (){
                          ImagePickers.previewVideo(_listVideoPaths[index].path!,);
                        },
                        child: Image.file(
                          File(
                            _listVideoPaths[index].thumbPath!,
                          ),
                          fit: BoxFit.cover,
                        ),
                      );
                    }),
                ElevatedButton(
                  onPressed: () {
                    selectVideos();
                  },
                  child: Text("选择视频"),
                ),

                InkWell(
                  onTap: (){
                    ImagePickers.previewImage("http://i1.sinaimg.cn/ent/d/2008-06-04/U105P28T3D2048907F326DT20080604225106.jpg");
                  },
                    child: Image.network("http://i1.sinaimg.cn/ent/d/2008-06-04/U105P28T3D2048907F326DT20080604225106.jpg",fit: BoxFit.cover,width: 100,height: 100,)),
                ElevatedButton(
                  onPressed: () {
                    Future<String?> future = ImagePickers.saveImageToGallery("http://i1.sinaimg.cn/ent/d/2008-06-04/U105P28T3D2048907F326DT20080604225106.jpg");
                    future.then((path){
                      print("保存图片路径:"+ path!);
                    });
                  },
                  child: Text("保存网络图片"),
                ),
                dataImagePath == "" ? Container():GestureDetector(onTap: (){
                  ImagePickers.previewImage(dataImagePath!);
                },child: Image.file(File(dataImagePath!),fit: BoxFit.cover,width: 100,height: 100,)),
                ElevatedButton(
                  onPressed: () async {

                    RenderRepaintBoundary boundary = globalKey!.currentContext!.findRenderObject() as RenderRepaintBoundary;
                    ui.Image image = await boundary.toImage(pixelRatio: 3);
                    ByteData byteData = await image.toByteData(format: ui.ImageByteFormat.png) as ByteData;
                    Uint8List data = byteData.buffer.asUint8List();

                    dataImagePath = await ImagePickers.saveByteDataImageToGallery(data,);

                    print("保存截屏图片 = "+ dataImagePath!);
                    setState(() {

                    });
                  },
                  child: Text("保存截屏图片"),
                ),

                ElevatedButton(
                  onPressed: () {
                      Future<String?> future = ImagePickers.saveVideoToGallery("http://vd4.bdstatic.com/mda-jbmn50510sid5yx5/sc/mda-jbmn50510sid5yx5.mp4");
                      future.then((path){
                        print("视频保存成功"+path!);
                      });
                  },
                  child: Text("保存视频"),
                ),
              ],
            ),
          ),
        ),
      ),
    );
  }
} 

Download Details:

Author: 

Source Code: https://pub.dev/packages/image_pickers

#flutter #android #Picker 

A Flutter Multimedia Picker Packages
Rupert  Beatty

Rupert Beatty

1667799426

BSImagePicker: A multiple image picker for iOS

BSImagePicker

A multiple image picker for iOS.

Features

  • Multiple selection.
  • Fullscreen preview
  • Switching albums.
  • Supports images, live photos and videos.
  • Customizable.
alt text

Usage

Info.plist

To be able to request permission to the users photo library you need to add this to your Info.plist

<key>NSPhotoLibraryUsageDescription</key>
<string>Why you want to access photo library</string>

Image picker

import BSImagePicker

let imagePicker = ImagePickerController()

presentImagePicker(imagePicker, select: { (asset) in
    // User selected an asset. Do something with it. Perhaps begin processing/upload?
}, deselect: { (asset) in
    // User deselected an asset. Cancel whatever you did when asset was selected.
}, cancel: { (assets) in
    // User canceled selection. 
}, finish: { (assets) in
    // User finished selection assets.
})

PHAsset

So you have a bunch of PHAssets now, great. But how do you use them? To get an UIImage from the asset you use a PHImageManager.

import Photos

// Request the maximum size. If you only need a smaller size make sure to request that instead.
PHImageManager.default().requestImage(for: asset, targetSize: PHImageManagerMaximumSize, contentMode: .aspectFit, options: nil) { (image, info) in
    // Do something with image
}

For more example you can clone this repo and look at the example app.

Installation

Cocoapods

Add the following line to your Podfile:

pod "BSImagePicker", "~> 3.1"

Carthage

Add the following line to your Cartfile:

github "mikaoj/BSImagePicker" ~> 3.1

Swift Package Manager

Add it to the dependencies value of your Package.swift.:

dependencies: [
.package(url: "https://github.com/mikaoj/BSImagePicker.git", from: "version-tag")
]

Xamarin

If you are Xamarin developer you can use Net.Xamarin.iOS.BSImagePicker

Contribution

Users are encouraged to become active participants in its continued development — by fixing any bugs that they encounter, or by improving the documentation wherever it’s found to be lacking.

If you wish to make a change, open a Pull Request — even if it just contains a draft of the changes you’re planning, or a test that reproduces an issue — and we can discuss it further from there.

Download Details:

Author: Mikaoj
Source Code: https://github.com/mikaoj/BSImagePicker 
License: MIT license

#swift #image #Picker 

BSImagePicker: A multiple image picker for iOS

Image Picker Tutorial in Flutter

flutter_timpage_picker

A new flutter plugin project.

Getting Started

This project is a starting point for a Flutter plug-in package, a specialized package that includes platform-specific implementation code for Android and/or iOS.

For help getting started with Flutter, view our online documentation, which offers tutorials, samples, guidance on mobile development, and a full API reference. 

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add flutter_timpage_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  flutter_timpage_picker: ^1.0.0

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:flutter_timpage_picker/flutter_timpage_picker.dart'; 

example/lib/main.dart

import 'package:flutter/material.dart';
import 'dart:async';

import 'package:flutter/services.dart';
import 'package:flutter_timpage_picker/flutter_timpage_picker.dart';
import 'package:flutter_timpage_picker/image_picker_option.dart';

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

class MyApp extends StatefulWidget {
  const MyApp({Key? key}) : super(key: key);

  @override
  State<MyApp> createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  String _platformVersion = 'Unknown';

  @override
  void initState() {
    super.initState();
    initPlatformState();
  }

  // Platform messages are asynchronous, so we initialize in an async method.
  Future<void> initPlatformState() async {
    String platformVersion;
    // Platform messages may fail, so we use a try/catch PlatformException.
    // We also handle the message potentially returning null.
    try {
      platformVersion = await FlutterTimpagePicker.platformVersion ??
          'Unknown platform version';
    } on PlatformException {
      platformVersion = 'Failed to get platform version.';
    }

    // If the widget was removed from the tree while the asynchronous platform
    // message was in flight, we want to discard the reply rather than calling
    // setState to update our non-existent appearance.
    if (!mounted) return;

    setState(() {
      _platformVersion = platformVersion;
    });
  }

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: const Text('Plugin example app'),
        ),
        body: Center(
            child: Column(
          children: [
            Text('Running on: $_platformVersion\n'),
            ElevatedButton(
              onPressed: () async {
                PickOptions options = PickOptions();
                options.imageCount = 1;
                options.isCrop = false;
                options.isCamera = false;
                options.showSelectedIndex = false;
                options.isRecordSelected = true;
                var ret = await FlutterTimpagePicker.showImagePicker(options);
                print("result:" + ret.toString());
              },
              child: Text("选择照片"),
            ),
            ElevatedButton(
              onPressed: () async {
                PickOptions options = PickOptions();
                options.imageCount = 1;
                options.isCrop = true;
                options.isCamera = false;
                options.showSelectedIndex = false;
                options.isRecordSelected = true;
                var ret = await FlutterTimpagePicker.openCamera(options);
                if (ret == null) {
                  print("camera null");
                } else {
                  print("camera result:" + ret.toString());
                }
              },
              child: Text("拍照"),
            ),
          ],
        )),
      ),
    );
  }
} 

Download Details:

Author: 

Source Code: https://pub.dev/packages/flutter_timpage_picker

#flutter #image #Picker 

Image Picker Tutorial in Flutter

Advanced Image Picker with Flutter

Advanced Image Picker

This is my custom Image Picker that enabling you to multiple pick image and Adv Camera with our Custom UI

Note: This plugin is still under development, and some Components might not be available yet or still has so many bugs.

Installation

First, add adv_image_picker as a dependency in your pubspec.yaml file.

Notes

If you are about to load the image in thumbnail size, it is recommended to get the image bytes from AdvImagePickerPlugin.getThumbnail Otherwise, it will be causing memory issue

adv_image_picker: ^1.0.6

Example

You can find the full example, here

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add adv_image_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  adv_image_picker: ^2.0.2

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:adv_image_picker/adv_image_picker.dart'; 

example/lib/main.dart

import 'dart:async';
import 'dart:io';
import 'dart:typed_data';

import 'package:adv_image_picker/adv_image_picker.dart';
import 'package:adv_image_picker/plugins/adv_image_picker_plugin.dart';
import 'package:flutter/material.dart';

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

class CustomImageCache extends WidgetsFlutterBinding {
  @override
  ImageCache createImageCache() {
    ImageCache imageCache = super.createImageCache();
    // Set your image cache size
    imageCache.maximumSize = 10;
    return imageCache;
  }
}

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: MyHomePage(title: 'Image Picker Demo Home Page'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key key, this.title}) : super(key: key);

  final String title;

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  List<File> files = [];
  List<ImageProvider> thumbnails = [];
  bool isPreparing = false;

  @override
  void initState() {
    super.initState();

    AdvImagePicker.cameraFolderName = "Camera Folder";
    AdvImagePicker.cameraFilePrefixName = "CameraTestingPrefixName_";
    AdvImagePicker.cameraSavePath = "/storage/emulated/0/CameraTestingFolder/";
  }

  @override
  void dispose() {
    //flushing every memory that was taken before
    if ((thumbnails?.length ?? 0) > 0) {
      for (ImageProvider each in thumbnails) {
        each.evict();
      }
    }

    super.dispose();
  }

  void _pickImage() async {
    files.addAll(await AdvImagePicker.pickImagesToFile(context, maxSize: 4080));
    print("files => ${files.map((e) => e.path).join("\n")}");
    prepare();
  }

  Future<void> prepare() async {
    List<ImageProvider> thumbnails = [];
    double screenWidth = MediaQuery.of(context).size.width;

    for (int i = 0; i < files.length; i++) {
      String path = files[i].path;
      ByteData data = await AdvImagePickerPlugin.getAlbumThumbnail(
        imagePath: path,
        height: screenWidth ~/ 4,
        width: screenWidth ~/ 4,
      );

      Uint8List imageData = data.buffer.asUint8List();

      thumbnails.add(MemoryImage(imageData));
    }

    this.thumbnails = List<ImageProvider>.from(thumbnails);

    if (this.mounted) setState(() {});
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(widget.title),
      ),
      body: Center(
        child: isPreparing ? CircularProgressIndicator() : GridView.count(
          crossAxisCount: 4,
          children: thumbnails
              .map((ImageProvider image) => Image(
                    image: image,
                    fit: BoxFit.cover,
                  ))
              .toList(),
        ),
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: _pickImage,
        child: Icon(Icons.add),
      ),
    );
  }
} 

Download Details:

Author: ricnaaru

Source Code: https://github.com/ricnaaru/adv_image_picker

#flutter #Picker #image 

Advanced Image Picker with Flutter

Animated Item Picker with Flutter

Animated Item Picker

Generic item picker that encapsulates single or multiple item selection logic.

Suitable for fixed size item lists, e.g level, week day or gender selector etc.

Supports tapUp/tapDown item opacity animation.

Preview

Usage

  @override
  Widget build(BuildContext context) {
    return AnimatedItemPicker(
          axis: Axis.horizontal,
          multipleSelection: false,
          itemCount: yourModelList.length,
          pressedOpacity: 0.85,
          initialSelection: {defaultItemIndex},
          onItemPicked: (index, selected) {
         
          },
          itemBuilder: (index, animValue, selected) => _YourItemWidget(
            name: yourModelList[index].name,
            borderColor: _colorTween1.transform(animValue),
            textColor: _colorTween2.transform(animValue),
            iconColor: _colorTween3.transform(animValue)
          ),
      );
  }

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add animated_item_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  animated_item_picker: ^1.0.5+1

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:animated_item_picker/animated_item_picker.dart'; 

example/lib/main.dart

import 'package:animated_item_picker/animated_item_picker.dart';
import 'package:example/model/day_of_week.dart';
import 'package:example/model/level.dart';
import 'package:example/ui/helper.dart';
import 'package:example/ui/item_widgets.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';

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

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(home: Material(child: HomePage(), color: Colors.black));
  }
}

class HomePage extends StatelessWidget {
  static ColorTween _firstPickerColorTween1 = ColorTween(begin: Colors.white, end: Colors.redAccent);
  static ColorTween _firstPickerColorTween2 = ColorTween(begin: Colors.black, end: Colors.redAccent);

  static ColorTween _secondPickerColorTween1 = ColorTween(begin: Colors.black, end: Colors.yellow);
  static ColorTween _secondPickerColorTween2 = ColorTween(begin: Colors.white, end: Colors.yellow);

  @override
  Widget build(BuildContext context) {
    return Column(mainAxisAlignment: MainAxisAlignment.center, mainAxisSize: MainAxisSize.min, children: [
      decorateFirstItemPicker(
        AnimatedItemPicker(
            axis: Axis.horizontal,
            multipleSelection: false,
            itemCount: Level.LIST.length,
            pressedOpacity: 0.85,
            initialSelection: {Level.LIST.indexOf(Level.BEGINNER)},
            expandedItems: true,
            onItemPicked: (index, selected) {
              print("Gender: ${Level.LIST[index]}, selected: $selected");
            },
            itemBuilder: (index, animValue) => GenderItemWidget(
                  name: Level.LIST[index].toString(),
                  borderColor: _firstPickerColorTween2.transform(animValue)!,
                  textColor: _firstPickerColorTween1.transform(animValue)!,
                )),
      ),
      decorateSecondItemPicker(
        AnimatedItemPicker(
          axis: Axis.vertical,
          multipleSelection: true,
          itemCount: DayOfWeek.LIST.length,
          maxItemSelectionCount: 6,
          expandedItems: true,
          initialSelection: {1},
          onItemPicked: (index, selected) {
            print("Day: ${DayOfWeek.LIST[index]}, selected: $selected");
          },
          itemBuilder: (index, animValue) => DayItemWidget(
            name: DayOfWeek.LIST[index],
            textColor: _secondPickerColorTween2.transform(animValue)!,
            backgroundColor: _secondPickerColorTween1.transform(animValue)!,
          ),
        ),
      ),
    ]);
  }
} 

Download Details:

Author: kirn-tech/

Source Code: https://github.com/kirn-tech/animated_item_picker

#Picker #animation #flutter 

Animated Item Picker with Flutter

Material Design Date Range Picker with Flutter

z_date_range_picker

Shows a full screen modal dialog containing a Material Design date range picker.

how to use

void showCustomRangePicker() async {
    var res = await showTCRDateRangePicker(
      context: context,
      // selectRange: CustomDateTimeRange(start: DateTime.now(), end: DateTime.now().add(Duration(days: 6))),
      selectRange: CustomDateTimeRange(),
      validRange: CustomDateTimeRange(start: DateTime(2021, 1), end: DateTime(2022, 7)),
    );
    print('res = $res');
  }

Images

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add z_date_range_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  z_date_range_picker: ^0.0.5

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:z_date_range_picker/date_range_picker.dart'; 

example/lib/main.dart

import 'package:flutter/material.dart';
import 'package:z_date_range_picker/date_range_picker.dart';

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

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      restorationScopeId: 'app',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: MyHomePage(title: 'Flutter Demo Home Page', restorationId: 'main'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key? key, this.title, this.restorationId}) : super(key: key);

  final String? title;
  final String? restorationId;

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

/// https://api.flutter.dev/flutter/material/showDateRangePicker.html
class _MyHomePageState extends State<MyHomePage> {
  // with RestorationMixin
  @override
  String? get restorationId => widget.restorationId;
  // final RestorableDateTimeN _startDate = RestorableDateTimeN(DateTime(2021, 1, 1));
  // final RestorableDateTimeN _endDate = RestorableDateTimeN(DateTime(2021, 1, 5));
  // late final RestorableRouteFuture<DateTimeRange?> _restorableDateRangePickerRouteFuture = RestorableRouteFuture<DateTimeRange?>(
  //   onComplete: _selectDateRange,
  //   onPresent: (NavigatorState navigator, Object? arguments) {
  //     return navigator.restorablePush(_dateRangePickerRoute, arguments: <String, dynamic>{
  //       'initialStartDate': _startDate.value?.millisecondsSinceEpoch,
  //       'initialEndDate': _endDate.value?.millisecondsSinceEpoch,
  //     });
  //   },
  // );
  //
  // void _selectDateRange(DateTimeRange? newSelectedDate) {
  //   if (newSelectedDate != null) {
  //     setState(() {
  //       _startDate.value = newSelectedDate.start;
  //       _endDate.value = newSelectedDate.end;
  //     });
  //   }
  // }
  //
  // @override
  // void restoreState(RestorationBucket? oldBucket, bool initialRestore) {
  //   registerForRestoration(_startDate, 'start_date');
  //   registerForRestoration(_endDate, 'end_date');
  //   registerForRestoration(_restorableDateRangePickerRouteFuture, 'date_picker_route_future');
  // }
  //
  // static Route<DateTimeRange?> _dateRangePickerRoute(
  //   BuildContext context,
  //   Object? arguments,
  // ) {
  //   return DialogRoute<DateTimeRange?>(
  //     context: context,
  //     builder: (BuildContext context) {
  //       return DateRangePickerDialog(
  //         restorationId: 'date_picker_dialog',
  //         initialDateRange: _initialDateTimeRange(arguments! as Map<dynamic, dynamic>),
  //         firstDate: DateTime(2021, 1, 1),
  //         currentDate: DateTime(2021, 1, 25),
  //         lastDate: DateTime(2022, 1, 1),
  //       );
  //     },
  //   );
  // }
  //
  // static DateTimeRange? _initialDateTimeRange(Map<dynamic, dynamic> arguments) {
  //   if (arguments['initialStartDate'] != null && arguments['initialEndDate'] != null) {
  //     return DateTimeRange(
  //       start: DateTime.fromMillisecondsSinceEpoch(arguments['initialStartDate'] as int),
  //       end: DateTime.fromMillisecondsSinceEpoch(arguments['initialEndDate'] as int),
  //     );
  //   }
  //
  //   return null;
  // }

  void showCustomRangePicker() async {
    var res = await showTCRDateRangePicker(
      context: context,
      // selectRange: CustomDateTimeRange(start: DateTime.now(), end: DateTime.now().add(Duration(days: 6))),
      selectRange: CustomDateTimeRange(),
      validRange: CustomDateTimeRange(start: DateTime(2021, 1), end: DateTime(2022, 7)),
    );
    print('res = $res');
  }

  void showSystemRangePicker() async {}

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(widget.title ?? 'X'),
      ),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: <Widget>[
            TextButton(onPressed: showCustomRangePicker, child: Text('show date range picker')),
            TextButton(onPressed: showCustomRangePicker, child: Text('show system date range picker')),
          ],
        ),
      ),
    );
  }
} 

Download Details:

Author: qqzhao

Source Code: https://gitee.com/qqzhao/flutter_pubs

#flutter #date #Picker 

Material Design Date Range Picker with Flutter

A Customizable Progressive Time Picker for Flutter

progressive_time_picker

A Customizable Progressive Time Picker for Flutter. This package allow us to customize time picker based on our requirements for selecting a specific range from time picker and it's supports multiple platforms.

Key Features

  • supports selection of both or single picker handler.
  • easy customization for decorating a time picker.
  • gives feature to show clock numbers in both 12 or 24 hours format and also supports customization for it.

Preview

progressive_time_picker

Basic Usage

Import it to your project file

import 'package:progressive_time_picker/progressive_time_picker.dart';

And add it in its most basic form like it:

  TimePicker(
    initTime: PickedTime(h: 0, m: 0),
    endTime: PickedTime(h: 8, m: 0),
    onSelectionChange: (a, b) =>
        print(
            'onSelectionChange => init : ${a.h}:${a.m}, end : ${b.h}:${b.m}'),
    onSelectionEnd: (a, b) =>
        print(
            'onSelectionEnd => init : ${a.h}:${a.m}, end : ${b.h}:${b.m}'),
  );

Required parameters of TimePicker


ParameterDescription
PickedTime initTimethe init PickedTime value in the selection
PickedTime endTimethe end PickedTime value in the selection
onSelectionChangecallback function when init and end PickedTime change
onSelectionEndcallback function when init and end PickedTime finish

Optional parameters of TimePicker


ParameterDefaultDescription
double height220height of the canvas
double width220width of the canvas
int primarySectors0the number of primary sectors to be painted
int secondarySectors0the number of secondary sectors to be painted
Widget childContainerwidget that would be mounted inside the circle
TimePickerDecoration decoration-used to decorate our TimePicker widget
bool isInitHandlerSelectabletrueused to enabled or disabled Selection of Init Handler
bool isEndHandlerSelectabletrueused to enabled or disabled Selection of End Handler

Required parameters of TimePickerDecoration


ParameterDescription
TimePickerSweepDecoration sweepDecorationused to decorate our sweep part or a part between our init and end point with various options
TimePickerHandlerDecoration initHandlerDecorationused to decorate our init or end handler of time picker
TimePickerHandlerDecoration endHandlerDecorationused to decorate our init or end handler of time picker

Optional parameters of TimePickerDecoration


ParameterDefaultDescription
Color baseColorcyanAccentdefines the background color of the picker
double pickerBaseCirclePadding0.0to add extra padding for picker base or outer circle
TimePickerSectorDecoration primarySectorsDecoration-used to decorate the primary sectors of out time picker
TimePickerSectorDecoration secondarySectorsDecoration-used to decorate the secondary of out time picker
TimePickerClockNumberDecoration clockNumberDecoration-Provides decoration options which will get applied to the internal clock's numbers when enable

Guideline for contributors


  • Contribution towards our repository is always welcome, we request contributors to create a pull request for development.

Guideline to report an issue/feature request


It would be great for us if the reporter can share the below things to understand the root cause of the issue.

  • Library version
  • Code snippet
  • Logs if applicable
  • Device specification like (Manufacturer, OS version, etc)
  • Screenshot/video with steps to reproduce the issue
  • Library used

LICENSE!

progressive_time_picker is MIT-licensed.

Let us know!

We’d be really happy if you send us links to your projects where you use our component. Just send an email to sales@mindinventory.com And do let us know if you have any questions or suggestion regarding our work

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add progressive_time_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  progressive_time_picker: ^0.0.6

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:progressive_time_picker/progressive_time_picker.dart'; 

example/lib/main.dart

import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:progressive_time_picker/progressive_time_picker.dart';
import 'package:intl/intl.dart' as intl;

void main() {
  /// To set fixed device orientation
  WidgetsFlutterBinding.ensureInitialized();
  SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp]).then(
    (value) => runApp(MyApp()),
  );
  SystemChrome.setSystemUIOverlayStyle(SystemUiOverlayStyle.light);
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: MyHomePage(),
      debugShowCheckedModeBanner: false,
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key? key}) : super(key: key);

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  ClockTimeFormat _clockTimeFormat = ClockTimeFormat.TWENTYFOURHOURS;
  ClockIncrementTimeFormat _clockIncrementTimeFormat =
      ClockIncrementTimeFormat.FIVEMIN;

  PickedTime _inBedTime = PickedTime(h: 0, m: 0);
  PickedTime _outBedTime = PickedTime(h: 8, m: 0);
  PickedTime _intervalBedTime = PickedTime(h: 0, m: 0);

  double _sleepGoal = 8.0;
  bool _isSleepGoal = false;

  @override
  void initState() {
    super.initState();
    _isSleepGoal = (_sleepGoal >= 8.0) ? true : false;
    _intervalBedTime = formatIntervalTime(
      init: _inBedTime,
      end: _outBedTime,
      clockTimeFormat: _clockTimeFormat,
      clockIncrementTimeFormat: _clockIncrementTimeFormat,
    );
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Color(0xFF141925),
      body: Column(
        mainAxisAlignment: MainAxisAlignment.spaceEvenly,
        children: [
          Text(
            'Sleep Time',
            style: TextStyle(
              color: Color(0xFF3CDAF7),
              fontSize: 30,
              fontWeight: FontWeight.bold,
            ),
          ),
          TimePicker(
            initTime: _inBedTime,
            endTime: _outBedTime,
            height: 260.0,
            width: 260.0,
            onSelectionChange: _updateLabels,
            onSelectionEnd: (a, b) => print(
                'onSelectionEnd => init : ${a.h}:${a.m}, end : ${b.h}:${b.m}'),
            primarySectors: _clockTimeFormat.value,
            secondarySectors: _clockTimeFormat.value * 2,
            decoration: TimePickerDecoration(
              baseColor: Color(0xFF1F2633),
              pickerBaseCirclePadding: 15.0,
              sweepDecoration: TimePickerSweepDecoration(
                pickerStrokeWidth: 30.0,
                pickerColor: _isSleepGoal ? Color(0xFF3CDAF7) : Colors.white,
                showConnector: true,
              ),
              initHandlerDecoration: TimePickerHandlerDecoration(
                color: Color(0xFF141925),
                shape: BoxShape.circle,
                radius: 12.0,
                icon: Icon(
                  Icons.power_settings_new_outlined,
                  size: 20.0,
                  color: Color(0xFF3CDAF7),
                ),
              ),
              endHandlerDecoration: TimePickerHandlerDecoration(
                color: Color(0xFF141925),
                shape: BoxShape.circle,
                radius: 12.0,
                icon: Icon(
                  Icons.notifications_active_outlined,
                  size: 20.0,
                  color: Color(0xFF3CDAF7),
                ),
              ),
              primarySectorsDecoration: TimePickerSectorDecoration(
                color: Colors.white,
                width: 1.0,
                size: 4.0,
                radiusPadding: 25.0,
              ),
              secondarySectorsDecoration: TimePickerSectorDecoration(
                color: Color(0xFF3CDAF7),
                width: 1.0,
                size: 2.0,
                radiusPadding: 25.0,
              ),
              clockNumberDecoration: TimePickerClockNumberDecoration(
                defaultTextColor: Colors.white,
                defaultFontSize: 12.0,
                scaleFactor: 2.0,
                showNumberIndicators: true,
                clockTimeFormat: _clockTimeFormat,
                clockIncrementTimeFormat: _clockIncrementTimeFormat,
              ),
            ),
            child: Padding(
              padding: const EdgeInsets.all(62.0),
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: [
                  Text(
                    '${intl.NumberFormat('00').format(_intervalBedTime.h)}Hr ${intl.NumberFormat('00').format(_intervalBedTime.m)}Min',
                    style: TextStyle(
                      fontSize: 14.0,
                      color: _isSleepGoal ? Color(0xFF3CDAF7) : Colors.white,
                      fontWeight: FontWeight.bold,
                    ),
                  ),
                ],
              ),
            ),
          ),
          Container(
            width: 300.0,
            alignment: Alignment.center,
            decoration: BoxDecoration(
              color: Color(0xFF1F2633),
              borderRadius: BorderRadius.circular(25.0),
            ),
            child: Padding(
              padding: const EdgeInsets.all(16.0),
              child: Text(
                _isSleepGoal
                    ? "Above Sleep Goal (>=8) 😄"
                    : 'below Sleep Goal (<=8) 😴',
                style: TextStyle(
                  color: Colors.white,
                  fontSize: 20,
                  fontWeight: FontWeight.bold,
                ),
              ),
            ),
          ),
          Row(
            mainAxisAlignment: MainAxisAlignment.spaceEvenly,
            children: [
              _timeWidget(
                'BedTime',
                _inBedTime,
                Icon(
                  Icons.power_settings_new_outlined,
                  size: 25.0,
                  color: Color(0xFF3CDAF7),
                ),
              ),
              _timeWidget(
                'WakeUp',
                _outBedTime,
                Icon(
                  Icons.notifications_active_outlined,
                  size: 25.0,
                  color: Color(0xFF3CDAF7),
                ),
              ),
            ],
          ),
        ],
      ),
    );
  }

  Widget _timeWidget(String title, PickedTime time, Icon icon) {
    return Container(
      width: 150.0,
      decoration: BoxDecoration(
        color: Color(0xFF1F2633),
        borderRadius: BorderRadius.circular(25.0),
      ),
      child: Padding(
        padding: const EdgeInsets.all(25.0),
        child: Column(
          children: [
            Text(
              '${intl.NumberFormat('00').format(time.h)}:${intl.NumberFormat('00').format(time.m)}',
              style: TextStyle(
                color: Color(0xFF3CDAF7),
                fontSize: 25,
                fontWeight: FontWeight.bold,
              ),
            ),
            SizedBox(height: 15),
            Text(
              '$title',
              style: TextStyle(
                color: Color(0xFF3CDAF7),
                fontSize: 16,
              ),
            ),
            SizedBox(height: 10),
            icon,
          ],
        ),
      ),
    );
  }

  void _updateLabels(PickedTime init, PickedTime end) {
    _inBedTime = init;
    _outBedTime = end;
    _intervalBedTime = formatIntervalTime(
      init: _inBedTime,
      end: _outBedTime,
      clockTimeFormat: _clockTimeFormat,
      clockIncrementTimeFormat: _clockIncrementTimeFormat,
    );
    _isSleepGoal = validateSleepGoal(
      inTime: init,
      outTime: end,
      sleepGoal: _sleepGoal,
      clockTimeFormat: _clockTimeFormat,
      clockIncrementTimeFormat: _clockIncrementTimeFormat,
    );
    setState(() {});
  }
} 

Download Details:

Author: Mindinventory

Source Code: https://github.com/Mindinventory/progressive_time_picker

#time #Picker #flutter 

A Customizable Progressive Time Picker for Flutter
Monty  Boehm

Monty Boehm

1662552329

4 Best React Image Picker Libraries

In today's post we will learn about 4 Best React Image Picker Libraries.

A highly customizable, stable, responsive photo gallery React. In this components you will learn about how react works to make images different in looks. You will put carousel plugin effects, react slider, React native slider ,React image gallery intense and so on. The original ratio of your pictures is maintained and actual elements are used. It is also feasible to add additional features such as captions and favourites to your custom picture parts.

1 - React Photo Gallery

  • Responsive, accessible, composable, and customizable image gallery component
  • Maintains the original aspect ratio of your photos
  • Creates a masonry or justified grid
  • Supports row or column direction layout
  • Provides an image renderer for custom implementation of things like image selection, favorites, captions, etc.
  • SSR app compatible

CodeSandbox Demos with Example Use Cases

To build some examples locally, git clone and run:

yarn install
yarn start

Then open localhost:8000 in a browser.

Minimal Setup Example

const photos = [
  {
    src: 'http://example.com/example/img1.jpg',
    width: 4,
    height: 3
  },
  {
    src: 'http://example.com/example/img2.jpg',
    width: 1,
    height: 1
  }
];

<Gallery photos={photos} />;

View on Github

2 - React-grid-gallery

Justified image gallery component for React inspired by Google Photos and based upon React Images.

Installation

Using npm:

npm install --save react-grid-gallery

Quick (and dirty) Start

import React from 'react';
import { render } from 'react-dom';
import Gallery from 'react-grid-gallery';

const IMAGES =
[{
        src: "https://c2.staticflickr.com/9/8817/28973449265_07e3aa5d2e_b.jpg",
        thumbnail: "https://c2.staticflickr.com/9/8817/28973449265_07e3aa5d2e_n.jpg",
        thumbnailWidth: 320,
        thumbnailHeight: 174,
        isSelected: true,
        caption: "After Rain (Jeshu John - designerspics.com)"
},
{
        src: "https://c2.staticflickr.com/9/8356/28897120681_3b2c0f43e0_b.jpg",
        thumbnail: "https://c2.staticflickr.com/9/8356/28897120681_3b2c0f43e0_n.jpg",
        thumbnailWidth: 320,
        thumbnailHeight: 212,
        tags: [{value: "Ocean", title: "Ocean"}, {value: "People", title: "People"}],
        caption: "Boats (Jeshu John - designerspics.com)"
},

{
        src: "https://c4.staticflickr.com/9/8887/28897124891_98c4fdd82b_b.jpg",
        thumbnail: "https://c4.staticflickr.com/9/8887/28897124891_98c4fdd82b_n.jpg",
        thumbnailWidth: 320,
        thumbnailHeight: 212
}]

render(
        <Gallery images={IMAGES}/>,
        document.getElementById('example-0')
);

View on Github

3 - Image-upload-react

react image picker

Install

npm install --save image-upload-react

Usage

import React, { useState } from 'react'
import ImageUpload from 'image-upload-react'
//important for getting nice style.
import 'image-upload-react/dist/index.css'

function App() {
  const [imageSrc, setImageSrc] = useState()

  const handleImageSelect = (e) => {
    setImageSrc(URL.createObjectURL(e.target.files[0]))
  }

  return (
    <ImageUpload
      handleImageSelect={handleImageSelect}
      imageSrc={imageSrc}
      setImageSrc={setImageSrc}
      style={{
        width: 700,
        height: 500,
        background: 'gold'
      }}
    />
  )
}

export default App

View on Github

4 - React-smart-gallery

Render images based on optimal layout, like facebook render images inside timeline.

Install:

npm install react-smart-gallery

Use:

import SmartGallery from 'react-smart-gallery';

const images = [
  'https://source.unsplash.com/random/400x400',
  'https://source.unsplash.com/random/400x400',
  'https://source.unsplash.com/random/400x400',
];

<SmartGallery images={images} />

View on Github

Thank you for following this article. 

Related videos:

Awesome React Photo Gallery Components

#react #image #Picker 

4 Best React Image Picker Libraries

A Flutter Package for Pick Images and Videos From Gallery

Flutter Gallery Picker

This a Flutter Gallery which allows you to pick image or video from gallery.

Features

Here are some features:

  • Easy, lightweight, open-source.
  • Flutter Native Screens
  • Gallery Like Screens
  • Preview Image
  • MIT licensed.
  • Easily extensible.

Getting Started

Installing

Add this to your package's pubspec.yaml file:

dependencies:
  flutter_gallery_picker: ^0.0.4

Import

import 'package:flutter_gallery_picker/flutter_gallery_picker.dart';

How to use

Android

Add the following permissions to your AndroidManifest.xml, located in <project root>/android/app/src/main/AndroidManifest.xml:

<manifest ...>
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
    ...
<manifest/>

API 29+

Add the following property to your AndroidManifest.xml, located in <project root>/android/app/src/main/AndroidManifest.xml to opt-out of scoped storage:

<manifest ...>
    ...
    <application
        android:requestLegacyExternalStorage="true"
        ...>
    <application/>
<manifest/>

Usage

Single

 File image = await GalleryScreen.getImage(context);
 print(image);

you can use the image as File

getImage() async {
    File image = await GalleryScreen.getImage(context);
    // print image path
    print(image.path);
    
    // from package rflutter_alert
    Alert(
      context: context,
      // show image from file (image)
      content: Image.file(image),
    ).show();

}

Multi

you can get List<File>

 List<File> images = await GalleryScreen.getImage(context , multi:true);
 print(images);
getImage() async {
    List<File> images = await GalleryScreen.getImage(context , multi:true);
    // print images list
    print(images);
    
    // from package rflutter_alert
    Alert(
      context: context,
      // show image from file (image)
      content: Image.file(image.first),
    ).show();

}

it's really easy :)

  • You can say Thank You, Donate to the developer.

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add flutter_gallery_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  flutter_gallery_picker: ^0.0.4

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:flutter_gallery_picker/flutter_gallery_picker.dart'; 

Download Details:

Author: 

Source Code: https://pub.dev/packages/flutter_gallery_picker/

#flutter #Picker #image 

A  Flutter Package for Pick Images and Videos From Gallery

Easy Folder Picker for Flutter

Easy Folder Picker

Easy directory picker for Flutter

A flutter package to pick directories and handles requesting required permissions as well. This package only supports ANDROID.

Picker Screenshot1 Picker Screenshot2

Installation

Add below line to your pubspec.yaml and run flutter packages get

  easy_folder_picker: ^latest version

Permissions

Add below line to your android/app/src/main/AndroidManifest.xml

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />

If you want to allow creating new folders directly from picker then add the below permission also

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

Android 10 (Q)

In Android 10, you need to add the Following Lines in AndroidManifest file:

<application
      android:requestLegacyExternalStorage="true"

Android 11

From Android 11, you need to manage permission within your app, if you want to write in different folders of external storage.

Steps

  1. Add the following Lines in AndroidManifest file
  <uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE"/>
  1. Add device_info package to check android version
  2. Check permission if app can manage external storage if its android 11 or greater Note: This is a runtime permission (might not show it in app info's permission section )
  var status = await Permission.manageExternalStorage.status;
      if (status!.isRestricted) {
        status = await Permission.manageExternalStorage.request();
      }

      if (status!.isDenied) {
        status = await Permission.manageExternalStorage.request();
      }
      if (status!.isPermanentlyDenied) {
        ScaffoldMessenger.of(context).showSnackBar(SnackBar(
          backgroundColor: Colors.green,
          content: Text('Please add permission for app to manage external storage'),
        ));
      }

Flutter Usage

import 'package:easy_folder_picker/FolderPicker.dart';

// In any callback call the below method
  Future<void> _pickDirectory(BuildContext context) async {
    Directory directory = selectedDirectory;
    if (directory == null) {
      directory = Directory(FolderPicker.ROOTPATH);
    }

    Directory newDirectory = await FolderPicker.pick(
        allowFolderCreation: true,
        context: context,
        rootDirectory: directory,
        shape: RoundedRectangleBorder(
            borderRadius: BorderRadius.all(Radius.circular(10))));
    setState(() {
      selectedDirectory = newDirectory;
      print(selectedDirectory);
    });
  }

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add easy_folder_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  easy_folder_picker: ^1.3.0

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:easy_folder_picker/DirectoryList.dart';
import 'package:easy_folder_picker/FolderPicker.dart'; 

example/lib/main.dart

import 'dart:io';

import 'package:easy_folder_picker/FolderPicker.dart';
import 'package:flutter/material.dart';

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

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Easy Folder Picker',
      debugShowCheckedModeBanner: false,
      theme: ThemeData(
        primarySwatch: Colors.blue,
        visualDensity: VisualDensity.adaptivePlatformDensity,
      ),
      home: HomePage(),
    );
  }
}

class HomePage extends StatefulWidget {
  @override
  _HomePageState createState() => _HomePageState();
}

class _HomePageState extends State<HomePage> {
  Directory? selectedDirectory;

  Future<void> _pickDirectory(BuildContext context) async {
    Directory? directory = selectedDirectory;
    if (directory == null) {
      directory = Directory(FolderPicker.rootPath);
    }

    Directory? newDirectory = await FolderPicker.pick(
        allowFolderCreation: true,
        context: context,
        rootDirectory: directory,
        shape: RoundedRectangleBorder(
            borderRadius: BorderRadius.all(Radius.circular(10))));
    setState(() {
      selectedDirectory = newDirectory;
      print(selectedDirectory);
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text("Folder"),
        centerTitle: true,
      ),
      body: Container(
        child: Column(
          children: [
            IconButton(
              icon: Icon(Icons.file_download),
              onPressed: () {
                _pickDirectory(context);
              },
            ),
            selectedDirectory != null
                ? Text("Selected Path : ${selectedDirectory!.path}")
                : Container(),
          ],
        ),
      ),
    );
  }
} 

Download Details:

Author: kapilmhr

Source Code: https://github.com/kapilmhr/Easy-Folder-Picker

#flutter #Picker 

Easy Folder Picker for Flutter

A Flutter Plugin to Provide A form Like A Contact Selector

contactor_picker

联系人选择器

Getting Started

1 Add [contactor_picker] latest version under dependencies to your package's pubspec.yaml file.

dependencies:
  contactor_picker: ^0.0.6

2 You can install packages from the command line:

$ flutter packages get

3 Api Usage

  • Usage
///列表加搜索
ContactorPicker.showPicker(
                    context,
                    ///数据源
                    dataList: [],
                    ///是否展示code 默认不展示
                    showGroupCode: true,
                    ///选中数据
                    onSelectedData: (data) {

                    },
                    ///标题
                    title: '联系人',
                    ///页面背景色
                    backgroundColor: Color(0xFFFAFAFA),
                    ///当前字母颜色
                    letterSelectedColor: Colors.blueAccent,
                  );
///仅搜索
   ContactorPicker.showSearchPicker(
                    context,
                    ///是否展示code 默认不展示
                    showGroupCode: true,
                    ///不展示
                    dataList: [],
                    ///背景色
                    backgroundColor: Color(0xFFFAFAFA),
                    ///选中数据
                    onSelectedData: (data) {
                    },
                  );
///支持嵌入其他Widget  详见example
 return Scaffold(
      appBar: AppBar(
        title: const Text('Plugin example app'),
      ),
      body: ContactorView(
        ///数据源
        dataList: DataUtil.dataList.map((element) {
          String pinyin = PinyinHelper.getPinyinE(element['name'],
              separator: " ",
              defPinyin: '#',
              format: PinyinFormat.WITHOUT_TONE);
          return ContactorDataListData(
            name: element['name'],
            id: int.tryParse(element['zip']),
            pinyin: pinyin,
            headerImageUrl: 'https://picsum.photos/250?image=9',
            code: element['label'],
            groupCode: element['zip'],
          );
        }).toList(),
        ///选中item时仅选中 不附带pop动作
        canPop: false,
        ///选中回调
        onSelectedData: (ContactorDataListData data) {
          print('${data.toString()}');
        },
      ),
  );

预览

image

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add contactor_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  contactor_picker: ^0.0.7

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:contactor_picker/contactor_picker.dart'; 

example/lib/main.dart

import 'package:contactor_picker_example/data_util.dart';
import 'package:flutter/material.dart';
import 'package:contactor_picker/contactor_picker.dart';
import 'package:lpinyin/lpinyin.dart';

void main() {
  runApp(MaterialApp(home: MyApp()));
}

class MyApp extends StatefulWidget {
  @override
  _MyAppState createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  @override
  void initState() {
    super.initState();
    print('length----${DataUtil.dataList.length}');
  }

  String _currentData = '';

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Plugin example app'),
      ),
      // body: ContactorView(
      //   dataList: DataUtil.dataList.map((element) {
      //     String pinyin = PinyinHelper.getPinyinE(element['name'],
      //         separator: " ",
      //         defPinyin: '#',
      //         format: PinyinFormat.WITHOUT_TONE);
      //     return ContactorDataListData(
      //       name: element['name'],
      //       id: int.tryParse(element['zip']),
      //       pinyin: pinyin,
      //       headerImageUrl: 'https://picsum.photos/250?image=9',
      //       code: element['label'],
      //       groupCode: element['zip'],
      //     );
      //   }).toList(),
      //   canPop: false,
      //   onSelectedData: (ContactorDataListData data) {
      //     print('${data.toString()}');
      //   },
      // ),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: [
            TextButton(
              onPressed: () {
                ContactorPicker.showPicker(
                  context,
                  showGroupCode: true,
                  dataList: DataUtil.dataList.map((element) {
                    String pinyin = PinyinHelper.getPinyinE(element['name'],
                        separator: "",
                        defPinyin: '#',
                        format: PinyinFormat.WITHOUT_TONE);
                    return ContactorDataListData(
                      name: element['name'],
                      id: int.tryParse(element['zip']),
                      pinyin: pinyin,
                      // headerImageUrl: 'https://picsum.photos/250?image=9',
                      code: element['label'],
                      groupCode: element['zip'],
                    );
                  }).toList(),
                  title: '地址簿',
                  extendWidget: Column(
                    crossAxisAlignment: CrossAxisAlignment.start,
                    children: [
                      Container(
                        alignment: Alignment.centerLeft,
                        height: 40,
                        child: Text('666666'),
                      ),
                      Container(
                        height: 40,
                        alignment: Alignment.centerLeft,
                        child: Text('555555'),
                      ),
                      Expanded(
                        child: Container(
                          height: 40,
                          alignment: Alignment.centerLeft,
                          child: Text('888888'),
                        ),
                      )
                    ],
                  ),
                  // backgroundColor: Color(0xFFFAFAFA),
                  letterSelectedColor: Colors.blueAccent,
                  onSelectedData: (data, pageNum) {
                    print(data.toJson());
                    _currentData = data.toJson().toString();
                    setState(() {});
                  },
                );
              },
              child: Text('地址簿'),
            ),
            TextButton(
              onPressed: () {
                ContactorPicker.showSearchPicker(
                  context,
                  showGroupCode: true,
                  dataList: DataUtil.dataList.map((element) {
                    String pinyin = PinyinHelper.getPinyinE(element['name'],
                        separator: " ",
                        defPinyin: '#',
                        format: PinyinFormat.WITHOUT_TONE);
                    return ContactorDataListData(
                      name: element['name'],
                      id: int.tryParse(element['zip']),
                      pinyin: pinyin,
                      code: element['label'],
                      groupCode: element['zip'],
                    );
                  }).toList(),
                  backgroundColor: Color(0xFFFAFAFA),
                  onSelectedData: (data, pageNum) {
                    print(data.toJson());
                    _currentData = data.toJson().toString();
                    setState(() {});
                  },
                );
              },
              child: Text('搜索'),
            ),
            Container(
              padding: EdgeInsets.symmetric(horizontal: 30),
              child: Text('currentData: $_currentData\n'),
            ),
          ],
        ),
      ),
    );
  }
} 

Download Details:

Author: shinenyok

Source Code: https://github.com/shinenyok/contactor_picker

#flutter #Picker 

A Flutter Plugin to Provide A form Like A Contact Selector

Flutter Plugin for City Picker, Popups Widgets, Call By Function

Language: English

city_pickers

中国的城市三级联动选择器

Demo

 

沟通QQ群

QQ 群号码: 935915271

image

开始

在flutter的项目文件中增加依赖

dependencies:
  ...
    city_pickers:^0.0.1

关于如何运行flutter项目, 参考官方文档documentation.

使用方法

Import city_pickers.dart

import 'package:zxj_city_pickers/city_pickers.dart';

简单使用方法

...
// type 1
Result result = await CityPickers.showCityPicker(
  context: context,
);
// type 2
Result result2 = await CityPickers.showFullPageCityPicker(
  context: context,
);
// type 3
Result result2 = await CityPickers.showCitiesSelector(
  context: context,
);

CityPickers 静态方法

NameTypeDesc
showCityPickerFunction呼出弹出层,显示多级选择器
showFullPageCityPickerFunction呼出一层界面, 显示多级选择器
showCitiesSelectorFunction呼出一层, 显示支持字母定位城市选择器
utilsFunction获取utils接口的钩子

showCityPicker 参数说明

NameTypeDefaultDesc
contextBuildContext 上下文对象
themeThemeDataTheme.of(context)主题, 可以自定义
locationCodeString110000初始化地址信息, 可以是省, 市, 区的地区码
heightdouble300弹出层的高度, 过高或者过低会导致容器报错
showTypeShowTypeShowType.pca三级联动, 显示类型
barrierOpacitydouble0.5弹出层的背景透明度, 应该是大于0, 小于1
barrierDismissiblebooltrue是否可以通过点击弹出层背景, 关闭弹出层
cancelWidgetWidget 用户自定义取消按钮
confirmWidgetWidget 用户自定义确认按钮
itemExtentdouble 目标框高度
itemBuilderWidget item生成器, function(String value, List
citiesDataMap城市数据选择器的城市与区的数据源
provincesDataMap省份数据选择器的省份数据源

showFullPageCityPicker 参数说明

NameTypeDefaultDesc
contextBuildContextnull上下文对象
themeThemeDataTheme.of(context)主题, 可以自定义
locationCodeString110000初始化地址信息, 可以是省, 市, 区的地区码
showTypeShowTypeShowType.pca三级联动, 显示类型

|citiesData|Map|城市数据|选择器的城市与区的数据源| |provincesData|Map|省份数据|选择器的省份数据源|

showCitiesSelector 参数说明

NameTypeDefaultDesc
contextBuildContextnull上下文对象
themeThemeDataTheme.of(context)主题, 可以自定义
locationCodeString110000初始化地址信息, 可以是省, 市, 区的地区码
titleString城市选择器弹出层界面标题
citiesDataMap城市数据选择器的城市与区的数据源
provincesDataMap省份数据选择器的省份数据源
hotCitiesList<HotCity>null热门城市
sideBarStyleBaseStyle初始默认样式右侧字母索引集样式
cityItemStyleBaseStyle初始默认样式城市选项样式
topStickStyleBaseStyle初始默认样式顶部索引吸顶样式

utils 说明

utils 是用来封装常用的一些方法, 方便使用者能更好的使用该插件. 使用者通过以下方式声明实例, 可以获取所有的工具类方法

// 声明实例
CityPickerUtil cityPickerUtils = CityPickers.utils();

Result getAreaResultByCode(String code)

使用者通过地区ID, 获取所在区域的省市县等相关信息. 当未查询到具体信息. 返回空的Result对象.

print('result>>> ${cityPickerUtils.getAreaResultByCode('100100)}');

// 输出为: result>>>> {"provinceName":"北京市","provinceId":"110000","cityName":"东城区","cityId":"110101"}

数据来源

National Bureau of Statistics

声明

本项目Example部份代码与样式, 参考借鉴Flutter Go, flutter go 是flutter 开发者帮助 APP,包含 flutter 常用 140+ 组件的demo 演示与中文文档

To Do List

  • [x] 城市选择器, 借鉴点评
  • [ ] 支持拼音等模糊搜索
  • [ ] 加入单元测试

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add zxj_city_pickers

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  zxj_city_pickers: ^1.1.1

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:zxj_city_pickers/city_pickers.dart';
import 'package:zxj_city_pickers/meta/province.dart';
import 'package:zxj_city_pickers/modal/base_citys.dart';
import 'package:zxj_city_pickers/modal/point.dart';
import 'package:zxj_city_pickers/modal/result.dart'; 

Download Details:

Author: 

Source Code: https://pub.dev/packages/zxj_city_pickers

#flutter #widgets #Picker 

Flutter Plugin for City Picker, Popups Widgets, Call By Function

File Picker Plugin for Flutter

File Picker

A package that allows you to use the native file explorer to pick single or multiple files, with extensions filtering support.

Currently supported features

  • Uses OS default native pickers
  • Supports multiple platforms (Mobile, Web, Desktop and Flutter GO)
  • Pick files using custom format filtering — you can provide a list of file extensions (pdf, svg, zip, etc.)
  • Pick files from cloud files (GDrive, Dropbox, iCloud)
  • Single or multiple file picks
  • Different default type filtering (media, image, video, audio or any)
  • Picking directories
  • Load file data immediately into memory (Uint8List) if needed;
  • Open a save-file / save-as dialog (a dialog that lets the user specify the drive, directory, and name of a file to save)

If you have any feature that you want to see in this package, please feel free to issue a suggestion. 🎉

Compatibility Chart

APIAndroidiOSLinuxmacOSWindowsWeb
clearTemporaryFiles()
getDirectoryPath()
pickFiles()
saveFile()

See the API section of the File Picker Wiki or the official API reference on pub.dev for further details.

Documentation

See the File Picker Wiki for every detail on about how to install, setup and use it.

File Picker Wiki

  1. Installation
  2. Setup
  3. API
  4. FAQ
  5. Troubleshooting

Usage

Quick simple usage example:

Single file

FilePickerResult? result = await FilePicker.platform.pickFiles();

if (result != null) {
  File file = File(result.files.single.path);
} else {
  // User canceled the picker
}

Multiple files

FilePickerResult? result = await FilePicker.platform.pickFiles(allowMultiple: true);

if (result != null) {
  List<File> files = result.paths.map((path) => File(path)).toList();
} else {
  // User canceled the picker
}

Multiple files with extension filter

FilePickerResult? result = await FilePicker.platform.pickFiles(
  type: FileType.custom,
  allowedExtensions: ['jpg', 'pdf', 'doc'],
);

Pick a directory

String? selectedDirectory = await FilePicker.platform.getDirectoryPath();

if (selectedDirectory == null) {
  // User canceled the picker
}

Save-file / save-as dialog

String? outputFile = await FilePicker.platform.saveFile(
  dialogTitle: 'Please select an output file:',
  fileName: 'output-file.pdf',
);

if (outputFile == null) {
  // User canceled the picker
}

Load result and file details

FilePickerResult? result = await FilePicker.platform.pickFiles();

if (result != null) {
  PlatformFile file = result.files.first;

  print(file.name);
  print(file.bytes);
  print(file.size);
  print(file.extension);
  print(file.path);
} else {
  // User canceled the picker
}

Pick and upload a file to Firebase Storage with Flutter Web

FilePickerResult? result = await FilePicker.platform.pickFiles();

if (result != null) {
  Uint8List fileBytes = result.files.first.bytes;
  String fileName = result.files.first.name;
  
  // Upload file
  await FirebaseStorage.instance.ref('uploads/$fileName').putData(fileBytes);
}

For full usage details refer to the Wiki above.

Example App

Android

Demo

iOS

DemoMultiFilters

MacOS

DemoMacOS

Linux

DemoLinux

Windows

DemoWindows

Getting Started

For help getting started with Flutter, view our online documentation.

For help on editing plugin code, view the documentation.

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add pfile_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  pfile_picker: ^4.5.1+3

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:pfile_picker/pfile_picker.dart'; 

example/lib/main.dart

import 'src/file_picker_demo.dart';
import 'package:flutter/widgets.dart';

void main() => runApp(FilePickerDemo()); 

Download Details:

Author: miguelpruivo

Source Code: https://github.com/miguelpruivo/flutter_file_picker

#flutter #Picker 

File Picker Plugin for Flutter

Flutter Plugin for City Picker, Address Picker, Popups Widgets

地址选择器

由于地址选择的数据来源会更新,为了统一,在后台配置一份城市数据,前端获取,否则各个平台都配置一份数据,维护会很麻烦,而且有可能每个平台城市的数据结构都不一样。 本库就是由此而来,数据从后台实时获取,只要解析成固定的数据结构就可以

效果示例

导入方式

dependencies:
    flutter_city_picker: ^1.0.4

使用方法

  1. 简单使用
    CityPicker.show(context: context, cityPickerListener: this);
  1. 多配置的使用
    CityPicker.show(
          context: context,
          // 主题颜色
          theme: ThemeData(
            // 弹窗的背景颜色
            dialogBackgroundColor: Colors.white,
          ),
          // 底部弹出框动画时间
          duration: 200,
          // 背景透明度
          opacity: 0.5,
          // 点击外部是否消失
          dismissible: true,
          // 高度
          height: 400,
          // 标题高度
          titleHeight: 50,
          // 顶部圆角
          corner: 20,
          // 距离左边的间距
          paddingLeft: 15,
          // 标题组件
          titleWidget: Container(
            padding: EdgeInsets.only(left: 15),
            child: Text(
              '请选择地址',
              style: TextStyle(
                color: Colors.black54,
                fontSize: 18,
                fontWeight: FontWeight.bold,
              ),
            ),
          ),
          // 关闭图标组件
          closeWidget: Icon(Icons.close),
          // tab 高度
          tabHeight: 40,
          // 是否启用街道
          enableStreet: _showStreet,
          // 是否显示指示器
          showTabIndicator: _showTabIndicator,
          // tab 指示器颜色
          tabIndicatorColor: Theme.of(context).primaryColor,
          // tab 指示器高度
          tabIndicatorHeight: 2,
          // tab 字体大小
          labelTextSize: 15,
          // tab 选中的字体颜色
          selectedLabelColor: Theme.of(context).primaryColor,
          // tab 未选中的字体颜色
          unselectedLabelColor: Colors.black54,
          // 列表 item 头部高度
          itemHeadHeight: 30,
          // 列表 item 头部背景颜色
          itemHeadBackgroundColor: Colors.white,
          // 列表 item 头部分割线颜色
          itemHeadLineColor: Colors.black,
          // 列表 item 头部分割线高度
          itemHeadLineHeight: 0.1,
          // 列表 item 头部文字样式
          itemHeadTextStyle: TextStyle(fontSize: 15, color: Colors.black),
          // 列表 item 高度
          itemHeight: 40,
          // 索引组件宽度
          indexBarWidth: 28,
          // 索引组件 item 高度
          indexBarItemHeight: 20,
          // 索引组件背景颜色
          indexBarBackgroundColor: Colors.black12,
          // 索引组件文字样式
          indexBarTextStyle: TextStyle(fontSize: 14, color: Colors.black54),
          // 列表选中的图标组件
          itemSelectedIconWidget:
              Icon(Icons.done, color: Theme.of(context).primaryColor, size: 16),
          // 列表选中的文字样式
          itemSelectedTextStyle: TextStyle(
              fontSize: 14,
              fontWeight: FontWeight.bold,
              color: Theme.of(context).primaryColor),
          // 列表未选中的文字样式
          itemUnSelectedTextStyle: TextStyle(fontSize: 14, color: Colors.black54),
          cityPickerListener: this,
        );
  1. 监听事件
    <你的组件> implements CityPickerListener

    @override
    Future<List<City>> loadProvinceData() async {
      // 发起网络请求,获取省级数据
      return 返回省级数据;
    }

    @override
    Future<List<City>> onProvinceSelected(String provinceCode, String provinceName) async {
      // 点击省份后的回调,根据城市代码或名称去请求市级数据
      return 返回市级数据;
    }

    @override
    Future<List<City>> onCitySelected(String cityCode, String cityName) async {
      // 点击城市后的回调,根据城市代码或名称去请求区级数据
      return 返回区级数据;
    }

    @override
    Future<List<City>> onDistrictSelected(String districtCode, String districtName) {
      // 点击区后的回调,根据城市代码或名称去请求街道数据
      return 返回街道数据;
    }

    @override
    void onFinish(String provinceCode, String provinceName, String cityCode,
        String cityName, String districtCode, String districtName, String streetCode, String streetName) {
      // 最终回调,返回省市区的代码和名称
      setState(() {
        _address = provinceName + " " + cityName + " " + districtName + " " + streetName;
      });
    }

待优化

欢迎提 PR 或者 ISSUE

Use this package as a library

Depend on it

Run this command:

With Flutter:

 $ flutter pub add flutter_city_picker

This will add a line like this to your package's pubspec.yaml (and run an implicit flutter pub get):

dependencies:
  flutter_city_picker: ^1.0.4

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

Import it

Now in your Dart code, you can use:

import 'package:flutter_city_picker/city_picker.dart';
import 'package:flutter_city_picker/listener/item_listener.dart';
import 'package:flutter_city_picker/listener/picker_listener.dart';
import 'package:flutter_city_picker/model/city.dart';
import 'package:flutter_city_picker/model/section_city.dart';
import 'package:flutter_city_picker/model/tab.dart';
import 'package:flutter_city_picker/view/city_picker.dart';
import 'package:flutter_city_picker/view/inherited_widget.dart';
import 'package:flutter_city_picker/view/item_widget.dart';
import 'package:flutter_city_picker/view/layout_delegate.dart';
import 'package:flutter_city_picker/view/listview_section.dart';
import 'package:flutter_city_picker/view/popup_route.dart'; 

example/lib/main.dart

import 'dart:async';

import 'package:city_picker_example/http/http_util.dart';
import 'package:flutter/material.dart';
import 'package:flutter_city_picker/city_picker.dart';
import 'package:flutter_colorpicker/flutter_colorpicker.dart';
import 'package:provider/provider.dart';

import 'provider/theme_provider.dart';
import 'view/item_text.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MultiProvider(
      providers: [
        ChangeNotifierProvider.value(value: ThemeProvider()),
      ],
      child: Consumer<ThemeProvider>(
        builder: (context, themeProvider, _) {
          Color color = themeProvider.themeColor;
          return MaterialApp(
            title: 'CityPickerExample',
            debugShowCheckedModeBanner: false,
            theme: ThemeData(
              primaryColor: color,
              dialogBackgroundColor: Colors.white,
            ),
            home: HomeWidget(),
          );
        },
      ),
    );
  }
}

class HomeWidget extends StatefulWidget {
  @override
  HomeWidgetState createState() => HomeWidgetState();
}

class HomeWidgetState extends State<HomeWidget> implements CityPickerListener {
  String _address = "请选择地区";
  Color _themeColor = Colors.blue;
  Color _backgroundColor = Colors.white;
  double _height = 400.0;
  double _opacity = 0.5;
  double _corner = 20;
  bool _dismissible = true;
  bool _showTabIndicator = true;
  bool _showStreet = false;

  @override
  void initState() {
    super.initState();
  }

  void show() {
    CityPicker.show(
      context: context,
      theme: ThemeData(
        dialogBackgroundColor: _backgroundColor,
      ),
      duration: 200,
      opacity: _opacity,
      dismissible: _dismissible,
      height: _height,
      titleHeight: 50,
      corner: _corner,
      paddingLeft: 15,
      titleWidget: Container(
        padding: EdgeInsets.only(left: 15),
        child: Text(
          '请选择地址',
          style: TextStyle(
            color: Colors.black54,
            fontSize: 18,
            fontWeight: FontWeight.bold,
          ),
        ),
      ),
      closeWidget: Icon(Icons.close),
      tabHeight: 40,
      enableStreet: _showStreet,
      showTabIndicator: _showTabIndicator,
      tabIndicatorColor: Theme.of(context).primaryColor,
      tabIndicatorHeight: 2,
      labelTextSize: 15,
      selectedLabelColor: Theme.of(context).primaryColor,
      unselectedLabelColor: Colors.black54,
      itemHeadHeight: 30,
      itemHeadLineColor: Colors.black,
      itemHeadLineHeight: 0.1,
      itemHeadTextStyle: TextStyle(fontSize: 15, color: Colors.black),
      itemHeight: 40,
      indexBarWidth: 28,
      indexBarItemHeight: 20,
      indexBarBackgroundColor: Colors.black12,
      indexBarTextStyle: TextStyle(fontSize: 14, color: Colors.black54),
      itemSelectedIconWidget:
          Icon(Icons.done, color: Theme.of(context).primaryColor, size: 16),
      itemSelectedTextStyle: TextStyle(
          fontSize: 14,
          fontWeight: FontWeight.bold,
          color: Theme.of(context).primaryColor),
      itemUnSelectedTextStyle: TextStyle(fontSize: 14, color: Colors.black54),
      cityPickerListener: this,
    );
  }

  Widget _buildTheme() {
    return InkWell(
      onTap: () {
        showDialog(
          context: context,
          builder: (BuildContext context) {
            return AlertDialog(
              title: Text('选择颜色'),
              content: SingleChildScrollView(
                child: BlockPicker(
                  pickerColor: _themeColor,
                  onColorChanged: (color) {
                    setState(() {
                      _themeColor = color;
                    });
                    Provider.of<ThemeProvider>(context, listen: false)
                        .setTheme(color);
                  },
                ),
              ),
            );
          },
        );
      },
      child: Container(
        color: _themeColor,
        width: double.infinity,
        padding: EdgeInsets.all(10),
        margin: EdgeInsets.fromLTRB(80, 10, 80, 10),
      ),
    );
  }

  Widget _buildColor() {
    return InkWell(
      onTap: () {
        showDialog(
          context: context,
          builder: (BuildContext context) {
            return AlertDialog(
              title: Text('选择颜色'),
              content: SingleChildScrollView(
                child: BlockPicker(
                  pickerColor: _backgroundColor,
                  onColorChanged: (color) {
                    setState(() {
                      _backgroundColor = color;
                    });
                  },
                ),
              ),
            );
          },
        );
      },
      child: Container(
        color: _backgroundColor,
        width: double.infinity,
        padding: EdgeInsets.all(10),
        margin: EdgeInsets.fromLTRB(80, 10, 80, 10),
      ),
    );
  }

  Widget _buildOpacity() {
    return Row(
      children: <Widget>[
        Expanded(
          flex: 1,
          child: Slider(
            value: _opacity,
            min: 0.01,
            max: 1.0,
            divisions: 100,
            activeColor: Theme.of(context).primaryColor,
            inactiveColor: Colors.grey,
            onChanged: (double) {
              setState(() {
                _opacity = double.toDouble();
              });
            },
          ),
        ),
        Text("${_opacity.toStringAsFixed(2)}")
      ],
    );
  }

  Widget _buildDismissible() {
    return Container(
        alignment: Alignment.centerRight,
        child: Switch(
          value: _dismissible,
          activeColor: Theme.of(context).primaryColor,
          onChanged: (bool val) {
            setState(() {
              _dismissible = !_dismissible;
            });
          },
        ));
  }

  Widget _buildHeight() {
    return Row(
      children: <Widget>[
        Expanded(
          flex: 1,
          child: Slider(
            value: _height,
            min: 200,
            max: 500,
            divisions: 100,
            activeColor: Theme.of(context).primaryColor,
            inactiveColor: Colors.grey,
            onChanged: (double) {
              setState(() {
                _height = double.toDouble();
              });
            },
          ),
        ),
        Text("${_height.toStringAsFixed(2)}")
      ],
    );
  }

  Widget _buildCorner() {
    return Row(
      children: <Widget>[
        Expanded(
          flex: 1,
          child: Slider(
            value: _corner,
            min: 0.0,
            max: 30,
            divisions: 100,
            activeColor: Theme.of(context).primaryColor,
            inactiveColor: Colors.grey,
            onChanged: (double) {
              setState(() {
                _corner = double.toDouble();
              });
            },
          ),
        ),
        Text("${_corner.toStringAsFixed(2)}")
      ],
    );
  }

  Widget _buildIndicator() {
    return Container(
        alignment: Alignment.centerRight,
        child: Switch(
          value: _showTabIndicator,
          activeColor: Theme.of(context).primaryColor,
          onChanged: (bool val) {
            setState(() {
              _showTabIndicator = !_showTabIndicator;
            });
          },
        ));
  }

  Widget _buildStreet() {
    return Container(
        alignment: Alignment.centerRight,
        child: Switch(
          value: _showStreet,
          activeColor: Theme.of(context).primaryColor,
          onChanged: (bool val) {
            setState(() {
              _showStreet = !_showStreet;
            });
          },
        ));
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('城市选择器'),
        backgroundColor: Theme.of(context).primaryColor,
      ),
      body: SingleChildScrollView(
        child: Column(
          children: [
            ItemTextWidget(
              title: '选择城市',
              subWidget: InkWell(
                onTap: () => show(),
                child: Padding(
                  padding: EdgeInsets.fromLTRB(0, 15, 0, 15),
                  child: Text(_address),
                ),
              ),
            ),
            ItemTextWidget(title: '主题颜色', subWidget: _buildTheme()),
            ItemTextWidget(title: '透明度', subWidget: _buildOpacity()),
            ItemTextWidget(title: '外部点击消失', subWidget: _buildDismissible()),
            ItemTextWidget(title: '弹窗背景颜色', subWidget: _buildColor()),
            ItemTextWidget(title: '弹窗高度', subWidget: _buildHeight()),
            ItemTextWidget(title: '顶部圆角', subWidget: _buildCorner()),
            ItemTextWidget(title: '显示 Indicator', subWidget: _buildIndicator()),
            ItemTextWidget(title: '开启第四级街道', subWidget: _buildStreet()),
          ],
        ),
      ),
    );
  }

  @override
  Future<List<City>> loadProvinceData() async {
    print("loadProvinceData");
    return HttpUtils.getCityData("");
  }

  @override
  Future<List<City>> onProvinceSelected(
      String? provinceCode, String? provinceName) async {
    print("onProvinceSelected --- provinceName: $provinceName");
    return HttpUtils.getCityData(provinceName!);
  }

  @override
  Future<List<City>> onCitySelected(String? cityCode, String? cityName) async {
    print("onCitySelected --- cityName: $cityName");
    return HttpUtils.getCityData(cityName!);
  }

  @override
  Future<List<City>> onDistrictSelected(
      String? districtCode, String? districtName) {
    print("onDistrictSelected --- districtName: $districtName");
    return HttpUtils.getCityData(districtName!);
  }

  @override
  void onFinish(
      String? provinceCode,
      String? provinceName,
      String? cityCode,
      String? cityName,
      String? districtCode,
      String? districtName,
      String? streetCode,
      String? streetName) {
    print("onFinish");
    setState(() {
      _address = provinceName! +
          " " +
          cityName! +
          " " +
          districtName! +
          " " +
          streetName!;
    });
  }
} 

Download Details:

Author: wenchaosong

Source Code: https://github.com/wenchaosong/FlutterCityPicker

#flutter #Picker #widgets 

Flutter Plugin for City Picker, Address Picker, Popups Widgets