Compare commits
22 Commits
4cbed48308
...
master
Author | SHA1 | Date | |
---|---|---|---|
811964e519 | |||
020857a1e7 | |||
2d338824f8 | |||
234d08d0c1 | |||
ffe2c13cdf | |||
7bbe593dde | |||
09ebd98fb4 | |||
|
9b7136b1af | ||
|
db214d217e | ||
|
3749cf22b0 | ||
5b3ae8684e | |||
378c897959 | |||
1b42cd208b | |||
412dd57577 | |||
f93d8c5c67 | |||
|
cd5efc6921 | ||
|
0da7ccae42 | ||
|
fc85d2f8f6 | ||
|
7a49396823 | ||
e03d8b48af | |||
f96465ed56 | |||
0b3e58f05e |
BIN
Podręcznik użytkowania.pdf
Normal file
BIN
Podręcznik użytkowania.pdf
Normal file
Binary file not shown.
21
README.md
21
README.md
@ -1,4 +1,4 @@
|
||||
# Analiza piłkarska z aplikacją `CoachStats`
|
||||
# Aplikacja `CoachStats`
|
||||
|
||||
## Wstęp
|
||||
|
||||
@ -9,21 +9,18 @@ CoachStats to innowacyjne narzędzie służące do analizowania statystyk Expect
|
||||
- **Analiza XG:** Analiza XG dla danej sytuacji meczowej.
|
||||
- **Personalizowana makieta:** Możliwość tworzenia własnej makiety odpowiadającej sytuacji meczowej.
|
||||
|
||||
## Technologie
|
||||
## Uruchomienie
|
||||
|
||||
## Instalacja i Uruchomienie
|
||||
Aby uruchomić aktualną wersję aplikacji, wykonaj następujące kroki:
|
||||
|
||||
Aby uruchomić beta wersję aplikacji, wykonaj następujące kroki:
|
||||
1. **Uruchomienie serwera:** Aby uruchomić serwer należy wejść w [link](https://sg-server-ne4h.onrender.com/) oraz zaczekać do pojawienia się komunikatu o błędzie 404. Aplikacja korzysta z darmowej wersji obsługi serwera, stąd sposób jego uruchomienia nie jest standardowy.
|
||||
|
||||
1. **Uruchomienie Klienta:**
|
||||
Otwórz terminal w folderze `app` i uruchom następującą komendę:\
|
||||
`npm run dev`
|
||||
|
||||
2. **Uruchomienie Serwera Flask:**
|
||||
W innym terminalu, przejdź do folderu `app/src/flask-server` i uruchom serwer Flask przy użyciu poniższej komendy:\
|
||||
`python server.py`
|
||||
|
||||
2. **Uruchomienie aplikacji webowej** Po wykonaiu kroku 1 można wejść na właściwą stronę [aplikacji](https://statgoals.onrender.com/).
|
||||
|
||||
## Dane
|
||||
|
||||
- <https://statsbomb.com/what-we-do/soccer-data/>
|
||||
|
||||
## Szczegóły
|
||||
|
||||
Działanie aplikacji zostało opisane w podręczniku użytkownika znajdującym się w drzewie plików na repozytorium. Poza tym odsyłam do [repozytorium](https://git.wmi.amu.edu.pl/s478993/fantastyczne_gole) uniwersytetu na którym powstała aplikacja. Zawiera ono kod źródłowy aplikacji.
|
||||
|
BIN
app/src/assets/bramka.jpeg
Normal file
BIN
app/src/assets/bramka.jpeg
Normal file
Binary file not shown.
After Width: | Height: | Size: 87 KiB |
@ -5,11 +5,49 @@ import { Link } from "react-router-dom";
|
||||
|
||||
const Hero = () => {
|
||||
|
||||
const [isOpen, setIsOpen] = useState(false);
|
||||
const [gameMinute, setGameMinute] = useState('');
|
||||
|
||||
const toggleDropdown = () => setIsOpen(!isOpen);
|
||||
const handleMinuteChange = (e) => setGameMinute(e.target.value);
|
||||
const [firstShot, setfirstShot] = useState(0);
|
||||
const [oneOnOne, SetoneOnOne] = useState(0);
|
||||
const [afterAirDuel, SetafterAirDuele] = useState(0);
|
||||
const [openGoal, SetOpenGoal] = useState(0);
|
||||
const [afterDribbling, SetafterDribbling] = useState(0);
|
||||
const [redirect, SetRedirect] = useState(0);
|
||||
|
||||
const handleMinuteChange = (e) => { setGameMinute(e.target.value);
|
||||
//sentQuestion();
|
||||
}
|
||||
|
||||
const handleFirstShotChange = (event) => {
|
||||
setfirstShot(event.target.checked);
|
||||
//sentQuestion();
|
||||
};
|
||||
|
||||
const handleOneOnOneChange = (event) => {
|
||||
SetoneOnOne(event.target.checked);
|
||||
//sentQuestion();
|
||||
};
|
||||
|
||||
const handleAfterAirDuelChange = (event) => {
|
||||
SetafterAirDuele(event.target.checked);
|
||||
//sentQuestion();
|
||||
};
|
||||
|
||||
const handleOpenGoalChange = (event) => {
|
||||
SetOpenGoal(event.target.checked);
|
||||
//sentQuestion();
|
||||
};
|
||||
|
||||
const handleAfterDribblingChange = (event) => {
|
||||
SetafterDribbling(event.target.checked);
|
||||
//sentQuestion();
|
||||
};
|
||||
|
||||
const handleRedirectChange = (event) => {
|
||||
SetRedirect(event.target.checked);
|
||||
//sentQuestion();
|
||||
};
|
||||
|
||||
|
||||
const [data, setData] = useState("");
|
||||
//zmienne globalne
|
||||
@ -17,10 +55,24 @@ const Hero = () => {
|
||||
//przez listener nanoszący zawodników na boisko. 1 - strzelec , 2 - bramkarz , 3 - obronca, 4 - napasnik. zmienna przez aktywacje przycskówk bb1, bb2, bb3 i bb4
|
||||
|
||||
let active_bbt = "bbt1";
|
||||
const [number_of_defenders, setNumberOfDevenders] = useState(0);
|
||||
const [number_of_strikers, setNumberOfStrikers] = useState(0)
|
||||
const [number_of_goalkeepers, setNumberOfGoalkeppers] = useState(0);
|
||||
const [number_of_shooters,setNumberOfShooters] = useState(0);
|
||||
const [number_of_defenders, setNumberOfDevenders] = useState(()=>{
|
||||
return 0;
|
||||
});
|
||||
|
||||
const [number_of_strikers, setNumberOfStrikers] = useState(() => {
|
||||
return 0;
|
||||
})
|
||||
const [number_of_goalkeepers, setNumberOfGoalkeppers] = useState(()=>{
|
||||
return 0;
|
||||
});
|
||||
const [number_of_shooters,setNumberOfShooters] = useState(() => {
|
||||
return 0}
|
||||
);
|
||||
|
||||
const number_of_shooters_rev = React.useRef(number_of_shooters)
|
||||
const number_of_strikers_rev = React.useRef(number_of_strikers)
|
||||
const number_of_goalkeepers_rev = React.useRef(number_of_goalkeepers)
|
||||
const number_of_defenders_rev = React.useRef(number_of_defenders)
|
||||
|
||||
// zmienne globalne bedace danymi wejsciowymi do modelu
|
||||
|
||||
@ -30,10 +82,10 @@ const Hero = () => {
|
||||
var stricers = new Array;
|
||||
var defenders = new Array;
|
||||
|
||||
const [bodyPart,setBodyPart] = useState('prawa');
|
||||
const [technique,setTechnique] = useState('zwykly');
|
||||
const [actionType,setActionType] = useState('pozycyjny');
|
||||
const [shooterPossition,setPossition] = useState('napastnik');
|
||||
const [bodyPart,setBodyPart] = useState('Right Foot');
|
||||
const [technique,setTechnique] = useState('Normal');
|
||||
const [actionType,setActionType] = useState('Open Play');
|
||||
const [shooterPossition,setPossition] = useState('Center Forward');
|
||||
|
||||
//zamiana procentowych pozycji na kartezyjskie
|
||||
function konwerturX(x){
|
||||
@ -57,7 +109,6 @@ const Hero = () => {
|
||||
|
||||
// Reset Boiska
|
||||
function resetField() {
|
||||
|
||||
var footballField = document.getElementById('footballField');
|
||||
var footballs = document.querySelectorAll('.football');
|
||||
var list = document.getElementById('list')
|
||||
@ -69,13 +120,20 @@ const Hero = () => {
|
||||
players.forEach(function(element) {
|
||||
list.removeChild(element);
|
||||
})
|
||||
|
||||
setNumberOfDevenders(0);
|
||||
setNumberOfStrikers(0)
|
||||
setNumberOfGoalkeppers(0)
|
||||
setNumberOfShooters(0)
|
||||
setGameMinute('')
|
||||
|
||||
number_of_shooters_rev.current = 0;
|
||||
number_of_goalkeepers_rev.current = 0;
|
||||
number_of_defenders_rev.current = 0;
|
||||
number_of_strikers_rev.current = 0;
|
||||
|
||||
document.getElementById("ex").innerHTML = 0;
|
||||
}
|
||||
|
||||
|
||||
//funkcja dodaje zawodnika do listy zawodnikow. zmienne x oraz y to wspolrzedne a position
|
||||
// to pozycja zawodnika 0 - strzelec, 1 - bramkarz, 2 - broniacy, 3 napastnik
|
||||
// ball - to odnosnik do punktu na boisku
|
||||
@ -86,14 +144,15 @@ const Hero = () => {
|
||||
list.removeChild(player)
|
||||
bojo.removeChild(ball)
|
||||
if(possition == 1){
|
||||
setNumberOfGoalkeppers(0)
|
||||
setNumberOfGoalkeppers(number_of_goalkeepers_rev.current -= 1);
|
||||
}else if(possition == 2){
|
||||
setNumberOfDevenders(number_of_defenders-1) ;
|
||||
setNumberOfDevenders(number_of_defenders_rev.current -= 1) ;
|
||||
}else if (possition == 3){
|
||||
setNumberOfStrikers(number_of_strikers-1) ;
|
||||
}else if(possition == 0){
|
||||
setNumberOfShooters(0)
|
||||
setNumberOfStrikers(number_of_strikers_rev.current -= 1);
|
||||
}else if(possition == 0){
|
||||
setNumberOfShooters(number_of_shooters_rev.current -= 1);
|
||||
}
|
||||
//sentQuestion()
|
||||
}
|
||||
|
||||
// funkcja zsczytuje pozycje zawodnikow przed wyslaniem zapytania do serwera
|
||||
@ -127,19 +186,22 @@ const Hero = () => {
|
||||
var pName = "Strzelec"
|
||||
//kolor kropki
|
||||
// kolor tła kafelka
|
||||
|
||||
var pColor = "#fc0303"
|
||||
if(possition == 1){
|
||||
var pName = "Bramkarz"
|
||||
var pColor = "#03e7fc"
|
||||
setNumberOfGoalkeppers(number_of_goalkeepers_rev.current += 1);
|
||||
}else if(possition == 2){
|
||||
var pName = "Obrońca"
|
||||
var pColor = "#0324fc"
|
||||
setNumberOfDevenders(number_of_defenders_rev.current += 1);
|
||||
}else if (possition ==3){
|
||||
var pName = "Napastnik"
|
||||
var pColor = "#fc6703"
|
||||
setNumberOfStrikers(number_of_strikers_rev.current += 1);
|
||||
}else{
|
||||
setNumberOfShooters(number_of_shooters_rev.current += 1);
|
||||
}
|
||||
|
||||
var player = document.createElement('div');
|
||||
player.className = 'player';
|
||||
player.style.width = "inherit"
|
||||
@ -148,18 +210,18 @@ const Hero = () => {
|
||||
|
||||
// div z nazwa gracza
|
||||
var tekst = document.createElement('div')
|
||||
tekst.style.fontSize = "10px";
|
||||
tekst.style.fontSize = "12px";
|
||||
tekst.innerHTML = pName;
|
||||
|
||||
// div z pozycja gracza
|
||||
var posytion = document.createElement('div')
|
||||
posytion.style.fontSize = "10px"
|
||||
posytion.innerHTML = "x:" + konwerturX(ball.style.left) + "m " + "y:" + konwetujY(ball.style.top) + "m";
|
||||
posytion.style.fontSize = "12px"
|
||||
posytion.innerHTML = konwerturX(ball.style.left) + " m, " + konwetujY(ball.style.top) + " m";
|
||||
player.setAttribute('possition',[konwerturX(ball.style.left),konwetujY(ball.style.top)])
|
||||
//div z przyciskiem usuwającym
|
||||
var btnDelete = document.createElement('button')
|
||||
btnDelete.innerHTML = 'Usun'
|
||||
btnDelete.style.fontSize = "10px"
|
||||
btnDelete.innerHTML = 'Usuń'
|
||||
btnDelete.style.fontSize = "12px"
|
||||
btnDelete.style = 'background-color: #FFB266;color:#000000'
|
||||
btnDelete.addEventListener("click",function(){deletePlayer(ball,player,possition)},false)
|
||||
//dodanie elementów do kafelka
|
||||
@ -209,8 +271,8 @@ const Hero = () => {
|
||||
tekst.style.color = "white"
|
||||
posytion.style.color = "white"
|
||||
|
||||
x = parseFloat(x) -2
|
||||
y = parseFloat(y) -2
|
||||
x = parseFloat(x) -3
|
||||
y = parseFloat(y) -3
|
||||
|
||||
if(bojo.parentNode.querySelector(":hover")){
|
||||
ball.style.left = x + "%"
|
||||
@ -220,25 +282,28 @@ const Hero = () => {
|
||||
//var shooterY = konwetujY(ball.style.top)
|
||||
posytion.innerHTML = "x:" + konwerturX(ball.style.left) + "m " + "y:" + konwetujY(ball.style.top) + "m";
|
||||
player.setAttribute('possition',[konwerturX(ball.style.left),konwetujY(ball.style.top)]);
|
||||
bojo.addEventListener("mouseup", function(){
|
||||
bojo.addEventListener("mouseup", function afterUp(){
|
||||
ball.style.background = pColor
|
||||
bojo.removeEventListener("mousemove", whileMove)
|
||||
bojo.removeEventListener("mouseup", afterUp)
|
||||
})
|
||||
|
||||
})
|
||||
})
|
||||
bojo.addEventListener("mouseup", function reload(){
|
||||
//sentQuestion();
|
||||
bojo.removeEventListener("mouseup",reload)
|
||||
})
|
||||
|
||||
})
|
||||
//sentQuestion();
|
||||
}
|
||||
|
||||
|
||||
|
||||
// // Wyłanie zapytania do serwera
|
||||
function sentQuestion() {
|
||||
///Dziwny Blad
|
||||
loadPlayers()
|
||||
if (number_of_shooters == 1) {
|
||||
if (number_of_shooters_rev.current == 1) {
|
||||
//console.log('Wysyłanie wartości: ', bodyPart, technique, actionType, shooterPossition, gameMinute, firstShot);
|
||||
// Użyj backticksów zamiast zwykłych cudzysłowów
|
||||
fetch(`http://127.0.0.1:5000/get_model?shooter=${shooter}&goalkeeper=${goalkeeper}&defenders=${defenders}&strickers=${stricers}&bodyPart=${bodyPart}&technique=${technique}&actionType=${actionType}&shooterPossition=${shooterPossition}`).then(
|
||||
fetch(`http://127.0.0.1:5000/get_model?shooter=${shooter}&goalkeeper=${goalkeeper}&defenders=${defenders}&strickers=${stricers}&bodyPart=${bodyPart}&technique=${technique}&actionType=${actionType}&shooterPossition=${shooterPossition}&gameMinute=${gameMinute}&shot_first_time=${firstShot}&shot_one_on_one=${oneOnOne}&shot_aerial_won=${afterAirDuel}&shot_open_goal=${openGoal}&shot_follows_dribble=${afterDribbling}&shot_redirect=${redirect}`).then(
|
||||
res => res.json()
|
||||
).then(
|
||||
data => {
|
||||
@ -246,7 +311,8 @@ const Hero = () => {
|
||||
console.log(data);
|
||||
// Przenieś tę linię do środka bloku .then(), aby uniknąć błędów
|
||||
let eX = data.response;
|
||||
document.getElementById("ex").innerHTML = "Współczynnik xG: " + eX;
|
||||
document.getElementById("ex").innerHTML = eX;
|
||||
//updateXGMeter(eX);
|
||||
}
|
||||
).catch(error => {
|
||||
console.error('Błąd:', error);
|
||||
@ -254,10 +320,9 @@ const Hero = () => {
|
||||
} else {
|
||||
alert('Piłka nie jest obecnie na boisku.');
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/* Funkcja dodająca listener do boiska*/
|
||||
@ -276,38 +341,32 @@ const Hero = () => {
|
||||
ball.style.top = y + "%"
|
||||
|
||||
//dodanie zawodnika do listy oraz punktu do mapy w zaleznosci od aktywnosci przycisku 1,2,3 lub 4
|
||||
|
||||
if(active_bbt=="bbt1"){
|
||||
if(number_of_shooters < 1 ){
|
||||
if(number_of_shooters_rev.current < 1 ){
|
||||
addPlayer(0,ball)
|
||||
bojo.appendChild(ball)
|
||||
ball.style.background = "#fc0303"
|
||||
setNumberOfShooters(number_of_shooters+1)
|
||||
}else{alert("mozesz dodac tylko jednego strzelca")}
|
||||
}else if(active_bbt == "bbt2"){
|
||||
|
||||
if ( number_of_goalkeepers < 1){
|
||||
if ( number_of_goalkeepers_rev.current < 1){
|
||||
addPlayer(1,ball)
|
||||
bojo.appendChild(ball)
|
||||
ball.style.background = "#03e7fc"
|
||||
setNumberOfGoalkeppers(number_of_goalkeepers+1)
|
||||
ball.style.background = "#03e7fc"
|
||||
}else{alert("mozesz dodac tylko jednego bramkarza")}
|
||||
}else if(active_bbt == "bbt3"){
|
||||
if(number_of_defenders <= 10){
|
||||
if(number_of_defenders_rev.current < 10){
|
||||
addPlayer(2,ball);
|
||||
setNumberOfDevenders(number_of_defenders+1)
|
||||
bojo.appendChild(ball)
|
||||
ball.style.background = "#0324fc"
|
||||
}else{alert("maksymalna liczba obroncow")}
|
||||
}else if(active_bbt == "bbt4"){
|
||||
if(number_of_strikers <= 10){
|
||||
if(number_of_strikers_rev.current < 10){
|
||||
addPlayer(3,ball);
|
||||
setNumberOfStrikers(number_of_strikers+1);
|
||||
bojo.appendChild(ball)
|
||||
ball.style.background = "#fc6703"
|
||||
}else{alert("maksymalna liczba napastnikow")}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
// funkcja działą po utworzeniu komponentów, dodaje listenry do elementów
|
||||
|
||||
@ -336,16 +395,18 @@ const Hero = () => {
|
||||
<div className="container">
|
||||
{/* Listy zwijane */}
|
||||
|
||||
<div className="top-bar">
|
||||
<div className="top-bar" id = "top-bar">
|
||||
|
||||
<form className="dropdown" id = "bodyPartList">
|
||||
<select className="dropbtn"
|
||||
onChange={event => setBodyPart(event.target.value)}
|
||||
onChange={event => {setBodyPart(event.target.value);
|
||||
//sentQuestion()
|
||||
}}
|
||||
defaultValue={bodyPart}>
|
||||
<option value = "prawa">Noga Prawa</option>
|
||||
<option value = "lewa">Noga Lewa</option>
|
||||
<option value = "glowa">Głowa</option>
|
||||
<option value = "inna" >Inna</option>
|
||||
<option value = "Right Foot">Noga Prawa</option>
|
||||
<option value = "Left Foot">Noga Lewa</option>
|
||||
<option value = "Head">Głowa</option>
|
||||
<option value = "Other" >Inna</option>
|
||||
</select>
|
||||
</form>
|
||||
|
||||
@ -353,37 +414,62 @@ const Hero = () => {
|
||||
|
||||
|
||||
<form className="dropdown" id = "shootTypeList">
|
||||
<select className="dropbtn" onChange={event => setTechnique(event.target.value)}
|
||||
<select className="dropbtn" onChange={event => {setTechnique(event.target.value);
|
||||
//sentQuestion()
|
||||
}}
|
||||
defaultValue = {technique}>
|
||||
<option value="zwykly"> Zwykły </option>
|
||||
<option value = "voley"> Wolej </option>
|
||||
<option value = "pol-voley"> Półwolej </option>
|
||||
<option value = "lob"> Lob </option>
|
||||
<option value = "szczupak"> Szczupak </option>
|
||||
<option value = "z_gory"> Kopnięcie z góry </option>
|
||||
<option value = "pietka"> Piętka </option>
|
||||
<option value="Normal"> Zwykły </option>
|
||||
<option value = "Volley"> Wolej </option>
|
||||
<option value = "Half Volley"> Półwolej </option>
|
||||
<option value = "Lob"> Lob </option>
|
||||
<option value = "Diving Header"> Szczupak </option>
|
||||
<option value = "Overhead Kick"> Kopnięcie z góry </option>
|
||||
<option value = "Backheel"> Piętka </option>
|
||||
</select>
|
||||
</form>
|
||||
|
||||
<form className="dropdown" id = "actionTypeList" onChange={event => setActionType(event.target.value)}
|
||||
<form className="dropdown" id = "actionTypeList" onChange={event => {setActionType(event.target.value);
|
||||
//sentQuestion()
|
||||
}}
|
||||
defaultValue={technique}>
|
||||
<select className="dropbtn">
|
||||
<option value = "pozycyjny"> Atak Pozycyjny </option>
|
||||
<option value = "wolny"> Rzut Wolny </option>
|
||||
<option value = "karny"> Rzut Karny </option>
|
||||
<option value= "rozny"> Rzut Rozny </option>
|
||||
<option value="rozpoczecie"> Rozpoczęcie </option>
|
||||
<option value = "Open Play"> Atak Pozycyjny </option>
|
||||
<option value = "Free Kick"> Rzut Wolny </option>
|
||||
<option value = "Penalty"> Rzut Karny </option>
|
||||
<option value= "Corner"> Rzut Rozny </option>
|
||||
</select>
|
||||
</form>
|
||||
<form className="dropdown" id = "possitionList"
|
||||
onChange={event => setPossition(event.target.value)}
|
||||
onChange={event => {setPossition(event.target.value);
|
||||
//sentQuestion()
|
||||
}}
|
||||
defaultValue={shooterPossition}>
|
||||
<select className="dropbtn">
|
||||
<option value= "napastnik" > Napastnik </option>
|
||||
<option value = "bramkarz"> Bramkarz </option>
|
||||
<option value = "obronca"> Obrońca </option>
|
||||
<option value = "pomocnik"> Pomocnik </option>
|
||||
|
||||
<option value="Right Center Forward">Prawy Środkowy Napastnik</option>
|
||||
<option value="Left Center Forward">Lewy Środkowy Napastnik</option>
|
||||
<option value="Secondary Striker">Drugi Napastnik</option>
|
||||
<option value="Center Forward">Środkowy Napastnik</option>
|
||||
<option value="Center Midfield">Środkowy Pomocnik</option>
|
||||
<option value="Left Center Midfield">Lewy Środkowy Pomocnik</option>
|
||||
<option value="Right Center Midfield">Prawy Środkowy Pomocnik</option>
|
||||
<option value="Left Midfield">Lewy Pomocnik</option>
|
||||
<option value="Center Attacking Midfield">Środkowy Ofensywny Pomocnik</option>
|
||||
<option value="Left Defensive Midfield">Lewy Defensywny Pomocnik</option>
|
||||
<option value="Left Attacking Midfield">Lewy Ofensywny Pomocnik</option>
|
||||
<option value="Right Attacking Midfield">Prawy Ofensywny Pomocnik</option>
|
||||
<option value="Right Defensive Midfield">Prawy Defensywny Pomocnik</option>
|
||||
<option value="Center Defensive Midfield">Środkowy Defensywny Pomocnik</option>
|
||||
<option value="Right Midfield">Prawy Pomocnik</option>
|
||||
<option value="Left Wing Back">Lewy Pomocnik Skrzydłowy</option>
|
||||
<option value="Left Wing">Lewe Skrzydło</option>
|
||||
<option value="Right Wing">Prawe Skrzydło</option>
|
||||
<option value="Right Wing Back">Prawy Pomocnik Skrzydłowy</option>
|
||||
<option value="Center Back">Środkowy Obrońca</option>
|
||||
<option value="Left Center Back">Lewy Środkowy Obrońca</option>
|
||||
<option value="Right Center Back">Prawy Środkowy Obrońca</option>
|
||||
<option value="Right Back">Prawy Obrońca</option>
|
||||
<option value="Left Back">Lewy Obrońca</option>
|
||||
<option value="Goalkeeper">Bramkarz</option>
|
||||
</select>
|
||||
</form>
|
||||
|
||||
@ -409,25 +495,40 @@ const Hero = () => {
|
||||
<div className="field-pic"></div>
|
||||
|
||||
</div>
|
||||
<div className="rightMenu">
|
||||
<div className="xg-meter">
|
||||
<b id="ex" className="xg-value">0</b>
|
||||
</div>
|
||||
|
||||
|
||||
{/* <div className="ChoosingPlayer">
|
||||
<button className="cho-one_on_one" id = "bbt8">Sam na sam</button>
|
||||
</div>
|
||||
<div className="ChoosingPlayer">
|
||||
<button className="cho-first_time" id = "bbt12">Pierwszy w meczu</button>
|
||||
</div>
|
||||
<div className="ChoosingPlayer">
|
||||
<button className="cho-aerial_won" id = "bbt13">Pojedynek powietrzny</button>
|
||||
</div>
|
||||
<div className="ChoosingPlayer">
|
||||
<button className="cho-follows_dribble" id = "bbt14">Drybling</button>
|
||||
</div>
|
||||
<div className="ChoosingPlayer">
|
||||
<button className="cho-redirect" id = "bbt15">Rykoszet</button>
|
||||
</div> */}
|
||||
|
||||
<div className="additional-parameters">
|
||||
<h3>Parametry strzału</h3>
|
||||
<label>
|
||||
<input type="checkbox" id="firstShot" onChange={handleFirstShotChange} />
|
||||
Pierwszy w meczu
|
||||
</label>
|
||||
<label>
|
||||
<input type="checkbox" id="oneOnOne" onChange={handleOneOnOneChange} />
|
||||
Akcja sam na sam
|
||||
</label>
|
||||
<label>
|
||||
<input type="checkbox" id="afterAirDuel" onChange={handleAfterAirDuelChange} />
|
||||
Po pojedynku powietrznym
|
||||
</label>
|
||||
<label>
|
||||
<input type="checkbox" id="openGoal" onChange={handleOpenGoalChange} />
|
||||
Na pustą bramkę
|
||||
</label>
|
||||
<label>
|
||||
<input type="checkbox" id="afterDribbling" onChange={handleAfterDribblingChange} />
|
||||
Poprzedzony dryblingiem
|
||||
</label>
|
||||
<label>
|
||||
<input type="checkbox" id="redirect" onChange={handleRedirectChange} />
|
||||
Rykoszet
|
||||
</label>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div className="bottom-bar">
|
||||
|
||||
<button className="cho-shooter" id = "bbt1">Strzelec</button>
|
||||
@ -437,13 +538,8 @@ const Hero = () => {
|
||||
<button className="reset-button" onClick={resetField}>Reset</button>
|
||||
<button className="info-button" onClick={sentQuestion}>xG</button>
|
||||
</div>
|
||||
<div>
|
||||
<b id = "ex" className="Ex">
|
||||
|
||||
</b>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
|
@ -3,6 +3,7 @@ import React from 'react'
|
||||
const Loader = () => {
|
||||
return (
|
||||
<div>Loader</div>
|
||||
|
||||
)
|
||||
}
|
||||
|
||||
|
BIN
app/src/flask-server/labelEncoder.joblib
Normal file
BIN
app/src/flask-server/labelEncoder.joblib
Normal file
Binary file not shown.
Binary file not shown.
BIN
app/src/flask-server/modele/__pycache__/modele.cpython-311.pyc
Normal file
BIN
app/src/flask-server/modele/__pycache__/modele.cpython-311.pyc
Normal file
Binary file not shown.
BIN
app/src/flask-server/modele/__pycache__/modele.cpython-312.pyc
Normal file
BIN
app/src/flask-server/modele/__pycache__/modele.cpython-312.pyc
Normal file
Binary file not shown.
Binary file not shown.
@ -2,105 +2,157 @@ from joblib import load
|
||||
import pandas as pd
|
||||
from math import sqrt
|
||||
import math
|
||||
import numpy as np
|
||||
import xgboost
|
||||
from sklearn.preprocessing import OrdinalEncoder
|
||||
|
||||
# Funkcja zwraca prawdopodobieństwo zdobycia gola
|
||||
def LogisticRegression_predict_proba(position_x, position_y, distance_to_goalM, angle, match_minute, Number_Intervening_Opponents, Number_Intervening_Teammates, isFoot, isHead):
|
||||
|
||||
# distance_to_goalM = sqrt(( (position_x**2) + (position_y**2)))
|
||||
|
||||
def LogisticRegression_predict_proba(position_x, position_y, distance_to_goalM, angle, match_minute, Number_Intervening_Opponents, Number_Intervening_Teammates, isFoot, isHead):
|
||||
# distance_to_goalM = sqrt(( (position_x**2) + (position_y**2)))
|
||||
model = load('regresja_logistyczna.joblib')
|
||||
X_new = pd.DataFrame(columns=['position_x', 'position_y', 'distance_to_goalM', 'angle','match_minute', 'Number_Intervening_Opponents','Number_Intervening_Teammates', 'isFoot', 'isHead'])
|
||||
X_new.loc[len(X_new.index)] = [position_x, position_y, distance_to_goalM, angle, match_minute, Number_Intervening_Opponents, Number_Intervening_Teammates, isFoot, isHead]
|
||||
return model.predict_proba(X_new)[0][1].round(2)
|
||||
|
||||
#xgBoost
|
||||
def xgboost_predict_proba(minute, position_name, shot_body_part_name, shot_technique_name,
|
||||
shot_type_name, shot_first_time, shot_one_on_one,
|
||||
shot_aerial_won, shot_deflected, shot_open_goal,
|
||||
shot_follows_dribble, shot_redirect, x1, y1,
|
||||
number_of_players_opponents, number_of_players_teammates,
|
||||
angle, distance, x_player_opponent_Goalkeeper,
|
||||
x_player_opponent_8, x_player_opponent_1, x_player_opponent_2,
|
||||
x_player_opponent_3, x_player_teammate_1, x_player_opponent_4,
|
||||
x_player_opponent_5, x_player_opponent_6, x_player_teammate_2,
|
||||
x_player_opponent_9, x_player_opponent_10, x_player_opponent_11,
|
||||
x_player_teammate_3, x_player_teammate_4, x_player_teammate_5,
|
||||
x_player_teammate_6, x_player_teammate_7, x_player_teammate_8,
|
||||
x_player_teammate_9, x_player_teammate_10,
|
||||
y_player_opponent_Goalkeeper, y_player_opponent_8,
|
||||
y_player_opponent_1, y_player_opponent_2, y_player_opponent_3,
|
||||
y_player_teammate_1, y_player_opponent_4, y_player_opponent_5,
|
||||
y_player_opponent_6, y_player_teammate_2, y_player_opponent_9,
|
||||
y_player_opponent_10, y_player_opponent_11, y_player_teammate_3,
|
||||
y_player_teammate_4, y_player_teammate_5, y_player_teammate_6,
|
||||
y_player_teammate_7, y_player_teammate_8, y_player_teammate_9,
|
||||
y_player_teammate_10, x_player_opponent_7, y_player_opponent_7,
|
||||
x_player_teammate_Goalkeeper, y_player_teammate_Goalkeeper,
|
||||
shot_kick_off):
|
||||
def xgboost_predict_proba(minute=0, position_name='Center Forward', shot_body_part_name='Right Foot',
|
||||
shot_technique_name='Normal', shot_type_name='Open Play', shot_first_time=False,
|
||||
shot_one_on_one=False, shot_aerial_won=False,
|
||||
shot_open_goal=False, shot_follows_dribble=False, shot_redirect=False, x1=0.0, y1=0.0,
|
||||
number_of_players_opponents=0, number_of_players_teammates=0,
|
||||
angle=0.0, distance=0.0, x_player_opponent_Goalkeeper=np.nan,
|
||||
x_player_opponent_8=np.nan, x_player_opponent_1=np.nan, x_player_opponent_2=np.nan,
|
||||
x_player_opponent_3=np.nan, x_player_teammate_1=np.nan, x_player_opponent_4=np.nan,
|
||||
x_player_opponent_5=np.nan, x_player_opponent_6=np.nan, x_player_teammate_2=np.nan,
|
||||
x_player_opponent_9=np.nan, x_player_opponent_10=np.nan, x_player_opponent_11=np.nan,
|
||||
x_player_teammate_3=np.nan, x_player_teammate_4=np.nan, x_player_teammate_5=np.nan,
|
||||
x_player_teammate_6=np.nan, x_player_teammate_7=np.nan, x_player_teammate_8=np.nan,
|
||||
y_player_opponent_Goalkeeper=np.nan, y_player_opponent_8=np.nan,
|
||||
x_player_teammate_9=np.nan, x_player_teammate_10=np.nan,
|
||||
y_player_opponent_1=np.nan, y_player_opponent_2=np.nan, y_player_opponent_3=np.nan,
|
||||
y_player_teammate_1=np.nan, y_player_opponent_4=np.nan, y_player_opponent_5=np.nan,
|
||||
y_player_opponent_6=np.nan, y_player_teammate_2=np.nan, y_player_opponent_9=np.nan,
|
||||
y_player_opponent_10=np.nan, y_player_opponent_11=np.nan, y_player_teammate_3=np.nan,
|
||||
y_player_teammate_4=np.nan, y_player_teammate_5=np.nan, y_player_teammate_6=np.nan,
|
||||
y_player_teammate_7=np.nan, y_player_teammate_8=np.nan, y_player_teammate_9=np.nan,
|
||||
y_player_teammate_10=np.nan, x_player_opponent_7=np.nan, y_player_opponent_7=np.nan,
|
||||
x_player_teammate_Goalkeeper=np.nan, y_player_teammate_Goalkeeper=np.nan):
|
||||
|
||||
model = load('xgboost.joblib')
|
||||
X_new = pd.DataFrame(columns=['minute', 'position_name', 'shot_body_part_name', 'shot_technique_name',
|
||||
'shot_type_name', 'shot_first_time', 'shot_one_on_one',
|
||||
'shot_aerial_won', 'shot_deflected', 'shot_open_goal',
|
||||
'shot_follows_dribble', 'shot_redirect', 'x1', 'y1',
|
||||
'number_of_players_opponents', 'number_of_players_teammates',
|
||||
'angle', 'distance', 'x_player_opponent_Goalkeeper',
|
||||
'x_player_opponent_8', 'x_player_opponent_1', 'x_player_opponent_2',
|
||||
'x_player_opponent_3', 'x_player_teammate_1', 'x_player_opponent_4',
|
||||
'x_player_opponent_5', 'x_player_opponent_6', 'x_player_teammate_2',
|
||||
'x_player_opponent_9', 'x_player_opponent_10', 'x_player_opponent_11',
|
||||
'x_player_teammate_3', 'x_player_teammate_4', 'x_player_teammate_5',
|
||||
'x_player_teammate_6', 'x_player_teammate_7', 'x_player_teammate_8',
|
||||
'x_player_teammate_9', 'x_player_teammate_10',
|
||||
'y_player_opponent_Goalkeeper', 'y_player_opponent_8',
|
||||
'y_player_opponent_1', 'y_player_opponent_2', 'y_player_opponent_3',
|
||||
'y_player_teammate_1', 'y_player_opponent_4', 'y_player_opponent_5',
|
||||
'y_player_opponent_6', 'y_player_teammate_2', 'y_player_opponent_9',
|
||||
'y_player_opponent_10', 'y_player_opponent_11', 'y_player_teammate_3',
|
||||
'y_player_teammate_4', 'y_player_teammate_5', 'y_player_teammate_6',
|
||||
'y_player_teammate_7', 'y_player_teammate_8', 'y_player_teammate_9',
|
||||
'y_player_teammate_10', 'x_player_opponent_7', 'y_player_opponent_7',
|
||||
'x_player_teammate_Goalkeeper', 'y_player_teammate_Goalkeeper',
|
||||
'shot_kick_off'])
|
||||
model = xgboost.XGBClassifier()
|
||||
model.load_model('xgboost.json')
|
||||
|
||||
enc = OrdinalEncoder()
|
||||
enc = load('labelEncoder.joblib')
|
||||
|
||||
X_new = pd.DataFrame(columns=['minute', 'position_name', 'shot_body_part_name', 'shot_technique_name',
|
||||
'shot_type_name', 'shot_first_time', 'shot_one_on_one',
|
||||
'shot_aerial_won', 'shot_open_goal',
|
||||
'shot_follows_dribble', 'shot_redirect', 'x1', 'y1',
|
||||
'number_of_players_opponents', 'number_of_players_teammates',
|
||||
'angle', 'distance', 'x_player_opponent_Goalkeeper',
|
||||
'x_player_opponent_8', 'x_player_opponent_1', 'x_player_opponent_2',
|
||||
'x_player_opponent_3', 'x_player_teammate_1', 'x_player_opponent_4',
|
||||
'x_player_opponent_5', 'x_player_opponent_6', 'x_player_teammate_2',
|
||||
'x_player_opponent_9', 'x_player_opponent_10', 'x_player_opponent_11',
|
||||
'x_player_teammate_3', 'x_player_teammate_4', 'x_player_teammate_5',
|
||||
'x_player_teammate_6', 'x_player_teammate_7', 'x_player_teammate_8',
|
||||
'x_player_teammate_9', 'x_player_teammate_10',
|
||||
'y_player_opponent_Goalkeeper', 'y_player_opponent_8',
|
||||
'y_player_opponent_1', 'y_player_opponent_2', 'y_player_opponent_3',
|
||||
'y_player_teammate_1', 'y_player_opponent_4', 'y_player_opponent_5',
|
||||
'y_player_opponent_6', 'y_player_teammate_2', 'y_player_opponent_9',
|
||||
'y_player_opponent_10', 'y_player_opponent_11', 'y_player_teammate_3',
|
||||
'y_player_teammate_4', 'y_player_teammate_5', 'y_player_teammate_6',
|
||||
'y_player_teammate_7', 'y_player_teammate_8', 'y_player_teammate_9',
|
||||
'y_player_teammate_10', 'x_player_opponent_7', 'y_player_opponent_7',
|
||||
'x_player_teammate_Goalkeeper', 'y_player_teammate_Goalkeeper'])
|
||||
|
||||
X_new.loc[len(X_new.index)] = [minute, position_name, shot_body_part_name, shot_technique_name,
|
||||
shot_type_name, shot_first_time, shot_one_on_one,
|
||||
shot_aerial_won, shot_deflected, shot_open_goal,
|
||||
shot_follows_dribble, shot_redirect, x1, y1,
|
||||
number_of_players_opponents, number_of_players_teammates,
|
||||
angle, distance, x_player_opponent_Goalkeeper,
|
||||
x_player_opponent_8, x_player_opponent_1, x_player_opponent_2,
|
||||
x_player_opponent_3, x_player_teammate_1, x_player_opponent_4,
|
||||
x_player_opponent_5, x_player_opponent_6, x_player_teammate_2,
|
||||
x_player_opponent_9, x_player_opponent_10, x_player_opponent_11,
|
||||
x_player_teammate_3, x_player_teammate_4, x_player_teammate_5,
|
||||
x_player_teammate_6, x_player_teammate_7, x_player_teammate_8,
|
||||
x_player_teammate_9, x_player_teammate_10,
|
||||
y_player_opponent_Goalkeeper, y_player_opponent_8,
|
||||
y_player_opponent_1, y_player_opponent_2, y_player_opponent_3,
|
||||
y_player_teammate_1, y_player_opponent_4, y_player_opponent_5,
|
||||
y_player_opponent_6, y_player_teammate_2, y_player_opponent_9,
|
||||
y_player_opponent_10, y_player_opponent_11, y_player_teammate_3,
|
||||
y_player_teammate_4, y_player_teammate_5, y_player_teammate_6,
|
||||
y_player_teammate_7, y_player_teammate_8, y_player_teammate_9,
|
||||
y_player_teammate_10, x_player_opponent_7, y_player_opponent_7,
|
||||
x_player_teammate_Goalkeeper, y_player_teammate_Goalkeeper,
|
||||
shot_kick_off]
|
||||
return model.predict_proba(X_new)[0][1].round(2)
|
||||
X_new.loc[len(X_new.index)] = [minute, position_name, shot_body_part_name, shot_technique_name,
|
||||
shot_type_name, shot_first_time, shot_one_on_one,
|
||||
shot_aerial_won, shot_open_goal,
|
||||
shot_follows_dribble, shot_redirect, x1, y1,
|
||||
number_of_players_opponents, number_of_players_teammates,
|
||||
angle, distance, x_player_opponent_Goalkeeper,
|
||||
x_player_opponent_8, x_player_opponent_1, x_player_opponent_2,
|
||||
x_player_opponent_3, x_player_teammate_1, x_player_opponent_4,
|
||||
x_player_opponent_5, x_player_opponent_6, x_player_teammate_2,
|
||||
x_player_opponent_9, x_player_opponent_10, x_player_opponent_11,
|
||||
x_player_teammate_3, x_player_teammate_4, x_player_teammate_5,
|
||||
x_player_teammate_6, x_player_teammate_7, x_player_teammate_8,
|
||||
x_player_teammate_9, x_player_teammate_10,
|
||||
y_player_opponent_Goalkeeper, y_player_opponent_8,
|
||||
y_player_opponent_1, y_player_opponent_2, y_player_opponent_3,
|
||||
y_player_teammate_1, y_player_opponent_4, y_player_opponent_5,
|
||||
y_player_opponent_6, y_player_teammate_2, y_player_opponent_9,
|
||||
y_player_opponent_10, y_player_opponent_11, y_player_teammate_3,
|
||||
y_player_teammate_4, y_player_teammate_5, y_player_teammate_6,
|
||||
y_player_teammate_7, y_player_teammate_8, y_player_teammate_9,
|
||||
y_player_teammate_10, x_player_opponent_7, y_player_opponent_7,
|
||||
x_player_teammate_Goalkeeper, y_player_teammate_Goalkeeper]
|
||||
|
||||
X_new[['position_name',
|
||||
'shot_technique_name',
|
||||
'shot_type_name',
|
||||
'shot_body_part_name']] = enc.transform(X_new[['position_name', 'shot_technique_name', 'shot_type_name', 'shot_body_part_name']], )
|
||||
|
||||
X_new[['minute',
|
||||
'position_name',
|
||||
'shot_technique_name',
|
||||
'shot_type_name',
|
||||
'number_of_players_opponents',
|
||||
'number_of_players_teammates',
|
||||
'shot_body_part_name']] = X_new[['minute',
|
||||
'position_name',
|
||||
'shot_technique_name',
|
||||
'shot_type_name',
|
||||
'number_of_players_opponents',
|
||||
'number_of_players_teammates',
|
||||
'shot_body_part_name']].astype(int)
|
||||
|
||||
# X_new[['minute',
|
||||
# 'position_name',
|
||||
# 'shot_technique_name',
|
||||
# 'shot_type_name',
|
||||
# 'number_of_players_opponents',
|
||||
# 'number_of_players_teammates',
|
||||
# 'shot_body_part_name']] = X_new[['minute',
|
||||
# 'position_name',
|
||||
# 'shot_technique_name',
|
||||
# 'shot_type_name',
|
||||
# 'number_of_players_opponents',
|
||||
# 'number_of_players_teammates',
|
||||
# 'shot_body_part_name']].astype('category')
|
||||
|
||||
X_new[['shot_first_time',
|
||||
'shot_one_on_one',
|
||||
'shot_aerial_won',
|
||||
'shot_open_goal',
|
||||
'shot_follows_dribble',
|
||||
'shot_redirect']] = X_new[['shot_first_time',
|
||||
'shot_one_on_one',
|
||||
'shot_aerial_won',
|
||||
'shot_open_goal',
|
||||
'shot_follows_dribble',
|
||||
'shot_redirect']].astype(int)
|
||||
print(X_new)
|
||||
print(X_new.dtypes)
|
||||
|
||||
|
||||
return model.predict_proba(X_new)[0][1].round(3)
|
||||
|
||||
#XgBoost_2
|
||||
|
||||
def xgboost_predict_proba_v2(shooter,goalkeeper,teamMatesList,opponentsList, minute,position_name,shot_body_part_name,
|
||||
shot_technique_name,shot_type_name,shot_first_time,shot_aerial_won,shot_deflected,shot_open_goal,
|
||||
shot_follows_dribble,shot_redirect, shot_kick_off):
|
||||
shot_technique_name,shot_type_name,shot_first_time,shot_aerial_won,shot_open_goal,
|
||||
shot_follows_dribble,shot_redirect):
|
||||
model = load('xgboost.joblib')
|
||||
X_new = pd.DataFrame(columns=['minute', 'position_name', 'shot_body_part_name',
|
||||
'shot_technique_name','shot_type_name', 'shot_first_time',
|
||||
'shot_one_on_one','shot_aerial_won', 'shot_deflected',
|
||||
'shot_one_on_one','shot_aerial_won',
|
||||
'shot_open_goal','shot_follows_dribble', 'shot_redirect',
|
||||
'x1', 'y1','number_of_players_opponents',
|
||||
'number_of_players_teammates','angle', 'distance',
|
||||
'x_player_opponent_Goalkeeper',
|
||||
'x_player_opponent_Goalkeeper', 'x_player_opponent_8',
|
||||
'x_player_opponent_1', 'x_player_opponent_2','x_player_opponent_3',
|
||||
'x_player_opponent_4','x_player_opponent_5', 'x_player_opponent_6',
|
||||
'x_player_teammate_2','x_player_opponent_9', 'x_player_opponent_10',
|
||||
@ -116,8 +168,7 @@ def xgboost_predict_proba_v2(shooter,goalkeeper,teamMatesList,opponentsList, min
|
||||
'y_player_teammate_4', 'y_player_teammate_5', 'y_player_teammate_6',
|
||||
'y_player_teammate_7', 'y_player_teammate_8', 'y_player_teammate_9',
|
||||
'y_player_teammate_10', 'x_player_opponent_7', 'y_player_opponent_7',
|
||||
'x_player_teammate_Goalkeeper', 'y_player_teammate_Goalkeeper',
|
||||
'shot_kick_off'])
|
||||
'x_player_teammate_Goalkeeper', 'y_player_teammate_Goalkeeper'])
|
||||
|
||||
|
||||
shooter = konwertujDoListy(shooter)
|
||||
@ -137,8 +188,10 @@ def xgboost_predict_proba_v2(shooter,goalkeeper,teamMatesList,opponentsList, min
|
||||
teamMatesList = zmienWMaciez(teamMatesList)
|
||||
opponentsList = zmienWMaciez(opponentsList)
|
||||
|
||||
number_of_players_opponents = len(teamMatesList)
|
||||
number_of_players_teammates = len(opponentsList)
|
||||
|
||||
# DO ROZBUDOWY
|
||||
number_of_players_opponents = 3
|
||||
number_of_players_teammates = 3
|
||||
# Bramkarz
|
||||
x_player_opponent_Goalkeeper = goalkeeper[0]
|
||||
y_player_opponent_Goalkeeper = goalkeeper[1]
|
||||
@ -146,19 +199,16 @@ def xgboost_predict_proba_v2(shooter,goalkeeper,teamMatesList,opponentsList, min
|
||||
shot_one_on_one = True if number_of_players_opponents == 1 else False
|
||||
# TeamMate goalkeppe
|
||||
|
||||
x_player_teammate_Goalkeeper = None
|
||||
y_player_teammate_Goalkeeper = None
|
||||
x_player_teammate_Goalkeeper = np.nan
|
||||
y_player_teammate_Goalkeeper = np.nan
|
||||
#Reszta Zawodnikow
|
||||
|
||||
print("AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA")
|
||||
print(X_new.head)
|
||||
X_new.loc[len(X_new.index)] = [minute, position_name, shot_body_part_name,
|
||||
shot_technique_name,shot_type_name, shot_first_time,
|
||||
shot_one_on_one,shot_aerial_won, shot_deflected,
|
||||
shot_one_on_one,shot_aerial_won,
|
||||
shot_open_goal,shot_follows_dribble, shot_redirect,
|
||||
shooter[0], shooter[1],number_of_players_opponents,
|
||||
number_of_players_teammates,angle, distance,
|
||||
x_player_opponent_Goalkeeper,
|
||||
x_player_opponent_Goalkeeper, opponentsList[8][0],
|
||||
opponentsList[0][0], opponentsList[1][0], opponentsList[2][0],
|
||||
opponentsList[3][0], opponentsList[4][0], opponentsList[5][0],
|
||||
opponentsList[6][0], opponentsList[7][0], teamMatesList[8][0],
|
||||
@ -175,13 +225,17 @@ def xgboost_predict_proba_v2(shooter,goalkeeper,teamMatesList,opponentsList, min
|
||||
teamMatesList[0][1],teamMatesList[1][1], teamMatesList[2][1],
|
||||
teamMatesList[4][1],teamMatesList[5][1], teamMatesList[6][1], teamMatesList[7][1],
|
||||
teamMatesList[8][1], teamMatesList[9][1],
|
||||
x_player_teammate_Goalkeeper, y_player_teammate_Goalkeeper,
|
||||
shot_kick_off]
|
||||
|
||||
x_player_teammate_Goalkeeper, y_player_teammate_Goalkeeper]
|
||||
|
||||
categorical_columns = ['position_name', 'shot_technique_name', 'shot_type_name', 'number_of_players_opponents', 'number_of_players_teammates', 'shot_body_part_name'] # list all your object columns here
|
||||
# X_new = pd.get_dummies(X_new, columns=categorical_columns)
|
||||
X_new[categorical_columns] = X_new[categorical_columns].astype('category')
|
||||
|
||||
return model.predict_proba(X_new)[0][1].round(2)
|
||||
|
||||
|
||||
# Pomocnicze Funkcje
|
||||
# trzeba uzupelnic
|
||||
def sortNearestToShooter(playerList, shooter):
|
||||
|
||||
return playerList
|
||||
@ -198,14 +252,14 @@ def loc2angle(x, y):
|
||||
rads = math.pi + rads if rads < 0 else rads
|
||||
deg = math.degrees(rads)
|
||||
return deg
|
||||
|
||||
# zamiana stringa odzielonego ',' na liste
|
||||
def konwertujDoListy(listaString):
|
||||
listaString = listaString.split(",")
|
||||
listaFloat = []
|
||||
for elem in listaString:
|
||||
listaFloat.append(float(elem))
|
||||
return listaFloat
|
||||
|
||||
#Zamiana listy w formie [1x,1y,2x,2y,3x,3y...] do postaci maciezy [xi, yi]
|
||||
def zmienWMaciez(lista):
|
||||
maciez = []
|
||||
for i in range(0,len(lista),2):
|
||||
@ -213,5 +267,5 @@ def zmienWMaciez(lista):
|
||||
maciez.append(player)
|
||||
if(len(maciez) < 10):
|
||||
for i in range(len(maciez),11,1):
|
||||
maciez.append([None,None])
|
||||
return maciez
|
||||
maciez.append([np.nan,np.nan])
|
||||
return maciez
|
||||
|
@ -1,6 +1,8 @@
|
||||
from flask import Flask, request, jsonify
|
||||
from flask_cors import CORS
|
||||
from modele.modele import LogisticRegression_predict_proba, xgboost_predict_proba, xgboost_predict_proba_v2
|
||||
import numpy as np
|
||||
import math
|
||||
|
||||
app = Flask(__name__)
|
||||
|
||||
@ -24,37 +26,218 @@ def get_model():
|
||||
|
||||
# Elementy z list: czesc ciała,rodzaj uderzenia,pozycja strzelca oraz typ akcji
|
||||
|
||||
position_name = request.args.get('shooter')
|
||||
body_part = request.args.get('bodyPart')
|
||||
technique = request.args.get('technique')
|
||||
acionType = request.args.get('actionType')
|
||||
minute = request.args.get('gameMinute')
|
||||
position_name = request.args.get('shooterPossition')
|
||||
gameMinute = request.args.get('gameMinute')
|
||||
|
||||
print("pozycja strzelca: " + position_name)
|
||||
shot_first_time = request.args.get('shot_first_time')
|
||||
shot_one_on_one = request.args.get('shot_one_on_one')
|
||||
shot_aerial_won = request.args.get('shot_aerial_won')
|
||||
shot_open_goal = request.args.get('shot_open_goal')
|
||||
shot_follows_dribble = request.args.get('shot_follows_dribble')
|
||||
shot_redirect = request.args.get('shot_redirect')
|
||||
|
||||
|
||||
shooter_x, shooter_y = shooter.split(',')
|
||||
|
||||
shooter_x = float(shooter_x)
|
||||
shooter_y = float(shooter_y)
|
||||
|
||||
print("minuta: ", minute)
|
||||
print("pozycja x1 strzelca: ", shooter_x)
|
||||
print("pozycja y1 strzelca: ", shooter_y)
|
||||
print("czesc ciala: " + body_part)
|
||||
print("technika: " + technique)
|
||||
print("typ akcji: " + acionType)
|
||||
|
||||
# lista wspolzawodnikow oraz przeciwnikow
|
||||
# lista atakujacy oraz obroncy
|
||||
|
||||
teamMatesList = request.args.get('defenders')
|
||||
opponentsList = request.args.get('strickers')
|
||||
def konwertujDoListy(listaString):
|
||||
listaString = listaString.split(",")
|
||||
listaFloat = []
|
||||
for elem in listaString:
|
||||
listaFloat.append(float(elem))
|
||||
return listaFloat
|
||||
|
||||
def zmienWMaciez(lista):
|
||||
maciez = []
|
||||
for i in range(0,len(lista),2):
|
||||
player = [float(lista[i]),float(lista[i+1])]
|
||||
maciez.append(player)
|
||||
if(len(maciez) < 10):
|
||||
for i in range(len(maciez),11,1):
|
||||
maciez.append([np.nan,np.nan])
|
||||
return maciez
|
||||
|
||||
|
||||
obroncy = request.args.get('defenders')
|
||||
atakujacy = request.args.get('strickers')
|
||||
|
||||
print("wspolrzedne obroncow: ", obroncy)
|
||||
|
||||
if obroncy == "":
|
||||
obroncy_macierz = [[np.nan, np.nan]]
|
||||
else:
|
||||
obroncy_lista = konwertujDoListy(obroncy)
|
||||
obroncy_macierz = zmienWMaciez(obroncy_lista)
|
||||
|
||||
print("wspolrzedne obroncow: " + teamMatesList)
|
||||
print("wspolrzedne przeciwnikow: " + opponentsList)
|
||||
if atakujacy == "":
|
||||
atakujacy_macierz = [[np.nan, np.nan]]
|
||||
else:
|
||||
atakujacy_lista = konwertujDoListy(atakujacy)
|
||||
atakujacy_macierz = zmienWMaciez(atakujacy_lista)
|
||||
|
||||
if gameMinute == "":
|
||||
gameMinute = 1.0 # to change
|
||||
|
||||
# Bramkarz
|
||||
goalkepper = "2,2"
|
||||
#goalkepper = request.args.get('goalkeeper')
|
||||
print("wspolrzedne obroncow: ", obroncy)
|
||||
print("wspolrzedne atakujacych: ", atakujacy)
|
||||
|
||||
def euclidean_distance(point1, point2):
|
||||
"""Calculate the Euclidean distance between two points."""
|
||||
return math.sqrt((point1[0] - point2[0])**2 + (point1[1] - point2[1])**2)
|
||||
|
||||
def sort_coordinates_by_distance(coordinates, reference_point):
|
||||
"""Sort a list of coordinates based on Euclidean distance from a reference point.
|
||||
Coordinates with NaN values are placed at the end of the list.
|
||||
"""
|
||||
def distance_or_inf(coord):
|
||||
"""Helper function to handle coordinates with NaN values."""
|
||||
if hasattr(coord, '__iter__') and len(coord) >= 2:
|
||||
if np.isnan(coord[0]) or np.isnan(coord[1]):
|
||||
return float('inf') # Set distance to infinity for NaN coordinates
|
||||
return euclidean_distance(coord, reference_point)
|
||||
return float('inf') # Set distance to infinity for non-iterable coordinates
|
||||
|
||||
sorted_coordinates = sorted(coordinates, key=distance_or_inf)
|
||||
|
||||
if(len(sorted_coordinates) < 10):
|
||||
for i in range(len(sorted_coordinates),11,1):
|
||||
sorted_coordinates.append([np.nan,np.nan])
|
||||
return sorted_coordinates
|
||||
|
||||
print("bramkarz: " + str(goalkepper) )
|
||||
# POSORTOWANI OBRONCY I ATAKUJACY
|
||||
posortowani_obroncy = sort_coordinates_by_distance(obroncy_macierz, [shooter_x, shooter_y])
|
||||
posortowani_atakujacy = sort_coordinates_by_distance(atakujacy_macierz, [shooter_x, shooter_y])
|
||||
|
||||
response = xgboost_predict_proba_v2(shooter = shooter,
|
||||
opponentsList = opponentsList, teamMatesList = teamMatesList ,minute = 20, position_name = position_name, shot_body_part_name = body_part, shot_technique_name = technique,
|
||||
shot_type_name = acionType, shot_first_time = False,
|
||||
shot_aerial_won = False, shot_deflected = False, shot_open_goal = False,
|
||||
shot_follows_dribble = False, shot_redirect = False, shot_kick_off = False, goalkeeper= goalkepper
|
||||
)
|
||||
print("Posortowani obroncy: ", posortowani_obroncy)
|
||||
|
||||
print("Posortowani atakujacy: ", posortowani_atakujacy)
|
||||
|
||||
|
||||
number_of_players_opponents = float(np.sum(~np.isnan(posortowani_obroncy).all(axis=1)))
|
||||
number_of_players_teammates = float(np.sum(~np.isnan(posortowani_atakujacy).all(axis=1)))
|
||||
|
||||
print("Liczba obroncow:", number_of_players_opponents)
|
||||
print("Liczba atakujacych:", number_of_players_teammates)
|
||||
## add angle, match minutes and number of players
|
||||
|
||||
def loc2angle(x, y):
|
||||
rads = math.atan(7.32 * x / (x**2 + (y - 34)**2 - (7.32/2)**2))
|
||||
rads = math.pi + rads if rads < 0 else rads
|
||||
deg = math.degrees(rads)
|
||||
return deg
|
||||
|
||||
def loc2distance(x, y):
|
||||
return math.sqrt(x**2 + (y - 34)**2)
|
||||
|
||||
angle = loc2angle(x = shooter_x, y = shooter_y)
|
||||
dist = loc2distance(x = shooter_x, y = shooter_y)
|
||||
|
||||
# BRAMKARZ
|
||||
goalkepper = request.args.get('goalkeeper')
|
||||
|
||||
if goalkepper == "null":
|
||||
goalkepper_x, goalkepper_y = np.nan, np.nan
|
||||
else:
|
||||
goalkepper_x, goalkepper_y = goalkepper.split(',')
|
||||
goalkepper_x = float(goalkepper_x)
|
||||
goalkepper_y = float(goalkepper_y)
|
||||
|
||||
print("bramkarz:", goalkepper_x, goalkepper_y)
|
||||
|
||||
if shot_first_time == 'true':
|
||||
shot_first_time = True
|
||||
else:
|
||||
shot_first_time = False
|
||||
if shot_one_on_one == 'true':
|
||||
shot_one_on_one = True
|
||||
else:
|
||||
shot_one_on_one = False
|
||||
if shot_aerial_won == 'true':
|
||||
shot_aerial_won = True
|
||||
else:
|
||||
shot_aerial_won = False
|
||||
if shot_open_goal == 'true':
|
||||
shot_open_goal = True
|
||||
else:
|
||||
shot_open_goal = False
|
||||
if shot_follows_dribble == 'true':
|
||||
shot_follows_dribble = True
|
||||
else:
|
||||
shot_follows_dribble = False
|
||||
if shot_redirect == 'true':
|
||||
shot_redirect = True
|
||||
else:
|
||||
shot_redirect = False
|
||||
|
||||
#### CHECKLIST
|
||||
print('CHECKLISTA')
|
||||
print('shot_first_time', shot_first_time)
|
||||
print('shot_one_on_one', shot_one_on_one)
|
||||
print('shot_aerial_won', shot_aerial_won)
|
||||
print('shot_open_goal', shot_open_goal)
|
||||
print('shot_follows_dribble', shot_follows_dribble)
|
||||
print('shot_redirect', shot_redirect)
|
||||
|
||||
# MODEL XGBOOST
|
||||
response = xgboost_predict_proba(minute=int(gameMinute), #minute=0,
|
||||
position_name=position_name,
|
||||
shot_body_part_name=body_part,
|
||||
shot_technique_name=technique,
|
||||
shot_type_name=acionType,
|
||||
shot_first_time=shot_first_time,
|
||||
shot_one_on_one=shot_one_on_one,
|
||||
shot_aerial_won=shot_aerial_won,
|
||||
shot_open_goal=shot_open_goal,
|
||||
shot_follows_dribble=shot_follows_dribble,
|
||||
shot_redirect=shot_redirect,
|
||||
x1=shooter_x, y1=shooter_y,
|
||||
number_of_players_opponents=number_of_players_opponents,
|
||||
number_of_players_teammates=number_of_players_teammates,
|
||||
angle=angle, distance=dist,
|
||||
x_player_opponent_Goalkeeper=goalkepper_x, y_player_opponent_Goalkeeper=goalkepper_y,
|
||||
x_player_opponent_1=posortowani_obroncy[0][0], y_player_opponent_1=posortowani_obroncy[0][1],
|
||||
x_player_opponent_2=posortowani_obroncy[1][0], y_player_opponent_2=posortowani_obroncy[1][1],
|
||||
x_player_opponent_3=posortowani_obroncy[2][0], y_player_opponent_3=posortowani_obroncy[2][1],
|
||||
x_player_opponent_4=posortowani_obroncy[3][0], y_player_opponent_4=posortowani_obroncy[3][1],
|
||||
x_player_opponent_5=posortowani_obroncy[4][0], y_player_opponent_5=posortowani_obroncy[4][1],
|
||||
x_player_opponent_6=posortowani_obroncy[5][0], y_player_opponent_6=posortowani_obroncy[5][1],
|
||||
x_player_opponent_7=posortowani_obroncy[6][0], y_player_opponent_7=posortowani_obroncy[6][1],
|
||||
x_player_opponent_8=posortowani_obroncy[7][0], y_player_opponent_8=posortowani_obroncy[7][1],
|
||||
x_player_opponent_9=posortowani_obroncy[8][0], y_player_opponent_9=posortowani_obroncy[8][1],
|
||||
x_player_opponent_10=posortowani_obroncy[9][0], y_player_opponent_10=posortowani_obroncy[9][1],
|
||||
x_player_teammate_Goalkeeper=np.nan, y_player_teammate_Goalkeeper=np.nan,
|
||||
x_player_teammate_1=posortowani_atakujacy[0][0], y_player_teammate_1=posortowani_atakujacy[0][1],
|
||||
x_player_teammate_2=posortowani_atakujacy[1][0], y_player_teammate_2=posortowani_atakujacy[1][1],
|
||||
x_player_teammate_3=posortowani_atakujacy[2][0], y_player_teammate_3=posortowani_atakujacy[2][1],
|
||||
x_player_teammate_4=posortowani_atakujacy[3][0], y_player_teammate_4=posortowani_atakujacy[3][1],
|
||||
x_player_teammate_5=posortowani_atakujacy[4][0], y_player_teammate_5=posortowani_atakujacy[4][1],
|
||||
x_player_teammate_6=posortowani_atakujacy[5][0], y_player_teammate_6=posortowani_atakujacy[5][1],
|
||||
x_player_teammate_7=posortowani_atakujacy[6][0], y_player_teammate_7=posortowani_atakujacy[6][1],
|
||||
x_player_teammate_8=posortowani_atakujacy[7][0], y_player_teammate_8=posortowani_atakujacy[7][1],
|
||||
x_player_teammate_9=posortowani_atakujacy[8][0], y_player_teammate_9=posortowani_atakujacy[8][1],
|
||||
x_player_teammate_10=posortowani_atakujacy[9][0], y_player_teammate_10=posortowani_atakujacy[9][1])
|
||||
|
||||
# response = xgboost_predict_proba(shooter = shooter,
|
||||
# opponentsList = opponentsList, teamMatesList = teamMatesList, minute = 20, position_name = position_name, shot_body_part_name = body_part, shot_technique_name = technique,
|
||||
# shot_type_name = acionType, shot_first_time = False,
|
||||
# shot_aerial_won = False, shot_deflected = False, shot_open_goal = False,
|
||||
# shot_follows_dribble = False, shot_redirect = False, shot_kick_off = False, goalkeeper= goalkepper
|
||||
# )
|
||||
|
||||
#print(response)
|
||||
res = str(response)
|
||||
|
Binary file not shown.
1
app/src/flask-server/xgboost.json
Normal file
1
app/src/flask-server/xgboost.json
Normal file
File diff suppressed because one or more lines are too long
@ -4,19 +4,55 @@
|
||||
@tailwind components;
|
||||
@tailwind utilities;
|
||||
|
||||
.Ex{
|
||||
display: block; /* Może być inline-block, jeśli preferujesz */
|
||||
margin: 20px auto; /* Centralnie i z marginesem */
|
||||
padding: 10px;
|
||||
background-color: #4CAF50; /* Przykładowy kolor tła */
|
||||
color: white; /* Kolor tekstu */
|
||||
text-align: center;
|
||||
border-radius: 5px; /* Lekko zaokrąglone rogi */
|
||||
font-size: 20px; /* Duża, czytelna czcionka */
|
||||
font-weight: bold; /* Pogrubienie dla lepszej widoczności */
|
||||
width: 50%; /* Dostosuj szerokość zgodnie z potrzebami */
|
||||
/* Dodatkowe style, takie jak cienie, mogą być dodane */
|
||||
}
|
||||
.Ex {
|
||||
display: block; /* Może być inline-block, jeśli preferujesz */
|
||||
margin: 20px auto; /* Centralnie i z marginesem */
|
||||
padding: 10px;
|
||||
background-color: #4CAF50; /* Przykładowy kolor tła */
|
||||
color: white; /* Kolor tekstu */
|
||||
text-align: center;
|
||||
border-radius: 5px; /* Lekko zaokrąglone rogi */
|
||||
font-size: 20px; /* Duża, czytelna czcionka */
|
||||
font-weight: bold; /* Pogrubienie dla lepszej widoczności */
|
||||
width: 100%; /* Poszerzone pole */
|
||||
box-shadow: 0px 4px 8px rgba(0, 0, 0, 0.5); /* Cień dla dodatkowej głębi */
|
||||
/* Opcjonalnie, można dodać gradient tła dla większego efektu */
|
||||
background-image: linear-gradient(to right, #32CD32 , #4CAF50);
|
||||
transition: transform 0.3s ease; /* Delikatna animacja */
|
||||
}
|
||||
|
||||
.Ex:hover {
|
||||
transform: scale(1.10); /* Efekt powiększenia przy najechaniu */
|
||||
}
|
||||
|
||||
.xg-meter {
|
||||
width: 200px;
|
||||
height: 100px; /* Zmiana wysokości, aby pasowała do proporcji bramki */
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
text-align: center;
|
||||
color: white;
|
||||
font-size: 48px;
|
||||
font-weight: bold;
|
||||
background: url('assets/bramka.jpeg') no-repeat center center; /* Tło z obrazem bramki */
|
||||
background-size: cover; /* Dopasowanie obrazu do rozmiaru elementu */
|
||||
border-radius: 10px; /* Opcjonalnie, dla zaokrąglonych rogów */
|
||||
}
|
||||
|
||||
.xg-value {
|
||||
display: block;
|
||||
background: rgba(0, 0, 0, 0.5); /* Półprzezroczyste tło dla lepszej czytelności tekstu */
|
||||
padding: 5px 10px; /* Dodanie odstępu */
|
||||
border-radius: 5px; /* Zaokrąglone rogi dla tekstu */
|
||||
}
|
||||
|
||||
|
||||
/* Funkcja JavaScript będzie sterować stopniem gradientu */
|
||||
|
||||
|
||||
|
||||
|
||||
body {
|
||||
margin: 50px;
|
||||
display: grid;
|
||||
@ -25,7 +61,7 @@
|
||||
grid-template-rows: auto;
|
||||
grid-template-columns: auto auto auto;
|
||||
}
|
||||
|
||||
|
||||
.container {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
@ -49,19 +85,20 @@
|
||||
max-height: 100%;
|
||||
}
|
||||
|
||||
|
||||
|
||||
.container span {
|
||||
display: block;
|
||||
}
|
||||
|
||||
.main-content {
|
||||
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
|
||||
|
||||
}
|
||||
|
||||
.main-content {
|
||||
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
|
||||
|
||||
}
|
||||
|
||||
.player{
|
||||
width: inherit;
|
||||
height: 8vh;
|
||||
@ -84,7 +121,7 @@
|
||||
background-color: #cccccc;
|
||||
justify-content: space-between;
|
||||
}
|
||||
|
||||
|
||||
.subMenu {
|
||||
display: grid;
|
||||
grid-template-rows: auto auto auto;
|
||||
@ -95,14 +132,15 @@
|
||||
background-color: #f0f0f0; /* Example background color */
|
||||
z-index: 1000; /* Ensure it stays on top of other content */
|
||||
}
|
||||
.player-list{
|
||||
|
||||
.player-list {
|
||||
background-color: rgb(61, 38, 38);
|
||||
width: 13vw;
|
||||
height: calc(50vw*68/105);
|
||||
overflow: scroll;
|
||||
|
||||
|
||||
font-size: 12px; /* Example font size - adjust as needed */
|
||||
}
|
||||
|
||||
.top-bar {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
@ -112,7 +150,7 @@
|
||||
/* Możesz dodać dodatkowe style, jak tło, obramowanie itp. */
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
|
||||
.bottom-bar {
|
||||
display: flex;
|
||||
justify-content: space-between; /* Rozmieszcza przyciski równomiernie */
|
||||
@ -128,7 +166,7 @@
|
||||
border-radius: 50%;
|
||||
position: absolute
|
||||
}
|
||||
|
||||
|
||||
.reset-button {
|
||||
position: relative;
|
||||
margin: 5px;
|
||||
@ -200,7 +238,7 @@
|
||||
color: #000000;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
|
||||
.cho-first_time {
|
||||
position: relative;
|
||||
padding: 10px;
|
||||
@ -237,7 +275,38 @@
|
||||
color: #000000;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
|
||||
.additional-parameters {
|
||||
position: relative; /* Or absolute, depending on layout */
|
||||
right: 0;
|
||||
top: 30%; /* Adjusted to a higher position */
|
||||
width: 250px; /* Increased width */
|
||||
background-color: #000000;
|
||||
padding: 15px; /* Increased padding */
|
||||
border: 1px solid #ddd;
|
||||
border-radius: 5px;
|
||||
box-shadow: 0 2px 5px rgba(0,0,0,0.2);
|
||||
z-index: 100; /* To ensure it stays on top */
|
||||
color: #ffffff; /* Optional: change text color for better visibility on dark background */
|
||||
}
|
||||
|
||||
.additional-parameters h3 {
|
||||
margin-top: 0;
|
||||
font-size: 18px; /* Increased font size for heading */
|
||||
}
|
||||
|
||||
.additional-parameters label {
|
||||
display: flex; /* Updated to flex for better alignment */
|
||||
align-items: center; /* Aligns checkbox and label text vertically */
|
||||
margin-bottom: 10px; /* Increased spacing between checkboxes */
|
||||
font-size: 16px; /* Increased font size for labels */
|
||||
}
|
||||
|
||||
.additional-parameters input[type="checkbox"] {
|
||||
margin-right: 10px; /* Adds spacing between checkbox and label text */
|
||||
}
|
||||
|
||||
|
||||
/* DROPDOWNS */
|
||||
/* Style the dropdown button */
|
||||
.dropbtn {
|
||||
@ -253,13 +322,13 @@
|
||||
.dropbtn:hover, .dropbtn:focus {
|
||||
background-color: #3e8e41;
|
||||
}
|
||||
|
||||
|
||||
/* The container <div> - needed to position the dropdown content */
|
||||
.dropdown {
|
||||
position: relative;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_body_part {
|
||||
display: none;
|
||||
position: absolute;
|
||||
@ -268,7 +337,7 @@
|
||||
box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_body_part a{
|
||||
color: black;
|
||||
padding: 12px 16px;
|
||||
@ -276,15 +345,15 @@
|
||||
display: block;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
|
||||
/* Change color of dropdown links on hover */
|
||||
.cho-dropdown_body_part a:hover {background-color: #f1f1f1}
|
||||
|
||||
|
||||
/* Show the dropdown menu on hover */
|
||||
.dropdown:hover .cho-dropdown_body_part {
|
||||
display: block;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_position_name {
|
||||
display: none;
|
||||
position: absolute;
|
||||
@ -293,7 +362,7 @@
|
||||
box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_position_name a {
|
||||
color: black;
|
||||
padding: 12px 16px;
|
||||
@ -301,15 +370,15 @@
|
||||
display: block;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
|
||||
/* Change color of dropdown links on hover */
|
||||
.cho-dropdown_position_name a:hover {background-color: #f1f1f1}
|
||||
|
||||
|
||||
/* Show the dropdown menu on hover */
|
||||
.dropdown:hover .cho-dropdown_position_name {
|
||||
display: block;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_technique_name {
|
||||
position: relative;
|
||||
display: none;
|
||||
@ -319,7 +388,7 @@
|
||||
box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_technique_name a {
|
||||
color: black;
|
||||
padding: 12px 16px;
|
||||
@ -327,15 +396,15 @@
|
||||
display: block;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
|
||||
/* Change color of dropdown links on hover */
|
||||
.cho-dropdown_technique_name a:hover {background-color: #f1f1f1}
|
||||
|
||||
|
||||
/* Show the dropdown menu on hover */
|
||||
.dropdown:hover .cho-dropdown_technique_name {
|
||||
display: block;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_type_name {
|
||||
display: none;
|
||||
position: absolute;
|
||||
@ -344,7 +413,7 @@
|
||||
box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
|
||||
.cho-dropdown_type_name a {
|
||||
color: black;
|
||||
padding: 12px 16px;
|
||||
@ -352,16 +421,16 @@
|
||||
display: block;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
|
||||
/* Change color of dropdown links on hover */
|
||||
.cho-dropdown_type_name a:hover {background-color: #f1f1f1}
|
||||
|
||||
|
||||
/* Show the dropdown menu on hover */
|
||||
.dropdown:hover .cho-dropdown_type_name {
|
||||
display: block;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/* MANUAL INPUT */
|
||||
.cho-minute {
|
||||
margin-top: 10px;
|
||||
@ -574,5 +643,5 @@
|
||||
-2.6em 0em 0 0em rgba(255, 255, 255, 0.7), -1.8em -1.8em 0 0em #ffffff;
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
BIN
data/.DS_Store
vendored
BIN
data/.DS_Store
vendored
Binary file not shown.
76686
data/final_data.csv
76686
data/final_data.csv
File diff suppressed because it is too large
Load Diff
82822
data/final_data_new.csv
Normal file
82822
data/final_data_new.csv
Normal file
File diff suppressed because it is too large
Load Diff
38343
data/final_data_old.csv
Normal file
38343
data/final_data_old.csv
Normal file
File diff suppressed because it is too large
Load Diff
BIN
notebooks/.DS_Store
vendored
BIN
notebooks/.DS_Store
vendored
Binary file not shown.
@ -11,33 +11,33 @@ library(purrr)
|
||||
|
||||
# code and data from https://github.com/Dato-Futbol/xg-model
|
||||
get_shots <- function(file_path, name_detail, save_files = F){
|
||||
|
||||
|
||||
players <- fromJSON("data/players.json")
|
||||
|
||||
|
||||
shots <- fromJSON(file_path) %>%
|
||||
filter(subEventName == "Shot")
|
||||
|
||||
|
||||
tags <- tibble(tags = shots$tags) %>%
|
||||
hoist(tags,
|
||||
hoist(tags,
|
||||
tags_id = "id") %>%
|
||||
unnest_wider(tags_id, names_sep = "")
|
||||
|
||||
|
||||
tags2 <- tags %>%
|
||||
mutate(is_goal = ifelse(rowSums(. == "101", na.rm = T) > 0, 1, 0),
|
||||
is_blocked = ifelse(rowSums(. == "2101", na.rm = T) > 0, 1, 0),
|
||||
is_CA = ifelse(rowSums(. == "1901", na.rm = T) > 0, 1, 0), # is countre attack
|
||||
body_part = ifelse(rowSums(. == "401", na.rm = T) > 0, "left",
|
||||
ifelse(rowSums(. == "402", na.rm = T) > 0, "right",
|
||||
body_part = ifelse(rowSums(. == "401", na.rm = T) > 0, "left",
|
||||
ifelse(rowSums(. == "402", na.rm = T) > 0, "right",
|
||||
ifelse(rowSums(. == "403", na.rm = T) > 0, "head/body", "NA"))))
|
||||
|
||||
|
||||
pos <- tibble(positions = shots$positions) %>%
|
||||
hoist(positions,
|
||||
hoist(positions,
|
||||
y = "y",
|
||||
x = "x") %>%
|
||||
unnest_wider(y, names_sep = "") %>%
|
||||
unnest_wider(x, names_sep = "") %>%
|
||||
dplyr::select(-c(x2, y2))
|
||||
|
||||
|
||||
shots_ok <- shots %>%
|
||||
dplyr::select(matchId, teamId, playerId, eventSec, matchPeriod) %>%
|
||||
bind_cols(pos, tags2) %>%
|
||||
@ -46,14 +46,14 @@ get_shots <- function(file_path, name_detail, save_files = F){
|
||||
left_join(players %>%
|
||||
dplyr::select(c("wyId", "foot")), by = c("playerId" = "wyId")) %>%
|
||||
mutate(league = name_detail)
|
||||
|
||||
|
||||
if(save_files){
|
||||
write_rds(shots, paste0("shots", name_detail, ".rds"))
|
||||
write_rds(tags2, paste0("tags2", name_detail, ".rds"))
|
||||
write_rds(pos, paste0("pos", name_detail, ".rds"))
|
||||
write_rds(shots_ok, paste0("unblocked_shots", name_detail, ".rds"))
|
||||
}
|
||||
|
||||
|
||||
shots_ok
|
||||
}
|
||||
# shotsEN <- get_shots("data/events/events_England.json", "EN")
|
||||
@ -63,12 +63,12 @@ get_shots <- function(file_path, name_detail, save_files = F){
|
||||
# shotsGE <- get_shots("data/events/events_Germany.json", "GE")
|
||||
# shotsFR <- get_shots("data/events/events_France.json", "FR")
|
||||
# shotsEC <- get_shots("data/events/events_European_Championship.json", "EC")
|
||||
#
|
||||
#
|
||||
# shots <- shotsEN %>%
|
||||
# bind_rows(shotsFR, shotsGE, shotsIT, shotsSP, shotsWC, shotsEC)
|
||||
|
||||
get_final_data <- function(data) {
|
||||
|
||||
|
||||
data <- data %>% select(eventSec, y1, x1, is_goal, is_blocked, is_CA, body_part, foot)
|
||||
data$x1 <- (100 - data$x1) * 105/100
|
||||
data$y1 <- data$y1 * data$y1/100
|
||||
@ -77,7 +77,7 @@ get_final_data <- function(data) {
|
||||
data <- data %>% mutate(distance = sqrt( (100 - x1)^2 + (34 - y1)^2),
|
||||
minute = round(eventSec / 60),
|
||||
eventSec = round(eventSec))
|
||||
|
||||
|
||||
data
|
||||
}
|
||||
|
||||
@ -89,14 +89,14 @@ get_final_data <- function(data) {
|
||||
get_data <- function(event_path, info_path) {
|
||||
events <- read.csv(event_path)
|
||||
info <- read.csv(info_path)
|
||||
|
||||
|
||||
events <- merge(events, info[, c('id_odsp', 'country', 'date')], by = 'id_odsp', all.x = TRUE)
|
||||
data <- subset(events, event_type == 1)
|
||||
|
||||
|
||||
data_final <- data %>% select(sort_order, time, shot_place, shot_outcome, is_goal, location, bodypart, assist_method, situation,
|
||||
fast_break)
|
||||
data_final
|
||||
|
||||
|
||||
}
|
||||
|
||||
# data2 <- get_data(event_path = "data/events.csv", info_path = "data/ginf.csv")
|
||||
@ -124,18 +124,18 @@ loc2locdistance <- function(x1, y1, x2, y2) {
|
||||
|
||||
get_shots2 <- function(json_file) {
|
||||
data <- fromJSON(json_file) %>% filter(type$name == "Shot") %>% dplyr::select(c(minute, position, location, shot))
|
||||
|
||||
|
||||
df_temp <- do.call(rbind, lapply(data$location, function(loc) c(120, 80) - loc))
|
||||
colnames(df_temp) <- c("x1", "y1")
|
||||
|
||||
|
||||
data$x1 <- df_temp[,1]
|
||||
data$y1 <- df_temp[,2]
|
||||
|
||||
|
||||
data$shot$freeze_frame <- Map(function(ff, x1, y1) {
|
||||
ff$x1 <- yd_to_m(x1)
|
||||
ff$y1 <- yd_to_m(y1)
|
||||
return(ff)
|
||||
},
|
||||
},
|
||||
data$shot$freeze_frame, data$x1, data$y1)
|
||||
|
||||
tryCatch({
|
||||
@ -148,17 +148,17 @@ get_shots2 <- function(json_file) {
|
||||
df <- df %>% mutate(teammate = ifelse(teammate, "teammate", "opponent"),
|
||||
distance = loc2locdistance(x1 = x, y1 = y, x2 = x1, y2 = y1)) %>%
|
||||
arrange(distance)
|
||||
|
||||
|
||||
groups_count <- df %>% group_by(teammate) %>% count() %>% as.data.frame()
|
||||
if ( !("opponent" %in% groups_count$teammate) ) {
|
||||
groups_count <- groups_count %>% add_row(teammate = "opponent", n = 0)
|
||||
} else if ( !("teammate" %in% groups_count$teammate) ) {
|
||||
groups_count <- groups_count %>% add_row(teammate = "teammate", n = 0)
|
||||
}
|
||||
|
||||
|
||||
na_df <- as.data.frame(matrix("na", nrow = 21 - nrow(df), ncol = ncol(df)))
|
||||
colnames(na_df) <- colnames(df)
|
||||
|
||||
|
||||
na_df$teammate <- rep(c("opponent", "teammate"), c(11, 10) - groups_count$n)
|
||||
dff <- rbind(df, na_df)
|
||||
dff <- dff %>% group_by(teammate) %>% mutate(rown = row_number(distance)) %>% ungroup() %>%
|
||||
@ -170,9 +170,9 @@ get_shots2 <- function(json_file) {
|
||||
dff <- as.data.frame(matrix("na", nrow = 21, ncol = 3))
|
||||
colnames(dff) <- c("x", "y", "teammate")
|
||||
dff$teammate <- rep(c("opponent", "teammate"), c(11, 10))
|
||||
dff <- dff %>% group_by(teammate) %>% mutate(rown = row_number()) %>% ungroup() %>%
|
||||
mutate(position_teammate = paste(teammate, rown, sep = "_")) %>%
|
||||
select(-c(teammate, rown)) %>%
|
||||
dff <- dff %>% group_by(teammate) %>% mutate(rown = row_number()) %>% ungroup() %>%
|
||||
mutate(position_teammate = paste(teammate, rown, sep = "_")) %>%
|
||||
select(-c(teammate, rown)) %>%
|
||||
mutate(x = ifelse(x == "na", NA, x),
|
||||
y = ifelse(x == "na", NA, y))
|
||||
}
|
||||
@ -181,7 +181,7 @@ get_shots2 <- function(json_file) {
|
||||
# %>%
|
||||
# stop("123")
|
||||
wider_df <- dff %>%
|
||||
pivot_wider(names_from = position_teammate, values_from = c(x, y), names_sep = "_player_") %>%
|
||||
pivot_wider(names_from = position_teammate, values_from = c(x, y), names_sep = "_player_") %>%
|
||||
mutate(across(everything(), as.numeric))
|
||||
wider_df
|
||||
# wider_df <- apply(wider_df, MARGIN = 2, unlist)
|
||||
@ -193,7 +193,7 @@ get_shots2 <- function(json_file) {
|
||||
print(paste("An error occurred:", e$message))
|
||||
})
|
||||
df_players_location <- df_players_location %>% t()
|
||||
|
||||
|
||||
tryCatch({ # TODO reduce error cases
|
||||
data$number_of_players_opponents <- mapply(function(sublist, x1_threshold) {
|
||||
# Extracting the first location value and converting it to numeric
|
||||
@ -213,12 +213,12 @@ get_shots2 <- function(json_file) {
|
||||
# handle the error
|
||||
print(paste("An error occurred:", e$message))
|
||||
})
|
||||
|
||||
|
||||
tryCatch({ # TODO reduce error cases
|
||||
data$number_of_players_teammates <- mapply(function(sublist, x1_threshold) {
|
||||
# Extracting the first location value and converting it to numeric
|
||||
first_location_values <- sapply(sublist$location, function(loc) as.numeric(loc[1]))
|
||||
|
||||
|
||||
if ("teammate" %in% names(sublist)) {
|
||||
# Filtering and counting
|
||||
res <- sum(sublist$teammate & first_location_values > x1_threshold) # error here
|
||||
@ -233,71 +233,71 @@ get_shots2 <- function(json_file) {
|
||||
# handle the error
|
||||
print(paste("An error occurred:", e$message))
|
||||
})
|
||||
|
||||
|
||||
|
||||
|
||||
data$shot <- data$shot %>% select(-freeze_frame, -statsbomb_xg, -key_pass_id)
|
||||
data$shot$body_part <- data$shot$body_part %>% select(-id)
|
||||
data$shot$technique <- data$shot$technique %>% select(-id)
|
||||
data$shot$type <- data$shot$type %>% select(-id)
|
||||
data$position <- data$position %>% select(-id)
|
||||
|
||||
|
||||
data$shot <- data$shot %>% select(-end_location)
|
||||
|
||||
|
||||
tryCatch({ # TODO reduce error cases
|
||||
if ("one_on_one" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$one_on_one), ]$shot$one_on_one <- FALSE
|
||||
} else {
|
||||
data$shot$one_on_one <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("first_time" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$first_time), ]$shot$first_time <- FALSE
|
||||
} else {
|
||||
data$shot$first_time <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("aerial_won" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$aerial_won), ]$shot$aerial_won <- FALSE
|
||||
} else {
|
||||
data$shot$aerial_won <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("saved_to_post" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$saved_to_post), ]$shot$saved_to_post <- FALSE
|
||||
} else {
|
||||
data$shot$saved_to_post <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("deflected" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$deflected), ]$shot$deflected <- FALSE
|
||||
} else {
|
||||
data$shot$deflected <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("saved_off_target" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$saved_off_target), ]$shot$saved_off_target <- FALSE
|
||||
} else {
|
||||
data$shot$saved_off_target <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("open_goal" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$open_goal), ]$shot$open_goal <- FALSE
|
||||
} else {
|
||||
data$shot$open_goal <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("follows_dribble" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$follows_dribble), ]$shot$follows_dribble <- FALSE
|
||||
} else {
|
||||
data$shot$follows_dribble <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("redirect" %in% colnames(data$shot)) {
|
||||
data[is.na(data$shot$redirect), ]$shot$redirect <- FALSE
|
||||
} else {
|
||||
data$shot$redirect <- FALSE
|
||||
}
|
||||
|
||||
|
||||
if ("kick_off" %in% colnames(data$kick_off)) {
|
||||
data[is.na(data$shot$kick_off), ]$shotf$kick_off <- FALSE
|
||||
} else {
|
||||
@ -308,21 +308,21 @@ get_shots2 <- function(json_file) {
|
||||
# handle the error
|
||||
print(paste("An error occurred:", e$message))
|
||||
})
|
||||
|
||||
|
||||
data <- data %>% mutate(is_goal = ifelse(shot$outcome$id == 97, 1, 0),
|
||||
x1 = yd_to_m(x1) %>% round(., digits = 1),
|
||||
y1 = yd_to_m(y1) %>% round(., digits = 1),
|
||||
angle = loc2angle(x1, y1) %>% round(., digits = 1),
|
||||
distance = loc2distance(x = x1, y = y1)) %>%
|
||||
distance = loc2distance(x = x1, y = y1)) %>%
|
||||
select(-location)
|
||||
data$shot$outcome <- data$shot$outcome %>% select(-id)
|
||||
data <- data %>% unnest(shot, names_sep = "_") %>%
|
||||
unnest(position, names_sep = "_") %>%
|
||||
unnest(shot_type, names_sep = "_") %>%
|
||||
data <- data %>% unnest(shot, names_sep = "_") %>%
|
||||
unnest(position, names_sep = "_") %>%
|
||||
unnest(shot_type, names_sep = "_") %>%
|
||||
unnest(shot_outcome, names_sep = "_") %>%
|
||||
unnest(shot_technique, names_sep = "_") %>%
|
||||
unnest(shot_technique, names_sep = "_") %>%
|
||||
unnest(shot_body_part, names_sep = "_")
|
||||
|
||||
|
||||
data <- cbind(data, df_players_location)
|
||||
data
|
||||
}
|
||||
@ -338,12 +338,12 @@ skimr::skim(combined_data)
|
||||
data3_final <- combined_data %>% select(-c(shot_outcome_name,
|
||||
shot_saved_off_target,
|
||||
shot_saved_to_post,
|
||||
kick_off)) %>%
|
||||
kick_off)) %>%
|
||||
mutate(shot_kick_off = ifelse(is.na(shot_kick_off), FALSE, shot_kick_off))
|
||||
pattern <- "^(x_player_|y_player_).*$"
|
||||
cols <- names(data3_final)[grepl(pattern, names(data3_final))]
|
||||
data_final <- data3_final %>% unnest(all_of(cols))
|
||||
skimr::skim(data_final)
|
||||
write_csv(data_final, file = "data/final_data.csv")
|
||||
df_test <- read.csv("data/final_data.csv", nrows = 1000)
|
||||
#df_test <- read.csv("data/final_data.csv", nrows = 10000)
|
||||
##################### The fourth dataset ##############################
|
||||
|
38343
notebooks/final_data.csv
Normal file
38343
notebooks/final_data.csv
Normal file
File diff suppressed because it is too large
Load Diff
82822
notebooks/final_data_new.csv
Normal file
82822
notebooks/final_data_new.csv
Normal file
File diff suppressed because it is too large
Load Diff
38343
notebooks/final_data_old.csv
Normal file
38343
notebooks/final_data_old.csv
Normal file
File diff suppressed because it is too large
Load Diff
BIN
notebooks/labelEncoder.joblib
Normal file
BIN
notebooks/labelEncoder.joblib
Normal file
Binary file not shown.
Binary file not shown.
File diff suppressed because one or more lines are too long
Loading…
Reference in New Issue
Block a user