mirror of
				https://gitlab.com/comunic/comunicmobile
				synced 2025-11-03 19:54:12 +00:00 
			
		
		
		
	Can create posts
This commit is contained in:
		
							
								
								
									
										205
									
								
								lib/ui/widgets/post_create_form_widget.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										205
									
								
								lib/ui/widgets/post_create_form_widget.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,205 @@
 | 
			
		||||
import 'dart:io';
 | 
			
		||||
 | 
			
		||||
import 'package:comunic/enums/post_kind.dart';
 | 
			
		||||
import 'package:comunic/enums/post_target.dart';
 | 
			
		||||
import 'package:comunic/enums/post_visibility_level.dart';
 | 
			
		||||
import 'package:comunic/helpers/posts_helper.dart';
 | 
			
		||||
import 'package:comunic/models/new_post.dart';
 | 
			
		||||
import 'package:comunic/utils/files_utils.dart';
 | 
			
		||||
import 'package:comunic/utils/intl_utils.dart';
 | 
			
		||||
import 'package:comunic/utils/post_utils.dart';
 | 
			
		||||
import 'package:comunic/utils/ui_utils.dart';
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
 | 
			
		||||
/// Widget that allows to create posts
 | 
			
		||||
///
 | 
			
		||||
/// @author Pierre HUBERT
 | 
			
		||||
 | 
			
		||||
const _ActiveButtonsColor = Colors.blue;
 | 
			
		||||
const _ActiveButtonsTextColor = Colors.white;
 | 
			
		||||
const _InactiveButtonsColor = Colors.grey;
 | 
			
		||||
const _InactiveButtonsTextColor = Colors.black;
 | 
			
		||||
 | 
			
		||||
class PostCreateFormWidget extends StatefulWidget {
 | 
			
		||||
  final PostTarget postTarget;
 | 
			
		||||
  final int targetID;
 | 
			
		||||
  final void Function() onCreated;
 | 
			
		||||
 | 
			
		||||
  const PostCreateFormWidget({
 | 
			
		||||
    Key key,
 | 
			
		||||
    @required this.postTarget,
 | 
			
		||||
    @required this.targetID,
 | 
			
		||||
    @required this.onCreated,
 | 
			
		||||
  })  : assert(postTarget != null),
 | 
			
		||||
        assert(targetID != null),
 | 
			
