#=============================================== # TkArrhenius #=============================================== package TkArrhenius; use clib::TkFittingCommon; @ISA = qw(TkFittingCommon); #公開したいサブルーチン #@EXPORT = qw(DelSpace Reduce01 MakePath RegExpQuote); use strict; use Utils; use IniFile; use CSV; use MyTk::GraphFrameArray; use GraphData; use MultiColumnData; use Sci qw($pi $kB $e $e0 $me $h $hbar $KToeV erfc); use Sci::ConductingMaterial; use Sci::Optimize; #============================================================ # 変数等取得関数 #============================================================ #============================================================ # コンストラクタ、デストラクタ #============================================================ #呼び出されることはない sub new { my ($module, $app) = @_; my $this = {}; bless $this; return $this; } sub DESTROY { my $this = shift; $this->SUPER::DESTROY(@_); } #============================================================ # 継承クラスで定義しなおす関数 #============================================================ sub CreateLeftFrame { my ($this, $ConfigSide, @args) = @_; # return $this->SUPER::CreateLeftFrame(); return undef; } sub CreateSelectFilePane { my ($this) = @_; # return $this->SUPER::CreateSelectFilePane(); return undef; } sub CreateFileContentPane { return undef; } sub CreateWidgets { my ($this, $DoSuperOnly) = @_; $DoSuperOnly = 0 if(!defined $DoSuperOnly); my $App = $this->App(); my $args = $App->Args(); my $mw = $this->mw(); my $Program = "Arrhenius Plot2007"; $this->{nm} = 3; $this->{ini} = new ConductingMaterial(); $this->{dini} = new ConductingMaterial(); $this->InitializeParameters($this->{ini}, $this->{dini}); $this->{DataFile} = new MultiColumnData; $this->SUPER::CreateWidgets(); return if($DoSuperOnly); $mw->SetTitle("$Program / TkPlot"); $this->App()->SetProgram("$Program / TkPlot"); #=================================================== # ペインを作製 #=================================================== my $EntryWidth = 12; my $Frame = $mw->MyFrame()->pack(-anchor => 'nw', -fill => 'x'); $this->MakeChooseFileEntry($Frame, 'Param', 'Param:', $this->{ini}->pVariable("ParameterFile", ""), '&Choose', sub { $this->ChooseFile(@_); }, "ChooseParameterFile"); $this->{SaveParamButton} = $Frame->MyButton( -text => '&Save', -takefocus => 1, -command => sub { $this->ButtonPressed('RButtonDown', 'SaveParam'); }, )->pack(-side => 'left'); $this->{EditParamButton} = $Frame->MyButton( -text => 'ed', -takefocus => 1, -command => sub { $this->ButtonPressed('RButtonDown', 'EditParam'); }, )->pack(-side => 'left'); $Frame = $mw->MyFrame()->pack(-anchor => 'nw', -fill => 'x'); $this->MakeChooseFileEntry($Frame, 'SampleCSV', 'Sample:', $this->{ini}->pVariable("SampleCSVFile", ""), '&Choose', sub { $this->ChooseFile(@_); }, "ChooseSampleFile"); $this->{EditDataButton} = $Frame->MyButton( -text => 'ed', -takefocus => 1, -command => sub { $this->ButtonPressed('RButtonDown', 'EditSampleCSV'); }, )->pack(-side => 'left'); $Frame = $mw->MyFrame()->pack(-anchor => 'nw', -fill => 'x'); $this->{ChooseXListBox} = $Frame->MyBrowseEntry( -label => "X:", -state => "readonly", -takefocus => 1, -width => 5, -Selections => [], -SelIndex => 0, )->pack(-side => 'left', -expand => 'yes', -fill => 'x'); $this->{ChooseXListBox}->configure(-browsecmd => sub { $this->SelChangeListBox("X", $this->{ChooseXListBox}); } ); $this->{ChooseY1ListBox} = $Frame->MyBrowseEntry( -label => "Y1:", -state => "readonly", -takefocus => 1, -width => 5, -Selections => [], -SelIndex => 1, )->pack(-side => 'left', -expand => 'yes', -fill => 'x'); $Frame = $mw->MyFrame()->pack(-anchor => 'nw', -fill => 'x'); $this->MakeLabelEntry($Frame, "XMin", "XMin(cal):", $this->{ini}->pVariable('XMin', ''), "%s", $EntryWidth-2, "", 0, 0); $this->MakeLabelEntry($Frame, "XMin", "XMax:", $this->{ini}->pVariable('XMax', ''), "%s", $EntryWidth-2, "", 0, 1); $this->MakeLabelEntry($Frame, "XStep", "Step:", $this->{ini}->pVariable('XStep', 0), "%s", $EntryWidth-2, "", 0, 2); $this->MakeLabelEntry($Frame, "FitXMin", "XMin(fit):", $this->{ini}->pVariable('FitXMin', ''), "%s", $EntryWidth-2, "", 1, 0); $this->MakeLabelEntry($Frame, "FitXMin", "XMax:", $this->{ini}->pVariable('FitXMax', ''), "%s", $EntryWidth-2, "", 1, 1); $this->MakeLabelEntry($Frame, "nSkipData", "nSkip:", $this->{ini}->pVariable('nSkipData', 0), "%d", $EntryWidth-2, "", 1, 2); $Frame = $mw->MyLabFrame( -label => 'LSQ', -labelside => 'acrosstop', )->pack(-anchor => 'nw'); my $Frame2 = $Frame->MyFrame()->pack(-anchor => 'nw', -fill => 'x'); $this->{ChooseLSQMethodListBox} = $Frame2->MyBrowseEntry( -label => "LSQ Method:", -state => "readonly", -takefocus => 1, -width => 5, -Selections => ['Amoeba::Simplex', 'PDL::Simplex', 'ModifiedNewton'], -SelIndex => 0, )->pack(-side => 'left', -expand => 'yes', -fill => 'x'); $this->{ChooseModelListBox} = $Frame2->MyBrowseEntry( -label => "Model:", -state => "readonly", -takefocus => 1, -width => 10, -Selections => ['log(|y|)-1/T'], -SelIndex => 0, )->pack(-side => 'left', -expand => 'yes', -fill => 'x'); $Frame2 = $Frame->MyFrame()->pack(-anchor => 'nw', -fill => 'x'); $this->MakeLabelEntry($Frame2, "EPS", "EPS:", $this->{ini}->pVariable('EPS', 1.0e-5), "%12.4g", $EntryWidth, "", 0, 0); $this->MakeLabelEntry($Frame2, "nMaxIter", "MaxIter:", $this->{ini}->pVariable('nMaxIter', 1000), "%d", $EntryWidth, "", 0, 1); $this->MakeLabelEntry($Frame2, "nSaveSpectraInterval", "SaveIntvl:", $this->{ini}->pVariable('nSaveSpectraInterval', 100), "%d", $EntryWidth, "", 1, 0); $Frame = $mw->MyLabFrame( -label => 'Polynominal', -labelside => 'acrosstop', )->pack(-anchor => 'nw'); for(my $i = 0 ; $i < $this->{nm} ; $i++) { $this->MakeCheckEntry($Frame, "m$i", "m$i:", $this->{dini}->pVariable("m${i}check", 0), $this->{ini}->pVariable("m$i", $i), "%g", $EntryWidth, "", $i, 0); $this->MakeCheckEntry($Frame, "c$i", "c$i:", $this->{dini}->pVariable("c${i}check", 0), $this->{ini}->pVariable("c$i", 0.0), "%g", $EntryWidth, "", $i, 1); } $this->UpdateParameters(); $Frame = $mw->MyFrame()->pack(-anchor => 'nw', -fill => 'x'); $this->{RecalcButton} = $Frame->MyButton( -text => 'Re&calc', -takefocus => 1, -command => sub { $this->ButtonPressed('RButtonDown', 'Recalc'); }, )->pack(-side => 'left'); $this->{FitButton} = $Frame->MyButton( -text => '&Fit', -takefocus => 1, -command => sub { $this->ButtonPressed('RButtonDown', 'Fit'); }, )->pack(-side => 'left'); #ツールバーのOpenボタンをファイル読み込みにバインドする $mw->{OpenButton}->configure( -command => sub { $this->ChooseFile('SampleCSV', $this->{SPEFileFileEntry}); }, ) if($mw->{OpenButton}); } sub Initialize { my ($this, $InitializeParameterFile, $InitializeData) = @_; $this->{DataFile} = new Ellipsometry; if($InitializeParameterFile) { $this->{ini}->{SampleCSVFile} = ''; $this->{ini}->{XMin} = ''; $this->{ini}->{XMax} = ''; $this->{ini}->{XStep} = ''; $this->{ini}->{FitXMin} = ''; $this->{ini}->{FitXMax} = ''; } if($InitializeData) { $this->{pCalX} = undef; $this->{pCalY} = undef; } } sub UpdateParameters { my ($this) = @_; my $ini = $this->{ini}; $this->SUPER::UpdateParameters(); } sub EntryFocusedIn { my ($this, $obj, $event, $type) = @_; if($event eq 'FocusIn') { $obj->{PrevValue} = $obj->GetText(); } else { $this->SUPER::EntryFocusedIn($obj, $event, $type); } } sub EntryFocusedOut { my ($this, $obj, $event, $type) = @_; my $ini = $this->{ini}; my $dini = $this->{dini}; if($event eq 'FocusOut') { $this->SUPER::EntryFocusedOut($obj, $event, $type); } else { $this->SUPER::EntryFocusedOut($obj, $event, $type); } } sub ButtonPressed { my ($this, $event, $type) = @_; my $App = $this->App(); if($type eq 'CalAll') { $this->CalAll(); } elsif($type eq 'SaveAll') { my $FileName = $this->{SampleCSVFileEntry}->GetText(); $FileName = Deps::ReplaceExtension($FileName, "AllData.csv"); $this->print("Save All Data\n"); $this->print(" Save to [$FileName].\n"); $this->CalAll($FileName); $this->print(" Data saved to [$FileName].\n"); } else { $this->SUPER::ButtonPressed($event, $type); } } #=================================================== # データ処理 #=================================================== sub Recalc { my ($this) = @_; return if(!defined $this->{DataFile}); printf "\nRecalc\n"; my $ini = $this->{ini}; # my $FitXMin = $ini->{FitXMin}; # my $FitXMax = $ini->{FitXMax}; my $XMin = $ini->{XMin}; my $XMax = $ini->{XMax}; my $XStep = $ini->{XStep}; my $nSkipData = $ini->{nSkipData}; my $Method = $this->{ChooseLSQMethodListBox}->GetText(); my $Model = $this->{ChooseModelListBox}->GetText(); my $XLabel = $this->{"ChooseXListBox"}->GetText(); my $Y1Label = $this->{"ChooseY1ListBox"}->GetText(); my $pX = $this->{DataFile}->GetData($XLabel) if($XLabel); my $pY1 = $this->{DataFile}->GetData($Y1Label) if($Y1Label); my @Y; if($Y1Label =~ /ue\/T/) { my $pY = $this->{DataFile}->GetData(".*ue.*"); for(my $i = 0 ; $i < @$pY ; $i++) { $Y[$i] = $pY->[$i] / $pX->[$i]; } $pY1 = \@Y; } elsif($Y1Label =~ /sigma\/T/) { my $pY = $this->{DataFile}->GetData("sigma*"); for(my $i = 0 ; $i < @$pY ; $i++) { $Y[$i] = $pY->[$i] / $pX->[$i]; } $pY1 = \@Y; } ($this->{pCalX}, $this->{pCalY1}) = $this->CalAll($Model, $pX, $pY1, $XMin, $XMax, $XStep, $nSkipData); # ($this->{pCalX}, $this->{pCalY1}) = $this->CalAll($Model, $pX, $pY1, $FitXMin, $FitXMax, $nSkipData); # $this->SetS2($S2); $this->CreateGraphFrame() if(!defined $this->{GraphFrameArray}); $this->AssignGraphData(1); $this->Draw(); } sub CalAll { my ($this, $Model, $pX, $pY1, $FitXMin, $FitXMax, $XStep, $nSkipData, $IsPrint) = @_; $IsPrint = 1 if(!defined $IsPrint); my $ini = $this->{ini}; my (@X, @CalX, @CalY1); my $Sync = 0; if(defined $XStep and $XStep > 0.0) { for(my $i = 0 ; ; $i++) { my $x = $FitXMin + $i * $XStep; last if($x > $FitXMax); $X[$i] = $x; } } else { @X = @$pX; $Sync = 1; } my $nData = @X; my $c = 0; for(my $i = 0 ; $i < $nData ; $i++) { next if($nSkipData > 0 and $i % $nSkipData != 0); my $x = $X[$i]; next if(defined $FitXMin and $x < $FitXMin); next if(defined $FitXMax and $FitXMax < $x); if($Model eq 'log(|y|)-1/T') { my $x1 = 1.0 / $x; my $ycal = 0.0; for(my $i = 0 ; $i < $this->{nm} ; $i++) { my $c = $ini->{"c$i"}; my $m = $ini->{"m$i"}; #print " i=$i: m=$m c=$c\n"; if($m == 0) { $ycal += $c; } elsif($m == 1) { $ycal += $c * $x1; } else { $ycal += $c * $x1**$m; } } if($Sync) { print "x=$x,$x1,$pY1->[$i],$ycal\n" if($IsPrint); } else { print "x=$x,$x1,$ycal\n" if($IsPrint); } $CalX[$c] = $x; $CalY1[$c] = exp($ycal); } $c++; } if($Model eq 'log(|y|)-1/T') { for(my $i = 0 ; $i < $this->{nm} ; $i++) { if(abs($ini->{"m$i"} - 0) < 1.0e-3) { my $A0 = exp($ini->{"c$i"}); print " A0=exp(c$i): $A0\n"; } elsif(abs($ini->{"m$i"} - 1) < 1.0e-3) { my $Ea = -$ini->{"c$i"} * $kB / $e; print " Ea=-c$i*kB/e: $Ea eV\n"; } elsif(abs($ini->{"m$i"} - 2) < 1.0e-3) { my $dE2 = $ini->{"c$i"} * 2.0 * $kB / $e * $kB / $e; my $dE = ($dE2 < 0.0)? "i*" . sqrt(-$dE2) : sqrt($dE2); print " dE=sqrt(2c$i*kB^2/e-2): $dE eV\n"; } elsif(abs($ini->{"m$i"} - 0.25) < 1.0e-3) { my $ci = -$ini->{"c$i"}; print " c(T^-1/4)=-c$i: $ci\n"; } } } return (\@CalX, \@CalY1); } sub Fit { my ($this) = @_; return if(!defined $this->{DataFile}); my $App = $this->App(); my $ini = $this->{ini}; printf "\nFit\n"; $this->UpdateParameters(); $this->BuildOptimize(0); my $optimize = $this->{Optimize}; my $FitXMin = $ini->{FitXMin}; my $FitXMax = $ini->{FitXMax}; my $nSkipData = $ini->{nSkipData}; my $Method = $this->{ChooseLSQMethodListBox}->GetText(); my $Model = $this->{ChooseModelListBox}->GetText(); my $XLabel = $this->{"ChooseXListBox"}->GetText(); my $Y1Label = $this->{"ChooseY1ListBox"}->GetText(); my $pX = $this->{DataFile}->GetData($XLabel) if($XLabel); my $pY1 = $this->{DataFile}->GetData($Y1Label) if($Y1Label); my @Y; if($Y1Label =~ /ue\/T/) { my $pY = $this->{DataFile}->GetData(".*ue.*"); for(my $i = 0 ; $i < @$pY ; $i++) { $Y[$i] = $pY->[$i] / $pX->[$i]; } $pY1 = \@Y; } elsif($Y1Label =~ /sigma\/T/) { my $pY = $this->{DataFile}->GetData("sigma*"); for(my $i = 0 ; $i < @$pY ; $i++) { $Y[$i] = $pY->[$i] / $pX->[$i]; } $pY1 = \@Y; } my ($OptVars, $MinVal) = $optimize->Optimize( $Method, undef, undef, undef, $ini->{EPS}, $ini->{nMaxIter}, $ini->{iPrintLevel}, sub { $this->CalS2($Model, $pX, $pY1, $FitXMin, $FitXMax, $nSkipData, @_); }, undef, sub { Optimize::BuildDifferentialMatrixes(@_); }, ); print "\nOptimized at:\n"; $optimize->PrintParameters(1, $OptVars, $MinVal, 1); $optimize->RecoverParameters($OptVars); $this->Recalc(); $this->SetS2($MinVal); $this->UpdateParameters(); $this->CreateGraphFrame() if(!defined $this->{GraphFrameArray}); $this->AssignGraphData(1); $this->Draw(); } sub CalS2 { my ($this, $Model, $pX, $pY1, $FitXMin, $FitXMax, $nSkipData, $pVars, $iPrintLevel) = @_; my $optimize = $this->{Optimize}; my $ini = $this->{ini}; $optimize->RecoverParameters($pVars); my ($d1, $d2); my $S2 = 0.0; my $c = 0; my ($pCalX, $pCalY1) = $this->CalAll($Model, $pX, $pY1, undef, undef, undef, 0, 0); my $nData = @$pX; for(my $i = 0 ; $i < $nData ; $i++) { next if($nSkipData > 0 and $i % $nSkipData != 0); my $x = $pX->[$i]; next if($x < $FitXMin or $FitXMax < $x); #print "X[$i]: $x < $FitXMin or $FitXMax < $x\n"; if($Model eq 'log(|y|)-1/T') { #print "$i: log(abs($pCalY1->[$i])) - log(abs($pY1->[$i]))\n"; my $d = log(abs($pCalY1->[$i])) - log(abs($pY1->[$i])); $S2 += $d*$d; } $c++; } $S2 /= $c if($c > 0); $optimize->IncrementnS2(); my $nS2 = $optimize->nS2Calculation(); print "S2[$nS2] = $S2 / "; $S2 += $optimize->CalPenalty(1.0e10, $pVars, 1); print "$S2\n"; $optimize->PrintParameters(1, $pVars, $S2, 0); my $nS2Interval = $ini->{nSaveSpectraInterval}; if($nS2Interval > 0 and $nS2 % $nS2Interval == 0) { $this->SetS2($S2, 0); $this->Recalc(); # $this->CreateGraphFrame(); $this->AssignGraphData(0); $this->Draw(); } $this->UpdateParameters(); $this->mw()->update(); return $S2; } sub BuildOptimize { my ($this, $IsPrint) = @_; my $ini = $this->{ini}; my $dini = $this->{dini}; my $XLabel = $this->{"ChooseXListBox"}->GetText(); my $Y1Label = $this->{"ChooseY1ListBox"}->GetText(); my $pX = $this->{DataFile}->GetData($XLabel) if($XLabel); my $pY1 = $this->{DataFile}->GetData($Y1Label) if($Y1Label); my $nData = $this->{DataFile}->nData(); my $optimize = new Optimize(); for(my $i = 0 ; $i < $this->{nm} ; $i++) { my $ii = $i; $optimize->AddParameters( "m$i", \$ini->{"m$i"}, $dini->{"m${i}check"}, $dini->{"m${i}scale"}, $dini->{"m${i}min"}, $dini->{"m${i}max"}, sub { $ini->{"m${ii}"} = $_[0]; }, "c$i", \$ini->{"c$i"}, $dini->{"c${i}check"}, $dini->{"c${i}scale"}, $dini->{"c${i}min"}, $dini->{"c${i}max"}, sub { $ini->{"c${ii}"} = $_[0]; }, ); } $this->{Optimize} = $optimize; } sub SaveParameterFile { my ($this, $filepath) = @_; $this->{ini}->{X} = $this->{ChooseXListBox}->GetText(); $this->{ini}->{Y1} = $this->{ChooseY1ListBox}->GetText(); if(!defined $filepath or $filepath eq '') { $filepath = $this->ChooseSaveFile('save.prm', '*.prm'); if($filepath) { $this->{ini}->{ParameterFile} = $filepath; } else { return; } } $this->{ini}->SetIniFile($filepath, undef, 1); $this->App()->print("\nSaveParameterFile:\n"); $this->ComposeParameters($this->{dini}, $this->{ini}); $this->{ini}->WriteAll(); $this->DecomposeParameters($this->{ini}, $this->{dini}); } sub ReadParameterFile { my ($this, $filepath) = @_; my $DirectorySeparator = Deps::DirectorySeparator(); my $RegSeparator = Utils::RegExpQuote($DirectorySeparator); my $ini = $this->{ini}; my $dini = $this->{dini}; $this->Initialize(1, 1); $this->App()->print("\nRead paramter from [$filepath].\n"); $this->{ini}->ReadAll($filepath); $this->DecomposeParameters($ini, $dini); if($this->{ini}->{SampleCSVFile}) { my $ret; if(-e $this->{ini}->{SampleCSVFile}) { $ret = $this->ReadSampleDataFile($this->{ini}->{SampleCSVFile}, 1, 0, 0); } unless($ret) { my ($drive0, $directory0, $filename0, $ext0, $lastdir0, $filebody0) = Deps::SplitFilePath($this->{ini}->{ParameterFile}); my ($drive1, $directory1, $filename1, $ext1, $lastdir1, $filebody1) = Deps::SplitFilePath($filepath); $this->{ini}->{SampleCSVFile} =~ s/\//$DirectorySeparator/g; #print "RelPath = Utils::MakeRelativePath($this->{ini}->{SampleCSVFile}, $drive0$directory0, 0)\n"; my $RelPath = Utils::MakeRelativePath($this->{ini}->{SampleCSVFile}, "$drive0$directory0"); #print "R: $RelPath\n"; $RelPath =~ s/^\.$RegSeparator/$drive1$directory1/; #print "R: $RelPath\n"; if(-e $RelPath) { $ret = $this->ReadSampleDataFile($RelPath, 1, 0, 0); } unless($ret) { ($drive0, $directory0, $filename0, $ext0, $lastdir0, $filebody0) = Deps::SplitFilePath($filepath); ($drive1, $directory1, $filename1, $ext1, $lastdir1, $filebody1) = Deps::SplitFilePath($this->{ini}->{SampleCSVFile}); my $f = Deps::MakePath("$drive0$directory0", $filename1, 0); $ret = $this->ReadSampleDataFile($f, 1, 0, 0); return undef unless($ret); $this->{ini}->{SampleCSVFile} = $f; } else { $this->{ini}->{SampleCSVFile} = $RelPath; } } } $this->{ini}->{ParameterFile} = $filepath; $this->{ChooseXListBox}->SetText($this->{ini}->{X}); $this->{ChooseY1ListBox}->SetText($this->{ini}->{Y1}); return 1; } sub ReadSampleDataFile { my ($this, $filepath, $IsPrint, $UpdateRange) = @_; $UpdateRange = 1 if(!defined $UpdateRange); my $App = $this->App(); #print "type=$type\n"; $this->Initialize(0, 1); $this->{Path} = $filepath; my ($nData, $pLabelArray, @pDataArray) = $this->{DataFile}->Read($filepath); if(!defined $nData) { $App->print("Error: Can not read [$filepath].\n"); return $this->{Path} = undef; } my $nDataArray = $this->{DataFile}->nDataArray(); #print "nDataArray: $nDataArray\n"; $this->{"ChooseXListBox"}->DeleteAllItem(); $this->{"ChooseY1ListBox"}->DeleteAllItem(); for(my $i = 0 ; $i < $nDataArray ; $i++) { #print "$i: $pLabelArray->[$i]\n"; $this->{"ChooseXListBox"}->AddItem($pLabelArray->[$i]); $this->{"ChooseY1ListBox"}->AddItem($pLabelArray->[$i]); my $s = $pLabelArray->[$i]; if($s =~ s/ue/ue\/T/) { $this->{ChooseXListBox}->AddItem($s); $this->{ChooseY1ListBox}->AddItem($s); } elsif($s =~ s/sigma/sigma\/T/) { $this->{ChooseXListBox}->AddItem($s); $this->{ChooseY1ListBox}->AddItem($s); } } $this->{"ChooseXListBox"}->SetCurSel('T.*', '1/T.*'); $this->{"ChooseY1ListBox"}->SetCurSel('sigma.*', 'ue.*', 'mobility.*'); if($UpdateRange or !defined $this->{ini}->{FitXMin}) { ($this->{ini}->{FitXMin}, $this->{ini}->{FitXMax}) = ($this->{ini}->{XMin}, $this->{ini}->{XMax}) = Utils::CalMinMax($pDataArray[0]); $this->{ini}->{XStep} = ($this->{ini}->{XMax} - $this->{ini}->{XMin}) / 20; $this->{ini}->{XMin} = int($this->{ini}->{XMin}); $this->{ini}->{XMax} = int($this->{ini}->{XMax} + $this->{ini}->{XStep}); $this->{ini}->{XStep} = ($this->{ini}->{XMax} - $this->{ini}->{XMin}) / 20; } $this->CreateGraphFrame(); $this->AssignGraphData(); return $filepath; } sub CreateGraphFrame { my ($this, $canvas, $TargetData) = @_; $canvas = $this->Canvas(); my $App = $this->App(); my $font = $App->{'GraphFrameFont'}; my @font = split(/,/, $font) if($font); my $w = $canvas->width(); my $h = $canvas->height(); my $GraphFrameArray = $this->{'GraphFrameArray'} = new GraphFrameArray($this->mw()); $GraphFrameArray->SetCanvasSize($w, $h); $GraphFrameArray->AddGraphFrame(); my $GraphFrame0 = $GraphFrameArray->GetGraphFrame(0); my $FramePosStr0 = $App->{"GraphFrame0Position"}; $GraphFrame0->SetPositionByStr($FramePosStr0); my $XScale0 = $GraphFrame0->GetXScale(0); my $YScale0 = $GraphFrame0->GetYScale(0); $XScale0->SetScaleStringVisible(1); $XScale0->SetCaptionVisible(1); $GraphFrame0->SetViewRange(0, 0, 1, 1); } sub AssignGraphData { my ($this, $ResetViewRange) = @_; $ResetViewRange = 1 if(!defined $ResetViewRange); my $GraphFrameArray = $this->GetGraphFrameArray(); my $GraphFrame0 = $GraphFrameArray->GetGraphFrame(0); $GraphFrame0->ClearAllData(); my $Model = $this->{"ChooseModelListBox"}->GetText(); my $XLabel = $this->{"ChooseXListBox"}->GetText(); my $Y1Label = $this->{"ChooseY1ListBox"}->GetText(); $GraphFrame0->SetXCaption($XLabel); $GraphFrame0->SetYCaption($Y1Label); my $pX = $this->{DataFile}->GetData($XLabel) if($XLabel); my $pY1 = $this->{DataFile}->GetData($Y1Label) if($Y1Label); my @Y; if($Y1Label =~ /ue\/T/) { my $pY = $this->{DataFile}->GetData(".*ue.*"); for(my $i = 0 ; $i < @$pY ; $i++) { $Y[$i] = $pY->[$i] / $pX->[$i]; } $pY1 = \@Y; } elsif($Y1Label =~ /sigma\/T/) { my $pY = $this->{DataFile}->GetData("sigma*"); for(my $i = 0 ; $i < @$pY ; $i++) { $Y[$i] = $pY->[$i] / $pX->[$i]; } $pY1 = \@Y; } my $nData = $this->{DataFile}->nData(); if($pX) { $GraphFrame0->AddGraphData($pX, $pY1, 0, "black", "circle", 6, "black", 0, "black", "XAutoSkip", "1/T(K)", "log({${Y1Label}|)") if($pY1); } my $pCalX = $this->{pCalX}; my $pCalY1 = $this->{pCalY1}; if($pCalX) { $GraphFrame0->AddGraphData($pCalX, $pCalY1, 1, "red", "", 6, "red", 0, "red", "XAutoSkip", "1/T(K)", "log(|${Y1Label}|)(cal)") if($pCalY1); } if($Model eq 'log(|y|)-1/T') { # $GraphFrame0->SetXCaption("1/$XLabel"); # $GraphFrame0->SetYCaption("log(|${Y1Label}|)"); # $GraphFrame0->SetXScalePlotType('1/x'); # $GraphFrame0->SetYScalePlotType('log(|x|)'); } if($ResetViewRange) { $GraphFrame0->CalMinMax(); $GraphFrame0->AdjustViewRange(0.05, 0.05, 0.05, 0.05); # $GraphFrame0->SetViewYRange(0); } } sub AdjustViewRange { my ($this) = @_; my $GraphFrameArray = $this->GetGraphFrameArray(); my $pGraphFrame = $GraphFrameArray->GetpGraphFrameArray(); my $FileType = $this->FileType(); # if($FileType =~ /(Ids)/i) { # } } sub InitializeParameters { my ($this, $ini, $dini) = @_; for(my $i = 0 ; $i < $this->{nm} ; $i++) { $this->AddParameters($ini, $dini, "m$i", $i, 0, 0.5, '', ''); $this->AddParameters($ini, $dini, "c$i", 0.0, 1, 1.0, '', ''); } } 1;