@rapropos sure! I still stripped out a decent amount from each file, this is a very rough/work in progress project so I have a lot of unneeded/extra code that I don’t want to confuse, but I’ll include both below with a description.
I realize I made the Player component as a page rather than a component, but I don’t think that should be causing problems. To give a brief description, DemoPage (or any page that I want the player to show on) imports and passes the PlayerPage into the constructor, and when that page hits ionViewDidLoad, it calls the player to set up the HammerJS associated with the player. When a user hits the playSong function, some logic is done to move the player into the view and then passes the song name from DemoPage into setSong() in Player.ts. I am seeing this.accessToken
set correctly in the controller, but it doesn’t reflect the update in the view. Please let me know if anything looks incorrect to you. Thank you!
Demo.ts - Parent Page
import { Component, NgZone } from '@angular/core';
import { Platform, ModalController, NavController, NavParams } from 'ionic-angular';
import { HTTP } from '@ionic-native/http';
import { Storage } from '@ionic/storage';
import sampleTracks from "../../assets/sampleMusic.js";
import { ErrorModalPage } from '../errorModal/errorModal';
import { PlayerPage } from '../player/player'
@Component({
selector: 'page-demo',
templateUrl: 'demo.html'
})
export class DemoPage {
result = {}
pictureList: any[];
previousPlayedTrack = { active: false };
recommendedTracksJson = [{}]
height: any
// poor choice here, but to keep it simple
// setting up a few vars to keep track of things.
// at issue is these values need to be encapsulated
// in some scope other than global.
lastPosX = 0;
lastPosY = 0;
isDragging = false;
activeSong: string
playingTrack = false;
timerId: any
constructor(public modalController: ModalController,
public navCtrl: NavController,
public platform: Platform,
private http: HTTP,
public navParams: NavParams,
public ngZone: NgZone,
private player: PlayerPage,
public storage: Storage) {
this.recommendedTracksJson = sampleTracks
this.platform.ready().then(() => {
this.height = this.platform.height()
})
}
ionViewDidLoad() {
this.player.setupPlayer()
}
playSong(event, item) {
var myBlock = document.getElementById('myElement');
myBlock.classList.add('animate');
if(!item.active || item.active == false) {
this.previousPlayedTrack.active = false;
item.active = true;
this.previousPlayedTrack = item
this.player.activeSong = item.name
this.player.setSong(item.name)
myBlock.style.top = this.height * .9 + "px"
} else {
this.player.setSong("")
item.active = false
myBlock.style.top = this.height + "px"
}
}
}
Player.ts - Component
import { Component, NgZone } from '@angular/core';
import { IonicPage, Platform } from 'ionic-angular';
import Hammer from 'hammerjs';
/**
* Generated class for the PlayerPage page.
*
* See https://ionicframework.com/docs/components/#navigation for more info on
* Ionic pages and navigation.
*/
@IonicPage()
@Component({
selector: 'page-player',
templateUrl: 'player.html',
})
export class PlayerPage {
height: any
lastPosX = 0;
lastPosY = 0;
isDragging = false;
activeSong: string = "Placeholder"
playingTrack = false;
timerId: any
constructor(public ngZone: NgZone, public platform: Platform) {
this.platform.ready().then(() => {
this.height = this.platform.height()
})
}
ionViewDidLoad() {
console.log('ionViewDidLoad PlayerPage');
}
setupPlayer() {
var myBlock = document.getElementById('myElement');
if (myBlock != null) {
var screenBottom = this.height
var screenMiddle = this.height * 0.9
var screenTop = this.height * 0.2
// create a simple instance on our object
var mc = new Hammer(myBlock);
// add a "PAN" recognizer to it (all directions)
mc.add( new Hammer.Pan({ direction: Hammer.DIRECTION_ALL, threshold: 0 }) );
// tie in the handler that will be called
mc.on("pan", this.handleDrag.bind(this), this.handleDrag);
// mc.on("pandown", handleDragDown);
var Tap = new Hammer.Tap({
taps: 1
});
mc.add(Tap)
mc.on('tap', this.handleTap.bind(this), this.handleTap)
} else {
console.log("Null block 2")
}
}
setSong(song) {
this.ngZone.run(() => {
this.activeSong = song;
});
console.log("Active song: " + this.activeSong)
}
handleTap(ev) {
var elem = ev.target;
document.getElementById('myElement').classList.add('animate');
elem.style.top = this.height * 0.2 + "px"
}
handleDrag(ev) {
var screenBottom = this.height
var screenMiddle = this.height * 0.9
var screenTop = this.height * 0.2
// for convience, let's get a reference to our object
var elem = ev.target;
document.getElementById('myElement').classList.remove('animate');
// DRAG STARTED
// here, let's snag the current position
// and keep track of the fact that we're dragging
if ( ! this.isDragging ) {
this.isDragging = true;
this.lastPosX = elem.offsetLeft;
this.lastPosY = elem.offsetTop;
}
// we simply need to determine where the x,y of this
// object is relative to where it's "last" known position is
// NOTE:
// deltaX and deltaY are cumulative
// Thus we need to always calculate 'real x and y' relative
// to the "lastPosX/Y"
var posY = ev.deltaY + this.lastPosY;
elem.style.top = posY + "px";
// DRAG ENDED
// this is where we simply forget we are dragging
if (ev.isFinal) {
var verticalDirection = this.lastPosY - posY
var positionAbove
var positionBelow
var closestPosition
if (posY <= screenMiddle) {
positionAbove = screenTop
positionBelow = screenMiddle
} else {
positionAbove = screenMiddle
positionBelow = screenBottom
}
if ((posY - positionAbove) < (positionBelow - posY)) {
closestPosition = positionAbove
} else {
closestPosition = positionBelow
}
document.getElementById('myElement').classList.add('animate');
if (verticalDirection < 0) {
elem.style.top = positionBelow + "px"
} else if (verticalDirection > 0 ){
elem.style.top = positionAbove + "px"
} else {
elem.style.top = closestPosition + "px"
}
this.isDragging = false;
}
}
}