		||||
        super(key: key);
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  _PostCreateFormWidgetState createState() => _PostCreateFormWidgetState();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class _PostCreateFormWidgetState extends State<PostCreateFormWidget> {
 | 
			
		||||
  // Helpers
 | 
			
		||||
  final PostsHelper _postHelper = PostsHelper();
 | 
			
		||||
 | 
			
		||||
  // Class members
 | 
			
		||||
  bool _isCreating = false;
 | 
			
		||||
  final TextEditingController _postTextController = TextEditingController();
 | 
			
		||||
  PostVisibilityLevel _postVisibilityLevel;
 | 
			
		||||
  File _postImage;
 | 
			
		||||
 | 
			
		||||
  bool get hasImage => _postImage != null;
 | 
			
		||||
 | 
			
		||||
  bool get canSubmitForm =>
 | 
			
		||||
      !_isCreating && _postTextController.text.length > 5 || hasImage;
 | 
			
		||||
 | 
			
		||||
  PostKind get postKind {
 | 
			
		||||
    if (hasImage)
 | 
			
		||||
      return PostKind.IMAGE;
 | 
			
		||||
    else
 | 
			
		||||
      return PostKind.TEXT;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  void initState() {
 | 
			
		||||
    super.initState();
 | 
			
		||||
 | 
			
		||||
    _postVisibilityLevel = widget.postTarget == PostTarget.GROUP_PAGE
 | 
			
		||||
        ? PostVisibilityLevel.GROUP_MEMBERS
 | 
			
		||||
        : PostVisibilityLevel.FRIENDS;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  Widget build(BuildContext context) {
 | 
			
		||||
    return Column(
 | 
			
		||||
      children: <Widget>[
 | 
			
		||||
        // Post text content
 | 
			
		||||
        TextField(
 | 
			
		||||
          controller: _postTextController,
 | 
			
		||||
          minLines: 3,
 | 
			
		||||
          maxLines: 10,
 | 
			
		||||
          decoration: InputDecoration(hintText: tr("Create a new post...")),
 | 
			
		||||
          onChanged: (s) => setState(() {}),
 | 
			
		||||
        ),
 | 
			
		||||
 | 
			
		||||
        // Post options
 | 
			
		||||
        Padding(
 | 
			
		||||
          padding: const EdgeInsets.only(right: 16.0),
 | 
			
		||||
          child: Row(
 | 
			
		||||
            mainAxisAlignment: MainAxisAlignment.spaceBetween,
 | 
			
		||||
            children: <Widget>[
 | 
			
		||||
              // Include image button
 | 
			
		||||
              _PostOptionWidget(
 | 
			
		||||
                icon: Icons.image,
 | 
			
		||||
                selected: hasImage,
 | 
			
		||||
                onTap: _pickImageForPost,
 | 
			
		||||
              ),
 | 
			
		||||
 | 
			
		||||
              // Post visibility level
 | 
			
		||||
              _PostOptionWidget(
 | 
			
		||||
                icon: PostVisibilityLevelsMapIcons[_postVisibilityLevel],
 | 
			
		||||
                selected: false,
 | 
			
		||||
                customColor: Colors.black,
 | 
			
		||||
                onTap: _changeVisibilityLevel,
 | 
			
		||||
              ),
 | 
			
		||||
 | 
			
		||||
              // Submit post button
 | 
			
		||||
              _isCreating
 | 
			
		||||
                  ? Container()
 | 
			
		||||
                  : FlatButton(
 | 
			
		||||
                      child: Text(tr("Send").toUpperCase()),
 | 
			
		||||
                      onPressed: canSubmitForm ? _submitForm : null,
 | 
			
		||||
                      color: _ActiveButtonsColor,
 | 
			
		||||
                      textColor: _ActiveButtonsTextColor,
 | 
			
		||||
                      disabledColor: _InactiveButtonsColor,
 | 
			
		||||
                      disabledTextColor: _InactiveButtonsTextColor,
 | 
			
		||||
                    ),
 | 
			
		||||
            ],
 | 
			
		||||
          ),
 | 
			
		||||
        )
 | 
			
		||||
      ],
 | 
			
		||||
    );
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /// Change post visibility level
 | 
			
		||||
  Future<void> _changeVisibilityLevel() async {
 | 
			
		||||
    final newLevel = await showPostVisibilityPicker(
 | 
			
		||||
      context: context,
 | 
			
		||||
      initialLevel: _postVisibilityLevel,
 | 
			
		||||
      isGroup: widget.postTarget == PostTarget.GROUP_PAGE,
 | 
			
		||||
    );
 | 
			
		||||
 | 
			
		||||
    setState(() => _postVisibilityLevel = newLevel);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /// Pick an image for the new post
 | 
			
		||||
  Future<void> _pickImageForPost() async {
 | 
			
		||||
    final image = await pickImage(context);
 | 
			
		||||
 | 
			
		||||
    if (image == null) return;
 | 
			
		||||
 | 
			
		||||
    setState(() {
 | 
			
		||||
      this._postImage = image;
 | 
			
		||||
    });
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  /// Submit new post
 | 
			
		||||
  Future<void> _submitForm() async {
 | 
			
		||||
    if (!canSubmitForm)
 | 
			
		||||
      showSimpleSnack(context, tr("Form can not be submitted at this point!"));
 | 
			
		||||
 | 
			
		||||
    setState(() => _isCreating = true);
 | 
			
		||||
 | 
			
		||||
    try {
 | 
			
		||||
      await _postHelper.createPost(NewPost(
 | 
			
		||||
        target: widget.postTarget,
 | 
			
		||||
        targetID: widget.targetID,
 | 
			
		||||
        visibility: _postVisibilityLevel,
 | 
			
		||||
        content: _postTextController.text,
 | 
			
		||||
        kind: postKind,
 | 
			
		||||
        image: _postImage,
 | 
			
		||||
      ));
 | 
			
		||||
      setState(() => _isCreating = false);
 | 
			
		||||
 | 
			
		||||
      showSimpleSnack(context, tr("The post has been successfully created!"));
 | 
			
		||||
 | 
			
		||||
      widget.onCreated();
 | 
			
		||||
    } catch (e) {
 | 
			
		||||
      setState(() => _isCreating = false);
 | 
			
		||||
      print("Error while creating post : " + e.toString());
 | 
			
		||||
      showSimpleSnack(context, tr("Could not create post !"));
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/// Widget for a single post option
 | 
			
		||||
class _PostOptionWidget extends StatelessWidget {
 | 
			
		||||
  final IconData icon;
 | 
			
		||||
  final bool selected;
 | 
			
		||||
  final Color customColor;
 | 
			
		||||
  final void Function() onTap;
 | 
			
		||||
 | 
			
		||||
  const _PostOptionWidget(
 | 
			
		||||
      {Key key,
 | 
			
		||||
      @required this.icon,
 | 
			
		||||
      @required this.selected,
 | 
			
		||||
      @required this.onTap,
 | 
			
		||||
      this.customColor})
 | 
			
		||||
      : assert(icon != null),
 | 
			
		||||
        assert(selected != null),
 | 
			
		||||
        assert(onTap != null),
 | 
			
		||||
        super(key: key);
 | 
			
		||||
 | 
			
		||||
  bool get hasCustomColor => customColor != null;
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  Widget build(BuildContext context) {
 | 
			
		||||
    return IconButton(
 | 
			
		||||
      icon: Icon(icon),
 | 
			
		||||
      onPressed: onTap,
 | 
			
		||||
      color: hasCustomColor
 | 
			
		||||
          ? customColor
 | 
			
		||||
          : selected ? _ActiveButtonsColor : _InactiveButtonsColor,
 | 
			
		||||
    );
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
		Reference in New Issue
	
	Block a user