# Copyright (c) 1997-2006 # Ewgenij Gawrilow, Michael Joswig (Technische Universitaet Berlin, Germany) # http://www.math.tu-berlin.de/polymake, mailto:polymake@math.tu-berlin.de # # This program is free software; you can redistribute it and/or modify it # under the terms of the GNU General Public License as published by the # Free Software Foundation; either version 2, or (at your option) any # later version: http://www.gnu.org/licenses/gpl.txt. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. #----------------------------------------------------------------------------- # $Project: polymake $$Id: JavaViewInteractiveViewer.pm 7573 2007-01-19 11:56:54Z thilosch $ use Poly::Sockets; package JavaView::Viewer::WindowParams; use Struct ( [ new => '$' ], [ '$embedding' => '#1' ], '$client', '@client_args', '%client_params', '$launcher_class', '@jars', '%jre_properties', ); # will overload it later unimport_function(*new); sub compose_command { my ($self, $socket_no)=@_; ( $self->client, map { $_ eq "==FD==" ? $socket_no : $_ } @{$self->client_args}, map { ("-$_", (defined($self->client_params->{$_}) ? ($self->client_params->{$_}) : ())) } keys %{$self->client_params}, ) } package JavaView::Viewer::Window; use Struct ( [ '@ISA' => 'JavaView::File' ], [ new => '$' ], [ '$title' => '#1' ], [ '$workfile' => 'undef' ], [ '$params' => 'undef' ], ); sub append { my $self=shift; foreach my $elem (@_) { if (defined (my $p=$elem->{points})) { if (defined (my $dyn=detect_dynamic($p))) { if (defined $self->params) { die "multiple interactive components in the same window are not supported\n" if $self->params->embedding != $dyn; } else { $self->params=new WindowParams($dyn); } my @indices=flatten_indices($p); $elem->{points}=[ map { "$_ 0 0" } @indices ? @indices : 0..$p->get_n_vertices-1 ]; $elem->{name} =~ s/^/dynamic:/; } } } $self->SUPER::append(@_); } package JavaView::Viewer::Interactive; my $static_launcher="de.tuberlin.polymake.common.JavaviewStaticControl"; use Struct ( '@windows', [ '$jvpid' => 'undef' ], [ '$jv_server_socket' => 'undef' ], [ '$jvx_socket' => 'undef' ], ); sub new_drawing { my ($self, $title)=@_; push @{$self->windows}, new Window($title); $self; } sub append { my $self=shift; $self->windows->[-1]->append(@_); } sub proceed { my ($self)=@_; # starter class with main() method my @classes=qw( de.tuberlin.polymake.common.Launcher ); my (@cl_sockets, @cl_ports, @clients, %jars, %jre_properties); foreach my $w (@{$self->windows}) { if (defined $w->params) { push @cl_sockets, new Poly::ServerSocket; push @clients, [ $w->params->compose_command($cl_sockets[-1]->fileno) ]; push @classes, $w->params->launcher_class, "-client_port", $cl_sockets[-1]->port; @jars{@{$w->params->jars}}=(); while (my ($prop, $value)=each %{$w->params->jre_properties}) { $jre_properties{$prop}=$value; } } else { push @classes, $static_launcher; } } ### FIXME: die "interactive viewer: unimplemented feature: cannot run several embedding clients simultaneously\n" if @clients>1; $self->jv_server_socket=new Poly::ServerSocket; my $jv_port=$self->jv_server_socket->port; if (!defined ($self->jvpid=fork)) { die "fork failed: $!\n"; } if (!$self->jvpid) { # child process undef @cl_sockets; undef $self->jv_server_socket; $jre_properties{"jv.licence"} = $install_top; if ($Switches::d) { $jre_properties{"polymake.debug"} = $Switches::d >= 2 ? "max" : "yes"; } my @bgColor = parse_color($JavaView::bgColor); $jre_properties{"polymake.javaview.bgcolor"} = $bgColor[1]; my @jre_args = map { "-D$_=$jre_properties{$_}" } keys %jre_properties; my $jar_path = $main::InstallTop; if (-f "$jar_path/jars/common.jar") { $jar_path .= "/jars"; } elsif (-f "$jar_path/java_build/common.jar") { $jar_path .= "/java_build"; } my $classpath = join(":", (map { "$jar_path/$_.jar" } keys %jars), "$jar_path/common.jar:$classpath"); my @java_command = ($java, @jre_args, "-cp", $classpath, @classes, "-ps_port", $jv_port); dbg_print( "launching @java_command" ) if $Switches::d; exec @java_command; die "exec($java_command[0]) failed: $!\n"; } # end child process my $JVX = $self->jvx_socket = $self->jv_server_socket->accept; { my $old_handle = select $JVX; $| = 1; select $old_handle; } foreach my $w (@{$self->windows}) { my $initial_jvx = $w->toString; warn $initial_jvx if $Switches::d>=2; print $JVX $initial_jvx; } foreach (@clients) { ### FIXME: background_client when implemented client(@$_); } $self; } sub DESTROY { my ($self)=@_; # it's JavaView that shuts down the connection, hence just wait here waitpid $self->jvpid, 0 if $self->jvpid; undef $self->jvx_socket; undef $self->jv_server_socket; } 1 # Local Variables: # c-basic-offset:3 # End: