PageRenderTime 43ms CodeModel.GetById 16ms RepoModel.GetById 0ms app.codeStats 0ms

/lib/Tie/Wx/Widget.pm

https://bitbucket.org/lichtkind/tie-wx-widget
Perl | 185 lines | 139 code | 46 blank | 0 comment | 14 complexity | eb4ba13371090fb6ce1ea778740ae845 MD5 | raw file
  1. use v5.6;
  2. use strict;
  3. use warnings;
  4. use Tie::Scalar;
  5. package Tie::Wx::Widget;
  6. our $VERSION = '1.1';
  7. our @ISA = 'Tie::Scalar';
  8. our $complainmethod = 'die';
  9. sub import { $complainmethod = 'warn_mode' if defined $_[1] and $_[1] eq 'warn'}
  10. sub die_mode { $complainmethod = 'die'}
  11. sub warn_mode{ $complainmethod = 'warn'}
  12. sub complain { $complainmethod eq 'die' ? die $_[0] : warn $_[0] }
  13. sub TIESCALAR {
  14. my ($self, $widget, $store, $fetch) = @_;
  15. if (not ref $widget) {complain("$widget isn't even a referece, has to be a Wx object")}
  16. elsif (index($widget, '=') == -1) {complain("$widget isn't even an object, has to be a Wx object")}
  17. elsif (not $widget->isa('Wx::Control')) {complain("$widget is no Wx widget")}
  18. elsif (not $widget->can('GetValue')) {complain("$widget has no method: GetValue")}
  19. elsif (not $widget->can('SetValue')) {complain("$widget has no method: SetValue")}
  20. elsif (defined $store and ref $store ne 'CODE'){complain("no coderef as STORE callback")}
  21. elsif (defined $fetch and ref $fetch ne 'CODE'){complain("no coderef as FETCH callback")}
  22. else {
  23. my %hash = ('w' => $widget, 'widget' => $widget);
  24. $hash{'store'} = $store if defined $store;
  25. $hash{'fetch'} = $fetch if defined $fetch;
  26. return bless \%hash, $self;
  27. }
  28. return 0;
  29. }
  30. sub FETCH {
  31. if (exists $_[0]->{'fetch'}) { &{$_[0]->{'fetch'}}( $_[0]->{'w'} ) }
  32. else { return $_[0]->{'w'}->GetValue }
  33. }
  34. sub STORE {
  35. if (exists $_[0]->{'store'}) { &{$_[0]->{'store'}}( $_[0]->{'w'}, $_[1] ) }
  36. else { return $_[0]->{'w'}->SetValue( $_[1] ) }
  37. }
  38. sub UNTIE {} # to prevent crashes if called
  39. sub DESTROY {} # to prevent crashes if called
  40. 'one';
  41. __END__
  42. =head1 NAME
  43. Tie::Wx::Widget - get and set main value of a Wx widget with less syntax and more magic
  44. =head1 SYNOPSIS
  45. use Tie::Wx::Widget;
  46. tie $tiedwidget, Tie::Wx::Widget, $widget;
  47. $tiedwidget = 7; # instead of $widget->SetValue(7);
  48. say $tiedwidget; # instead of say $widget->GetValue;
  49. untie $tiedwidget; # now $tiedwidget is a normal scalar again (not required)
  50. =head1 CALLBACKS
  51. Often are the widget values coupled with each other. For instance in
  52. L<App::Spirograph> is a slider, which max value is the value of another slider.
  53. Once you know this, why keep track of it and change the range by hand
  54. any given time?
  55. tie $tslider, Tie::Wx::Widget, $slider,
  56. sub { $[0]->SetValue($[1]); $subslider->SetRange(1, $[1]) };
  57. The first parameter to the callback is always the Wx object reference,
  58. the assign-callback gets also a second with the assigned value.
  59. Own callbacks replace the the ones, generated by default.
  60. The complete parameter list is is:
  61. tie $tw, Tie::Wx::Widget, $widget, [&$do_when_assign, &$do_when_retrieve];
  62. Yes, its also doable with events, but thats also more syntax than this.
  63. Plus, its a different event for many widgets, why remember this?
  64. Plus, a tied widget still gives you the freedom to change the value
  65. under the radar. See section L</INTERNALS> for more.
  66. =head1 WARNINGS
  67. Your program will C<die>, if you don't provide a proper Wx widget,
  68. that has a GetValue and SetValue method, or the callbacks are no coderef.
  69. Unless you init with:
  70. use Tie::Wx::Widget 'warn_mode';
  71. or do later:
  72. Tie::Wx::Widget::warn_mode();
  73. Then will be called C<warn> instead of C<die>.
  74. But you can switch anytime back with:
  75. Tie::Wx::Widget::die_mode();
  76. Wich has only effect for all variables tied afterwards.
  77. Because if the Wx ref is not good, there will be no tying anyway.
  78. =head1 INTERNALS
  79. # how to get a reference to the Tie::Wx::Widget object ?
  80. $tieobject = tie $tiedwidget, Tie::Wx::Widget, $widget;
  81. $tieobject = tied $tiedwidget;
  82. # now you even can:
  83. $tieobject->FETCH()
  84. # aka:
  85. $tieobject->{'widget'}->GetValue;
  86. # or do any other method on the wx object
  87. $tieobject->{'w'}->Show(0);
  88. # works too (hides the widget)
  89. $tieobject->STORE(7);
  90. # doesn't do anything
  91. $tieobject->DESTROY()
  92. =head1 BUGS
  93. Please report any bugs or feature requests to C<bug-tie-wx-widget at rt.cpan.org>, or through
  94. the web interface at L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Tie-Wx-Widget>. I will be notified, and then you'll
  95. automatically be notified of progress on your bug as I make changes.
  96. =head1 SUPPORT
  97. You can find documentation for this module with the perldoc command.
  98. perldoc Tie::Wx::Widget
  99. You can also look for information at:
  100. =over 4
  101. =item * RT: CPAN's request tracker (report bugs here)
  102. L<http://rt.cpan.org/NoAuth/Bugs.html?Dist=Tie-Wx-Widget>
  103. =item * AnnoCPAN: Annotated CPAN documentation
  104. L<http://annocpan.org/dist/Tie-Wx-Widget>
  105. =item * CPAN Ratings
  106. L<http://cpanratings.perl.org/d/Tie-Wx-Widget>
  107. =item * Search CPAN
  108. L<http://search.cpan.org/dist/Tie-Wx-Widget/>
  109. =item * Source Repository: (in case you want to fork :))
  110. L<http://bitbucket.org/lichtkind/tie-wx-widget>
  111. =back
  112. =head1 ACKNOWLEDGEMENTS
  113. This was solely my idea before Linuxtag 2011. Started as a slide for it.
  114. =head1 AUTHOR
  115. Herbert Breunung, C<< <lichtkind at cpan.org> >>
  116. =head1 LICENSE AND COPYRIGHT
  117. Copyright 2011 Herbert Breunung.
  118. This program is free software; you can redistribute it and/or modify it
  119. under the terms of either: the GNU General Public License as published
  120. by the Free Software Foundation; or the Artistic License.
  121. See http://dev.perl.org/licenses/ for more information.