@@ -38,6 +38,7 @@ var CSS_CLASS_NAMES = {
3838 page_data : '@CSS_PAGE_DATA_CN@' ,
3939 background_image : '@CSS_BACKGROUND_IMAGE_CN@' ,
4040 link : '@CSS_LINK_CN@' ,
41+ input_radio : '@CSS_INPUT_RADIO_CN@' ,
4142 __dummy__ : 'no comma'
4243} ;
4344
@@ -61,10 +62,12 @@ var DEFAULT_CONFIG = {
6162 'render_timeout' : 100 ,
6263 // zoom ratio step for each zoom in/out event
6364 'scale_step' : 0.9 ,
64- // register global key handler
65+ // register global key handler, allowing navigation by keyboard
6566 'key_handler' : true ,
66- // register hashchange handler
67+ // register hashchange handler, navigate to the location specified by the hash
6768 'hashchange_handler' : true ,
69+ // register view history handler, allowing going back to the previous location
70+ 'view_history_handler' : true ,
6871
6972 '__dummy__' : 'no comma'
7073} ;
@@ -261,7 +264,7 @@ Viewer.prototype = {
261264 } ,
262265
263266 initialize_radio_button : function ( ) {
264- var elements = document . getElementsByClassName ( 'ir' ) ;
267+ var elements = document . getElementsByClassName ( CSS_CLASS_NAMES . input_radio ) ;
265268
266269 for ( var i = 0 ; i < elements . length ; i ++ ) {
267270 var r = elements [ i ] ;
@@ -312,6 +315,12 @@ Viewer.prototype = {
312315 } , false ) ;
313316 }
314317
318+ if ( this . config [ 'view_history_handler' ] ) {
319+ window . addEventListener ( 'popstate' , function ( e ) {
320+ if ( e . state ) self . navigate_to_dest ( e . state ) ;
321+ } , false ) ;
322+ }
323+
315324 // register schedule rendering
316325 // renew old schedules since scroll() may be called frequently
317326 this . container . addEventListener ( 'scroll' , function ( ) {
@@ -759,13 +768,13 @@ Viewer.prototype = {
759768
760769 fit_width : function ( ) {
761770 var page_idx = this . cur_page_idx ;
762- this . rescale ( this . container . clientWidth / this . pages [ page_idx ] . width ( ) , false ) ;
771+ this . rescale ( this . container . clientWidth / this . pages [ page_idx ] . width ( ) , true ) ;
763772 this . scroll_to ( page_idx ) ;
764773 } ,
765774
766775 fit_height : function ( ) {
767776 var page_idx = this . cur_page_idx ;
768- this . rescale ( this . container . clientHeight / this . pages [ page_idx ] . height ( ) , false ) ;
777+ this . rescale ( this . container . clientHeight / this . pages [ page_idx ] . height ( ) , true ) ;
769778 this . scroll_to ( page_idx ) ;
770779 } ,
771780 /**
@@ -797,6 +806,13 @@ Viewer.prototype = {
797806 var detail_str = /** @type {string } */ ( target . getAttribute ( 'data-dest-detail' ) ) ;
798807 if ( ! detail_str ) return ;
799808
809+ if ( this . config [ 'view_history_handler' ] ) {
810+ try {
811+ var cur_hash = this . get_current_view_hash ( ) ;
812+ window . history . replaceState ( cur_hash , '' , '#' + cur_hash ) ;
813+ window . history . pushState ( detail_str , '' , '#' + detail_str ) ;
814+ } catch ( ex ) { }
815+ }
800816 this . navigate_to_dest ( detail_str , this . get_containing_page ( target ) ) ;
801817 e . preventDefault ( ) ;
802818 } ,
@@ -883,7 +899,6 @@ Viewer.prototype = {
883899
884900 this . rescale ( zoom , false ) ;
885901
886-
887902 var self = this ;
888903 /**
889904 * page should of type Page
@@ -926,6 +941,26 @@ Viewer.prototype = {
926941 var container = this . container ;
927942 container . scrollLeft += pos [ 0 ] - cur_target_pos [ 0 ] ;
928943 container . scrollTop += pos [ 1 ] - cur_target_pos [ 1 ] ;
944+ } ,
945+
946+ /**
947+ * generate the hash for the current view
948+ */
949+ get_current_view_hash : function ( ) {
950+ var detail = [ ] ;
951+ var cur_page = this . pages [ this . cur_page_idx ] ;
952+
953+ detail . push ( cur_page . num ) ;
954+ detail . push ( 'XYZ' ) ;
955+
956+ var cur_pos = cur_page . view_position ( ) ;
957+ cur_pos = transform ( cur_page . ictm , [ cur_pos [ 0 ] , cur_page . height ( ) - cur_pos [ 1 ] ] ) ;
958+ detail . push ( cur_pos [ 0 ] / this . scale ) ;
959+ detail . push ( cur_pos [ 1 ] / this . scale ) ;
960+
961+ detail . push ( this . scale ) ;
962+
963+ return JSON . stringify ( detail ) ;
929964 }
930965} ;
931966
0 commit comments