Explorar el Código

Merge remote-tracking branch 'origin/master'

# Conflicts:
#	lib/chat/ChatPage.dart
#	lib/chat/ChatPageItem.dart
#	lib/chat/input_bar.dart
#	lib/utils/CustomUI.dart
#	lib/utils/HttpUtil.dart
master
jiahao hace 5 años
padre
commit
434c2c5d72
Se han modificado 27 ficheros con 652 adiciones y 376 borrados
  1. +1
    -1
      .flutter-plugins-dependencies
  2. +62
    -24
      lib/chat/ChatPage.dart
  3. +203
    -120
      lib/chat/ChatPageItem.dart
  4. +0
    -3
      lib/chat/company_server_view.dart
  5. +202
    -127
      lib/chat/group_chat_item.dart
  6. +47
    -32
      lib/chat/group_chat_view.dart
  7. +20
    -11
      lib/chat/input_bar.dart
  8. +0
    -1
      lib/chat/translate_state.dart
  9. +2
    -0
      lib/data/UserData.dart
  10. +1
    -11
      lib/data/translate_hk_data_mgr.dart
  11. +0
    -3
      lib/home/AddProgram.dart
  12. +0
    -3
      lib/home/InformUser.dart
  13. +0
    -3
      lib/home/ProfilePage.dart
  14. +1
    -3
      lib/home/homeMain.dart
  15. +0
    -14
      lib/home/realtimehelper/translation_butler_page.dart
  16. +0
    -3
      lib/home/realtimehelper/translation_evaluation_dialog.dart
  17. +1
    -0
      lib/main.dart
  18. +11
    -0
      lib/utils/CustomUI.dart
  19. +31
    -3
      lib/utils/HttpUtil.dart
  20. +1
    -4
      lib/utils/count_down_button.dart
  21. +0
    -1
      lib/utils/file_cache_mgr.dart
  22. +0
    -1
      lib/utils/image_util.dart
  23. +1
    -3
      lib/utils/msgHandler.dart
  24. +0
    -1
      lib/utils/screen_shot.dart
  25. +52
    -0
      lib/utils/white_opacity_anim.dart
  26. +12
    -3
      pubspec.lock
  27. +4
    -1
      pubspec.yaml

+ 1
- 1
.flutter-plugins-dependencies Ver fichero

@@ -1 +1 @@
{"_info":"// This is a generated file; do not edit or check into version control.","dependencyGraph":[{"name":"agora_rtc_engine","dependencies":[]},{"name":"amap_location","dependencies":[]},{"name":"android_intent","dependencies":[]},{"name":"app_installer","dependencies":[]},{"name":"apple_sign_in","dependencies":[]},{"name":"audioplayer","dependencies":[]},{"name":"auto_orientation","dependencies":[]},{"name":"city_pickers","dependencies":[]},{"name":"connectivity","dependencies":[]},{"name":"easy_contact_picker","dependencies":[]},{"name":"file_picker","dependencies":[]},{"name":"flutter_app_badger","dependencies":[]},{"name":"flutter_audio_recorder","dependencies":[]},{"name":"flutter_bugly","dependencies":[]},{"name":"flutter_facebook_login","dependencies":[]},{"name":"flutter_ijkplayer","dependencies":[]},{"name":"flutter_inapp_purchase","dependencies":[]},{"name":"flutter_local_notifications","dependencies":[]},{"name":"flutter_native_image","dependencies":[]},{"name":"flutter_plugin_android_lifecycle","dependencies":[]},{"name":"flutter_qr_reader","dependencies":["image_picker"]},{"name":"flutter_webview_plugin","dependencies":[]},{"name":"fluwx_no_pay","dependencies":[]},{"name":"geolocator","dependencies":["google_api_availability","location_permissions"]},{"name":"google_api_availability","dependencies":[]},{"name":"google_maps_flutter","dependencies":[]},{"name":"image_cropper","dependencies":[]},{"name":"image_gallery_saver","dependencies":[]},{"name":"image_picker","dependencies":["flutter_plugin_android_lifecycle"]},{"name":"jpush_flutter","dependencies":[]},{"name":"keyboard_utils","dependencies":[]},{"name":"location","dependencies":[]},{"name":"location_permissions","dependencies":[]},{"name":"multi_image_picker","dependencies":[]},{"name":"open_file","dependencies":[]},{"name":"package_info","dependencies":[]},{"name":"path_provider","dependencies":[]},{"name":"permission_handler","dependencies":[]},{"name":"photo_manager","dependencies":[]},{"name":"receive_sharing_intent","dependencies":[]},{"name":"share","dependencies":[]},{"name":"share_extend","dependencies":[]},{"name":"shared_preferences","dependencies":["shared_preferences_macos","shared_preferences_web"]},{"name":"shared_preferences_macos","dependencies":[]},{"name":"shared_preferences_web","dependencies":[]},{"name":"sqflite","dependencies":[]},{"name":"url_launcher","dependencies":[]},{"name":"video_player","dependencies":[]},{"name":"video_thumbnail","dependencies":[]},{"name":"wifi_info_plugin","dependencies":[]}]}
{"_info":"// This is a generated file; do not edit or check into version control.","dependencyGraph":[{"name":"agora_rtc_engine","dependencies":[]},{"name":"amap_location","dependencies":[]},{"name":"android_intent","dependencies":[]},{"name":"app_installer","dependencies":[]},{"name":"apple_sign_in","dependencies":[]},{"name":"audioplayer","dependencies":[]},{"name":"auto_orientation","dependencies":[]},{"name":"city_pickers","dependencies":[]},{"name":"connectivity","dependencies":[]},{"name":"device_info","dependencies":[]},{"name":"easy_contact_picker","dependencies":[]},{"name":"file_picker","dependencies":[]},{"name":"flutter_app_badger","dependencies":[]},{"name":"flutter_audio_recorder","dependencies":[]},{"name":"flutter_bugly","dependencies":[]},{"name":"flutter_facebook_login","dependencies":[]},{"name":"flutter_ijkplayer","dependencies":[]},{"name":"flutter_inapp_purchase","dependencies":[]},{"name":"flutter_local_notifications","dependencies":[]},{"name":"flutter_native_image","dependencies":[]},{"name":"flutter_plugin_android_lifecycle","dependencies":[]},{"name":"flutter_qr_reader","dependencies":["image_picker"]},{"name":"flutter_webview_plugin","dependencies":[]},{"name":"fluwx_no_pay","dependencies":[]},{"name":"geolocator","dependencies":["google_api_availability","location_permissions"]},{"name":"google_api_availability","dependencies":[]},{"name":"google_maps_flutter","dependencies":[]},{"name":"image_cropper","dependencies":[]},{"name":"image_gallery_saver","dependencies":[]},{"name":"image_picker","dependencies":["flutter_plugin_android_lifecycle"]},{"name":"jpush_flutter","dependencies":[]},{"name":"keyboard_utils","dependencies":[]},{"name":"location","dependencies":[]},{"name":"location_permissions","dependencies":[]},{"name":"multi_image_picker","dependencies":[]},{"name":"open_file","dependencies":[]},{"name":"package_info","dependencies":[]},{"name":"path_provider","dependencies":[]},{"name":"permission_handler","dependencies":[]},{"name":"photo_manager","dependencies":[]},{"name":"receive_sharing_intent","dependencies":[]},{"name":"share","dependencies":[]},{"name":"share_extend","dependencies":[]},{"name":"shared_preferences","dependencies":["shared_preferences_macos","shared_preferences_web"]},{"name":"shared_preferences_macos","dependencies":[]},{"name":"shared_preferences_web","dependencies":[]},{"name":"sqflite","dependencies":[]},{"name":"url_launcher","dependencies":[]},{"name":"video_player","dependencies":[]},{"name":"video_thumbnail","dependencies":[]},{"name":"wifi_info_plugin","dependencies":[]}]}

+ 62
- 24
lib/chat/ChatPage.dart Ver fichero

