我正在使用 FIREBASE DATABASE ,我想添加一个倒数计时器,以便同时向所有用户显示。
如何以非常简单的方式执行此操作?
我的数据库是这样的:
time:"9000" //which represent the 9 seconds
`
我试图做这样的事情,但它只检索时间的开始,没有更新数据库的时间。 总体思路是我希望每个用户在进入活动时看到同一时间
value= FirebaseDatabase.getInstance().getReference().child("time");
value.addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(DataSnapshot dataSnapshot) {
long v= (long) dataSnapshot.getValue();
CountDownTimer countDownTimer=new CountDownTimer(v,1000) {
@Override
public void onTick(long millisUntilFinished) {
show.setText("time : "+millisUntilFinished/1000);
}
@Override
public void onFinish() {
Intent i=new Intent(Main4Activity.this,OneActivity.class);
startActivity(i);
}
}.start();
}
@Override
public void onCancelled(DatabaseError databaseError) {
}
});
答案 0 :(得分:0)
这可能/可能不是您想要的,因为它取决于几个因素。 (特别是成本)
你可以将firebase-functions作为你的计时器,但它的最大执行时间为540秒,并且在一定的配额之后,它们不是免费的。 https://cloud.google.com/functions/pricing
如果你有这样的结构:
root
- connectedUsers
- userUid:true
- time: <time> // put your time in ms here
- observedTime: 0
- startTimer
然后你需要做一些事情:
1:在您的活动的onStart()/ onStop()中,通过ref.child('connectedUsers').child(FirebaseAuth.getInstance().getCurrentUser().getUid()).setValue(true/null);
2:创建2个函数触发器(伪代码)
exports.connectedUsers = functions.database.ref('/connectedUsers/{userId}').onWrite((event) => {
// return db.child('connectedUsers').get() as promise
// then check the childCount
// if it's 5, return db.child('startTimer').set(true);
// otherwise return 0
});
exports.timerFunction = functions.database.ref('/startTimer/').onWrite((event) => {
// start a timer, make sure it's a promise
// on each interval (seconds) call(not return) db.child('observedTime').set(timeLeft);
// after timer is done, return promise
// then return db.child('startTimer').delete();
});
3:在你的Activity onStart里面还添加一个指向ref.child("observedTime")
的ValueEventListener并设置你的Text(别忘了解析为字符串)
就是这样,只要有5个人连接,connectUsers函数就会触发timerFunction,它会启动一个计时器并更新每个间隔的observeTime,之后它会删除triggerRequest。
注意,如果一个客户端失去连接,他们的计时器将停止。您需要处理更多边缘情况(如果第六个客户端连接?或者一个离开?会怎样?)
如果您不想使用函数进行倒计时,您当然可以让客户端更新它,但这会增加复杂性(更新计时器的用户?)
另一个解决方案可能是所有用户都在手机上使用本地计时器,在“startTimer”节点上收听,当它进入时,他们就会开始倒计时。有人(函数/客户端)仍然需要发布该请求供所有人观察,而客户端可能不是100%同步
答案 1 :(得分:0)
@Override
protected void onStart() {
super.onStart();
//fetch test time in minutes
//and convert that into milli seconds
mTimerRef = FirebaseDatabase.getInstance().getReference("eTest").child(key).child("TestMinutes");
mTimerRef.addListenerForSingleValueEvent(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
mTimeLeftInMillis = (Integer.parseInt(dataSnapshot.getValue(String.class))) * 6000;
}
@Override
public void onCancelled(@NonNull DatabaseError databaseError) {
throw databaseError.toException();
}
});
mCountDownTimer = new CountDownTimer(mTimeLeftInMillis,1000) {
@Override
public void onTick(long millisUntilFinished) {
mTimeLeftInMillis = millisUntilFinished;
updateCountDownText();
}
@Override
public void onFinish() {
mTimerRunning = false;
//when timer will finish
//submit marks to firebase and close this activity
//once marks is been submitted to firebase then close the quiz
FirebaseDatabase.getInstance().getReference("eTest").child(key).child("Marks").child(sIdHeader).setValue(Integer.toString(mScore));
Intent intent = new Intent(QnA_Test_Activity.this, Attempt_eTest_Activity.class);
startActivity(intent);
finish();
QnA_Test_Activity.this.finish();
}
}.start();
mTimerRunning = true;
}
private void updateCountDownText(){
int minutes = (int) (mTimeLeftInMillis / 1000) / 60;
int seconds = (int) (mTimeLeftInMillis / 1000) % 60;
String timeLeftFormatted = String.format(Locale.getDefault(),"%02d:%02d",minutes,seconds);
mQnATimer.setText(timeLeftFormatted);
}
我希望这会对您有所帮助, 只需在firebase中设置分钟,此代码将获取分钟并将其转换为毫,然后实现计时器。