So I was wondering if I send an Embed for something with my Bot, can I edit it with the Bot afterwards?
If that's possible, then show me how to do it please.
This is my Code that I`ve got so far, but idk how to edit that EmbedBuilder afterwards:
public class Giveaway extends ListenerAdapter {
#Override
public void onMessageReceived(MessageReceivedEvent event) {
if (event.getMessage().getContentDisplay().startsWith("+giveaway")) {
if (event.getMessage().getContentDisplay().substring(10, 11) != null) {
long msgid = event.getMessageIdLong();
String count = event.getMessage().getContentDisplay().substring(10, 11);
EmbedBuilder eb = new EmbedBuilder();
eb.setTitle("It's GIVEAWAY-TIME!");
eb.setDescription("Prize: " + "\n Winners: " + count);
eb.setColor(Color.BLUE);
event.getTextChannel().sendMessage(eb.build()).queue();
}
}
}
}
So to be clear, what I want to do is add a footer to the message afterwards and change the description in some cases.
I have tried some things but I've not come up with a solution yet.
Would be nice if you answer.
Kind regards,
lxxrxtz
You can keep the embed builder and create a new embed:
eb.setFooter(...);
MessageEmbed embed = eb.build();
Then all you have to do is call message.editMessage(embed).queue() with the message you want to edit. You can access the message from the callback in your sendMessage:
channel.sendMessage(embed).queue(message -> {
eb.setFooter(...);
message.editMessage(eb.build()).queue();
});
Related
I have a problem, I am trying to code a bot using Java Discord API (JDA).
When a new user joins a server, the bot shall send a message, but my code is not working.
Code:
public class UserJoinModule extends ListenerAdapter {
public void onGuildMemberJoined(GuildMemberJoinEvent event) throws LoginException {
String user = event.getMember().getAsMention();
JDA client = new JDABuilder("awesome token").build();
final List<TextChannel> channels = client.getTextChannelsByName("awesome channel name", true);
for (final TextChannel ch : channels) {
ch.sendMessage("New member joined: " + user).queue();
}
}
}
Can someone tell me what is wrong?
For me the issue was not from the listener and method I override.
I believe you have to add GatewayIntent.GUILD_MEMBERS to your JDABuilder.
builder.enableIntents(GatewayIntent.GUILD_MEMBERS);
This fixed the same issue for me.
In your Main.java or whatever the file is, there is a variable of type JDABuilder, on it's same line of code, there is your token, a .build() at the end etc...
Insert this code into that line:
.enableIntents(GatewayIntent.GUILD_MEMBERS)
So it looks like this:
jda = JDABuilder.createDefault("TOKEN").enableIntents(GatewayIntent.GUILD_MEMBERS).build();
For it to work, go to your Discord Developer Portal, click your bot, from the menu on the left, click Bot, then scroll down and enable:
Server Members Intent
There are still noticeable errors like registering a new client on every message and other issues, fix them, then start your bot and it shall work.
Your code should look like this:
public class UserJoinModule extends ListenerAdapter {
#Override // USE THIS WHEN YOU WANT TO OVERRIDE A METHOD
public void onGuildMemberJoin(GuildMemberJoinEvent event) {
String user = event.getMember().getAsMention();
JDA client = event.getJDA(); // DO NOT CREATE A NEW JDA INSTANCE EVERY TIME
List<TextChannel> channels = client.getTextChannelsByName("awesome channel name", true);
for (TextChannel ch : channels) {
ch.sendMessage("New member joined: " + user).queue();
}
}
}
And you must register this listeners in your JDABuilder instance, preferably you only have one of these in your entire codebase. See addEventListeners.
You have 2 problems in your code.
You are creating a new JDA client every time a member joins.
You are sending messages to every channel with that name, in every guild. Not just the guild that the user joined.
Here is what you want to do:
public class UserJoinModule extends ListenerAdapter {
#Override
public void onGuildMemberJoin(GuildMemberJoinEvent event) {
Guild guild = event.getGuild(); // Get the guild that the user joined.
User user = event.getUser(); // Get the user that joined.
JDA client = event.getJDA(); // Get the already existing JDA instance.
List<TextChannel> channels = guild.getTextChannelsByName("awesome channel name", true); // Get the list of channels in the guild that matches that name.
for (TextChannel channel : channels) { // Loops through the channels and sends a message to each one.
channel.sendMessage("New member joined: " + user).queue();
}
}
}
I'm trying to create an app that only adds an entry to the database if there is no entry already at a specific time intervals and modifies the existing entry if there is already one in the database. I'm using Room.
It works, but only with a workaroud, because I have to call the add function twice before the value gets added (make the input two times before it works). And I also don't like my adding the Observer and immediately removing it afterwards. I also had to implement the workaround when instatiating the DB, with a value when it was first created.
How can I get the data from my LiveData List inside the Repository class and change it without ending up in an endless loop or how do I have to redesign my code to avoid that?
The complete code can be found on my Github account: Github repository
I would really appreciate any suggestion fix my problem and learn to design and plan my code better.
MainActivity
public void ok_clicked(View view) {
Intent intent = new Intent(this, DataActivity.class);
...
Diary addDiary = new Diary(new Date(), diaryCh.isChecked(), readingCh.isChecked(),writingCh.isChecked(),pianoCh.isChecked(),youtubeCh.isChecked());
mDiaryViewModel.insert(addDiary);
startActivity(intent);
}
DiaryViewModel
public void insert(Diary diary) {mRepositroy.add(diary);}
DiaryRepository
public class DiaryRepository {
private DiaryDao mDiaryDao;
private LiveData<List<Diary>> mEntriesToday;
DiaryRepository(Application application) {
AppDatabase db = AppDatabase.getDatabase(application);
mDiaryDao = db.diaryDao();
mEntriesToday = mDiaryDao.findEntriesByDate(Dates.getYesterdayMidnight(), Dates.getTomdayMidnight());
}
LiveData<List<Diary>> getmEntriesToday() { return mEntriesToday;}
void add(Diary diary) {
Observer<List<Diary>> observerEntriesToday = new Observer<List<Diary>>() {
#Override
public void onChanged(List<Diary> diaries) {
if (diaries != null) {
Log.e(TAG, "add: with matching entries"+ diaries.get(0) + " add: " + diary );
diaries.get(0).addAttributes(diary);
new updateDiaryAsyncTask(mDiaryDao).execute(diaries.get(0));
} else {
Log.e(TAG, "add: without matching entries"+" add: " + diary );
new insertDiaryAsyncTask(mDiaryDao).execute(diary);
}
}
};
getmEntriesToday().observeForever(observerEntriesToday);
getmEntriesToday().removeObserver(observerEntriesToday);
}
You shouldn't be using LiveData in this scenario at all. It is only a wrapper for data that will be observed from Activity/Fragment.
First you need to modify mEntriesToday to be MutableLiveData so you can update it.
In your case, you can omit using Observer for updating DB, and so something simple like:
void add(Diary diary){
if (mEntriesToday.getValue() != null) {
Log.e(TAG, "add: with matching entries"+ mEntriesToday.getValue().get(0) + " add: " + diary );
mEntriesToday.getValue().get(0).addAttributes(diary);
new updateDiaryAsyncTask(mDiaryDao).execute(mEntriesToday.getValue().get(0));
} else {
Log.e(TAG, "add: without matching entries"+" add: " + diary );
new insertDiaryAsyncTask(mDiaryDao).execute(diary);
}
}
If you need this data, outside this class, then you can use getmEntriesToday() and observe it.
You can get the value of the LiveData using the getValue() method
void add(Diary diary) {
List<Diary> diaries = mEntriesToday.getValue();
if(diaries!=null){
diaries.get(0).addAttributes(diary);
//update
}else{
//insert
}
in my current Discord (java) bot im trying to apply a command to a user name. how can i make sure this is an actual existing user ?
in psuedo code:
if User "A" exists {
User "A" types something at all
send message "hello"+ user "A"
}
else
{
this is no valid user;
}
i can't figure out how to write the 'check if exist code'.
This is from JDA-Utilities which is a really useful tool when building discord bots.
import com.jagrosh.jdautilities.command.Command;
import com.jagrosh.jdautilities.command.CommandEvent;
public class Example extends Command {
public Example() {
this.name = "'isBot";
this.help = "Tells you if the user is a bot!";
}
#Override
protected void execute(CommandEvent e) {
if (e.getAuthor().isBot()) {
e.reply("Hey you're not a person!!");
} else {
e.reply("Hey " + e.getAuthor().getName() + ", you're not a bot!");
}
}
}
I am trying to convert Parse to Clevertap in the application I'm working on. I have tried looking at https://blog.clevertap.com/transitioning-from-parse-push-notifications/ but haven't had much luck on what I'm trying to accomplish.
In the method that needs to be converted, I am wanting the user to have the ability to subscribe and unsubscribe from a channel using:
private class AllPushClickListener implements View.OnClickListener {
private AppFeed mAppFeed;
public AllPushClickListener(AppFeed appFeed) {
mAppFeed = appFeed;
}
#Override
public void onClick(View v) {
Log.d(TAG, "subscribing to " + getPushChannelName(mAppFeed) + "_all");
ParsePush.unsubscribeInBackground(getPushChannelName(mAppFeed) + "_top");
ParsePush.subscribeInBackground(getPushChannelName(mAppFeed) + "_all");
mAppFeed.setPushNotificationsOn(true);
mAppFeed.setReceiveTopNotifications(false);
mAppFeed.setChannelName(getPushChannelName(mAppFeed) + "_all");
hideNotificationButtons();
mPushAllStoriesSelectedButton.setVisibility(View.VISIBLE);
mPersistedFeedDaoHelper.createOrUpdate(mAppFeed);
}
}
Not sure how to transition this into Clevertap.
Thanks for the help.
You can find the Parse migration guide here - https://github.com/CleverTap/parse-migrate and, channels is discussed here - https://github.com/CleverTap/parse-migrate#managing-channels. Do write to support#clevertap.com if you need more help, or have any questions.
I was successfully deleting selected items from listbox and after that all objects were deleted from db and listbox was refreshed.
then i added the confirmation box with yes and no option, then my list wasn't refreshed. i saw this thread with similar problem on zk forum with a solution, i implemented it but getting the class cast exception
I am using MVVM
http://forum.zkoss.org/question/73640/refreshing-listbox-after-deleting-an-itemrow/
code getting the exception:
AnnotateDataBinder binder = (AnnotateDataBinder) userWin.getAttribute("binder");
binder.loadAll();
exception:
Mar 21, 2013 5:22:23 PM org.zkoss.zk.ui.impl.UiEngineImpl handleError:1352
SEVERE: >>java.lang.ClassCastException: org.zkoss.bind.AnnotateBinder cannot be cast to org.zkoss.zkplus.databind.AnnotateDataBinder
looking forward to hear from you. I have searched the net, but couldn't find anything but updating the zk. i am already using the latest version of zk 6.5.1.1.
thanks in advance.
#after adding your suggested line of code, my list was not updated, here is my method
#Override
#Command("deleteAllSelected")
#NotifyChange({"selectedObject","objectList"})
public void deleteAllSelected() {
logger.info("in deleteAllSelected()>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
logger.info("direct selection: " + objectList.getSelection());
final Set<UserIntelliopsDTO> setMe = objectList.getSelection();
logger.info("selectedion size in dellete all" + setMe.size());
EventListener<ClickEvent> clickListener = new EventListener<Messagebox.ClickEvent>() {
public void onEvent(ClickEvent event) throws Exception {
if (Messagebox.Button.YES.equals(event.getButton())) {
int i =0;
for(UserIntelliopsDTO dto:setMe){
userService.deleteUserIntelliops(dto.getUserIntelliOps().getUserId());
logger.info("siapa:userIntelliops " + dto.getUserIntelliOps() + dto.getUserIntelliOps().getUserId());
selectedObject = null;
logger.info("iteration: " + i);
++i;
}
selectedObject = null;
deleteAllSelectedButton.setVisible(false);
enableEditMode(true);
}
}
};
Messagebox.show("Are you sure you want to delete all selected records?", "Delete All Selected",
new Messagebox.Button[] { Messagebox.Button.YES,
Messagebox.Button.NO }, Messagebox.QUESTION,
clickListener);
BindUtils.postNotifyChange(null, null, this, "*");
}
I am assuming you are using MVVM Model..So you can do this thing when you will click on delete button below method will code...
#Command
public void doDeleteItems(#ContextParam(ContextType.VIEW) Component view) {
logger.debug("Delete Icon selected");
if (myModel.getSelectedListItem() == null || myModel.getSelectedListItem().isEmpty()) {
showError("No rows are selected");
} else {
Messagebox.show("Are you sure you want to delete?", "Alert !!", Messagebox.YES | Messagebox.NO, Messagebox.QUESTION,new org.zkoss.zk.ui.event.EventListener() {
public void onEvent(Event evt) throws InterruptedException {
if (evt.getName().equals("onYes")) {
//Add code for Deletion
if (listModel.contains(deletedObj))
listModel.remove(deletedObj);
}
else{
//Do somthing else
}
BindUtils.postNotifyChange(null, null, this, "*");//this means current viewmodel object and refresh the variables
}
As i did BindUtils.postNotifyChange() it will do magic for you refreshing the list or you can use NotifyChange("*")
One more thing you have to do here remove object from list after deleting the record...