diff --git a/.pkgmeta b/.pkgmeta new file mode 100644 index 0000000..6fd9bde --- /dev/null +++ b/.pkgmeta @@ -0,0 +1,7 @@ +package-as: BagSync + +externals: + libs/CustomSearch-1.0: https://github.com/Jaliborc/CustomSearch-1.0.git + libs/LibDataBroker-1.1: https://github.com/tekkub/libdatabroker-1-1.git + libs/LibItemSearch-1.2: https://github.com/Jaliborc/LibItemSearch-1.2.git + libs/Unfit-1.0: https://github.com/Jaliborc/Unfit-1.0.git diff --git a/libs/CustomSearch-1.0 b/libs/CustomSearch-1.0 deleted file mode 160000 index fe0d78b..0000000 --- a/libs/CustomSearch-1.0 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit fe0d78b4249eab4b2338126deb443777533831de diff --git a/libs/CustomSearch-1.0/.DS_Store b/libs/CustomSearch-1.0/.DS_Store new file mode 100644 index 0000000..b95bdac Binary files /dev/null and b/libs/CustomSearch-1.0/.DS_Store differ diff --git a/libs/CustomSearch-1.0/CustomSearch-1.0.lua b/libs/CustomSearch-1.0/CustomSearch-1.0.lua new file mode 100644 index 0000000..f8d4455 --- /dev/null +++ b/libs/CustomSearch-1.0/CustomSearch-1.0.lua @@ -0,0 +1,202 @@ +--[[ +Copyright 2013 João Cardoso +CustomSearch is distributed under the terms of the GNU General Public License (Version 3). +As a special exception, the copyright holders of this library give you permission to embed it +with independent modules to produce an addon, regardless of the license terms of these +independent modules, and to copy and distribute the resulting software under terms of your +choice, provided that you also meet, for each embedded independent module, the terms and +conditions of the license of that module. Permission is not granted to modify this library. + +This library is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with the library. If not, see <http://www.gnu.org/licenses/gpl-3.0.txt>. + +This file is part of CustomSearch. +--]] + +local Lib = LibStub:NewLibrary('CustomSearch-1.0', 9) +if not Lib then + return +end + + +--[[ Parsing ]]-- + +function Lib:Matches(object, search, filters) + if object then + self.filters = filters + self.object = object + + return self:MatchAll(search or '') + end +end + +function Lib:MatchAll(search) + for phrase in self:Clean(search):gmatch('[^&]+') do + if not self:MatchAny(phrase) then + return + end + end + + return true +end + +function Lib:MatchAny(search) + for phrase in search:gmatch('[^|]+') do + if self:Match(phrase) then + return true + end + end +end + +function Lib:Match(search) + local tag, rest = search:match('^%s*(%S+):(.*)$') + if tag then + tag = '^' .. tag + search = rest + end + + local words = search:gmatch('%S+') + local failed + + for word in words do + if word == self.OR then + if failed then + failed = false + else + break + end + + else + local negate, rest = word:match('^([!~]=*)(.*)$') + if negate or word == self.NOT_MATCH then + word = rest and rest ~= '' and rest or words() or '' + negate = -1 + else + negate = 1 + end + + local operator, rest = word:match('^(=*[<>]=*)(.*)$') + if operator then + word = rest ~= '' and rest or words() + end + + local result = self:Filter(tag, operator, word) and 1 or -1 + if result * negate ~= 1 then + failed = true + end + end + end + + return not failed +end + + +--[[ Filtering ]]-- + +function Lib:Filter(tag, operator, search) + if not search then + return true + end + + if tag then + for _, filter in pairs(self.filters) do + for _, value in pairs(filter.tags or {}) do + if value:find(tag) then + return self:UseFilter(filter, operator, search) + end + end + end + else + for _, filter in pairs(self.filters) do + if not filter.onlyTags and self:UseFilter(filter, operator, search) then + return true + end + end + end +end + +function Lib:UseFilter(filter, operator, search) + local data = {filter:canSearch(operator, search, self.object)} + if data[1] then + return filter:match(self.object, operator, unpack(data)) + end +end + + +--[[ Utilities ]]-- + +function Lib:Find(search, ...) + for i = 1, select('#', ...) do + local text = select(i, ...) + if text and self:Clean(text):find(search) then + return true + end + end +end + +function Lib:Clean(string) + string = string:lower() + string = string:gsub('[%(%)%.%%%+%-%*%?%[%]%^%$]', function(c) return '%'..c end) + + for accent, char in pairs(self.ACCENTS) do + string = string:gsub(accent, char) + end + + return string +end + +function Lib:Compare(op, a, b) + if op then + if op:find('<') then + if op:find('=') then + return a <= b + end + + return a < b + end + + if op:find('>')then + if op:find('=') then + return a >= b + end + + return a > b + end + end + + return a == b +end + + +--[[ Localization ]]-- + +do + local no = {enUS = 'Not', frFR = 'Pas', deDE = 'Nicht'} + local accents = { + a = {'à','â','ã','å'}, + e = {'è','é','ê','ê','ë'}, + i = {'ì', 'í', 'î', 'ï'}, + o = {'ó','ò','ô','õ'}, + u = {'ù', 'ú', 'û', 'ü'}, + c = {'ç'}, n = {'ñ'} + } + + Lib.ACCENTS = {} + for char, accents in pairs(accents) do + for _, accent in ipairs(accents) do + Lib.ACCENTS[accent] = char + end + end + + Lib.OR = Lib:Clean(JUST_OR) + Lib.NOT = no[GetLocale()] or NO + Lib.NOT_MATCH = Lib:Clean(Lib.NOT) + setmetatable(Lib, {__call = Lib.Matches}) +end + +return Lib \ No newline at end of file diff --git a/libs/CustomSearch-1.0/README.md b/libs/CustomSearch-1.0/README.md new file mode 100644 index 0000000..2b8dad3 --- /dev/null +++ b/libs/CustomSearch-1.0/README.md @@ -0,0 +1,69 @@ +# CustomSearch-1.0 +Framework for building search engines in lua. Handles most of the heavy work for you, such as concept separation, +non ascii character support, logical operators and user criteria selection. + +### API Overview +|Name|Description| +|:--|:--| +| :Matches(article, search, filters) | Returns wether the given `article` matches the `search` query using the `filters` structure as the criteria. | +| :Find(search, field1, field2, ...) | Returns wether the `search` string is present on any of the string `fields` provided. | +| :Compare(operator, a, b) | Returns an inequality operation between `a` and `b`, where `operator` is the string representation of the operation. | + +### Filters Specification +The `filters` data structure allows you to easly build a search engine of your own. +`filters` is a set of filter objects. Each filter is akin to an independent criteria of the engine: +if any filter approves the `article` for a given `search` query, the `article` is approved. + +For an object to be a filter, it must implement the following fields: + +|Name|Description| +|:--|:--| +| :canSearch(operator, search, article) | Returns wether the filter can process this query. If not `.match` will not be called and this filter will not be considered for the query. Can return any number of arguments. | +| :match(article, operator, data1, data2, ...) | Returns wether this filter approves the `article` for a given query. 'data1', 'data2', etc are the return arguments of :canSearch. | +| .tags | Optional. Array of identifiers that can be placed at the beggining of a `search` query to perform a `:Match` using only this filter. | + +### Examples + local Lib = LibStub('CustomSearch-1.0') + + Lib:Find('(João)', 'Roses are red', 'Violets are (jóaô)', 'Wait that was wrong') -- true + Lib:Find('banana', 'Roses are red', 'Violets are jóaô', 'Wait that was wrong') -- false + + Lib:Compare('<', 3, 4) -- true + Lib:Compare('>', 3, 4) -- false + Lib:Compare('>=', 5, 5) -- true + + local Filters = { + isBanana = { + tags = {'b', 'ba'}, + + canSearch = function(self, operator, search) + return true + end, + + match = function(self, article, operator, search) + return Lib:Find(article, 'banana') + end + }, + + searchingApple = { + tags = {'a', 'app'}, + + canSearch = function(self, operator, search) + if not operator then + return search + end + end, + + match = function(self, article, operator, search) + return Lib:Find(search, 'apple') + end + } + } + + Lib:Match('Banana', '', Filters) -- true + Lib:Match('', 'Apple', Filters) -- true + Lib:Match('', '> Apple', Filters) -- false + Lib:Match('Apple', 'Banana', Filters) -- false + Lib:Match('', 'b:Apple', Filters) -- false + Lib:Match('', 'a:Apple', Filters) -- true + diff --git a/libs/LibDataBroker-1.1 b/libs/LibDataBroker-1.1 deleted file mode 160000 index 1a63ede..0000000 --- a/libs/LibDataBroker-1.1 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 1a63ede0248c11aa1ee415187c1f9c9489ce3e02 diff --git a/libs/LibDataBroker-1.1/LibDataBroker-1.1.lua b/libs/LibDataBroker-1.1/LibDataBroker-1.1.lua new file mode 100644 index 0000000..f47c0cd --- /dev/null +++ b/libs/LibDataBroker-1.1/LibDataBroker-1.1.lua @@ -0,0 +1,90 @@ + +assert(LibStub, "LibDataBroker-1.1 requires LibStub") +assert(LibStub:GetLibrary("CallbackHandler-1.0", true), "LibDataBroker-1.1 requires CallbackHandler-1.0") + +local lib, oldminor = LibStub:NewLibrary("LibDataBroker-1.1", 4) +if not lib then return end +oldminor = oldminor or 0 + + +lib.callbacks = lib.callbacks or LibStub:GetLibrary("CallbackHandler-1.0"):New(lib) +lib.attributestorage, lib.namestorage, lib.proxystorage = lib.attributestorage or {}, lib.namestorage or {}, lib.proxystorage or {} +local attributestorage, namestorage, callbacks = lib.attributestorage, lib.namestorage, lib.callbacks + +if oldminor < 2 then + lib.domt = { + __metatable = "access denied", + __index = function(self, key) return attributestorage[self] and attributestorage[self][key] end, + } +end + +if oldminor < 3 then + lib.domt.__newindex = function(self, key, value) + if not attributestorage[self] then attributestorage[self] = {} end + if attributestorage[self][key] == value then return end + attributestorage[self][key] = value + local name = namestorage[self] + if not name then return end + callbacks:Fire("LibDataBroker_AttributeChanged", name, key, value, self) + callbacks:Fire("LibDataBroker_AttributeChanged_"..name, name, key, value, self) + callbacks:Fire("LibDataBroker_AttributeChanged_"..name.."_"..key, name, key, value, self) + callbacks:Fire("LibDataBroker_AttributeChanged__"..key, name, key, value, self) + end +end + +if oldminor < 2 then + function lib:NewDataObject(name, dataobj) + if self.proxystorage[name] then return end + + if dataobj then + assert(type(dataobj) == "table", "Invalid dataobj, must be nil or a table") + self.attributestorage[dataobj] = {} + for i,v in pairs(dataobj) do + self.attributestorage[dataobj][i] = v + dataobj[i] = nil + end + end + dataobj = setmetatable(dataobj or {}, self.domt) + self.proxystorage[name], self.namestorage[dataobj] = dataobj, name + self.callbacks:Fire("LibDataBroker_DataObjectCreated", name, dataobj) + return dataobj + end +end + +if oldminor < 1 then + function lib:DataObjectIterator() + return pairs(self.proxystorage) + end + + function lib:GetDataObjectByName(dataobjectname) + return self.proxystorage[dataobjectname] + end + + function lib:GetNameByDataObject(dataobject) + return self.namestorage[dataobject] + end +end + +if oldminor < 4 then + local next = pairs(attributestorage) + function lib:pairs(dataobject_or_name) + local t = type(dataobject_or_name) + assert(t == "string" or t == "table", "Usage: ldb:pairs('dataobjectname') or ldb:pairs(dataobject)") + + local dataobj = self.proxystorage[dataobject_or_name] or dataobject_or_name + assert(attributestorage[dataobj], "Data object not found") + + return next, attributestorage[dataobj], nil + end + + local ipairs_iter = ipairs(attributestorage) + function lib:ipairs(dataobject_or_name) + local t = type(dataobject_or_name) + assert(t == "string" or t == "table", "Usage: ldb:ipairs('dataobjectname') or ldb:ipairs(dataobject)") + + local dataobj = self.proxystorage[dataobject_or_name] or dataobject_or_name + assert(attributestorage[dataobj], "Data object not found") + + return ipairs_iter, attributestorage[dataobj], 0 + end +end diff --git a/libs/LibDataBroker-1.1/README.textile b/libs/LibDataBroker-1.1/README.textile new file mode 100644 index 0000000..ef16fed --- /dev/null +++ b/libs/LibDataBroker-1.1/README.textile @@ -0,0 +1,13 @@ +LibDataBroker is a small WoW addon library designed to provide a "MVC":http://en.wikipedia.org/wiki/Model-view-controller interface for use in various addons. +LDB's primary goal is to "detach" plugins for TitanPanel and FuBar from the display addon. +Plugins can provide data into a simple table, and display addons can receive callbacks to refresh their display of this data. +LDB also provides a place for addons to register "quicklaunch" functions, removing the need for authors to embed many large libraries to create minimap buttons. +Users who do not wish to be "plagued" by these buttons simply do not install an addon to render them. + +Due to it's simple generic design, LDB can be used for any design where you wish to have an addon notified of changes to a table. + +h2. Links + +* "API documentation":http://github.com/tekkub/libdatabroker-1-1/wikis/api +* "Data specifications":http://github.com/tekkub/libdatabroker-1-1/wikis/data-specifications +* "Addons using LDB":http://github.com/tekkub/libdatabroker-1-1/wikis/addons-using-ldb diff --git a/libs/LibItemSearch-1.2 b/libs/LibItemSearch-1.2 deleted file mode 160000 index 50231da..0000000 --- a/libs/LibItemSearch-1.2 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 50231da80984e21f894f3ced0bea4480907f632f diff --git a/libs/LibItemSearch-1.2/.DS_Store b/libs/LibItemSearch-1.2/.DS_Store new file mode 100644 index 0000000..126778d Binary files /dev/null and b/libs/LibItemSearch-1.2/.DS_Store differ diff --git a/libs/LibItemSearch-1.2/LibItemSearch-1.2.lua b/libs/LibItemSearch-1.2/LibItemSearch-1.2.lua new file mode 100644 index 0000000..a754bf8 --- /dev/null +++ b/libs/LibItemSearch-1.2/LibItemSearch-1.2.lua @@ -0,0 +1,276 @@ +--[[ + ItemSearch + An item text search engine of some sort +--]] + +local Search = LibStub('CustomSearch-1.0') +local Unfit = LibStub('Unfit-1.0') +local Lib = LibStub:NewLibrary('LibItemSearch-1.2', 13) +if Lib then + Lib.Filters = {} +else + return +end + + +--[[ User API ]]-- + +function Lib:Matches(link, search) + return Search(link, search, self.Filters) +end + +function Lib:Tooltip(link, search) + return link and self.Filters.tip:match(link, nil, search) +end + +function Lib:TooltipPhrase(link, search) + return link and self.Filters.tipPhrases:match(link, nil, search) +end + +function Lib:InSet(link, search) + if IsEquippableItem(link) then + local id = tonumber(link:match('item:(%-?%d+)')) + return self:BelongsToSet(id, (search or ''):lower()) + end +end + + +--[[ Basics ]]-- + +Lib.Filters.name = { + tags = {'n', 'name'}, + + canSearch = function(self, operator, search) + return not operator and search + end, + + match = function(self, item, _, search) + local name = item:match('%[(.-)%]') + return Search:Find(search, name) + end +} + +Lib.Filters.type = { + tags = {'t', 'type', 's', 'slot'}, + + canSearch = function(self, operator, search) + return not operator and search + end, + + match = function(self, item, _, search) + local type, subType, _, equipSlot = select(6, GetItemInfo(item)) + return Search:Find(search, type, subType, _G[equipSlot]) + end +} + +Lib.Filters.level = { + tags = {'l', 'level', 'lvl', 'ilvl'}, + + canSearch = function(self, _, search) + return tonumber(search) + end, + + match = function(self, link, operator, num) + local lvl = select(4, GetItemInfo(link)) + if lvl then + return Search:Compare(operator, lvl, num) + end + end +} + +Lib.Filters.requiredlevel = { + tags = {'r', 'req', 'rl', 'reql', 'reqlvl'}, + + canSearch = function(self, _, search) + return tonumber(search) + end, + + match = function(self, link, operator, num) + local lvl = select(5, GetItemInfo(link)) + if lvl then + return Search:Compare(operator, lvl, num) + end + end +} + + +--[[ Quality ]]-- + +local qualities = {} +for i = 0, #ITEM_QUALITY_COLORS do + qualities[i] = _G['ITEM_QUALITY' .. i .. '_DESC']:lower() +end + +Lib.Filters.quality = { + tags = {'q', 'quality'}, + + canSearch = function(self, _, search) + for i, name in pairs(qualities) do + if name:find(search) then + return i + end + end + end, + + match = function(self, link, operator, num) + local quality = link:sub(1, 9) == 'battlepet' and tonumber(link:match('%d+:%d+:(%d+)')) or select(3, GetItemInfo(link)) + return Search:Compare(operator, quality, num) + end, +} + + +--[[ Usable ]]-- + +Lib.Filters.usable = { + tags = {}, + + canSearch = function(self, operator, search) + return not operator and search == 'usable' + end, + + match = function(self, link) + if not Unfit:IsItemUnusable(link) then + local lvl = select(5, GetItemInfo(link)) + return lvl and (lvl == 0 or lvl > UnitLevel('player')) + end + end +} + + +--[[ Tooltip Searches ]]-- + +local scanner = LibItemSearchTooltipScanner or CreateFrame('GameTooltip', 'LibItemSearchTooltipScanner', UIParent, 'GameTooltipTemplate') + +Lib.Filters.tip = { + tags = {'tt', 'tip', 'tooltip'}, + onlyTags = true, + + canSearch = function(self, _, search) + return search + end, + + match = function(self, link, _, search) + if link:find('item:') then + scanner:SetOwner(UIParent, 'ANCHOR_NONE') + scanner:SetHyperlink(link) + + for i = 1, scanner:NumLines() do + if Search:Find(search, _G[scanner:GetName() .. 'TextLeft' .. i]:GetText()) then + return true + end + end + end + end +} + +Lib.Filters.tipPhrases = { + canSearch = function(self, _, search) + return self.keywords[search] + end, + + match = function(self, link, _, search) + local id = link:match('item:(%d+)') + if not id then + return + end + + local cached = self.cache[search][id] + if cached ~= nil then + return cached + end + + scanner:SetOwner(UIParent, 'ANCHOR_NONE') + scanner:SetHyperlink(link) + + local matches = false + for i = 1, scanner:NumLines() do + if search == _G['LibItemSearchTooltipScannerTextLeft' .. i]:GetText() then + matches = true + break + end + end + + self.cache[search][id] = matches + return matches + end, + + cache = setmetatable({}, {__index = function(t, k) local v = {} t[k] = v return v end}), + keywords = { + [ITEM_SOULBOUND:lower()] = ITEM_BIND_ON_PICKUP, + ['bound'] = ITEM_BIND_ON_PICKUP, + ['bop'] = ITEM_BIND_ON_PICKUP, + ['boe'] = ITEM_BIND_ON_EQUIP, + ['bou'] = ITEM_BIND_ON_USE, + ['boa'] = ITEM_BIND_TO_BNETACCOUNT, + [GetItemClassInfo(LE_ITEM_CLASS_QUESTITEM):lower()] = ITEM_BIND_QUEST, + [QUESTS_LABEL:lower()] = ITEM_BIND_QUEST, + [TOY:lower()] = TOY, + [MINIMAP_TRACKING_VENDOR_REAGENT:lower()] = PROFESSIONS_USED_IN_COOKING, + ['reagent'] = PROFESSIONS_USED_IN_COOKING, + ['crafting'] = PROFESSIONS_USED_IN_COOKING, + ['naval'] = 'naval equipment', + ['follower'] = 'follower', + ['followe'] = 'follower', + ['follow'] = 'follower', + } +} + + +--[[ Equipment Sets ]]-- + +if IsAddOnLoaded('ItemRack') then + local sameID = ItemRack.SameID + + function Lib:BelongsToSet(id, search) + for name, set in pairs(ItemRackUser.Sets) do + if name:sub(1,1) ~= '' and Search:Find(search, name) then + for _, item in pairs(set.equip) do + if sameID(id, item) then + return true + end + end + end + end + end + +elseif IsAddOnLoaded('Wardrobe') then + function Lib:BelongsToSet(id, search) + for _, outfit in ipairs(Wardrobe.CurrentConfig.Outfit) do + local name = outfit.OutfitName + if Search:Find(search, name) then + for _, item in pairs(outfit.Item) do + if item.IsSlotUsed == 1 and item.ItemID == id then + return true + end + end + end + end + end + +else + function Lib:BelongsToSet(id, search) + for i = 1, GetNumEquipmentSets() do + local name = GetEquipmentSetInfo(i) + if Search:Find(search, name) then + local items = GetEquipmentSetItemIDs(name) + for _, item in pairs(items) do + if id == item then + return true + end + end + end + end + end +end + +Lib.Filters.sets = { + tags = {'s', 'set'}, + + canSearch = function(self, operator, search) + return not operator and search + end, + + match = function(self, link, _, search) + return Lib:InSet(link, search) + end, +} \ No newline at end of file diff --git a/libs/LibItemSearch-1.2/LibItemSearch-1.2.toc b/libs/LibItemSearch-1.2/LibItemSearch-1.2.toc new file mode 100644 index 0000000..3d148de --- /dev/null +++ b/libs/LibItemSearch-1.2/LibItemSearch-1.2.toc @@ -0,0 +1,8 @@ +## Interface: 70000 +## Title: LibItemSearch +## Notes: An item search library +## OptionalDeps: LibStub, Unfit-1.0, CustomSearch-1.0, ItemRack, Wardrobe +## Author: Jaliborc (João Cardoso), Tuller, Yewbacca +## LoadOnDemand: 1 + +LibItemSearch-1.2.lua \ No newline at end of file diff --git a/libs/LibItemSearch-1.2/README.markdown b/libs/LibItemSearch-1.2/README.markdown new file mode 100644 index 0000000..5c88ae3 --- /dev/null +++ b/libs/LibItemSearch-1.2/README.markdown @@ -0,0 +1,5 @@ +### A search engine for World of Warcraft items + +For information regarding the search syntax, see [this page](https://github.com/Jaliborc/LibItemSearch-1.2/wiki/Search-Syntax). + +Requires [LibStub](http://www.wowace.com/addons/libstub/) and [CustomSearch](https://github.com/Jaliborc/CustomSearch-1.0). \ No newline at end of file diff --git a/libs/Unfit-1.0 b/libs/Unfit-1.0 deleted file mode 160000 index d769a30..0000000 --- a/libs/Unfit-1.0 +++ /dev/null @@ -1 +0,0 @@ -Subproject commit d769a3050a9c2c2f84a88a4cf12cb0135993df52 diff --git a/libs/Unfit-1.0/.gitignore b/libs/Unfit-1.0/.gitignore new file mode 100644 index 0000000..ae649c2 --- /dev/null +++ b/libs/Unfit-1.0/.gitignore @@ -0,0 +1,2 @@ +.DS_Store* +Icon? \ No newline at end of file diff --git a/libs/Unfit-1.0/License.url b/libs/Unfit-1.0/License.url new file mode 100644 index 0000000..9bf56c7 --- /dev/null +++ b/libs/Unfit-1.0/License.url @@ -0,0 +1,2 @@ +[InternetShortcut] +URL=http://www.gnu.org/licenses/gpl-3.0.txt diff --git a/libs/Unfit-1.0/Tests.lua b/libs/Unfit-1.0/Tests.lua new file mode 100644 index 0000000..8449256 --- /dev/null +++ b/libs/Unfit-1.0/Tests.lua @@ -0,0 +1,14 @@ +if not WoWUnit then + return +end + +local Tests = WoWUnit('Unfit', 'PLAYER_LOGIN', 'GET_ITEM_INFO_RECEIVED') +local Replace, IsFalse, IsTrue = WoWUnit.Replace, WoWUnit.IsFalse, WoWUnit.IsTrue +local Unfit = LibStub('Unfit-1.0') + +function Tests:Leather() + Replace(Unfit.unusable, 'Leather', true) + + IsFalse(Unfit:IsItemUnusable(2318)) -- light leather + IsTrue(Unfit:IsItemUnusable(6085)) -- leather chest +end \ No newline at end of file diff --git a/libs/Unfit-1.0/Unfit-1.0.lua b/libs/Unfit-1.0/Unfit-1.0.lua new file mode 100644 index 0000000..0f668a9 --- /dev/null +++ b/libs/Unfit-1.0/Unfit-1.0.lua @@ -0,0 +1,127 @@ +--[[ +Copyright 2011-2015 João Cardoso +Unfit is distributed under the terms of the GNU General Public License (Version 3). +As a special exception, the copyright holders of this library give you permission to embed it +with independent modules to produce an addon, regardless of the license terms of these +independent modules, and to copy and distribute the resulting software under terms of your +choice, provided that you also meet, for each embedded independent module, the terms and +conditions of the license of that module. Permission is not granted to modify this library. + +This library is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with the library. If not, see <http://www.gnu.org/licenses/gpl-3.0.txt>. + +This file is part of Unfit. +--]] + +local Lib = LibStub:NewLibrary('Unfit-1.0', 9) +if not Lib then + return +end + + +--[[ Data ]]-- + +do + local _, Class = UnitClass('player') + local Unusable + + if Class == 'DEATHKNIGHT' then + Unusable = { -- weapon, armor, dual-wield + {LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_STAFF,LE_ITEM_WEAPON_UNARMED, LE_ITEM_WEAPON_DAGGER, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW, LE_ITEM_WEAPON_WAND}, + {LE_ITEM_ARMOR_SHIELD} + } + elseif Class == 'DEMONHUNTER' then + Unusable = { + {LE_ITEM_WEAPON_AXE2H, LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_MACE1H, LE_ITEM_WEAPON_MACE2H, LE_ITEM_WEAPON_POLEARM, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_STAFF, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW, LE_ITEM_WEAPON_WAND}, + {LE_ITEM_ARMOR_MAIL, LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD} + } + elseif Class == 'DRUID' then + Unusable = { + {LE_ITEM_WEAPON_AXE1H, LE_ITEM_WEAPON_AXE2H, LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_SWORD1H, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW, LE_ITEM_WEAPON_WAND}, + {LE_ITEM_ARMOR_MAIL, LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD}, + true + } + elseif Class == 'HUNTER' then + Unusable = { + {LE_ITEM_WEAPON_MACE1H, LE_ITEM_WEAPON_MACE2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_WAND}, + {LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD} + } + elseif Class == 'MAGE' then + Unusable = { + {LE_ITEM_WEAPON_AXE1H, LE_ITEM_WEAPON_AXE2H, LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_MACE1H, LE_ITEM_WEAPON_MACE2H, LE_ITEM_WEAPON_POLEARM, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_UNARMED, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW}, + {LE_ITEM_ARMOR_LEATHER, LE_ITEM_ARMOR_MAIL, LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD}, + true + } + elseif Class == 'MONK' then + Unusable = { + {LE_ITEM_WEAPON_AXE2H, LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_MACE2H, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_DAGGER, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW, LE_ITEM_WEAPON_WAND}, + {LE_ITEM_ARMOR_MAIL, LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD} + } + elseif Class == 'PALADIN' then + Unusable = { + {LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_STAFF, LE_ITEM_WEAPON_UNARMED, LE_ITEM_WEAPON_DAGGER, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW, LE_ITEM_WEAPON_WAND}, + {}, + true + } + elseif Class == 'PRIEST' then + Unusable = { + {LE_ITEM_WEAPON_AXE1H, LE_ITEM_WEAPON_AXE2H, LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_MACE2H, LE_ITEM_WEAPON_POLEARM, LE_ITEM_WEAPON_SWORD1H, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_UNARMED, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW}, + {LE_ITEM_ARMOR_LEATHER, LE_ITEM_ARMOR_MAIL, LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD}, + true + } + elseif Class == 'ROGUE' then + Unusable = { + {LE_ITEM_WEAPON_AXE2H, LE_ITEM_WEAPON_MACE2H, LE_ITEM_WEAPON_POLEARM, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_STAFF, LE_ITEM_WEAPON_WAND}, + {LE_ITEM_ARMOR_MAIL, LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD} + } + elseif Class == 'SHAMAN' then + Unusable = { + {LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_POLEARM, LE_ITEM_WEAPON_SWORD1H, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW, LE_ITEM_WEAPON_WAND}, + {LE_ITEM_ARMOR_PLATEM} + } + elseif Class == 'WARLOCK' then + Unusable = { + {LE_ITEM_WEAPON_AXE1H, LE_ITEM_WEAPON_AXE2H, LE_ITEM_WEAPON_BOWS, LE_ITEM_WEAPON_GUNS, LE_ITEM_WEAPON_MACE1H, LE_ITEM_WEAPON_MACE2H, LE_ITEM_WEAPON_POLEARM, LE_ITEM_WEAPON_SWORD2H, LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_UNARMED, LE_ITEM_WEAPON_THROWN, LE_ITEM_WEAPON_CROSSBOW}, + {LE_ITEM_ARMOR_LEATHER, LE_ITEM_ARMOR_MAIL, LE_ITEM_ARMOR_PLATE, LE_ITEM_ARMOR_SHIELD}, + true + } + elseif Class == 'WARRIOR' then + Unusable = {{LE_ITEM_WEAPON_WARGLAIVE, LE_ITEM_WEAPON_WAND}, {}} + else + Unusable = {{}, {}} + end + + + Lib.unusable = {} + Lib.cannotDual = Unusable[3] + + for i, class in ipairs({LE_ITEM_CLASS_WEAPON, LE_ITEM_CLASS_ARMOR}) do + local list = {} + for _, subclass in ipairs(Unusable[i]) do + list[subclass] = true + end + + Lib.unusable[class] = list + end +end + + +--[[ API ]]-- + +function Lib:IsItemUnusable(...) + if ... then + local slot, _,_, class, subclass = select(9, GetItemInfo(...)) + return Lib:IsClassUnusable(class, subclass, slot) + end +end + +function Lib:IsClassUnusable(class, subclass, slot) + if class and subclass and Lib.unusable[class] then + return slot ~= '' and Lib.unusable[class][subclass] or slot == 'INVTYPE_WEAPONOFFHAND' and Lib.cannotDual + end +end diff --git a/libs/Unfit-1.0/Unfit-1.0.toc b/libs/Unfit-1.0/Unfit-1.0.toc new file mode 100644 index 0000000..997ec52 --- /dev/null +++ b/libs/Unfit-1.0/Unfit-1.0.toc @@ -0,0 +1,8 @@ +## Interface: 50400 +## Title: Unfit-1.0 +## Notes: Determines which items are usable or not for the player's class. +## Author: João Cardoso (Jaliborc) +## OptionalDeps: LibStub +## X-Category: Library + +Unfit-1.0.lua \ No newline at end of file