Employee Promotion, Transfer - modal to add details to child table
diff --git a/erpnext/hr/doctype/employee_promotion/employee_promotion.js b/erpnext/hr/doctype/employee_promotion/employee_promotion.js
index c1bb788..54e06f4 100644
--- a/erpnext/hr/doctype/employee_promotion/employee_promotion.js
+++ b/erpnext/hr/doctype/employee_promotion/employee_promotion.js
@@ -1,6 +1,8 @@
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
// For license information, please see license.txt
+{% include 'erpnext/hr/employee_property_update.js' %}
+
frappe.ui.form.on('Employee Promotion', {
refresh: function(frm) {
diff --git a/erpnext/hr/doctype/employee_transfer/employee_transfer.js b/erpnext/hr/doctype/employee_transfer/employee_transfer.js
index 1d694bd..af751a7 100644
--- a/erpnext/hr/doctype/employee_transfer/employee_transfer.js
+++ b/erpnext/hr/doctype/employee_transfer/employee_transfer.js
@@ -1,6 +1,8 @@
// Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
// For license information, please see license.txt
+{% include 'erpnext/hr/employee_property_update.js' %}
+
frappe.ui.form.on('Employee Transfer', {
refresh: function(frm) {
diff --git a/erpnext/hr/employee_property_update.js b/erpnext/hr/employee_property_update.js
new file mode 100644
index 0000000..d49c1ab
--- /dev/null
+++ b/erpnext/hr/employee_property_update.js
@@ -0,0 +1,147 @@
+frappe.ui.form.on(cur_frm.doctype, {
+ setup: function(frm) {
+ frm.set_query("employee", function() {
+ return {
+ filters: {
+ "status": "Active"
+ }
+ };
+ })
+ },
+ onload: function(frm){
+ if(frm.doc.__islocal){
+ if(frm.doctype == "Employee Promotion"){
+ frm.doc.promotion_details = [];
+ }else if (frm.doctype == "Employee Transfer") {
+ frm.doc.transfer_details = [];
+ }
+ }
+ },
+ employee: function(frm) {
+ frm.add_fetch("employee", "company", "company");
+ },
+ refresh: function(frm) {
+ var table;
+ if(frm.doctype == "Employee Promotion"){
+ table = "promotion_details";
+ }else if (frm.doctype == "Employee Transfer") {
+ table = "transfer_details"
+ }
+ if(!table){return}
+ cur_frm.fields_dict[table].grid.wrapper.find('.grid-add-row').hide();
+ cur_frm.fields_dict[table].grid.add_custom_button(__('Add Row'), () => {
+ if(!frm.doc.employee){
+ frappe.msgprint(__("Please select Employee"));
+ return;
+ }
+ frappe.call({
+ method: 'erpnext.hr.utils.get_employee_fields_label',
+ callback: function(r) {
+ if(r.message){
+ show_dialog(frm, table, r.message);
+ }
+ }
+ });
+ });
+ }
+});
+
+var show_dialog = function(frm, table, field_labels) {
+ var d = new frappe.ui.Dialog({
+ title: "Update Property",
+ fields: [
+ {fieldname: "property", label: __('Select Property'), fieldtype:"Select", options: field_labels},
+ {fieldname: "current", fieldtype: "Data", label:__('Current'), read_only: true},
+ {fieldname: "field_html", fieldtype: "HTML"}
+ ],
+ primary_action_label: __('Add to Details'),
+ primary_action: () => {
+ d.get_primary_btn().attr('disabled', true);
+ if(d.data){
+ add_to_details(frm, d, table);
+ }
+ }
+ });
+ d.fields_dict["property"].df.onchange = () => {
+ let property = d.get_values().property;
+ d.data.fieldname = property;
+ if(!property){return;}
+ frappe.call({
+ method: 'erpnext.hr.utils.get_employee_field_property',
+ args: {employee: frm.doc.employee, fieldname: property},
+ callback: function(r) {
+ if(r.message){
+ d.data.current = r.message.value;
+ d.data.property = r.message.label;
+ d.fields_dict.field_html.$wrapper.html("");
+ d.set_value('current', r.message.value);
+ render_dynamic_field(d, r.message.datatype, r.message.options, property);
+ d.get_primary_btn().attr('disabled', false);
+ }
+ }
+ });
+ };
+ d.get_primary_btn().attr('disabled', true);
+ d.data = {};
+ d.show();
+}
+
+var render_dynamic_field = function(d, fieldtype, options, fieldname) {
+ d.data.new = null;
+ var dynamic_field = frappe.ui.form.make_control({
+ df: {
+ "fieldtype": fieldtype,
+ "fieldname": fieldname,
+ "options": options || ''
+ },
+ parent: d.fields_dict.field_html.wrapper,
+ only_input: false
+ });
+ dynamic_field.make_input();
+ $(dynamic_field.label_area).text(__("New"));
+ dynamic_field.$input.on("change", function(e) {
+ d.data.new = e.target.value;
+ }).on("awesomplete-close", function(e) {
+ d.data.new = e.target.value;
+ });
+}
+
+var add_to_details = function(frm, d, table) {
+ let data = d.data;
+ if(data.fieldname){
+ if(validate_duplicate(frm, table, data.fieldname)){
+ frappe.show_alert({message:__("Property already added"), indicator:'orange'});
+ return false;
+ }
+ if(data.current == data.new){
+ frappe.show_alert({message:__("Nothing to change"), indicator:'orange'});
+ d.get_primary_btn().attr('disabled', false);
+ return false;
+ }
+ frm.add_child(table, {
+ fieldname: data.fieldname,
+ property: data.property,
+ current: data.current,
+ new: data.new
+ });
+ frm.refresh_field(table);
+ d.fields_dict.field_html.$wrapper.html("");
+ d.set_value("property", "");
+ d.set_value('current', "");
+ frappe.show_alert({message:__("Added to details"),indicator:'green'});
+ d.data = {};
+ }else {
+ frappe.show_alert({message:__("Value missing"),indicator:'red'});
+ }
+}
+
+var validate_duplicate = function(frm, table, fieldname){
+ let duplicate = false;
+ $.each(frm.doc[table], function(i, detail) {
+ if(detail.fieldname === fieldname){
+ duplicate = true;
+ return;
+ }
+ });
+ return duplicate;
+}
diff --git a/erpnext/hr/utils.py b/erpnext/hr/utils.py
index aa456aa..057f406 100644
--- a/erpnext/hr/utils.py
+++ b/erpnext/hr/utils.py
@@ -4,7 +4,48 @@
from __future__ import unicode_literals
import frappe
from frappe import _
+from frappe.utils import formatdate, format_datetime
+from frappe.utils import getdate, get_datetime
def set_employee_name(doc):
if doc.employee and not doc.employee_name:
doc.employee_name = frappe.db.get_value("Employee", doc.employee, "employee_name")
+
+@frappe.whitelist()
+def get_employee_fields_label():
+ fields = []
+ for df in frappe.get_meta("Employee").get("fields"):
+ if df.fieldtype in ["Data", "Date", "Datetime", "Float", "Int",
+ "Link", "Percent", "Select", "Small Text"] and df.fieldname not in ["lft", "rgt", "old_parent"]:
+ fields.append({"value": df.fieldname, "label": df.label})
+ return fields
+
+@frappe.whitelist()
+def get_employee_field_property(employee, fieldname):
+ if employee and fieldname:
+ field = frappe.get_meta("Employee").get_field(fieldname)
+ value = frappe.db.get_value("Employee", employee, fieldname)
+ options = field.options
+ if field.fieldtype == "Date":
+ value = formatdate(value)
+ elif field.fieldtype == "Datetime":
+ value = format_datetime(value)
+ return {
+ "value" : value,
+ "datatype" : field.fieldtype,
+ "label" : field.label,
+ "options" : options
+ }
+ else:
+ return False
+
+def update_employee(employee, details, cancel=False):
+ for item in details:
+ fieldtype = frappe.get_meta("Employee").get_field(item.fieldname).fieldtype
+ new_data = item.new if not cancel else item.current
+ if fieldtype == "Date" and new_data:
+ new_data = getdate(new_data)
+ elif fieldtype =="Datetime" and new_data:
+ new_data = get_datetime(new_data)
+ setattr(employee, item.fieldname, new_data)
+ return employee