Project::OSiRiON - Git repositories
Project::OSiRiON
News . About . Screenshots . Downloads . Forum . Wiki . Tracker . Git
summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/client/inventorylistview.cc39
-rw-r--r--src/client/inventorylistview.h11
-rw-r--r--src/client/trademenu.cc50
-rw-r--r--src/client/trademenu.h4
-rw-r--r--src/core/inventory.cc2
-rw-r--r--src/core/inventory.h2
-rw-r--r--src/core/item.cc2
-rw-r--r--src/game/base/cargo.cc67
-rw-r--r--src/game/base/cargo.h2
-rw-r--r--src/game/base/game.cc57
-rw-r--r--src/game/base/game.h1
-rw-r--r--src/ui/listitem.cc1
-rw-r--r--src/ui/listitem.h10
-rw-r--r--src/ui/listview.cc7
-rw-r--r--src/ui/listview.h3
-rw-r--r--src/ui/widget.cc9
-rw-r--r--src/ui/widget.h3
17 files changed, 245 insertions, 25 deletions
diff --git a/src/client/inventorylistview.cc b/src/client/inventorylistview.cc
index 1b46fd0..d2752d6 100644
--- a/src/client/inventorylistview.cc
+++ b/src/client/inventorylistview.cc
@@ -11,17 +11,23 @@ namespace client {
InventoryListView::InventoryListView(ui::Widget *parent) : ui::ListView (parent)
{
+ listview_timestamp = 0;
set_inventory(0, 0);
}
InventoryListView::~InventoryListView() {
}
-void InventoryListView::set_inventory(core::Inventory *inventory, core::InfoType *info_type)
+void InventoryListView::set_inventory(core::Inventory *inventory, core::InfoType *infotype)
{
remove_children();
- if (!inventory || !info_type) {
+ listview_inventory = inventory;
+ listview_infotype = infotype;
+
+ const core::Item *selecteditem = (selected() ? selected()->item() : 0);
+
+ if (!inventory || !infotype) {
return;
}
@@ -31,15 +37,38 @@ void InventoryListView::set_inventory(core::Inventory *inventory, core::InfoType
for (core::Inventory::Items::const_iterator it = inventory->items().begin(); it != inventory->items().end(); it++) {
core::Item *item = (*it);
- if (item->info() && item->info()->type() == info_type) {
- ui::ListItem *listitem = 0;
- listitem = new ui::ListItem(this, item->info()->name().c_str());
+ if (item->info() && (item->info()->type() == infotype) && (item->amount() != 0) ) {
+ ui::ListItem *listitem = 0;
+
+ std::ostringstream str;
+ str << item->info()->name().c_str();
+
+ if (item->amount() > 0) {
+ str << " (" << item->amount() << ")";
+ }
+ listitem = new ui::ListItem(this, str.str().c_str());
listitem->set_height(listitem->font()->height() * 2.0f);
+ listitem->set_item(item);
listitem->set_info(item->info());
+ // preserve previous selection during update
+ if (item == selecteditem) {
+ ui::ListView::select(listitem);
+ }
}
}
+ listview_timestamp = inventory->timestamp();
+
event_resize();
}
+void InventoryListView::draw()
+{
+ if (listview_timestamp != listview_inventory->timestamp()) {
+ set_inventory(listview_inventory, listview_infotype);
+ }
+
+ ListView::draw();
+}
+
} // namespace client \ No newline at end of file
diff --git a/src/client/inventorylistview.h b/src/client/inventorylistview.h
index 82a9cc4..0d14072 100644
--- a/src/client/inventorylistview.h
+++ b/src/client/inventorylistview.h
@@ -19,7 +19,16 @@ public:
InventoryListView(ui::Widget *parent = 0);
~InventoryListView();
- void set_inventory(core::Inventory *inventory, core::InfoType *info_type);
+ void set_inventory(core::Inventory *inventory, core::InfoType *infotype);
+
+protected:
+
+ virtual void draw();
+
+private:
+ unsigned long listview_timestamp;
+ core::Inventory *listview_inventory;
+ core::InfoType *listview_infotype;
};
} // namespace client
diff --git a/src/client/trademenu.cc b/src/client/trademenu.cc
index 837ee87..d93864d 100644
--- a/src/client/trademenu.cc
+++ b/src/client/trademenu.cc
@@ -42,6 +42,15 @@ TradeMenu::TradeMenu(ui::Widget *parent, const char * label) : ui::Window(parent
menu_inventorylistview->set_background(false);
menu_inventorylistview->set_border(true);
+ menu_inventorylabel = new ui::Label(menu_tradewindow);
+ menu_inventorylabel->set_label("label");
+ menu_inventorylabel->set_background(false);
+ menu_inventorylabel->set_border(false);
+ menu_inventorylabel->set_font(ui::root()->font_small());
+ menu_inventorylabel->set_alignment(ui::AlignLeft);
+
+
+
menu_modelview = new ui::ModelView(menu_tradewindow);
menu_modelview->set_label("modelview");
menu_modelview->set_background(false);
@@ -57,12 +66,19 @@ TradeMenu::TradeMenu(ui::Widget *parent, const char * label) : ui::Window(parent
menu_traderlistview->set_background(false);
menu_traderlistview->set_border(true);
+ menu_traderlabel = new ui::Label(menu_tradewindow);
+ menu_traderlabel->set_label("label");
+ menu_traderlabel->set_background(false);
+ menu_traderlabel->set_border(false);
+ menu_traderlabel->set_font(ui::root()->font_small());
+ menu_traderlabel->set_alignment(ui::AlignLeft);
+
menu_closebutton = new ui::Button(menu_tradewindow, "Return", "view hide");
menu_buyallbutton = new ui::Button(menu_modelview, "<<");
menu_buybutton = new ui::Button(menu_modelview, "<");
- menu_sellallbutton = new ui::Button(menu_modelview, ">");
- menu_sellbutton = new ui::Button(menu_modelview, ">>");
+ menu_sellallbutton = new ui::Button(menu_modelview, ">>");
+ menu_sellbutton = new ui::Button(menu_modelview, ">");
std::string test("test");
@@ -99,7 +115,8 @@ void TradeMenu::set_item_type(core::InfoType *item_type)
void TradeMenu::set_item(ui::ListItem *item)
{
menu_infotext.clear();
- menu_namelabel->clear();
+ menu_namelabel->set_text("Trade");
+ menu_traderlabel->clear();
if (!item || !item->info()) {
menu_traderlistview->deselect();
@@ -135,6 +152,10 @@ void TradeMenu::set_item(ui::ListItem *item)
menu_buybutton->show();
menu_buybutton->set_command("remote buy " + item->info()->type()->label() + " " + item->info()->label() + " 1; ");
+ std::ostringstream str;
+ str << "Price: " << item->item()->price();
+ menu_traderlabel->set_text(str.str());
+
menu_sellallbutton->hide();
menu_sellbutton->hide();
@@ -177,9 +198,12 @@ void TradeMenu::resize()
menu_namelabel->set_location(fontmargin, fontmargin);
// resize inventory listview
- menu_inventorylistview->set_size(ui::UI::elementsize.width(), menu_tradewindow->height() - smallmargin * 2.0f - fontmargin * 3.0f);
+ menu_inventorylistview->set_size(ui::UI::elementsize.width(), menu_tradewindow->height() - smallmargin * 2.0f - fontmargin * 6.0f);
menu_inventorylistview->set_location(fontmargin, fontmargin * 3.0f);
+ menu_inventorylabel->set_size(menu_inventorylistview->width(), fontmargin);
+ menu_inventorylabel->set_location(menu_inventorylistview->left(), menu_inventorylistview->bottom() + fontmargin);
+
// resize modelview
menu_modelview->set_size(menu_tradewindow->width() - 2.0f * ui::UI::elementsize.width() - fontmargin * 4.0f, ui::UI::elementsize.width());
menu_modelview->set_location(fontmargin * 2.0f + ui::UI::elementsize.width(), fontmargin * 3.0f);
@@ -198,13 +222,16 @@ void TradeMenu::resize()
menu_sellbutton->set_location(menu_modelview->width() - 3.0f * fontmargin, menu_modelview->height() - fontmargin);
// resize scrollpane
- menu_scrollpane->set_size(menu_tradewindow->width() - 2.0f * ui::UI::elementsize.width() - fontmargin * 4.0f, menu_inventorylistview->height() - fontmargin - ui::UI::elementsize.width());
+ menu_scrollpane->set_size(menu_tradewindow->width() - 2.0f * ui::UI::elementsize.width() - fontmargin * 4.0f, menu_inventorylistview->height() + 2.0f * fontmargin - ui::UI::elementsize.width());
menu_scrollpane->set_location(fontmargin * 2.0f + ui::UI::elementsize.width(), fontmargin * 4.0f + ui::UI::elementsize.width());
// resize trader listview
- menu_traderlistview->set_size(ui::UI::elementsize.width(), menu_tradewindow->height() - smallmargin * 2.0f - fontmargin * 3.0f);
+ menu_traderlistview->set_size(ui::UI::elementsize.width(), menu_tradewindow->height() - smallmargin * 2.0f - fontmargin * 6.0f);
menu_traderlistview->set_location(menu_tradewindow->width() - menu_traderlistview->width() - fontmargin, fontmargin * 3.0f);
-
+
+ menu_traderlabel->set_size(menu_traderlistview->width(), fontmargin);
+ menu_traderlabel->set_location(menu_traderlistview->left(), menu_traderlistview->bottom() + fontmargin);
+
// resize close button
menu_closebutton->set_size(ui::UI::elementsize);
menu_closebutton->set_location(0.5f * (menu_tradewindow->width() - ui::UI::elementsize.width()), menu_tradewindow->height() - smallmargin * 1.5f );
@@ -220,4 +247,13 @@ bool TradeMenu::on_emit(Widget *sender, const Event event, void *data)
return ui::Window::on_emit(sender, event, data);
}
+void TradeMenu::draw()
+{
+ std::stringstream str;
+ str << "Credits: " << core::localplayer()->credits();
+ menu_inventorylabel->set_text(str.str());
+
+ Window::draw();
+}
+
}
diff --git a/src/client/trademenu.h b/src/client/trademenu.h
index 477a372..5f56a08 100644
--- a/src/client/trademenu.h
+++ b/src/client/trademenu.h
@@ -34,6 +34,8 @@ protected:
/// resize event handler
virtual void resize();
+ virtual void draw();
+
/// emit event handler
virtual bool on_emit(Widget *sender, const Event event, void *data);
@@ -43,6 +45,8 @@ private:
ui::Window *menu_tradewindow;
ui::Button *menu_closebutton;
ui::Label *menu_namelabel;
+ ui::Label *menu_inventorylabel;
+ ui::Label *menu_traderlabel;
ui::ModelView *menu_modelview;
ui::ScrollPane *menu_scrollpane;
diff --git a/src/core/inventory.cc b/src/core/inventory.cc
index 6afa76f..c659178 100644
--- a/src/core/inventory.cc
+++ b/src/core/inventory.cc
@@ -29,7 +29,7 @@ void Inventory::set_timestamp(const unsigned long timestamp)
inventory_timestamp = timestamp;
}
-void Inventory::mark()
+void Inventory::set_dirty()
{
inventory_timestamp = core::game()->timestamp();
}
diff --git a/src/core/inventory.h b/src/core/inventory.h
index c715116..0a412b0 100644
--- a/src/core/inventory.h
+++ b/src/core/inventory.h
@@ -74,7 +74,7 @@ public:
/**
* @brief set the timestamp to the current game time
*/
- void mark();
+ void set_dirty();
private:
Items inventory_items;
diff --git a/src/core/item.cc b/src/core/item.cc
index 3528c1a..ca51775 100644
--- a/src/core/item.cc
+++ b/src/core/item.cc
@@ -16,7 +16,7 @@ Item::Item(const Info *info)
{
item_info = info;
item_amount = 0;
- item_price = 0;
+ item_price = info->price();
}
Item::~Item()
diff --git a/src/game/base/cargo.cc b/src/game/base/cargo.cc
index 420d4d3..689ae92 100644
--- a/src/game/base/cargo.cc
+++ b/src/game/base/cargo.cc
@@ -103,16 +103,81 @@ Cargo *Cargo::find(const std::string & label)
return (Cargo *) core::Info::find(cargo_infotype, label);
}
+// main 'sell cargo' function
+void Cargo::sell(core::EntityControlable *seller, core::Entity *buyer, const int amount)
+{
+ if (!buyer || !seller)
+ return;
+
+ // can only sell at planets and stations
+ if ((buyer->moduletype() != station_enttype) && (buyer->moduletype() != planet_enttype)) {
+ seller->owner()->send("^BCan not sell here");
+ return;
+ }
+
+ if (!seller->owner())
+ return;
+
+ if (!buyer->inventory() || !seller->inventory()) {
+ seller->owner()->send("^BCan not sell here");
+ return;
+ }
+
+ if (!amount) {
+ return;
+ }
+
+ core::Item *seller_item = seller->inventory()->find(this);
+ if (!seller_item) {
+ if (seller->owner()) {
+ seller->owner()->send("^BYou do not own any " + name());
+ }
+ return;
+ }
+
+ int negotiated_amount = amount;
+ if (negotiated_amount < 0) {
+ negotiated_amount = seller_item->amount();
+ } else if (negotiated_amount > seller_item->amount()) {
+ negotiated_amount = seller_item->amount();
+ }
+
+ int negotiated_price = price(); // base price
+ core::Item *buyer_item = buyer->inventory()->find(this);
+ if (buyer_item) {
+ negotiated_price = buyer_item->price();
+ }
+
+
+ seller_item->set_amount(seller_item->amount() - negotiated_amount);
+ seller->owner()->set_credits(seller->owner()->credits() + negotiated_price * negotiated_amount);
+ seller->inventory()->set_dirty();
+
+ // send a cargo purchased message
+ std::stringstream msgstr;
+ msgstr << "^BSold " << negotiated_amount << " " << aux::plural("unit", negotiated_amount) << " of " << name() << " for " << negotiated_price * negotiated_amount << " credits";
+ seller->owner()->send(msgstr.str());
+ seller->owner()->sound("game/buy");
+
+}
+
// main 'buy cargo' function
void Cargo::buy(core::EntityControlable *buyer, core::Entity *seller, const int amount)
{
if (!buyer || !seller)
return;
+
+ // can only buy at planets and stations
+ if ((seller->moduletype() != station_enttype) && (seller->moduletype() != planet_enttype)) {
+ buyer->owner()->send("^BCan not buy here");
+ return;
+ }
if (!buyer->owner())
return;
if (!buyer->inventory() || !seller->inventory()) {
+ buyer->owner()->send("^BCan not buy here");
return;
}
@@ -156,6 +221,8 @@ void Cargo::buy(core::EntityControlable *buyer, core::Entity *seller, const int
buyer_item->inc_amount(negotiated_amount);
buyer->owner()->set_credits(buyer->owner()->credits() - negotiated_price * negotiated_amount);
+ buyer->inventory()->set_dirty();
+
// send a cargo purchased message
std::stringstream msgstr;
msgstr << "^BPurchased " << negotiated_amount << " " << aux::plural("unit", negotiated_amount) << " of " << name() << " for " << negotiated_price * negotiated_amount << " credits";
diff --git a/src/game/base/cargo.h b/src/game/base/cargo.h
index 9b2bca5..1e97d40 100644
--- a/src/game/base/cargo.h
+++ b/src/game/base/cargo.h
@@ -19,6 +19,8 @@ public:
void buy(core::EntityControlable *buyer, core::Entity *seller, const int amount);
+ void sell(core::EntityControlable *seller, core::Entity *buyer, const int amount);
+
/* -- static functions -- */
static core::InfoType *cargo_infotype;
diff --git a/src/game/base/game.cc b/src/game/base/game.cc
index 9f8dabc..83d0be8 100644
--- a/src/game/base/game.cc
+++ b/src/game/base/game.cc
@@ -267,34 +267,71 @@ void Game::func_give(core::Player *player, const std::string &args)
}
}
+// sell request from a player
+void Game::func_sell(core::Player *player, const std::string &args)
+{
+ std::istringstream is(args);
+ std::string typestr;
+ std::string labelstr;
+
+ if (!(is >> typestr)) {
+ player->send("Usage: sell [string] [string] [int] sell an item: specify type, label and amount");
+ return;
+ } else {
+ aux::to_label(typestr);
+ }
+
+ if (!(is >> labelstr)) {
+ player->send("Usage: sell [string] [string] [int] sell an item: specify type, label and amount");
+ return;
+ } else {
+ aux::to_label(labelstr);
+ }
+
+ int amount = 0;
+ if (!(is >> amount))
+ amount = 0;
+
+ if (typestr.compare("cargo") == 0) {
+ Cargo *cargo = Cargo::find(labelstr);
+ if (cargo) {
+ cargo->sell(player->control(), player->view(), amount);
+ } else {
+ player->send("Unkown cargo type '" + labelstr + "'");
+ }
+ } else {
+ player->send("Unkown item type '" + typestr + "'");
+ }
+ return;
+}
+
// buy request from a player
void Game::func_buy(core::Player *player, const std::string &args)
{
std::istringstream is(args);
std::string typestr;
std::string labelstr;
- int amount = 0;
if (!(is >> typestr)) {
- player->send("Usage: buy [string] [string] buy an item, specify type and label");
+ player->send("Usage: buy [string] [string] [int] buy an item: specify type, label and amount");
return;
} else {
aux::to_label(typestr);
}
if (!(is >> labelstr)) {
- labelstr.clear();
+ player->send("Usage: buy [string] [string] [int] buy an item: specify type, label and amount");
+ return;
} else {
aux::to_label(labelstr);
}
-
+
+ int amount = 0;
if (!(is >> amount))
amount = 0;
if (typestr.compare("ship") == 0) {
- ShipDealer::func_buy(player, labelstr);
-
-
+ ShipDealer::func_buy(player, labelstr);
} else if (typestr.compare("cargo") == 0) {
Cargo *cargo = Cargo::find(labelstr);
if (cargo) {
@@ -305,7 +342,6 @@ void Game::func_buy(core::Player *player, const std::string &args)
} else {
player->send("Unkown item type '" + typestr + "'");
}
-
return;
}
@@ -495,8 +531,11 @@ Game::Game() : core::Module("Project::OSiRiON", true)
func->set_info("leave the game and spectate");
func = core::Func::add("buy", Game::func_buy);
- func->set_info("[string] [string] buy type of item, name of item");
+ func->set_info("[string] [string] [int] buy an item: specify type, label and amount");
+ func = core::Func::add("sell", Game::func_sell);
+ func->set_info("[string] [string] [int] sell an item: specify type, label and amount");
+
func = core::Func::add("give", Game::func_give);
func->set_info("cheat functions");
diff --git a/src/game/base/game.h b/src/game/base/game.h
index e091630..ce37fa6 100644
--- a/src/game/base/game.h
+++ b/src/game/base/game.h
@@ -107,6 +107,7 @@ private:
static void func_respawn(core::Player *player, std::string const &args);
static void func_goto(core::Player *player, const std::string &args);
static void func_buy(core::Player *player, std::string const &args);
+ static void func_sell(core::Player *player, const std::string &args);
static void func_give(core::Player *player, const std::string &args);
};
diff --git a/src/ui/listitem.cc b/src/ui/listitem.cc
index dcd4e2a..601d5a8 100644
--- a/src/ui/listitem.cc
+++ b/src/ui/listitem.cc
@@ -15,6 +15,7 @@ ListItem::ListItem(ListView *parent, const char * text) : Label(parent, text) {
set_label("listitem");
listitem_info = 0;
+ listitem_item = 0;
}
ListItem::~ListItem() {
diff --git a/src/ui/listitem.h b/src/ui/listitem.h
index cc03621..1d4cd33 100644
--- a/src/ui/listitem.h
+++ b/src/ui/listitem.h
@@ -10,6 +10,7 @@
#include <string>
#include "core/info.h"
+#include "core/item.h"
#include "ui/label.h"
namespace ui
@@ -30,9 +31,17 @@ public:
return listitem_info;
}
+ inline const core::Item *item() const {
+ return listitem_item;
+ }
+
inline void set_info(const core::Info *info) {
listitem_info = info;
}
+
+ inline void set_item(const core::Item *item) {
+ listitem_item = item;
+ }
protected:
/// keypress event handler
@@ -45,6 +54,7 @@ protected:
private:
const core::Info *listitem_info;
+ const core::Item *listitem_item;
};
} // namespace ui
diff --git a/src/ui/listview.cc b/src/ui/listview.cc
index 646b168..e503807 100644
--- a/src/ui/listview.cc
+++ b/src/ui/listview.cc
@@ -73,6 +73,13 @@ void ListView::deselect()
listview_selecteditem = 0;
}
+void ListView::select(ListItem *item)
+{
+ if (is_child(item)) {
+ listview_selecteditem = item;
+ }
+}
+
void ListView::clear()
{
listview_selecteditem = 0;
diff --git a/src/ui/listview.h b/src/ui/listview.h
index a650348..a0c185b 100644
--- a/src/ui/listview.h
+++ b/src/ui/listview.h
@@ -53,6 +53,9 @@ public:
/// clear all listitems
void clear();
+ /// set selection to specified ListItem
+ void select(ListItem *item);
+
/// set selection to nothing
void deselect();
diff --git a/src/ui/widget.cc b/src/ui/widget.cc
index 5fe6f17..79281a1 100644
--- a/src/ui/widget.cc
+++ b/src/ui/widget.cc
@@ -47,6 +47,15 @@ void Widget::remove_children()
widget_children.clear();
}
+bool Widget::is_child(const Widget *widget) const
+{
+ for (Children::const_iterator it = widget_children.begin(); it != widget_children.end(); it++) {
+ if (widget == (*it))
+ return true;
+ }
+ return false;
+}
+
size_t Widget::list(const size_t indent, const bool visible_only) const
{
if (visible_only && !visible())
diff --git a/src/ui/widget.h b/src/ui/widget.h
index 880b71c..3ae75d2 100644
--- a/src/ui/widget.h
+++ b/src/ui/widget.h
@@ -139,6 +139,9 @@ public:
/// returns true if the widget has mouse focus
bool has_mouse_focus() const;
+
+ /// return true of the widget is a child widget
+ bool is_child(const Widget *widget) const;
/* -- mutators --------------------------------------------- */