be-components 5.8.1 → 5.8.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (108) hide show
  1. package/lib/commonjs/Campaign/api/index.js +124 -0
  2. package/lib/commonjs/Campaign/api/index.js.map +1 -1
  3. package/lib/commonjs/Campaign/components/ActionList.js +46 -9
  4. package/lib/commonjs/Campaign/components/ActionList.js.map +1 -1
  5. package/lib/commonjs/Campaign/components/BetAlert.js +22 -10
  6. package/lib/commonjs/Campaign/components/BetAlert.js.map +1 -1
  7. package/lib/commonjs/Campaign/components/CampaignAnalytics.js +142 -11
  8. package/lib/commonjs/Campaign/components/CampaignAnalytics.js.map +1 -1
  9. package/lib/commonjs/Campaign/components/NewPlayerAlert.js +139 -0
  10. package/lib/commonjs/Campaign/components/NewPlayerAlert.js.map +1 -0
  11. package/lib/commonjs/Campaign/components/ParticipantCard.js +5 -0
  12. package/lib/commonjs/Campaign/components/ParticipantCard.js.map +1 -1
  13. package/lib/commonjs/Campaign/components/ParticipantsList.js +0 -1
  14. package/lib/commonjs/Campaign/components/ParticipantsList.js.map +1 -1
  15. package/lib/commonjs/Campaign/index.js +564 -222
  16. package/lib/commonjs/Campaign/index.js.map +1 -1
  17. package/lib/commonjs/MarketComponents/api/index.js +21 -0
  18. package/lib/commonjs/MarketComponents/api/index.js.map +1 -1
  19. package/lib/commonjs/Ticker/index.js +112 -26
  20. package/lib/commonjs/Ticker/index.js.map +1 -1
  21. package/lib/module/Campaign/api/index.js +124 -0
  22. package/lib/module/Campaign/api/index.js.map +1 -1
  23. package/lib/module/Campaign/components/ActionList.js +46 -9
  24. package/lib/module/Campaign/components/ActionList.js.map +1 -1
  25. package/lib/module/Campaign/components/BetAlert.js +22 -10
  26. package/lib/module/Campaign/components/BetAlert.js.map +1 -1
  27. package/lib/module/Campaign/components/CampaignAnalytics.js +144 -13
  28. package/lib/module/Campaign/components/CampaignAnalytics.js.map +1 -1
  29. package/lib/module/Campaign/components/NewPlayerAlert.js +132 -0
  30. package/lib/module/Campaign/components/NewPlayerAlert.js.map +1 -0
  31. package/lib/module/Campaign/components/ParticipantCard.js +5 -0
  32. package/lib/module/Campaign/components/ParticipantCard.js.map +1 -1
  33. package/lib/module/Campaign/components/ParticipantsList.js +0 -1
  34. package/lib/module/Campaign/components/ParticipantsList.js.map +1 -1
  35. package/lib/module/Campaign/index.js +564 -222
  36. package/lib/module/Campaign/index.js.map +1 -1
  37. package/lib/module/MarketComponents/api/index.js +21 -0
  38. package/lib/module/MarketComponents/api/index.js.map +1 -1
  39. package/lib/module/Ticker/index.js +115 -29
  40. package/lib/module/Ticker/index.js.map +1 -1
  41. package/lib/typescript/lib/commonjs/Campaign/api/index.d.ts +11 -0
  42. package/lib/typescript/lib/commonjs/Campaign/api/index.d.ts.map +1 -1
  43. package/lib/typescript/lib/commonjs/Campaign/components/ActionList.d.ts +4 -1
  44. package/lib/typescript/lib/commonjs/Campaign/components/ActionList.d.ts.map +1 -1
  45. package/lib/typescript/lib/commonjs/Campaign/components/BetAlert.d.ts +3 -1
  46. package/lib/typescript/lib/commonjs/Campaign/components/BetAlert.d.ts.map +1 -1
  47. package/lib/typescript/lib/commonjs/Campaign/components/CampaignAnalytics.d.ts +4 -2
  48. package/lib/typescript/lib/commonjs/Campaign/components/CampaignAnalytics.d.ts.map +1 -1
  49. package/lib/typescript/lib/commonjs/Campaign/components/NewPlayerAlert.d.ts +10 -0
  50. package/lib/typescript/lib/commonjs/Campaign/components/NewPlayerAlert.d.ts.map +1 -0
  51. package/lib/typescript/lib/commonjs/Campaign/components/ParticipantCard.d.ts +3 -1
  52. package/lib/typescript/lib/commonjs/Campaign/components/ParticipantCard.d.ts.map +1 -1
  53. package/lib/typescript/lib/commonjs/Campaign/components/ParticipantsList.d.ts.map +1 -1
  54. package/lib/typescript/lib/commonjs/Campaign/index.d.ts +8 -5
  55. package/lib/typescript/lib/commonjs/Campaign/index.d.ts.map +1 -1
  56. package/lib/typescript/lib/commonjs/MarketComponents/api/index.d.ts +1 -0
  57. package/lib/typescript/lib/commonjs/MarketComponents/api/index.d.ts.map +1 -1
  58. package/lib/typescript/lib/commonjs/Ticker/index.d.ts +2 -1
  59. package/lib/typescript/lib/commonjs/Ticker/index.d.ts.map +1 -1
  60. package/lib/typescript/lib/module/Campaign/api/index.d.ts +11 -0
  61. package/lib/typescript/lib/module/Campaign/api/index.d.ts.map +1 -1
  62. package/lib/typescript/lib/module/Campaign/components/ActionList.d.ts +4 -1
  63. package/lib/typescript/lib/module/Campaign/components/ActionList.d.ts.map +1 -1
  64. package/lib/typescript/lib/module/Campaign/components/BetAlert.d.ts +3 -1
  65. package/lib/typescript/lib/module/Campaign/components/BetAlert.d.ts.map +1 -1
  66. package/lib/typescript/lib/module/Campaign/components/CampaignAnalytics.d.ts +4 -2
  67. package/lib/typescript/lib/module/Campaign/components/CampaignAnalytics.d.ts.map +1 -1
  68. package/lib/typescript/lib/module/Campaign/components/NewPlayerAlert.d.ts +10 -0
  69. package/lib/typescript/lib/module/Campaign/components/NewPlayerAlert.d.ts.map +1 -0
  70. package/lib/typescript/lib/module/Campaign/components/ParticipantCard.d.ts +3 -1
  71. package/lib/typescript/lib/module/Campaign/components/ParticipantCard.d.ts.map +1 -1
  72. package/lib/typescript/lib/module/Campaign/components/ParticipantsList.d.ts.map +1 -1
  73. package/lib/typescript/lib/module/Campaign/index.d.ts +8 -5
  74. package/lib/typescript/lib/module/Campaign/index.d.ts.map +1 -1
  75. package/lib/typescript/lib/module/MarketComponents/api/index.d.ts +1 -0
  76. package/lib/typescript/lib/module/MarketComponents/api/index.d.ts.map +1 -1
  77. package/lib/typescript/lib/module/Ticker/index.d.ts +2 -1
  78. package/lib/typescript/lib/module/Ticker/index.d.ts.map +1 -1
  79. package/lib/typescript/src/Campaign/api/index.d.ts +21 -6
  80. package/lib/typescript/src/Campaign/api/index.d.ts.map +1 -1
  81. package/lib/typescript/src/Campaign/components/ActionList.d.ts +5 -2
  82. package/lib/typescript/src/Campaign/components/ActionList.d.ts.map +1 -1
  83. package/lib/typescript/src/Campaign/components/BetAlert.d.ts +4 -2
  84. package/lib/typescript/src/Campaign/components/BetAlert.d.ts.map +1 -1
  85. package/lib/typescript/src/Campaign/components/CampaignAnalytics.d.ts +6 -3
  86. package/lib/typescript/src/Campaign/components/CampaignAnalytics.d.ts.map +1 -1
  87. package/lib/typescript/src/Campaign/components/NewPlayerAlert.d.ts +12 -0
  88. package/lib/typescript/src/Campaign/components/NewPlayerAlert.d.ts.map +1 -0
  89. package/lib/typescript/src/Campaign/components/ParticipantCard.d.ts +4 -2
  90. package/lib/typescript/src/Campaign/components/ParticipantCard.d.ts.map +1 -1
  91. package/lib/typescript/src/Campaign/index.d.ts +7 -4
  92. package/lib/typescript/src/Campaign/index.d.ts.map +1 -1
  93. package/lib/typescript/src/MarketComponents/api/index.d.ts +3 -2
  94. package/lib/typescript/src/MarketComponents/api/index.d.ts.map +1 -1
  95. package/lib/typescript/src/Ticker/index.d.ts +2 -1
  96. package/lib/typescript/src/Ticker/index.d.ts.map +1 -1
  97. package/package.json +1 -1
  98. package/src/Campaign/api/index.ts +86 -4
  99. package/src/Campaign/components/ActionList.tsx +38 -13
  100. package/src/Campaign/components/BetAlert.tsx +15 -6
  101. package/src/Campaign/components/CampaignAnalytics.tsx +76 -13
  102. package/src/Campaign/components/NewPlayerAlert.tsx +81 -0
  103. package/src/Campaign/components/ParticipantCard.tsx +7 -2
  104. package/src/Campaign/components/ParticipantsList.tsx +1 -1
  105. package/src/Campaign/index.tsx +421 -188
  106. package/src/MarketComponents/api/index.ts +16 -2
  107. package/src/Ticker/index.tsx +64 -32
  108. package/src/types.d.ts +3 -0
@@ -5,7 +5,8 @@ type TickerProps = {
5
5
  color_mode?: 'light' | 'dark';
6
6
  distinct_id?: string;
7
7
  onOrders?: (orders: OrderProps[]) => void;
8
+ onCreateOrder?: (order: OrderProps) => void;
8
9
  };
9
- declare const Ticker: ({ league_ids, color_mode, distinct_id, onOrders }: TickerProps) => React.JSX.Element;
10
+ declare const Ticker: ({ league_ids, color_mode, distinct_id, onOrders, onCreateOrder }: TickerProps) => React.JSX.Element;
10
11
  export default Ticker;
11
12
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/Ticker/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA8B,MAAM,OAAO,CAAC;AAEnD,OAAO,KAAK,EAA0E,UAAU,EAA0C,MAAM,UAAU,CAAC;AAW3J,KAAK,WAAW,GAAG;IACf,UAAU,EAAC,MAAM,EAAE,CAAC;IACpB,UAAU,CAAC,EAAC,OAAO,GAAC,MAAM,CAAC;IAC3B,WAAW,CAAC,EAAC,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAC,CAAC,MAAM,EAAC,UAAU,EAAE,KAAK,IAAI,CAAA;CAC1C,CAAA;AAKD,QAAA,MAAM,MAAM,GAAI,mDAAkD,WAAW,sBAsP5E,CAAA;AAED,eAAe,MAAM,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/Ticker/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA8B,MAAM,OAAO,CAAC;AAEnD,OAAO,KAAK,EAA0E,UAAU,EAA0C,MAAM,UAAU,CAAC;AAY3J,KAAK,WAAW,GAAG;IACf,UAAU,EAAC,MAAM,EAAE,CAAC;IACpB,UAAU,CAAC,EAAC,OAAO,GAAC,MAAM,CAAC;IAC3B,WAAW,CAAC,EAAC,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAC,CAAC,MAAM,EAAC,UAAU,EAAE,KAAK,IAAI,CAAC;IACxC,aAAa,CAAC,EAAC,CAAC,KAAK,EAAC,UAAU,KAAK,IAAI,CAAA;CAC5C,CAAA;AAKD,QAAA,MAAM,MAAM,GAAI,kEAAiE,WAAW,sBAoR3F,CAAA;AAED,eAAe,MAAM,CAAA"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "be-components",
3
- "version": "5.8.1",
3
+ "version": "5.8.2",
4
4
  "description": "Components for BettorEdge Apps",