@@ -4,6 +4,7 @@ import 'package:chat/data/translate_hk_data_mgr.dart';
import 'package:chat/home/audio_chat_view.dart';
import 'package:chat/utils/screen.dart';
import 'package:chat/utils/upload_util.dart';
import 'package:chat/utils/white_opacity_anim.dart';
import 'package:fixnum/fixnum.dart';
import 'package:cached_network_image/cached_network_image.dart';
import 'package:chat/chat/translate_state.dart';
@@ -63,7 +64,10 @@ class ChatPage extends StatefulWidget {
}
class _ChatPageState extends State<ChatPage> {
ScrollController _scrollCtrl = ScrollController();
final ItemScrollController itemScrollController = ItemScrollController();
final ItemPositionsListener itemPositionListener =
ItemPositionsListener.create();
//ScrollController _scrollCtrl = ScrollController();
MessageMgr msgMgr = MessageMgr();
@@ -82,6 +86,8 @@ class _ChatPageState extends State<ChatPage> {
bool isTranslateButlerFinish=false;///翻译管家是否已经结束
int jumpTime;
@override
void dispose() {
var endTime = DateTime.now().millisecondsSinceEpoch ~/ 1000;
@@ -92,14 +98,36 @@ class _ChatPageState extends State<ChatPage> {
msgMgr.off('Keyboard Hide', dealWithKeyboardHide);
msgMgr.off('Delete Select Message', _deleteItem);
msgMgr.off(MessageMgr.TRANSLATE_HK_END_CHAT, translateHKChatEnd);
msgMgr.off('Jump to Msg', jumpToMsg);
MsgHandler.curActiveSession = 0;
SoundUtils().stop();
nickNameController.dispose();
_scrollCtrl.dispose();
super.dispose();
}
jumpToMsg(time) {
//var screenItemNums = itemPositionListener.itemPositions.value.length;
int jumIndex = 0;
jumpTime = time;
for (int i = 0; i < msgList.length; i++) {
if (time == msgList[i].time) {
jumIndex = i - 1; // - screenItemNums + 2;
break;
}
}
if (jumIndex < 0) {
jumIndex = 0;
}
if (jumIndex > msgList.length - 1) {
jumIndex = msgList.length - 1;
}
setState(() {
itemScrollController.scrollTo(
index: jumIndex, duration: new Duration(microseconds: 1));
});
}
@override
void initState() {
super.initState();
@@ -119,12 +147,14 @@ class _ChatPageState extends State<ChatPage> {
msgMgr.on('Send CoinBag', _sendCoin);
msgMgr.on('Delete Select Message', _deleteItem);
msgMgr.on(MessageMgr.TRANSLATE_HK_END_CHAT, translateHKChatEnd);
msgMgr.on('Jump to Msg', jumpToMsg);
}
translateHKChatEnd(args){
setState(() {
isTranslateButlerFinish=true;
});
}
void _sendFile(File file) async {
@@ -507,8 +537,7 @@ class _ChatPageState extends State<ChatPage> {
Widget zoomAudioButton() {
if (friendInfo == null || !isShowZoomButton || isTranslateButlerFinish) {
if (friendInfo == null || !isShowZoomButton) {
return Container();
}
@@ -645,13 +674,15 @@ class _ChatPageState extends State<ChatPage> {
))
: NotificationListener(
child: Scrollbar(
child: ListView.builder(
reverse: true,
shrinkWrap: true,
child: ScrollablePositionedList.builder(
physics: new ClampingScrollPhysics(),
itemCount: msgList.length,
controller: _scrollCtrl,
padding: EdgeInsets.all(8.0),
itemBuilder: _buildItem,
itemScrollController: itemScrollController,
itemPositionsListener: itemPositionListener,
//padding: EdgeInsets.all(8.0),
reverse: true,
hitCallback: hideKeyBoard,
)),
onNotification: (notification) {
if (notification is ScrollNotification) {
@@ -690,12 +721,8 @@ class _ChatPageState extends State<ChatPage> {
MsgHandler.sendChatMsg(msg);
if (mounted) {
setState(() {});
if (_scrollCtrl.hasClients) {
_scrollCtrl.animateTo(0,
duration: new Duration(milliseconds: 500), curve: Curves.ease);
}
itemScrollController.jumpTo(index: 0);
}
// testBig(msg);
}
MsgModel msg;
@@ -719,10 +746,6 @@ class _ChatPageState extends State<ChatPage> {
void receiveMsg(args) {
if (mounted) {
setState(() {});
if (_scrollCtrl.hasClients) {
_scrollCtrl.animateTo(0,
duration: new Duration(milliseconds: 500), curve: Curves.ease);
}
}
}
@@ -741,11 +764,26 @@ class _ChatPageState extends State<ChatPage> {
}
MsgModel msg = msgList[index];
return ChatPageItem(
if (msg.time == jumpTime) {
return WhiteOpacityAnim(
key: Key(msg.time.toString()),
msg: msg,
hideKeyboard: readOnly,
friendInfo: friendInfo,
lastMsgTime: lastMsgTime);
child: ChatPageItem(
key: Key(msg.time.toString()),
msg: msg,
hideKeyboard: readOnly,
friendInfo: friendInfo,
lastMsgTime: lastMsgTime),
animFinishCallback: () {
jumpTime = null;
},
);
} else {
return ChatPageItem(
key: Key(msg.time.toString()),
msg: msg,
hideKeyboard: readOnly,
friendInfo: friendInfo,
lastMsgTime: lastMsgTime);
}
}
}

+ 203
- 120
lib/chat/ChatPageItem.dart Ver fichero

@@ -90,6 +90,8 @@ class _ChatPageItemState extends State<ChatPageItem>
CancelToken _cancelToken = CancelToken();
bool isLongPressed = false;
double maxWidth = Screen.width - 140;
@override
void initState() {
super.initState();
@@ -146,10 +148,10 @@ class _ChatPageItemState extends State<ChatPageItem>
}
}
getTodayTime(msgDate) {
getTodayTime(msgDate, {var sendTime}) {
String showTimeStr;
var sendTime = widget.msg.time;
sendTime = sendTime ?? widget.msg.time;
var today = DateTime.now();
//今天
if (msgDate.year == today.year &&
@@ -188,7 +190,7 @@ class _ChatPageItemState extends State<ChatPageItem>
return Container(
width: Screen.width,
margin: const EdgeInsets.symmetric(vertical: 10.0),
margin: const EdgeInsets.symmetric(vertical: 18.0,horizontal: 8),
child: Column(
children: <Widget>[
showTime == null
@@ -258,6 +260,7 @@ class _ChatPageItemState extends State<ChatPageItem>
} else {
///todo 翻译管家系统通知消息
print('这里应该要有翻译管家');
if (type == ChatType.GroupChatNoticeType.value && widget.msg.channelType ==ChatChannelType.Session.value) {
TransHKChatNotice res = TransHKChatNotice.fromBuffer(widget.msg.msgContent);
@@ -312,55 +315,100 @@ class _ChatPageItemState extends State<ChatPageItem>
}
_textMsg(List<int> msgContent) {
List<Widget> showMsg = [];
var width = 0.0;
var msg = utf8.decode(msgContent);
bool isUrl =false;
if(textList[curTextType].contains('http') ){
isUrl =true;
if (msg.contains('[ ')) {
msg = msg.replaceAll('[ ', '[');
}
if (msg.contains(' ]')) {
msg = msg.replaceAll(' ]', ']');
}
bool isUrl = false;
if (textList[curTextType].contains('http')) {
isUrl = true;
}
if (widget.msg.refMsgContent != null &&
widget.msg.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(widget.msg.refMsgContent);
var refName = Provider.of<RefNameProvider>(context)
.getRefName(friendInfo.userId, friendInfo.nickName);
var msgDate =
DateTime.fromMillisecondsSinceEpoch(quoteMsg.sendTime.toInt());
var showTimeStr = getTodayTime(msgDate, sendTime: quoteMsg.sendTime.toInt());
var timetWidth = CustomUI.getRealTextWidht(showTimeStr, 13);
var nameWidhth = CustomUI.getRealTextWidht(refName, 13);
width = timetWidth + (nameWidhth > 70 ? 70 : nameWidhth) + 36;
var tempIndex = quoteMsg.content.indexOf(':');
var quoteContent = tempIndex == -1
? quoteMsg.content
: quoteMsg.content.substring(quoteMsg.content.indexOf(':') + 2);
var contentWidht = _getTextWidth(quoteContent, fontSize: 13);
width = min(max(width, contentWidht), maxWidth);
showMsg.add(InkWell(
onTap: () {
MessageMgr().emit('Jump to Msg', quoteMsg.sendTime.toInt());
},
child: Container(
padding: EdgeInsets.all(8),
margin: EdgeInsets.only(bottom: 5),
decoration: BoxDecoration(
color: Color(0xFFC4E0F5),
borderRadius: BorderRadius.circular(5.5)),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Row(children: <Widget>[
Container(
constraints: BoxConstraints(maxWidth: 70),
child: Text(
refName,
style: TextStyle(fontSize: 13),
overflow: TextOverflow.ellipsis,
)),
SizedBox(width: 20),
Text(
showTimeStr,
style: TextStyle(fontSize: 13),
)
]),
SizedBox(height: 7.5),
Text(
quoteContent,
style: TextStyle(fontSize: 13),
)
],
),
)));
}
Widget text = Container(
var contentWidth = _getTextWidth(textList[curTextType]);
if (contentWidth > width && contentWidth <= maxWidth) {
width = contentWidth;
}
showMsg.add(Container(
constraints: BoxConstraints(maxWidth: maxWidth, minHeight: 22),
alignment: Alignment.centerLeft,
child: extendedText(
textList[curTextType],
color: isUrl ? Colors.blue : Constants.BlackTextColor,
hideKeyboard: widget.hideKeyboard,
fontSize: FontSize,
)));
return Container(
constraints: BoxConstraints(maxWidth: Screen.width - 120),
child: extendedText(
msg,
hideKeyboard: widget.hideKeyboard,
fontSize: FontSize,
color: isUrl?Colors.blue:Colors.black,
),
width: width + 20,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start, children: showMsg),
padding: EdgeInsets.symmetric(horizontal: 9, vertical: 10.5),
decoration: BoxDecoration(
color: isLongPressed ? Colors.grey[300] : SendMsgBg,
border: Border.all(color: Color(0xFFB9CBD7), width: 0.6),
borderRadius: BorderRadius.all(Radius.circular(ChatRadius))),
);
if (widget.msg.refMsgContent != null &&
widget.msg.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(widget.msg.refMsgContent);
return Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.end,
children: <Widget>[
text,
SizedBox(height: 2),
Container(
constraints: BoxConstraints(maxWidth: Screen.width - 120),
padding: EdgeInsets.symmetric(vertical: 1, horizontal: 3),
child: Text(
quoteMsg.content,
maxLines: 1,
textScaleFactor: 1.0,
overflow: TextOverflow.ellipsis,
style: TextStyle(fontSize: 12),
),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(5)),
)
],
);
} else {
return text;
}
}
_soundMsg() {
@@ -503,7 +551,9 @@ class _ChatPageItemState extends State<ChatPageItem>
_imgMsg(List<int> imgData) {
var imgSize = _getImgSize();
ImageProvider provider = MemoryImage(widget.msg.localFile==null?Uint8List.fromList(imgData):File(widget.msg.localFile).readAsBytesSync());
ImageProvider provider = MemoryImage(widget.msg.localFile == null
? Uint8List.fromList(imgData)
: File(widget.msg.localFile).readAsBytesSync());
return GestureDetector(
child: ClipRRect(
@@ -663,43 +713,42 @@ class _ChatPageItemState extends State<ChatPageItem>
///转发
if (widget.msg.msgType == ChatType.TextChatType.value||
widget.msg.msgType == ChatType.ImageChatType.value||
widget.msg.msgType == ChatType.ShortVideoChatType.value||
widget.msg.msgType == ChatType.PlaceChatType.value||
widget.msg.msgType == ChatType.EmoticonType.value||
widget.msg.msgType == ChatType.FileChatType.value
){
actions.add( I18n.of(context).forward);
if (widget.msg.msgType == ChatType.TextChatType.value ||
widget.msg.msgType == ChatType.ImageChatType.value ||
widget.msg.msgType == ChatType.ShortVideoChatType.value ||
widget.msg.msgType == ChatType.PlaceChatType.value ||
widget.msg.msgType == ChatType.EmoticonType.value ||
widget.msg.msgType == ChatType.FileChatType.value) {
actions.add(I18n.of(context).forward);
actionsFunc.add(() {
print('转发消息');
if(widget.msg.msgType == ChatType.FileChatType.value && widget.msg.localFile==null){
if (widget.msg.msgType == ChatType.FileChatType.value &&
widget.msg.localFile == null) {
showToast('请先下载文件');
return ;
return;
}
AppNavigator.pushForwardPage(context, widget.msg);
});
}
if (widget.msg.msgType == ChatType.FileChatType.value &&widget.msg.localFile!=null) {
if (widget.msg.msgType == ChatType.FileChatType.value &&
widget.msg.localFile != null) {
//分享文件
actions.add(I18n.of(context).copy_download_url);
actionsFunc.add(() async{
actionsFunc.add(() async {
UploadUtil().copyFileUrl(widget.msg, context);
String path = widget.msg.localFile;
String type='file';
if(path.contains('mp4') ||path.contains('mp3')){
String type = 'file';
if (path.contains('mp4') || path.contains('mp3')) {
type = 'video';
}else if(path.contains('png')||path.contains('jpg')||path.contains('jpeg')||path.contains('JPG')||path.contains('PNG')){
} else if (path.contains('png') ||
path.contains('jpg') ||
path.contains('jpeg') ||
path.contains('JPG') ||
path.contains('PNG')) {
type = 'image';
}
@@ -735,18 +784,17 @@ class _ChatPageItemState extends State<ChatPageItem>
});
}
// String date2 = DateTime.fromMillisecondsSinceEpoch(widget.msg.time).toString();
bool isUrl =false;
if(widget.msg.msgType==ChatType.TextChatType.value ){
if( textList[curTextType].contains('http')){
isUrl =true;
bool isUrl = false;
if (widget.msg.msgType == ChatType.TextChatType.value) {
if (textList[curTextType].contains('http')) {
isUrl = true;
}
}
return WPopupMenu(
return WPopupMenu(
child: item,
actions: actions,
onTap: ()async{
if(isUrl){
onTap: () async {
if (isUrl) {
if (await canLaunch(textList[curTextType])) {
launch(textList[curTextType]);
}
@@ -783,9 +831,9 @@ class _ChatPageItemState extends State<ChatPageItem>
return extendedText(text, hideKeyboard: widget.hideKeyboard);
}
double _getTextWidth(String text) {
double _getTextWidth(String text, {double fontSize: FontSize}) {
var tp = TextPainter(
text: TextSpan(style: TextStyle(fontSize: FontSize), text: text),
text: TextSpan(style: TextStyle(fontSize: fontSize), text: text),
textAlign: TextAlign.left,
textDirection: TextDirection.ltr,
textScaleFactor: 1,
@@ -812,11 +860,70 @@ class _ChatPageItemState extends State<ChatPageItem>
_receiveText(MsgModel msg) {
List<Widget> showMsg = [];
double width = 0.0;
if (textList.length > 0) {
bool isUrl = false;
if (textList[curTextType].contains('http')) {
isUrl = true;
}
if (msg.refMsgContent != null && msg.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(msg.refMsgContent);
var refName = Provider.of<RefNameProvider>(context)
.getGroupRefName(msg.sessionId, quoteMsg.sendUserId);
var msgDate =
DateTime.fromMillisecondsSinceEpoch(quoteMsg.sendTime.toInt());
var showTimeStr = getTodayTime(msgDate, sendTime: quoteMsg.sendTime.toInt());
bool isUrl =false;
if(textList[curTextType].contains('http') ){
isUrl =true;
var timetWidth = CustomUI.getRealTextWidht(showTimeStr, 13);
var nameWidhth = CustomUI.getRealTextWidht(refName, 13);
width = timetWidth + (nameWidhth > 70 ? 70 : nameWidhth) + 36;
var quoteContent =
quoteMsg.content.substring(quoteMsg.content.indexOf(':') + 2);
var contentWidht = _getTextWidth(quoteContent, fontSize: 13);
width = min(max(width, contentWidht), maxWidth);
showMsg.add(InkWell(
onTap: () {
MessageMgr().emit('Jump to Msg', quoteMsg.sendTime.toInt());
},
child: Container(
padding: EdgeInsets.all(8),
margin: EdgeInsets.only(bottom: 5),
decoration: BoxDecoration(
color: Color(0xFFC4E0F5),
borderRadius: BorderRadius.circular(5.5)),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Row(children: <Widget>[
Container(
constraints: BoxConstraints(maxWidth: 70),
child: Text(
refName,
style: TextStyle(fontSize: 13),
overflow: TextOverflow.ellipsis,
)),
SizedBox(width: 20),
Text(
showTimeStr,
style: TextStyle(fontSize: 13),
)
]),
SizedBox(height: 7.5),
Text(
quoteContent,
style: TextStyle(fontSize: 13),
)
],
),
)));
}
var contentWidth = _getTextWidth(textList[curTextType]);
if (contentWidth > width && contentWidth <= maxWidth) {
width = contentWidth;
}
showMsg.add(InkWell(
@@ -833,8 +940,7 @@ class _ChatPageItemState extends State<ChatPageItem>
}
},
child: Container(
constraints:
BoxConstraints(maxWidth: Screen.width - 140, minHeight: 22),
constraints: BoxConstraints(maxWidth: maxWidth, minHeight: 22),
alignment: Alignment.centerLeft,
child: extendedText(
textList[curTextType],
@@ -844,9 +950,7 @@ class _ChatPageItemState extends State<ChatPageItem>
))));
}
var width = _getTextWidth(textList[curTextType]);
var minWidth = width;
var minWidth = width + 20;
if (msg.transTag != 0) {
minWidth = 200;
showMsg.add(Padding(
@@ -870,7 +974,7 @@ class _ChatPageItemState extends State<ChatPageItem>
color: isLongPressed ? Colors.grey[300] : Colors.white,
borderRadius: BorderRadius.all(Radius.circular(ChatRadius))),
),
msg.transTag != 1
msg.transTag != 1 && msg.transTag != 0
? Positioned(
right: 5,
top: 5,
@@ -884,34 +988,7 @@ class _ChatPageItemState extends State<ChatPageItem>
: Container()
]);
if (msg.refMsgContent != null && msg.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(msg.refMsgContent);
return Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
text,
SizedBox(height: 2),
Container(
constraints: BoxConstraints(maxWidth: Screen.width - 120),
padding: EdgeInsets.symmetric(vertical: 1, horizontal: 3),
child: Text(
quoteMsg.content,
maxLines: 1,
textScaleFactor: 1.0,
overflow: TextOverflow.ellipsis,
style: TextStyle(fontSize: 12),
),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(5)),
)
],
);
} else {
return text;
}
return text;
}
_translateItemWidget(int code, String title, Function onTap) {
@@ -949,14 +1026,17 @@ class _ChatPageItemState extends State<ChatPageItem>
if (transTag == 1) {
//机器翻译中
userTranslateWidget = _translateItemWidget(0xe670, I18n.of(context).man_retranslate, null);
userTranslateWidget =
_translateItemWidget(0xe670, I18n.of(context).man_retranslate, null);
machineTranslateWidget =
_translateItemWidget(0xe671, I18n.of(context).robotTranslate, null);
} else if (transTag == 2) {
//人工翻译中
userTranslateWidget = _translateItemWidget(0xe670, I18n.of(context).ManTranslate, null);
machineTranslateWidget = _translateItemWidget(0xe671, I18n.of(context).robot_retranslate, () {
userTranslateWidget =
_translateItemWidget(0xe670, I18n.of(context).ManTranslate, null);
machineTranslateWidget =
_translateItemWidget(0xe671, I18n.of(context).robot_retranslate, () {
setState(() {
curTextType += 1;
curTextType %= textList.length;
@@ -1008,7 +1088,8 @@ class _ChatPageItemState extends State<ChatPageItem>
});
}
});
machineTranslateWidget = _translateItemWidget(0xe671, I18n.of(context).robot_retranslate, () {
machineTranslateWidget =
_translateItemWidget(0xe671, I18n.of(context).robot_retranslate, () {
setState(() {
curTextType += 1;
curTextType %= textList.length;
@@ -1063,7 +1144,8 @@ class _ChatPageItemState extends State<ChatPageItem>
))
],
)));
machineTranslateWidget = _translateItemWidget(0xe675, I18n.of(context).see_original, () {
machineTranslateWidget =
_translateItemWidget(0xe675, I18n.of(context).see_original, () {
setState(() {
curTextType = textList.length - 1;
});
@@ -1085,15 +1167,16 @@ class _ChatPageItemState extends State<ChatPageItem>
}
_receiveImg(BuildContext context, List<int> imgData, {String downloadData}) {
ImageProvider provider = MemoryImage(widget.msg.localFile==null?Uint8List.fromList(imgData):File(widget.msg.localFile).readAsBytesSync());
ImageProvider provider = MemoryImage(widget.msg.localFile == null
? Uint8List.fromList(imgData)
: File(widget.msg.localFile).readAsBytesSync());
var imgSize = _getImgSize();
return DownloadItem(
isAutoDown: false,
msg: widget.msg,
onFinishTap: (){
onFinishTap: () {
widget.hideKeyboard();
showFullImg(context, widget.msg);
},


+ 0
- 3
lib/chat/company_server_view.dart Ver fichero

@@ -7,8 +7,6 @@ import 'package:chat/data/constants.dart';
import 'package:chat/generated/i18n.dart';
import 'package:chat/models/ChatMsg.dart';
import 'package:chat/models/UserInfo.dart';
import 'package:chat/photo/entity/options.dart';
import 'package:chat/photo/photo.dart';
import 'package:chat/proto/chat.pb.dart';
import 'package:chat/r.dart';
import 'package:chat/utils/CustomUI.dart';
@@ -23,7 +21,6 @@ import 'package:flutter/services.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:multi_image_picker/multi_image_picker.dart';
import 'package:oktoast/oktoast.dart';
import 'package:photo_manager/photo_manager.dart';
import 'package:chat/utils/MessageMgr.dart';
class CompanyServerPage extends StatefulWidget {


+ 202
- 127
lib/chat/group_chat_item.dart Ver fichero

@@ -36,7 +36,6 @@ import 'package:chat/utils/video_anim.dart';
import 'package:dio/dio.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:path_provider/path_provider.dart';
import 'package:provider/provider.dart';
import 'package:oktoast/oktoast.dart';
import 'package:chat/utils/HttpUtil.dart';
@@ -92,6 +91,8 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
bool isLongPressed = false;
double maxWidth = Screen.width - 140;
@override
void initState() {
super.initState();
@@ -145,10 +146,10 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
}
}
getTodayTime(msgDate) {
getTodayTime(msgDate, {var sendTime}) {
String showTimeStr;
var sendTime = widget.msg.time;
sendTime = sendTime ?? widget.msg.time;
var today = DateTime.now();
//今天
if (msgDate.year == today.year &&
@@ -187,6 +188,7 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
return Container(
width: Screen.width,
color: Colors.white.withOpacity(0),
margin: const EdgeInsets.symmetric(vertical: 10.0),
child: Column(
children: <Widget>[
@@ -277,6 +279,8 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
}
_textMsg(MsgModel msgModel) {
List<Widget> showMsg = [];
var width = 0.0;
var msg = utf8.decode(msgModel.msgContent);
if (msg.contains('[ ')) {
msg = msg.replaceAll('[ ', '[');
@@ -284,53 +288,94 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
if (msg.contains(' ]')) {
msg = msg.replaceAll(' ]', ']');
}
bool isUrl =false;
if(textList[curTextType].contains('http') ){
isUrl =true;
bool isUrl = false;
if (textList[curTextType].contains('http')) {
isUrl = true;
}
if (msgModel.refMsgContent != null && msgModel.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(msgModel.refMsgContent);
var refName = Provider.of<RefNameProvider>(context)
.getGroupRefName(msgModel.sessionId, quoteMsg.sendUserId);
var msgDate =
DateTime.fromMillisecondsSinceEpoch(quoteMsg.sendTime.toInt());
var showTimeStr =
getTodayTime(msgDate, sendTime: quoteMsg.sendTime.toInt());
var timetWidth = CustomUI.getRealTextWidht(showTimeStr, 13);
var nameWidhth = CustomUI.getRealTextWidht(refName, 13);
width = timetWidth + (nameWidhth > 70 ? 70 : nameWidhth) + 36;
var tempIndex = quoteMsg.content.indexOf(':');
var quoteContent = tempIndex == -1
? quoteMsg.content
: quoteMsg.content.substring(quoteMsg.content.indexOf(':') + 2);
var contentWidht = _getTextWidth(quoteContent, fontSize: 13);
width = min(max(width, contentWidht), maxWidth);
showMsg.add(InkWell(
onTap: () {
MessageMgr().emit('Jump to Msg', quoteMsg.sendTime.toInt());
},
child: Container(
padding: EdgeInsets.all(8),
margin: EdgeInsets.only(bottom: 5),
decoration: BoxDecoration(
color: Color(0xFFC4E0F5),
borderRadius: BorderRadius.circular(5.5)),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Row(children: <Widget>[
Container(
constraints: BoxConstraints(maxWidth: 70),
child: Text(
refName,
style: TextStyle(fontSize: 13),
overflow: TextOverflow.ellipsis,
)),
SizedBox(width: 20),
Text(
showTimeStr,
style: TextStyle(fontSize: 13),
)
]),
SizedBox(height: 7.5),
Text(
quoteContent,
style: TextStyle(fontSize: 13),
)
],
),
)));
}
var contentWidth = _getTextWidth(textList[curTextType]);
if (contentWidth > width && contentWidth <= maxWidth) {
width = contentWidth;
}
Widget text = Container(
showMsg.add(Container(
constraints: BoxConstraints(maxWidth: maxWidth, minHeight: 22),
alignment: Alignment.centerLeft,
child: extendedText(
textList[curTextType],
color: isUrl ? Colors.blue : Constants.BlackTextColor,
hideKeyboard: widget.hideKeyboard,
fontSize: FontSize,
)));
return Container(
constraints: BoxConstraints(maxWidth: Screen.width - 120),
child: extendedText(
msg,
hideKeyboard: widget.hideKeyboard,
fontSize: FontSize,
color: isUrl?Colors.blue:SendMsgText,
),
width: width + 20,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start, children: showMsg),
padding: EdgeInsets.symmetric(horizontal: 9, vertical: 10.5),
decoration: BoxDecoration(
color: isLongPressed ? Colors.grey[300] : SendMsgBg,
border: Border.all(color: Color(0xFFB9CBD7), width: 0.6),
borderRadius: BorderRadius.all(Radius.circular(ChatRadius))),
);
if (msgModel.refMsgContent != null && msgModel.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(msgModel.refMsgContent);
return Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.end,
children: <Widget>[
text,
SizedBox(height: 2),
Container(
constraints: BoxConstraints(maxWidth: Screen.width - 120),
padding: EdgeInsets.symmetric(vertical: 1, horizontal: 3),
child: Text(
quoteMsg.content,
maxLines: 1,
textScaleFactor: 1.0,
overflow: TextOverflow.ellipsis,
style: TextStyle(fontSize: 12),
),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(5)),
)
],
);
} else {
return text;
}
}
_soundMsg() {
@@ -472,7 +517,9 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
_imgMsg(List<int> imgData) {
var imgSize = _getImgSize();
ImageProvider provider = MemoryImage(widget.msg.localFile==null?Uint8List.fromList(imgData):File(widget.msg.localFile).readAsBytesSync());
ImageProvider provider = MemoryImage(widget.msg.localFile == null
? Uint8List.fromList(imgData)
: File(widget.msg.localFile).readAsBytesSync());
return GestureDetector(
child: ClipRRect(
@@ -484,7 +531,7 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
width: imgSize.width,
child: Image(
fit: BoxFit.contain,
image:provider,
image: provider,
),
)),
borderRadius: BorderRadius.circular(5),
@@ -586,46 +633,46 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
MessageMgr().emit('Delete Select Message', widget.msg);
});
///转发
if (widget.msg.msgType == ChatType.TextChatType.value||
widget.msg.msgType == ChatType.ImageChatType.value||
widget.msg.msgType == ChatType.ShortVideoChatType.value||
widget.msg.msgType == ChatType.PlaceChatType.value||
widget.msg.msgType == ChatType.EmoticonType.value||
widget.msg.msgType == ChatType.FileChatType.value
){
actions.add( I18n.of(context).forward);
if (widget.msg.msgType == ChatType.TextChatType.value ||
widget.msg.msgType == ChatType.ImageChatType.value ||
widget.msg.msgType == ChatType.ShortVideoChatType.value ||
widget.msg.msgType == ChatType.PlaceChatType.value ||
widget.msg.msgType == ChatType.EmoticonType.value ||
widget.msg.msgType == ChatType.FileChatType.value) {
actions.add(I18n.of(context).forward);
actionsFunc.add(() {
print('转发消息');
if(widget.msg.msgType == ChatType.FileChatType.value && widget.msg.localFile==null){
if (widget.msg.msgType == ChatType.FileChatType.value &&
widget.msg.localFile == null) {
showToast('请先下载文件');
return ;
return;
}
AppNavigator.pushForwardPage(context, widget.msg);
});
}
if (widget.msg.msgType == ChatType.FileChatType.value &&widget.msg.localFile!=null) {
if (widget.msg.msgType == ChatType.FileChatType.value &&
widget.msg.localFile != null) {
//分享文件
actions.add( I18n.of(context).copy_download_url);
actionsFunc.add(() async{
actions.add(I18n.of(context).copy_download_url);
actionsFunc.add(() async {
//如果是文件增加复制下载地址
String path = widget.msg.localFile;
UploadUtil().copyFileUrl(widget.msg, context);
String type='file';
if(path.contains('mp4') ||path.contains('mp3')){
type = 'video';
}else if(path.contains('png')||path.contains('jpg')||path.contains('jpeg')||path.contains('JPG')||path.contains('PNG')){
type = 'image';
}
ShareExtend.share(FileCacheMgr.replacePath(path), type);
String path = widget.msg.localFile;
UploadUtil().copyFileUrl(widget.msg, context);
String type = 'file';
if (path.contains('mp4') || path.contains('mp3')) {
type = 'video';
} else if (path.contains('png') ||
path.contains('jpg') ||
path.contains('jpeg') ||
path.contains('JPG') ||
path.contains('PNG')) {
type = 'image';
}
ShareExtend.share(FileCacheMgr.replacePath(path), type);
});
}
if (widget.msg.msgType == ChatType.TextChatType.value) {
@@ -639,8 +686,6 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
});
}
if (widget.msg.msgType == ChatType.ShortVoiceChatType.value) {
var soundPlayMode =
Provider.of<KeyboardIndexProvider>(context).soundPlayMode;
@@ -656,23 +701,22 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
}
// String date2 = DateTime.fromMillisecondsSinceEpoch(widget.msg.time).toString();
bool isUrl =false;
if(widget.msg.msgType==ChatType.TextChatType.value ){
if( textList[curTextType].contains('http')){
isUrl =true;
bool isUrl = false;
if (widget.msg.msgType == ChatType.TextChatType.value) {
if (textList[curTextType].contains('http')) {
isUrl = true;
}
}
return WPopupMenu(
child: item,
actions: actions,
onTap: ()async{
if(isUrl){
if (await canLaunch(textList[curTextType])) {
launch(textList[curTextType]);
onTap: () async {
if (isUrl) {
if (await canLaunch(textList[curTextType])) {
launch(textList[curTextType]);
}
}
}
},
onLongPressStart: () {
isLongPressed = true;
@@ -739,16 +783,16 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
selectionEnabled: false, hideKeyboard: widget.hideKeyboard));
}
double _getTextWidth(String text) {
double _getTextWidth(String text, {double fontSize = FontSize}) {
var tp = TextPainter(
text: TextSpan(
style: TextStyle(fontSize: FontSize), text: textList[curTextType]),
style: TextStyle(fontSize: fontSize), text: textList[curTextType]),
textAlign: TextAlign.left,
textDirection: TextDirection.ltr,
textScaleFactor: 1,
);
tp.layout(maxWidth: Screen.width - 140);
tp.layout(maxWidth: maxWidth);
if (text.contains('[')) {
if (text.length < 5 && text.startsWith('[') && text.endsWith(']')) {
///单表情
@@ -763,7 +807,7 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
if (length > 6) scale = 7;
double width = tp.width + length * scale;
return width > (Screen.width - 140) ? Screen.width - 140 : width;
return width > (maxWidth) ? maxWidth : width;
}
}
return tp.width;
@@ -785,10 +829,71 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
_receiveText(MsgModel msg) {
List<Widget> showMsg = [];
double width = 0.0;
if (textList.length > 0) {
bool isUrl =false;
if(textList[curTextType].contains('http') ){
isUrl =true;
bool isUrl = false;
if (textList[curTextType].contains('http')) {
isUrl = true;
}
if (msg.refMsgContent != null && msg.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(msg.refMsgContent);
var refName = Provider.of<RefNameProvider>(context)
.getGroupRefName(msg.sessionId, quoteMsg.sendUserId);
var msgDate =
DateTime.fromMillisecondsSinceEpoch(quoteMsg.sendTime.toInt());
var showTimeStr =
getTodayTime(msgDate, sendTime: quoteMsg.sendTime.toInt());
var timetWidth = CustomUI.getRealTextWidht(showTimeStr, 13);
var nameWidhth = CustomUI.getRealTextWidht(refName, 13);
width = timetWidth + (nameWidhth > 70 ? 70 : nameWidhth) + 36;
var quoteContent =
quoteMsg.content.substring(quoteMsg.content.indexOf(':') + 2);
var contentWidht = _getTextWidth(quoteContent, fontSize: 13);
width = min(max(width, contentWidht), maxWidth);
showMsg.add(InkWell(
onTap: () {
MessageMgr().emit('Jump to Msg', quoteMsg.sendTime.toInt());
},
child: Container(
padding: EdgeInsets.all(8),
margin: EdgeInsets.only(bottom: 5),
decoration: BoxDecoration(
color: Color(0xFFC4E0F5),
borderRadius: BorderRadius.circular(5.5)),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Row(children: <Widget>[
Container(
constraints: BoxConstraints(maxWidth: 70),
child: Text(
refName,
style: TextStyle(fontSize: 13),
overflow: TextOverflow.ellipsis,
)),
SizedBox(width: 20),
Text(
showTimeStr,
style: TextStyle(fontSize: 13),
)
]),
SizedBox(height: 7.5),
Text(
quoteContent,
style: TextStyle(fontSize: 13),
)
],
),
)));
}
var contentWidth = _getTextWidth(textList[curTextType]);
if (contentWidth > width && contentWidth <= maxWidth) {
width = contentWidth;
}
showMsg.add(InkWell(
@@ -805,8 +910,7 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
}
},
child: Container(
constraints:
BoxConstraints(maxWidth: Screen.width - 140, minHeight: 22),
constraints: BoxConstraints(maxWidth: maxWidth, minHeight: 22),
alignment: Alignment.centerLeft,
child: extendedText(
textList[curTextType],
@@ -816,8 +920,6 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
))));
}
var width = _getTextWidth(textList[curTextType]);
var minWidth = width + 20;
if (msg.transTag != 0) {
minWidth = 200;
@@ -841,7 +943,7 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
color: isLongPressed ? Colors.grey[300] : Colors.white,
borderRadius: BorderRadius.all(Radius.circular(ChatRadius))),
),
msg.transTag != 1 && msg.transTag !=0
msg.transTag != 1 && msg.transTag != 0
? Positioned(
right: 5,
top: 5,
@@ -855,34 +957,7 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
: Container()
]);
if (msg.refMsgContent != null && msg.refMsgContent.length > 0) {
QuoteMsg quoteMsg = QuoteMsg.fromBuffer(msg.refMsgContent);
return Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
text,
SizedBox(height: 2),
Container(
constraints: BoxConstraints(maxWidth: Screen.width - 120),
padding: EdgeInsets.symmetric(vertical: 1, horizontal: 3),
child: Text(
quoteMsg.content,
maxLines: 1,
textScaleFactor: 1.0,
overflow: TextOverflow.ellipsis,
style: TextStyle(fontSize: 12),
),
decoration: BoxDecoration(
color: Colors.grey[300],
borderRadius: BorderRadius.circular(5)),
)
],
);
} else {
return text;
}
return text;
}
//用户评价人工翻译,差评
@@ -1083,14 +1158,16 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
_receiveImg(BuildContext context, List<int> imgData, {String downloadData}) {
// ImageProvider provider = MemoryImage(Uint8List.fromList(imgData));
ImageProvider provider = MemoryImage(widget.msg.localFile==null?Uint8List.fromList(imgData):File(widget.msg.localFile).readAsBytesSync());
ImageProvider provider = MemoryImage(widget.msg.localFile == null
? Uint8List.fromList(imgData)
: File(widget.msg.localFile).readAsBytesSync());
var imgSize = _getImgSize();
return DownloadItem(
isAutoDown: false,
msg: widget.msg,
onFinishTap: (){
onFinishTap: () {
widget.hideKeyboard();
showFullImg(context, widget.msg);
},
@@ -1106,7 +1183,6 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
),
),
);
}
_receiveVideo(BuildContext context, List<int> imgData,
@@ -1116,7 +1192,6 @@ class _GroupChatPageItemState extends State<GroupChatPageItem>
return InkWell(
onTap: () {
if (widget.msg.localFile != null) {
showVideoPage(context, widget.msg.localFile);
}
},


+ 47
- 32
lib/chat/group_chat_view.dart Ver fichero

@@ -24,6 +24,7 @@ import 'package:chat/utils/sound_util.dart';
import 'package:chat/utils/sp_utils.dart';
import 'package:chat/utils/sql_util.dart';
import 'package:chat/utils/upload_util.dart';
import 'package:chat/utils/white_opacity_anim.dart';
import 'package:extended_text/extended_text.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
@@ -75,6 +76,8 @@ class _GroupChatPageState extends State<GroupChatPage> {
String alterUserName = '';
int jumpTime;
@override
void dispose() {
var endTime = DateTime.now().millisecondsSinceEpoch ~/ 1000;
@@ -84,6 +87,7 @@ class _GroupChatPageState extends State<GroupChatPage> {
msgMgr.off('Keyboard Hide', dealWithKeyboardHide);
msgMgr.off('Update Group Info', updateGroupInfo);
msgMgr.off('Delete Select Message', _deleteItem);
msgMgr.off('Jump to Msg', jumpToMsg);
MsgHandler.curActiveSession = 0;
SoundUtils().stop();
@@ -126,6 +130,7 @@ class _GroupChatPageState extends State<GroupChatPage> {
msgMgr.on('Keyboard Hide', dealWithKeyboardHide);
msgMgr.on('Update Group Info', updateGroupInfo);
msgMgr.on('Delete Select Message', _deleteItem);
msgMgr.on('Jump to Msg', jumpToMsg);
WidgetsBinding.instance.addPostFrameCallback((_) {
if (widget.enterType == 1) {
@@ -157,6 +162,26 @@ class _GroupChatPageState extends State<GroupChatPage> {
});
}
jumpToMsg(time) {
//var screenItemNums = itemPositionListener.itemPositions.value.length;
jumpTime = time;
int jumIndex = 0;
for (int i = 0; i < msgList.length; i++) {
if (time == msgList[i].time) {
jumIndex = i - 1; // - screenItemNums + 2;
break;
}
}
if (jumIndex < 0) {
jumIndex = 0;
}
if (jumIndex > msgList.length - 1) {
jumIndex = msgList.length - 1;
}
itemScrollController.scrollTo(
index: jumIndex, duration: new Duration(microseconds: 1));
}
void _sendFile(File file) async {
// File file = await FilePicker.getFile();
int fileSize = file.lengthSync();
@@ -253,7 +278,7 @@ class _GroupChatPageState extends State<GroupChatPage> {
Map refMap = Provider.of<RefNameProvider>(context).refMap;
bool isHaveUnreadNews = unreadTime !=null;
bool isHaveUnreadNews = unreadTime != null;
bool isAlterYou = alterTime != null;
return MultiProvider(
@@ -301,31 +326,9 @@ class _GroupChatPageState extends State<GroupChatPage> {
right: 0,
child: InkWell(
onTap: () {
var screenItemNums =
itemPositionListener
.itemPositions.value.length;
int jumIndex = 0;
if (isAlterYou) {
for (int i = 0;
i < msgList.length;
i++) {
if (alterTime == msgList[i].time) {
jumIndex = i - screenItemNums + 2;
break;
}
}
} else {
for (int i = 0;
i < msgList.length;
i++) {
if (unreadTime == msgList[i].time) {
jumIndex = i - screenItemNums + 2;
break;
}
}
}
itemScrollController.jumpTo(
index: jumIndex);
jumpToMsg(isAlterYou
? alterTime
: unreadTime);
unreadTime = null;
setState(() {});
},
@@ -349,7 +352,7 @@ class _GroupChatPageState extends State<GroupChatPage> {
child: Row(
children: <Widget>[
Icon(
Icons.file_upload,
Icons.arrow_upward,
color: Color(0xFF3875E9),
size: 20,
),
@@ -495,7 +498,7 @@ class _GroupChatPageState extends State<GroupChatPage> {
itemPositionsListener: itemPositionListener,
padding: EdgeInsets.all(8.0),
reverse: true,
// hitCallback: hideKeyBoard,
hitCallback: hideKeyBoard,
)),
);
}
@@ -518,9 +521,10 @@ class _GroupChatPageState extends State<GroupChatPage> {
MsgHandler.insertMsgToDB(msg);
MsgHandler.sendChatMsg(msg);
if (mounted) {
setState(() {});
setState(() {
itemScrollController.jumpTo(index: 0);
});
}
itemScrollController.jumpTo(index: 0);
}
MsgModel msg;
@@ -566,18 +570,29 @@ class _GroupChatPageState extends State<GroupChatPage> {
}
MsgModel msg = msgList[index];
var result;
if (msg.from == 0) {
return GroupChatPageItem(
result = GroupChatPageItem(
key: Key(msg.time.toString()), msg: msg, lastMsgTime: lastMsgTime);
} else {
return GroupChatPageItem(
result = GroupChatPageItem(
key: Key(msg.time.toString()),
msg: msg,
memberModel: widget.groupInfoModel.getMember(msg.from),
hideKeyboard: readOnly,
lastMsgTime: lastMsgTime);
}
if (msg.time == jumpTime) {
result = WhiteOpacityAnim(
key: Key(msg.time.toString()),
child: result,
animFinishCallback: () {
jumpTime = null;
},
);
}
return result;
}
quiteGroup() {


+ 20
- 11
lib/chat/input_bar.dart Ver fichero

@@ -153,7 +153,7 @@ class InputBarState extends State<InputBar>
// SystemChannels.textInput.invokeMethod('TextInput.show');
}
_getRefShortText() {
_getRefShortText(){
if (refMsg == null) {
return null;
}
@@ -209,11 +209,19 @@ class InputBarState extends State<InputBar>
break;
default:
}
GroupInfoModel groupInfoModel = Provider.of<GroupInfoModel>(context);
var member = groupInfoModel.getMember(refMsg.from);
return '${member.refName}: $desc';
if (refMsg.channelType == ChatChannelType.Group.value) {
GroupInfoModel groupInfoModel = Provider.of<GroupInfoModel>(context);
var member = groupInfoModel.getMember(refMsg.from);
return '${member.refName}: $desc';
//}
//else if (refMsg.channelType == ChatChannelType.Session.value) {
// UserInfo info = await HttpUtil().getFriendInfo(refMsg.from);
// var refName = Provider.of<RefNameProvider>(context)
// .getRefName(info.userId, info.nickName);
// return '$refName: $desc';
} else {
return desc;
}
}
bool isReceiver = false;
@@ -229,8 +237,7 @@ class InputBarState extends State<InputBar>
Widget centerWidget;
Widget input = Container(
child:
TextField(
child: TextField(
// textSelectionControls: ExtendedMaterialTextSelectionControls(),
keyboardAppearance: Brightness.light,
onChanged: (String messageText) {
@@ -700,14 +707,16 @@ class InputBarState extends State<InputBar>
for (var i = 0; i < resultList.length; i++) {
Asset photoEntity = resultList[i];
ByteData byteData = await photoEntity.getByteData();
File file = await FileCacheMgr().writeFile('temp-photo-${DateTime.now().millisecondsSinceEpoch}-${photoEntity.name}', byteData.buffer.asInt8List(0));
File file = await FileCacheMgr().writeFile(
'temp-photo-${DateTime.now().millisecondsSinceEpoch}-${photoEntity.name}',
byteData.buffer.asInt8List(0));
_sendPhotoFile(file);
}
}
} on Exception catch (e) {
print(e.toString());
print(e.toString());
}
@@ -765,7 +774,7 @@ class InputBarState extends State<InputBar>
if (imgSize > ImgSizeLimit) {
print('图片大于 $ImgSizeLimit,压缩');
//发送压缩图 WidgetUtil.getCompressImg(path,quality: 80,percentage: 80);
sendImg = await WidgetUtil.getCompressImg(imgFile.absolute.path );
sendImg = await WidgetUtil.getCompressImg(imgFile.absolute.path);
isNeedUpload = true;
} else {
sendImg = imgFile.readAsBytesSync();


+ 0
- 1
lib/chat/translate_state.dart Ver fichero

@@ -3,7 +3,6 @@ import 'package:chat/data/constants.dart';
import 'package:chat/generated/i18n.dart';
import 'package:chat/utils/HttpUtil.dart';
import 'package:chat/utils/MessageMgr.dart';
import 'package:chat/utils/msgHandler.dart';
import 'package:chat/utils/screen.dart';
import 'package:flutter/material.dart';
import 'package:oktoast/oktoast.dart';


+ 2
- 0
lib/data/UserData.dart Ver fichero

@@ -65,6 +65,8 @@ class UserData {
int homemainIndex = 0;
String currentCity = '';
String deviceLanguageCode;
Map<String, dynamic> toJson() {
Map<String, dynamic> json = new Map<String, dynamic>();
json['language'] = language;


+ 1
- 11
lib/data/translate_hk_data_mgr.dart Ver fichero

@@ -1,14 +1,4 @@
import 'dart:convert';

import 'package:chat/data/UserData.dart';
import 'package:chat/data/chat_data_mgr.dart';
import 'package:chat/models/group_info_model.dart';
import 'package:chat/proto/chat.pbserver.dart';
import 'package:chat/utils/MessageMgr.dart';
import 'package:chat/utils/group_member_model.dart';
import 'package:chat/utils/sql_util.dart';
import 'package:chat/utils/upload_util.dart';
import 'package:crclib/crclib.dart';



class TranslateOrder{


+ 0
- 3
lib/home/AddProgram.dart Ver fichero

@@ -12,8 +12,6 @@ import 'package:chat/home/SelectPage.dart';
import 'package:chat/home/VerificationCenter.dart';
import 'package:chat/home/VipPage.dart';
import 'package:chat/models/money_change.dart';
import 'package:chat/photo/entity/options.dart';
import 'package:chat/photo/photo.dart';
import 'package:chat/utils/ChargeMoney.dart';
import 'package:chat/utils/CustomUI.dart';
import 'package:chat/utils/HttpUtil.dart';
@@ -31,7 +29,6 @@ import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:multi_image_picker/multi_image_picker.dart';
import 'package:oktoast/oktoast.dart';
import 'package:photo_manager/photo_manager.dart';
import 'package:provider/provider.dart';
import 'package:shared_preferences/shared_preferences.dart';
import '../utils/ShadowButton.dart';


+ 0
- 3
lib/home/InformUser.dart Ver fichero

@@ -6,8 +6,6 @@ import 'package:chat/data/UserData.dart';
import 'package:chat/data/WebData.dart';
import 'package:chat/data/constants.dart';
import 'package:chat/generated/i18n.dart';
import 'package:chat/photo/entity/options.dart';
import 'package:chat/photo/photo.dart';
import 'package:chat/utils/CustomUI.dart';
import 'package:chat/utils/HttpUtil.dart';
import 'package:chat/utils/PicSwiper.dart';
@@ -18,7 +16,6 @@ import 'package:flutter/material.dart';
import 'package:multi_image_picker/multi_image_picker.dart';
import 'package:oktoast/oktoast.dart';
import 'package:photo_manager/photo_manager.dart';
import '../data/UserData.dart';
import '../utils/TokenMgr.dart';


+ 0
- 3
lib/home/ProfilePage.dart Ver fichero

@@ -6,8 +6,6 @@ import 'package:chat/home/rich_title.dart';
import 'package:chat/models/money_change.dart';
import 'package:chat/models/ref_name_provider.dart';
import 'package:chat/models/voucher_change.dart';
import 'package:chat/photo/entity/options.dart';
import 'package:chat/photo/photo.dart';
import 'package:chat/utils/ChargeMoney.dart';
import 'package:chat/utils/app_navigator.dart';
import 'package:chat/utils/blacklist_mgr.dart';
@@ -42,7 +40,6 @@ import 'package:image_picker/image_picker.dart';
import 'package:multi_image_picker/multi_image_picker.dart';
import 'package:oktoast/oktoast.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:photo_manager/photo_manager.dart';
import 'package:provider/provider.dart';
import 'package:share/share.dart';
import '../utils/FullWithButton.dart';


+ 1
- 3
lib/home/homeMain.dart Ver fichero

@@ -10,7 +10,6 @@ import 'package:chat/home/realtimehelper/real_time_helper_page.dart';
import 'package:chat/home/unread_dot_widget.dart';
import 'package:chat/models/UserInfo.dart';
import 'package:chat/models/ref_name_provider.dart';
import 'package:chat/proto/transhousekeeper.pb.dart';
import 'package:chat/utils/CustomUI.dart';
import 'package:chat/utils/HttpUtil.dart';
import 'package:chat/utils/MessageMgr.dart';
@@ -35,7 +34,6 @@ import 'package:shared_preferences/shared_preferences.dart';
import 'package:chat/utils/my_bottom_navigation_bar.dart' as myBottm;
import 'friend_page.dart';
import 'group_chat_page.dart';
class NavigationIconView {
final BottomNavigationBarItem item;
@@ -175,7 +173,7 @@ class _HomeMainState extends State<HomeMain> {
postContact(null);
postLoaction();
locationSchedule();
HttpUtil().saveMobileInfo();
WidgetsBinding.instance.addPostFrameCallback((_) {
VersionUtils.versionUpdate(context);
ReceiveShareFile.start();


+ 0
- 14
lib/home/realtimehelper/translation_butler_page.dart Ver fichero

@@ -1,36 +1,22 @@
import 'dart:async';

import 'package:cached_network_image/cached_network_image.dart';
import 'package:chat/chat/ChatPage.dart';
import 'package:chat/data/UserData.dart';
import 'package:chat/data/chat_data_mgr.dart';
import 'package:chat/data/group_data_mgr.dart';
import 'package:chat/data/translate_hk_data_mgr.dart';
import 'package:chat/home/add_friend.dart';
import 'package:chat/home/group_announcement.dart';
import 'package:chat/home/group_manage_page.dart';
import 'package:chat/models/group_info_model.dart';
import 'package:chat/models/money_change.dart';
import 'package:chat/models/ref_name_provider.dart';
import 'package:chat/utils/LoadingDialog.dart';
import 'package:chat/utils/MessageMgr.dart';
import 'package:chat/utils/group_member_model.dart';
import 'package:chat/utils/msgHandler.dart';
import 'package:chat/utils/screen.dart';
import 'package:chat/utils/sp_utils.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:oktoast/oktoast.dart';
import 'package:provider/provider.dart';

import '../../data/constants.dart';
import '../../generated/i18n.dart';
import '../../r.dart';
import '../../utils/CustomUI.dart';
import '../../utils/FullWithButton.dart';
import '../../utils/app_navigator.dart';
import '../create_group_view.dart';
import 'package:chat/utils/PopUpMenu.dart' as myPop;

class TranslationButlerPage extends StatefulWidget {


+ 0
- 3
lib/home/realtimehelper/translation_evaluation_dialog.dart Ver fichero

@@ -31,13 +31,11 @@ class TravelEvaluationPageState extends State<TravelEvaluationPage> {

@override
void initState() {
// TODO: implement initState
super.initState();
}

@override
void didChangeDependencies() {
// TODO: implement didChangeDependencies
super.didChangeDependencies();
posList = [
EvaluationBean(6, I18n.of(context).translation_pos_1),
@@ -81,7 +79,6 @@ class TravelEvaluationPageState extends State<TravelEvaluationPage> {

@override
Widget build(BuildContext context) {
// TODO: implement build

List<Widget> evaluationWidget = getItem(isGood ? posList : negList);



+ 1
- 0
lib/main.dart Ver fichero

@@ -405,6 +405,7 @@ class _MyAppState extends State<MyApp> with WidgetsBindingObserver {
final String lang =
deviceLocale != null ? deviceLocale.toString() : "";
print('#### fl: $lang');
UserData().deviceLanguageCode = deviceLocale.toString();
//设置设备语言
if (language.containsKey(deviceLocale.toString()))
UserData().deviceLanguage =


+ 11
- 0
lib/utils/CustomUI.dart Ver fichero

@@ -1280,4 +1280,15 @@ class CustomUI {
child: TravelEvaluationPage(),
));
}
static double getRealTextWidht(String text, double fontSize) {
TextPainter _textPainter = TextPainter(
maxLines: 2,
text: TextSpan(
text: text,
style: TextStyle(fontSize: fontSize, color: Colors.black)),
textDirection: TextDirection.ltr)
..layout();
return _textPainter.width;
}
}

+ 31
- 3
lib/utils/HttpUtil.dart Ver fichero

@@ -24,6 +24,7 @@ import 'package:chat/utils/local_notification_util.dart';
import 'package:chat/utils/sp_utils.dart';
import 'package:chat/utils/sql_util.dart';
import 'package:chat/utils/user_info_table.dart';
import 'package:device_info/device_info.dart';
import 'dart:core';
import 'package:dio/dio.dart';
import 'package:flutter/material.dart';
@@ -35,7 +36,6 @@ import 'dart:io';
import '../data/UserData.dart';
import '../utils/TokenMgr.dart';
import 'package:http_parser/http_parser.dart';
import 'package:chat/utils/friend_list_mgr.dart';
class HttpUtil {
static HttpUtil _instance;
@@ -836,10 +836,9 @@ class HttpUtil {
UserData().stationOpenSwitch = config['station'] == 1;
UserData().myProgramOpenSwitch = config['myProgram'] == 1;
UserData().nearbyOpenSwitch = config['nearby'] == 1;
UserData().isTranslateUser = config['isTranslateUser'] == 1;
// print('### config: start');
print('### config: isTranslateUser:${config['isTranslateUser']}');
// print('### config: iapPay:${config['iapPay']}');
}
}
}
@@ -1419,6 +1418,35 @@ class HttpUtil {
}
}
//保存设备名称和编码
saveMobileInfo() async {
String mobileType = '';
DeviceInfoPlugin deviceInfo = DeviceInfoPlugin();
if (Platform.isAndroid) {
AndroidDeviceInfo androidInfo = await deviceInfo.androidInfo;
mobileType = androidInfo.model;
print('Running on ${androidInfo.model}'); // e.g. "Moto G (4)"
} else if (Platform.isIOS) {
IosDeviceInfo iosInfo = await deviceInfo.iosInfo;
mobileType = iosInfo.utsname.machine;
}
Map data = {
"userId": UserData().basicInfo.userId,
};
data['sign'] = TokenMgr().getSign(data);
data['model'] = mobileType;
data['coding'] = UserData().deviceLanguageCode;
Response res =
await HttpUtil().post('user/save/modelAndCoding', data: data);
Map resData = res.data;
print(resData);
}
///实时帮-翻译管家评价
evaluationTransalteHK(String orderNo,String value,bool isGood,Function callback) async {
Map data = {


+ 1
- 4
lib/utils/count_down_button.dart Ver fichero

@@ -14,7 +14,7 @@ class CountDownButton extends StatefulWidget{

@override
State<StatefulWidget> createState() {
// TODO: implement createState
return CountDownButtonState();
}

@@ -44,7 +44,6 @@ class CountDownButtonState extends State<CountDownButton> {
}
@override
void initState() {
// TODO: implement initState
super.initState();
secondsPassed = widget.countDownTime;
timer = Timer.periodic(Duration(seconds: 1), (Timer t){
@@ -54,14 +53,12 @@ class CountDownButtonState extends State<CountDownButton> {

@override
void dispose() {
// TODO: implement dispose
super.dispose();
timer?.cancel();
}

@override
Widget build(BuildContext context) {
// TODO: implement build
// ~/ 取整操作
int seconds = secondsPassed % 60;
int minutes = secondsPassed ~/ 60;


+ 0
- 1
lib/utils/file_cache_mgr.dart Ver fichero

@@ -1,5 +1,4 @@
import 'dart:io';
import 'dart:typed_data';
import 'package:path/path.dart' as p;
import 'package:path_provider/path_provider.dart';


+ 0
- 1
lib/utils/image_util.dart Ver fichero

@@ -5,7 +5,6 @@ import 'dart:ui';
import 'package:cached_network_image/cached_network_image.dart';
import 'package:chat/data/group_data_mgr.dart';
import 'package:chat/models/group_info_model.dart';
import 'package:chat/utils/screen.dart';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'package:flutter/widgets.dart';


+ 1
- 3
lib/utils/msgHandler.dart Ver fichero

@@ -9,7 +9,6 @@ import 'package:chat/data/group_data_mgr.dart';
import 'package:chat/data/translate_hk_data_mgr.dart';
import 'package:chat/generated/i18n.dart';
import 'package:chat/home/IndexPage.dart';
import 'package:chat/home/realtimehelper/translation_butler_page.dart';
import 'package:chat/models/ChatMsg.dart';
import 'package:chat/models/group_info_model.dart';
import 'package:chat/proto/all.pbserver.dart';
@@ -26,7 +25,6 @@ import 'package:flutter/material.dart';
import 'package:oktoast/oktoast.dart';
import 'package:fixnum/fixnum.dart';
import 'LoadingDialog.dart';
import 'MessageMgr.dart';
const MaxMsgContentSize = 1024 * 1024 * 3;
@@ -414,7 +412,7 @@ class MsgHandler {
channelType: ChatChannelType.Group.value);
}
}
else if(isTranslateHK){ //TODO ddddd
else if(isTranslateHK){
var myId = UserData().basicInfo.userId;
print('chat.contentBuff:${chat.contentBuff.length}');
TransHKChatNotice notice = TransHKChatNotice.fromBuffer(chat.contentBuff);


+ 0
- 1
lib/utils/screen_shot.dart Ver fichero

@@ -1,7 +1,6 @@
import 'dart:typed_data';
import 'dart:io';
import 'package:chat/map/location_result.dart';
import 'package:chat/utils/screen.dart';
import 'package:flutter/services.dart';
import 'package:flutter_native_image/flutter_native_image.dart';
//import 'package:flutter_image_compress/flutter_image_compress.dart';


+ 52
- 0
lib/utils/white_opacity_anim.dart Ver fichero

@@ -0,0 +1,52 @@
import 'package:flutter/material.dart';

class WhiteOpacityAnim extends StatefulWidget {
final Widget child;
final animFinishCallback;
WhiteOpacityAnim(
{Key key, @required this.child, @required this.animFinishCallback});
@override
_WhiteOpacityAnimState createState() => _WhiteOpacityAnimState();
}

class _WhiteOpacityAnimState extends State<WhiteOpacityAnim>
with SingleTickerProviderStateMixin {
Animation<double> _animation;
AnimationController _controller;

@override
void initState() {
super.initState();
// 启动动画controller
_controller = new AnimationController(
duration: Duration(milliseconds: 1000), vsync: this);
_controller.addStatusListener((AnimationStatus status) {
setState(() {});
if (status == AnimationStatus.completed) {
widget.animFinishCallback();
}
});

_animation = new Tween<double>(begin: 1, end: 0).animate(_controller)
..addListener(() {
setState(() {});
});

_controller.forward();
}

@override
void dispose() {
_controller.stop();
_controller.dispose();
super.dispose();
}

@override
Widget build(BuildContext context) {
return Container(
child: widget.child,
color: Colors.white.withOpacity(_animation.value),
);
}
}

+ 12
- 3
pubspec.lock Ver fichero

@@ -259,6 +259,13 @@ packages:
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.2.9"
device_info:
dependency: "direct main"
description:
name: device_info
url: "https://pub.flutter-io.cn"
source: hosted
version: "0.4.2+1"
dio:
dependency: "direct main"
description:
@@ -919,9 +926,11 @@ packages:
scrollable_positioned_list:
dependency: "direct main"
description:
name: scrollable_positioned_list
url: "https://pub.flutter-io.cn"
source: hosted
path: "."
ref: HEAD
resolved-ref: "6ac696b0550694de0eac3f4c30956e21a6dad748"
url: "https://github.com/KerwinZheng/scrollable_positioned_list.git"
source: git
version: "0.1.2"
share:
dependency: "direct main"


+ 4
- 1
pubspec.yaml Ver fichero

@@ -177,7 +177,10 @@ dependencies:
share_extend: ^1.1.1
#多图片选择
multi_image_picker: ^4.6.4
scrollable_positioned_list: ^0.1.2
scrollable_positioned_list:
git: https://github.com/KerwinZheng/scrollable_positioned_list.git
#设备信息
device_info: ^0.4.2+1

dev_dependencies:
flutter_test:


Cargando…
Cancelar
Guardar