From b8e6e80d8157552f4bd468bef7c690c969881e9b Mon Sep 17 00:00:00 2001 From: Bohung Date: Wed, 26 Jan 2022 19:19:28 +0800 Subject: [PATCH] Update to version2.(Fix all known bugs.) --- app/assets/javascripts/cancer_predict.js | 317 ++++++------- app/assets/stylesheets/cancer_predict.scss | 6 +- .../stylesheets/cancer_predict_print.scss | 99 ++-- .../admin/cancerpredicts_controller.rb | 211 +++++---- app/controllers/cancerpredicts_controller.rb | 91 ++-- app/models/cancerpredictfields.rb | 425 ++++++++++++------ .../_export_cancer_tool_record.xlsx.axlsx | 5 +- app/views/admin/cancerpredicts/_form.html.erb | 30 +- app/views/admin/cancerpredicts/index.html.erb | 148 +++--- .../admin/cancerpredicts/showSubmit.html.erb | 2 +- cancerpredict.gemspec | 63 +-- config/locales/en.yml | 10 +- config/locales/zh_tw.yml | 14 +- config/routes.rb | 1 + .../cancer_predict_index.html.erb | 4 +- modules/cancerpredict/info.json | 8 +- 16 files changed, 815 insertions(+), 619 deletions(-) diff --git a/app/assets/javascripts/cancer_predict.js b/app/assets/javascripts/cancer_predict.js index 3026a19..ba5dc75 100644 --- a/app/assets/javascripts/cancer_predict.js +++ b/app/assets/javascripts/cancer_predict.js @@ -6,18 +6,25 @@ Array.prototype.get_nearest_value = function(goal){ } function change_object_variables(obj1,obj2,operator="-",target="new"){ var obj_new = {}; - Object.keys(function(k){ - if(operator == "-"){ + var obj_keys = Object.keys(obj1); + obj_keys.forEach(function(k){ + if(obj2[k] == undefined){ if( target == "new"){ - obj_new[k] = obj1[k] - obj2[k]; - }else{ - obj1[k] = obj1[k] - obj2[k]; + obj_new[k] = obj1[k]; } - }else if(operator == "+"){ - if( target == "new"){ - obj_new[k] = obj1[k] + obj2[k]; - }else{ - obj1[k] = obj1[k] + obj2[k]; + }else{ + if(operator == "-"){ + if( target == "new"){ + obj_new[k] = obj1[k] - obj2[k]; + }else{ + obj1[k] = obj1[k] - obj2[k]; + } + }else if(operator == "+"){ + if( target == "new"){ + obj_new[k] = obj1[k] + obj2[k]; + }else{ + obj1[k] = obj1[k] + obj2[k]; + } } } }) @@ -315,13 +322,22 @@ $(document).ready(function(){ $('#hormone_therapy .cancer_table_btn').removeAttr('disabled'); $('[for="hormone_therapy"]').css('color',''); }; - if(post_json["HER2_status"] != 1){ - $('#Targeted_therapy .cancer_table_btn').attr('disabled','disabled'); - $('[for="Targeted_therapy"]').css('color','rgb(204, 204, 204)'); - }else{ - $('#Targeted_therapy .cancer_table_btn').removeAttr('disabled'); - $('[for="Targeted_therapy"]').css('color',''); - }; + /*disable_condition start*/ + if(post_json["ER_status"] == 2 && post_json["PR_status"] == 2){ + $('#hormone_therapy .cancer_table_btn').attr('disabled','disabled'); + $('[for="hormone_therapy"]').css('color','rgb(204, 204, 204)'); + }else{ + $('#hormone_therapy .cancer_table_btn').removeAttr('disabled'); + $('[for="hormone_therapy"]').css('color',''); + } + if(post_json["HER2_status"] != 1){ + $('#Targeted_therapy .cancer_table_btn').attr('disabled','disabled'); + $('[for="Targeted_therapy"]').css('color','rgb(204, 204, 204)'); + }else{ + $('#Targeted_therapy .cancer_table_btn').removeAttr('disabled'); + $('[for="Targeted_therapy"]').css('color',''); + } + /*disable_condition end*/ return post_json; }else{ return null; @@ -374,23 +390,28 @@ $(document).ready(function(){ $('#cancer_table_right_result .cancer-btn-group').eq(i).find('.cancer_table_btn').eq(0).addClass('active'); $('#cancer_table_right_result .cancer-btn-group').eq(i).find('>input').eq(0).attr('value',"1"); }; - var treatmeny_method = result.responseJSON.treatmeny_method; - $('tr.'+treatmeny_method[0]).addClass('tr_show') - var lpv = [0,-0.8397,-0.4147,-0.3203,-0.4687]; + var treatment_method = result.responseJSON.treatment_method; + var treatment_method_active_indices = result.responseJSON.treatment_method_active_indices; + $('tr.'+treatment_method[0]).addClass('tr_show'); var servive_ratio_arr = [result.responseJSON.servive_ratio] var yes = (I18n.locale=="zh_tw") ? "是" : "yes"; var year = $('#current_year').attr('value'); var active_treatment = ['Surgery_only']; $('tr.'+active_treatment[0]+' .Overall_Survival').html(servive_ratio_arr[0]+'%'); + $('span.'+active_treatment[0]+'.Overall_Survival').html(Math.round(servive_ratio_arr[0])); $('#cancer_predict_result_block').css('display','block'); var lpv_real = [result.responseJSON['lpv_variable']]; - var lpv_dict={} - var lpv_calc=/*lpv_calc_formula_start*/{"1":"0.8095037**( Math.exp(lpv_current) )","1.5":"0.729158**( Math.exp(lpv_current) )","2":"0.6717211**( Math.exp(lpv_current) )","2.5":"0.6056773**( Math.exp(lpv_current) )"}/*lpv_calc_formula_end*/ + var lpv = /*therapy_lpv start*/[0, -0.8397, -0.4147, -0.3203, -0.4687];/*therapy_lpv end*/; + var lpv_dict={}; + var lpv_calc=/*lpv_calc_formula_start*/{"1":"Math.exp(-0.001476145)**( Math.exp(lpv_current) )","3":"Math.exp(-0.01261639)**( Math.exp(lpv_current) )","5":"Math.exp(-0.02519608)**( Math.exp(lpv_current) )"};/*lpv_calc_formula_end*/ active_treatment.push = function() { if(arguments.length == 1){ var year = $('#current_year').attr('value'); - var lpv_current = change_object_variables(lpv_real[lpv_real.length-1],lpv_dict[arguments[0]],'+'); + console.log(lpv_real); + console.log(lpv_dict[arguments[0]]) + var lpv_current = change_object_variables(lpv_real[lpv_real.length-1],{"lpv": lpv_dict[arguments[0]]},'+'); lpv_real.push(lpv_current); + lpv_current = lpv_current['lpv']; var servive_ratio = round((1 - eval(lpv_calc[year]))*100,2); var benefit = servive_ratio - servive_ratio_arr[servive_ratio_arr.length - 1]; servive_ratio_arr.push(servive_ratio); @@ -433,9 +454,10 @@ $(document).ready(function(){ var year = $('#current_year').attr('value'); if(index < this.length - 1){ for(var i = index + 1;i < this.length; i++){ - change_object_variables(lpv_real[i] , lpv_dict[arguments[0]] , '-' , 'self'); + change_object_variables(lpv_real[i] , {"lpv": lpv_dict[arguments[0]]} , '-' , 'self'); var lpv_current = lpv_real[i]; - var servive_ratio = round(eval(lpv_calc[year])*100,2); + lpv_current = lpv_current['lpv']; + var servive_ratio = round((1 - eval(lpv_calc[year]))*100,2); servive_ratio_arr[i] = servive_ratio; var benefit = servive_ratio - ((i == index+1) ? servive_ratio_arr[index - 1] : servive_ratio_arr[i - 1]); $('tr.'+active_treatment[i]+' td.Overall_Survival').html(servive_ratio+'%'); @@ -471,39 +493,15 @@ $(document).ready(function(){ $('.addition').css('display','none'); $('#result_text_content .extra-text').css('display','none'); }; - console.log(this) return Array.prototype.remove_item_from_array.apply(this, arguments); }else{ - console.log(this) return Array.prototype.remove_item_from_array.apply(this, arguments); }; }; - for(var i = 0;iinput').attr('value',0); - $(this).parent().find('>input').eq(index).attr('value',1); - $(this).parent().find('>button').removeClass('active'); - $(this).parent().removeClass('cancertable_empty'); - if($('.cancertable_empty').length == 0){ - $('#danger_texts').remove(); - }; - }catch(e){}; - $(this).addClass('active'); - if(!click_flag){ - if(!active_treatment.includes($(this).parent().attr('id'))){ - click_flag = true; - active_treatment.push($(this).parent().attr('id')); - click_flag = false; - }; - } - }); - $('#'+treatmeny_method[i]+' .cancer_table_btn').eq(0).off('click'); - $('#'+treatmeny_method[i]+' .cancer_table_btn').eq(0).click(function(){ + $('#'+treatment_method[i]+' .cancer_table_btn').off('click').click(function(){ var index = $(this).index()/2; try{ $(this).parent().find('>input').attr('value',0); @@ -523,6 +521,26 @@ $(document).ready(function(){ }; }; }); + $('#'+treatment_method[i]+' .cancer_table_btn').eq(treatment_method_active_indices[i]).off('click').click(function(){ + var index = $(this).index()/2; + try{ + $(this).parent().find('>input').attr('value',0); + $(this).parent().find('>input').eq(index).attr('value',1); + $(this).parent().find('>button').removeClass('active'); + $(this).parent().removeClass('cancertable_empty'); + if($('.cancertable_empty').length == 0){ + $('#danger_texts').remove(); + }; + }catch(e){}; + $(this).addClass('active'); + if(!click_flag){ + if(!active_treatment.includes($(this).parent().attr('id'))){ + click_flag = true; + active_treatment.push($(this).parent().attr('id')); + click_flag = false; + }; + } + }); }; $('#current_year').change(function(){ year = $(this).attr('value'); @@ -592,134 +610,82 @@ $(document).ready(function(){ }; }; /* auto add start */ -function calculate_first_lpv(result_json){ + function calculate_first_lpv(result_json){ result = {}; var map_values , mapping_hash , temp_index ,temp_value , index , closest_value; - result['sex_value'] = (2 - Number(result_json['sex_value'])); - result['age'] = Number(result_json['age']); - mapping_hash = mapping_data_from_csv['age']; - temp_index = 0; - temp_value = result[age]; - index = 0; - $.each(mapping_hash,function(k,v){ - if( i == 0 ){ - var index_val = v.indexOf(temp_value); - if( index_val != -1 ){ - temp_index = index_val; - }else{ - closest_value = v.get_nearest_value(temp_value); - temp_index = v.indexOf(closest_value) - } - } - result[k] = v[temp_index]; - index++; - }); - result['calH'] = Number(result_json['calH']); - mapping_hash = mapping_data_from_csv['calH']; - temp_index = 0; - temp_value = result[calH]; - index = 0; - $.each(mapping_hash,function(k,v){ - if( i == 0 ){ - var index_val = v.indexOf(temp_value); - if( index_val != -1 ){ - temp_index = index_val; - }else{ - closest_value = v.get_nearest_value(temp_value); - temp_index = v.indexOf(closest_value) - } - } - result[k] = v[temp_index]; - index++; - }); - result['calAH'] = Number(result_json['calAH']); - mapping_hash = mapping_data_from_csv['calAH']; - temp_index = 0; - temp_value = result[calAH]; - index = 0; - $.each(mapping_hash,function(k,v){ - if( i == 0 ){ - var index_val = v.indexOf(temp_value); - if( index_val != -1 ){ - temp_index = index_val; - }else{ - closest_value = v.get_nearest_value(temp_value); - temp_index = v.indexOf(closest_value) - } - } - result[k] = v[temp_index]; - index++; - }); - result['calDH'] = Number(result_json['calDH']); - mapping_hash = mapping_data_from_csv['calDH']; - temp_index = 0; - temp_value = result[calDH]; - index = 0; - $.each(mapping_hash,function(k,v){ - if( i == 0 ){ - var index_val = v.indexOf(temp_value); - if( index_val != -1 ){ - temp_index = index_val; - }else{ - closest_value = v.get_nearest_value(temp_value); - temp_index = v.indexOf(closest_value) - } - } - result[k] = v[temp_index]; - index++; - }); - result['fat'] = Number(result_json['fat']); - mapping_hash = mapping_data_from_csv['fat']; - temp_index = 0; - temp_value = result[fat]; - index = 0; - $.each(mapping_hash,function(k,v){ - if( i == 0 ){ - var index_val = v.indexOf(temp_value); - if( index_val != -1 ){ - temp_index = index_val; - }else{ - closest_value = v.get_nearest_value(temp_value); - temp_index = v.indexOf(closest_value) - } - } - result[k] = v[temp_index]; - index++; - }); - result['N4'] = (2 - Number(result_json['N4'])); - result['N12'] = (2 - Number(result_json['N12'])); - result['N20'] = (2 - Number(result_json['N20'])); - result['N31'] = (2 - Number(result_json['N31'])); - result['O6'] = (2 - Number(result_json['O6'])); - result['N34'] = (2 - Number(result_json['N34'])); - result['N14'] = (2 - Number(result_json['N14'])); - result['N26'] = (2 - Number(result_json['N26'])); - result['O3'] = (2 - Number(result_json['O3'])); - result['O20'] = (2 - Number(result_json['O20'])); - result['O18'] = (2 - Number(result_json['O18'])); - result['O11'] = (2 - Number(result_json['O11'])); - result['N29'] = (2 - Number(result_json['N29'])); - result['N6'] = (2 - Number(result_json['N6'])); - result['O14'] = (2 - Number(result_json['O14'])); - result['N43'] = (2 - Number(result_json['N43'])); - result['O17'] = (2 - Number(result_json['O17'])); - result['O9'] = (2 - Number(result_json['O9'])); + result['age'] = Number(result_json['age']); + result['size'] = Number(result_json['size']); + result['lymph_nodes_examined'] = Number(result_json['lymph_nodes_examined']); + result['lymph_nodes_positive'] = Number(result_json['lymph_nodes_positive']); + result['grade'] = Number(result_json['grade']); + result['ER_status'] = Number(result_json['ER_status']); + result['PR_status'] = Number(result_json['PR_status']); + result['HER2_status'] = Number(result_json['HER2_status']); + result['Distant_Metastasis'] = Number(result_json['Distant_Metastasis']); + result['micrometastasis'] = Number(result_json['micrometastasis']); + result['tumor_direct_extension'] = Number(result_json['tumor_direct_extension']); + result['lvi'] = Number(result_json['lvi']); + result['hormone_therapy'] = Number(result_json['hormone_therapy']); + result['Chemotherapy'] = Number(result_json['Chemotherapy']); + result['Radiotherapy'] = Number(result_json['Radiotherapy']); + result['Targeted_therapy'] = Number(result_json['Targeted_therapy']); + Object.keys(result).forEach(function(k){ + if(Number.isNaN(result[k])){ + result[k] = 0; + } + }) + age1 = (result["age"] / 100.0) ** (0.5); + age2 = age1 * Math.log(result["age"] / 100.0); + size1 = Math.log(result["size"] / 10.0); + ratio = (result["lymph_nodes_examined"] == 0 ? 0 : (1.0 * result["lymph_nodes_positive"] / result["lymph_nodes_examined"])); + ratio = (ratio > 1 ? 1 : ratio); + T4 = (result["tumor_direct_extension"] == 1); + T1 = !T4 && (result["size"] <= 20); + T2 = !T4 && !T1 && (result["size"] > 20 && result["size"] <= 50); + T = (T4 ? 'T4' : (T1 ? 'T1' : (T2 ? 'T2' : 'T3'))); + N0 = (result["lymph_nodes_positive"] == 0); + N1_or_N1mi = !N0 && (result["lymph_nodes_positive"] >= 1 && result["lymph_nodes_positive"] <= 3); + N1 = N1_or_N1mi && result["micrometastasis"] != 1; + N1mi = N1_or_N1mi && result["micrometastasis"] == 1; + N2 = !N0 && !N1_or_N1mi && (result["lymph_nodes_positive"] <= 9); + N = (N0 ? 'N0' : (N1 ? 'N1' : (N1mi ? 'N1mi' : (N2 ? 'N2' : 'N3')))); + M = (result["Distant_Metastasis"] != 1) ? 'M0' : 'M1'; + pstage = (M == 'M1' ? 4 : ((T == 'T1' && (N == 'N0' || N == 'N1mi')) ? 1 : (((T == 'T2' || T == 'T3') && (N == 'N0')) || ((T == 'T1' || T == 'T2') && (N == 'N1')) ? 2 : 3)) ); + nposit = ((ratio + 0.1) / 0.1) ** 0.5; + grade_2 = (result["grade"] == 2 || result["grade"] == 4) ? 1 : 0; + grade_3 = (result["grade"] == 3) ? 1 : 0; + subtype_1 = (result["ER_status"] != 2 || result["PR_status"] != 2) && (result["HER2_status"] != 1); + subtype_2 = !subtype_1 && (result["HER2_status"] == 1); + subtype_3 = !subtype_1 && !subtype_2 && (result["ER_status"] == 2 && result["PR_status"] == 2 && result["HER2_status"] != 1); + subtype_HER2 = subtype_2 ? 1 : 0; + subtype_triple = subtype_3 ? 1 : 0; + pstage_2 = (pstage == 2) ? 1 : 0; + pstage_3 = (pstage == 3) ? 1 : 0; + pstage_4 = (pstage == 4) ? 1 : 0; + lvi_yes = (result["lvi"] == 1) ? 1 : 0; + chemo = (result["Chemotherapy"] == 2) ? 1 : 0; + radio = (result["Radiotherapy"] == 2) ? 1 : 0; + hormone = (result["hormone_therapy"] == 2) ? 1 : 0; + target = (result["Targeted_therapy"] == 2) ? 1 : 0; try{ - result['lpv'] = (A = 0.1327868* (result["sex_value"]- 0.4858824) + 0.0371720* (result["age_test1"] - 61.56000) -0.07447278* (result["age_test2"] - 13.10152) + 0.4315686* (result["age_test3"] - 0.9844332) + 0.0009163615*( result["calH_test1"] - 182.9347) -0.0007536899*( result["calH_test2"] - 124.8706) -0.00004697183*( result["calH_test3"] -80.75636) + 0.0001401325*( result["calAH_test1"] - 700.7824) -0.001349783*( result["calAH_test2"] - 634.2167) +0.001753832*( result["calAH_test3"] -419.3361) + 0.0001906046*( result["calDH_test1"] -835.2894) -0.000251567*( result["calDH_test2"] - 213.1630) -0.002173942*( result["fat_test1"] -108.4149)+0.003066541*( result["fat_test2"] - 28.33497) +0.6700708*(result["N4"]-0.3241176) +0.3336162*(result["O3"]-0.4994118) +0.1322476*(result["O20"]-0.1741176) +0.9084972*(result["O18"]-0.008823529) +0.2978388*(result["N12"]-0.1152941) +0.1777935*(result["N20"]-0.3582353) +1.588042*(result["N31"]-0.002352941) +0.2197419*(result["O6"]-0.07823529) +1.791159*(result["N34"]-0.001176471) +0.4305973*(result["N14"]-0.02176471) -0.4472885*(result["N29"]-0.02411765) +0.2601319*(result["N26"]-0.04941176) -0.2364269*(result["O11"]-0.1164706) +0.1784179*(result["N6"]-0.1070588) +0.6023170*(result["O14"]-0.01294118) -1.031959*(result["N43"]-0.007058824) +0.4257809*(result["O17"]-0.01823529) +0.2002546*(result["O9"]-0.06176471)); - }catch(e){result['lpv'] = "error"}; - console.log(result['lpv']); - result['lpv_variable']['A'] = A; + lpv = ((age1-0.7276655)*(-10.87)+(age2+0.4540707)*8.968+(size1-0.643632)*0.7678+(nposit-1.346932)*0.5339+ grade_2*0.4795+grade_3*0.818+subtype_HER2*0.1806+subtype_triple*0.6457+pstage_2*0.5311+ pstage_3*1.134+pstage_4*2.172+lvi_yes*0.3321-0.04+chemo*(-0.4147)+radio*(-0.3203)+hormone*(-0.8397)+target*(-0.4687) + ) + }catch(e){console.log(e)}; + result['lpv_variable'] = {}; + result['lpv_variable']['lpv'] = lpv; + result['lpv'] = lpv; + result['lpv_variable']['lpv'] = result['lpv']; return result; }; function calculate_and_change_result_value(obj){ obj.servive_ratio_arr = []; for(var i = 0;i a{ - writing-mode: vertical-lr; - -webkit-writing-mode: vertical-lr; - color: white; + writing-mode: vertical-lr !important; + -webkit-writing-mode: vertical-lr !important; + color: white !important; } .result_tab_group{ - width: 15%; - margin: 0; - float: left; + display: none; } .result_content_group{ - width: 85%; + width: 100%; margin: 0; - float: right; + float: none; } .result_content{ - display: none; + display: block; min-height: 25em; - border: 0.125em solid #c0cbdd; + border: 0.125em solid #c0cbdd !important; padding: 0.5em; } .result_content:first-of-type{ @@ -315,13 +322,13 @@ input.float_num{ color:white; } .cancer_th{ - color: white; - background-color: #003d79; + color: white !important; + background-color: #003d79 !important; border-right: 0.375em solid white; border-top: 0.375em solid white; } .cancer_td { - background-color: #e9eaf5; + background-color: #e9eaf5 !important; border-right: 0.375em solid white; border-top: 0.375em solid white; } @@ -362,30 +369,32 @@ div.texts_show{ width: 80%; } #cancer_table_right{ -float:right; -width:50%; + float:right; + width:50%; } #cancer_table_left{ -float:left; -width:50%; + float:left; + width:50%; } #cancer_table_right_result{ -width: 50%; -float: right; + width: 50%; + float: right; } #cancer_table_left_result{ -width: 50%; -float: left; + width: 50%; + float: left; } #cancer_predict_result{ -width: 50%; -float: left; + width: 50%; + float: left; } .result_title{ -margin-top: 1em; + margin-top: 1em; +} +* { + -webkit-print-color-adjust: exact !important; +} +.layout-content{ + background: #fff !important; } -@media print { - * { - -webkit-print-color-adjust: exact !important; - } } \ No newline at end of file diff --git a/app/controllers/admin/cancerpredicts_controller.rb b/app/controllers/admin/cancerpredicts_controller.rb index c459150..d3f2a46 100644 --- a/app/controllers/admin/cancerpredicts_controller.rb +++ b/app/controllers/admin/cancerpredicts_controller.rb @@ -27,11 +27,11 @@ class Admin::CancerpredictsController < OrbitAdminController @title_images_id.each{|image_id| @title_images.push Headimages.find_by(:id=>image_id.to_s)} rescue nil @head_new_image = Headimages.new(:cancerpredictfields_id => @form_to_show.id) end - def edit - other_in_use_locales = Site.first.in_use_locales.map{|l| l.to_s} - other_in_use_locales.delete(params[:locale]) - if !(params["cancerpredictfields"].nil?) - org_nums = @form_to_show.form_show_was.keys + def edit + other_in_use_locales = Site.first.in_use_locales.map{|l| l.to_s} + other_in_use_locales.delete(params[:locale]) + if !(params["cancerpredictfields"].nil?) + org_nums = @form_to_show.form_show_was.keys remain_org_nums = params["cancerpredictfields"]["form_show"].values.map{|property| property["old_num"]}.select{|n| n.present?} delete_nums = org_nums - remain_org_nums if !delete_nums.blank? @@ -59,41 +59,57 @@ class Admin::CancerpredictsController < OrbitAdminController end next if key.include?("_file") if (key != "old_num") - if value != "0" && value != "1" - if key != params[:locale] - @form_to_show.form_show[num.to_s] = {} if @form_to_show.form_show[num.to_s].nil? - type = Cancerpredictfields::FIELDINFO[key.to_s].constantize rescue String - if @form_to_show.form_show[num.to_s][key.to_s].class != Array && type != Array - @form_to_show.form_show[num.to_s][key.to_s] = value + if key != params[:locale] + @form_to_show.form_show[num.to_s] = {} if @form_to_show.form_show[num.to_s].nil? + type = Cancerpredictfields::FIELDINFO[key.to_s] + if type && Cancerpredictfields::Field_relations[type] + type = Cancerpredictfields::Field_relations[type] + end + type = type.constantize rescue String + if @form_to_show.form_show[num.to_s][key.to_s].class != Array && type != Array + if type == Fixnum + @form_to_show.form_show[num.to_s][key.to_s] = value.to_i rescue 0 + elsif type == Float + @form_to_show.form_show[num.to_s][key.to_s] = value.to_f rescue 0.0 else - if value.length > 2 - @form_to_show.form_show[num.to_s][key.to_s] = YAML.load(value) - else - @form_to_show.form_show[num.to_s][key.to_s] = [] - end + @form_to_show.form_show[num.to_s][key.to_s] = value end else - value.each do |sub_property,sub_value| - type = Cancerpredictfields::FIELDINFO[sub_property.to_s].constantize rescue String - @form_to_show.form_show[ num.to_s ][ sub_property ] = {} if @form_to_show.form_show[num.to_s][ sub_property ].nil? - if @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s].class != Array && type != Array - @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value - else - if sub_value.length > 2 - @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = YAML.load(sub_value) - else - @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = [] - end - end - if(property["old_num"].present? && property["old_num"] != num.to_s) - other_in_use_locales.each do |locale| - @form_to_show.form_show[ num.to_s ][ sub_property ][locale] = @form_to_show.form_show_was[ property["old_num"] ][ sub_property ][locale] - end - end + if value.length > 2 + @form_to_show.form_show[num.to_s][key.to_s] = YAML.load(value) + else + @form_to_show.form_show[num.to_s][key.to_s] = [] end end else - @form_to_show.form_show[num.to_s][key.to_s] = value.to_i + value.each do |sub_property,sub_value| + type = Cancerpredictfields::FIELDINFO[sub_property.to_s] + if type && Cancerpredictfields::Field_relations[type] + type = Cancerpredictfields::Field_relations[type] + end + type = type.constantize rescue String + @form_to_show.form_show[ num.to_s ][ sub_property ] = {} if @form_to_show.form_show[num.to_s][ sub_property ].nil? + if @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s].class != Array && type != Array + if type == Fixnum + @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value.to_i rescue 0 + elsif type == Float + @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value.to_f rescue 0.0 + else + @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value + end + else + if sub_value.length > 2 + @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = YAML.load(sub_value) + else + @form_to_show.form_show[ num.to_s ][ sub_property ][params[:locale].to_s] = [] + end + end + if(property["old_num"] != nil && property["old_num"] != num.to_s) + other_in_use_locales.each do |locale| + @form_to_show.form_show[ num.to_s ][ sub_property ][locale] = @form_to_show.form_show_was[ property["old_num"] ][ sub_property ][locale] + end + end + end end end end @@ -128,42 +144,62 @@ class Admin::CancerpredictsController < OrbitAdminController if value[:_destroy] == "1" mapping_file = CancerPredictMappingFile.find(value[:id]) mapping_file.destroy - @form_to_show.form_show[num.to_s][key.to_s] = "" + @form_to_show.form_show_in_result[num.to_s][key.to_s] = "" end end next if key.include?("_file") if (key != "old_num") - if value != "0" && value != "1" - if key != params[:locale] - if @form_to_show.form_show_in_result[num.to_s][key.to_s].class != Array - @form_to_show.form_show_in_result[num.to_s][key.to_s] = value + if key != params[:locale] + @form_to_show.form_show_in_result[num.to_s] = {} if @form_to_show.form_show_in_result[num.to_s].nil? + type = Cancerpredictfields::FIELDINFO[key.to_s] + if type && Cancerpredictfields::Field_relations[type] + type = Cancerpredictfields::Field_relations[type] + end + type = type.constantize rescue String + if @form_to_show.form_show_in_result[num.to_s][key.to_s].class != Array && type != Array + if type == Fixnum + @form_to_show.form_show_in_result[num.to_s][key.to_s] = value.to_i rescue 0 + elsif type == Float + @form_to_show.form_show_in_result[num.to_s][key.to_s] = value.to_f rescue 0.0 else - if value.length > 2 - @form_to_show.form_show_in_result[num.to_s][key.to_s] = YAML.load(value) - else - @form_to_show.form_show_in_result[num.to_s][key.to_s] = [] - end + @form_to_show.form_show_in_result[num.to_s][key.to_s] = value end else - value.each do |sub_property,sub_value| - if @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s].class != Array - @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value - else - if sub_value.length > 2 - @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = YAML.load(sub_value) - else - @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = [] - end - end - if(property["old_num"] != nil && property["old_num"] != num.to_s) - other_in_use_locales.each do |locale| - @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][locale] = @form_to_show.form_show_in_result_was[ property["old_num"] ][ sub_property ][locale] - end - end + if value.length > 2 + @form_to_show.form_show_in_result[num.to_s][key.to_s] = YAML.load(value) + else + @form_to_show.form_show_in_result[num.to_s][key.to_s] = [] end end else - @form_to_show.form_show_in_result[num.to_s][key.to_s] = value.to_i + value.each do |sub_property,sub_value| + type = Cancerpredictfields::FIELDINFO[sub_property.to_s] + if type && Cancerpredictfields::Field_relations[type] + type = Cancerpredictfields::Field_relations[type] + end + type = type.constantize rescue String + @form_to_show.form_show_in_result[ num.to_s ][ sub_property ] = {} if @form_to_show.form_show[num.to_s][ sub_property ].nil? + if @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s].class != Array && type != Array + if type == Fixnum + @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value.to_i rescue 0 + elsif type == Float + @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value.to_f rescue 0.0 + else + @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = sub_value + end + else + if sub_value.length > 2 + @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = YAML.load(sub_value) + else + @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][params[:locale].to_s] = [] + end + end + if(property["old_num"] != nil && property["old_num"] != num.to_s) + other_in_use_locales.each do |locale| + @form_to_show.form_show_in_result[ num.to_s ][ sub_property ][locale] = @form_to_show.form_show_was[ property["old_num"] ][ sub_property ][locale] + end + end + end end end end @@ -175,7 +211,7 @@ class Admin::CancerpredictsController < OrbitAdminController end end end - @create_items = ['title_texts','form_result_is_right','text_descibe','years','table_above_texts','text_above_texts','surgery_only_texts','extra_texts','extra_therapy_texts','danger_texts','texts_between_Result_and_result_block','prediction_formula'] + @create_items = ['title_texts','form_result_is_right','text_descibe','years','table_above_texts','text_above_texts','surgery_only_texts','extra_texts','extra_therapy_texts','danger_texts','texts_between_Result_and_result_block','prediction_formula','hidden_variables','advance_mode'] params_cancer = params.require("cancerpredictfields").permit! @create_items.each do |item| if (@form_to_show[item].class == BSON::Document) || (@form_to_show.send(item).class == Hash) @@ -269,7 +305,7 @@ class Admin::CancerpredictsController < OrbitAdminController Headimages.find_by(:id => @image_id ).destroy rescue next @form_to_show.title_images_id.delete(@image_id) end - file_ids = @form_to_show.form_show.values.map{|property| [property[:variable],property[:cancer_predict_mapping_file]]}.select{|k,f| f.present?}.to_h + file_ids = (@form_to_show.form_show.values + @form_to_show.form_show_in_result.values).map{|property| [property[:variable],property[:cancer_predict_mapping_file]]}.select{|k,f| f.present?}.to_h mapping_data_from_csv = {} if !file_ids.blank? file_ids.each do |k,v| @@ -342,14 +378,14 @@ class Admin::CancerpredictsController < OrbitAdminController @table_str_left += '' - if @field_property["comment_text"] != "" + if @field_property["comment_text"].present? @table_str_left += '' @table_str_left += '' else @site_locales = current_site.in_use_locales @site_locales.delete(current_locale) @site_locales.each do |locale| - next if property["comment_text"][locale.to_s] == "" + next if property["comment_text"][locale.to_s].blank? @field_property["comment_text"] = property["comment_text"][locale.to_s] break end @@ -370,7 +406,6 @@ class Admin::CancerpredictsController < OrbitAdminController @table_str_left += '
' @table_str_left += '' @table_str_left += '' - @please_choice = (current_locale.to_s == "zh_tw") ? "請選擇" : "Please choice" @table_str_left += '' else @site_locales = current_site.in_use_locales @site_locales.delete(current_locale) @site_locales.each do |locale| - next if property["comment_text"][locale.to_s] == "" + next if property["comment_text"][locale.to_s].blank? @field_property["comment_text"] = property["comment_text"][locale.to_s] break end @@ -493,18 +528,18 @@ class Admin::CancerpredictsController < OrbitAdminController @table_result_choice_fileds += '' - if @field_property["comment_text"] != "" + if @field_property["comment_text"].present? @table_result_choice_fileds += '' @table_result_choice_fileds += '' else @site_locales = current_site.in_use_locales @site_locales.delete(current_locale) @site_locales.each do |locale| - next if property["comment_text"][locale.to_s] == "" + next if property["comment_text"][locale.to_s].blank? @field_property["comment_text"] = property["comment_text"][locale.to_s] break end - if @field_property["comment_text"] != "" + if @field_property["comment_text"].present? @table_result_choice_fileds += '' @table_result_choice_fileds += '' else @@ -587,7 +622,7 @@ class Admin::CancerpredictsController < OrbitAdminController @pagination = create_pagination(@page_num.to_i) end def export_cancer_tool_record - @cancer_records = Cancerpredictrecord.where("title"=>@app_title).asc(:id) + @cancer_records = Cancerpredictrecord.where("title"=>@app_title).desc(:id) dir_path = 'tmp/cancer_tool/' #FileUtils.rm_r(dir_path, :force => true) if Dir.exist?(dir_path) FileUtils.mkdir dir_path if !Dir.exist?(dir_path) #create dir for storing tmp_file if dir doesn't exist @@ -662,21 +697,21 @@ class Admin::CancerpredictsController < OrbitAdminController end pagination += (((page==all_page_num) ? '
  • ['+I18n.t('cancerpredict.next_page')+']
  • ' : '
  • ['+I18n.t('cancerpredict.next_page')+']
  • ')+'
    ') end - def read_mapping_file(mapping_file_id) - mapping_file = CancerPredictMappingFile.find(mapping_file_id) rescue nil - if !mapping_file.nil? - csv_rows = CSV.read(mapping_file.temp_file.file.path) - titles = csv_rows[0] - infos = {} - titles.each_with_index do |title,i| - infos[title] = [] - csv_rows[1..-1].each do |row| - infos[title] << row[i].to_f - end - end - return infos - else - return {} - end - end + def read_mapping_file(mapping_file_id) + mapping_file = CancerPredictMappingFile.find(mapping_file_id) rescue nil + if !mapping_file.nil? + csv_rows = CSV.read(mapping_file.temp_file.file.path) + titles = csv_rows[0] + infos = {} + titles.each_with_index do |title,i| + infos[title] = [] + csv_rows[1..-1].each do |row| + infos[title] << row[i].to_f + end + end + return infos + else + return {} + end + end end \ No newline at end of file diff --git a/app/controllers/cancerpredicts_controller.rb b/app/controllers/cancerpredicts_controller.rb index de3ff70..b85d485 100644 --- a/app/controllers/cancerpredicts_controller.rb +++ b/app/controllers/cancerpredicts_controller.rb @@ -8,7 +8,6 @@ class CancerpredictsController < ApplicationController end def calculate create_first_field - #begin if params['header'].to_i == 1 locale = params['locale'].to_s rescue 'zh_tw' locale = 'zh_tw' if locale == 'zh_cn' @@ -41,7 +40,7 @@ class CancerpredictsController < ApplicationController @choice_values = [] @choice_names = [] @form_to_show.form_show.values.each{|choice| @choice_keys.push choice[:variable]} - @form_to_show.form_show.values.each{|choice| @choice_values.push choice[:choice_fields]} + @form_to_show.form_show.values.each{|choice| @choice_values.push ((choice[:is_num] == 1) ? [] : choice[:choice_fields])} @form_to_show.form_show.values.each{|choice| @choice_names.push choice[:name]} @choice_keys.each_with_index{|key,i| @record.names[key] = @choice_names[i]} @choice_keys.each_with_index{|key,i| @record.values[key] = @choice_values[i]} @@ -53,14 +52,10 @@ class CancerpredictsController < ApplicationController locale = params['data']['locale'].to_s rescue 'zh_tw' locale = 'zh_tw' if locale == 'zh_cn' result = {} - # result['sex_value'] = params['data']['sex'].to_i - 1 - # result['Age_value'] = params['data']['age'].to_i - # if params['data']['calcification_score'].to_i < 1400 - # result['cal_value'] = 0 - # else - # result['cal_value'] = 1 - # end mapping_data_from_csv = JSON.parse(@form_to_show.mapping_data_from_csv) rescue {} + @form_to_show.all_variables.each do |v| + result[v] = 0 + end @form_to_show.form_show.each do |num,property| @variable = property[:variable] if @variable.present? @@ -71,17 +66,21 @@ class CancerpredictsController < ApplicationController result[@variable] = params['data'][@variable].to_i rescue 0 end elsif property[:choice_fields].present? - if property[:map_values].class == Array && property[:choice_fields].class == Array && property[:map_values].length == property[:choice_fields].length - result[@variable] = property[:map_values][params['data'][@variable].to_i - 1] + if !(@form_to_show.advance_mode) + result[@variable] = params['data'][@variable].to_i rescue 0 else - if property[:revert_value].to_i != 1 - result[@variable] = params['data'][@variable].to_i - 1 + if property[:need_map_values] == 1 + result[@variable] = property[:map_values][params['data'][@variable].to_i - 1] else - result[@variable] = ((property[:choice_fields].length - params['data'][@variable].to_i) rescue params['data'][@variable].to_i) + if property[:revert_value] != 1 + result[@variable] = params['data'][@variable].to_i - 1 + else + result[@variable] = ((property[:choice_fields].length - params['data'][@variable].to_i) rescue params['data'][@variable].to_i) + end end end end - if property[:cancer_predict_mapping_file].present? + if @form_to_show.advance_mode && property[:cancer_predict_mapping_file].present? if (mapping_data_from_csv != {}) mapping_hash = mapping_data_from_csv[@variable] temp_index = 0 @@ -102,43 +101,32 @@ class CancerpredictsController < ApplicationController end end end - #result['lpv'] = -0.51427548* (result['sex_value']- 0.508312) + 0.05764604* (result['Age_value'] - 61.894501) + 0.49138819*(result['cal_value'] - 0.334399) rescue 'error' - formula_variables = @form_to_show.tmp_lpv_variables + formula_variables = @form_to_show.tmp_lpv_variables + begin + eval_hidden_variables(result) + rescue => e + @form_to_show.generate_eval_formula + eval_hidden_variables(result) + end begin eval_formula(result) rescue => e @form_to_show.generate_eval_formula eval_formula(result) end - result['lpv'] = instance_variable_get(formula_variables.last) + result['lpv'] = result[formula_variables.last] result['lpv_variable'] = {} formula_variables.each do |variable_name| - result['lpv_variable']["#{variable_name[1..-1]}"] = instance_variable_get(variable_name) + result['lpv_variable']["#{variable_name}"] = result[variable_name] end @years = @form_to_show.years - result['table'] = '

    '+@form_to_show.table_above_texts[locale].to_s+'

    ' - result['table'] += (''+(locale == 'zh_tw' ? '第' : '')+'') result['years'] = @years - @years.each{|year| result['table'] += ('')} - result['table'] += (''+(locale == 'zh_tw' ? '年' : '')+'') - #@head_name = ['Treatment','Additional_Benefit','Overall_Survival'] - @head_name = ['Treatment','Overall_Survival'] - @table_head = @head_name.map{|name| I18n.t('cancerpredict.table.'+name)} @therapy_choices = [I18n.t('cancerpredict.table.Surgeryonly')] @form_to_show.form_show_in_result.values.each{|choice| @therapy_choices.push choice["name"][locale]} - @therapy_names = ['Surgery_only'] - @form_to_show.form_show_in_result.values.each{|choice| @therapy_names.push choice["variable"]} - result['treatmeny_method'] = @therapy_names - result['table'] += '' - @table_head.each_with_index{|head,index| result['table'] += ('')} - result['table'] += '' - @therapy_choices.each_with_index do |choice,i| - result['table'] += '' - @table_head.each_with_index do |head,index| - result['table'] += ('') - end - result['table'] += '' - end + @therapy_names = @form_to_show.treatment_method + result['treatment_method'] = @therapy_names + result['treatment_method_active_indices'] = @form_to_show.treatment_method_active_indices + result['table'] = @form_to_show.result_table_translations[locale] year = params['data']['year'] rescue nil if year.nil? year = @years.first.to_f @@ -148,35 +136,12 @@ class CancerpredictsController < ApplicationController year_index = @years.index(year) @servive_ratio = eval(@form_to_show.tmp_years_settings_for_ruby[year_index]) @servive_ratio = ((1 - @servive_ratio) * 100).round(2) - @texts = @form_to_show.text_above_texts[locale].to_s.gsub('
    ','
    ').gsub('{{Surgery_only}}',''+@servive_ratio.round(2).to_s+'') - @texts = @texts.split('{{years}}') - @texts.delete('') - result['texts'] = ''+@texts[0] - @years.each{|year| result['texts'] += ('')} - if @texts.count > 1 - result['texts'] += (@texts[1]+'') if @texts.count > 1 - else - result['texts'] += '' - end - if !@form_to_show.surgery_only_texts[locale].blank? - @surgery_only_texts = @form_to_show.surgery_only_texts[locale] - @surgery_only_texts.insert(0,'

    ') - @surgery_only_texts = @surgery_only_texts.gsub('{{Surgery_only}}',''+@servive_ratio.round.to_s+'') - @surgery_only_texts = @surgery_only_texts.gsub('{{surgery_year}}',''+@years[-1].to_s+'') - @surgery_only_texts += '' - else - @surgery_only_texts = '' - end - result['texts'] += @surgery_only_texts - result['texts'] += ''+@form_to_show.extra_texts[locale]+'

    ' + result['texts'] = @form_to_show.result_text_translations[locale] result['extra_therapy_texts'] = @form_to_show.extra_therapy_texts[locale] rescue @form_to_show.extra_therapy_texts['zh_tw'] result['servive_ratio'] = @servive_ratio end result = result.merge(params) render :json=> result -# rescue - # render :json=> params - #end end def index uid = OrbitHelper.params[:uid] rescue "" diff --git a/app/models/cancerpredictfields.rb b/app/models/cancerpredictfields.rb index ad70628..3661bcb 100644 --- a/app/models/cancerpredictfields.rb +++ b/app/models/cancerpredictfields.rb @@ -1,107 +1,133 @@ class Cancerpredictfields - require 'pathname' + require "pathname" require 'json' include Mongoid::Document include Mongoid::Timestamps - include OrbitModel::Status - include OrbitModel::Impression - # encoding: utf-8 - include OrbitTag::Taggable - include OrbitCategory::Categorizable - FIELDINFO = {"variable"=>"String","name"=>"String","is_num"=>"Fixnum","hint"=>"String","comment_text"=>"String","choice_fields"=>"Array","range"=>"Array","right"=>"Fixnum","is_float"=>"Fixnum","revert_value"=>"Fixnum","map_values"=>"Array","cancer_predict_mapping_file"=>"String"} - NonLoclaized = ["variable","is_num","range","right","is_float","revert_value","map_values","cancer_predict_mapping_file"] + Field_relations = {"number_field"=>"Fixnum","text_area"=>"String"} + FIELDINFO = {"variable"=>"String","name"=>"String","is_num"=>"Fixnum","hint"=>"String","comment_text"=>"String","choice_fields"=>"Array","range"=>"Array","right"=>"Fixnum","is_float"=>"Fixnum","revert_value"=>"Fixnum","map_values"=>"Array","cancer_predict_mapping_file"=>"String","lpv_impact"=>"Float","active_choice"=>"number_field","disable_condition"=>"text_area"} + NonLoclaized = ["variable","is_num","range","right","is_float","revert_value","map_values","cancer_predict_mapping_file","lpv_impact","active_choice","disable_condition"] + AdvanceFields = ["revert_value","map_values","cancer_predict_mapping_file"] + TherapyFields = ["variable","name","hint","comment_text","choice_fields","lpv_impact","active_choice","disable_condition"] + TherapyOnly = ["lpv_impact","active_choice","disable_condition"] field :title ,type:String ,default:"" - field :form_show , :type=> Hash ,default:{0=>{:variable=>"sex",:name=>{"zh_tw"=>"性別
    (Sex)","en"=>"Sex"},:is_num=>0, :hint=>{'zh_tw'=>'','en'=>''} , :comment_text=>{'zh_tw'=>'','en'=>''}, :choice_fields=> {"zh_tw"=>['男','女'],"en"=>['Male','Female']},:range=>[],:right=>0,:is_float=>0,:revert_value=>0,:map_values=>[],:cancer_predict_mapping_file=>""}, - 1=>{:variable=>"age",:name=>{"zh_tw"=>"年齡
    (Age)","en"=>"Age"},:is_num=>1, :hint=>{'zh_tw'=>'從 20 歲(含)開始至 98 歲','en'=>'Age must be between 20 and 98'} , :comment_text=>{'zh_tw'=>'','en'=>''}, :choice_fields=> {"zh_tw"=>[],"en"=>[]},:range=>[20,98],:right=>0,:is_float=>0,:revert_value=>0,:map_values=>[],:cancer_predict_mapping_file=>""}, - 2=>{:variable=>"calcification_score",:name=>{"zh_tw"=>"鈣化指數
    (Calcification score)","en"=>"Calcification score"},:is_num=>1,:hint=>{'zh_tw'=>'請輸入0到5000的數字','en'=>'Please enter a number between 0 and 5000'}, :comment_text=>{'zh_tw'=>'','en'=>''}, :choice_fields=> {"zh_tw"=>[],"en"=>[]},:range=>[0,5000],:right=>0,:is_float=>1,:revert_value=>0,:map_values=>[],:cancer_predict_mapping_file=>""} - } - field :form_show_in_result , :type=> Hash ,default:{}#{0=>{:variable=>"hormone_therapy",:name=>{"zh_tw"=>"賀爾蒙治療","en"=>"Hormone/Steroid therapy"},:is_num=>0, :hint=>{'zh_tw'=>'適用賀爾蒙受體陽性病人','en'=>'Hormone/ steroid therapy is available when ER status is positive'} , :comment_text=>{'zh_tw'=>'','en'=>''}, :choice_fields=> {"zh_tw"=>['否','是'],"en"=>['No','Yes']},:range=>[]}, - #1=>{:variable=>"Chemotherapy",:name=>{"zh_tw"=>"化學治療","en"=>"Chemotherapy"},:is_num=>0,:hint=>{'zh_tw'=>'','en'=>''}, :comment_text=>{'zh_tw'=>'','en'=>''}, :choice_fields=> {"zh_tw"=>['否','是'],"en"=>['No','Yes']},:range=>[]}, - #2=>{:variable=>"Radiotherapy",:name=>{"zh_tw"=>"放射治療","en"=>"Radiotherapy"},:is_num=>0,:hint=>{'zh_tw'=>'','en'=>''}, :comment_text=>{'zh_tw'=>'','en'=>''}, :choice_fields=> {"zh_tw"=>['否','是'],"en"=>['No','Yes']},:range=>[]}, - #3=>{:variable=>"Targeted_therapy",:name=>{"zh_tw"=>"標靶治療","en"=>"Targeted therapy"},:is_num=>0,:hint=>{'zh_tw'=>'抗HER2治療','en'=>''}, :comment_text=>{'zh_tw'=>'','en'=>''}, :choice_fields=> {"zh_tw"=>['否','是'],"en"=>['No','Yes']},:range=>[]} - #} + field :advance_mode, type: Boolean, default: true + field :form_show , :type=> Hash ,default:{ + "0"=>{"variable"=>"sex_value", "name"=>{"zh_tw"=>"性別
    (Sex)", "en"=>"Sex"}, "is_num"=>0, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["男", "女"], "en"=>["Male", "Female"]}, "range"=>[], "right"=>0, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "1"=>{"variable"=>"age", "name"=>{"zh_tw"=>"年齡
    (Age)", "en"=>"Age"}, "is_num"=>1, "hint"=>{"zh_tw"=>"從 20 歲(含)開始至 98 歲", "en"=>"Age must be between 20 and 98"}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>[], "en"=>[]}, "range"=>[20, 98], "right"=>0, "is_float"=>0, "revert_value"=>0, "map_values"=>[], "cancer_predict_mapping_file"=>BSON::ObjectId('5f8e60441d41c801f600011a'), "need_map_values"=>0}, + "2"=>{"variable"=>"calH", "name"=>{"zh_tw"=>"心臟鈣化分數
    (Heart Calcification score)", "en"=>"Heart Calcification score"}, "is_num"=>1, "hint"=>{"zh_tw"=>"請輸入0到5000的數字", "en"=>"Please enter a number between 0 and 5000"}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>[], "en"=>[]}, "range"=>[0, 5000], "right"=>0, "is_float"=>1, "revert_value"=>0, "map_values"=>[], "cancer_predict_mapping_file"=>BSON::ObjectId('5f8e66c71d41c801f6000139'), "need_map_values"=>0}, + "3"=>{"variable"=>"calAH", "name"=>{"zh_tw"=>"升主動脈鈣化分數", "en"=>"Aorta ascendens Calcification score"}, "hint"=>{"zh_tw"=>"請輸入0到10000的數字", "en"=>"Please enter a number between 0 and 10000"}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>[], "en"=>[]}, "is_num"=>1, "range"=>[0, 10000], "right"=>0, "is_float"=>1, "revert_value"=>0, "map_values"=>[], "cancer_predict_mapping_file"=>BSON::ObjectId('5f8e6ded1d41c801f600013d'), "need_map_values"=>0}, + "4"=>{"variable"=>"calDH", "name"=>{"zh_tw"=>"降主動脈鈣化分數", "en"=>"Aorta descendens Calcification score"}, "hint"=>{"zh_tw"=>"請輸 入0到10000的數字", "en"=>"Please enter a number between 0 and 10000"}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>[], "en"=>[]}, "is_num"=>1, "range"=>[0, 10000], "right"=>0, "is_float"=>1, "revert_value"=>0, "map_values"=>[], "cancer_predict_mapping_file"=>BSON::ObjectId('5f8e6ded1d41c801f600013e'), "need_map_values"=>0}, + "5"=>{"variable"=>"fat", "name"=>{"zh_tw"=>"脂肪分數", "en"=>"Fat"}, "hint"=>{"zh_tw"=>"請輸入20到408的數字", "en"=>"Please enter a number between 20 and 408"}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>[], "en"=>[]}, "is_num"=>1, "range"=>[20, 408], "right"=>0, "is_float"=>1, "revert_value"=>0, "map_values"=>[], "cancer_predict_mapping_file"=>BSON::ObjectId('5f8e6ded1d41c801f600013f'), "need_map_values"=>0}, + "6"=>{"variable"=>"N4", "name"=>{"zh_tw"=>"腫瘤", "en"=>"Neoplasia"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>0, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "7"=>{"variable"=>"N12", "name"=>{"zh_tw"=>"癡呆症", "en"=>"Dementias"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>0, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "8"=>{"variable"=>"N20", "name"=>{"zh_tw"=>"慢性肝炎", "en"=>" Chronic hepatitis"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>0, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "9"=>{"variable"=>"N31", "name"=>{"zh_tw"=>"垂體侏儒症", "en"=>" Pituitary dwarfism"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>0, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "10"=>{"variable"=>"O6", "name"=>{"zh_tw"=>"慢性腎病", "en"=>" Chronic Kidney Disease"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "11"=>{"variable"=>"N34", "name"=>{"zh_tw"=>"克羅恩病和潰瘍性結腸炎", "en"=>"Crohn's disease and ulcerative colitis"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "12"=>{"variable"=>"N14", "name"=>{"zh_tw"=>"帕金森氏", "en"=>"Parkinson's disease"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "13"=>{"variable"=>"N26", "name"=>{"zh_tw"=>"多發性硬化症", "en"=>"Multiple sclerosis"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>[" 有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "14"=>{"variable"=>"O3", "name"=>{"zh_tw"=>"高血壓", "en"=>"Multiple sclerosis"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "15"=>{"variable"=>"O20", "name"=>{"zh_tw"=>"嚴重精神疾病", "en"=>"Severe mental illness"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "16"=>{"variable"=>"O18", "name"=>{"zh_tw"=>"類風溼關節炎", "en"=>"Rheumatoid arthritis"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "cancer_predict_mapping_file"=>"", "need_map_values"=>0}, + "17"=>{"variable"=>"O11", "name"=>{"zh_tw"=>"非出血性腦血管疾病", "en"=>"Non-Hemorrhagic Cerebrovascular Disease"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "need_map_values"=>0}, + "18"=>{"variable"=>"N29", "name"=>{"zh_tw"=>"強直性脊柱炎", "en"=>"Ankylosing spondylitis"}, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "need_map_values"=>0}, + "19"=>{"variable"=>"N6", "name"=>{"zh_tw"=>"動脈血管", "en"=>"Arterial vasculopathy"}, "is_num"=>0, "hint"=>{"zh_tw"=>"", "en"=>""}, "comment_text"=>{"zh_tw"=>"", "en"=>""}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>["yes", "no"]}, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "need_map_values"=>0}, + "20"=>{"variable"=>"O14", "name"=>{"zh_tw"=>"葡萄糖不耐症", "en"=>nil}, "is_num"=>0, "hint"=>{"zh_tw"=>"", "en"=>nil}, "comment_text"=>{"zh_tw"=>"", "en"=>nil}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>nil}, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "need_map_values"=>0}, + "21"=>{"variable"=>"N43", "name"=>{"zh_tw"=>"Basedow's disease", "en"=>nil}, "is_num"=>0, "hint"=>{"zh_tw"=>"", "en"=>nil}, "comment_text"=>{"zh_tw"=>"", "en"=>nil}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>nil}, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "need_map_values"=>0}, + "22"=>{"variable"=>"O17", "name"=>{"zh_tw"=>"偏頭痛", "en"=>nil}, "is_num"=>0, "hint"=>{"zh_tw"=>"", "en"=>nil}, "comment_text"=>{"zh_tw"=>"", "en"=>nil}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>nil}, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "need_map_values"=>0}, + "23"=>{"variable"=>"O9", "name"=>{"zh_tw"=>"心臟衰竭", "en"=>nil}, "hint"=>{"zh_tw"=>"", "en"=>nil}, "comment_text"=>{"zh_tw"=>"", "en"=>nil}, "choice_fields"=>{"zh_tw"=>["有", "沒有"], "en"=>nil}, "is_num"=>0, "range"=>[], "right"=>1, "is_float"=>0, "revert_value"=>1, "map_values"=>[], "need_map_values"=>0} + } + field :form_show_in_result , :type=> Hash ,default: {} field :form_result_is_right , :type=> Integer ,default: 0 - field :text_descibe ,type:Hash ,default:{"zh_tw"=>"歡迎使用台灣心血管疾病預後預測系統
    本預測系統由全民健保資料庫2017年~2020年間共1964位病人電腦斷層影像所建立之預測模型
    請在下方填入相關資訊","en"=>"Welcome to the Taiwan Breast Cancer Prediction System!
    The prediction system is constructed using clinical data from 90,841 breast cancer patients in the Taiwan Cancer Registry database between 2011 to 2015, and validated using clinical data from 49,374 breast cancer patients in the U.S.-based Surveillance, Epidemiology and End Results (SEER) database.
    To start, please select the information below."} + field :text_descibe ,type:Hash ,default: { + "zh_tw"=>"歡迎使用台灣心血管 疾病預後預測系統
    \r\n本預測系統由全民健保資料庫2017年~2020年間共1700位病人電腦斷層影像所建立之預測模型
    \r\n請 在下方填入相關資訊", + "en"=>"Welcome to the Taiwan cardiovascular disease prognosis prediction System!
    \r\nThe prediction system is a prediction model established by CT images of 1,700 patients form the National Health Insurance Database between 2017 to 2020.
    \r\nTo start, please select the information below." + } field :small ,type:Hash ,default:{'font_size'=>"0.825em",'active'=>0} field :medium ,type:Hash ,default:{'font_size'=>"1em",'active'=>1} field :large ,type:Hash ,default:{'font_size'=>"1.25em",'active'=>0} field :head_images_id ,type:Array , default: [] field :title_images_id ,type:Array , default: [] - field :title_texts ,type:Hash ,default:{'zh_tw'=>'臺灣心血管疾病存活預測','en'=>'Cardiovascular Disease Survival Forecast in Taiwan'} - field :table_above_texts ,type:Hash ,default:{'zh_tw'=>"下表之分析為針對手術後病人,根據選定的術後治療,分別估計在半年、一年及一年半的再住院或死亡機率。",'en'=>'The analysis is for women who had undergone surgery.The table shows the 0.5-, 1- and 1.5-year survival rates,based on the treatment you have selected.'} - field :text_above_texts ,type:Hash ,default:{'zh_tw'=>"此研究分析來自於照射胸部電腦斷層所得之結果,根據您所輸入的資訊,在第{{years}}年內,有2.69%的機率可能再住院或死亡{{Surgery_only}}%。",'en'=>'此研究分析來自於照射胸部電腦斷層所得之結果,根據您所輸入的資訊,在第{{years}}年內,有2.69%的機率可能再住院或死亡{{Surgery_only}}%。'} - field :surgery_only_texts ,type:Hash ,default:{'zh_tw'=>'','en'=>''} - field :extra_texts ,type:Hash ,default:{'zh_tw'=>',此外','en'=>''} - field :extra_therapy_texts ,type:Hash ,default:{'zh_tw'=>'100 位在術後有接受{{extra_therapy}}的婦女中,有{{survival_num}}位婦女,術後{{surgery_year}}年仍為存活(多了{{Additional_Benefit}}位)','en'=>'{{survival_num}} out of 100 women treated with {{extra_therapy}} are alive (an extra {{Additional_Benefit}})'} - field :danger_texts ,type:Hash ,default:{'zh_tw'=>'請注意紅框的輸入資料是否符合要求!','en'=>'Please check whether input data in red blocks are correct!'} - field :years ,type:Array ,default:[1,1.5,2,2.5] - field :texts_between_Result_and_result_block ,type:Hash ,default:{'zh_tw'=>'如果欲將預測結果應用於臨床上,請務必與您的主治醫師討論後再做最後決定。','en'=>'Please note that the patients need to consult with their medical doctors before making any decision.'} + field :title_texts ,type:Hash ,default: {"zh_tw"=>"臺灣心血管疾病存活預測", "en"=>"Cardiovascular Disease Survival Forecast in Taiwan"} + field :table_above_texts ,type:Hash ,default: {"zh_tw"=>"下表之分析為針對手術後病人,根據選定的術後治療,分別估計在一年、一年半、兩年及兩年半的心血管疾病住院或死亡機率。", "en"=>"The analysis is for women who had undergone surgery.The table shows the 1,1.5, 2 and 2.5 year survival rates,based on the treatment you have selected."} + field :text_above_texts ,type:Hash ,default: {"zh_tw"=>"此研究分析來自於照射胸部電腦斷層所得之結果,根據您所輸入的資訊,在第{{years}}年內,有{{Surgery_only}}%的 機率可能心血管疾病住院或死亡。", "en"=>"This research comes from the results obtained by irradiating the chest CT. According to the information you entered that you have the {{Surgery_only}}% of hospitalization or death for cardiovascular disease within {{years}} years."} + field :surgery_only_texts ,type:Hash ,default: {"zh_tw"=>"", "en"=>""} + field :extra_texts ,type:Hash ,default: {"zh_tw"=>",此外", "en"=>""} + field :extra_therapy_texts ,type:Hash ,default: {"zh_tw"=>"100 位在術後有接受{{extra_therapy}}的婦女中,有{{survival_num}}位婦女,術後{{surgery_year}}年仍為存活(多了{{Additional_Benefit}}位)", "en"=>"{{survival_num}} out of 100 women treated with {{extra_therapy}} are alive (an extra {{Additional_Benefit}})"} + field :danger_texts ,type:Hash ,default: {"zh_tw"=>"請注意紅框的輸入資料是否符合要求!", "en"=>"Please check whether input data in red blocks are correct!"} + field :years ,type:Array ,default:[1, 1.5, 2, 2.5] + field :texts_between_Result_and_result_block ,type:Hash ,default: {"zh_tw"=>"如果欲將預測結果應用於臨床上,請務必與您的主治醫師討論後再做最後決定。", "en"=>"Please note that the patients need to consult with their medical doctors before making any decision."} #field :image_uploader ,type:Object field :prediction_formula , type: String ,default: "A = 0.1327868* (sex_value- 0.4858824) - + 0.0371720* (age_test1 - 61.56000) -0.07447278* (age_test2 - 13.10152) + + 0.0371720* (age_test1 - 61.56000) -0.07447278* (age_test2 - 13.10152) - + 0.4315686* (age_test3 - 0.9844332) + + 0.4315686* (age_test3 - 0.9844332) - + 0.0009163615*( calH_test1 - 182.9347) + + 0.0009163615*( calH_test1 - 182.9347) - -0.0007536899*( calH_test2 - 124.8706) -0.00004697183*( calH_test3 -80.75636) + -0.0007536899*( calH_test2 - 124.8706) -0.00004697183*( calH_test3 -80.75636) - + 0.0001401325*( calAH_test1 - 700.7824) + + 0.0001401325*( calAH_test1 - 700.7824) + -0.001349783*( calAH_test2 - 634.2167) +0.001753832*( calAH_test3 -419.3361) - -0.001349783*( calAH_test2 - 634.2167) +0.001753832*( calAH_test3 -419.3361) + + 0.0001906046*( calDH_test1 -835.2894) -0.000251567*( calDH_test2 - 213.1630) - + 0.0001906046*( calDH_test1 -835.2894) -0.000251567*( calDH_test2 - 213.1630) + -0.002173942*( fat_test1 -108.4149)+0.003066541*( fat_test2 - 28.33497) + +0.6700708*(N4-0.3241176) - -0.002173942*( fat_test1 -108.4149)+0.003066541*( fat_test2 - 28.33497) + +0.3336162*(O3-0.4994118) - +0.6700708*(N4-0.3241176) + +0.1322476*(O20-0.1741176) - +0.3336162*(O3-0.4994118) + +0.9084972*(O18-0.008823529) - +0.1322476*(O20-0.1741176) + +0.2978388*(N12-0.1152941) - +0.9084972*(O18-0.008823529) + +0.1777935*(N20-0.3582353) - +0.2978388*(N12-0.1152941) + +1.588042*(N31-0.002352941) - +0.1777935*(N20-0.3582353) + +0.2197419*(O6-0.07823529) - +1.588042*(N31-0.002352941) + +1.791159*(N34-0.001176471) - +0.2197419*(O6-0.07823529) + +0.4305973*(N14-0.02176471) - +1.791159*(N34-0.001176471) + -0.4472885*(N29-0.02411765) - +0.4305973*(N14-0.02176471) + +0.2601319*(N26-0.04941176) - -0.4472885*(N29-0.02411765) + -0.2364269*(O11-0.1164706) - +0.2601319*(N26-0.04941176) + +0.1784179*(N6-0.1070588) - -0.2364269*(O11-0.1164706) + +0.6023170*(O14-0.01294118) - +0.1784179*(N6-0.1070588) + -1.031959*(N43-0.007058824) + +0.4257809*(O17-0.01823529) - +0.6023170*(O14-0.01294118) - - -1.031959*(N43-0.007058824) - - +0.4257809*(O17-0.01823529) - - +0.2002546*(O9-0.06176471)" - field :years_settings , type: Array , default: ["0.8095037^( exp(A) )","0.729158^( exp(A) )","0.6717211^( exp(A) )","0.6056773^( exp(A) )"] + +0.2002546*(O9-0.06176471)" + field :years_settings , type: Array , default: ["0.8095037^( exp(A) )", "0.729158^( exp(A) )", "0.6717211^( exp(A) )", "0.6056773^( exp(A) )"] field :tmp_years_settings , type: Array , default: [] field :tmp_years_settings_for_ruby , type: Array , default: [] + field :hidden_variables, type: String, default: "" + field :fix_hidden_variables, type: Array, default: [] + field :tmp_hidden_variables_for_ruby, type: String, default: "" + field :tmp_hidden_variables_for_js, type: String, default: "" field :lpv_calc, type: Hash, default: {} #for js code field :tmp_lpv_ruby_code, type: String, default: "" field :tmp_lpv_variables, type: Array, default: [] field :mapping_data_from_csv , type: String ,default: "" - scope :can_display, ->{where(:is_hidden=>false,:is_preview => false).any_of({:postdate.lt=>Time.now, :deadline.gt=>Time.now},{:postdate.lt=>Time.now, :deadline=>nil}).order_by([:is_top, :desc],[:postdate, :desc])} - scope :is_approved, ->{where(:approved => true)} + field :all_variables, type: Array, default: [] + field :treatment_method, type: Array, default: ['Surgery_only'] + field :treatment_method_active_indices, type: Array, default: [1] + field :result_table, type: String, default: "", localize: true + field :result_text, type: String, default: "", localize: true + field :therapy_lpv, type: Array, default: [0] #before_create :set_expire before_save do self.form_show.each do |num,property| @@ -114,104 +140,174 @@ class Cancerpredictfields result_keys << variable_name end end + self.form_show_in_result.each do |num,property| + variable_name = property[:variable] + if variable_name.present? + result_keys << variable_name + end + end mapping_data = JSON.parse(self.mapping_data_from_csv) rescue {} - if mapping_data.present? + if self.advance_mode && mapping_data.present? mapping_data.each do |k,v| result_keys += (v.keys rescue []) end end - formula = self.prediction_formula.gsub("\r\n"," ").gsub("^","**") + result_keys = result_keys.uniq + self.all_variables = result_keys + formula = text_to_math(self.prediction_formula) + tmp_hidden_variables = text_to_math(self.hidden_variables) result_keys.each do |k| - formula = formula.gsub(/#{k}?(-|\+|\*|\/|\s|\=)/){ "result[\"#{k}\"]#{$1}" } + formula = formula.gsub(/(\A|[^\w])#{k}($|[^\w])/){|f| "#{$1}result[\"#{k.strip}\"]#{$2}" } + tmp_hidden_variables = tmp_hidden_variables.gsub(/(\A|[^\w])#{k}($|[^\w])/){|f| "#{$1}result[\"#{k.strip}\"]#{$2}" } end - formula = formula.split(/^([^=]+)=([^=])/).select{|s| s.present?}.each_slice(2).map do |a,b| + self.tmp_hidden_variables_for_js = tmp_hidden_variables.rstrip.gsub(/\n\s+/,"\n ").gsub("\n",";\n") + ";" + self.fix_hidden_variables = [] + self.tmp_hidden_variables_for_ruby = tmp_hidden_variables.split(/^([^=!]+)=([^=!])/).select{|s| s.present?}.each_slice(2).map do |a,b| + a = a.strip + self.fix_hidden_variables << a if b - ("@"+ a + "=" + b) + ("result[\"#{a}\"]=" + b.gsub("\n","")) else - "@"+ a + a end end.join("\n") + self.fix_hidden_variables = self.fix_hidden_variables.uniq + formula = formula.split(/^([^=!]+)=([^=!])/).select{|s| s.present?}.each_slice(2).map do |a,b| + a = a.strip + if b + ("result[\"#{a}\"]=" + b.gsub("\n","")) + else + a + end + end.join("\n") + self.fix_hidden_variables.each do |v| + formula = formula.gsub(/(\A|[^\w\"])#{v}($|[^\w])/){|f| "#{$1}result[\"#{v.strip}\"]#{$2}"} + self.tmp_hidden_variables_for_ruby = self.tmp_hidden_variables_for_ruby.gsub(/(\A|[^\w\"])#{v}($|[^\w])/){|f| "#{$1}result[\"#{v.strip}\"]#{$2}"} + end self.tmp_lpv_ruby_code = formula - formula_variables = formula.enum_for(:scan,/([^\=\(\)]+)?=[^=]/).map {|x| x[-1] }.compact.map{|s| s.strip} + formula_variables = formula.enum_for(:scan,/([^\=\(\)]+)?=[^=]/).map {|x| x[-1] }.compact.map{|s| s.strip[8..-3]} self.tmp_lpv_variables = formula_variables self.tmp_years_settings = self.years_settings.map do |s| - s.gsub('^','**').gsub('exp','Math.exp') + text_to_math(s) end self.tmp_years_settings_for_ruby = self.tmp_years_settings.clone formula_variables.each do |variable_name| self.tmp_years_settings_for_ruby = self.tmp_years_settings_for_ruby.map do |y| - y.gsub(variable_name[1..-1],variable_name) + y.gsub(variable_name,"result[\"#{variable_name}\"]") + end + end + self.treatment_method = ['Surgery_only'] + self.form_show_in_result.values.each do |choice| + variable = choice["variable"] + if variable.present? + self.treatment_method << variable + end + end + tmp_table_translations = {} + tmp_text_translations = {} + @years = self.years + # @head_name = ['Treatment','Additional_Benefit','Overall_Survival'] + @head_name = ['Treatment','Overall_Survival'] + @table_head = @head_name.map{|name| I18n.t('cancerpredict.table.'+name)} + @therapy_names = self.treatment_method + I18n.available_locales.each do |locale| + I18n.with_locale(locale) do + @therapy_choices = [I18n.t('cancerpredict.table.Surgeryonly')] + self.form_show_in_result.values.each{|choice| @therapy_choices.push choice["name"][locale]} + tmp_table = "#{I18n.t("cancerpredict.table.table")}
    " + tmp_table += '

    '+self.table_above_texts[locale].to_s+'

    ' + tmp_table += (''+(locale.to_s == 'zh_tw' ? '第' : '')+'') + @years.each{|year| tmp_table += ('')} + tmp_table += (''+(locale == 'zh_tw' ? '年' : '')+'') + tmp_table += '
    ' + head + '
    ' + ((index == 0) ? (((i==0)? '' : '+') + choice) : '-') + '
    ' + @table_head.each_with_index{|head,index| tmp_table += ('')} + tmp_table += '' + @therapy_choices.each_with_index do |choice,i| + tmp_table += '' + @table_head.each_with_index do |head,index| + tmp_table += ('') + end + tmp_table += '' + end + tmp_table_translations[locale] = tmp_table + @texts = self.text_above_texts[locale].to_s.gsub('
    ','
    ').gsub('{{Surgery_only}}','') + @texts = @texts.split('{{years}}') + @texts.delete('') + tmp_text = "#{I18n.t("cancerpredict.table.text")}
    " + tmp_text += (''+@texts[0]) + @years.each{|year| tmp_text += ('')} + if @texts.count > 1 + tmp_text += (@texts[1]+'') if @texts.count > 1 + else + tmp_text += '
    ' + end + if !self.surgery_only_texts[locale].blank? + @surgery_only_texts = self.surgery_only_texts[locale] + @surgery_only_texts.insert(0,'

    ') + @surgery_only_texts = @surgery_only_texts.gsub('{{Surgery_only}}','') + @surgery_only_texts = @surgery_only_texts.gsub('{{surgery_year}}',''+@years[-1].to_s+'') + @surgery_only_texts += '' + else + @surgery_only_texts = '' + end + tmp_text += @surgery_only_texts + tmp_text += ''+self.extra_texts[locale]+'

    ' + tmp_text_translations[locale] = tmp_text + end + end + self.result_table_translations = tmp_table_translations + self.result_text_translations = tmp_text_translations + self.treatment_method_active_indices = [1] + self.form_show_in_result.each do |num, property| + v = property[:active_choice] + if v.present? + self.treatment_method_active_indices << (v - 1) + else + self.treatment_method_active_indices << 1 end end self.lpv_calc = get_years_settings_dict self.generate_eval_formula end def generate_eval_formula + eval_hidden_variables = "def eval_hidden_variables(result); #{self.tmp_hidden_variables_for_ruby}; end" + CancerpredictsController.module_eval(eval_hidden_variables) eval_formula = "def eval_formula(result); #{self.tmp_lpv_ruby_code}; end" CancerpredictsController.module_eval(eval_formula) end - def update_user - User.find(update_user_id) rescue nil - end - def update_user=(user) - self.update_user_id = user.id - end - def email_members - MemberProfile.find(self.email_member_ids) rescue [] - end - def email_addresses - addresses = self.email_members.collect{|member| member.email} rescue [] - addresses = addresses +[self.other_mailaddress] if !self.other_mailaddress.blank? - addresses.flatten - end - def email - mail = Email.find(self.email_id) rescue nil - end - def expired? - (self.deadline < Time.now) rescue false - end - def destroy_email - mail = Email.find(self.email_id) rescue nil - mail.destroy if !mail.nil? - end - def self.remove_expired_status - self.where(:is_top => true, :top_end_date.ne => nil, :top_end_date.lt => Time.now).each do |b| - b.is_top = false - b.top_end_date = nil - b.save - end - end def generate_jscode js_code = "var map_values , mapping_hash , temp_index ,temp_value , index , closest_value;\r\n" - mapping_data_from_csv = YAML.load(self.mapping_data_from_csv) rescue {} - variable_keys = [] - self.form_show.each do |num,property| + mapping_data_from_csv = JSON.parse(self.mapping_data_from_csv) rescue {} + tmp_hash = self.form_show.values + self.form_show_in_result.values + tmp_hash.each do |property| @variable = property[:variable] if @variable.present? if property[:is_num] == 1 - js_code += "\t\t\t\tresult['#{@variable}'] = Number(result_json['#{@variable}']);\r\n" + js_code += " result['#{@variable}'] = Number(result_json['#{@variable}']);\r\n" elsif property[:choice_fields].present? - if property[:need_map_values] == 1 - js_code += "\t\t\t\tmap_values = #{property[:map_values]};\r\n" - js_code += "\t\t\t\tresult['#{@variable}'] = map_values[Number(result_json['#{@variable}'']) - 1];\r\n" + if !(self.advance_mode) + js_code += " result['#{@variable}'] = Number(result_json['#{@variable}']);\r\n" else - if property[:revert_value] != 1 - js_code += "\t\t\t\tresult['#{@variable}'] = Number(result_json['#{@variable}']) - 1;\r\n" + if property[:need_map_values] == 1 + js_code += " map_values = #{property[:map_values]};\r\n" + js_code += " result['#{@variable}'] = map_values[Number(result_json['#{@variable}'']) - 1];\r\n" else - js_code += "\t\t\t\tresult['#{@variable}'] = (#{property[:choice_fields].length} - Number(result_json['#{@variable}']));\r\n" + if property[:revert_value] != 1 + js_code += " result['#{@variable}'] = Number(result_json['#{@variable}']) - 1;\r\n" + else + js_code += " result['#{@variable}'] = (#{property[:choice_fields].length} - Number(result_json['#{@variable}']));\r\n" + end end end end - variable_keys.push(@variable) - if property[:cancer_predict_mapping_file].present? + if self.advance_mode && property[:cancer_predict_mapping_file].present? if (mapping_data_from_csv != {} && !mapping_data_from_csv[@variable].blank?) - variable_keys.concat(mapping_data_from_csv[@variable].keys) - js_code += "\t\t\t\tmapping_hash = mapping_data_from_csv['#{@variable}'];\r\n" - js_code += "\t\t\t\ttemp_index = 0;\r\n" - js_code += "\t\t\t\ttemp_value = result[#{@variable}];\r\n" - js_code += "\t\t\t\tindex = 0; + js_code += " mapping_hash = mapping_data_from_csv['#{@variable}'];\r\n" + js_code += " temp_index = 0;\r\n" + js_code += " temp_value = result['#{@variable}'];\r\n" + js_code += " index = 0; $.each(mapping_hash,function(k,v){ - if( i == 0 ){ + if( index == 0 ){ var index_val = v.indexOf(temp_value); if( index_val != -1 ){ temp_index = index_val; @@ -227,29 +323,37 @@ class Cancerpredictfields end end end - formula = self.prediction_formula.gsub("\r\n"," ").gsub("^","**") - variable_keys.each do |k| - formula = formula.gsub(/#{k}?(-|\+|\*|\s|\=)/){ "result[\"#{k}\"]#{$1}" } + js_code += "\n Object.keys(result).forEach(function(k){ + if(Number.isNaN(result[k])){ + result[k] = 0; + } + })" + js_code += "\n #{self.tmp_hidden_variables_for_js}" + formula = text_to_math(self.prediction_formula) + self.all_variables.each do |k| + formula = formula.gsub(/#{k}?(-|\+|\*|\s|\=)/){ "result[\"#{k.strip}\"]#{$1}" } end - formula_variables = formula.enum_for(:scan,/([^\=]*)?=/).map { ::Regexp.last_match[1] }.map{|s| s.strip.split(/(\s*|;\r\n)/).last} - js_code = "function calculate_first_lpv(result_json){ + formula_variables = self.tmp_lpv_variables.map{|v| v} + js_code = "\n function calculate_first_lpv(result_json){ result = {}; #{js_code} try{ - result['lpv'] = (#{formula.gsub(/\s{2,10}/," ")}); - }catch(e){result['lpv'] = \"error\"}; - console.log(result['lpv']); - #{formula_variables.map{|v| "result['lpv_variable']['#{v}'] = #{v};"}.join("\r\n\t\t\t\t") } + #{formula.gsub(/\s{2,10}/," ").gsub("\n","\n ")} + }catch(e){console.log(e)}; + result['lpv_variable'] = {}; + #{formula_variables.map{|v| "result['lpv_variable']['#{v}'] = #{v};"}.join("\n ") } + result['lpv'] = #{formula_variables.count == 0 ? 0 : formula_variables.last}; + result['lpv_variable']['lpv'] = result['lpv']; return result; }; function calculate_and_change_result_value(obj){ obj.servive_ratio_arr = []; for(var i = 0;i <% keys.each do |key| %> + + <%= render :partial => 'form_file', :object => (CancerPredictMappingFile.where(:id=> property[key]).first rescue nil), :locals => {:f => make_fields, :key=>key} %> <% else %> <% value = property[key] %> - <% if property == {} %> - <% value_type = Cancerpredictfields::FIELDINFO[key].constantize rescue String %> - <% value = "[]" if value_type == Array %> - <% else %> - <% value_type = value.class %> - <% end %> + <% value_type = Cancerpredictfields::FIELDINFO[key] %> + <% value = "[]" if property == {} && value_type == 'Array' %> + <% is_localized = Cancerpredictfields::NonLoclaized.exclude?(key) %> <% @value= value %> - <% if value_type == BSON::Document || value_type == Hash %> + <% if is_localized %> <% @disp_value = @value[I18n.locale.to_s] rescue "" %> <%else%> <% @disp_value = @value %> <%end%> - <% if value_type == Fixnum %> + <% field_type = ((value_type == 'String' || value_type == 'Array' || value_type == 'Float') ? "text_field" : value_type) %> + <% if value_type == 'Fixnum' %> <% if @value == 1%> - + <%= make_fields.check_box key,{:checked=>true,:class=>"checkbox",:style=>"float:left;"}%> <% else%> - + <%= make_fields.check_box key,{:checked=>false,:class=>"checkbox",:style=>"float:left;"}%> <%end%> - <% elsif Cancerpredictfields::NonLoclaized.exclude?(key) %> + <% elsif is_localized %> <%=make_fields.fields_for I18n.locale.to_s do |locale_fields|%> - + <%= locale_fields.send(field_type, key,{:value=>@disp_value}) %> <%end%> <% else %> - + <%= make_fields.send(field_type, key,{:value=>@disp_value})%> <%end%> <%end%> + <%end%> \ No newline at end of file diff --git a/app/views/admin/cancerpredicts/index.html.erb b/app/views/admin/cancerpredicts/index.html.erb index 9f46f89..5935c71 100644 --- a/app/views/admin/cancerpredicts/index.html.erb +++ b/app/views/admin/cancerpredicts/index.html.erb @@ -1,4 +1,5 @@ <%= stylesheet_link_tag "lib/fileupload"%> +<%= stylesheet_link_tag "lib/togglebox"%> <% content_for :page_specific_javascript do %> <%= javascript_include_tag "lib/bootstrap-fileupload" %> <%#= javascript_include_tag "lib/bootstrap-datetimepicker" %> @@ -26,7 +27,53 @@ .remove_div:hover{ font-size: 1.3em; } + <% Cancerpredictfields::AdvanceFields.each do |field| %> + table .<%=field%>{ + display: none; + } + table.advance_mode .<%=field%>{ + display: block; + } + <% end%> + .solid_line_hr{ + margin: 0.3em; + border-top: 0.2em dashed; + } + .sort_table input, .sort_table textarea{ + font-family: sans-serif; + } + .advance_mode_help_btn{ + float:left; + cursor: pointer; + padding: 0em 0.475em; + font-size: 1.25em; + border-radius: 1.5em; + background-color: rgb(210, 106, 2); + border-color: rgb(210, 106, 2); + color: white; + width: 1.8em; + height: 1.8em; + line-height: 1em; + } +
    <%=form_for @form_to_show ,:url=>{:controller=>"cancerpredicts" ,:action=>"edit"} do |form|%> <%= t('cancerpredict.title') %> @@ -181,17 +228,28 @@ <%end%> <%end%> <%end%> + <%= t('cancerpredict.module_mode') %> +
    +
    + +
    + +
    +
    +
    <%= t('cancerpredict.Input_fields') %>
    -
    ' + head + '
    ' + ((index == 0) ? (((i==0)? '' : '+') + choice) : '-') + '
    <% if key.include? "_file" %> - - <%= render :partial => 'form_file', :object => (CancerPredictMappingFile.where(:id=> property[key]).first rescue nil), :locals => {:f => make_fields, :key=>key} %> - <%= make_fields.check_box key,{:checked=>true,:class=>"checkbox",:style=>"float:left;"}%><%= make_fields.check_box key,{:checked=>false,:class=>"checkbox",:style=>"float:left;"}%><%= locale_fields.text_field key,{:value=>@disp_value}%><%= make_fields.text_field key,{:value=>@disp_value}%><%= make_fields.hidden_field :old_num,:value=>num.to_s %>
    - <% keys = @form_to_show.form_show.values[0].keys rescue [] %> - <% keys = Cancerpredictfields::FIELDINFO.keys if keys.blank? %> +
    + <% keys = Cancerpredictfields::FIELDINFO.keys - Cancerpredictfields::TherapyOnly %> <% keys.each do |key|%> - + <%end%> @@ -228,15 +286,14 @@ <% end %>
    <% end %> -
    <%=t("cancerpredict.table.#{key}")%><%=t("cancerpredict.table.#{key}")%>
    +
    - <% keys = @form_to_show.form_show_in_result.values[0].keys rescue [] %> - <% keys = Cancerpredictfields::FIELDINFO.keys if keys.blank? %> + <% keys = Cancerpredictfields::TherapyFields %> <% keys.each do |key,vlaue|%> - + <%end%> @@ -244,38 +301,7 @@ <%= form.fields_for :form_show_in_result do |formfield|%> <% @form_to_show.form_show_in_result.each do |num,property| %> <%=formfield.fields_for num.to_s do |make_fields|%> - - - - <% property.each do |key,value|%> - <% if key.include? "_file" %> - - <% else %> - <% @value= value %> - <% if @value.class == BSON::Document || @value.class == Hash %> - <% @disp_value = @value[I18n.locale.to_s] rescue "" %> - <%else%> - <% @disp_value = @value %> - <%end%> - <% if Cancerpredictfields::FIELDINFO[key] == "Fixnum" %> - <% if @value == 1%> - - <% else%> - - <%end%> - <% elsif Cancerpredictfields::NonLoclaized.exclude?(key) %> - <%=make_fields.fields_for I18n.locale.to_s do |locale_fields|%> - - <%end%> - <% else %> - - <%end%> - <%end%> - <%end%> - - + <%= render :partial => 'form', :locals=>{:make_fields=>make_fields,:property=>property,:num=>num,:keys => Cancerpredictfields::TherapyFields} %> <%end%> <%end%> <%end%> @@ -285,23 +311,32 @@
    <%=t('cancerpredict.table.calculate_settings')%>
    +
    +
    + +
    +
    + <%= form.text_area :hidden_variables, :rows=>"5", :style=> 'width: 100%;font-family: sans-serif;' %> +
    +
    +
    - <%= form.text_area :prediction_formula, :rows=>"5", :style=> 'width: calc(100% - 12em);' %> + <%= form.text_area :prediction_formula, :rows=>"5", :style=> 'width: 100%;font-family: sans-serif;' %>
    <% years = @form_to_show.years %> <% years.each_with_index do |year,i| %>
    -
    - +
    +
    - +
    <% end %> @@ -310,6 +345,19 @@ <%end%> {{table}} - - \ No newline at end of file +<%= stylesheet_link_tag "bootstrap.min.print", media: "print" %> +<%= stylesheet_link_tag "cancer_predict_print", media: "print" %> \ No newline at end of file diff --git a/modules/cancerpredict/info.json b/modules/cancerpredict/info.json index 7b4c1d1..95cad8e 100644 --- a/modules/cancerpredict/info.json +++ b/modules/cancerpredict/info.json @@ -3,8 +3,8 @@ { "filename" : "cancer_predict_index", "name" : { - "zh_tw" : "1. 乳癌預測工具", - "en" : "1. Breast cancer predict tool" + "zh_tw" : "1. 臺灣心血管疾病存活預測工具", + "en" : "1. Cardiovascular Disease Survival Forecast Tool" }, "thumbnail" : "thumb.png" } @@ -13,8 +13,8 @@ { "filename" : "cancer_predict_widget", "name" : { - "zh_tw" : "1. 乳癌預測工具", - "en" : "1. Breast cancer predict tool" + "zh_tw" : "1. 臺灣心血管疾病存活預測工具", + "en" : "1. Cardiovascular Disease Survival Forecast Tool" }, "thumbnail" : "thumb.png" }
    <%=t("cancerpredict.table.#{key}")%><%=t("cancerpredict.table.#{key}")%>
    - <%= render :partial => 'form_file', :object => (CancerPredictMappingFile.where(:id=> property[key]).first rescue nil), :locals => {:f => make_fields, :key=>key} %> - <%= make_fields.check_box key,{:checked=>true,:class=>"checkbox",:style=>"float:left;"}%><%= make_fields.check_box key,{:checked=>false,:class=>"checkbox",:style=>"float:left;"}%><%= locale_fields.text_field key,{:value=>@disp_value}%><%= make_fields.text_field key,{:value=>@disp_value}%><%= make_fields.hidden_field :old_num,:value=>num.to_s %>