#!/usr/bin/env python

# This file is part of Window-Switch.
# Copyright (c) 2009-2013 Antoine Martin <antoine@nagafix.co.uk>
# Window-Switch is released under the terms of the GNU GPL v3

import pygtk
pygtk.require("2.0")
import gtk
import gobject

from winswitch.util.simple_logger import Logger
from winswitch.ui.ui_util import get_ui_util
from winswitch.ui import icons



dialog_util = None
def get_dialog_util():
	global dialog_util
	if not dialog_util:
		dialog_util = Dialog_Util()
	return	dialog_util

class Dialog_Util:

	def __init__(self):
		Logger(self, log_colour=Logger.HIGHLIGHTED_BLUE)
		self.dialogs = {}					#maps UUID to a dialog

	def close(self):
		self.close_dialogs()


	#****************************************************************
	# Dialogs util
	# you can call do_xxx from UI threads (ie: event callbacks)
	def ask(self, title, text, cancel_callback, ok_callback, password=False, ask_save_password=False, buttons=None, icon=None, UUID=None):
		gobject.idle_add(self.do_ask, title, text, cancel_callback, ok_callback, password, ask_save_password, buttons, icon, UUID)

	def do_ask(self, title, text, cancel_callback, ok_callback, password=False, ask_save_password=False, buttons=None, icon=None, UUID=None):
		box = gtk.VBox(False, 0)
		for s in text.split("\n"):
			label = gtk.Label(s)
			label.set_padding(20, 0)
			box.pack_start(label)
		self.do_ask_dialog(title, [box], cancel_callback, ok_callback, password, ask_save_password, buttons, icon, UUID)
		return	False

	def do_ask_dialog(self, title, body_parts, cancel_callback, ok_callback, password=False, ask_save_password=False, buttons=None, icon=None, UUID=None):
		self.slog(None, title, body_parts, cancel_callback, ok_callback, password, ask_save_password, buttons, icon, UUID)
		if buttons is None:
			buttons = (gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL, gtk.STOCK_OK, gtk.RESPONSE_OK)
		dialog = gtk.Dialog(title, None, gtk.DIALOG_MODAL, buttons)
		dialog.set_default_response(gtk.RESPONSE_OK)
		dialog.vbox.set_spacing(10)
		dialog.set_border_width(15)
		if icon:
			dialog.set_icon(icon)
		else:
			dialog.set_icon(icons.get("winswitch"))
		dialog.vbox.pack_start(get_ui_util().make_label(title,"sans 14"))
		for part in body_parts:
			dialog.vbox.pack_start(part)
		password_field = None
		if password:
			password_field = gtk.Entry(max=64)
			password_field.set_width_chars(24)
			password_field.set_visibility(False)
			dialog.vbox.pack_start(password_field)
		save_password = None
		if ask_save_password:
			if ask_save_password is True:
				save_label = "save password"
			else:
				save_label = ask_save_password
			save_password = gtk.CheckButton(save_label)
			dialog.vbox.pack_start(save_password)

		if UUID:
			existing_dialog = self.dialogs.get(UUID)
			if existing_dialog:
				try:
					existing_dialog.destroy()
				except Exception, e:
					self.serr(None, e, title, body_parts, cancel_callback, ok_callback, password, buttons, icon)
		#dismiss = gtk.CheckButton("Do not show this warning again")
		#dialog.vbox.pack_start(dismiss)
		def close_dialog(*args):
			dialog.destroy()
		get_ui_util().add_close_accel(dialog, close_dialog)

		def ask_response_callback(dialog, response_id):
			self.sdebug(None, dialog, response_id)
			if response_id==gtk.RESPONSE_OK and ok_callback:
				if password_field:
					password = password_field.get_text()
					close_dialog()
					if save_password:
						ok_callback(password, save_password.get_active())
					else:
						ok_callback(password)
				else:
					close_dialog()
					ok_callback()
				return
			if response_id==gtk.RESPONSE_CANCEL and cancel_callback:
				close_dialog()
				cancel_callback()
				return
			close_dialog()

		if password_field:
			def password_activated(*args):
				ask_response_callback(dialog, gtk.RESPONSE_OK)
				dialog.destroy()
			password_field.connect("activate", password_activated)

		dialog.connect('response', lambda dialog, response_id: ask_response_callback(dialog, response_id))
		if cancel_callback:
			dialog.connect('close', cancel_callback)
		if UUID:
			def dialog_closed(*args):
				if UUID in self.dialogs.keys():
					del self.dialogs[UUID]
			dialog.connect('close', dialog_closed)
			self.dialogs[UUID] = dialog
		dialog.set_keep_above(True)
		dialog.show_all()
		dialog.present()


	def close_dialogs(self):
		for UUID,dialog in self.dialogs.items():
			try:
				dialog.destroy()
			except Exception, e:
				self.serr("closing %s" % UUID, e)
		self.dialogs = {}

	def cancel_ask(self, UUID):
		dialog = self.dialogs.get(UUID)
		if not dialog:
			self.sdebug("dialog already closed", UUID)
			return
		self.sdebug("calling %s.destroy()" % dialog, UUID)
		try:
			dialog.destroy()
		except Exception, e:
			self.err("failed to close %s" % dialog, e, UUID)
		del self.dialogs[UUID]
