view release on metacpan or search on metacpan
1.0.10 2002/03/08 joern
Bugfixes:
- setting Reply-To didn't work
Features:
- added "Reply Group" button which replies to the address
of the "To:" header field. Useful for replying into
mailing lists.
- you can simply specify another From address per mail
by selecting the appropriate entry of the recipient
popup in the compose mail dialog.
- if you have many email aliases forwarded to one account
this one is for you: when replying JaM checks the To:
field against the addresses listed in the Non-Reply
user configuration field (it assumes that these are
your aliases). The first address which matches and
is not your normal From: address configured in the
mail account window, will be set as From by default.
This way you don't change your address inside one
thread, if a mail was posted to one of your alias
addresses.
multi value fields
- it was not possible to save html filtered mail
attachments
- when replying to a mail with "reply all" all recipients
were added to the "To" header field, instead of using
'CC' for other recipients than the original sender.
0.9.4 2001/08/16 joern
Bugfixes:
- input filter were applied on outgoing mails sometimes
- filter adding via folder and subject popup menus did
not work
- path values of folders are now computed correctly,
when folder with childs move
- name clashing is prevented now when creating, moving
and renaming folders
- the folder "Mail" is not displayed anymore. it only
wastes space and can confuse if someone drops a folder
beside it
Features:
- reset schema version to 1 (yet possible, because there
are no production installations, what will change soon ;)
- today I throw away my Netscape Mailer
0.9.2 2001/08/14 joern
New Features:
- parent folders with child folders which have unread
mail can be colored differently. the new configuration
parameter pushes schema version to 2.
- quickly adding new filter rules now via right click folder
popup menu. target folder will be set accordingly.
- quickly adding new filter rules now via right click subjects
popup menu. target folder will be set accordingly *and*
toccfrom will be set to the "To:" adresse of the clicked mail.
this way you create mailing list filters with one click.
- quick search via right click subjects menu for
- sender
- subject
- body
- recipient
lib/JaM/GUI/Folders.pm view on Meta::CPAN
my ($closed_pix, $closed_mask);
my ($opened_pix, $opened_mask);
my ($leaf_pix, $leaf_mask);
# get/set selected Folder
sub selected_folder_object { my $s = shift; $s->{selected_folder_object }
= shift if @_; $s->{selected_folder_object} }
# get/set selected Folder object on which a Popup is requested
sub popup_folder_object { my $s = shift; $s->{popup_folder_object}
= shift if @_; $s->{popup_folder_object} }
# get/set selected row on which a Popup is requested
sub popup_row { my $s = shift; $s->{popup_row}
= shift if @_; $s->{popup_row} }
# get/set list ref of folder gtk items
sub gtk_folder_items { my $s = shift; $s->{gtk_folder_items}
= shift if @_; $s->{gtk_folder_items} }
# get/set gtk object for folder scrollable window
sub gtk_folders { my $s = shift; $s->{gtk_folders}
= shift if @_; $s->{gtk_folders} }
# get/set gtk object for folder ctree
lib/JaM/GUI/Folders.pm view on Meta::CPAN
= shift if @_; $s->{gtk_read_style} }
# get/set gtk style for folder with unread mails
sub gtk_unread_style { my $s = shift; $s->{gtk_unread_style}
= shift if @_; $s->{gtk_unread_style} }
# get/set gtk style for folder with unread child folders
sub gtk_unread_child_style { my $s = shift; $s->{gtk_unread_child_style}
= shift if @_; $s->{gtk_unread_child_style} }
# popup menu separator for "Create Template"
sub gtk_template_sep { my $s = shift; $s->{gtk_template_sep}
= shift if @_; $s->{gtk_template_sep} }
# popup menu item for "Create Template"
sub gtk_template_item { my $s = shift; $s->{gtk_template_item}
= shift if @_; $s->{gtk_template_item} }
sub gtk_ignore_reply_to { my $s = shift; $s->{gtk_ignore_reply_to}
= shift if @_; $s->{gtk_ignore_reply_to} }
sub gtk_dont_ignore_reply_to
{ my $s = shift; $s->{gtk_dont_ignore_reply_to}
= shift if @_; $s->{gtk_dont_ignore_reply_to} }
lib/JaM/GUI/Folders.pm view on Meta::CPAN
$self->add_tree (
tree => $root_tree,
parent_id => 1
);
$folders->show;
$root_tree->signal_connect('button_press_event', sub { $self->cb_click_clist(@_) } );
# now build popup Menu
my $popup = $root_tree->{popup} = Gtk::Menu->new;
my $item;
$item = Gtk::MenuItem->new ("Advanced Search...");
$popup->append($item);
$item->signal_connect ("activate", sub {$self->cb_search_in_folder ( @_ ) } );
$item->show;
$item = Gtk::MenuItem->new;
$popup->append($item);
$item->show;
$item = Gtk::MenuItem->new ("Rename Folder...");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_rename_folder ( @_ ) } );
$item->show;
$item = Gtk::MenuItem->new ("Create New Folder...");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_create_folder ( @_ ) } );
$item->show;
$item = Gtk::MenuItem->new ("Delete Folder...");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_delete_folder ( @_ ) } );
$item->show;
$item = Gtk::MenuItem->new;
$popup->append($item);
$item->show;
$item = Gtk::MenuItem->new ("Add Input Filter...");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_add_input_filter ( @_ ) } );
$item->show;
$item = Gtk::MenuItem->new;
$popup->append($item);
$item->show;
my $ignore_reply_to_item = Gtk::RadioMenuItem->new_with_label ("Ignore Reply-To Header");
$popup->append($ignore_reply_to_item);
$ignore_reply_to_item->signal_connect ("activate", sub { $self->cb_ignore_reply_to ( @_ ) } );
$ignore_reply_to_item->show;
$self->gtk_ignore_reply_to ($ignore_reply_to_item);
$item = Gtk::RadioMenuItem->new_with_label ("Don't ignore Reply-To Header", $ignore_reply_to_item);
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_dont_ignore_reply_to ( @_ ) } );
$item->show;
$self->gtk_dont_ignore_reply_to ($item);
$item = Gtk::MenuItem->new;
$popup->append($item);
$self->gtk_template_sep ( $item );
$item = Gtk::MenuItem->new ("Create New Template...");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_create_new_template ( @_ ) } );
$self->gtk_template_item ( $item );
$self->widget ($folders);
$self->update_folder_stati;
return $self;
}
lib/JaM/GUI/Folders.pm view on Meta::CPAN
return $item;
}
sub cb_click_clist {
my $self = shift;
my ($widget, $event) = @_;
my ( $row, $column ) = $widget->get_selection_info( $event->{x}, $event->{y} );
$self->popup_folder_object (
JaM::Folder->by_id($widget->node_nth( $row )->{folder_id})
);
$self->popup_row ($widget->node_nth( $row ));
if ( $event->{button} == 3 and $widget->{'popup'} ) {
if ( $self->popup_folder_object->folder_id ==
$self->config('templates_folder_id') ) {
$self->gtk_template_sep->show;
$self->gtk_template_item->show;
} else {
$self->gtk_template_sep->hide;
$self->gtk_template_item->hide;
}
if ( $self->popup_folder_object->ignore_reply_to ) {
$self->gtk_ignore_reply_to->set_active(1);
} else {
$self->gtk_dont_ignore_reply_to->set_active(1);
}
$widget->{'popup'}->popup(undef,undef,$event->{button},1);
}
1;
}
sub cb_rename_folder {
my $self = shift;
my $folder_object = $self->popup_folder_object;
my $name = $folder_object->name;
my $dialog;
$dialog = $self->folder_dialog (
title => "Rename Folder",
label => "Enter new name for folder '$name'",
value => $name,
cb => sub {
my ($text) = @_;
return $self->rename_folder (
lib/JaM/GUI/Folders.pm view on Meta::CPAN
);
}
);
1;
}
sub cb_search_in_folder {
my $self = shift;
my $folder_object = $self->popup_folder_object;
require JaM::GUI::Search;
my $search = JaM::GUI::Search->new (
dbh => $self->dbh
);
$search->open_window;
$search->folder_chosen ($folder_object->id);
1;
lib/JaM/GUI/Folders.pm view on Meta::CPAN
$folder_object->save;
$self->update_folder_item ( folder_object => $folder_object );
1;
}
sub cb_create_folder {
my $self = shift;
my $folder_object = $self->popup_folder_object;
my $dialog;
$dialog = $self->folder_dialog (
title => "Create Folder",
label => "Enter name for the new folder",
value => "",
cb => sub {
my ($text) = @_;
return $self->create_folder (
parent_folder_object => $folder_object,
lib/JaM/GUI/Folders.pm view on Meta::CPAN
# update item (may be it has been renamed)
$self->update_folder_item ( folder_object => $moved_object );
1;
}
sub cb_delete_folder {
my $self = shift;
my $folder_object = $self->popup_folder_object;
my $trash_id = $self->config('trash_folder_id');
my $trash_object = JaM::Folder->by_id($trash_id);
# check if this *is* the trash folder itself
if ( $trash_id == $folder_object->id ) {
$self->message_window (
message => "You can't trash trash."
);
return 1;
lib/JaM/GUI/Folders.pm view on Meta::CPAN
if ( not $filter ) {
require JaM::GUI::IO_Filter;
$filter = JaM::GUI::IO_Filter->new (
dbh => $self->dbh,
);
$filter->open_window;
}
$filter->add_new_filter (
folder_object => $self->popup_folder_object
);
$filter->gtk_win->focus(1);
1;
}
sub empty_trash_folder {
my $self = shift;
lib/JaM/GUI/Folders.pm view on Meta::CPAN
$self->comp('folders')->update_folder_item (
folder_object => $folder
);
1;
}
sub cb_ignore_reply_to {
my $self = shift;
my $folder_object = $self->popup_folder_object;
$folder_object->ignore_reply_to (1);
$folder_object->save;
1;
}
sub cb_dont_ignore_reply_to {
my $self = shift;
my $folder_object = $self->popup_folder_object;
$folder_object->ignore_reply_to (0);
$folder_object->save;
1;
}
1;
lib/JaM/GUI/HTMLSurface.pm view on Meta::CPAN
= shift if @_; $s->{handle} }
sub image_pool { my $s = shift; $s->{image_pool}
= shift if @_; $s->{image_pool} }
sub url_in_focus { my $s = shift; $s->{url_in_focus}
= shift if @_; $s->{url_in_focus} }
sub button3_callback{ my $s = shift; $s->{button3_callback}
= shift if @_; $s->{button3_callback} }
sub mail_link_callback { my $s = shift; $s->{mail_link_callback}
= shift if @_; $s->{mail_link_callback} }
sub gtk_attachment_popup { my $s = shift; $s->{gtk_attachment_popup}
= shift if @_; $s->{gtk_attachment_popup} }
sub new {
my $type = shift;
my %par = @_;
my ($image_dir, $button3_callback, $mail_link_callback) =
@par{'image_dir','button3_callback','mail_link_callback'};
my $widget;
lib/JaM/GUI/HTMLSurface.pm view on Meta::CPAN
$widget->signal_connect ('url_requested', sub { $self->cb_url_requested (@_) } );
# $widget->signal_connect ('object_requested', sub { $self->cb_object_requested (@_) } );
$widget->signal_connect ('on_url', sub { $self->cb_on_url (@_) } );
# $widget->signal_connect ('link_clicked', sub { $self->cb_link_clicked (@_) } );
$widget->signal_connect ('button_press_event', sub { $self->cb_button_press (@_) } );
# $widget->signal_connect ('button_release_event', sub { print Dumper (\@_) } );
$widget->show;
# build popup menu for attachments
my $popup = $self->gtk_attachment_popup (Gtk::Menu->new);
my $item = Gtk::MenuItem->new ("Save as ...");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_save_attachment_file_dialog ( @_ ) } );
$item->show;
return $self;
}
sub show_eval {
my $self = shift;
my %par = @_;
my ($file) = @par{'file'};
lib/JaM/GUI/HTMLSurface.pm view on Meta::CPAN
my $browser_prog = $self->config('browser_prog');
system ("$browser_prog -remote 'openURL($url)' >/dev/null 2>&1 &");
return 1;
} elsif ( $url =~ /mailto:([^\s]+)/ ) {
my $cb = $self->mail_link_callback;
&$cb( address => $1 );
return 1;
}
if ( $event->{button} == 3 ) {
$self->gtk_attachment_popup->popup (undef, undef, $event->{button}, 0);
} elsif ( $event->{button} == 1 ) {
$self->cb_save_attachment_file_dialog;
}
}
sub cb_save_attachment_file_dialog {
my $self = shift;
my $url = $self->url_in_focus;
return if not $url;
lib/JaM/GUI/IO_Filter.pm view on Meta::CPAN
$folder_entry->show;
$folder_entry->set_text("Click to select folder");
$folder_entry->set_editable(0);
$self->gtk_filter_folder ( $folder_entry );
my $folder_menu = $self->gtk_folder_menu;
$folder_entry->signal_connect('button_press_event', sub {
my ($widget, $event) = @_;
$folder_menu->popup (undef, undef, undef, $event->{button});
});
$radio1_hbox->pack_start($radio1, 0, 1, 0);
$radio1_hbox->pack_start($folder_entry, 1, 1, 0);
$radio_vbox->pack_start($radio1_hbox, 0, 1, 0);
$radio_vbox->pack_start($radio2, 0, 1, 0);
$table->attach_defaults ($label, 0, 1, 1, 2);
$table->attach_defaults ($radio_vbox, 1, 2, 1, 2);
lib/JaM/GUI/Mail.pm view on Meta::CPAN
use JaM::GUI::HTMLSurface;
# get/set gtk object for mail content scrolled window
sub gtk_mail_html { my $s = shift; $s->{gtk_mail_html}
= shift if @_; $s->{gtk_mail_html} }
# get/set gtk object for mail content HTMLSurface object
sub gtk_mail_html_object{ my $s = shift; $s->{gtk_mail_html_object}
= shift if @_; $s->{gtk_mail_html_object} }
# get/set gtk object for mail popup menu
sub gtk_popup { my $s = shift; $s->{gtk_popup}
= shift if @_; $s->{gtk_popup} }
# get/set actual viewed mail (JaM::Mail object)
sub mail { my $s = shift; $s->{mail}
= shift if @_; $s->{mail} }
# get/set actual flag for viewing all header fields or only common fields
sub show_all_header { my $s = shift; $s->{show_all_header}
= shift if @_; $s->{show_all_header} }
# this flag controls whether mails status should be changed when viewd
lib/JaM/GUI/Mail.pm view on Meta::CPAN
# build mail viewer widget
sub build {
my $self = shift;
# Create a table to hold the text widget and scrollbars
my $sw = new Gtk::ScrolledWindow(undef, undef);
$sw->set_policy('automatic', 'automatic');
my $html = JaM::GUI::HTMLSurface->new (
image_dir => "/tmp",
button3_callback => sub { $self->popup_menu(@_) },
mail_link_callback => sub { $self->open_mail_link_window ( @_ ) }
);
my $widget = $html->widget;
$sw->show;
$sw->add($widget);
# Add a handler to put a message in the html widget when it is realized
$self->gtk_mail_html ($widget);
$self->gtk_mail_html_object ($html);
$self->widget ($sw);
# build popup menu for right click
my $item;
my $popup = $self->gtk_popup (Gtk::Menu->new);
$item = Gtk::MenuItem->new ("Show only common header fields");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_show_all_header(0) } );
$item->show;
$item = Gtk::MenuItem->new ("Show complete header");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_show_all_header(1) } );
$item->show;
return $self;
}
sub show {
my $self = shift;
my %par = @_;
my ($mail_id) = @par{'mail_id'};
lib/JaM/GUI/Mail.pm view on Meta::CPAN
$widget->write ($entity->filename);
$widget->br;
$widget->bold ("Size: ");
$widget->write (int($entity->content_length/1024)." KB");
$widget->br;
$widget->write ("</td></tr></table>");
}
sub popup_menu {
my $self = shift;
my ($event) = @_;
$self->gtk_popup->popup (undef, undef, $event->{button}, 0);
}
sub cb_show_all_header {
my $self = shift;
my ($flag) = @_;
$self->show_all_header($flag);
return if not $self->mail;
$self->show (mail_id => $self->mail->mail_id);
1;
}
lib/JaM/GUI/MailAsHTML.pm view on Meta::CPAN
use strict;
use Carp;
sub widget { confess "widget called" }
sub image_dir { confess "image_dir called" }
sub handle { confess "handle called" }
sub image_pool { return {} }
sub url_in_focus { confess "url_in_focus called" }
sub gtk_attachment_popup { confess "gtk_attachment_popup called" }
sub html { my $s = shift; $s->{html}
= shift if @_; $s->{html} }
sub new {
my $type = shift;
my %par = @_;
my ($quote) = @par{'quote'};
my $self = bless {
lib/JaM/GUI/MailAsText.pm view on Meta::CPAN
use strict;
use Carp;
sub widget { confess "widget called" }
sub image_dir { confess "image_dir called" }
sub handle { confess "handle called" }
sub image_pool { return {} }
sub url_in_focus { confess "url_in_focus called" }
sub gtk_attachment_popup { confess "gtk_attachment_popup called" }
sub text { my $s = shift; $s->{text}
= shift if @_; $s->{text} }
sub quote { my $s = shift; $s->{quote}
= shift if @_; $s->{quote} }
sub wrap_length { my $s = shift; $s->{quote}
= shift if @_; $s->{quote} }
sub new {
my $type = shift;
lib/JaM/GUI/Search.pm view on Meta::CPAN
my $folder_label = Gtk::Label->new ("Search in folder");
$folder_label->show;
my $folder_entry = Gtk::Entry->new;
$folder_entry->show;
$folder_entry->set_text("Click to select folder");
$folder_entry->set_editable(0);
$folder_entry->set_usize(200, 20);
$folder_entry->signal_connect('button_press_event', sub {
my ($widget, $event) = @_;
$folder_menu->popup (undef, undef, undef, $event->{button});
});
my $folder_recursive = Gtk::CheckButton->new ("Include subfolders");
$folder_recursive->show;
$folder_recursive->set_active(0);
$folder_recursive->signal_connect ('clicked', sub {
$self->search_recursive ( $folder_recursive->get_active );
});
my $search_button = Gtk::Button->new (" Start Query ");
lib/JaM/GUI/Subjects.pm view on Meta::CPAN
use strict;
use JaM::Func;
use JaM::GUI::Component;
my $DEBUG = 1;
# get/set currently listed mails
sub mail_ids { my $s = shift; $s->{mail_ids}
= shift if @_; $s->{mail_ids} }
# get/set currently mail id where popup opened
sub popup_mail_id { my $s = shift; $s->{popup_mail_id}
= shift if @_; $s->{popup_mail_id} }
# get/set currently selected folder
sub folder_object { my $s = shift; $s->{folder_object}
= shift if @_; $s->{folder_object} }
# get/set gtk object for subjects scrolled window
sub gtk_subjects { my $s = shift; $s->{gtk_subjects}
= shift if @_; $s->{gtk_subjects} }
# get/set gtk object for subjects clist
lib/JaM/GUI/Subjects.pm view on Meta::CPAN
$self->config('subjects_column_'.$_[1], $_[2]);
}
);
$subjects->signal_connect("size-allocate",
sub { $self->config('subjects_height', $_[1]->[3]) }
);
}
$list->show();
# now build popup Menu
$list->signal_connect('button_press_event', sub { $self->cb_click_subjects(@_) } );
my $popup = $list->{popup} = Gtk::Menu->new;
my $item;
# $item = Gtk::MenuItem->new ("Mark selected mail(s) as read...");
# $popup->append($item);
# $item->signal_connect ("activate", sub { $self->cb_mark_mail_as_read ( @_ ) } );
# $item->show;
my $folder_menu_item = Gtk::MenuItem->new ("Move selected mail(s) to folder...");
$popup->append($folder_menu_item);
$folder_menu_item->show;
my $folder_menu = $self->comp('folders')->build_menu_of_folders (
callback => sub { $self->move_selected_mails ( folder_id => $_[0] ); }
);
$folder_menu_item->set_submenu($folder_menu);
$item = Gtk::MenuItem->new;
$popup->append($item);
$item->show;
$item = Gtk::MenuItem->new ("Add Input Filter...");
$popup->append($item);
$item->signal_connect ("activate", sub { $self->cb_add_input_filter ( @_ ) } );
$item->show;
if ( not $without_quick_search ) {
$item = Gtk::MenuItem->new;
$popup->append($item);
$item->show;
$item = Gtk::MenuItem->new ("Quick Search Sender...");
$popup->append($item);
$item->signal_connect ("activate", sub {
$self->comp('subjects')->quick_search(
type => 'sender'
);
});
$item->show;
$item = Gtk::MenuItem->new ("Quick Search Subject...");
$popup->append($item);
$item->signal_connect ("activate", sub {
$self->comp('subjects')->quick_search(
type => 'subject'
);
});
$item->show;
$item = Gtk::MenuItem->new ("Quick Search Body...");
$popup->append($item);
$item->signal_connect ("activate", sub {
$self->comp('subjects')->quick_search(
type => 'body'
);
});
$item->show;
$item = Gtk::MenuItem->new ("Quick Search Recipient...");
$popup->append($item);
$item->signal_connect ("activate", sub {
$self->comp('subjects')->quick_search(
type => 'recipient'
);
});
$item->show;
$item = Gtk::MenuItem->new;
$popup->append($item);
$item->show;
$item = Gtk::MenuItem->new ("Advanced Search...");
$popup->append($item);
$item->signal_connect ("activate", sub {
require JaM::GUI::Search;
my $search = JaM::GUI::Search->new (
dbh => $self->dbh
);
$search->open_window;
$search->folder_chosen ($self->folder_object->id);
});
$item->show;
lib/JaM/GUI/Subjects.pm view on Meta::CPAN
return $self;
}
sub cb_click_subjects {
my $self = shift;
my ($widget, $event) = @_;
my ( $row, $column ) = $widget->get_selection_info( $event->{x}, $event->{y} );
if ( $self->mail_ids ) {
$self->popup_mail_id ( $self->mail_ids->[$row] );
} else {
$self->popup_mail_id (undef);
}
if ( $event->{button} == 3 and $widget->{'popup'} ) {
my $folder_menu_item = $self->gtk_folder_menu_item;
$folder_menu_item->remove_submenu;
my $folder_menu = $self->comp('folders')->build_menu_of_folders (
callback => sub { $self->move_selected_mails ( folder_id => $_[0] ); }
);
$folder_menu_item->set_submenu($folder_menu);
$widget->{'popup'}->popup(undef,undef,$event->{button},1);
}
1;
}
sub cb_add_input_filter {
my $self = shift;
my $filter;
eval { $filter = $self->comp('input_filter') };
if ( not $filter ) {
require JaM::GUI::IO_Filter;
$filter = JaM::GUI::IO_Filter->new (
dbh => $self->dbh,
);
$filter->open_window;
}
my $mail = JaM::Mail->load ( dbh => $self->dbh, mail_id => $self->popup_mail_id );
my $folder = JaM::Folder->by_id ($mail->folder_id);
$filter->add_new_filter (
folder_object => $folder,
mail_object => $mail
);
$filter->gtk_win->focus(1);
1;