We launched new forums in March 2019—join us there. In a hurry for help with your website? Get Help Now!
    • 36552
    • 32 Posts
    This is a really odd one I've never experienced before. I have a snippet that generates some HTML and javascript to include Vimeo videos on the page. The javascript is necessary as I use some of the Vimeo data (using the vimeo.php library) to set some variables within the script.

    There are 2 different scripts that are created. The Froogaloop vimeo script is included with $modx->regClientStartupScript and it is only placed once, as expected.

    The second script is the customized js that uses $modx->regClientScript. This is somehow appearing twice on my page. I comment out the command and it doesn't appear at all (correct).

    I've been pouring through the code looking for any points of repetition to explain the second instance and I can't find anything. I've even added print_r comments for every step to see if any functions are getting called twice and it all appears to be a single execution.

    SNIPPET:
    <?php
    require_once MODX_BASE_PATH.'assets/snippets/includeVideo/includeVideo.class.php';
    $param=array();
    if(isset($docid))
    	$param['docid']=$docid;
            /*$docid is used to specify another document*/
    if(isset($type))
    	$param['type'] = $type;
            /*$type has 2 settings, default uses a modal layer to display the video (trigger by click event) and embed embeds the video in the content*/
    if(isset($vimeoID))
    	$param['vimeoID'] = $vimeoID;
            /*$vimeoID allows the editor to directly enter the ID in the snippet call */
    $includeVideoApp = new includeVideo($param);
    return $includeVideoApp->output;
    ?>


    The original snippet used a TV to set the Vimeo video id for that resource. The modification I'm working on allows for the direct entry of the ID in the snippet call.

    Below is the includeVideo Class. I've removed the actual javascript as it is irrelevant to the problem and I wanted to make this compact without excluding any of the php functions.

    The parameters are pass and the class is constructed, dispatching the primary function, buildVideo().

    If the Vimeo ID exists, I use the vimeo.php library to get the video data I need (width and height), which is then passed to the function buildPageScript().

    This is where the video data I grabbed from Vimeo is used to set some dimension variables in the customized javascript, which is written to the class variable, $scripts ($this->scripts in the php below). I use a randomized string to create a unique ID for each video on the page. There is only one video on this particular page.

    As I said, I have not found any instance of the php executing any function more than once. The $modx->regClientStartupScript($this->froogaloop) correctly fires once, but the $modx->regClientScript($this->scripts) results in 2 instances of the same script with 2 different custom IDs on the page. As both scripts are using the same Vimeo ID, they are in conflict.

    I'm really hoping somebody can help me out here because this makes no sense at all to me.

    CLASS:
    <?php
    if(!class_exists('includeVideo')){
    	class includeVideo {
    		public $version = '0.0.1';
    		var $basePath = MODX_BASE_PATH;
    		var $params = array();
    		var $debug = false;
    		var $froogaloop = '/* froogaloop js code */';
    		var $script;
    		
    		function __construct($params=array()){
    			global $modx;
    			$default_params = array();
    			$this->params=array_merge($default_params,$params);
    			$this->dispatch('BuildVideo');
    		}
    	
    		private function BuildVideo(){
    			global $modx;
    			if(isset($this->params['vimeoID'])){
    				$values['vimeoID'] = $this->params['vimeoID'];
    			} else {
    				$docid = isset($this->params['docid']) ? $this->params['docid'] : $modx->documentIdentifier;
    				$values = $modx->getTemplateVarOutput('vimeoID',$docid);
    			}			
    			if($values['vimeoID'] != ''){
    				$data = $this->getVimeoData($values['vimeoID']);
    				$p = array(
    					'vimeoId' => $values['vimeoID'],
    					'width' => $data->width,
    					'height' => $data->height
    				);
    				self::buildPageScript($p);
    				$modx->regClientStartupScript($this->froogaloop);
    				$modx->regClientScript($this->script);
    				return;
    			} else {
    				die('No Vimeo ID was found.');
    			}
    		}
    		private function getVimeoData($id){
    			global $modx;
    			require_once(MODX_BASE_PATH.'assets/lib/vimeo/vimeo.php');
    			$vimeo = new phpVimeo('my consumer key', 'my consumer secret');
    			$vimeo->enableCache(phpVimeo::CACHE_FILE, MODX_BASE_PATH.'assets/cache', 300);
    			$dataArray = array(
    				'video_id' => $id,
    			);
    			$videos = $vimeo->call('vimeo.videos.getInfo', $dataArray);
    			$data = $videos->video[0];
    			return $data;
    		}
    
    		public function dispatch($dispatch=NULL,$vars=NULL){
    			if(method_exists($this, $dispatch)){
    				if($this->debug){ $this->output .= '<br>Calling => '.$dispatch.'<br />'; }
    				self::$dispatch($vars);
    			} else {
    				$this->output .= str_replace('[+dispatch+]', $dispatch,$this->lang['GlobalDispatchError']);	
    			}
    		}
    		
    		function buildPageScript($p){
    			global $modx;
    			$vW = $p['width'];
    			$vH = $p['height'];
    			$f = '$f'; //to prevent PHP from interpreting the JS $f as a variable.
    			
                            if($this->params['type'] != 'embed'){
    				$itemID = $this->generateRandomString(21);
    				$this->script = "<script type=\"text/javascript\">
    					/* event triggered modal js */
                                    </script>";
    			} else {
    				$itemID = $this->generateRandomString(21);
    				$this->output = '<iframe id="'.$itemID.'" width="100%" height="100%" frameborder="0" src="http://player.vimeo.com/video/'.$p['vimeoId'].'?title=0&byline=0&portrait=0&color=ffc423&autoplay=0&api=1&player_id='.$itemID.'" webkitAllowFullScreen mozallowfullscreen allowFullScreen></iframe>';
    				$this->script = "<script type=\"text/javascript\" name=\"vimeo_scripts\">
    					/* embedded video  js*/
    				</script>";
    			}
    		}
    		
    		function generateRandomString($length = 24) {
    		    $characters = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
    		    $randomString = 'con';
    		    for ($i = 0; $i < $length; $i++) {
    		        $randomString .= $characters[rand(0, strlen($characters) - 1)];
    		    }
    		    return $randomString;
    		}
    	//-- END OF CLASS
    	}
    }
    

    This question has been answered by multiple community members. See the first response.

      • 13428 ☆ A M B ☆
      • 1,031 Posts
      Think you should call the vimeo snippet cached on the page. The result of the regClient functions could be saved to page cache and then inserted second time by the uncached snippet otherwise.
      • discuss.answer
        • 36552
        • 32 Posts
        Jako,

        Thanks for the response.

        Actually, everything on this page is cached. I use the "Include" snippet to handle my page templates (and the reusable parts that make them up), therefore uncached snippets on those page will not work.

        [!includeVideo? &param=`etc…`!]
        simply results in the snippet call be displayed as text.

        [[includeVideo? & param=`etc…`]]
        results in the snippet functioning properly (minus this particular glitch).

        What I ended up doing was to simply attach the necessary custom js to the output returned to the page. It was the only way I could avoid this double-dipping.

        At the same time, I'm not MODx caching expert and there may be something else I'm missing. I have tried using the regClientScript method with the resource cacheable on and off with no change in the result.
          • 13428 ☆ A M B ☆
          • 1,031 Posts
          Quote from: djad33 at May 12, 2014, 08:22 AM
          I use the "Include" snippet to handle my page templates …
          Do you change that "Include call" by PHx? Or do use PHx somewhere around the Vimeo Snippet?

          Then you could be stumbling on a PHx issue: PHx executes every snippet in the 'then' and 'else' branch even if the PHx expression is not hit - only the output is suppressed. This way two instances of the Vimeo Snippet could be called and each inserts another code by regClient functions.
            • 36552
            • 32 Posts
            I'm not using PHX, but I am using the 'if' snippet. Not sure if it does the same thing regarding snippet execution, but there is definitely a then/else.

            [[if? &is=`[+content+]:empty` &then=`[+page_main_art+]` &else=`[+content+]`]]


            These resources populate a carousel, so the editor can place an image with a tv or use the content field. In this instance, we are using the content field to call the 'includeVideo' snippet.

            If this were to be the problem, how would I work around it?

            The regClientStartupScript (used to pull in the Froogaloog.js) has only ever executed once on the page. Seems like an redundancy caused by 'if' or PHx would cause that to also be included twice, right?

            • discuss.answer
              • 13428 ☆ A M B ☆
              • 1,031 Posts
              [[if? &is=`[+content+]:empty` &then=`[+page_main_art+]` &else=`[+content+]`]]

              This will call [+content+] (and executes everything inside) twice and should have produced your issue.
                • 36552
                • 32 Posts
                Jako! Thank you!

                That was indeed the problem. I created a new variable to switch the output source and avoid the double parsing of the field values in the If snippet.

                I really appreciate your help with this. Thanks, again!