2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
package gui
|
|
|
|
|
|
|
|
// viewAnalysisGui_Couple.go implements pages to view a couple genetic analysis
|
|
|
|
|
|
|
|
import "fyne.io/fyne/v2"
|
|
|
|
import "fyne.io/fyne/v2/container"
|
|
|
|
import "fyne.io/fyne/v2/layout"
|
|
|
|
import "fyne.io/fyne/v2/theme"
|
|
|
|
import "fyne.io/fyne/v2/widget"
|
|
|
|
|
|
|
|
import "seekia/resources/geneticReferences/monogenicDiseases"
|
|
|
|
import "seekia/resources/geneticReferences/polygenicDiseases"
|
|
|
|
import "seekia/resources/geneticReferences/traits"
|
|
|
|
|
|
|
|
import "seekia/internal/appMemory"
|
2024-06-02 10:43:39 +02:00
|
|
|
import "seekia/internal/encoding"
|
|
|
|
import "seekia/internal/genetics/geneticAnalysis"
|
2024-04-11 15:51:56 +02:00
|
|
|
import "seekia/internal/genetics/myGenomes"
|
|
|
|
import "seekia/internal/genetics/myPeople"
|
|
|
|
import "seekia/internal/genetics/readGeneticAnalysis"
|
|
|
|
import "seekia/internal/helpers"
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
import "slices"
|
2024-04-11 15:51:56 +02:00
|
|
|
import "errors"
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisPage(window fyne.Window, person1Identifier string, person2Identifier string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, numberOfPerson1GenomesAnalyzed int, numberOfPerson2GenomesAnalyzed int, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
appMemory.SetMemoryEntry("CurrentViewedPage", "ViewCoupleGeneticAnalysisPage")
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisPage(window, person1Identifier, person2Identifier, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, numberOfPerson1GenomesAnalyzed, numberOfPerson2GenomesAnalyzed, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Genetic Analysis")
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
warningLabel1 := getBoldLabelCentered("WARNING: Results are not accurate!")
|
|
|
|
warningLabel2 := getBoldLabelCentered("The analysis algorithms have known issues that are being worked on.")
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person1Found, person1Name, _, _, err := myPeople.GetPersonInfo(person1Identifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
if (person1Found == false){
|
2024-04-11 15:51:56 +02:00
|
|
|
setErrorEncounteredPage(window, errors.New("Couple person A not found."), previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person2Found, person2Name, _, _, err := myPeople.GetPersonInfo(person2Identifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
if (person2Found == false){
|
2024-04-11 15:51:56 +02:00
|
|
|
setErrorEncounteredPage(window, errors.New("Couple person B not found."), previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
coupleNameLabel := widget.NewLabel("Couple Name:")
|
2024-06-02 10:43:39 +02:00
|
|
|
coupleNameText := getBoldLabel(person1Name + " + " + person2Name)
|
2024-04-11 15:51:56 +02:00
|
|
|
coupleNameRow := container.NewHBox(layout.NewSpacer(), coupleNameLabel, coupleNameText, layout.NewSpacer())
|
|
|
|
|
|
|
|
numberOfAnalyzedGenomesLabel := getLabelCentered("Number of Analyzed Genomes:")
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person1NameLabel := widget.NewLabel(person1Name + ":")
|
|
|
|
person1NumberOfGenomesAnalyzedString := helpers.ConvertIntToString(numberOfPerson1GenomesAnalyzed)
|
|
|
|
person1NumberOfGenomesAnalyzedLabel := getBoldLabel(person1NumberOfGenomesAnalyzedString)
|
|
|
|
person1NumberOfAnalyzedGenomesRow := container.NewHBox(layout.NewSpacer(), person1NameLabel, person1NumberOfGenomesAnalyzedLabel, layout.NewSpacer())
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person2NameLabel := widget.NewLabel(person2Name + ":")
|
|
|
|
person2NumberOfGenomesAnalyzedString := helpers.ConvertIntToString(numberOfPerson2GenomesAnalyzed)
|
|
|
|
person2NumberOfGenomesAnalyzedLabel := getBoldLabel(person2NumberOfGenomesAnalyzedString)
|
|
|
|
person2NumberOfAnalyzedGenomesRow := container.NewHBox(layout.NewSpacer(), person2NameLabel, person2NumberOfGenomesAnalyzedLabel, layout.NewSpacer())
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
generalButton := widget.NewButton("General", func(){
|
|
|
|
//TODO: Offspring inbred rating (kinship of parents), ancestry
|
|
|
|
showUnderConstructionDialog(window)
|
|
|
|
})
|
|
|
|
monogenicDiseasesButton := widget.NewButton("Monogenic Diseases", func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisMonogenicDiseasesPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
polygenicDiseasesButton := widget.NewButton("Polygenic Diseases", func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisPolygenicDiseasesPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
traitsButton := widget.NewButton("Traits", func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisTraitsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
categoryButtonsGrid := getContainerCentered(container.NewGridWithColumns(1, generalButton, monogenicDiseasesButton, polygenicDiseasesButton, traitsButton))
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), warningLabel1, warningLabel2, widget.NewSeparator(), coupleNameRow, widget.NewSeparator(), numberOfAnalyzedGenomesLabel, person1NumberOfAnalyzedGenomesRow, person2NumberOfAnalyzedGenomesRow, widget.NewSeparator(), categoryButtonsGrid)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisMonogenicDiseasesPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisMonogenicDiseasesPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Genetic Analysis - Monogenic Diseases")
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is an analysis of the monogenic disease probabilities for the couple's offspring.")
|
|
|
|
|
|
|
|
//TODO: Sort so highest risk diseases are at the top. Everything else should be in normal order
|
|
|
|
|
|
|
|
getMonogenicDiseasesGrid := func()(*fyne.Container, error){
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, _, _, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){ return nil, err }
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
diseaseNameLabel := getItalicLabelCentered("Disease Name")
|
|
|
|
|
|
|
|
offspringProbabilityOfLabel := getItalicLabelCentered("Offspring Probability Of")
|
|
|
|
havingDiseaseLabel := getItalicLabelCentered("Having Disease")
|
|
|
|
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
conflictExistsLabel := getItalicLabelCentered("Conflict Exists?")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
emptyLabelD := widget.NewLabel("")
|
|
|
|
|
|
|
|
diseaseNameColumn := container.NewVBox(emptyLabelA, diseaseNameLabel, widget.NewSeparator())
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn := container.NewVBox(offspringProbabilityOfLabel, havingDiseaseLabel, widget.NewSeparator())
|
|
|
|
conflictExistsColumn := container.NewVBox(emptyLabelB, conflictExistsLabel, widget.NewSeparator())
|
|
|
|
viewButtonsColumn := container.NewVBox(emptyLabelC, emptyLabelD, widget.NewSeparator())
|
|
|
|
|
|
|
|
monogenicDiseaseNamesList, err := monogenicDiseases.GetMonogenicDiseaseNamesList()
|
|
|
|
if (err != nil){ return nil, err }
|
|
|
|
|
|
|
|
for _, diseaseName := range monogenicDiseaseNamesList{
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1GenomeIdentifierSlice := slices.Concat(pair1Person1GenomeIdentifier[:], pair1Person2GenomeIdentifier[:])
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1GenomeIdentifier := [32]byte(pair1GenomeIdentifierSlice)
|
|
|
|
|
|
|
|
offspringHasDiseaseProbabilityIsKnown, _, genomePairOffspringProbabilityOfHavingDisease, _, _, _, conflictExists, err := readGeneticAnalysis.GetOffspringMonogenicDiseaseInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, pair1GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
getOffspringProbabilityOfHavingDiseaseText := func()string{
|
2024-06-02 10:43:39 +02:00
|
|
|
if (offspringHasDiseaseProbabilityIsKnown == false){
|
2024-04-11 15:51:56 +02:00
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return genomePairOffspringProbabilityOfHavingDisease
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingDiseaseText := getOffspringProbabilityOfHavingDiseaseText()
|
|
|
|
|
|
|
|
diseaseNameText := getBoldLabelCentered(diseaseName)
|
|
|
|
diseaseNameColumn.Add(diseaseNameText)
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingDiseaseLabel := getBoldLabelCentered(offspringProbabilityOfHavingDiseaseText)
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn.Add(offspringProbabilityOfHavingDiseaseLabel)
|
|
|
|
|
|
|
|
conflictExistsString := helpers.ConvertBoolToYesOrNoString(conflictExists)
|
|
|
|
conflictExistsLabel := getBoldLabelCentered(conflictExistsString)
|
|
|
|
conflictExistsColumn.Add(conflictExistsLabel)
|
|
|
|
|
|
|
|
viewDetailsButton := getWidgetCentered(widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisMonogenicDiseaseDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
}))
|
|
|
|
viewButtonsColumn.Add(viewDetailsButton)
|
|
|
|
|
|
|
|
diseaseNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn.Add(widget.NewSeparator())
|
|
|
|
conflictExistsColumn.Add(widget.NewSeparator())
|
|
|
|
viewButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingDiseaseHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringProbabilityOfHavingMonogenicDiseaseExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn.Add(offspringProbabilityOfHavingDiseaseHelpButton)
|
|
|
|
|
|
|
|
diseasesGrid := container.NewHBox(layout.NewSpacer(), diseaseNameColumn, offspringProbabilityOfHavingDiseaseColumn)
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
|
|
|
|
|
|
|
conflictExistsHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setCoupleGeneticAnalysisConflictExistsExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
conflictExistsColumn.Add(conflictExistsHelpButton)
|
|
|
|
|
|
|
|
diseasesGrid.Add(conflictExistsColumn)
|
|
|
|
}
|
|
|
|
|
|
|
|
diseasesGrid.Add(viewButtonsColumn)
|
|
|
|
diseasesGrid.Add(layout.NewSpacer())
|
|
|
|
|
|
|
|
return diseasesGrid, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
monogenicDiseasesContainer, err := getMonogenicDiseasesGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), monogenicDiseasesContainer)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisMonogenicDiseaseDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisMonogenicDiseaseDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Couple Analysis - " + diseaseName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
getDescriptionSection := func()*fyne.Container{
|
|
|
|
|
|
|
|
if (secondGenomePairExists == false){
|
|
|
|
description := getLabelCentered("Below are the disease probabilities for the couple's offspring.")
|
|
|
|
|
|
|
|
return description
|
|
|
|
}
|
|
|
|
|
|
|
|
description1 := getLabelCentered("Below are the disease probabilities for the couple's offspring.")
|
|
|
|
description2 := getLabelCentered("Each genome pair combines different genomes from each person.")
|
|
|
|
|
|
|
|
descriptionsSection := container.NewVBox(description1, description2)
|
|
|
|
|
|
|
|
return descriptionsSection
|
|
|
|
}
|
|
|
|
|
|
|
|
descriptionSection := getDescriptionSection()
|
|
|
|
|
|
|
|
diseaseNameLabel := widget.NewLabel("Disease:")
|
|
|
|
diseaseNameText := getBoldLabel(diseaseName)
|
|
|
|
diseaseNameInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
|
|
|
setViewMonogenicDiseaseDetailsPage(window, diseaseName, currentPage)
|
|
|
|
})
|
|
|
|
diseaseNameRow := container.NewHBox(layout.NewSpacer(), diseaseNameLabel, diseaseNameText, diseaseNameInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
emptyLabel1 := widget.NewLabel("")
|
|
|
|
emptyLabel2 := widget.NewLabel("")
|
|
|
|
|
|
|
|
emptyLabel3 := widget.NewLabel("")
|
|
|
|
emptyLabel4 := widget.NewLabel("")
|
|
|
|
|
|
|
|
offspringProbabilityOfLabel1 := getItalicLabelCentered("Offspring Probability Of")
|
|
|
|
havingDiseaseLabel := getItalicLabelCentered("Having Disease")
|
|
|
|
|
|
|
|
offspringProbabilityOfLabel2 := getItalicLabelCentered("Offspring Probability Of")
|
|
|
|
havingVariantLabel := getItalicLabelCentered("Having Variant")
|
|
|
|
|
|
|
|
emptyLabel5 := widget.NewLabel("")
|
|
|
|
emptyLabel6 := widget.NewLabel("")
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn := container.NewVBox(emptyLabel1, emptyLabel2, widget.NewSeparator())
|
|
|
|
pairNameColumn := container.NewVBox(emptyLabel3, emptyLabel4, widget.NewSeparator())
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn := container.NewVBox(offspringProbabilityOfLabel1, havingDiseaseLabel, widget.NewSeparator())
|
|
|
|
offspringProbabilityOfHavingVariantColumn := container.NewVBox(offspringProbabilityOfLabel2, havingVariantLabel, widget.NewSeparator())
|
|
|
|
viewOffspringVariantButtonsColumn := container.NewVBox(emptyLabel5, emptyLabel6, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomePairRow := func(genomePairName string, person1GenomeIdentifier [16]byte, person2GenomeIdentifier [16]byte)error{
|
|
|
|
|
|
|
|
genomePairIdentifierSlice := slices.Concat(person1GenomeIdentifier[:], person2GenomeIdentifier[:])
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePairIdentifier := [32]byte(genomePairIdentifierSlice)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringProbabilityOfHavingDiseaseIsKnown, _, genomePairOffspringProbabilityOfHavingDisease, offspringProbabilityOfHavingAVariantIsKnown, _, genomePairOffspringProbabilityOfHavingAVariant, _, err := readGeneticAnalysis.GetOffspringMonogenicDiseaseInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getOffspringProbabilityOfHavingDiseaseText := func()string{
|
2024-06-02 10:43:39 +02:00
|
|
|
if (offspringProbabilityOfHavingDiseaseIsKnown == false){
|
2024-04-11 15:51:56 +02:00
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return genomePairOffspringProbabilityOfHavingDisease
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingDiseaseText := getOffspringProbabilityOfHavingDiseaseText()
|
|
|
|
|
|
|
|
getOffspringProbabilityOfHavingAVariantText := func()string{
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
if (offspringProbabilityOfHavingAVariantIsKnown == false){
|
2024-04-11 15:51:56 +02:00
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
return genomePairOffspringProbabilityOfHavingAVariant
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingAVariantText := getOffspringProbabilityOfHavingAVariantText()
|
|
|
|
|
|
|
|
genomePairNameLabel := getBoldLabelCentered(genomePairName)
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingDiseaseLabel := getBoldLabelCentered(offspringProbabilityOfHavingDiseaseText)
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingAVariantLabel := getBoldLabelCentered(offspringProbabilityOfHavingAVariantText)
|
|
|
|
|
|
|
|
viewGenomePairButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisMonogenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
viewOffspringVariantsButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleMonogenicDiseaseVariantsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn.Add(viewGenomePairButton)
|
|
|
|
pairNameColumn.Add(genomePairNameLabel)
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn.Add(offspringProbabilityOfHavingDiseaseLabel)
|
|
|
|
offspringProbabilityOfHavingVariantColumn.Add(offspringProbabilityOfHavingAVariantLabel)
|
|
|
|
viewOffspringVariantButtonsColumn.Add(viewOffspringVariantsButton)
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
pairNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn.Add(widget.NewSeparator())
|
|
|
|
offspringProbabilityOfHavingVariantColumn.Add(widget.NewSeparator())
|
|
|
|
viewOffspringVariantButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
err = addGenomePairRow("Pair 1", pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
2024-06-02 10:43:39 +02:00
|
|
|
err := addGenomePairRow("Pair 2", pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingDiseaseHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringProbabilityOfHavingMonogenicDiseaseExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingVariantHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringProbabilityOfHavingVariantExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
offspringProbabilityOfHavingDiseaseColumn.Add(offspringProbabilityOfHavingDiseaseHelpButton)
|
|
|
|
offspringProbabilityOfHavingVariantColumn.Add(offspringProbabilityOfHavingVariantHelpButton)
|
|
|
|
|
|
|
|
genomesContainer := container.NewHBox(layout.NewSpacer(), viewGenomePairButtonsColumn, pairNameColumn, offspringProbabilityOfHavingDiseaseColumn, offspringProbabilityOfHavingVariantColumn, viewOffspringVariantButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), descriptionSection, widget.NewSeparator(), diseaseNameRow, widget.NewSeparator(), genomesContainer)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisMonogenicDiseaseGenomePairDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, genomePairIdentifier [32]byte, genomePairName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisMonogenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Couple Genome Pair Info")
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is the disease information for both genomes in the genome pair.")
|
|
|
|
|
|
|
|
diseaseNameLabel := widget.NewLabel("Disease:")
|
|
|
|
diseaseNameText := getBoldLabel(diseaseName)
|
|
|
|
diseaseNameInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
|
|
|
setViewMonogenicDiseaseDetailsPage(window, diseaseName, currentPage)
|
|
|
|
})
|
|
|
|
diseaseNameRow := container.NewHBox(layout.NewSpacer(), diseaseNameLabel, diseaseNameText, diseaseNameInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
genomePairLabel := widget.NewLabel("Genome Pair:")
|
|
|
|
genomePairNameLabel := getBoldLabel(genomePairName)
|
|
|
|
genomePairHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setCoupleGenomePairExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
genomePairRow := container.NewHBox(layout.NewSpacer(), genomePairLabel, genomePairNameLabel, genomePairHelpButton, layout.NewSpacer())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
diseaseVariantsMap, err := monogenicDiseases.GetMonogenicDiseaseVariantsMap(diseaseName)
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
totalNumberOfVariants := len(diseaseVariantsMap)
|
|
|
|
totalNumberOfVariantsString := helpers.ConvertIntToString(totalNumberOfVariants)
|
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
personNameLabel := getItalicLabelCentered("Person Name")
|
|
|
|
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
genomeNameLabel := getItalicLabelCentered("Genome Name")
|
|
|
|
|
|
|
|
probabilityOfLabel := getItalicLabelCentered("Probability Of")
|
|
|
|
passingAVariantLabel := getItalicLabelCentered("Passing A Variant")
|
|
|
|
|
|
|
|
numberOfLabel := getItalicLabelCentered("Number Of")
|
|
|
|
variantsTestedLabel := getItalicLabelCentered("Variants Tested")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
emptyLabelD := widget.NewLabel("")
|
|
|
|
|
|
|
|
personNameColumn := container.NewVBox(emptyLabelA, personNameLabel, widget.NewSeparator())
|
|
|
|
genomeNameColumn := container.NewVBox(emptyLabelB, genomeNameLabel, widget.NewSeparator())
|
|
|
|
probabilityOfPassingAVariantColumn := container.NewVBox(probabilityOfLabel, passingAVariantLabel, widget.NewSeparator())
|
|
|
|
numberOfVariantsTestedColumn := container.NewVBox(numberOfLabel, variantsTestedLabel, widget.NewSeparator())
|
|
|
|
viewGenomeButtonsColumn := container.NewVBox(emptyLabelC, emptyLabelD, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomeRow := func(isPerson1 bool, personName string, inputGenomeIdentifier [16]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
personAnalysisGenomeIdentifier, _, genomeIsCombined, combinedType, err := readGeneticAnalysis.GetMatchingPersonAnalysisGenomeIdentifierFromCoupleAnalysis(isPerson1, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, inputGenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
personNameTrimmed, _, err := helpers.TrimAndFlattenString(personName, 10)
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
personNameLabel := getBoldLabelCentered(personNameTrimmed)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
getPersonAnalysisObject := func()geneticAnalysis.PersonAnalysis{
|
|
|
|
if (isPerson1 == true){
|
|
|
|
return person1AnalysisObject
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
return person2AnalysisObject
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
personAnalysisObject := getPersonAnalysisObject()
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
getGenomeName := func()(string, error){
|
|
|
|
|
|
|
|
if (genomeIsCombined == false){
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
genomeFound, _, _, _, _, _, companyName, _, _, err := myGenomes.GetMyRawGenomeMetadata(personAnalysisGenomeIdentifier)
|
|
|
|
if (err != nil) { return "", err }
|
|
|
|
if (genomeFound == false){
|
2024-06-02 10:43:39 +02:00
|
|
|
return "", errors.New("MyGenomeInfo for genome from analysisObject not found.")
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
return companyName, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
return combinedType, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
genomeName, err := getGenomeName()
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
genomeNameLabel := getBoldLabelCentered(genomeName)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
probabilitiesKnown, _, _, probabilityOfPassingAVariantFormatted, personNumberOfVariantsTested, _, _, _, err := readGeneticAnalysis.GetPersonMonogenicDiseaseInfoFromGeneticAnalysis(personAnalysisObject, diseaseName, personAnalysisGenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getProbabilityOfPassingAVariantText := func()string{
|
|
|
|
|
|
|
|
if (probabilitiesKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return probabilityOfPassingAVariantFormatted
|
|
|
|
}
|
|
|
|
genomeProbabilityOfPassingAVariantText := getProbabilityOfPassingAVariantText()
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
genomeProbabilityOfPassingAVariantLabel := getBoldLabelCentered(genomeProbabilityOfPassingAVariantText)
|
|
|
|
|
|
|
|
personNumberOfVariantsTestedString := helpers.ConvertIntToString(personNumberOfVariantsTested)
|
2024-06-02 10:43:39 +02:00
|
|
|
genomeNumberOfVariantsTestedLabel := getBoldLabelCentered(personNumberOfVariantsTestedString + "/" + totalNumberOfVariantsString)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
viewGenomeButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewPersonGenomeMonogenicDiseaseVariantsPage(window, personAnalysisObject, personAnalysisGenomeIdentifier, genomeName, diseaseName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
personNameColumn.Add(personNameLabel)
|
|
|
|
genomeNameColumn.Add(genomeNameLabel)
|
|
|
|
probabilityOfPassingAVariantColumn.Add(genomeProbabilityOfPassingAVariantLabel)
|
|
|
|
numberOfVariantsTestedColumn.Add(genomeNumberOfVariantsTestedLabel)
|
|
|
|
viewGenomeButtonsColumn.Add(viewGenomeButton)
|
|
|
|
|
|
|
|
personNameColumn.Add(widget.NewSeparator())
|
|
|
|
genomeNameColumn.Add(widget.NewSeparator())
|
|
|
|
probabilityOfPassingAVariantColumn.Add(widget.NewSeparator())
|
|
|
|
numberOfVariantsTestedColumn.Add(widget.NewSeparator())
|
|
|
|
viewGenomeButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person1GenomeIdentifier, person2GenomeIdentifier := helpers.Split32ByteArrayInHalf(genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
err = addGenomeRow(true, person1Name, person1GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
err = addGenomeRow(false, person2Name, person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOfPassingAVariantHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setPersonProbabilityOfPassingVariantExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
numberOfVariantsTestedHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setNumberOfTestedVariantsExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
probabilityOfPassingAVariantColumn.Add(probabilityOfPassingAVariantHelpButton)
|
|
|
|
numberOfVariantsTestedColumn.Add(numberOfVariantsTestedHelpButton)
|
|
|
|
|
|
|
|
genomesGrid := container.NewHBox(layout.NewSpacer(), personNameColumn, genomeNameColumn, probabilityOfPassingAVariantColumn, numberOfVariantsTestedColumn, viewGenomeButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, diseaseNameRow, genomePairRow, widget.NewSeparator(), genomesGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// This function provides a page to view the offspring disease variant probabilities for a particular genome pair from a couple genetic analysis
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleMonogenicDiseaseVariantsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, genomePairIdentifier [32]byte, genomePairName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
setLoadingScreen(window, "Loading Disease Variants", "Loading disease variants...")
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleMonogenicDiseaseVariantsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("View Offspring Disease Variants - " + diseaseName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description1 := widget.NewLabel("Below are the disease variant probabilities for offspring from this genome pair.")
|
|
|
|
variantsHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setMonogenicDiseaseVariantsExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
description1Row := container.NewHBox(layout.NewSpacer(), description1, variantsHelpButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
genomePairLabel := widget.NewLabel("Genome Pair:")
|
|
|
|
genomePairNameLabel := getBoldLabel(genomePairName)
|
|
|
|
viewGenomePairInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisMonogenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
genomePairRow := container.NewHBox(layout.NewSpacer(), genomePairLabel, genomePairNameLabel, viewGenomePairInfoButton, layout.NewSpacer())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
//Outputs:
|
|
|
|
// -int: Number of variants tested
|
|
|
|
// -int: Number of loci tested
|
|
|
|
// -int: Number of phased loci
|
|
|
|
getVariantAndLociInfo := func()(int, int, int, error){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person1GenomeIdentifier, person2GenomeIdentifier := helpers.Split32ByteArrayInHalf(genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person1AnalysisGenomeIdentifier, _, _, _, err := readGeneticAnalysis.GetMatchingPersonAnalysisGenomeIdentifierFromCoupleAnalysis(true, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, person1GenomeIdentifier)
|
|
|
|
if (err != nil) { return 0, 0, 0, err }
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
_, _, _, _, person1NumberOfVariantsTested, person1NumberOfLociTested, person1NumberOfPhasedLoci, _, err := readGeneticAnalysis.GetPersonMonogenicDiseaseInfoFromGeneticAnalysis(person1AnalysisObject, diseaseName, person1AnalysisGenomeIdentifier)
|
|
|
|
if (err != nil) { return 0, 0, 0, err }
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person2AnalysisGenomeIdentifier, _, _, _, err := readGeneticAnalysis.GetMatchingPersonAnalysisGenomeIdentifierFromCoupleAnalysis(false, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, person2GenomeIdentifier)
|
|
|
|
if (err != nil) { return 0, 0, 0, err }
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
_, _, _, _, person2NumberOfVariantsTested, person2NumberOfLociTested, person2NumberOfPhasedLoci, _, err := readGeneticAnalysis.GetPersonMonogenicDiseaseInfoFromGeneticAnalysis(person2AnalysisObject, diseaseName, person2AnalysisGenomeIdentifier)
|
|
|
|
if (err != nil) { return 0, 0, 0, err }
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
numberOfVariantsTested := person1NumberOfVariantsTested + person2NumberOfVariantsTested
|
|
|
|
numberOfLociTested := person1NumberOfLociTested + person2NumberOfLociTested
|
|
|
|
numberOfPhasedLoci := person1NumberOfPhasedLoci + person2NumberOfPhasedLoci
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
return numberOfVariantsTested, numberOfLociTested, numberOfPhasedLoci, nil
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
numberOfVariantsTested, numberOfLociTested, numberOfPhasedLoci, err := getVariantAndLociInfo()
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
diseaseVariantsMap, err := monogenicDiseases.GetMonogenicDiseaseVariantsMap(diseaseName)
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
totalNumberOfVariants := len(diseaseVariantsMap) * 2
|
|
|
|
totalNumberOfVariantsString := helpers.ConvertIntToString(totalNumberOfVariants)
|
|
|
|
|
|
|
|
numberOfVariantsTestedString := helpers.ConvertIntToString(numberOfVariantsTested)
|
|
|
|
|
|
|
|
variantsTestedLabel := widget.NewLabel("Variants Tested:")
|
|
|
|
variantsTestedText := getBoldLabel(numberOfVariantsTestedString + "/" + totalNumberOfVariantsString)
|
|
|
|
variantsTestedHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setNumberOfTestedVariantsExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
variantsTestedRow := container.NewHBox(layout.NewSpacer(), variantsTestedLabel, variantsTestedText, variantsTestedHelpButton, layout.NewSpacer())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
numberOfLociTestedString := helpers.ConvertIntToString(numberOfLociTested)
|
|
|
|
numberOfPhasedLociString := helpers.ConvertIntToString(numberOfPhasedLoci)
|
|
|
|
|
|
|
|
phasedLociLabel := widget.NewLabel("Phased Loci:")
|
|
|
|
phasedLociText := getBoldLabel(numberOfPhasedLociString + "/" + numberOfLociTestedString)
|
|
|
|
phasedLociHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setNumberOfPhasedLociExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
phasedLociRow := container.NewHBox(layout.NewSpacer(), phasedLociLabel, phasedLociText, phasedLociHelpButton, layout.NewSpacer())
|
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
//TODO: Add navigation with pages
|
|
|
|
|
|
|
|
getVariantsGrid := func()(*fyne.Container, error){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
variantNameLabel := getItalicLabelCentered("Variant Name")
|
|
|
|
|
|
|
|
probabilityOfLabelA := getItalicLabelCentered("Probability Of")
|
|
|
|
zeroMutationsLabel := getItalicLabelCentered("0 Mutations")
|
|
|
|
|
|
|
|
probabilityOfLabelB := getItalicLabelCentered("Probability Of")
|
|
|
|
oneMutationLabel := getItalicLabelCentered("1 Mutation")
|
|
|
|
|
|
|
|
probabilityOfLabelC := getItalicLabelCentered("Probability Of")
|
|
|
|
twoMutationsLabel := getItalicLabelCentered("2 Mutations")
|
|
|
|
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
|
|
|
|
variantNameColumn := container.NewVBox(emptyLabelA, variantNameLabel, widget.NewSeparator())
|
|
|
|
probabilityOf0MutationsColumn := container.NewVBox(probabilityOfLabelA, zeroMutationsLabel, widget.NewSeparator())
|
|
|
|
probabilityOf1MutationColumn := container.NewVBox(probabilityOfLabelB, oneMutationLabel, widget.NewSeparator())
|
|
|
|
probabilityOf2MutationsColumn := container.NewVBox(probabilityOfLabelC, twoMutationsLabel, widget.NewSeparator())
|
|
|
|
variantInfoButtonsColumn := container.NewVBox(emptyLabelB, emptyLabelC, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addVariantRow := func(variantIdentifierHex string)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
variantObject, exists := diseaseVariantsMap[variantIdentifierHex]
|
2024-04-11 15:51:56 +02:00
|
|
|
if (exists == false){
|
|
|
|
return errors.New("Cannot add variant row: Variant missing from diseaseVariantsMap")
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
variantIdentifier, err := encoding.DecodeHexStringTo3ByteArray(variantIdentifierHex)
|
|
|
|
if (err != nil){
|
|
|
|
return errors.New("addVariantRow called with invalid variantIdentifier: " + variantIdentifierHex)
|
|
|
|
}
|
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
variantName := variantObject.VariantNames[0]
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringProbabilitiesKnown, probabilityOf0MutationsLowerBound, probabilityOf0MutationsUpperBound, probabilityOf0MutationsFormatted, probabilityOf1MutationLowerBound, probabilityOf1MutationUpperBound, probabilityOf1MutationFormatted, probabilityOf2MutationsLowerBound, probabilityOf2MutationsUpperBound, probabilityOf2MutationsFormatted, err := readGeneticAnalysis.GetOffspringMonogenicDiseaseVariantInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, variantIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getProbabilityOf0MutationsText := func()string{
|
|
|
|
if (offspringProbabilitiesKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
if (probabilityOf0MutationsLowerBound == 0 && probabilityOf0MutationsUpperBound == 100){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return probabilityOf0MutationsFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOf0MutationsText := getProbabilityOf0MutationsText()
|
|
|
|
|
|
|
|
getProbabilityOf1MutationText := func()string{
|
|
|
|
if (offspringProbabilitiesKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
if (probabilityOf1MutationLowerBound == 0 && probabilityOf1MutationUpperBound == 100){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return probabilityOf1MutationFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOf1MutationText := getProbabilityOf1MutationText()
|
|
|
|
|
|
|
|
getProbabilityOf2MutationsText := func()string{
|
|
|
|
if (offspringProbabilitiesKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
if (probabilityOf2MutationsLowerBound == 0 && probabilityOf2MutationsUpperBound == 100){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return probabilityOf2MutationsFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOf2MutationsText := getProbabilityOf2MutationsText()
|
|
|
|
|
|
|
|
variantNameLabel := getBoldLabelCentered(variantName)
|
|
|
|
|
|
|
|
probabilityOf0MutationsLabel := getBoldLabelCentered(probabilityOf0MutationsText)
|
|
|
|
probabilityOf1MutationLabel := getBoldLabelCentered(probabilityOf1MutationText)
|
|
|
|
probabilityOf2MutationsLabel := getBoldLabelCentered(probabilityOf2MutationsText)
|
|
|
|
|
|
|
|
viewVariantDetailsButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisMonogenicDiseaseVariantDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, variantIdentifier, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
variantNameColumn.Add(variantNameLabel)
|
|
|
|
probabilityOf0MutationsColumn.Add(probabilityOf0MutationsLabel)
|
|
|
|
probabilityOf1MutationColumn.Add(probabilityOf1MutationLabel)
|
|
|
|
probabilityOf2MutationsColumn.Add(probabilityOf2MutationsLabel)
|
|
|
|
variantInfoButtonsColumn.Add(viewVariantDetailsButton)
|
|
|
|
|
|
|
|
variantNameColumn.Add(widget.NewSeparator())
|
|
|
|
probabilityOf0MutationsColumn.Add(widget.NewSeparator())
|
|
|
|
probabilityOf1MutationColumn.Add(widget.NewSeparator())
|
|
|
|
probabilityOf2MutationsColumn.Add(widget.NewSeparator())
|
|
|
|
variantInfoButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
variantsWithNonZeroRiskList := make([]string, 0)
|
|
|
|
variantsWithZeroRiskFullyKnownList := make([]string, 0)
|
|
|
|
variantsWithZeroRiskPartiallyKnownList := make([]string, 0)
|
|
|
|
variantsWithUnknownRiskList := make([]string, 0)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
for variantIdentifierHex, _ := range diseaseVariantsMap{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
variantIdentifier, err := encoding.DecodeHexStringTo3ByteArray(variantIdentifierHex)
|
|
|
|
if (err != nil){
|
|
|
|
return nil, errors.New("diseaseVariantsMap contains invalid variantIdentifier: " + variantIdentifierHex)
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilitesKnown, probabilityOf0MutationsLowerBound, probabilityOf0MutationsUpperBound, _, probabilityOf1MutationLowerBound, probabilityOf1MutationUpperBound, _, probabilityOf2MutationsLowerBound, probabilityOf2MutationsUpperBound, _, err := readGeneticAnalysis.GetOffspringMonogenicDiseaseVariantInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, variantIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
if (probabilitesKnown == false){
|
2024-06-02 10:43:39 +02:00
|
|
|
variantsWithUnknownRiskList = append(variantsWithUnknownRiskList, variantIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
continue
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
if (probabilityOf1MutationLowerBound != 0 || probabilityOf2MutationsLowerBound != 0){
|
2024-06-02 10:43:39 +02:00
|
|
|
variantsWithNonZeroRiskList = append(variantsWithNonZeroRiskList, variantIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
// Risk is either 0 or partially unknown
|
|
|
|
if (probabilityOf0MutationsLowerBound == 100 && probabilityOf0MutationsUpperBound == 100 && probabilityOf1MutationLowerBound == 0 && probabilityOf1MutationUpperBound == 0 && probabilityOf2MutationsLowerBound == 0 && probabilityOf2MutationsUpperBound == 0){
|
2024-06-02 10:43:39 +02:00
|
|
|
variantsWithZeroRiskFullyKnownList = append(variantsWithZeroRiskFullyKnownList, variantIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
continue
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
|
|
|
|
variantsWithZeroRiskPartiallyKnownList = append(variantsWithZeroRiskPartiallyKnownList, variantIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
// We sort each list so the variants show up in the same order each time
|
|
|
|
|
|
|
|
helpers.SortStringListToUnicodeOrder(variantsWithNonZeroRiskList)
|
|
|
|
helpers.SortStringListToUnicodeOrder(variantsWithZeroRiskFullyKnownList)
|
|
|
|
helpers.SortStringListToUnicodeOrder(variantsWithZeroRiskPartiallyKnownList)
|
|
|
|
helpers.SortStringListToUnicodeOrder(variantsWithUnknownRiskList)
|
|
|
|
|
|
|
|
for _, variantIdentifier := range variantsWithNonZeroRiskList{
|
|
|
|
|
|
|
|
err = addVariantRow(variantIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
for _, variantIdentifier := range variantsWithZeroRiskFullyKnownList{
|
|
|
|
|
|
|
|
err = addVariantRow(variantIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
for _, variantIdentifier := range variantsWithZeroRiskPartiallyKnownList{
|
|
|
|
|
|
|
|
err = addVariantRow(variantIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
for _, variantIdentifier := range variantsWithUnknownRiskList{
|
|
|
|
|
|
|
|
err = addVariantRow(variantIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
|
|
|
|
variantsGrid := container.NewHBox(layout.NewSpacer(), variantNameColumn, probabilityOf0MutationsColumn, probabilityOf1MutationColumn, probabilityOf2MutationsColumn, variantInfoButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
return variantsGrid, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
variantsGrid, err := getVariantsGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description1Row, widget.NewSeparator(), genomePairRow, widget.NewSeparator(), variantsTestedRow, widget.NewSeparator(), phasedLociRow, widget.NewSeparator(), variantsGrid)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// This function provides a page to view the details of a specific variant from a genetic analysis
|
|
|
|
// It will show the variant details for all of the couple's genome pairs
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisMonogenicDiseaseVariantDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, variantIdentifier [3]byte, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisMonogenicDiseaseVariantDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, variantIdentifier, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Disease Variant Details - " + diseaseName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
variantIdentifierHex := encoding.EncodeBytesToHexString(variantIdentifier[:])
|
|
|
|
|
|
|
|
variantObject, err := monogenicDiseases.GetMonogenicDiseaseVariantObject(diseaseName, variantIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
variantName := variantObject.VariantNames[0]
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is the disease variant analysis for the couple.")
|
|
|
|
|
|
|
|
variantNameLabel := widget.NewLabel("Variant Name:")
|
|
|
|
variantNameText := getBoldLabel(variantName)
|
|
|
|
variantInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewMonogenicDiseaseVariantDetailsPage(window, diseaseName, variantIdentifierHex, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
variantNameRow := container.NewHBox(layout.NewSpacer(), variantNameLabel, variantNameText, variantInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
getGenomePairsHaveVariantGrid := func()(*fyne.Container, error){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
genomePairLabel := getItalicLabelCentered("Genome Pair")
|
|
|
|
|
|
|
|
probabilityOfLabelA := getItalicLabelCentered("Probability Of")
|
|
|
|
zeroMutationsLabel := getItalicLabelCentered("0 Mutations")
|
|
|
|
|
|
|
|
probabilityOfLabelB := getItalicLabelCentered("Probability Of")
|
|
|
|
oneMutationLabel := getItalicLabelCentered("1 Mutation")
|
|
|
|
|
|
|
|
probabilityOfLabelC := getItalicLabelCentered("Probability Of")
|
|
|
|
twoMutationsLabel := getItalicLabelCentered("2 Mutations")
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn := container.NewVBox(emptyLabelA, emptyLabelB, widget.NewSeparator())
|
|
|
|
genomePairNameColumn := container.NewVBox(emptyLabelC, genomePairLabel, widget.NewSeparator())
|
|
|
|
probabilityOf0MutationsColumn := container.NewVBox(probabilityOfLabelA, zeroMutationsLabel, widget.NewSeparator())
|
|
|
|
probabilityOf1MutationColumn := container.NewVBox(probabilityOfLabelB, oneMutationLabel, widget.NewSeparator())
|
|
|
|
probablityOf2MutationsColumn := container.NewVBox(probabilityOfLabelC, twoMutationsLabel, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomePairRow := func(genomePairName string, genomePairIdentifier [32]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
probabilitiesKnown, probabilityOf0MutationsLowerBound, probabilityOf0MutationsUpperBound, probabilityOf0MutationsFormatted, probabilityOf1MutationLowerBound, probabilityOf1MutationUpperBound, probabilityOf1MutationFormatted, probabilityOf2MutationsLowerBound, probabilityOf2MutationsUpperBound, probabilityOf2MutationsFormatted, err := readGeneticAnalysis.GetOffspringMonogenicDiseaseVariantInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, variantIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getProbabilityOf0MutationsText := func()string{
|
|
|
|
if (probabilitiesKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
if (probabilityOf0MutationsLowerBound == 0 && probabilityOf0MutationsUpperBound == 100){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return probabilityOf0MutationsFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOf0MutationsText := getProbabilityOf0MutationsText()
|
|
|
|
|
|
|
|
getProbabilityOf1MutationText := func()string{
|
|
|
|
if (probabilitiesKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
if (probabilityOf1MutationLowerBound == 0 && probabilityOf1MutationUpperBound == 100){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return probabilityOf1MutationFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOf1MutationText := getProbabilityOf1MutationText()
|
|
|
|
|
|
|
|
getProbabilityOf2MutationsText := func()string{
|
|
|
|
if (probabilitiesKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
if (probabilityOf2MutationsLowerBound == 0 && probabilityOf2MutationsUpperBound == 100){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return probabilityOf2MutationsFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOf2MutationsText := getProbabilityOf2MutationsText()
|
|
|
|
|
|
|
|
viewGenomePairInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisMonogenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
genomePairNameLabel := getBoldLabelCentered(genomePairName)
|
|
|
|
|
|
|
|
probabilityOf0MutationsLabel := getBoldLabelCentered(probabilityOf0MutationsText)
|
|
|
|
probabilityOf1MutationLabel := getBoldLabelCentered(probabilityOf1MutationText)
|
|
|
|
probabilityOf2MutationsLabel := getBoldLabelCentered(probabilityOf2MutationsText)
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn.Add(viewGenomePairInfoButton)
|
|
|
|
genomePairNameColumn.Add(genomePairNameLabel)
|
|
|
|
probabilityOf0MutationsColumn.Add(probabilityOf0MutationsLabel)
|
|
|
|
probabilityOf1MutationColumn.Add(probabilityOf1MutationLabel)
|
|
|
|
probablityOf2MutationsColumn.Add(probabilityOf2MutationsLabel)
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
genomePairNameColumn.Add(widget.NewSeparator())
|
|
|
|
probabilityOf0MutationsColumn.Add(widget.NewSeparator())
|
|
|
|
probabilityOf1MutationColumn.Add(widget.NewSeparator())
|
|
|
|
probablityOf2MutationsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){ return nil, err }
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePair1Identifier := helpers.JoinTwo16ByteArrays(pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
err = addGenomePairRow("Pair 1", genomePair1Identifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePair2Identifier := helpers.JoinTwo16ByteArrays(pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
err := addGenomePairRow("Pair 2", genomePair2Identifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
|
|
|
|
genomesContainer := container.NewHBox(layout.NewSpacer(), viewGenomePairInfoButtonsColumn, genomePairNameColumn, probabilityOf0MutationsColumn, probabilityOf1MutationColumn, probablityOf2MutationsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
return genomesContainer, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
genomePairsHaveVariantGrid, err := getGenomePairsHaveVariantGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), variantNameRow, widget.NewSeparator(), genomePairsHaveVariantGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisPolygenicDiseasesPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisPolygenicDiseasesPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Genetic Analysis - Polygenic Diseases")
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is an analysis of the polygenic disease risk probabilities for the couple's offspring.")
|
|
|
|
|
|
|
|
getDiseasesGrid := func()(*fyne.Container, error){
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, _, _, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){ return nil, err }
|
|
|
|
|
|
|
|
diseaseNameLabel := getItalicLabelCentered("Disease Name")
|
|
|
|
|
|
|
|
offspringRiskScoreLabel := getItalicLabelCentered("Offspring Risk Score")
|
|
|
|
|
|
|
|
conflictExistsLabel := getItalicLabelCentered("Conflict Exists?")
|
|
|
|
|
|
|
|
emptyLabel := widget.NewLabel("")
|
|
|
|
|
|
|
|
diseaseNameColumn := container.NewVBox(diseaseNameLabel, widget.NewSeparator())
|
|
|
|
offspringRiskScoreColumn := container.NewVBox(offspringRiskScoreLabel, widget.NewSeparator())
|
|
|
|
conflictExistsColumn := container.NewVBox(conflictExistsLabel, widget.NewSeparator())
|
|
|
|
viewButtonsColumn := container.NewVBox(emptyLabel, widget.NewSeparator())
|
|
|
|
|
|
|
|
diseaseNamesList, err := polygenicDiseases.GetPolygenicDiseaseNamesList()
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
for _, diseaseName := range diseaseNamesList{
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
mainGenomePairIdentifier := helpers.JoinTwo16ByteArrays(pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringRiskScoreKnown, _, offspringRiskScoreFormatted, _, conflictExists, err := readGeneticAnalysis.GetOffspringPolygenicDiseaseInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, mainGenomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
getRiskScoreLabelText := func()string{
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
if (offspringRiskScoreKnown == false){
|
2024-04-11 15:51:56 +02:00
|
|
|
result := translate("Unknown")
|
|
|
|
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return offspringRiskScoreFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskScoreLabelText := getRiskScoreLabelText()
|
|
|
|
|
|
|
|
diseaseNameText := getBoldLabelCentered(diseaseName)
|
|
|
|
diseaseNameColumn.Add(diseaseNameText)
|
|
|
|
|
|
|
|
offspringRiskScoreText := getBoldLabelCentered(offspringRiskScoreLabelText)
|
|
|
|
offspringRiskScoreColumn.Add(offspringRiskScoreText)
|
|
|
|
|
|
|
|
conflictExistsString := helpers.ConvertBoolToYesOrNoString(conflictExists)
|
|
|
|
conflictExistsLabel := getBoldLabelCentered(conflictExistsString)
|
|
|
|
conflictExistsColumn.Add(conflictExistsLabel)
|
|
|
|
|
|
|
|
viewDetailsButton := getWidgetCentered(widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisPolygenicDiseaseDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
}))
|
|
|
|
viewButtonsColumn.Add(viewDetailsButton)
|
|
|
|
|
|
|
|
diseaseNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringRiskScoreColumn.Add(widget.NewSeparator())
|
|
|
|
conflictExistsColumn.Add(widget.NewSeparator())
|
|
|
|
viewButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskScoreHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringPolygenicDiseaseRiskScoreExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
offspringRiskScoreColumn.Add(offspringRiskScoreHelpButton)
|
|
|
|
|
|
|
|
diseasesGrid := container.NewHBox(layout.NewSpacer(), diseaseNameColumn, offspringRiskScoreColumn)
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
|
|
|
|
|
|
|
conflictExistsHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setCoupleGeneticAnalysisConflictExistsExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
conflictExistsColumn.Add(conflictExistsHelpButton)
|
|
|
|
|
|
|
|
diseasesGrid.Add(conflictExistsColumn)
|
|
|
|
}
|
|
|
|
|
|
|
|
diseasesGrid.Add(viewButtonsColumn)
|
|
|
|
diseasesGrid.Add(layout.NewSpacer())
|
|
|
|
|
|
|
|
return diseasesGrid, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
diseasesGrid, err := getDiseasesGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), diseasesGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisPolygenicDiseaseDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisPolygenicDiseaseDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Couple Analysis - " + diseaseName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
getDescriptionSection := func()*fyne.Container{
|
|
|
|
|
|
|
|
if (secondGenomePairExists == false){
|
|
|
|
description := getLabelCentered("Below is the disease analysis for the couple's offspring.")
|
|
|
|
|
|
|
|
return description
|
|
|
|
}
|
|
|
|
|
|
|
|
description1 := getLabelCentered("Below is the disease analysis for the couple's offspring.")
|
|
|
|
description2 := getLabelCentered("Each genome pair combines different genomes from each person.")
|
|
|
|
|
|
|
|
descriptionsSection := container.NewVBox(description1, description2)
|
|
|
|
|
|
|
|
return descriptionsSection
|
|
|
|
}
|
|
|
|
|
|
|
|
descriptionSection := getDescriptionSection()
|
|
|
|
|
|
|
|
diseaseNameLabel := widget.NewLabel("Disease:")
|
|
|
|
diseaseNameText := getBoldLabel(diseaseName)
|
|
|
|
diseaseNameInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
|
|
|
setViewPolygenicDiseaseDetailsPage(window, diseaseName, currentPage)
|
|
|
|
})
|
|
|
|
diseaseNameRow := container.NewHBox(layout.NewSpacer(), diseaseNameLabel, diseaseNameText, diseaseNameInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
|
|
|
|
offspringRiskScoreLabel := getItalicLabelCentered("Offspring Risk Score")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
emptyLabelD := widget.NewLabel("")
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn := container.NewVBox(emptyLabelA, widget.NewSeparator())
|
|
|
|
pairNameColumn := container.NewVBox(emptyLabelB, widget.NewSeparator())
|
|
|
|
offspringRiskScoreColumn := container.NewVBox(offspringRiskScoreLabel, widget.NewSeparator())
|
|
|
|
viewLifetimeRiskButtonsColumn := container.NewVBox(emptyLabelC, widget.NewSeparator())
|
|
|
|
viewOffspringLociButtonsColumn := container.NewVBox(emptyLabelD, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomePairRow := func(genomePairName string, person1GenomeIdentifier [16]byte, person2GenomeIdentifier [16]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePairIdentifier := helpers.JoinTwo16ByteArrays(person1GenomeIdentifier, person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringRiskScoreKnown, _, offspringRiskScoreFormatted, _, _, err := readGeneticAnalysis.GetOffspringPolygenicDiseaseInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getRiskScoreLabelText := func()string{
|
|
|
|
|
|
|
|
if (offspringRiskScoreKnown == false){
|
|
|
|
result := translate("Unknown")
|
|
|
|
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return offspringRiskScoreFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
riskScoreLabelText := getRiskScoreLabelText()
|
|
|
|
|
|
|
|
genomePairNameLabel := getBoldLabelCentered(genomePairName)
|
|
|
|
|
|
|
|
offspringRiskScoreLabel := getBoldLabelCentered(riskScoreLabelText)
|
|
|
|
|
|
|
|
viewGenomePairButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisPolygenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
viewOffspringLifetimeRiskButton := widget.NewButtonWithIcon("", theme.HistoryIcon(), func(){
|
|
|
|
|
|
|
|
diseaseObject, err := polygenicDiseases.GetPolygenicDiseaseObject(diseaseName)
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, currentPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
getPageMaleOrFemale := func()string{
|
|
|
|
|
|
|
|
//TODO: Get user sex from myLocalProfiles
|
|
|
|
|
|
|
|
diseaseEffectedSex := diseaseObject.EffectedSex
|
|
|
|
if (diseaseEffectedSex == "Both"){
|
|
|
|
return "Male"
|
|
|
|
}
|
|
|
|
|
|
|
|
return diseaseEffectedSex
|
|
|
|
}
|
|
|
|
|
|
|
|
pageMaleOrFemale := getPageMaleOrFemale()
|
|
|
|
|
|
|
|
setViewPersonPolygenicDiseaseLifetimeProbabilitiesPage(window, diseaseName, genomePairName, pageMaleOrFemale, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
viewOffspringLociButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCouplePolygenicDiseaseLociPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn.Add(viewGenomePairButton)
|
|
|
|
pairNameColumn.Add(genomePairNameLabel)
|
|
|
|
offspringRiskScoreColumn.Add(offspringRiskScoreLabel)
|
|
|
|
viewLifetimeRiskButtonsColumn.Add(viewOffspringLifetimeRiskButton)
|
|
|
|
viewOffspringLociButtonsColumn.Add(viewOffspringLociButton)
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
pairNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringRiskScoreColumn.Add(widget.NewSeparator())
|
|
|
|
viewOffspringLociButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
err = addGenomePairRow("Pair 1", pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
2024-06-02 10:43:39 +02:00
|
|
|
err := addGenomePairRow("Pair 2", pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskScoreHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringPolygenicDiseaseRiskScoreExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
offspringRiskScoreColumn.Add(offspringRiskScoreHelpButton)
|
|
|
|
|
|
|
|
genomesContainer := container.NewHBox(layout.NewSpacer(), viewGenomePairButtonsColumn, pairNameColumn, offspringRiskScoreColumn, viewOffspringLociButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), descriptionSection, widget.NewSeparator(), diseaseNameRow, widget.NewSeparator(), genomesContainer)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisPolygenicDiseaseGenomePairDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, genomePairIdentifier [32]byte, genomePairName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisPolygenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Couple Genome Pair Info")
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is the disease information for both genomes in the genome pair.")
|
|
|
|
|
|
|
|
diseaseNameLabel := widget.NewLabel("Disease:")
|
|
|
|
diseaseNameText := getBoldLabel(diseaseName)
|
|
|
|
diseaseNameInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
|
|
|
setViewPolygenicDiseaseDetailsPage(window, diseaseName, currentPage)
|
|
|
|
})
|
|
|
|
diseaseNameRow := container.NewHBox(layout.NewSpacer(), diseaseNameLabel, diseaseNameText, diseaseNameInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
genomePairLabel := widget.NewLabel("Genome Pair:")
|
|
|
|
genomePairNameLabel := getBoldLabel(genomePairName)
|
|
|
|
genomePairHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setCoupleGenomePairExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
genomePairRow := container.NewHBox(layout.NewSpacer(), genomePairLabel, genomePairNameLabel, genomePairHelpButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
personNameLabel := getItalicLabelCentered("Person Name")
|
|
|
|
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
genomeNameLabel := getItalicLabelCentered("Genome Name")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
riskScoreLabel := getItalicLabelCentered("Risk Score")
|
|
|
|
|
|
|
|
numberOfLabel := getItalicLabelCentered("Number Of")
|
|
|
|
lociTestedLabel := getItalicLabelCentered("Loci Tested")
|
|
|
|
|
|
|
|
emptyLabelD := widget.NewLabel("")
|
|
|
|
emptyLabelE := widget.NewLabel("")
|
|
|
|
|
|
|
|
personNameColumn := container.NewVBox(emptyLabelA, personNameLabel, widget.NewSeparator())
|
|
|
|
genomeNameColumn := container.NewVBox(emptyLabelB, genomeNameLabel, widget.NewSeparator())
|
|
|
|
riskScoreColumn := container.NewVBox(emptyLabelC, riskScoreLabel, widget.NewSeparator())
|
|
|
|
numberOfLociTestedColumn := container.NewVBox(numberOfLabel, lociTestedLabel, widget.NewSeparator())
|
|
|
|
viewGenomeButtonsColumn := container.NewVBox(emptyLabelD, emptyLabelE, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomeRow := func(isPerson1 bool, personName string, inputGenomeIdentifier [16]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
personAnalysisGenomeIdentifier, _, genomeIsCombined, combinedType, err := readGeneticAnalysis.GetMatchingPersonAnalysisGenomeIdentifierFromCoupleAnalysis(isPerson1, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, inputGenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
personNameTrimmed, _, err := helpers.TrimAndFlattenString(personName, 10)
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
personNameLabel := getBoldLabelCentered(personNameTrimmed)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
getPersonAnalysisObject := func()geneticAnalysis.PersonAnalysis{
|
|
|
|
if (isPerson1 == true){
|
|
|
|
return person1AnalysisObject
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
return person2AnalysisObject
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
personAnalysisObject := getPersonAnalysisObject()
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
getGenomeName := func()(string, error){
|
|
|
|
|
|
|
|
if (genomeIsCombined == false){
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
genomeFound, _, _, _, _, _, companyName, _, _, err := myGenomes.GetMyRawGenomeMetadata(personAnalysisGenomeIdentifier)
|
|
|
|
if (err != nil) { return "", err }
|
|
|
|
if (genomeFound == false){
|
2024-06-02 10:43:39 +02:00
|
|
|
return "", errors.New("MyGenomeInfo for genome from analysisObject not found.")
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
return companyName, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
return combinedType, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
genomeName, err := getGenomeName()
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
genomeNameLabel := getBoldLabelCentered(genomeName)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
personRiskScoreKnown, _, personRiskScoreFormatted, numberOfLociTested, _, err := readGeneticAnalysis.GetPersonPolygenicDiseaseInfoFromGeneticAnalysis(personAnalysisObject, diseaseName, personAnalysisGenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getPersonRiskScoreLabelText := func()string{
|
|
|
|
if (personRiskScoreKnown == false){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
return personRiskScoreFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
personRiskScoreLabelText := getPersonRiskScoreLabelText()
|
|
|
|
|
|
|
|
genomeRiskScoreLabel := getBoldLabelCentered(personRiskScoreLabelText)
|
|
|
|
|
|
|
|
numberOfLociTestedString := helpers.ConvertIntToString(numberOfLociTested)
|
|
|
|
numberOfLociTestedText := getBoldLabelCentered(numberOfLociTestedString)
|
|
|
|
|
|
|
|
viewGenomeButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewPersonGenomePolygenicDiseaseLociPage(window, personAnalysisObject, diseaseName, personAnalysisGenomeIdentifier, genomeName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
personNameColumn.Add(personNameLabel)
|
|
|
|
genomeNameColumn.Add(genomeNameLabel)
|
|
|
|
riskScoreColumn.Add(genomeRiskScoreLabel)
|
|
|
|
numberOfLociTestedColumn.Add(numberOfLociTestedText)
|
|
|
|
viewGenomeButtonsColumn.Add(viewGenomeButton)
|
|
|
|
|
|
|
|
personNameColumn.Add(widget.NewSeparator())
|
|
|
|
genomeNameColumn.Add(widget.NewSeparator())
|
|
|
|
riskScoreColumn.Add(widget.NewSeparator())
|
|
|
|
numberOfLociTestedColumn.Add(widget.NewSeparator())
|
|
|
|
viewGenomeButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person1GenomeIdentifier, person2GenomeIdentifier := helpers.Split32ByteArrayInHalf(genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
err := addGenomeRow(true, person1Name, person1GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
err = addGenomeRow(false, person2Name, person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
riskScoreHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setPolygenicDiseaseRiskScoreExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
riskScoreColumn.Add(riskScoreHelpButton)
|
|
|
|
|
|
|
|
numberOfLociTestedHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setPolygenicDiseaseNumberOfLociTestedExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
numberOfLociTestedColumn.Add(numberOfLociTestedHelpButton)
|
|
|
|
|
|
|
|
genomesGrid := container.NewHBox(layout.NewSpacer(), personNameColumn, genomeNameColumn, riskScoreColumn, numberOfLociTestedColumn, viewGenomeButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), diseaseNameRow, widget.NewSeparator(), genomePairRow, widget.NewSeparator(), genomesGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// This function provides a page to view the couple offspring locus probabilities for a particular genome pair
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCouplePolygenicDiseaseLociPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, genomePairIdentifier [32]byte, genomePairName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
setLoadingScreen(window, "Loading Polygenic Disease Loci", "Loading disease loci...")
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCouplePolygenicDiseaseLociPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("View Offspring Disease Loci - " + diseaseName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description1 := widget.NewLabel("Below are the disease loci probabilities for offspring from this genome pair.")
|
|
|
|
diseaseLociHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setPolygenicDiseaseLociExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
description1Row := container.NewHBox(layout.NewSpacer(), description1, diseaseLociHelpButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
genomePairLabel := widget.NewLabel("Genome Pair:")
|
|
|
|
genomePairNameLabel := getBoldLabel(genomePairName)
|
|
|
|
viewGenomePairInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisPolygenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
genomePairRow := container.NewHBox(layout.NewSpacer(), genomePairLabel, genomePairNameLabel, viewGenomePairInfoButton, layout.NewSpacer())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
_, _, _, numberOfLociTested, _, err := readGeneticAnalysis.GetOffspringPolygenicDiseaseInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
numberOfLociTestedString := helpers.ConvertIntToString(numberOfLociTested)
|
|
|
|
|
|
|
|
diseaseLociMap, err := polygenicDiseases.GetPolygenicDiseaseLociMap(diseaseName)
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
totalNumberOfLoci := len(diseaseLociMap)
|
|
|
|
totalNumberOfLociString := helpers.ConvertIntToString(totalNumberOfLoci)
|
|
|
|
|
|
|
|
lociTestedLabel := widget.NewLabel("Loci Tested:")
|
|
|
|
lociTestedText := getBoldLabel(numberOfLociTestedString + "/" + totalNumberOfLociString)
|
|
|
|
lociTestedHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringPolygenicDiseaseNumberOfLociTestedExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
lociTestedRow := container.NewHBox(layout.NewSpacer(), lociTestedLabel, lociTestedText, lociTestedHelpButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
getLociGrid := func()(*fyne.Container, error){
|
|
|
|
|
|
|
|
locusNameLabel := getItalicLabelCentered("Locus Name")
|
|
|
|
|
|
|
|
offspringRiskWeightLabel := getItalicLabelCentered("Offspring Risk Weight")
|
|
|
|
|
|
|
|
offspringOddsRatioLabel := getItalicLabelCentered("Offspring Odds Ratio")
|
|
|
|
|
|
|
|
emptyLabel := widget.NewLabel("")
|
|
|
|
|
|
|
|
locusNameColumn := container.NewVBox(locusNameLabel, widget.NewSeparator())
|
|
|
|
offspringRiskWeightColumn := container.NewVBox(offspringRiskWeightLabel, widget.NewSeparator())
|
|
|
|
offspringOddsRatioColumn := container.NewVBox(offspringOddsRatioLabel, widget.NewSeparator())
|
|
|
|
lociInfoButtonsColumn := container.NewVBox(emptyLabel, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addLocusRow := func(locusIdentifierHex string)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
locusObject, exists := diseaseLociMap[locusIdentifierHex]
|
2024-04-11 15:51:56 +02:00
|
|
|
if (exists == false) {
|
2024-06-02 10:43:39 +02:00
|
|
|
return errors.New("Cannot add locus row: Locus not found in diseaseLociMap: " + locusIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
locusIdentifier, err := encoding.DecodeHexStringTo3ByteArray(locusIdentifierHex)
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
locusRSID := locusObject.LocusRSID
|
|
|
|
locusRSIDString := helpers.ConvertInt64ToString(locusRSID)
|
|
|
|
locusName := "rs" + locusRSIDString
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringRiskWeightKnown, offspringRiskWeight, offspringOddsRatioKnown, _, offspringOddsRatioFormatted, err := readGeneticAnalysis.GetOffspringPolygenicDiseaseLocusInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, locusIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getOffspringRiskWeightText := func()string{
|
|
|
|
|
|
|
|
if (offspringRiskWeightKnown == false){
|
|
|
|
|
|
|
|
unknownTextTranslated := translate("Unknown")
|
|
|
|
return unknownTextTranslated
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskWeightString := helpers.ConvertIntToString(offspringRiskWeight)
|
|
|
|
|
|
|
|
return offspringRiskWeightString
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskWeightText := getOffspringRiskWeightText()
|
|
|
|
|
|
|
|
getOffspringOddsRatioText := func()string{
|
|
|
|
|
|
|
|
if (offspringOddsRatioKnown == false){
|
|
|
|
|
|
|
|
unknownTextTranslated := translate("Unknown")
|
|
|
|
return unknownTextTranslated
|
|
|
|
}
|
|
|
|
|
|
|
|
return offspringOddsRatioFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringOddsRatioText := getOffspringOddsRatioText()
|
|
|
|
|
|
|
|
locusNameLabel := getBoldLabelCentered(locusName)
|
|
|
|
|
|
|
|
locusRiskWeightLabel := getBoldLabelCentered(offspringRiskWeightText)
|
|
|
|
locusOddsRatioLabel := getBoldLabelCentered(offspringOddsRatioText)
|
|
|
|
|
|
|
|
viewLocusDetailsButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisPolygenicDiseaseLocusDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, locusIdentifier, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
locusNameColumn.Add(locusNameLabel)
|
|
|
|
offspringRiskWeightColumn.Add(locusRiskWeightLabel)
|
|
|
|
offspringOddsRatioColumn.Add(locusOddsRatioLabel)
|
|
|
|
lociInfoButtonsColumn.Add(viewLocusDetailsButton)
|
|
|
|
|
|
|
|
locusNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringRiskWeightColumn.Add(widget.NewSeparator())
|
|
|
|
offspringOddsRatioColumn.Add(widget.NewSeparator())
|
|
|
|
lociInfoButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
lociWithKnownRiskWeightList := make([]string, 0)
|
|
|
|
lociWithUnknownRiskWeightList := make([]string, 0)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
for locusIdentifierHex, _ := range diseaseLociMap{
|
|
|
|
|
|
|
|
locusIdentifier, err := encoding.DecodeHexStringTo3ByteArray(locusIdentifierHex)
|
|
|
|
if (err != nil) { return nil, err }
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringRiskWeightKnown, _, _, _, _, err := readGeneticAnalysis.GetOffspringPolygenicDiseaseLocusInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, locusIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
if (offspringRiskWeightKnown == true){
|
2024-06-02 10:43:39 +02:00
|
|
|
lociWithKnownRiskWeightList = append(lociWithKnownRiskWeightList, locusIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
} else {
|
2024-06-02 10:43:39 +02:00
|
|
|
lociWithUnknownRiskWeightList = append(lociWithUnknownRiskWeightList, locusIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// We sort the lists so loci show up in the same order whenever page is refreshed
|
|
|
|
|
|
|
|
helpers.SortStringListToUnicodeOrder(lociWithKnownRiskWeightList)
|
|
|
|
helpers.SortStringListToUnicodeOrder(lociWithUnknownRiskWeightList)
|
|
|
|
|
|
|
|
for _, locusIdentifier := range lociWithKnownRiskWeightList{
|
|
|
|
|
|
|
|
err = addLocusRow(locusIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, locusIdentifier := range lociWithUnknownRiskWeightList{
|
|
|
|
|
|
|
|
err = addLocusRow(locusIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskWeightHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringPolygenicDiseaseLocusRiskWeightExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
offspringRiskWeightColumn.Add(offspringRiskWeightHelpButton)
|
|
|
|
|
|
|
|
offspringOddsRatioHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
//TODO
|
|
|
|
showUnderConstructionDialog(window)
|
|
|
|
})
|
|
|
|
offspringOddsRatioColumn.Add(offspringOddsRatioHelpButton)
|
|
|
|
|
|
|
|
lociGrid := container.NewHBox(layout.NewSpacer(), locusNameColumn, offspringRiskWeightColumn, offspringOddsRatioColumn, lociInfoButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
return lociGrid, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
lociGrid, err := getLociGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description1Row, widget.NewSeparator(), genomePairRow, widget.NewSeparator(), lociTestedRow, widget.NewSeparator(), lociGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// This function provides a page to view the details of a specific locus from a genetic analysis
|
|
|
|
// It will show the locus details for all of the couple's genome pairs
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisPolygenicDiseaseLocusDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, diseaseName string, locusIdentifier [3]byte, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisPolygenicDiseaseLocusDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, locusIdentifier, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Disease Locus Details - " + diseaseName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
locusIdentifierHex := encoding.EncodeBytesToHexString(locusIdentifier[:])
|
|
|
|
|
|
|
|
locusObject, err := polygenicDiseases.GetPolygenicDiseaseLocusObject(diseaseName, locusIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
locusRSID := locusObject.LocusRSID
|
|
|
|
locusRSIDString := helpers.ConvertInt64ToString(locusRSID)
|
|
|
|
locusName := "rs" + locusRSIDString
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is the locus analysis for the couple.")
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
locusNameLabel := widget.NewLabel("Locus Name:")
|
|
|
|
locusNameText := getBoldLabel(locusName)
|
|
|
|
locusInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewPolygenicDiseaseLocusDetailsPage(window, diseaseName, locusIdentifierHex, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
locusNameRow := container.NewHBox(layout.NewSpacer(), locusNameLabel, locusNameText, locusInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
getGenomePairsLocusInfoGrid := func()(*fyne.Container, error){
|
|
|
|
|
|
|
|
emptyLabel := widget.NewLabel("")
|
|
|
|
|
|
|
|
genomePairLabel := getItalicLabelCentered("Genome Pair")
|
|
|
|
|
|
|
|
offspringRiskWeightLabel := getItalicLabelCentered("Offspring Risk Weight")
|
|
|
|
|
|
|
|
offspringOddsRatioLabel := getItalicLabelCentered("Offspring Odds Ratio")
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn := container.NewVBox(emptyLabel, widget.NewSeparator())
|
|
|
|
genomePairNameColumn := container.NewVBox(genomePairLabel, widget.NewSeparator())
|
|
|
|
offspringRiskWeightColumn := container.NewVBox(offspringRiskWeightLabel, widget.NewSeparator())
|
|
|
|
offspringOddsRatioColumn := container.NewVBox(offspringOddsRatioLabel, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomePairRow := func(genomePairName string, genomePairIdentifier [32]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringRiskWeightKnown, offspringRiskWeight, offspringOddsRatioKnown, _, offspringOddsRatioFormatted, err := readGeneticAnalysis.GetOffspringPolygenicDiseaseLocusInfoFromGeneticAnalysis(coupleAnalysisObject, diseaseName, locusIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getOffspringRiskWeightText := func()string{
|
|
|
|
|
|
|
|
if (offspringRiskWeightKnown == false){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskWeightString := helpers.ConvertIntToString(offspringRiskWeight)
|
|
|
|
|
|
|
|
return offspringRiskWeightString
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskWeightText := getOffspringRiskWeightText()
|
|
|
|
|
|
|
|
getOffspringOddsRatioText := func()string{
|
|
|
|
if (offspringOddsRatioKnown == false){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
return offspringOddsRatioFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringOddsRatioText := getOffspringOddsRatioText()
|
|
|
|
|
|
|
|
viewGenomePairInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisPolygenicDiseaseGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, diseaseName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
genomePairNameLabel := getBoldLabelCentered(genomePairName)
|
|
|
|
|
|
|
|
offspringRiskWeightLabel := getBoldLabelCentered(offspringRiskWeightText)
|
|
|
|
offspringOddsRatioLabel := getBoldLabelCentered(offspringOddsRatioText)
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn.Add(viewGenomePairInfoButton)
|
|
|
|
genomePairNameColumn.Add(genomePairNameLabel)
|
|
|
|
offspringRiskWeightColumn.Add(offspringRiskWeightLabel)
|
|
|
|
offspringOddsRatioColumn.Add(offspringOddsRatioLabel)
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
genomePairNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringRiskWeightColumn.Add(widget.NewSeparator())
|
|
|
|
offspringOddsRatioColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){ return nil, err }
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePair1Identifier := helpers.JoinTwo16ByteArrays(pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
err = addGenomePairRow("Pair 1", genomePair1Identifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePair2Identifier := helpers.JoinTwo16ByteArrays(pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
err := addGenomePairRow("Pair 2", genomePair2Identifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringRiskWeightHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringPolygenicDiseaseLocusRiskWeightExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
offspringOddsRatioHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
//TODO
|
|
|
|
showUnderConstructionDialog(window)
|
|
|
|
})
|
|
|
|
|
|
|
|
offspringRiskWeightColumn.Add(offspringRiskWeightHelpButton)
|
|
|
|
offspringOddsRatioColumn.Add(offspringOddsRatioHelpButton)
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
genomesContainer := container.NewHBox(layout.NewSpacer(), viewGenomePairInfoButtonsColumn, genomePairNameColumn, offspringRiskWeightColumn, offspringOddsRatioColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
return genomesContainer, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
genomePairsLocusInfoGrid, err := getGenomePairsLocusInfoGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), locusNameRow, widget.NewSeparator(), genomePairsLocusInfoGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisTraitsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisTraitsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Genetic Analysis - Traits")
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is an analysis of the average trait scores for the couple's offspring.")
|
|
|
|
|
|
|
|
getTraitsGrid := func()(*fyne.Container, error){
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, _, _, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){ return nil, err }
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
traitNameLabel := getItalicLabelCentered("Trait Name")
|
|
|
|
|
|
|
|
offspringOutcomeScoresLabel := getItalicLabelCentered("Offspring Outcome Scores")
|
|
|
|
|
|
|
|
conflictExistsLabel := getItalicLabelCentered("Conflict Exists?")
|
|
|
|
|
|
|
|
emptyLabel := widget.NewLabel("")
|
|
|
|
|
|
|
|
traitNameColumn := container.NewVBox(traitNameLabel, widget.NewSeparator())
|
|
|
|
offspringOutcomeScoresColumn := container.NewVBox(offspringOutcomeScoresLabel, widget.NewSeparator())
|
|
|
|
conflictExistsColumn := container.NewVBox(conflictExistsLabel, widget.NewSeparator())
|
|
|
|
viewButtonsColumn := container.NewVBox(emptyLabel, widget.NewSeparator())
|
|
|
|
|
|
|
|
traitObjectsList, err := traits.GetTraitObjectsList()
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
for _, traitObject := range traitObjectsList{
|
|
|
|
|
|
|
|
traitName := traitObject.TraitName
|
|
|
|
|
|
|
|
traitRulesList := traitObject.RulesList
|
|
|
|
|
|
|
|
if (len(traitRulesList) == 0){
|
|
|
|
// This trait does not have any rules
|
|
|
|
// We cannot analyze it yet
|
|
|
|
// We will add neural network prediction so we can predict these traits
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
mainGenomePairIdentifier := helpers.JoinTwo16ByteArrays(pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
|
|
|
|
|
|
|
offspringOutcomeScoresKnown, offspringAverageOutcomeScoresMap, _, conflictExists, err := readGeneticAnalysis.GetOffspringTraitInfoFromGeneticAnalysis(coupleAnalysisObject, traitName, mainGenomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
// We add all of the columns except for the trait outcomes column, which may be multiple rows high
|
|
|
|
|
|
|
|
traitNameText := getBoldLabelCentered(traitName)
|
|
|
|
|
|
|
|
conflictExistsString := helpers.ConvertBoolToYesOrNoString(conflictExists)
|
|
|
|
conflictExistsLabel := getBoldLabelCentered(conflictExistsString)
|
|
|
|
|
|
|
|
viewDetailsButton := getWidgetCentered(widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisTraitDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
}))
|
|
|
|
|
|
|
|
traitNameColumn.Add(traitNameText)
|
|
|
|
conflictExistsColumn.Add(conflictExistsLabel)
|
|
|
|
viewButtonsColumn.Add(viewDetailsButton)
|
|
|
|
|
|
|
|
if (offspringOutcomeScoresKnown == false){
|
|
|
|
|
|
|
|
unknownTranslated := translate("Unknown")
|
|
|
|
unknownLabel := getBoldLabelCentered(unknownTranslated)
|
|
|
|
|
|
|
|
offspringOutcomeScoresColumn.Add(unknownLabel)
|
|
|
|
} else {
|
|
|
|
|
|
|
|
outcomeNamesList := helpers.GetListOfMapKeys(offspringAverageOutcomeScoresMap)
|
|
|
|
|
|
|
|
// We have to sort outcome names so they always show up in the same order
|
|
|
|
helpers.SortStringListToUnicodeOrder(outcomeNamesList)
|
|
|
|
|
|
|
|
for index, outcomeName := range outcomeNamesList{
|
|
|
|
|
|
|
|
outcomeScore, exists := offspringAverageOutcomeScoresMap[outcomeName]
|
|
|
|
if (exists == false){
|
|
|
|
return nil, errors.New("Outcome name not found in outcomeScoresMap after being found already.")
|
|
|
|
}
|
|
|
|
|
|
|
|
outcomeScoreString := helpers.ConvertFloat64ToStringRounded(outcomeScore, 2)
|
|
|
|
|
|
|
|
outcomeRow := getBoldLabelCentered(outcomeName + ": " + outcomeScoreString)
|
|
|
|
offspringOutcomeScoresColumn.Add(outcomeRow)
|
|
|
|
|
|
|
|
if (index > 0){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
|
|
|
|
traitNameColumn.Add(emptyLabelA)
|
|
|
|
conflictExistsColumn.Add(emptyLabelB)
|
|
|
|
viewButtonsColumn.Add(emptyLabelC)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
traitNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringOutcomeScoresColumn.Add(widget.NewSeparator())
|
|
|
|
conflictExistsColumn.Add(widget.NewSeparator())
|
|
|
|
viewButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringOutcomeScoresHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringTraitOutcomeScoresExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
offspringOutcomeScoresColumn.Add(offspringOutcomeScoresHelpButton)
|
|
|
|
|
|
|
|
traitsGrid := container.NewHBox(layout.NewSpacer(), traitNameColumn, offspringOutcomeScoresColumn)
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
|
|
|
|
|
|
|
conflictExistsHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setCoupleGeneticAnalysisConflictExistsExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
conflictExistsColumn.Add(conflictExistsHelpButton)
|
|
|
|
|
|
|
|
traitsGrid.Add(conflictExistsColumn)
|
|
|
|
}
|
|
|
|
|
|
|
|
traitsGrid.Add(viewButtonsColumn)
|
|
|
|
traitsGrid.Add(layout.NewSpacer())
|
|
|
|
|
|
|
|
return traitsGrid, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
traitsGrid, err := getTraitsGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), traitsGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisTraitDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, traitName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisTraitDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Couple Analysis - " + traitName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
getDescriptionSection := func()*fyne.Container{
|
|
|
|
|
|
|
|
if (secondGenomePairExists == false){
|
|
|
|
description := getLabelCentered("Below is the trait analysis for the couple's offspring.")
|
|
|
|
|
|
|
|
return description
|
|
|
|
}
|
|
|
|
|
|
|
|
description1 := getLabelCentered("Below is the trait analysis for the couple's offspring.")
|
|
|
|
description2 := getLabelCentered("Each genome pair combines different genomes from each person.")
|
|
|
|
|
|
|
|
descriptionsSection := container.NewVBox(description1, description2)
|
|
|
|
|
|
|
|
return descriptionsSection
|
|
|
|
}
|
|
|
|
|
|
|
|
descriptionSection := getDescriptionSection()
|
|
|
|
|
|
|
|
traitNameLabel := widget.NewLabel("Trait:")
|
|
|
|
traitNameText := getBoldLabel(traitName)
|
|
|
|
traitNameInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
|
|
|
setViewTraitDetailsPage(window, traitName, currentPage)
|
|
|
|
})
|
|
|
|
traitNameRow := container.NewHBox(layout.NewSpacer(), traitNameLabel, traitNameText, traitNameInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
|
|
|
|
offspringOutcomeScoresLabel := getItalicLabelCentered("Offspring Outcome Scores")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn := container.NewVBox(emptyLabelA, widget.NewSeparator())
|
|
|
|
pairNameColumn := container.NewVBox(emptyLabelB, widget.NewSeparator())
|
|
|
|
offspringOutcomeScoresColumn := container.NewVBox(offspringOutcomeScoresLabel, widget.NewSeparator())
|
|
|
|
viewOffspringRulesButtonsColumn := container.NewVBox(emptyLabelC, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomePairRow := func(genomePairName string, person1GenomeIdentifier [16]byte, person2GenomeIdentifier [16]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePairIdentifier := helpers.JoinTwo16ByteArrays(person1GenomeIdentifier, person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
genomePairNameLabel := getBoldLabelCentered(genomePairName)
|
|
|
|
|
|
|
|
viewGenomePairButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisTraitGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
|
|
|
|
viewOffspringRulesButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleTraitRulesPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
// We add all of the columns except for the trait rule column, which may be multiple rows high
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn.Add(viewGenomePairButton)
|
|
|
|
pairNameColumn.Add(genomePairNameLabel)
|
|
|
|
viewOffspringRulesButtonsColumn.Add(viewOffspringRulesButton)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringOutcomeScoresKnown, offspringOutcomeScoresMap, _, _, err := readGeneticAnalysis.GetOffspringTraitInfoFromGeneticAnalysis(coupleAnalysisObject, traitName, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
if (offspringOutcomeScoresKnown == false){
|
|
|
|
|
|
|
|
unknownTranslated := translate("Unknown")
|
|
|
|
unknownLabel := getBoldLabelCentered(unknownTranslated)
|
|
|
|
|
|
|
|
offspringOutcomeScoresColumn.Add(unknownLabel)
|
|
|
|
|
|
|
|
} else {
|
|
|
|
|
|
|
|
outcomeNamesList := helpers.GetListOfMapKeys(offspringOutcomeScoresMap)
|
|
|
|
|
|
|
|
// We have to sort the outcome names so they always show up in the same order
|
|
|
|
helpers.SortStringListToUnicodeOrder(outcomeNamesList)
|
|
|
|
|
|
|
|
for index, outcomeName := range outcomeNamesList{
|
|
|
|
|
|
|
|
outcomeScore, exists := offspringOutcomeScoresMap[outcomeName]
|
|
|
|
if (exists == false){
|
|
|
|
return errors.New("Outcome name not found in outcome scores map after being found already.")
|
|
|
|
}
|
|
|
|
|
|
|
|
outcomeScoreString := helpers.ConvertFloat64ToStringRounded(outcomeScore, 2)
|
|
|
|
|
|
|
|
outcomeRow := getBoldLabelCentered(outcomeName + ": " + outcomeScoreString)
|
|
|
|
offspringOutcomeScoresColumn.Add(outcomeRow)
|
|
|
|
|
|
|
|
if (index > 0){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
|
|
|
|
pairNameColumn.Add(emptyLabelA)
|
|
|
|
viewGenomePairButtonsColumn.Add(emptyLabelB)
|
|
|
|
viewOffspringRulesButtonsColumn.Add(emptyLabelC)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
viewGenomePairButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
pairNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringOutcomeScoresColumn.Add(widget.NewSeparator())
|
|
|
|
viewOffspringRulesButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
err = addGenomePairRow("Pair 1", pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
2024-06-02 10:43:39 +02:00
|
|
|
err := addGenomePairRow("Pair 2", pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) {
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringOutcomeScoresHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringTraitOutcomeScoresExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
offspringOutcomeScoresColumn.Add(offspringOutcomeScoresHelpButton)
|
|
|
|
|
|
|
|
genomesContainer := container.NewHBox(layout.NewSpacer(), viewGenomePairButtonsColumn, pairNameColumn, offspringOutcomeScoresColumn, viewOffspringRulesButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), descriptionSection, widget.NewSeparator(), traitNameRow, widget.NewSeparator(), genomesContainer)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisTraitGenomePairDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, traitName string, genomePairIdentifier [32]byte, genomePairName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisTraitGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, genomePairIdentifier, genomePairName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Viewing Couple Genome Pair Info")
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is the trait information for both genomes in the genome pair.")
|
|
|
|
|
|
|
|
traitNameLabel := widget.NewLabel("Trait:")
|
|
|
|
traitNameText := getBoldLabel(traitName)
|
|
|
|
traitNameInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
|
|
|
setViewTraitDetailsPage(window, traitName, currentPage)
|
|
|
|
})
|
|
|
|
traitNameRow := container.NewHBox(layout.NewSpacer(), traitNameLabel, traitNameText, traitNameInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
genomePairLabel := widget.NewLabel("Genome Pair:")
|
|
|
|
genomePairNameLabel := getBoldLabel(genomePairName)
|
|
|
|
genomePairHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setCoupleGenomePairExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
genomePairRow := container.NewHBox(layout.NewSpacer(), genomePairLabel, genomePairNameLabel, genomePairHelpButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
personNameLabel := getItalicLabelCentered("Person Name")
|
|
|
|
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
genomeNameLabel := getItalicLabelCentered("Genome Name")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
outcomeScoresLabel := getItalicLabelCentered("Outcome Scores")
|
|
|
|
|
|
|
|
numberOfLabel := getItalicLabelCentered("Number Of")
|
|
|
|
rulesTestedLabel := getItalicLabelCentered("Rules Tested")
|
|
|
|
|
|
|
|
emptyLabelD := widget.NewLabel("")
|
|
|
|
emptyLabelE := widget.NewLabel("")
|
|
|
|
|
|
|
|
personNameColumn := container.NewVBox(emptyLabelA, personNameLabel, widget.NewSeparator())
|
|
|
|
genomeNameColumn := container.NewVBox(emptyLabelB, genomeNameLabel, widget.NewSeparator())
|
|
|
|
outcomeScoresColumn := container.NewVBox(emptyLabelC, outcomeScoresLabel, widget.NewSeparator())
|
|
|
|
numberOfRulesTestedColumn := container.NewVBox(numberOfLabel, rulesTestedLabel, widget.NewSeparator())
|
|
|
|
viewGenomeButtonsColumn := container.NewVBox(emptyLabelD, emptyLabelE, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomeRow := func(isPerson1 bool, personName string, inputGenomeIdentifier [16]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
personAnalysisGenomeIdentifier, _, genomeIsCombined, combinedType, err := readGeneticAnalysis.GetMatchingPersonAnalysisGenomeIdentifierFromCoupleAnalysis(isPerson1, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, inputGenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
personNameTrimmed, _, err := helpers.TrimAndFlattenString(personName, 10)
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
personNameLabel := getBoldLabelCentered(personNameTrimmed)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
getPersonAnalysisObject := func()geneticAnalysis.PersonAnalysis{
|
|
|
|
if (isPerson1 == true){
|
|
|
|
return person1AnalysisObject
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
return person2AnalysisObject
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
personAnalysisObject := getPersonAnalysisObject()
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
getGenomeName := func()(string, error){
|
|
|
|
|
|
|
|
if (genomeIsCombined == false){
|
|
|
|
|
|
|
|
genomeFound, _, _, _, _, _, companyName, _, _, err := myGenomes.GetMyRawGenomeMetadata(personAnalysisGenomeIdentifier)
|
|
|
|
if (err != nil) { return "", err }
|
|
|
|
if (genomeFound == false){
|
2024-06-02 10:43:39 +02:00
|
|
|
return "", errors.New("MyGenomeInfo for genome from analysisObject not found.")
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
return companyName, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
return combinedType, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
genomeName, err := getGenomeName()
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
genomeNameLabel := getBoldLabelCentered(genomeName)
|
|
|
|
|
|
|
|
// We add all of the columns except for the trait rule column, which may be multiple rows high
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
_, anyTraitRuleTested, outcomeScoresMap, numberOfRulesTested, _, err := readGeneticAnalysis.GetPersonTraitInfoFromGeneticAnalysis(personAnalysisObject, traitName, personAnalysisGenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
numberOfRulesTestedString := helpers.ConvertIntToString(numberOfRulesTested)
|
|
|
|
numberOfRulesTestedText := getBoldLabelCentered(numberOfRulesTestedString)
|
|
|
|
|
|
|
|
viewGenomeButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewPersonGenomeTraitRulesPage(window, personAnalysisObject, traitName, personAnalysisGenomeIdentifier, genomeName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
personNameColumn.Add(personNameLabel)
|
|
|
|
genomeNameColumn.Add(genomeNameLabel)
|
|
|
|
numberOfRulesTestedColumn.Add(numberOfRulesTestedText)
|
|
|
|
viewGenomeButtonsColumn.Add(viewGenomeButton)
|
|
|
|
|
|
|
|
if (anyTraitRuleTested == false){
|
|
|
|
|
|
|
|
unknownTranslated := translate("Unknown")
|
|
|
|
unknownLabel := getBoldLabelCentered(unknownTranslated)
|
|
|
|
|
|
|
|
outcomeScoresColumn.Add(unknownLabel)
|
|
|
|
|
|
|
|
} else {
|
|
|
|
|
|
|
|
outcomeNamesList := helpers.GetListOfMapKeys(outcomeScoresMap)
|
|
|
|
|
|
|
|
// We have to sort the outcome names so they always show up in the same order
|
|
|
|
helpers.SortStringListToUnicodeOrder(outcomeNamesList)
|
|
|
|
|
|
|
|
for index, outcomeName := range outcomeNamesList{
|
|
|
|
|
|
|
|
outcomeScore, exists := outcomeScoresMap[outcomeName]
|
|
|
|
if (exists == false){
|
|
|
|
return errors.New("Outcome name not found in outcome scores map after being found already.")
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
outcomeScoreString := helpers.ConvertIntToString(outcomeScore)
|
|
|
|
|
|
|
|
outcomeRow := getBoldLabelCentered(outcomeName + ": " + outcomeScoreString)
|
|
|
|
outcomeScoresColumn.Add(outcomeRow)
|
|
|
|
|
|
|
|
if (index > 0){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
emptyLabelD := widget.NewLabel("")
|
|
|
|
|
|
|
|
personNameColumn.Add(emptyLabelA)
|
|
|
|
genomeNameColumn.Add(emptyLabelB)
|
|
|
|
numberOfRulesTestedColumn.Add(emptyLabelC)
|
|
|
|
viewGenomeButtonsColumn.Add(emptyLabelD)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
personNameColumn.Add(widget.NewSeparator())
|
|
|
|
genomeNameColumn.Add(widget.NewSeparator())
|
|
|
|
outcomeScoresColumn.Add(widget.NewSeparator())
|
|
|
|
numberOfRulesTestedColumn.Add(widget.NewSeparator())
|
|
|
|
viewGenomeButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
person1GenomeIdentifier, person2GenomeIdentifier := helpers.Split32ByteArrayInHalf(genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
err := addGenomeRow(true, person1Name, person1GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
err = addGenomeRow(false, person2Name, person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
outcomeScoresHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringTraitOutcomeScoresExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
outcomeScoresColumn.Add(outcomeScoresHelpButton)
|
|
|
|
|
|
|
|
numberOfRulesTestedHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringTraitNumberOfRulesTestedExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
numberOfRulesTestedColumn.Add(numberOfRulesTestedHelpButton)
|
|
|
|
|
|
|
|
genomesGrid := container.NewHBox(layout.NewSpacer(), personNameColumn, genomeNameColumn, outcomeScoresColumn, numberOfRulesTestedColumn, viewGenomeButtonsColumn, layout.NewSpacer())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), traitNameRow, widget.NewSeparator(), genomePairRow, widget.NewSeparator(), genomesGrid)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// This function provides a page to view the couple offspring rule probabilities for a particular genome pair
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleTraitRulesPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, traitName string, genomePairIdentifier [32]byte, genomePairName string, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
setLoadingScreen(window, "Loading Trait Rules", "Loading trait rules...")
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleTraitRulesPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, genomePairIdentifier, genomePairName, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("View Offspring Trait Rules - " + traitName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description1 := widget.NewLabel("Below are the trait rule probabilities for offspring from this genome pair.")
|
|
|
|
traitRulesHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringTraitRulesExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
description1Row := container.NewHBox(layout.NewSpacer(), description1, traitRulesHelpButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
genomePairLabel := widget.NewLabel("Genome Pair:")
|
|
|
|
genomePairNameLabel := getBoldLabel(genomePairName)
|
|
|
|
viewGenomePairInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisTraitGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
genomePairRow := container.NewHBox(layout.NewSpacer(), genomePairLabel, genomePairNameLabel, viewGenomePairInfoButton, layout.NewSpacer())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
_, _, numberOfRulesTested, _, err := readGeneticAnalysis.GetOffspringTraitInfoFromGeneticAnalysis(coupleAnalysisObject, traitName, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
numberOfRulesTestedString := helpers.ConvertIntToString(numberOfRulesTested)
|
|
|
|
|
|
|
|
traitRulesMap, err := traits.GetTraitRulesMap(traitName)
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
totalNumberOfRules := len(traitRulesMap)
|
|
|
|
totalNumberOfRulesString := helpers.ConvertIntToString(totalNumberOfRules)
|
|
|
|
|
|
|
|
rulesTestedLabel := widget.NewLabel("Rules Tested:")
|
|
|
|
rulesTestedText := getBoldLabel(numberOfRulesTestedString + "/" + totalNumberOfRulesString)
|
|
|
|
rulesTestedHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringTraitNumberOfRulesTestedExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
|
|
|
|
rulesTestedRow := container.NewHBox(layout.NewSpacer(), rulesTestedLabel, rulesTestedText, rulesTestedHelpButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
getRulesGrid := func()(*fyne.Container, error){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
ruleIdentifierLabel := getItalicLabelCentered("Rule Identifier")
|
|
|
|
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
ruleEffectsLabel := getItalicLabelCentered("Rule Effects")
|
|
|
|
|
|
|
|
offspringProbabilityOfLabel := getItalicLabelCentered("Offspring Probability Of")
|
|
|
|
passingRuleLabel := getItalicLabelCentered("Passing Rule")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
emptyLabelD := widget.NewLabel("")
|
|
|
|
|
|
|
|
ruleIdentifierColumn := container.NewVBox(emptyLabelA, ruleIdentifierLabel, widget.NewSeparator())
|
|
|
|
ruleEffectsColumn := container.NewVBox(emptyLabelB, ruleEffectsLabel, widget.NewSeparator())
|
|
|
|
offspringProbabilityOfPassingRuleColumn := container.NewVBox(offspringProbabilityOfLabel, passingRuleLabel, widget.NewSeparator())
|
|
|
|
ruleInfoButtonsColumn := container.NewVBox(emptyLabelC, emptyLabelD, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addRuleRow := func(ruleIdentifierHex string)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
ruleIdentifierLabel := getBoldLabelCentered(ruleIdentifierHex)
|
|
|
|
|
|
|
|
ruleIdentifier, err := encoding.DecodeHexStringTo3ByteArray(ruleIdentifierHex)
|
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
offspringRuleProbabilityKnown, _, offspringProbabilityOfPassingRuleFormatted, err := readGeneticAnalysis.GetOffspringTraitRuleInfoFromGeneticAnalysis(coupleAnalysisObject, traitName, ruleIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
viewRuleDetailsButton := widget.NewButtonWithIcon("", theme.VisibilityIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisTraitRuleDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, ruleIdentifier, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
getProbabilityOfPassingRuleText := func()string{
|
|
|
|
if (offspringRuleProbabilityKnown == false){
|
|
|
|
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
return offspringProbabilityOfPassingRuleFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
probabilityOfPassingRuleText := getProbabilityOfPassingRuleText()
|
|
|
|
probabilityOfPassingRuleTextLabel := getBoldLabelCentered(probabilityOfPassingRuleText)
|
|
|
|
|
|
|
|
// We add all of the columns except for the rule effects column
|
|
|
|
// We do this because the rule effects column may be multiple rows tall
|
|
|
|
|
|
|
|
ruleIdentifierColumn.Add(ruleIdentifierLabel)
|
|
|
|
offspringProbabilityOfPassingRuleColumn.Add(probabilityOfPassingRuleTextLabel)
|
|
|
|
ruleInfoButtonsColumn.Add(viewRuleDetailsButton)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
traitRuleObject, exists := traitRulesMap[ruleIdentifierHex]
|
2024-04-11 15:51:56 +02:00
|
|
|
if (exists == false){
|
2024-06-02 10:43:39 +02:00
|
|
|
return errors.New("Trait rule not found after being found already: " + ruleIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
ruleOutcomePointsMap := traitRuleObject.OutcomePointsMap
|
|
|
|
|
|
|
|
outcomeNamesList := helpers.GetListOfMapKeys(ruleOutcomePointsMap)
|
|
|
|
|
|
|
|
// We have to sort the outcome names so they always show up in the same order
|
|
|
|
helpers.SortStringListToUnicodeOrder(outcomeNamesList)
|
|
|
|
|
|
|
|
for index, outcomeName := range outcomeNamesList{
|
|
|
|
|
|
|
|
outcomeChange, exists := ruleOutcomePointsMap[outcomeName]
|
|
|
|
if (exists == false){
|
|
|
|
return errors.New("OutcomeName not found in ruleOutcomePointsMap after being found already: " + outcomeName)
|
|
|
|
}
|
|
|
|
|
|
|
|
getOutcomeEffectString := func()string{
|
|
|
|
|
|
|
|
outcomeChangeString := helpers.ConvertIntToString(outcomeChange)
|
|
|
|
|
|
|
|
if (outcomeChange < 0){
|
|
|
|
return outcomeChangeString
|
|
|
|
}
|
|
|
|
outcomeEffect := "+" + outcomeChangeString
|
|
|
|
return outcomeEffect
|
|
|
|
}
|
|
|
|
|
|
|
|
outcomeEffect := getOutcomeEffectString()
|
|
|
|
|
|
|
|
outcomeRow := getBoldLabelCentered(outcomeName + ": " + outcomeEffect)
|
|
|
|
ruleEffectsColumn.Add(outcomeRow)
|
|
|
|
|
|
|
|
if (index > 0){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
|
|
|
|
ruleIdentifierColumn.Add(emptyLabelA)
|
|
|
|
offspringProbabilityOfPassingRuleColumn.Add(emptyLabelB)
|
|
|
|
ruleInfoButtonsColumn.Add(emptyLabelC)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
ruleIdentifierColumn.Add(widget.NewSeparator())
|
|
|
|
ruleEffectsColumn.Add(widget.NewSeparator())
|
|
|
|
offspringProbabilityOfPassingRuleColumn.Add(widget.NewSeparator())
|
|
|
|
ruleInfoButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
rulesWithKnownProbabilityList := make([]string, 0)
|
|
|
|
rulesWithUnknownProbabilityList := make([]string, 0)
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
for ruleIdentifierHex, _ := range traitRulesMap{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
ruleIdentifier, err := encoding.DecodeHexStringTo3ByteArray(ruleIdentifierHex)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
offspringRuleProbabilityKnown, _, _, err := readGeneticAnalysis.GetOffspringTraitRuleInfoFromGeneticAnalysis(coupleAnalysisObject, traitName, ruleIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
if (offspringRuleProbabilityKnown == true){
|
2024-06-02 10:43:39 +02:00
|
|
|
rulesWithKnownProbabilityList = append(rulesWithKnownProbabilityList, ruleIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
} else {
|
2024-06-02 10:43:39 +02:00
|
|
|
rulesWithUnknownProbabilityList = append(rulesWithUnknownProbabilityList, ruleIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Now we sort rules so they show up in the same order each time
|
|
|
|
|
|
|
|
helpers.SortStringListToUnicodeOrder(rulesWithKnownProbabilityList)
|
|
|
|
helpers.SortStringListToUnicodeOrder(rulesWithUnknownProbabilityList)
|
|
|
|
|
|
|
|
for _, ruleIdentifier := range rulesWithKnownProbabilityList{
|
|
|
|
|
|
|
|
err = addRuleRow(ruleIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, ruleIdentifier := range rulesWithUnknownProbabilityList{
|
|
|
|
|
|
|
|
err = addRuleRow(ruleIdentifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
|
|
|
|
|
|
|
ruleEffectsHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setTraitRuleOutcomeEffectsExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
ruleEffectsColumn.Add(ruleEffectsHelpButton)
|
|
|
|
|
|
|
|
offspringProbabilityOfPassingRuleHelpButton := widget.NewButtonWithIcon("", theme.QuestionIcon(), func(){
|
|
|
|
setOffspringProbabilityOfPassingTraitRuleExplainerPage(window, currentPage)
|
|
|
|
})
|
|
|
|
offspringProbabilityOfPassingRuleColumn.Add(offspringProbabilityOfPassingRuleHelpButton)
|
|
|
|
|
|
|
|
rulesGrid := container.NewHBox(layout.NewSpacer(), ruleIdentifierColumn, ruleEffectsColumn, offspringProbabilityOfPassingRuleColumn, ruleInfoButtonsColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
return rulesGrid, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
rulesGrid, err := getRulesGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description1Row, widget.NewSeparator(), genomePairRow, widget.NewSeparator(), rulesTestedRow, widget.NewSeparator(), rulesGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// This function implements a page to view the details of a specific rule from a genetic analysis
|
|
|
|
// It will show the rule details for all of the couple's genome pairs
|
2024-06-02 10:43:39 +02:00
|
|
|
func setViewCoupleGeneticAnalysisTraitRuleDetailsPage(window fyne.Window, person1Name string, person2Name string, person1AnalysisObject geneticAnalysis.PersonAnalysis, person2AnalysisObject geneticAnalysis.PersonAnalysis, coupleAnalysisObject geneticAnalysis.CoupleAnalysis, traitName string, ruleIdentifier [3]byte, previousPage func()){
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
currentPage := func(){setViewCoupleGeneticAnalysisTraitRuleDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, ruleIdentifier, previousPage)}
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
title := getPageTitleCentered("Trait Rule Details - " + traitName)
|
|
|
|
|
|
|
|
backButton := getBackButtonCentered(previousPage)
|
|
|
|
|
|
|
|
description := getLabelCentered("Below is the trait rule analysis for the couple.")
|
2024-06-02 10:43:39 +02:00
|
|
|
|
|
|
|
ruleIdentifierHex := encoding.EncodeBytesToHexString(ruleIdentifier[:])
|
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
ruleIdentifierLabel := widget.NewLabel("Rule Identifier:")
|
2024-06-02 10:43:39 +02:00
|
|
|
ruleIdentifierText := getBoldLabel(ruleIdentifierHex)
|
2024-04-11 15:51:56 +02:00
|
|
|
ruleInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewTraitRuleDetailsPage(window, traitName, ruleIdentifierHex, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
ruleIdentifierRow := container.NewHBox(layout.NewSpacer(), ruleIdentifierLabel, ruleIdentifierText, ruleInfoButton, layout.NewSpacer())
|
|
|
|
|
|
|
|
getGenomePairsRuleInfoGrid := func()(*fyne.Container, error){
|
|
|
|
|
|
|
|
emptyLabelA := widget.NewLabel("")
|
|
|
|
emptyLabelB := widget.NewLabel("")
|
|
|
|
|
|
|
|
emptyLabelC := widget.NewLabel("")
|
|
|
|
genomePairLabel := getItalicLabelCentered("Genome Pair")
|
|
|
|
|
|
|
|
offspringProbabilityOfLabel := getItalicLabelCentered("Offspring Probability Of")
|
|
|
|
passingRuleLabel := getItalicLabelCentered("Passing Rule")
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn := container.NewVBox(emptyLabelA, emptyLabelB, widget.NewSeparator())
|
|
|
|
genomePairNameColumn := container.NewVBox(emptyLabelC, genomePairLabel, widget.NewSeparator())
|
|
|
|
offspringProbabilityOfPassingRuleColumn := container.NewVBox(offspringProbabilityOfLabel, passingRuleLabel, widget.NewSeparator())
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
addGenomePairRow := func(genomePairName string, genomePairIdentifier [32]byte)error{
|
2024-04-11 15:51:56 +02:00
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
offspringRuleProbabilityKnown, _, offspringProbabilityOfPassingRuleFormatted, err := readGeneticAnalysis.GetOffspringTraitRuleInfoFromGeneticAnalysis(coupleAnalysisObject, traitName, ruleIdentifier, genomePairIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil) { return err }
|
|
|
|
|
|
|
|
getOffspringProbabilityOfPassingRuleText := func()string{
|
|
|
|
|
|
|
|
if (offspringRuleProbabilityKnown == false){
|
|
|
|
result := translate("Unknown")
|
|
|
|
return result
|
|
|
|
}
|
|
|
|
|
|
|
|
return offspringProbabilityOfPassingRuleFormatted
|
|
|
|
}
|
|
|
|
|
|
|
|
offspringProbabilityOfPassingRuleText := getOffspringProbabilityOfPassingRuleText()
|
|
|
|
|
|
|
|
viewGenomePairInfoButton := widget.NewButtonWithIcon("", theme.InfoIcon(), func(){
|
2024-06-02 10:43:39 +02:00
|
|
|
setViewCoupleGeneticAnalysisTraitGenomePairDetailsPage(window, person1Name, person2Name, person1AnalysisObject, person2AnalysisObject, coupleAnalysisObject, traitName, genomePairIdentifier, genomePairName, currentPage)
|
2024-04-11 15:51:56 +02:00
|
|
|
})
|
|
|
|
|
|
|
|
genomePairNameLabel := getBoldLabelCentered(genomePairName)
|
|
|
|
|
|
|
|
offspringProbabilityOfPassingRuleLabel := getBoldLabelCentered(offspringProbabilityOfPassingRuleText)
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn.Add(viewGenomePairInfoButton)
|
|
|
|
genomePairNameColumn.Add(genomePairNameLabel)
|
|
|
|
offspringProbabilityOfPassingRuleColumn.Add(offspringProbabilityOfPassingRuleLabel)
|
|
|
|
|
|
|
|
viewGenomePairInfoButtonsColumn.Add(widget.NewSeparator())
|
|
|
|
genomePairNameColumn.Add(widget.NewSeparator())
|
|
|
|
offspringProbabilityOfPassingRuleColumn.Add(widget.NewSeparator())
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier, secondGenomePairExists, pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier, _, _, _, _, _, _, err := readGeneticAnalysis.GetMetadataFromCoupleGeneticAnalysis(coupleAnalysisObject)
|
2024-04-11 15:51:56 +02:00
|
|
|
if (err != nil){ return nil, err }
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePair1Identifier := helpers.JoinTwo16ByteArrays(pair1Person1GenomeIdentifier, pair1Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
err = addGenomePairRow("Pair 1", genomePair1Identifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
|
|
|
|
if (secondGenomePairExists == true){
|
|
|
|
|
2024-06-02 10:43:39 +02:00
|
|
|
genomePair2Identifier := helpers.JoinTwo16ByteArrays(pair2Person1GenomeIdentifier, pair2Person2GenomeIdentifier)
|
2024-04-11 15:51:56 +02:00
|
|
|
|
|
|
|
err := addGenomePairRow("Pair 2", genomePair2Identifier)
|
|
|
|
if (err != nil) { return nil, err }
|
|
|
|
}
|
2024-06-02 10:43:39 +02:00
|
|
|
|
2024-04-11 15:51:56 +02:00
|
|
|
genomesContainer := container.NewHBox(layout.NewSpacer(), viewGenomePairInfoButtonsColumn, genomePairNameColumn, offspringProbabilityOfPassingRuleColumn, layout.NewSpacer())
|
|
|
|
|
|
|
|
return genomesContainer, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
genomePairsRuleInfoGrid, err := getGenomePairsRuleInfoGrid()
|
|
|
|
if (err != nil){
|
|
|
|
setErrorEncounteredPage(window, err, previousPage)
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
page := container.NewVBox(title, backButton, widget.NewSeparator(), description, widget.NewSeparator(), ruleIdentifierRow, widget.NewSeparator(), genomePairsRuleInfoGrid)
|
|
|
|
|
|
|
|
setPageContent(page, window)
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|