Prima
view release on metacpan or search on metacpan
examples/dock.pl view on Meta::CPAN
=pod
=head1 NAME
examples/dock.pl - Docking widgets
=head1 FEATURES
This is the demonstration of Prima::Dock and Prima::DockManager
modules. The window created is docking client, and it's able
to accept toolbars and panels, and toolbars in turn accept buttons.
buttons are very samplish; there are two panels, Edit and Banner,
that are docked in different ways.
Note the following unevident features:
=over 4
=item popup on the border of the window ( and the Customize command there)
=item dragging of buttons on the window and the extreior
=item dragging panels and toolbar to the exterior
=item storing of the geometry in the ~/.demo_dock file
=back
=cut
use strict;
use warnings;
use Prima;
use Prima::Application;
use Prima::Edit;
use Prima::Buttons;
use Prima::DockManager;
use Prima::Utils;
package dmfp;
use constant Edit => 0x100000;
use constant Vertical => 0x200000;
use constant Horizontal => 0x400000;
# This is the main window. it's responsible for
# command handling and bar visiblity;
# NB - bars are not owned by this window when undocked.
package Prima::Dock::BasicWindow;
use vars qw(@ISA);
@ISA = qw(Prima::Window);
sub profile_default
{
my $def = $_[0]-> SUPER::profile_default;
my %prf = (
instance => undef,
);
@$def{keys %prf} = values %prf;
return $def;
}
sub init
{
my $self = shift;
my %profile = $self-> SUPER::init( @_);
$self-> $_($profile{$_}) for qw(instance);
$self-> {toolBarPopup} = $self-> insert( Popup =>
autoPopup => 0,
items => $self-> make_popupitems(),
);
$self-> {mainDock} = $self-> insert( FourPartDocker =>
rect => [ 0, 0, $self-> size],
fingerprint => dmfp::Tools|dmfp::Toolbar|dmfp::Edit|dmfp::Horizontal|dmfp::Vertical,
dockup => $self-> instance,
dockerCommonProfile => {
hasPocket => 0,
onPopup => sub { # all dockers would render this popup
my ( $me, $btn, $x, $y) = @_;
( $x, $y) = $self-> screen_to_client( $me-> client_to_screen($x, $y));
$self-> {toolBarPopup}-> popup( $x, $y);
$me-> clear_event;
}
},
dockerProfileClient => { # allow docking only to Edit
fingerprint => dmfp::Edit,
},
dockerProfileLeft => { fingerprint => dmfp::Vertical|dmfp::Tools|dmfp::Toolbar },
dockerProfileRight => { fingerprint => dmfp::Vertical|dmfp::Tools|dmfp::Toolbar },
dockerProfileTop => { fingerprint => dmfp::Horizontal|dmfp::Tools|dmfp::Toolbar },
dockerProfileBottom => { fingerprint => dmfp::Horizontal|dmfp::Tools|dmfp::Toolbar },
);
$self-> instance-> add_notification( 'ToolbarChange', \&on_toolbarchange, $self);
$self-> instance-> add_notification( 'PanelChange', \&on_toolbarchange, $self);
$self-> instance-> add_notification( 'Command', \&on_command, $self);
return %profile;
}
sub make_popupitems
{
my $items = $_[0]-> instance-> toolbar_menuitems( \&Menu_Check_Toolbars);
# actually DockManager doesn't care if panel CLSID and toolbar name intermix.
# this is the demonstration of resolving that clash
$$_[0] .= ',toolbar' for @$items;
push ( @$items, []);
push ( @$items, @{$_[0]-> instance-> panel_menuitems( \&Menu_Check_Panels)});
push ( @$items, []);
push ( @$items, ['customize' => "~Customize..." => q(open_dockmanaging)]);
return $items;
}
sub Menu_Check_Toolbars
{
my ( $self, $var) = @_;
my $toolname = $var;
$toolname =~ s/\,toolbar$//;
$self-> instance-> toolbar_visible(
$self-> instance-> toolbar_by_name($toolname),
$self-> {toolBarPopup}-> toggle( $var)
);
}
sub Menu_Check_Panels
{
my ( $self, $var) = @_;
$self-> instance-> panel_visible(
$var, $self-> {toolBarPopup}-> toggle( $var));
}
sub instance
{
return $_[0]-> {instance} unless $#_;
$_[0]-> {instance} = $_[1];
}
sub on_toolbarchange
{
$_[0]-> {toolBarPopup}-> items( $_[0]-> make_popupitems());
}
sub on_command
{
my ( $self, $instance, $command) = @_;
$command =~ s/\://g;
my $x = $self-> can( $command);
return unless $x;
$x-> ( $self);
}
# we'll take our actions we need to reflect the state.
sub open_dockmanaging
{
my $self = $_[0];
my $i = $self-> instance;
return if $i-> interactiveDrag;
my $wpanel = Prima::Window-> create(
name => 'Customize tools',
size => [ 400, 200],
onClose => sub {
$self-> {toolBarPopup}-> customize-> enabled(1);
$i-> interactiveDrag(0);
},
);
$i-> create_manager( $wpanel, dockerProfile => {
hint => 'Drag here unneeded buttons',
});
$i-> interactiveDrag(1);
$self-> {toolBarPopup}-> customize-> enabled(0);
}
sub get_docks
{
my $self = $_[0];
my @docks = ( $self-> {mainDock});
my $sid = $self-> {mainDock}-> open_session({
self => $self-> {mainDock},
sizes => [[0,0]],
sizeable => [1,1],
});
if ( $sid) {
while ( 1) {
my $x = $self-> {mainDock}-> next_docker( $sid);
last unless $x;
next if $x-> isa(q(Prima::DockManager::LaunchPad));
push ( @docks, $x);
}
$self-> {mainDock}-> close_session( $sid);
}
return @docks;
}
sub init_read
{
my ( $self, $fd) = @_;
my $last = undef;
my @docks = $self-> get_docks;
my $state;
my %docks = map { my $x = $_-> name; $x =~ s/(\W)/\%sprintf("%02x",$1)/; $x => $_} @docks;
examples/dock.pl view on Meta::CPAN
},
profile => {
vScroll => 1,
text => '',
},
});
$i-> register_panel( 'Banner' => {
class => 'Banner',
text => 'Banner window',
dockerProfile => {
fingerprint => dmfp::Horizontal,
size => [ 200, 30]
},
});
my $resFile = Prima::Utils::path('demo_dock');
# after all that, creating window ( the window itself is of small importance...)
my $ww = Prima::Dock::BasicWindow -> create(
instance => $i,
onClose => sub {
if ( open F, "> $resFile") {
$_[0]-> init_write( *F);
close F;
} else {
warn "Cannot open $resFile:$!\n";
};
},
onDestroy => sub {
$::application-> destroy;
},
size => [ 400, 400],
text => 'Docking example',
onActivate => sub { $i-> activate; },
onWindowState => sub { $i-> windowState( $_[1]); },
);
# opening predefined bars
if ( open F, $resFile) {
$ww-> init_read(*F);
close F;
} else {
$i-> predefined_panels( "Edit" => $ww-> {mainDock}-> ClientDocker);
}
$i-> predefined_toolbars( {
name => "File",
list => ["File::Open", "File::Close"],
dock => $ww-> {mainDock}-> TopDocker,
origin => [ 0, 0],
}, {
name => "Edit",
list => [ "Edit::OK", "Edit::Cancel", ],
dock => $ww-> {mainDock}-> TopDocker,
origin => [ 0, 0],
});
#$ww-> open_dockmanaging; # uncomment this for Customize window popup immediately
run Prima;
1;
( run in 0.521 second using v1.01-cache-2.11-cpan-364913b4093 )