gwaslab 3.5.7__py3-none-any.whl → 3.6.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of gwaslab might be problematic. Click here for more details.
- gwaslab/__init__.py +2 -0
- gwaslab/bd_common_data.py +1 -0
- gwaslab/bd_get_hapmap3.py +0 -1
- gwaslab/data/formatbook.json +78 -0
- gwaslab/data/reference.json +3 -1
- gwaslab/g_Sumstats.py +110 -25
- gwaslab/g_SumstatsMulti.py +287 -0
- gwaslab/g_SumstatsPair.py +101 -16
- gwaslab/g_Sumstats_polars.py +245 -0
- gwaslab/g_headers.py +12 -3
- gwaslab/g_meta.py +124 -47
- gwaslab/g_meta_update.py +48 -0
- gwaslab/g_vchange_status_polars.py +44 -0
- gwaslab/g_version.py +2 -2
- gwaslab/hm_casting.py +169 -110
- gwaslab/hm_casting_polars.py +202 -0
- gwaslab/hm_harmonize_sumstats.py +19 -8
- gwaslab/io_load_ld.py +529 -0
- gwaslab/io_preformat_input.py +11 -0
- gwaslab/io_preformat_input_polars.py +632 -0
- gwaslab/io_process_args.py +25 -1
- gwaslab/io_read_ldsc.py +34 -3
- gwaslab/io_read_pipcs.py +62 -6
- gwaslab/prscs_gigrnd.py +122 -0
- gwaslab/prscs_mcmc_gtb.py +136 -0
- gwaslab/prscs_parse_genet.py +98 -0
- gwaslab/qc_build.py +53 -0
- gwaslab/qc_check_datatype.py +10 -8
- gwaslab/qc_check_datatype_polars.py +128 -0
- gwaslab/qc_fix_sumstats.py +25 -23
- gwaslab/qc_fix_sumstats_polars.py +193 -0
- gwaslab/util_ex_calculate_ldmatrix.py +49 -19
- gwaslab/util_ex_gwascatalog.py +71 -28
- gwaslab/util_ex_infer_ancestry.py +65 -0
- gwaslab/util_ex_ldsc.py +67 -21
- gwaslab/util_ex_match_ldmatrix.py +396 -0
- gwaslab/util_ex_run_2samplemr.py +0 -2
- gwaslab/util_ex_run_ccgwas.py +155 -0
- gwaslab/util_ex_run_coloc.py +1 -1
- gwaslab/util_ex_run_hyprcoloc.py +117 -0
- gwaslab/util_ex_run_magma.py +74 -0
- gwaslab/util_ex_run_mesusie.py +155 -0
- gwaslab/util_ex_run_mtag.py +92 -0
- gwaslab/util_ex_run_prscs.py +85 -0
- gwaslab/util_ex_run_susie.py +40 -9
- gwaslab/util_in_estimate_ess.py +18 -0
- gwaslab/util_in_fill_data.py +20 -1
- gwaslab/util_in_filter_value.py +10 -5
- gwaslab/util_in_get_sig.py +71 -13
- gwaslab/util_in_meta.py +168 -4
- gwaslab/util_in_meta_polars.py +174 -0
- gwaslab/viz_aux_annotate_plot.py +13 -2
- gwaslab/viz_plot_compare_effect.py +87 -23
- gwaslab/viz_plot_credible_sets.py +55 -11
- gwaslab/viz_plot_effect.py +22 -12
- gwaslab/viz_plot_miamiplot2.py +3 -2
- gwaslab/viz_plot_mqqplot.py +94 -84
- gwaslab/viz_plot_qqplot.py +9 -7
- gwaslab/viz_plot_regional2.py +2 -1
- gwaslab/viz_plot_stackedregional.py +4 -1
- {gwaslab-3.5.7.dist-info → gwaslab-3.6.0.dist-info}/METADATA +46 -68
- gwaslab-3.6.0.dist-info/RECORD +119 -0
- {gwaslab-3.5.7.dist-info → gwaslab-3.6.0.dist-info}/WHEEL +1 -1
- gwaslab-3.5.7.dist-info/RECORD +0 -96
- {gwaslab-3.5.7.dist-info → gwaslab-3.6.0.dist-info/licenses}/LICENSE +0 -0
- {gwaslab-3.5.7.dist-info → gwaslab-3.6.0.dist-info/licenses}/LICENSE_before_v3.4.39 +0 -0
- {gwaslab-3.5.7.dist-info → gwaslab-3.6.0.dist-info}/top_level.txt +0 -0
|
@@ -0,0 +1,174 @@
|
|
|
1
|
+
|
|
2
|
+
import pandas as pd
|
|
3
|
+
import numpy as np
|
|
4
|
+
from scipy.stats.distributions import chi2
|
|
5
|
+
from scipy.stats import norm
|
|
6
|
+
from gwaslab.g_Log import Log
|
|
7
|
+
from gwaslab.io_to_pickle import load_data_from_pickle
|
|
8
|
+
from gwaslab.g_Sumstats import Sumstats
|
|
9
|
+
import gc
|
|
10
|
+
import polars as pl
|
|
11
|
+
import statsmodels.api as sm
|
|
12
|
+
########################################################################################################################################################################################################################################################################################################################################################
|
|
13
|
+
########################################################################################################################################################################################################################################################################################################################################################
|
|
14
|
+
########################################################################################################################################################################################################################################################################################################################################################
|
|
15
|
+
################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################################
|
|
16
|
+
########################################################################################################################################################################################################################################################################################################################################################
|
|
17
|
+
########################################################################################################################################################################################################################################################################################################################################################
|
|
18
|
+
|
|
19
|
+
def meta_analyze_polars(sumstats_multi,
|
|
20
|
+
random_effects=False,
|
|
21
|
+
nstudy=1,
|
|
22
|
+
log=Log()):
|
|
23
|
+
log.write("Start to perform meta-analysis...")
|
|
24
|
+
###########################################################################
|
|
25
|
+
log.write(" -Initiating result DataFrame...")
|
|
26
|
+
|
|
27
|
+
sumstats_multi = sumstats_multi.with_row_index()
|
|
28
|
+
|
|
29
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
30
|
+
N=pl.lit(0),
|
|
31
|
+
_BETAW_SUM = pl.lit(0.0),
|
|
32
|
+
_BETA2W_SUM =pl.lit(0.0),
|
|
33
|
+
_W_SUM =pl.lit(0.0),
|
|
34
|
+
_W2_SUM=pl.lit(0.0),
|
|
35
|
+
_EA_N=pl.lit(0.0),
|
|
36
|
+
_NEA_N=pl.lit(0.0),
|
|
37
|
+
DIRECTION =pl.lit(""),
|
|
38
|
+
BETA=pl.lit(0.0),
|
|
39
|
+
SE=pl.lit(0.0),
|
|
40
|
+
DOF =pl.lit(-1),
|
|
41
|
+
_R2=pl.lit(0.0),
|
|
42
|
+
)
|
|
43
|
+
|
|
44
|
+
for i in range(nstudy):
|
|
45
|
+
n="N_{}".format(i+1)
|
|
46
|
+
beta="BETA_{}".format(i+1)
|
|
47
|
+
se="SE_{}".format(i+1)
|
|
48
|
+
eaf="EAF_{}".format(i+1)
|
|
49
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
50
|
+
pl.when(pl.col(beta).is_null())
|
|
51
|
+
.then(pl.col("N"))
|
|
52
|
+
.otherwise(pl.col("N") + pl.col(n))
|
|
53
|
+
.alias("N")
|
|
54
|
+
).with_columns(
|
|
55
|
+
pl.when(pl.col(beta).is_null())
|
|
56
|
+
.then(pl.col("DOF") )
|
|
57
|
+
.otherwise(pl.col("DOF") + 1 )
|
|
58
|
+
.alias("DOF")
|
|
59
|
+
).with_columns(
|
|
60
|
+
pl.when(pl.col(beta).is_null())
|
|
61
|
+
.then(pl.col("_BETA2W_SUM"))
|
|
62
|
+
.otherwise(pl.col("_BETA2W_SUM") + pl.col(beta)**2 *(1/(pl.col(se)**2)))
|
|
63
|
+
.alias("_BETA2W_SUM")
|
|
64
|
+
).with_columns(
|
|
65
|
+
pl.when(pl.col(beta).is_null())
|
|
66
|
+
.then( pl.col("_BETAW_SUM") )
|
|
67
|
+
.otherwise(pl.col("_BETAW_SUM") + pl.col(beta)*(1/(pl.col(se)**2)) )
|
|
68
|
+
.alias("_BETAW_SUM")
|
|
69
|
+
).with_columns(
|
|
70
|
+
pl.when(pl.col(beta).is_null())
|
|
71
|
+
.then( pl.col("_W_SUM") )
|
|
72
|
+
.otherwise(pl.col("_W_SUM") + 1/(pl.col(se)**2))
|
|
73
|
+
.alias("_W_SUM")
|
|
74
|
+
).with_columns(
|
|
75
|
+
pl.when(pl.col(beta).is_null())
|
|
76
|
+
.then( pl.col("_W2_SUM") )
|
|
77
|
+
.otherwise(pl.col("_W2_SUM") + pl.col("_W_SUM")**2)
|
|
78
|
+
.alias("_W2_SUM")
|
|
79
|
+
).with_columns(
|
|
80
|
+
pl.when(pl.col(beta).is_null())
|
|
81
|
+
.then( pl.col("_EA_N") )
|
|
82
|
+
.otherwise(pl.col("_EA_N") + pl.col(n)*pl.col(eaf))
|
|
83
|
+
.alias("_EA_N")
|
|
84
|
+
).with_columns(
|
|
85
|
+
pl.when(pl.col(beta).is_null())
|
|
86
|
+
.then( pl.col("_NEA_N") )
|
|
87
|
+
.otherwise(pl.col("_EA_N") + pl.col(n)*(1-pl.col(eaf)))
|
|
88
|
+
.alias("_NEA_N")
|
|
89
|
+
).with_columns(
|
|
90
|
+
pl.when(pl.col(beta) <0 )
|
|
91
|
+
.then( pl.col("DIRECTION") +"-" )
|
|
92
|
+
.otherwise( pl.col("DIRECTION") )
|
|
93
|
+
.alias("DIRECTION")
|
|
94
|
+
).with_columns(
|
|
95
|
+
pl.when(pl.col(beta) >0 )
|
|
96
|
+
.then( pl.col("DIRECTION") +"-" )
|
|
97
|
+
.otherwise( pl.col("DIRECTION") )
|
|
98
|
+
.alias("DIRECTION")
|
|
99
|
+
).with_columns(
|
|
100
|
+
pl.when(pl.col(beta) ==0 )
|
|
101
|
+
.then( pl.col("DIRECTION") +"0" )
|
|
102
|
+
.otherwise( pl.col("DIRECTION") )
|
|
103
|
+
.alias("DIRECTION")
|
|
104
|
+
).with_columns(
|
|
105
|
+
pl.when(pl.col(beta).is_null() )
|
|
106
|
+
.then( pl.col("DIRECTION") +"?" )
|
|
107
|
+
.otherwise( pl.col("DIRECTION") )
|
|
108
|
+
.alias("DIRECTION")
|
|
109
|
+
)
|
|
110
|
+
|
|
111
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
112
|
+
BETA = pl.col("_BETAW_SUM") / pl.col("_W_SUM"),
|
|
113
|
+
EAF = pl.col("_EA_N") / (pl.col("_EA_N") + pl.col("_NEA_N")),
|
|
114
|
+
SE = (1/pl.col("_W_SUM")).sqrt(),
|
|
115
|
+
Q = pl.col("_BETA2W_SUM") - (pl.col("_BETAW_SUM")**2/pl.col("_W_SUM"))
|
|
116
|
+
)
|
|
117
|
+
|
|
118
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
119
|
+
Z = pl.col("BETA") / pl.col("SE")
|
|
120
|
+
).with_columns(
|
|
121
|
+
P = pl.col("Z").map_batches(lambda x: pl.Series(2*norm.sf(x.abs())))
|
|
122
|
+
)
|
|
123
|
+
|
|
124
|
+
if random_effects==True:
|
|
125
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
126
|
+
_R2 = (pl.col("Q") - pl.col("DOF")) / (pl.col("_W_SUM") - (pl.col("_W2_SUM")/pl.col("_W_SUM")))
|
|
127
|
+
).with_columns(
|
|
128
|
+
pl.when(pl.col("_R2")<0 )
|
|
129
|
+
.then( pl.lit(0) )
|
|
130
|
+
.otherwise( pl.col("_R2") )
|
|
131
|
+
.alias("_R2")
|
|
132
|
+
)
|
|
133
|
+
|
|
134
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
135
|
+
_BETAW_SUM_R = pl.lit(0.0),
|
|
136
|
+
_W_SUM_R =pl.lit(0.0),
|
|
137
|
+
BETA_RANDOM =pl.col("BETA"),
|
|
138
|
+
SE_RANDOM = pl.col("SE")
|
|
139
|
+
)
|
|
140
|
+
|
|
141
|
+
|
|
142
|
+
|
|
143
|
+
for i in range(nstudy):
|
|
144
|
+
n="N_{}".format(i+1)
|
|
145
|
+
beta="BETA_{}".format(i+1)
|
|
146
|
+
se="SE_{}".format(i+1)
|
|
147
|
+
eaf="EAF_{}".format(i+1)
|
|
148
|
+
|
|
149
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
150
|
+
pl.when( pl.col(beta).is_null() )
|
|
151
|
+
.then(pl.col("_BETAW_SUM_R"))
|
|
152
|
+
.otherwise(pl.col("_BETAW_SUM_R") + pl.col(beta)*(1/ (pl.col(se)**2 + pl.col("_R2")) ))
|
|
153
|
+
.alias("_BETAW_SUM_R")
|
|
154
|
+
).with_columns(
|
|
155
|
+
pl.when( pl.col(beta).is_null() )
|
|
156
|
+
.then(pl.col("_W_SUM_R") )
|
|
157
|
+
.otherwise( pl.col("_W_SUM_R") + 1/(pl.col(se)**2 + pl.col("_R2") ) )
|
|
158
|
+
.alias("_W_SUM_R")
|
|
159
|
+
)
|
|
160
|
+
|
|
161
|
+
sumstats_multi = sumstats_multi.with_columns(
|
|
162
|
+
BETA_RANDOM = (pl.col("_BETAW_SUM_R") / pl.col("_W_SUM_R"))
|
|
163
|
+
).with_columns(
|
|
164
|
+
SE_RANDOM = ( (1/pl.col("_W_SUM_R")).sqrt() )
|
|
165
|
+
).with_columns(
|
|
166
|
+
Z_RANDOM = pl.col("BETA_RANDOM") / pl.col("SE_RANDOM")
|
|
167
|
+
).with_columns(
|
|
168
|
+
P_RANDOM = pl.col("Z_RANDOM").map_batches(lambda x: pl.Series(2*norm.sf(x.abs()))
|
|
169
|
+
)
|
|
170
|
+
)
|
|
171
|
+
|
|
172
|
+
sumstats_multi = sumstats_multi.select(pl.all().exclude("^_.*$|\w+_[\d]+$") )
|
|
173
|
+
log.write("Finished performing meta-analysis.")
|
|
174
|
+
return sumstats_multi
|
gwaslab/viz_aux_annotate_plot.py
CHANGED
|
@@ -26,6 +26,7 @@ def annotate_single(
|
|
|
26
26
|
anno_alias,
|
|
27
27
|
anno_style,
|
|
28
28
|
anno_args,
|
|
29
|
+
anno_args_single,
|
|
29
30
|
arm_scale,
|
|
30
31
|
anno_max_iter,
|
|
31
32
|
arm_scale_d,
|
|
@@ -216,13 +217,23 @@ def annotate_single(
|
|
|
216
217
|
if anno_style == "tight" :
|
|
217
218
|
anno_default["rotation"] = 90
|
|
218
219
|
################################################################################################################################
|
|
219
|
-
|
|
220
|
+
# anno args for all
|
|
220
221
|
for key,value in anno_args.items():
|
|
221
222
|
anno_default[key]=value
|
|
222
|
-
|
|
223
|
+
|
|
224
|
+
# anno args for highlight group
|
|
225
|
+
if len(highlight_i) >0:
|
|
223
226
|
if row["i"] in highlight_i:
|
|
224
227
|
for key,value in highlight_anno_args.items():
|
|
225
228
|
anno_default[key]=value
|
|
229
|
+
|
|
230
|
+
# anno args for specifc
|
|
231
|
+
#try:
|
|
232
|
+
if row[snpid] in anno_args_single.keys():
|
|
233
|
+
for key,value in anno_args_single[row[snpid]].items():
|
|
234
|
+
anno_default[key]=value
|
|
235
|
+
#except:
|
|
236
|
+
# pass
|
|
226
237
|
################################################################################################################################
|
|
227
238
|
if anno_adjust==True:
|
|
228
239
|
if _invert==False:
|
|
@@ -51,11 +51,12 @@ def compare_effect(path1,
|
|
|
51
51
|
reg_box=None,
|
|
52
52
|
is_reg=True,
|
|
53
53
|
fdr=False,
|
|
54
|
+
reg_text="full",
|
|
54
55
|
allele_match=False,
|
|
55
56
|
r_se=False,
|
|
56
57
|
is_45_helper_line=True,
|
|
57
58
|
legend_mode="full",
|
|
58
|
-
legend_title=r'
|
|
59
|
+
legend_title=r'$\mathregular{ P < 5 x 10^{-8}}$ in:',
|
|
59
60
|
legend_title2=r'Heterogeneity test:',
|
|
60
61
|
legend_pos='upper left',
|
|
61
62
|
scatterargs=None,
|
|
@@ -85,12 +86,12 @@ def compare_effect(path1,
|
|
|
85
86
|
scaled1 = True
|
|
86
87
|
scaled2 = True
|
|
87
88
|
|
|
88
|
-
if legend_title== r'
|
|
89
|
+
if legend_title== r'$\mathregular{ P < 5 x 10^{-8}}$ in:' and sig_level!=5e-8:
|
|
89
90
|
|
|
90
91
|
exponent = math.floor(math.log10(sig_level))
|
|
91
92
|
mantissa = sig_level / 10**exponent
|
|
92
93
|
|
|
93
|
-
legend_title = '
|
|
94
|
+
legend_title = '$\mathregular{ P < {} x 10^{{{}}}}$ in:'.format(mantissa, exponent)
|
|
94
95
|
|
|
95
96
|
if is_q_mc=="fdr" or is_q_mc=="bon":
|
|
96
97
|
is_q = True
|
|
@@ -100,6 +101,8 @@ def compare_effect(path1,
|
|
|
100
101
|
if save_args is None:
|
|
101
102
|
save_args = {"dpi":300,"facecolor":"white"}
|
|
102
103
|
if reg_box is None:
|
|
104
|
+
reg_box= None
|
|
105
|
+
elif reg_box==True:
|
|
103
106
|
reg_box = dict(boxstyle='round', facecolor='white', alpha=1,edgecolor="grey")
|
|
104
107
|
if sep is None:
|
|
105
108
|
sep = ["\t","\t"]
|
|
@@ -116,7 +119,7 @@ def compare_effect(path1,
|
|
|
116
119
|
if helper_line_args is None:
|
|
117
120
|
helper_line_args={"color":'black', "linestyle":'-',"lw":1}
|
|
118
121
|
if plt_args is None:
|
|
119
|
-
plt_args={"figsize":(
|
|
122
|
+
plt_args={"figsize":(7,7),"dpi":300}
|
|
120
123
|
if scatterargs is None:
|
|
121
124
|
scatterargs={"s":20}
|
|
122
125
|
if label is None:
|
|
@@ -487,9 +490,23 @@ def compare_effect(path1,
|
|
|
487
490
|
ax.spines[spine].set_visible(False)
|
|
488
491
|
|
|
489
492
|
###regression line##############################################################################################################################
|
|
490
|
-
ax =
|
|
491
|
-
|
|
492
|
-
|
|
493
|
+
ax = configure_regression_line(is_reg=is_reg,
|
|
494
|
+
reg_text=reg_text,
|
|
495
|
+
reg_box=reg_box,
|
|
496
|
+
sig_list_merged=sig_list_merged,
|
|
497
|
+
ax=ax,
|
|
498
|
+
mode=mode,
|
|
499
|
+
xl=xl,
|
|
500
|
+
yl=yl,
|
|
501
|
+
xh=xh,
|
|
502
|
+
yh=yh,
|
|
503
|
+
null_beta=null_beta,
|
|
504
|
+
r_se=r_se,
|
|
505
|
+
is_45_helper_line=is_45_helper_line,
|
|
506
|
+
helper_line_args=helper_line_args,
|
|
507
|
+
font_kwargs=font_kwargs,
|
|
508
|
+
log=log,
|
|
509
|
+
verbose=verbose)
|
|
493
510
|
|
|
494
511
|
|
|
495
512
|
ax.set_xlabel(xylabel_prefix+label[0],**font_kwargs)
|
|
@@ -1128,9 +1145,23 @@ def scatter_annotation(ax, sig_list_merged,anno, anno_het, is_q, mode,
|
|
|
1128
1145
|
return ax
|
|
1129
1146
|
|
|
1130
1147
|
|
|
1131
|
-
def
|
|
1132
|
-
|
|
1133
|
-
|
|
1148
|
+
def configure_regression_line(is_reg,
|
|
1149
|
+
reg_box,
|
|
1150
|
+
reg_text,
|
|
1151
|
+
sig_list_merged,
|
|
1152
|
+
ax,
|
|
1153
|
+
mode,
|
|
1154
|
+
xl,
|
|
1155
|
+
yl,
|
|
1156
|
+
xh,
|
|
1157
|
+
yh,
|
|
1158
|
+
null_beta,
|
|
1159
|
+
r_se,
|
|
1160
|
+
is_45_helper_line,
|
|
1161
|
+
helper_line_args,
|
|
1162
|
+
font_kwargs,
|
|
1163
|
+
log,
|
|
1164
|
+
verbose):
|
|
1134
1165
|
if len(sig_list_merged)<3: is_reg=False
|
|
1135
1166
|
if is_reg is True:
|
|
1136
1167
|
if mode=="beta" or mode=="BETA" or mode=="Beta":
|
|
@@ -1149,8 +1180,8 @@ def confire_regression_line(is_reg, reg_box, sig_list_merged, ax, mode,xl,yl,xh
|
|
|
1149
1180
|
|
|
1150
1181
|
#### calculate p values based on selected value , default = 0
|
|
1151
1182
|
log.write(" -Calculating p values based on given null slope :",null_beta, verbose=verbose)
|
|
1152
|
-
t_score = (reg[0]-null_beta) / reg[4]
|
|
1153
|
-
degree = len(sig_list_merged.dropna())-2
|
|
1183
|
+
#t_score = (reg[0]-null_beta) / reg[4]
|
|
1184
|
+
#degree = len(sig_list_merged.dropna())-2
|
|
1154
1185
|
p = reg[3]
|
|
1155
1186
|
#ss.t.sf(abs(t_score), df=degree)*2
|
|
1156
1187
|
log.write(" -Beta = ", reg[0], verbose=verbose)
|
|
@@ -1174,9 +1205,25 @@ def confire_regression_line(is_reg, reg_box, sig_list_merged, ax, mode,xl,yl,xh
|
|
|
1174
1205
|
except:
|
|
1175
1206
|
p12="0"
|
|
1176
1207
|
pe="0"
|
|
1177
|
-
|
|
1208
|
+
if p > 1e-300:
|
|
1209
|
+
p_text="$\mathregular{p = " + p12 + " \\times 10^{"+pe+"}}$"
|
|
1210
|
+
else:
|
|
1211
|
+
p_text="$\mathregular{p < 1 \\times 10^{-300}}$"
|
|
1178
1212
|
p_latex= f'{p_text}'
|
|
1179
|
-
|
|
1213
|
+
|
|
1214
|
+
if reg_text=="full":
|
|
1215
|
+
reg_string = "y = "+"{:.2f}".format(reg[1]) +" + "+ "{:.2f}".format(reg[0])+" x, "+ p_latex + ", r = " +"{:.2f}".format(reg[2])+r_se_jackknife_string
|
|
1216
|
+
ax.text(0.98,0.02,
|
|
1217
|
+
reg_string,
|
|
1218
|
+
va="bottom",ha="right",transform=ax.transAxes, bbox=reg_box, **font_kwargs)
|
|
1219
|
+
elif reg_text=="r":
|
|
1220
|
+
reg_string ="r = " +"{:.2f}".format(reg[2])+r_se_jackknife_string
|
|
1221
|
+
ax.text(0.98,0.02,
|
|
1222
|
+
reg_string, va="bottom",ha="right",transform=ax.transAxes, bbox=reg_box, **font_kwargs)
|
|
1223
|
+
elif reg_text=="r2":
|
|
1224
|
+
reg_string = "$\mathregular{r^{2}} = " +"{:.2f}".format(reg[2]**2)
|
|
1225
|
+
ax.text(0.98,0.02,
|
|
1226
|
+
reg_string, va="bottom",ha="right",transform=ax.transAxes, bbox=reg_box, **font_kwargs)
|
|
1180
1227
|
else:
|
|
1181
1228
|
#if regression coeeficient <0 : auxiliary line slope = -1
|
|
1182
1229
|
if is_45_helper_line is True:
|
|
@@ -1191,9 +1238,25 @@ def confire_regression_line(is_reg, reg_box, sig_list_merged, ax, mode,xl,yl,xh
|
|
|
1191
1238
|
except:
|
|
1192
1239
|
p12="0"
|
|
1193
1240
|
pe="0"
|
|
1194
|
-
|
|
1241
|
+
|
|
1242
|
+
if p > 1e-300:
|
|
1243
|
+
p_text="$\mathregular{p = " + p12 + " \\times 10^{"+pe+"}}$"
|
|
1244
|
+
else:
|
|
1245
|
+
p_text="$\mathregular{p < 1 \\times 10^{-300}}$"
|
|
1195
1246
|
p_latex= f'{p_text}'
|
|
1196
|
-
|
|
1247
|
+
|
|
1248
|
+
if reg_text=="full":
|
|
1249
|
+
ax.text(0.98,0.02,
|
|
1250
|
+
"y = "+"{:.2f}".format(reg[1]) +" - "+ "{:.2f}".format(abs(reg[0]))+" x, "+ p_latex + ", r = " +"{:.2f}".format(reg[2])+r_se_jackknife_string,
|
|
1251
|
+
va="bottom",ha="right",transform=ax.transAxes,bbox=reg_box,**font_kwargs)
|
|
1252
|
+
elif reg_text=="r":
|
|
1253
|
+
ax.text(0.98,0.02,
|
|
1254
|
+
"r = " +"{:.2f}".format(reg[2])+r_se_jackknife_string,
|
|
1255
|
+
va="bottom",ha="right",transform=ax.transAxes, bbox=reg_box, **font_kwargs)
|
|
1256
|
+
elif reg_text=="r2":
|
|
1257
|
+
ax.text(0.98,0.02,
|
|
1258
|
+
"$\mathregular{r^{2}} = " +"{:.2f}".format(reg[2]**2),
|
|
1259
|
+
va="bottom",ha="right",transform=ax.transAxes, bbox=reg_box, **font_kwargs)
|
|
1197
1260
|
|
|
1198
1261
|
if mode=="beta" or mode=="BETA" or mode=="Beta":
|
|
1199
1262
|
middle = sig_list_merged["EFFECT_1"].mean()
|
|
@@ -1216,7 +1279,8 @@ def configure_legend(fig, ax, legend_mode, is_q, is_q_mc, legend_elements, legen
|
|
|
1216
1279
|
"handletextpad":0.8,
|
|
1217
1280
|
"edgecolor":"grey",
|
|
1218
1281
|
"borderpad":0.3,
|
|
1219
|
-
"alignment":"left"
|
|
1282
|
+
"alignment":"left",
|
|
1283
|
+
"frameon":False
|
|
1220
1284
|
}
|
|
1221
1285
|
|
|
1222
1286
|
if legend_args is not None:
|
|
@@ -1227,14 +1291,14 @@ def configure_legend(fig, ax, legend_mode, is_q, is_q_mc, legend_elements, legen
|
|
|
1227
1291
|
title_proxy = Rectangle((0,0), 0, 0, color='w',label=legend_title)
|
|
1228
1292
|
title_proxy2 = Rectangle((0,0), 0, 0, color='w',label=legend_title2)
|
|
1229
1293
|
if is_q_mc=="fdr":
|
|
1230
|
-
het_label_sig = r"
|
|
1231
|
-
het_label_sig2 = r"
|
|
1294
|
+
het_label_sig = r"$\mathregular{FDR_{het} < }$" + "{}".format(q_level)
|
|
1295
|
+
het_label_sig2 = r"$\mathregular{FDR_{het} > }$" + "{}".format(q_level)
|
|
1232
1296
|
elif is_q_mc=="bon":
|
|
1233
|
-
het_label_sig = r"
|
|
1234
|
-
het_label_sig2 = r"
|
|
1297
|
+
het_label_sig = r"$\mathregular{P_{het,bon} < }$" + "{}".format(q_level)
|
|
1298
|
+
het_label_sig2 = r"$\mathregular{P_{het,bon} > }$" + "{}".format(q_level)
|
|
1235
1299
|
else:
|
|
1236
|
-
het_label_sig = r"
|
|
1237
|
-
het_label_sig2 = r"
|
|
1300
|
+
het_label_sig = r"$\mathregular{P_{het} < }$" + "{}".format(q_level)
|
|
1301
|
+
het_label_sig2 = r"$\mathregular{P_{het} > }$" + "{}".format(q_level)
|
|
1238
1302
|
het_sig = Rectangle((0,0), 0, 0, facecolor='#cccccc',edgecolor="black", linewidth=1, label=het_label_sig)
|
|
1239
1303
|
het_nonsig = Rectangle((0,0), 0, 0, facecolor='#cccccc',edgecolor="white",linewidth=1, label=het_label_sig2)
|
|
1240
1304
|
|
|
@@ -9,39 +9,56 @@ from gwaslab.viz_plot_mqqplot import _process_xlabel
|
|
|
9
9
|
from gwaslab.bd_common_data import get_number_to_chr
|
|
10
10
|
from gwaslab.util_in_filter_value import _filter_region
|
|
11
11
|
from gwaslab.io_process_args import _extract_kwargs
|
|
12
|
+
import copy
|
|
12
13
|
|
|
13
|
-
def _plot_cs(
|
|
14
|
-
region,
|
|
14
|
+
def _plot_cs(pipcs_raw,
|
|
15
|
+
region=None,
|
|
16
|
+
locus=None,
|
|
15
17
|
figax=None,
|
|
16
18
|
_posdiccul=None,
|
|
17
19
|
xtick_chr_dict=None,
|
|
18
20
|
pip="PIP",
|
|
19
21
|
onlycs=False,
|
|
22
|
+
pos="POS",
|
|
23
|
+
chrom="CHR",
|
|
20
24
|
cs="CREDIBLE_SET_INDEX",
|
|
25
|
+
cs_category = "CS_CATEGORY",
|
|
21
26
|
marker_size=(45,85),
|
|
22
27
|
fontsize = 12,
|
|
23
28
|
font_family = "Arial",
|
|
24
|
-
legend_title="Credible
|
|
29
|
+
legend_title="Credible set",
|
|
30
|
+
fig_args=None,
|
|
25
31
|
log=Log(),
|
|
26
32
|
verbose=True,
|
|
27
33
|
**kwargs):
|
|
28
34
|
'''
|
|
29
35
|
pipcs : a DataFrame of finemapping results
|
|
30
36
|
'''
|
|
37
|
+
pipcs = pipcs_raw.copy()
|
|
31
38
|
## parameters #############################
|
|
32
39
|
if xtick_chr_dict is None:
|
|
33
40
|
xtick_chr_dict = get_number_to_chr()
|
|
34
|
-
|
|
41
|
+
if fig_args is None:
|
|
42
|
+
fig_args={"figsize":(15,5),"dpi":400}
|
|
35
43
|
scatter_kwargs = _extract_kwargs("scatter", dict(), locals())
|
|
36
44
|
|
|
37
45
|
region_marker_shapes = ['o', '^','s','D','*','P','X','h','8']
|
|
38
46
|
region_ld_colors_m = ["grey","#E51819","green","#F07818","#AD5691","yellow","purple"]
|
|
39
47
|
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
48
|
+
if region is not None:
|
|
49
|
+
## filter data #############################
|
|
50
|
+
pipcs = _filter_region(pipcs, region)
|
|
51
|
+
log.write(" -Loading PIP and CS for variants in the region :{}".format(region))
|
|
52
|
+
|
|
53
|
+
if locus is not None:
|
|
54
|
+
pipcs = pipcs.loc[pipcs["LOCUS"] == locus,:].copy()
|
|
55
|
+
log.write(" -Loading PIP and CS for variants in the locus :{}".format(region))
|
|
56
|
+
if region is None:
|
|
57
|
+
region = (pipcs[chrom].iloc[0],pipcs[pos].min(),pipcs[pos].max())
|
|
58
|
+
log.write(" -Extracted region:{}".format(region))
|
|
43
59
|
if onlycs ==True:
|
|
44
60
|
pipcs = pipcs.loc[pipcs[cs]>0,:]
|
|
61
|
+
log.write(" -Loading only variants in CS...")
|
|
45
62
|
|
|
46
63
|
pipcs[cs] = pipcs[cs].astype("string")
|
|
47
64
|
|
|
@@ -50,7 +67,7 @@ def _plot_cs(pipcs,
|
|
|
50
67
|
ax=figax[1]
|
|
51
68
|
fig=figax[0]
|
|
52
69
|
else:
|
|
53
|
-
fig, ax = plt.subplots()
|
|
70
|
+
fig, ax = plt.subplots(**fig_args)
|
|
54
71
|
|
|
55
72
|
# assign i
|
|
56
73
|
pipcs,chrom_df=_quick_assign_i_with_rank(pipcs, chrpad=0.00,
|
|
@@ -58,12 +75,17 @@ def _plot_cs(pipcs,
|
|
|
58
75
|
chrom="CHR",pos="POS",
|
|
59
76
|
drop_chr_start=False,
|
|
60
77
|
_posdiccul=_posdiccul)
|
|
78
|
+
|
|
61
79
|
pipcs = pipcs.sort_values(by=cs,ascending=True)
|
|
62
80
|
|
|
63
81
|
## plot ##########################################
|
|
64
82
|
scatter_kwargs["markers"]= {m:region_marker_shapes[i] for i,m in enumerate(pipcs[cs].unique())}
|
|
65
83
|
palette = sns.color_palette(region_ld_colors_m,n_colors=pipcs[cs].nunique())
|
|
66
84
|
edgecolor="none"
|
|
85
|
+
|
|
86
|
+
if cs_category in pipcs.columns:
|
|
87
|
+
cs_category_dic = pipcs.loc[~pipcs[cs_category].isna(), [cs, cs_category]].drop_duplicates().set_index(cs).to_dict()
|
|
88
|
+
|
|
67
89
|
|
|
68
90
|
plot = sns.scatterplot(data=pipcs,
|
|
69
91
|
x="i",
|
|
@@ -75,6 +97,17 @@ def _plot_cs(pipcs,
|
|
|
75
97
|
s=marker_size[1],
|
|
76
98
|
ax=ax,
|
|
77
99
|
**scatter_kwargs)
|
|
100
|
+
|
|
101
|
+
region_step=21
|
|
102
|
+
region_ticks = list(map('{:.3f}'.format,np.linspace(region[1], region[2], num=region_step).astype("int")/1000000))
|
|
103
|
+
|
|
104
|
+
most_left_snp = pipcs["i"].idxmin()
|
|
105
|
+
# distance between leftmost variant position to region left bound
|
|
106
|
+
i_pos_offset = pipcs.loc[most_left_snp,"i"] - pipcs.loc[most_left_snp,pos]
|
|
107
|
+
ax.set_xticks(np.linspace(i_pos_offset+region[1], i_pos_offset+region[2], num=region_step))
|
|
108
|
+
ax.set_xticklabels(region_ticks,rotation=45)
|
|
109
|
+
xlabel = "Chromosome "+str(region[0])+" (MB)"
|
|
110
|
+
ax.set_xlabel(xlabel,fontsize=fontsize,family=font_family)
|
|
78
111
|
|
|
79
112
|
# process legend
|
|
80
113
|
handles, labels = ax.get_legend_handles_labels()
|
|
@@ -82,18 +115,29 @@ def _plot_cs(pipcs,
|
|
|
82
115
|
new_handles = []
|
|
83
116
|
ncol = len(labels)
|
|
84
117
|
|
|
118
|
+
ax.tick_params(axis='y',
|
|
119
|
+
labelsize=fontsize,
|
|
120
|
+
labelfontfamily=font_family)
|
|
121
|
+
|
|
85
122
|
for i,label in enumerate(labels):
|
|
86
123
|
if label in [str(j) for j in range(1,10)]:
|
|
87
|
-
|
|
124
|
+
if cs_category in pipcs.columns:
|
|
125
|
+
new_labels.append("#{} - {}".format(labels[i],cs_category_dic[cs_category][label]) )
|
|
126
|
+
else:
|
|
127
|
+
new_labels.append("#"+labels[i])
|
|
88
128
|
new_handles.append(handles[i])
|
|
89
129
|
|
|
130
|
+
|
|
90
131
|
ax.legend(labels =new_labels,
|
|
91
132
|
handles=new_handles,
|
|
92
133
|
loc="upper right",
|
|
93
134
|
bbox_to_anchor=(0.995, 0.995),
|
|
94
135
|
ncol=1,
|
|
95
|
-
|
|
136
|
+
markerfirst=False,
|
|
137
|
+
scatterpoints=1,
|
|
96
138
|
title=legend_title,
|
|
97
|
-
|
|
139
|
+
title_fontproperties={"size":fontsize,"family":font_family},
|
|
140
|
+
prop={"size":fontsize,"family":font_family},
|
|
141
|
+
frameon=False)
|
|
98
142
|
|
|
99
143
|
return fig, log
|
gwaslab/viz_plot_effect.py
CHANGED
|
@@ -86,6 +86,8 @@ def _plot_effect(to_plot,
|
|
|
86
86
|
verbose=True,
|
|
87
87
|
legend_mode=1,
|
|
88
88
|
ncol=2,
|
|
89
|
+
fontsize=12,
|
|
90
|
+
font_family="Arial",
|
|
89
91
|
size=None,
|
|
90
92
|
hue=None,
|
|
91
93
|
style=None,
|
|
@@ -188,26 +190,28 @@ def _plot_effect(to_plot,
|
|
|
188
190
|
**err_kwargs)
|
|
189
191
|
|
|
190
192
|
ax1.axvline(x=0,linestyle="dashed",c="grey")
|
|
191
|
-
ax1.set_yticks(to_plot[y], labels = to_plot[y_name])
|
|
192
|
-
ax1.set_ylabel(ylabel)
|
|
193
|
+
ax1.set_yticks(to_plot[y], labels = to_plot[y_name], fontsize=fontsize, family=font_family)
|
|
194
|
+
ax1.set_ylabel(ylabel, fontsize=fontsize, family=font_family)
|
|
193
195
|
|
|
194
196
|
if title is not None:
|
|
195
|
-
ax1.set_title(title)
|
|
197
|
+
ax1.set_title(title,fontsize=fontsize, family=font_family)
|
|
196
198
|
|
|
197
199
|
if eaf_panel==True:
|
|
198
200
|
ax2.barh(y=to_plot[y], width=to_plot[eaf], zorder=100, **eaf_args)
|
|
199
|
-
ax2.set_xlabel(eaf)
|
|
201
|
+
ax2.set_xlabel(eaf, fontsize=fontsize, family=font_family)
|
|
200
202
|
|
|
201
203
|
if snpvar_panel==True:
|
|
202
204
|
ax3.barh(y=to_plot[y], width=to_plot[snpr2], zorder=100,**snpr2_args)
|
|
203
|
-
ax3.set_xlabel(snpr2)
|
|
205
|
+
ax3.set_xlabel(snpr2, fontsize=fontsize, family=font_family)
|
|
204
206
|
|
|
205
207
|
#try:
|
|
206
208
|
if legend_mode==1:
|
|
207
209
|
#if ncols==1:
|
|
208
210
|
sns.move_legend(
|
|
209
211
|
ax1, "upper left",
|
|
210
|
-
bbox_to_anchor=(1, 1), title=None, frameon=False, bbox_transform = axes[-1].transAxes
|
|
212
|
+
bbox_to_anchor=(1, 1), title=None, frameon=False, bbox_transform = axes[-1].transAxes,
|
|
213
|
+
title_fontproperties={"size":fontsize,"family":font_family},
|
|
214
|
+
prop={"size":fontsize,"family":font_family}
|
|
211
215
|
)
|
|
212
216
|
#else:
|
|
213
217
|
##
|
|
@@ -269,15 +273,21 @@ def _plot_effect(to_plot,
|
|
|
269
273
|
# for legend_row in legend_rows[:-1]:
|
|
270
274
|
# ax1.add_artist(legend_row)
|
|
271
275
|
|
|
272
|
-
|
|
273
|
-
|
|
274
276
|
if effect_label is not None:
|
|
275
|
-
ax1.set_xlabel(effect_label)
|
|
277
|
+
ax1.set_xlabel(effect_label, fontsize=fontsize, family=font_family)
|
|
278
|
+
ax1.tick_params(axis='x',
|
|
279
|
+
labelsize=fontsize,
|
|
280
|
+
labelfontfamily=font_family)
|
|
276
281
|
if eaf_label is not None:
|
|
277
|
-
ax2.set_xlabel(eaf_label)
|
|
282
|
+
ax2.set_xlabel(eaf_label, fontsize=fontsize, family=font_family)
|
|
283
|
+
ax2.tick_params(axis='x',
|
|
284
|
+
labelsize=fontsize,
|
|
285
|
+
labelfontfamily=font_family)
|
|
278
286
|
if snpr2_label is not None:
|
|
279
|
-
ax3.set_xlabel(snpr2_label)
|
|
280
|
-
|
|
287
|
+
ax3.set_xlabel(snpr2_label, fontsize=fontsize, family=font_family)
|
|
288
|
+
ax3.tick_params(axis='x',
|
|
289
|
+
labelsize=fontsize,
|
|
290
|
+
labelfontfamily=font_family)
|
|
281
291
|
save_figure(fig, save, keyword="forest",save_args=save_kwargs, log=log, verbose=verbose)
|
|
282
292
|
|
|
283
293
|
return fig
|
gwaslab/viz_plot_miamiplot2.py
CHANGED
|
@@ -301,6 +301,7 @@ def plot_miami2(
|
|
|
301
301
|
ax5l, ax5r = ax1.get_xlim()
|
|
302
302
|
ax1.set_xlim([min(ax1l,ax5l), max(ax1r,ax5r)])
|
|
303
303
|
ax5.set_xlim([min(ax1l,ax5l), max(ax1r,ax5r)])
|
|
304
|
+
|
|
304
305
|
#####################################################################################################################
|
|
305
306
|
ax5.set_xlabel("")
|
|
306
307
|
#ax5.set_xticks(chrom_df)
|
|
@@ -317,8 +318,8 @@ def plot_miami2(
|
|
|
317
318
|
|
|
318
319
|
ax1.tick_params(axis='x', which='major', pad=xtick_label_pad)
|
|
319
320
|
|
|
320
|
-
ax1.set_ylabel("
|
|
321
|
-
ax5.set_ylabel("
|
|
321
|
+
ax1.set_ylabel("$\mathregular{-log_{10}(P)}$",fontsize=fontsize,family=font_family)
|
|
322
|
+
ax5.set_ylabel("$\mathregular{-log_{10}(P)}$",fontsize=fontsize,family=font_family)
|
|
322
323
|
|
|
323
324
|
ax1.set_title(titles[0],y=titles_pad_adjusted[0],family=font_family)
|
|
324
325
|
ax5.set_title(titles[1],y=titles_pad_adjusted[1],family=font_family)
|