diff --git a/frappe/model/rename_doc.py b/frappe/model/rename_doc.py index 12c57f2780..9b1bf09c4c 100644 --- a/frappe/model/rename_doc.py +++ b/frappe/model/rename_doc.py @@ -3,13 +3,29 @@ from __future__ import unicode_literals, print_function import frappe -from frappe import _ +from frappe import _, bold from frappe.utils import cint from frappe.model.naming import validate_name from frappe.model.dynamic_links import get_dynamic_link_map from frappe.utils.password import rename_password from frappe.model.utils.user_settings import sync_user_settings, update_user_settings_data + +@frappe.whitelist() +def update_document_title(doctype, docname, title_field, old_title, new_title, old_name, new_name): + """ + Update title from header in form view + """ + if new_title and old_title != new_title: + frappe.db.set_value(doctype, docname, title_field, new_title) + frappe.msgprint(_('Saved'), alert=True, indicator='green') + + if new_name and old_name != new_name: + return rename_doc(doctype, old_name, new_name) + + return old_name + + @frappe.whitelist() def rename_doc(doctype, old, new, force=False, merge=False, ignore_permissions=False, ignore_if_exists=False): """ @@ -83,6 +99,7 @@ def rename_doc(doctype, old, new, force=False, merge=False, ignore_permissions=F frappe.clear_cache() frappe.enqueue('frappe.utils.global_search.rebuild_for_doctype', doctype=doctype) + frappe.msgprint(_('Document renamed from {0} to {1}').format(bold(old), bold(new)), alert=True, indicator='green') return new diff --git a/frappe/public/js/frappe/form/toolbar.js b/frappe/public/js/frappe/form/toolbar.js index 7f5882f517..200640ee2b 100644 --- a/frappe/public/js/frappe/form/toolbar.js +++ b/frappe/public/js/frappe/form/toolbar.js @@ -52,10 +52,14 @@ frappe.ui.form.Toolbar = Class.extend({ this.set_indicator(); }, is_title_editable: function() { - if (this.frm.meta.title_field==="title" + let title_field = this.frm.meta.title_field; + let doc_field = this.frm.get_docfield(title_field); + + if (title_field && this.frm.perm[0].write - && !this.frm.get_docfield("title").options - && !this.frm.doc.__islocal) { + && !this.frm.doc.__islocal + && doc_field.fieldtype === "Data" + && !doc_field.read_only) { return true; } else { return false; @@ -64,25 +68,82 @@ frappe.ui.form.Toolbar = Class.extend({ can_rename: function() { return this.frm.perm[0].write && this.frm.meta.allow_rename && !this.frm.doc.__islocal; }, - setup_editable_title: function() { - var me = this; - this.page.$title_area.find(".title-text").on("click", function() { - if(me.is_title_editable()) { - frappe.prompt({fieldname: "title", fieldtype:"Data", - label: __("Title"), reqd: 1, "default": me.frm.doc.title }, - function(data) { - if(data.title) { - me.frm.set_value("title", data.title); - if(!me.frm.doc.__islocal) { - me.frm.save_or_update(); - } else { - me.set_title(); - } - } - }, __("Edit Title"), __("Update")); + setup_editable_title: function () { + let me = this; + + this.page.$title_area.find(".title-text").on("click", () => { + let fields = []; + let doctype = me.frm.doctype; + let docname = me.frm.doc.name; + let title_field = me.frm.meta.title_field || ''; + + // check if title is updateable + if (me.is_title_editable()) { + let title_field_label = me.frm.get_docfield(title_field).label; + + fields.push({ + label: __("New {0}", [__(title_field_label)]), + fieldname: "title", + fieldtype: "Data", + reqd: 1, + default: me.frm.doc[title_field] + }); } - if(me.can_rename()) { - me.frm.rename_doc(); + + // check if docname is updateable + if (me.can_rename()) { + fields.push(...[{ + label: __("New Name"), + fieldname: "name", + fieldtype: "Data", + reqd: 1, + default: docname + }, { + label: __("Merge with existing"), + fieldname: "merge", + fieldtype: "Check", + default: 0 + }]); + } + + // create dialog + if (fields.length > 0) { + let d = new frappe.ui.Dialog({ + title: __("Rename"), + fields: fields + }); + d.show(); + + d.set_primary_action(__("Rename"), function () { + let args = d.get_values(); + if (args.title != me.frm.doc[title_field] || args.name != docname) { + frappe.call({ + method: "frappe.model.rename_doc.update_document_title", + args: { + doctype, + docname, + title_field, + old_title: me.frm.doc[title_field], + new_title: args.title, + old_name: docname, + new_name: args.name + }, + btn: d.get_primary_btn() + }).then((res) => { + me.frm.reload_doc(); + if (!res.exc && (args.name != docname)) { + $(document).trigger("rename", [doctype, docname, res.message || args.name]); + if (locals[doctype] && locals[doctype][docname]) delete locals[doctype][docname]; + } + }); + } else { + frappe.show_alert({ + indicator: "yellow", + message: __("Unchanged") + }); + } + d.hide(); + }); } }); },