diff --git a/lib/graphql/github_users.dart b/lib/graphql/github_users.dart index 1434b0b..44e21b6 100644 --- a/lib/graphql/github_users.dart +++ b/lib/graphql/github_users.dart @@ -51,7 +51,12 @@ class GithubUsersUser extends GithubUsersAuditEntryActor @override String avatarUrl; - String bio; + String company; + + @override + String location; + + DateTime createdAt; GithubUsersFollowerConnection followers; @@ -62,8 +67,17 @@ class GithubUsersUser extends GithubUsersAuditEntryActor String resolveType; @override - List get props => - [login, name, avatarUrl, bio, followers, following, resolveType]; + List get props => [ + login, + name, + avatarUrl, + company, + location, + createdAt, + followers, + following, + resolveType + ]; Map toJson() => _$GithubUsersUserToJson(this); } @@ -240,11 +254,13 @@ class GithubUsersProfileOwner with EquatableMixin { String name; + String location; + @JsonKey(name: '__typename') String resolveType; @override - List get props => [login, name, resolveType]; + List get props => [login, name, location, resolveType]; Map toJson() => _$GithubUsersProfileOwnerToJson(this); } @@ -307,6 +323,9 @@ class GithubUsersOrganization extends GithubUsersAuditEntryActor @override String avatarUrl; + @override + String location; + GithubUsersOrganizationMemberConnection membersWithRole; @override @@ -315,7 +334,7 @@ class GithubUsersOrganization extends GithubUsersAuditEntryActor @override List get props => - [login, name, avatarUrl, membersWithRole, resolveType]; + [login, name, avatarUrl, location, membersWithRole, resolveType]; Map toJson() => _$GithubUsersOrganizationToJson(this); } @@ -608,7 +627,19 @@ class GithubUsersQuery extends GraphQLQuery { directives: [], selectionSet: null), FieldNode( - name: NameNode(value: 'bio'), + name: NameNode(value: 'company'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'location'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'createdAt'), alias: null, arguments: [], directives: [], @@ -679,7 +710,19 @@ class GithubUsersQuery extends GraphQLQuery { directives: [], selectionSet: null), FieldNode( - name: NameNode(value: 'bio'), + name: NameNode(value: 'company'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'location'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'createdAt'), alias: null, arguments: [], directives: [], @@ -752,7 +795,19 @@ class GithubUsersQuery extends GraphQLQuery { directives: [], selectionSet: null), FieldNode( - name: NameNode(value: 'bio'), + name: NameNode(value: 'company'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'location'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'createdAt'), alias: null, arguments: [], directives: [], @@ -794,6 +849,12 @@ class GithubUsersQuery extends GraphQLQuery { arguments: [], directives: [], selectionSet: null), + FieldNode( + name: NameNode(value: 'location'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), FieldNode( name: NameNode(value: 'membersWithRole'), alias: null, @@ -860,7 +921,19 @@ class GithubUsersQuery extends GraphQLQuery { directives: [], selectionSet: null), FieldNode( - name: NameNode(value: 'bio'), + name: NameNode(value: 'company'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'location'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'createdAt'), alias: null, arguments: [], directives: [], @@ -947,7 +1020,19 @@ class GithubUsersQuery extends GraphQLQuery { directives: [], selectionSet: null), FieldNode( - name: NameNode(value: 'bio'), + name: NameNode(value: 'company'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'location'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'createdAt'), alias: null, arguments: [], directives: [], @@ -1020,7 +1105,19 @@ class GithubUsersQuery extends GraphQLQuery { directives: [], selectionSet: null), FieldNode( - name: NameNode(value: 'bio'), + name: NameNode(value: 'company'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'location'), + alias: null, + arguments: [], + directives: [], + selectionSet: null), + FieldNode( + name: NameNode(value: 'createdAt'), alias: null, arguments: [], directives: [], diff --git a/lib/graphql/github_users.g.dart b/lib/graphql/github_users.g.dart index c9268a3..b443af1 100644 --- a/lib/graphql/github_users.g.dart +++ b/lib/graphql/github_users.g.dart @@ -33,7 +33,11 @@ GithubUsersUser _$GithubUsersUserFromJson(Map json) { ..login = json['login'] as String ..name = json['name'] as String ..avatarUrl = json['avatarUrl'] as String - ..bio = json['bio'] as String + ..company = json['company'] as String + ..location = json['location'] as String + ..createdAt = json['createdAt'] == null + ? null + : DateTime.parse(json['createdAt'] as String) ..followers = json['followers'] == null ? null : GithubUsersFollowerConnection.fromJson( @@ -50,7 +54,9 @@ Map _$GithubUsersUserToJson(GithubUsersUser instance) => 'login': instance.login, 'name': instance.name, 'avatarUrl': instance.avatarUrl, - 'bio': instance.bio, + 'company': instance.company, + 'location': instance.location, + 'createdAt': instance.createdAt?.toIso8601String(), 'followers': instance.followers?.toJson(), 'following': instance.following?.toJson(), '__typename': instance.resolveType, @@ -189,6 +195,7 @@ GithubUsersProfileOwner _$GithubUsersProfileOwnerFromJson( return GithubUsersProfileOwner() ..login = json['login'] as String ..name = json['name'] as String + ..location = json['location'] as String ..resolveType = json['__typename'] as String; } @@ -197,6 +204,7 @@ Map _$GithubUsersProfileOwnerToJson( { 'login': instance.login, 'name': instance.name, + 'location': instance.location, '__typename': instance.resolveType, }; @@ -237,6 +245,7 @@ GithubUsersOrganization _$GithubUsersOrganizationFromJson( ..login = json['login'] as String ..name = json['name'] as String ..avatarUrl = json['avatarUrl'] as String + ..location = json['location'] as String ..membersWithRole = json['membersWithRole'] == null ? null : GithubUsersOrganizationMemberConnection.fromJson( @@ -250,6 +259,7 @@ Map _$GithubUsersOrganizationToJson( 'login': instance.login, 'name': instance.name, 'avatarUrl': instance.avatarUrl, + 'location': instance.location, 'membersWithRole': instance.membersWithRole?.toJson(), '__typename': instance.resolveType, }; diff --git a/lib/graphql/github_users.graphql b/lib/graphql/github_users.graphql index 54cc3ae..b60b75d 100644 --- a/lib/graphql/github_users.graphql +++ b/lib/graphql/github_users.graphql @@ -12,7 +12,9 @@ query( login name avatarUrl - bio + company + location + createdAt followers(first: 30, after: $after) @include(if: $isFollowers) { pageInfo { hasNextPage @@ -22,7 +24,9 @@ query( login name avatarUrl - bio + company + location + createdAt } } following(first: 30, after: $after) @include(if: $isFollowing) { @@ -34,7 +38,9 @@ query( login name avatarUrl - bio + company + location + createdAt } } } @@ -42,6 +48,7 @@ query( login name avatarUrl + location membersWithRole(first: 30, after: $after) @include(if: $isFollowing) { pageInfo { hasNextPage @@ -51,7 +58,9 @@ query( login name avatarUrl - bio + company + location + createdAt } } } @@ -65,7 +74,9 @@ query( login name avatarUrl - bio + company + location + createdAt } } stargazers(first: 30, after: $after) @include(if: $isStar) { @@ -77,7 +88,9 @@ query( login name avatarUrl - bio + company + location + createdAt } } } diff --git a/lib/screens/me.dart b/lib/screens/me.dart index d68d062..6820191 100644 --- a/lib/screens/me.dart +++ b/lib/screens/me.dart @@ -34,7 +34,7 @@ class MeScreen extends StatelessWidget { login: user.login, name: user.name, avatarUrl: user.avatarUrl, - bio: user.bio, + bio: Text(user.bio ?? ''), inUserScreen: true, ), CommonStyle.border, diff --git a/lib/screens/trending.dart b/lib/screens/trending.dart index 2a76ced..575e7c3 100644 --- a/lib/screens/trending.dart +++ b/lib/screens/trending.dart @@ -46,7 +46,6 @@ class TrendingScreen extends StatelessWidget { login: item.username, name: item.name, avatarUrl: item.avatar, - bio: '', ); default: throw ''; diff --git a/lib/screens/user.dart b/lib/screens/user.dart index 744ad24..6000c00 100644 --- a/lib/screens/user.dart +++ b/lib/screens/user.dart @@ -79,7 +79,7 @@ class UserScreen extends StatelessWidget { login: user.login, name: user.name, avatarUrl: user.avatarUrl, - bio: user.bio, + bio: Text(user.bio ?? ''), inUserScreen: true, ), CommonStyle.border, @@ -201,7 +201,7 @@ class UserScreen extends StatelessWidget { login: payload.login, name: payload.name, avatarUrl: payload.avatarUrl, - bio: payload.description, + bio: Text(payload.description ?? ''), inUserScreen: true, ), CommonStyle.border, diff --git a/lib/screens/users.dart b/lib/screens/users.dart index a4ccbc4..1b53e52 100644 --- a/lib/screens/users.dart +++ b/lib/screens/users.dart @@ -1,9 +1,12 @@ import 'package:flutter/material.dart'; import 'package:git_touch/graphql/github_users.dart'; +import 'package:git_touch/models/theme.dart'; import 'package:git_touch/scaffolds/list_stateful.dart'; +import 'package:git_touch/utils/utils.dart'; import 'package:git_touch/widgets/app_bar_title.dart'; import 'package:git_touch/widgets/user_item.dart'; import 'package:git_touch/models/auth.dart'; +import 'package:intl/intl.dart'; import 'package:provider/provider.dart'; enum UsersScreenType { @@ -93,6 +96,50 @@ class UsersScreen extends StatelessWidget { } } + static final _dateFormat = DateFormat.yMMMMd(); + + Widget _buildBio(BuildContext context, String company, String location, + DateTime createdAt) { + final theme = Provider.of(context); + if (company != null && company.isNotEmpty) { + return Row( + children: [ + Icon( + Octicons.organization, + size: 15, + color: theme.palette.secondaryText, + ), + SizedBox(width: 4), + Text(company), + ], + ); + } + if (location != null && location.isNotEmpty) { + return Row( + children: [ + Icon( + Octicons.location, + size: 15, + color: theme.palette.secondaryText, + ), + SizedBox(width: 4), + Text(location), + ], + ); + } + return Row( + children: [ + Icon( + Octicons.clock, + size: 15, + color: theme.palette.secondaryText, + ), + SizedBox(width: 4), + Text('Joined on ${_dateFormat.format(createdAt)}'), + ], + ); + } + @override Widget build(BuildContext context) { return ListStatefulScaffold( @@ -104,7 +151,8 @@ class UsersScreen extends StatelessWidget { login: payload.login, name: payload.name, avatarUrl: payload.avatarUrl, - bio: payload.bio, + bio: _buildBio( + context, payload.company, payload.location, payload.createdAt), ); }, ); diff --git a/lib/widgets/text_contains_organization.dart b/lib/widgets/text_contains_organization.dart index 9be038a..dc016b5 100644 --- a/lib/widgets/text_contains_organization.dart +++ b/lib/widgets/text_contains_organization.dart @@ -29,7 +29,7 @@ class TextContainsOrganization extends StatelessWidget { return RichText( text: TextSpan(children: spans, style: style), - overflow: oneLine ? TextOverflow.ellipsis : null, + overflow: oneLine ? TextOverflow.ellipsis : TextOverflow.clip, maxLines: oneLine ? 1 : null, ); } diff --git a/lib/widgets/user_item.dart b/lib/widgets/user_item.dart index c41aec3..bc3ac96 100644 --- a/lib/widgets/user_item.dart +++ b/lib/widgets/user_item.dart @@ -3,7 +3,6 @@ import 'package:git_touch/models/theme.dart'; import 'package:git_touch/utils/utils.dart'; import 'package:git_touch/widgets/avatar.dart'; import 'package:git_touch/widgets/link.dart'; -import 'package:git_touch/widgets/text_contains_organization.dart'; import 'package:provider/provider.dart'; const userGqlChunk = ''' @@ -17,7 +16,7 @@ class UserItem extends StatelessWidget { final String login; final String name; final String avatarUrl; - final String bio; + final Widget bio; final bool inUserScreen; UserItem({ @@ -33,7 +32,7 @@ class UserItem extends StatelessWidget { }) : login = data['login'], name = data['name'], avatarUrl = data['avatarUrl'], - bio = data['bio']; + bio = Text(data['bio']); @override Widget build(BuildContext context) { @@ -42,12 +41,12 @@ class UserItem extends StatelessWidget { final widget = Container( padding: CommonStyle.padding, child: Row( - crossAxisAlignment: CrossAxisAlignment.start, children: [ Avatar(url: avatarUrl, size: AvatarSize.large), SizedBox(width: 10), Expanded( child: Column( + mainAxisAlignment: MainAxisAlignment.spaceBetween, crossAxisAlignment: CrossAxisAlignment.start, children: [ Row( @@ -69,14 +68,13 @@ class UserItem extends StatelessWidget { ], ), SizedBox(height: 6), - if (bio != null && bio.isNotEmpty) - TextContainsOrganization( - bio, + if (bio != null) + DefaultTextStyle( style: TextStyle( color: theme.palette.secondaryText, fontSize: 15, ), - oneLine: true, + child: bio, ), ], ),