5
5
  "main": "lib/commonjs/index",
6
6
  "module": "lib/module/index",
@@ -1,13 +1,14 @@
1
1
 
2
2
  import axios from 'axios';
3
- import type { CampaignParticipantProps, CampaignProps, OrderAnalyticsProps, OrderProps, OverallOrderAnalyticsProps, PublicPlayerProps } from '../../types';
3
+ import type { CampaignParticipantProps, CampaignProps, CompetitionProps, EventProps, MatchProps, NewOverallAnalytics, OrderAnalyticsProps, OrderProps, PollCampaignProps, PublicPlayerProps, TournamentProps } from '../../types';
4
4
  import { APIOverrides } from '../../ApiOverrides';
5
- import moment from 'moment-mini';
5
+ import moment, { type Moment } from 'moment-mini';
6
6
 
7
7
  //let SOCIAL_SVC_API = '';
8
8
  //let EVENT_SVC_API = '';
9
9
  let MK_SVC_API = '';
10
10
  let AUTH_SVC_API = '';
11
+ let TP_SVC_API = ''
11
12
 
12
13
  export const CampaignApi = {
13
14
  setEnvironment: () => {
@@ -16,6 +17,7 @@ export const CampaignApi = {
16
17
  //EVENT_SVC_API = endpoints['EVENT_SVC_API'] as string;
17
18
  MK_SVC_API = endpoints['MK_SVC_API'] as string;
18
19
  AUTH_SVC_API = endpoints['AUTH_SVC_API'] as string;
20
+ TP_SVC_API = endpoints['TP_SVC_API'] as string;
19
21
 
20
22
  },
21
23
  getPlayersByPlayerIds : async(player_ids:string[]):Promise<PublicPlayerProps[]> => {
@@ -35,6 +37,51 @@ export const CampaignApi = {
35
37
  return { campaign: undefined, campaign_participants:[] }
36
38
  }
37
39
  },
40
+ getPollCampaignsByIds: async(poll_campaign_ids:string[]):Promise<PollCampaignProps[]> => {
41
+ try {
42
+ if(poll_campaign_ids.length == 0){ return [] }
43
+ const resp = await axios.post(`${AUTH_SVC_API}/v1/polls/campaigns/bulk/get`, { poll_campaign_ids });
44
+ return resp.data.poll_campaigns
45
+ } catch (e) {
46
+ console.log(e)
47
+ return []
48
+ }
49
+ },
50
+ getCompetitionsByIds: async(competition_ids:string[]):Promise<CompetitionProps[]> => {
51
+ try {
52
+ if(competition_ids.length == 0){ return [] }
53
+ const resp = await axios.post(`${TP_SVC_API}/v2/competitions/bulk/get`, { competition_ids });
54
+ return resp.data.competitions
55
+ } catch (e) {
56
+ console.log(e)
57
+ return []
58
+ }
59
+ },
60
+ joinCampaign: async(campaign_id:string):Promise<CampaignParticipantProps|undefined> => {
61
+ try {
62
+ const resp = await axios.post(`${AUTH_SVC_API}/v1/campaigns/campaign/join`, { campaign_id });
63
+ return resp.data.campaign_participant
64
+ } catch (e) {
65
+ console.log(e)
66
+ return undefined
67
+ }
68
+ },
69
+ leaveCampaign: async(campaign_participant_id:string):Promise<CampaignParticipantProps|undefined> => {
70
+ try {
71
+ const resp = await axios.post(`${AUTH_SVC_API}/v1/campaigns/campaign/leave`, { campaign_participant_id });
72
+ return resp.data.campaign_participant
73
+ } catch (e) {
74
+ return undefined
75
+ }
76
+ },
77
+ getMyCampaignParticipants: async():Promise<{ campaigns:CampaignProps[], campaign_participants:CampaignParticipantProps[] }> => {
78
+ try {
79
+ const resp = await axios.get(`${AUTH_SVC_API}/v1/campaigns/participant/me`);
80
+ return resp.data
81
+ } catch (e) {
82
+ return { campaigns:[], campaign_participants:[] }
83
+ }
84
+ },
38
85
  getCampaignAction: async(campaign_id:string):Promise<OrderProps[]> => {
39
86
  try {
40
87
  const resp = await axios.get(`${MK_SVC_API}/v1/orders/campaign/action/${campaign_id}`);
@@ -53,9 +100,8 @@ export const CampaignApi = {
53
100
  }
54
101
  }
55
102
  }
56
-
57
103
  export const CampaignHelpers = {
58
- aggregateAnalytics: (analytics:OrderAnalyticsProps[]):OverallOrderAnalyticsProps&{roi_pct:number, win_pct:number, earnings:number} => {
104
+ aggregateAnalytics: (analytics:OrderAnalyticsProps[]):NewOverallAnalytics => {
59
105
  const wins = analytics.reduce((a,b) => a + b.wins, 0);
60
106
  const losses = analytics.reduce((a,b) => a + b.losses, 0);
61
107
  const draws = analytics.reduce((a,b) => a + b.draws, 0);
@@ -82,11 +128,47 @@ export const CampaignHelpers = {
82
128
  roi_pct
83
129
  }
84
130
  },
131
+ getCampaignLeaderboard: (analytics:OrderAnalyticsProps[]):NewOverallAnalytics[] => {
132
+ let unique_player_ids = [ ...new Set(analytics.map(a => a.player_id)) ]
133
+ let overall_analytics:NewOverallAnalytics[] = []
134
+ unique_player_ids.map(id => {
135
+ let anals = analytics.filter(a => a.player_id == id);
136
+ let agg_analytics = CampaignHelpers.aggregateAnalytics(anals)
137
+ overall_analytics.push({ ...agg_analytics, player_id: id })
138
+ });
139
+ return overall_analytics.sort((a,b) => b.earnings - a.earnings);
140
+ },
85
141
  getTimeOptions: () => {
86
142
  const time_options = [
87
143
  { label: 'All Time', to: moment().unix(), from: moment().subtract(7, 'years').unix() },
88
144
  { label: 'Last 7 Days', to: moment().unix(), from: moment().subtract(7, 'days').unix() }
89
145
  ]
90
146
  return time_options
147
+ },
148
+ getContestDetails: (contest_type:'team'|'tournament'|'match', event?:EventProps, tournament?:TournamentProps, match?:MatchProps) => {
149
+ const default_response = { contest_title: '', contest_details:'' }
150
+ switch(contest_type){
151
+ case 'team':
152
+ if(!event){ return default_response }
153
+ let details = ['created','scheduled'].includes(event.status) ? moment(event.scheduled_datetime).format('MMM dd hh:mm a') : event.status
154
+ return { contest_title: event.event_title, contest_details: details }
155
+ case 'tournament':
156
+ if(!tournament){ return default_response }
157
+ return { contest_title:tournament.tournament_name, contest_details: moment(tournament.scheduled_datetime).format('MMM dd hh:mm a') }
158
+ case 'match':
159
+ if(!match){ return default_response }
160
+ return { contest_title:match.match_title, contest_details: moment(match.scheduled_datetime).format('MMM dd hh:mm a') }
161
+ default: return default_response
162
+ }
163
+ },
164
+ sortEngagements: (competitions:CompetitionProps[], poll_campaigns:PollCampaignProps[]) => {
165
+ let sorted_engagements: { id:string, type:'poll_campaign'|'competition', scheduled_datetime:Moment }[] = []
166
+ competitions.map(c =>
167
+ sorted_engagements.push({ id: c.competition_id, type:'competition', scheduled_datetime: moment(c.scheduled_datetime) })
168
+ )
169
+ poll_campaigns.map(pc =>
170
+ sorted_engagements.push({ id:pc.poll_campaign_id, type:'poll_campaign', scheduled_datetime:moment().add(2, 'hours') })
171
+ )
172
+ return sorted_engagements.sort((a,b) => a.scheduled_datetime.unix() - b.scheduled_datetime.unix())
91
173
  }
92
174
  }
@@ -1,26 +1,36 @@
1
1
  import React from 'react';
2
2
  import { Text, View } from "../../Components/Themed"
3
- import type { EventProps, OrderProps, PublicPlayerProps } from "../../types"
3
+ import type { EventProps, MatchProps, OrderProps, PublicPlayerProps, TournamentProps } from "../../types"
4
4
  import { FlatList, Image } from 'react-native';
5
5
  import moment from 'moment-mini';
6
6
  import OrderGradeBar from '../../MarketComponents/components/OrderGradeBar';
7
+ import { CampaignHelpers } from '../api';
8
+ import { MarketComponentHelpers } from '../../MarketComponents/api';
9
+ import { Icons } from '../../Components';
10
+ import { useColors } from '../../constants/useColors';
7
11
 
8
12
  type ActionListProps = {
9
13
  orders:OrderProps[],
10
14
  events:EventProps[],
15
+ tournaments:TournamentProps[],
16
+ matches:MatchProps[],
17
+ hide_header?:boolean,
11
18
  players:PublicPlayerProps[]
12
19
  }
13
20
 
14
- const ActionList = ({ orders, events, players }:ActionListProps) => {
15
-
21
+ const ActionList = ({ orders, events, players, tournaments, matches, hide_header }:ActionListProps) => {
22
+ const Colors = useColors();
16
23
  const renderAction = (data:{ item:OrderProps, index:number }) => {
17
24
  const event = events.find(e => e.event_id == data.item.event_id);
18
- if(!event){ return <></> }
25
+ const tournament = tournaments.find(t => t.tournament_id == data.item.event_id);
26
+ const match = matches.find(m => m.match_id == data.item.event_id);
27
+ const { contest_title } = CampaignHelpers.getContestDetails(data.item.event_type, event, tournament, match);
28
+
19
29
  const player = players.find(p => p.player_id == data.item.player_id)
20
30
  return (
21
- <View float style={{ margin:10 }}>
31
+ <View float style={{ margin:5 }}>
22
32
  <View type='header' style={{ flexDirection:'row', alignItems:'center', padding:8, borderTopRightRadius:8, borderTopLeftRadius:8 }}>
23
- <Text style={{ flex:1 }} theme='h2'>{event.event_title}</Text>
33
+ <Text style={{ flex:1 }} theme='h2'>{contest_title}</Text>
24
34
  <Text theme='action'>{moment(data.item.create_datetime).fromNow()}</Text>
25
35
  </View>
26
36
  <View transparent style={{ flexDirection:'row', alignItems:'center', padding:10 }}>
@@ -42,7 +52,11 @@ const ActionList = ({ orders, events, players }:ActionListProps) => {
42
52
  view_type='book'
43
53
  />
44
54
  </View>
45
- :<></>}
55
+ :
56
+ <View transparent>
57
+ <Text theme='h1'>{MarketComponentHelpers.getOddsLabel(data.item.odds)}</Text>
58
+ </View>
59
+ }
46
60
  </View>
47
61
  </View>
48
62
  )
@@ -51,12 +65,23 @@ const ActionList = ({ orders, events, players }:ActionListProps) => {
51
65
 
52
66
  return (
53
67
  <View transparent style={{ flex:1 }}>
54
- <FlatList
55
- data={orders}
56
- renderItem={renderAction}
57
- keyExtractor={(item) => item.order_id.toString()}
58
- key={'campaign_action'}
59
- />
68
+ {!hide_header ?
69
+ <View type='header' style={{ flexDirection:'row', alignItems:'center', padding:10 }}>
70
+ <Icons.ActivityIcon size={20} color={Colors.text.h1} />
71
+ <View transparent style={{ flex:1, marginLeft:10 }}>
72
+ <Text theme='h1'>Recent Action</Text>
73
+ <Text theme='description' style={{ marginTop:3 }}>Action placed while checked in</Text>
74
+ </View>
75
+ </View>
76
+ :<></>}
77
+ <View>
78
+ <FlatList
79
+ data={orders}
80
+ renderItem={renderAction}
81
+ keyExtractor={(item) => item.order_id.toString()}
82
+ key={'campaign_action'}
83
+ />
84
+ </View>
60
85
  </View>
61
86
  )
62
87
  }
@@ -1,7 +1,7 @@
1
1
  import { Image } from "react-native";
2
2
  import { Icons } from "../../Components";
3
3
  import { Text, View } from "../../Components/Themed";
4
- import type { AthleteProps, EventProps, OrderProps, PublicPlayerProps, TeamProps } from "../../types"
4
+ import type { AthleteProps, EventProps, LeagueProps, OrderProps, PublicPlayerProps, TeamProps, TournamentProps } from "../../types"
5
5
  import React from 'react';
6
6
  import OrderGradeBar from "../../MarketComponents/components/OrderGradeBar";
7
7
  import { MarketComponentHelpers } from "../../MarketComponents/api";
@@ -9,19 +9,22 @@ import QRCode from "react-qr-code";
9
9
  import { useColors } from "../../constants/useColors";
10
10
  import moment from "moment-mini";
11
11
  import ProgressTimer from "./ProgressTimer";
12
+ import { AthleteImage } from "../../Components/Jerseys";
12
13
 
13
14
  type BetAlertProps = {
14
15
  order:OrderProps,
16
+ league?:LeagueProps,
15
17
  team?:TeamProps,
16
18
  athlete?:AthleteProps,
17
19
  event?:EventProps,
20
+ tournament?:TournamentProps,
18
21
  player?:PublicPlayerProps,
19
22
  color_mode?:'light'|'dark'
20
23
 
21
24
  onClose:() => void
22
25
  }
23
26
 
24
- const BetAlert = ({ player, order, team, athlete, event, color_mode, onClose }:BetAlertProps) => {
27
+ const BetAlert = ({ player, order, league, team, athlete, event, tournament, color_mode, onClose }:BetAlertProps) => {
25
28
  const Colors = useColors({ mode: color_mode });
26
29
 
27
30
  return (
@@ -52,6 +55,11 @@ const BetAlert = ({ player, order, team, athlete, event, color_mode, onClose }:B
52
55
  <Text theme='h2'>{event.home?.market_name}</Text>
53
56
  </View>
54
57
  :<></>}
58
+ {tournament ?
59
+ <View style={{ flexDirection:'row', alignItems:'center', justifyContent:'center', padding:10 }}>
60
+ <Text theme='h1' style={{ marginRight:20, marginLeft:20 }}>{tournament.tournament_name}</Text>
61
+ </View>
62
+ :<></>}
55
63
  {player ?
56
64
  <View>
57
65
  <Image
@@ -68,10 +76,11 @@ const BetAlert = ({ player, order, team, athlete, event, color_mode, onClose }:B
68
76
  resizeMode='cover'
69
77
  />
70
78
  :athlete ?
71
- <Image
72
- source={{ uri: athlete.image?.url }}
73
- style={{ height:60, width:60 }}
74
- resizeMode='cover'
79
+ <AthleteImage
80
+ athlete={athlete}
81
+ size={40}
82
+ number_size={18}
83
+ league={league}
75
84
  />
76
85
  :<></>}
77
86
 
@@ -1,18 +1,24 @@
1
1
  import React, { useEffect, useState } from 'react';
2
- import { View } from "../../Components/Themed"
2
+ import { Text, View } from "../../Components/Themed"
3
3
  import moment from 'moment-mini';
4
- import { CampaignApi } from '../api';
5
- import type { OrderAnalyticsProps } from '../../types';
4
+ import { CampaignApi, CampaignHelpers } from '../api';
5
+ import type { CampaignParticipantProps, NewOverallAnalytics, OrderAnalyticsProps, PublicPlayerProps } from '../../types';
6
+ import { ActivityIndicator, FlatList, Image } from 'react-native';
7
+ import { useColors } from '../../constants/useColors';
8
+ import { Icons } from '../../Components';
9
+ import { CompetitionHelpers } from '../../Competition/api';
6
10
 
7
11
 
8
- type CampaignAnalyticsProps = {
9
- campaign_id:string
12
+ type CampaignLeaderboardProps = {
13
+ campaign_id:string,
14
+ players:PublicPlayerProps[],
15
+ campaign_participants:CampaignParticipantProps[]
10
16
  }
11
17
 
12
- const CampaignAnalytics = ({ campaign_id }:CampaignAnalyticsProps) => {
13
-
18
+ const CampaignLeaderboard = ({ campaign_id, players, campaign_participants }:CampaignLeaderboardProps) => {
19
+ const Colors = useColors();
14
20
  const time_options = [
15
- { label: 'Last 7 Days', to: moment().unix(), from: moment().subtract(7, 'days').unix() }
21
+ { label: 'Last Year', to: moment().unix(), from: moment().subtract(365, 'days').unix() }
16
22
  ]
17
23
 
18
24
  const [ module_state, setModuleState ] = useState<{
@@ -20,11 +26,11 @@ const CampaignAnalytics = ({ campaign_id }:CampaignAnalyticsProps) => {
20
26
  time_option: any,
21
27
  analytics:OrderAnalyticsProps[]
22
28
  }>({
23
- loading:false,
29
+ loading:true,
24
30
  time_option: time_options[0],
25
31
  analytics: []
26
32
  });
27
- //const { analytics } = module_state;
33
+ const { loading, analytics } = module_state;
28
34
 
29
35
  useEffect(() => {
30
36
  let option = time_options[0]
@@ -34,20 +40,77 @@ const CampaignAnalytics = ({ campaign_id }:CampaignAnalyticsProps) => {
34
40
 
35
41
  const handleLoadAnalytics = async(option:{ label:string, to:number, from:number }) => {
36
42
  CampaignApi.setEnvironment();
43
+ setModuleState({ ...module_state, loading:true });
37
44
  const analytics = await CampaignApi.getCampaignAnalytics(campaign_id, option.to, option.from);
38
45
  setModuleState({
39
46
  ...module_state,
47
+ loading:false,
40
48
  time_option: option,
41
49
  analytics
42
50
  })
43
51
  }
44
52
 
45
- //const agg = CampaignHelpers.aggregateAnalytics(analytics)
53
+ const renderLeaders = (data:{ item:NewOverallAnalytics, index:number }) => {
54
+ const player = players.find(p => p.player_id == data.item.player_id);
55
+ if(!player){ return <></> }
56
+ const participant = campaign_participants.find(cp => cp.player_id == data.item.player_id);
57
+ return (
58
+ <View style={{ flexDirection:'row', alignItems:'center', padding:10, borderBottomWidth:1, borderColor:Colors.borders.light }}>
59
+ <View transparent style={{ paddingRight:10, borderRightWidth:1, borderColor:Colors.borders.light }}>
60
+ <Text theme='h1'>{CompetitionHelpers.formatPlace(data.index + 1)}</Text>
61
+ </View>
62
+ <Image
63
+ source={{ uri: player.profile_pic && player.profile_pic != '' ? player.profile_pic : 'https://res.cloudinary.com/hoabts6mc/image/upload/v1722453927/default_man_n96ofq.webp' }}
64
+ style={{ height:40, width:40, borderRadius:100, marginLeft:10 }}
65
+ />
66
+ <View transparent style={{ flex:1, marginLeft:10 }}>
67
+ <Text theme='h1'>@{player.username}</Text>
68
+ {participant ?
69
+ <Text theme='description' style={{ marginTop:3 }}>First checked in {moment(participant.create_datetime).fromNow()}</Text>
70
+ :<></>}
71
+ </View>
72
+ <View>
73
+ <Text theme='description' color={data.item.roi_pct >= 0 ? Colors.text.success : Colors.text.error}>{(data.item.roi_pct * 100).toFixed(2)}%</Text>
74
+ </View>
75
+ </View>
76
+ )
77
+ }
78
+
79
+ const leaders = CampaignHelpers.getCampaignLeaderboard(analytics);
46
80
  return (
47
81
  <View>
48
-
82
+ <View type='header' style={{ flexDirection:'row', alignItems:'center', padding:10 }}>
83
+ <Icons.LeaderboardIcon size={28} color={Colors.text.h1} />
84
+ <View transparent style={{ flex:1, marginLeft:10 }}>
85
+ <Text theme='h1'>Leaderboard</Text>
86
+ <Text theme='description' style={{ marginTop:3 }}>Leaders based on action placed while checked in</Text>
87
+ </View>
88
+ <View transparent style={{ marginLeft:5 }}>
89
+ <Text theme='action'>ROI %</Text>
90
+ </View>
91
+ </View>
92
+ <View transparent>
93
+ {loading ?
94
+ <ActivityIndicator style={{ margin:20 }} size='large' color={Colors.text.h1} />
95
+ :<></>}
96
+ {leaders.length > 0 ?
97
+ <FlatList
98
+ data={leaders}
99
+ key={'campaign_leaders'}
100
+ keyExtractor={(item) => item.player_id.toString()}
101
+ renderItem={renderLeaders}
102
+ />
103
+ : !loading ?
104
+ <View style={{ alignItems:'center', padding:10 }}>
105
+ <View float style={{ height:120, width:120, borderRadius:8, padding:10, justifyContent:'center', alignItems:'center' }}>
106
+ <Icons.LeaderboardIcon size={36} color={Colors.text.h1} />
107
+ <Text theme='h1' style={{ marginTop:10 }} textAlign='center'>No Data Yet!</Text>
108
+ </View>
109
+ </View>
110
+ :<></>}
111
+ </View>
49
112
  </View>
50
113
  )
51
114
  }
52
115
 
53
- export default CampaignAnalytics
116
+ export default CampaignLeaderboard
@@ -0,0 +1,81 @@
1
+ import React from 'react';
2
+ import { Button, Text, View } from "../../Components/Themed"
3
+ import type { CampaignParticipantProps, PublicPlayerProps } from "../../types"
4
+ import { Icons } from '../../Components';
5
+ import { useColors } from '../../constants/useColors';
6
+ import moment from 'moment-mini';
7
+ import { Image } from 'react-native';
8
+ import ProgressTimer from './ProgressTimer';
9
+ import QRCode from 'react-qr-code';
10
+
11
+ type NewPlayerAlertProps = {
12
+ view_mode:'desktop'|'mobile',
13
+ player:PublicPlayerProps,
14
+ campaign_participant:CampaignParticipantProps,
15
+ onViewProfile?:(player:PublicPlayerProps) => void
16
+ onClose:() => void
17
+ }
18
+
19
+ const NewPlayerAlert = ({ player, view_mode, campaign_participant, onClose, onViewProfile }:NewPlayerAlertProps) => {
20
+ const Colors = useColors();
21
+ return (
22
+ <View float style={{ width:350 }}>
23
+ <View type='header' style={{ flexDirection:'row', alignItems:'center', padding:18, borderTopRightRadius:8, borderTopLeftRadius:8 }}>
24
+ <Icons.BettorEdgeIcon size={18} color={Colors.text.h1} />
25
+ <View transparent style={{ flex:1, marginLeft:20, marginRight:10 }}>
26
+ <Text theme='h1'>NEW PLAYER ALERT!</Text>
27
+ <Text theme='description' style={{ marginTop:5 }}>@{player?.username} {`\u2022`} First Checked In {moment(campaign_participant.create_datetime).fromNow()}</Text>
28
+ </View>
29
+ </View>
30
+ <View type='body'>
31
+ <Image
32
+ source={{ uri: player.profile_pic && player.profile_pic != '' ? player.profile_pic : 'https://res.cloudinary.com/hoabts6mc/image/upload/v1722453927/default_man_n96ofq.webp' }}
33
+ style={{ height:200, width:350 }}
34
+ resizeMode='cover'
35
+ />
36
+ <View type='header' style={{ flexDirection:'row', alignItems:'center', padding:10 }}>
37
+ <View transparent style={{ flex:1, marginLeft:10 }}>
38
+ <Text theme='h1'>@{player.username}</Text>
39
+ <Text style={{ marginTop:3 }} theme='description'>Joined BettorEdge {moment(player.create_datetime).fromNow()}</Text>
40
+ </View>
41
+ </View>
42
+ {view_mode == 'desktop' ?
43
+ <View type='header' style={{alignItems:'center', padding:10}}>
44
+ <QRCode
45
+ size={100}
46
+ value={`https://play.bettoredge.com/social/player/${campaign_participant.player_id}`}
47
+ />
48
+ <Text textAlign='center' theme='h2' style={{ marginTop:4 }}>CHECK OUT MY PROFILE</Text>
49
+ </View>
50
+ :<></>}
51
+ </View>
52
+ <View type='footer' style={{ borderBottomRightRadius:view_mode == 'desktop' ? 8: 0, borderBottomLeftRadius:view_mode == 'desktop'?8:0 }}>
53
+ <ProgressTimer
54
+ onTimesUp={() => onClose()}
55
+ time_id={campaign_participant.campaign_participant_id.toString()}
56
+ total_time={15}
57
+ />
58
+ </View>
59
+ {view_mode == 'mobile' ?
60
+ <View type='footer' style={{ flexDirection:'row', alignItems:'center', borderBottomRightRadius:8, borderBottomLeftRadius:8, padding:10 }}>
61
+ {onViewProfile ?
62
+ <Button
63
+ title='View Profile'
64
+ type='success'
65
+ style={{ flex:1, marginRight:3 }}
66
+ onPress={() => onViewProfile(player)}
67
+ />
68
+ :<></>}
69
+ <Button
70
+ title='CLOSE'
71
+ type='error'
72
+ style={{ flex:1, marginLeft:3 }}
73
+ onPress={() => onClose()}
74
+ />
75
+ </View>
76
+ :<></>}
77
+ </View>
78
+ )
79
+ }
80
+
81
+ export default NewPlayerAlert
@@ -1,6 +1,6 @@
1
1
  import React from 'react';
2
2
  import { Text, View } from "../../Components/Themed"
3
- import type { CampaignParticipantProps, EventProps, OrderAnalyticsProps, OrderProps, PublicPlayerProps } from "../../types"
3
+ import type { CampaignParticipantProps, EventProps, MatchProps, OrderAnalyticsProps, OrderProps, PublicPlayerProps, TournamentProps } from "../../types"
4
4
  import { Image } from 'react-native';
5
5
  import moment from 'moment-mini';
6
6
  import ActionList from './ActionList';
@@ -11,10 +11,12 @@ type ParticipantCardProps = {
11
11
  campaign_participant:CampaignParticipantProps,
12
12
  player:PublicPlayerProps,
13
13
  orders:OrderProps[],
14
+ tournaments:TournamentProps[],
15
+ matches:MatchProps[],
14
16
  analytics:OrderAnalyticsProps[],
15
17
  events:EventProps[]
16
18
  }
17
- const ParticipantCard = ({ player, campaign_participant, orders, events, analytics }:ParticipantCardProps) => {
19
+ const ParticipantCard = ({ player, campaign_participant, orders, events, tournaments, matches, analytics }:ParticipantCardProps) => {
18
20
  const agg = CampaignHelpers.aggregateAnalytics(analytics);
19
21
 
20
22
  return (
@@ -67,6 +69,9 @@ const ParticipantCard = ({ player, campaign_participant, orders, events, analyti
67
69
  </View>
68
70
  <ActionList
69
71
  orders={orders}
72
+ hide_header
73
+ tournaments={tournaments}
74
+ matches={matches}
70
75
  players={[player]}
71
76
  events={events}
72
77
  />
@@ -44,7 +44,7 @@ const ParticipantsList = ({ campaign_participants, players, selected_participant
44
44
  }
45
45
 
46
46
  return (
47
- <View type='header' style={{ flex:1 }}>
47
+ <View style={{ flex:1 }}>
48
48
  <View type='header' style={{ flexDirection:'row', alignItems:'center', padding:10 }}>
49
49
  <View transparent style={{ flex:1, marginRight:10 }}>
50
50
  <Text theme='h1'>Participants</Text>