Compare commits

...

10 commits

Author SHA1 Message Date
Nicholas Ignoffo 7b67070c65 Minor refactoring 2018-09-29 16:49:47 -07:00
Nicholas Ignoffo 23ae02af78 Beginning of soul system 2018-09-29 16:49:05 -07:00
Nicholas Ignoffo 85733d44d3 Fix an AIOB with bonus value getter 2018-09-15 17:03:52 -07:00
Nicholas Ignoffo 47938e8688 Add upgrade incompatibility and negative status to upgrade definition 2018-09-15 17:03:24 -07:00
Nicholas Ignoffo dbeced4839 Update README 2018-09-14 21:47:52 -07:00
Nicholas Ignoffo c3bf39aa78 Re-license under LGPL 2.1
For code, we're rewriting everything so this is fine to do. As for assets, we were given permission to do with them as we wish.
2018-09-14 21:47:42 -07:00
Nicholas Ignoffo 0003cc7847 Finish implementing jump upgrade
"living armor is done guys it has a properly functioning upgrade now :LUL:"
2018-09-09 16:46:38 -07:00
Nicholas Ignoffo 59142c2a9c JSON-based living upgrade definitions
Since they're just data, it's okay for them to be data driven. Also makes
it easier for outside sources (ie: a wiki) to parse the data to keep it
up to date.
2018-09-06 20:20:49 -07:00
Nicholas Ignoffo 2ca458aaea :zoomeyes: 😓
Just something I was playing around with
2018-09-04 19:58:09 -07:00
Nicholas Ignoffo 26af9d5c6d Initial commit for 3.0
The altar mostly works. Sigils exist. Orbs exist. Living Armor framework exists. Probably some other things.
2018-09-04 19:54:09 -07:00
1784 changed files with 8169 additions and 90976 deletions

557
LICENSE
View file

@ -1,87 +1,502 @@
Creative Commons Attribution 4.0 International Public License
GNU LESSER GENERAL PUBLIC LICENSE
Version 2.1, February 1999
By exercising the Licensed Rights (defined below), You accept and agree to be bound by the terms and conditions of this Creative Commons Attribution 4.0 International Public License ("Public License"). To the extent this Public License may be interpreted as a contract, You are granted the Licensed Rights in consideration of Your acceptance of these terms and conditions, and the Licensor grants You such rights in consideration of benefits the Licensor receives from making the Licensed Material available under these terms and conditions.
Copyright (C) 1991, 1999 Free Software Foundation, Inc.
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Section 1 Definitions.
[This is the first released version of the Lesser GPL. It also counts
as the successor of the GNU Library Public License, version 2, hence
the version number 2.1.]
Adapted Material means material subject to Copyright and Similar Rights that is derived from or based upon the Licensed Material and in which the Licensed Material is translated, altered, arranged, transformed, or otherwise modified in a manner requiring permission under the Copyright and Similar Rights held by the Licensor. For purposes of this Public License, where the Licensed Material is a musical work, performance, or sound recording, Adapted Material is always produced where the Licensed Material is synched in timed relation with a moving image.
Adapter's License means the license You apply to Your Copyright and Similar Rights in Your contributions to Adapted Material in accordance with the terms and conditions of this Public License.
Copyright and Similar Rights means copyright and/or similar rights closely related to copyright including, without limitation, performance, broadcast, sound recording, and Sui Generis Database Rights, without regard to how the rights are labeled or categorized. For purposes of this Public License, the rights specified in Section 2(b)(1)-(2) are not Copyright and Similar Rights.
Effective Technological Measures means those measures that, in the absence of proper authority, may not be circumvented under laws fulfilling obligations under Article 11 of the WIPO Copyright Treaty adopted on December 20, 1996, and/or similar international agreements.
Exceptions and Limitations means fair use, fair dealing, and/or any other exception or limitation to Copyright and Similar Rights that applies to Your use of the Licensed Material.
Licensed Material means the artistic or literary work, database, or other material to which the Licensor applied this Public License.
Licensed Rights means the rights granted to You subject to the terms and conditions of this Public License, which are limited to all Copyright and Similar Rights that apply to Your use of the Licensed Material and that the Licensor has authority to license.
Licensor means the individual(s) or entity(ies) granting rights under this Public License.
Share means to provide material to the public by any means or process that requires permission under the Licensed Rights, such as reproduction, public display, public performance, distribution, dissemination, communication, or importation, and to make material available to the public including in ways that members of the public may access the material from a place and at a time individually chosen by them.
Sui Generis Database Rights means rights other than copyright resulting from Directive 96/9/EC of the European Parliament and of the Council of 11 March 1996 on the legal protection of databases, as amended and/or succeeded, as well as other essentially equivalent rights anywhere in the world.
You means the individual or entity exercising the Licensed Rights under this Public License. Your has a corresponding meaning.
Section 2 Scope.
Preamble
License grant.
Subject to the terms and conditions of this Public License, the Licensor hereby grants You a worldwide, royalty-free, non-sublicensable, non-exclusive, irrevocable license to exercise the Licensed Rights in the Licensed Material to:
reproduce and Share the Licensed Material, in whole or in part; and
produce, reproduce, and Share Adapted Material.
Exceptions and Limitations. For the avoidance of doubt, where Exceptions and Limitations apply to Your use, this Public License does not apply, and You do not need to comply with its terms and conditions.
Term. The term of this Public License is specified in Section 6(a).
Media and formats; technical modifications allowed. The Licensor authorizes You to exercise the Licensed Rights in all media and formats whether now known or hereafter created, and to make technical modifications necessary to do so. The Licensor waives and/or agrees not to assert any right or authority to forbid You from making technical modifications necessary to exercise the Licensed Rights, including technical modifications necessary to circumvent Effective Technological Measures. For purposes of this Public License, simply making modifications authorized by this Section 2(a)(4) never produces Adapted Material.
Downstream recipients.
Offer from the Licensor Licensed Material. Every recipient of the Licensed Material automatically receives an offer from the Licensor to exercise the Licensed Rights under the terms and conditions of this Public License.
No downstream restrictions. You may not offer or impose any additional or different terms or conditions on, or apply any Effective Technological Measures to, the Licensed Material if doing so restricts exercise of the Licensed Rights by any recipient of the Licensed Material.
No endorsement. Nothing in this Public License constitutes or may be construed as permission to assert or imply that You are, or that Your use of the Licensed Material is, connected with, or sponsored, endorsed, or granted official status by, the Licensor or others designated to receive attribution as provided in Section 3(a)(1)(A)(i).
Other rights.
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
Licenses are intended to guarantee your freedom to share and change
free software--to make sure the software is free for all its users.
Moral rights, such as the right of integrity, are not licensed under this Public License, nor are publicity, privacy, and/or other similar personality rights; however, to the extent possible, the Licensor waives and/or agrees not to assert any such rights held by the Licensor to the limited extent necessary to allow You to exercise the Licensed Rights, but not otherwise.
Patent and trademark rights are not licensed under this Public License.
To the extent possible, the Licensor waives any right to collect royalties from You for the exercise of the Licensed Rights, whether directly or through a collecting society under any voluntary or waivable statutory or compulsory licensing scheme. In all other cases the Licensor expressly reserves any right to collect such royalties.
Section 3 License Conditions.
This license, the Lesser General Public License, applies to some
specially designated software packages--typically libraries--of the
Free Software Foundation and other authors who decide to use it. You
can use it too, but we suggest you first think carefully about whether
this license or the ordinary General Public License is the better
strategy to use in any particular case, based on the explanations below.
Your exercise of the Licensed Rights is expressly made subject to the following conditions.
When we speak of free software, we are referring to freedom of use,
not price. Our General Public Licenses are designed to make sure that
you have the freedom to distribute copies of free software (and charge
for this service if you wish); that you receive source code or can get
it if you want it; that you can change the software and use pieces of
it in new free programs; and that you are informed that you can do
these things.
Attribution.
To protect your rights, we need to make restrictions that forbid
distributors to deny you these rights or to ask you to surrender these
rights. These restrictions translate to certain responsibilities for
you if you distribute copies of the library or if you modify it.
If You Share the Licensed Material (including in modified form), You must:
For example, if you distribute copies of the library, whether gratis
or for a fee, you must give the recipients all the rights that we gave
you. You must make sure that they, too, receive or can get the source
code. If you link other code with the library, you must provide
complete object files to the recipients, so that they can relink them
with the library after making changes to the library and recompiling
it. And you must show them these terms so they know their rights.
retain the following if it is supplied by the Licensor with the Licensed Material:
identification of the creator(s) of the Licensed Material and any others designated to receive attribution, in any reasonable manner requested by the Licensor (including by pseudonym if designated);
a copyright notice;
a notice that refers to this Public License;
a notice that refers to the disclaimer of warranties;
a URI or hyperlink to the Licensed Material to the extent reasonably practicable;
indicate if You modified the Licensed Material and retain an indication of any previous modifications; and
indicate the Licensed Material is licensed under this Public License, and include the text of, or the URI or hyperlink to, this Public License.
You may satisfy the conditions in Section 3(a)(1) in any reasonable manner based on the medium, means, and context in which You Share the Licensed Material. For example, it may be reasonable to satisfy the conditions by providing a URI or hyperlink to a resource that includes the required information.
If requested by the Licensor, You must remove any of the information required by Section 3(a)(1)(A) to the extent reasonably practicable.
If You Share Adapted Material You produce, the Adapter's License You apply must not prevent recipients of the Adapted Material from complying with this Public License.
Section 4 Sui Generis Database Rights.
We protect your rights with a two-step method: (1) we copyright the
library, and (2) we offer you this license, which gives you legal
permission to copy, distribute and/or modify the library.
Where the Licensed Rights include Sui Generis Database Rights that apply to Your use of the Licensed Material:
To protect each distributor, we want to make it very clear that
there is no warranty for the free library. Also, if the library is
modified by someone else and passed on, the recipients should know
that what they have is not the original version, so that the original
author's reputation will not be affected by problems that might be
introduced by others.
for the avoidance of doubt, Section 2(a)(1) grants You the right to extract, reuse, reproduce, and Share all or a substantial portion of the contents of the database;
if You include all or a substantial portion of the database contents in a database in which You have Sui Generis Database Rights, then the database in which You have Sui Generis Database Rights (but not its individual contents) is Adapted Material; and
You must comply with the conditions in Section 3(a) if You Share all or a substantial portion of the contents of the database.
For the avoidance of doubt, this Section 4 supplements and does not replace Your obligations under this Public License where the Licensed Rights include other Copyright and Similar Rights.
Section 5 Disclaimer of Warranties and Limitation of Liability.
Finally, software patents pose a constant threat to the existence of
any free program. We wish to make sure that a company cannot
effectively restrict the users of a free program by obtaining a
restrictive license from a patent holder. Therefore, we insist that
any patent license obtained for a version of the library must be
consistent with the full freedom of use specified in this license.
Unless otherwise separately undertaken by the Licensor, to the extent possible, the Licensor offers the Licensed Material as-is and as-available, and makes no representations or warranties of any kind concerning the Licensed Material, whether express, implied, statutory, or other. This includes, without limitation, warranties of title, merchantability, fitness for a particular purpose, non-infringement, absence of latent or other defects, accuracy, or the presence or absence of errors, whether or not known or discoverable. Where disclaimers of warranties are not allowed in full or in part, this disclaimer may not apply to You.
To the extent possible, in no event will the Licensor be liable to You on any legal theory (including, without limitation, negligence) or otherwise for any direct, special, indirect, incidental, consequential, punitive, exemplary, or other losses, costs, expenses, or damages arising out of this Public License or use of the Licensed Material, even if the Licensor has been advised of the possibility of such losses, costs, expenses, or damages. Where a limitation of liability is not allowed in full or in part, this limitation may not apply to You.
The disclaimer of warranties and limitation of liability provided above shall be interpreted in a manner that, to the extent possible, most closely approximates an absolute disclaimer and waiver of all liability.
Section 6 Term and Termination.
Most GNU software, including some libraries, is covered by the
ordinary GNU General Public License. This license, the GNU Lesser
General Public License, applies to certain designated libraries, and
is quite different from the ordinary General Public License. We use
this license for certain libraries in order to permit linking those
libraries into non-free programs.
This Public License applies for the term of the Copyright and Similar Rights licensed here. However, if You fail to comply with this Public License, then Your rights under this Public License terminate automatically.
Where Your right to use the Licensed Material has terminated under Section 6(a), it reinstates:
When a program is linked with a library, whether statically or using
a shared library, the combination of the two is legally speaking a
combined work, a derivative of the original library. The ordinary
General Public License therefore permits such linking only if the
entire combination fits its criteria of freedom. The Lesser General
Public License permits more lax criteria for linking other code with
the library.
automatically as of the date the violation is cured, provided it is cured within 30 days of Your discovery of the violation; or
upon express reinstatement by the Licensor.
For the avoidance of doubt, this Section 6(b) does not affect any right the Licensor may have to seek remedies for Your violations of this Public License.
For the avoidance of doubt, the Licensor may also offer the Licensed Material under separate terms or conditions or stop distributing the Licensed Material at any time; however, doing so will not terminate this Public License.
Sections 1, 5, 6, 7, and 8 survive termination of this Public License.
Section 7 Other Terms and Conditions.
We call this license the "Lesser" General Public License because it
does Less to protect the user's freedom than the ordinary General
Public License. It also provides other free software developers Less
of an advantage over competing non-free programs. These disadvantages
are the reason we use the ordinary General Public License for many
libraries. However, the Lesser license provides advantages in certain
special circumstances.
The Licensor shall not be bound by any additional or different terms or conditions communicated by You unless expressly agreed.
Any arrangements, understandings, or agreements regarding the Licensed Material not stated herein are separate from and independent of the terms and conditions of this Public License.
Section 8 Interpretation.
For example, on rare occasions, there may be a special need to
encourage the widest possible use of a certain library, so that it becomes
a de-facto standard. To achieve this, non-free programs must be
allowed to use the library. A more frequent case is that a free
library does the same job as widely used non-free libraries. In this
case, there is little to gain by limiting the free library to free
software only, so we use the Lesser General Public License.
For the avoidance of doubt, this Public License does not, and shall not be interpreted to, reduce, limit, restrict, or impose conditions on any use of the Licensed Material that could lawfully be made without permission under this Public License.
To the extent possible, if any provision of this Public License is deemed unenforceable, it shall be automatically reformed to the minimum extent necessary to make it enforceable. If the provision cannot be reformed, it shall be severed from this Public License without affecting the enforceability of the remaining terms and conditions.
No term or condition of this Public License will be waived and no failure to comply consented to unless expressly agreed to by the Licensor.
Nothing in this Public License constitutes or may be interpreted as a limitation upon, or waiver of, any privileges and immunities that apply to the Licensor or You, including from the legal processes of any jurisdiction or authority.
In other cases, permission to use a particular library in non-free
programs enables a greater number of people to use a large body of
free software. For example, permission to use the GNU C Library in
non-free programs enables many more people to use the whole GNU
operating system, as well as its variant, the GNU/Linux operating
system.
Although the Lesser General Public License is Less protective of the
users' freedom, it does ensure that the user of a program that is
linked with the Library has the freedom and the wherewithal to run
that program using a modified version of the Library.
The precise terms and conditions for copying, distribution and
modification follow. Pay close attention to the difference between a
"work based on the library" and a "work that uses the library". The
former contains code derived from the library, whereas the latter must
be combined with the library in order to run.
GNU LESSER GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License Agreement applies to any software library or other
program which contains a notice placed by the copyright holder or
other authorized party saying it may be distributed under the terms of
this Lesser General Public License (also called "this License").
Each licensee is addressed as "you".
A "library" means a collection of software functions and/or data
prepared so as to be conveniently linked with application programs
(which use some of those functions and data) to form executables.
The "Library", below, refers to any such software library or work
which has been distributed under these terms. A "work based on the
Library" means either the Library or any derivative work under
copyright law: that is to say, a work containing the Library or a
portion of it, either verbatim or with modifications and/or translated
straightforwardly into another language. (Hereinafter, translation is
included without limitation in the term "modification".)
"Source code" for a work means the preferred form of the work for
making modifications to it. For a library, complete source code means
all the source code for all modules it contains, plus any associated
interface definition files, plus the scripts used to control compilation
and installation of the library.
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running a program using the Library is not restricted, and output from
such a program is covered only if its contents constitute a work based
on the Library (independent of the use of the Library in a tool for
writing it). Whether that is true depends on what the Library does
and what the program that uses the Library does.
1. You may copy and distribute verbatim copies of the Library's
complete source code as you receive it, in any medium, provided that
you conspicuously and appropriately publish on each copy an
appropriate copyright notice and disclaimer of warranty; keep intact
all the notices that refer to this License and to the absence of any
warranty; and distribute a copy of this License along with the
Library.
You may charge a fee for the physical act of transferring a copy,
and you may at your option offer warranty protection in exchange for a
fee.
2. You may modify your copy or copies of the Library or any portion
of it, thus forming a work based on the Library, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) The modified work must itself be a software library.
b) You must cause the files modified to carry prominent notices
stating that you changed the files and the date of any change.
c) You must cause the whole of the work to be licensed at no
charge to all third parties under the terms of this License.
d) If a facility in the modified Library refers to a function or a
table of data to be supplied by an application program that uses
the facility, other than as an argument passed when the facility
is invoked, then you must make a good faith effort to ensure that,
in the event an application does not supply such function or
table, the facility still operates, and performs whatever part of
its purpose remains meaningful.
(For example, a function in a library to compute square roots has
a purpose that is entirely well-defined independent of the
application. Therefore, Subsection 2d requires that any
application-supplied function or table used by this function must
be optional: if the application does not supply it, the square
root function must still compute square roots.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Library,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Library, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote
it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Library.
In addition, mere aggregation of another work not based on the Library
with the Library (or with a work based on the Library) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may opt to apply the terms of the ordinary GNU General Public
License instead of this License to a given copy of the Library. To do
this, you must alter all the notices that refer to this License, so
that they refer to the ordinary GNU General Public License, version 2,
instead of to this License. (If a newer version than version 2 of the
ordinary GNU General Public License has appeared, then you can specify
that version instead if you wish.) Do not make any other change in
these notices.
Once this change is made in a given copy, it is irreversible for
that copy, so the ordinary GNU General Public License applies to all
subsequent copies and derivative works made from that copy.
This option is useful when you wish to copy part of the code of
the Library into a program that is not a library.
4. You may copy and distribute the Library (or a portion or
derivative of it, under Section 2) in object code or executable form
under the terms of Sections 1 and 2 above provided that you accompany
it with the complete corresponding machine-readable source code, which
must be distributed under the terms of Sections 1 and 2 above on a
medium customarily used for software interchange.
If distribution of object code is made by offering access to copy
from a designated place, then offering equivalent access to copy the
source code from the same place satisfies the requirement to
distribute the source code, even though third parties are not
compelled to copy the source along with the object code.
5. A program that contains no derivative of any portion of the
Library, but is designed to work with the Library by being compiled or
linked with it, is called a "work that uses the Library". Such a
work, in isolation, is not a derivative work of the Library, and
therefore falls outside the scope of this License.
However, linking a "work that uses the Library" with the Library
creates an executable that is a derivative of the Library (because it
contains portions of the Library), rather than a "work that uses the
library". The executable is therefore covered by this License.
Section 6 states terms for distribution of such executables.
When a "work that uses the Library" uses material from a header file
that is part of the Library, the object code for the work may be a
derivative work of the Library even though the source code is not.
Whether this is true is especially significant if the work can be
linked without the Library, or if the work is itself a library. The
threshold for this to be true is not precisely defined by law.
If such an object file uses only numerical parameters, data
structure layouts and accessors, and small macros and small inline
functions (ten lines or less in length), then the use of the object
file is unrestricted, regardless of whether it is legally a derivative
work. (Executables containing this object code plus portions of the
Library will still fall under Section 6.)
Otherwise, if the work is a derivative of the Library, you may
distribute the object code for the work under the terms of Section 6.
Any executables containing that work also fall under Section 6,
whether or not they are linked directly with the Library itself.
6. As an exception to the Sections above, you may also combine or
link a "work that uses the Library" with the Library to produce a
work containing portions of the Library, and distribute that work
under terms of your choice, provided that the terms permit
modification of the work for the customer's own use and reverse
engineering for debugging such modifications.
You must give prominent notice with each copy of the work that the
Library is used in it and that the Library and its use are covered by
this License. You must supply a copy of this License. If the work
during execution displays copyright notices, you must include the
copyright notice for the Library among them, as well as a reference
directing the user to the copy of this License. Also, you must do one
of these things:
a) Accompany the work with the complete corresponding
machine-readable source code for the Library including whatever
changes were used in the work (which must be distributed under
Sections 1 and 2 above); and, if the work is an executable linked
with the Library, with the complete machine-readable "work that
uses the Library", as object code and/or source code, so that the
user can modify the Library and then relink to produce a modified
executable containing the modified Library. (It is understood
that the user who changes the contents of definitions files in the
Library will not necessarily be able to recompile the application
to use the modified definitions.)
b) Use a suitable shared library mechanism for linking with the
Library. A suitable mechanism is one that (1) uses at run time a
copy of the library already present on the user's computer system,
rather than copying library functions into the executable, and (2)
will operate properly with a modified version of the library, if
the user installs one, as long as the modified version is
interface-compatible with the version that the work was made with.
c) Accompany the work with a written offer, valid for at
least three years, to give the same user the materials
specified in Subsection 6a, above, for a charge no more
than the cost of performing this distribution.
d) If distribution of the work is made by offering access to copy
from a designated place, offer equivalent access to copy the above
specified materials from the same place.
e) Verify that the user has already received a copy of these
materials or that you have already sent this user a copy.
For an executable, the required form of the "work that uses the
Library" must include any data and utility programs needed for
reproducing the executable from it. However, as a special exception,
the materials to be distributed need not include anything that is
normally distributed (in either source or binary form) with the major
components (compiler, kernel, and so on) of the operating system on
which the executable runs, unless that component itself accompanies
the executable.
It may happen that this requirement contradicts the license
restrictions of other proprietary libraries that do not normally
accompany the operating system. Such a contradiction means you cannot
use both them and the Library together in an executable that you
distribute.
7. You may place library facilities that are a work based on the
Library side-by-side in a single library together with other library
facilities not covered by this License, and distribute such a combined
library, provided that the separate distribution of the work based on
the Library and of the other library facilities is otherwise
permitted, and provided that you do these two things:
a) Accompany the combined library with a copy of the same work
based on the Library, uncombined with any other library
facilities. This must be distributed under the terms of the
Sections above.
b) Give prominent notice with the combined library of the fact
that part of it is a work based on the Library, and explaining
where to find the accompanying uncombined form of the same work.
8. You may not copy, modify, sublicense, link with, or distribute
the Library except as expressly provided under this License. Any
attempt otherwise to copy, modify, sublicense, link with, or
distribute the Library is void, and will automatically terminate your
rights under this License. However, parties who have received copies,
or rights, from you under this License will not have their licenses
terminated so long as such parties remain in full compliance.
9. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Library or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Library (or any work based on the
Library), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Library or works based on it.
10. Each time you redistribute the Library (or any work based on the
Library), the recipient automatically receives a license from the
original licensor to copy, distribute, link with or modify the Library
subject to these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties with
this License.
11. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Library at all. For example, if a patent
license would not permit royalty-free redistribution of the Library by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Library.
If any portion of this section is held invalid or unenforceable under any
particular circumstance, the balance of the section is intended to apply,
and the section as a whole is intended to apply in other circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
12. If the distribution and/or use of the Library is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Library under this License may add
an explicit geographical distribution limitation excluding those countries,
so that distribution is permitted only in or among countries not thus
excluded. In such case, this License incorporates the limitation as if
written in the body of this License.
13. The Free Software Foundation may publish revised and/or new
versions of the Lesser General Public License from time to time.
Such new versions will be similar in spirit to the present version,
but may differ in detail to address new problems or concerns.
Each version is given a distinguishing version number. If the Library
specifies a version number of this License which applies to it and
"any later version", you have the option of following the terms and
conditions either of that version or of any later version published by
the Free Software Foundation. If the Library does not specify a
license version number, you may choose any version ever published by
the Free Software Foundation.
14. If you wish to incorporate parts of the Library into other free
programs whose distribution conditions are incompatible with these,
write to the author to ask for permission. For software which is
copyrighted by the Free Software Foundation, write to the Free
Software Foundation; we sometimes make exceptions for this. Our
decision will be guided by the two goals of preserving the free status
of all derivatives of our free software and of promoting the sharing
and reuse of software generally.
NO WARRANTY
15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO
WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY
KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE
LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME
THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN
WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY
AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU
FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR
CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
DAMAGES.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Libraries
If you develop a new library, and you want it to be of the greatest
possible use to the public, we recommend making it free software that
everyone can redistribute and change. You can do so by permitting
redistribution under these terms (or, alternatively, under the terms of the
ordinary General Public License).
To apply these terms, attach the following notices to the library. It is
safest to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least the
"copyright" line and a pointer to where the full notice is found.
<one line to give the library's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
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
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Also add information on how to contact you by electronic and paper mail.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the library, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the
library `Frob' (a library for tweaking knobs) written by James Random Hacker.
<signature of Ty Coon>, 1 April 1990
Ty Coon, President of Vice
That's all there is to it!

121
README.md
View file

@ -1,120 +1,65 @@
# Blood Magic: Alchemical Wizardry [![](http://cf.way2muchnoise.eu/full_blood-magic_downloads.svg)](https://minecraft.curseforge.com/projects/blood-magic) [![Discord](https://img.shields.io/discord/259683256348311552.svg?colorB=7289DA&logo=data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAHYAAABWAgMAAABnZYq0AAAACVBMVEUAAB38%2FPz%2F%2F%2F%2Bm8P%2F9AAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAsTAQCanBgAAAAHdElNRQfhBxwQJhxy2iqrAAABoElEQVRIx7WWzdGEIAyGgcMeKMESrMJ6rILZCiiBg4eYKr%2Fd1ZAfgXFm98sJfAyGNwno3G9sLucgYGpQ4OGVRxQTREMDZjF7ILSWjoiHo1n%2BE03Aw8p7CNY5IhkYd%2F%2F6MtO3f8BNhR1QWnarCH4tr6myl0cWgUVNcfMcXACP1hKrGMt8wcAyxide7Ymcgqale7hN6846uJCkQxw6GG7h2MH4Czz3cLqD1zHu0VOXMfZjHLoYvsdd0Q7ZvsOkafJ1P4QXxrWFd14wMc60h8JKCbyQvImzlFjyGoZTKzohwWR2UzSONHhYXBQOaKKsySsahwGGDnb%2FiYPJw22sCqzirSULYy1qtHhXGbtgrM0oagBV4XiTJok3GoLoDNH8ooTmBm7ZMsbpFzi2bgPGoXWXME6XT%2BRJ4GLddxJ4PpQy7tmfoU2HPN6cKg%2BledKHBKlF8oNSt5w5g5o8eXhu1IOlpl5kGerDxIVT%2BztzKepulD8utXqpChamkzzuo7xYGk%2FkpSYuviLXun5bzdRf0Krejzqyz7Z3p0I1v2d6HmA07dofmS48njAiuMgAAAAASUVORK5CYII%3D)](https://discord.gg/VtNrGrs)
# Blood Magic: Alchemical Wizardry [![](https://cf.way2muchnoise.eu/full_blood-magic_downloads.svg)](https://minecraft.curseforge.com/projects/blood-magic) [![Discord](https://img.shields.io/discord/259683256348311552.svg?colorB=7289DA&logo=data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAHYAAABWAgMAAABnZYq0AAAACVBMVEUAAB38%2FPz%2F%2F%2F%2Bm8P%2F9AAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAsTAQCanBgAAAAHdElNRQfhBxwQJhxy2iqrAAABoElEQVRIx7WWzdGEIAyGgcMeKMESrMJ6rILZCiiBg4eYKr%2Fd1ZAfgXFm98sJfAyGNwno3G9sLucgYGpQ4OGVRxQTREMDZjF7ILSWjoiHo1n%2BE03Aw8p7CNY5IhkYd%2F%2F6MtO3f8BNhR1QWnarCH4tr6myl0cWgUVNcfMcXACP1hKrGMt8wcAyxide7Ymcgqale7hN6846uJCkQxw6GG7h2MH4Czz3cLqD1zHu0VOXMfZjHLoYvsdd0Q7ZvsOkafJ1P4QXxrWFd14wMc60h8JKCbyQvImzlFjyGoZTKzohwWR2UzSONHhYXBQOaKKsySsahwGGDnb%2FiYPJw22sCqzirSULYy1qtHhXGbtgrM0oagBV4XiTJok3GoLoDNH8ooTmBm7ZMsbpFzi2bgPGoXWXME6XT%2BRJ4GLddxJ4PpQy7tmfoU2HPN6cKg%2BledKHBKlF8oNSt5w5g5o8eXhu1IOlpl5kGerDxIVT%2BztzKepulD8utXqpChamkzzuo7xYGk%2FkpSYuviLXun5bzdRf0Krejzqyz7Z3p0I1v2d6HmA07dofmS48njAiuMgAAAAASUVORK5CYII%3D)](https://discord.gg/VtNrGrs)
### Gruesome? Probably. Worth it? Definitely!
### [Downloads](http://minecraft.curseforge.com/projects/blood-magic/files)
## Information
Gruesome? Probably. Worth it? Definitely!
Have you ever picked up a magic mod for Minecraft, and thought that it was too tame? Was there not enough danger involved when creating your next high-tech gadget? Bored with all of those peaceful animals just staring at you without a care in the world? Well then, I am glad you came here!
Blood Magic is an arcane art that is practiced by mages who attempt to gather a vast amount of power through utilizing a forbidden material: blood. Even though it does grant a huge amount of power, every single action that is performed with this volatile magic can prove deadly. You have been warned.
## Links
* [Minecraft Forum Thread](https://www.minecraftforum.net/forums/mapping-and-modding/minecraft-mods/1290532-bm)
### WayofTime:
* Twitter: [@WayofTime](https://twitter.com/WayofTime)
* Wiki: Found at [FTBWiki](http://ftbwiki.org/Blood_Magic)
* [Minecraft Forum Thread](http://www.minecraftforum.net/forums/mapping-and-modding/minecraft-mods/1290532-bm)
* [Curseforge](http://minecraft.curseforge.com/projects/blood-magic)
* [Donate](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=J7SNY7L82PQ82)
* [Patreon](https://www.patreon.com/BloodMagic)
## Development Setup
### TehNut
1. Fork this project to your own Github repository and clone it to your desktop.
2. Navigate to the directory you cloned to. Follow the [Forge Documentation](http://mcforge.readthedocs.io/en/latest/gettingstarted/#from-zero-to-modding) (start at step 4) to setup your workspace. If you use IDEA, follow [this set](http://mcforge.readthedocs.io/en/latest/gettingstarted/#terminal-free-intellij-idea-configuration) of steps.
* Twitter: [@OfficialTehNut](https://twitter.com/OfficialTehNut)
* [Website](https://tehnut.info)
#### IntelliJ IDEA extra steps
## Building
1. Navigate to `File > Settings > Plugins > Browse repositories...`. Search for Lombok and install the plugin.
2. Navigate to `File > Settings > Build, Execution, Deployment > Compiler > Annotation Processors`. Check `Enable annotation processing`.
[Setup video](https://www.youtube.com/watch?v=8VEdtQLuLO0&feature=youtu.be) by LexManos. For more information, refer to the [Forge Forums](http://www.minecraftforge.net/forum/index.php/topic,14048.0.html).
## Developing Addons
Add to your build.gradle:
repositories {
maven {
url "http://tehnut.info/maven/"
}
}
dependencies {
deobfCompile "com.wayoftime.bloodmagic:BloodMagic:<BLOODMAGIC-VERSION>"
}
`<BLOODMAGIC-VERSION>` can be found on CurseForge (or via the Maven itself), check the file name of the version you want.
## Custom Builds
**Custom builds are *unsupported*. If you have an issue while using an unofficial build, it is not guaranteed that you will get support.**
#### How to make a custom build:
1. Clone directly from this repository to your desktop.
2. Navigate to the directory you cloned to. Open a command window there and run `gradlew build`
3. Once it completes, your new build will be found at `../build/libs/BloodMagic-*.jar`. You can ignore the `deobf`, `sources`, and `javadoc` jars.
1. Clone this repository to your local file system.
2. Open a terminal in the directory you cloned to.
3. Run `gradlew build` (or `./gradlew build` if that doesn't work).
4. Navigate to `./build/libs`, you will find the compiled jars there.
## License
![CCA4.0](https://licensebuttons.net/l/by/4.0/88x31.png)
Blood Magic: AlchemicalWizardry by WayofTime is licensed under a [Creative Commons Attribution 4.0 International License](http://creativecommons.org/licenses/by/4.0/).
Blood Magic: AlchemicalWizardry by WayofTime is licensed under the [GNU Lesser General Public License 2.1](https://tldrlegal.com/license/gnu-lesser-general-public-license-v2.1-(lgpl-2.1)).
## Installation Instructions
This mod requires "Minecraft Forge" in order to operate. It is incredibly easy to download and set up, so might as well get to it!
1. Download [Forge](http://files.minecraftforge.net/). Usually "Recommended" is best - you want the "universal", not the source. Forge also has an "install" option now, so all you need to do is launch that program and it will make a lovely Forge profile. If you haven't, look up how to use the installer and the new 1.6.x launcher if you are confused!
1. Download [Forge](https://files.minecraftforge.net/). Usually "Recommended" is best - you want the "universal", not the source. Forge also has an "install" option now, so all you need to do is launch that program and it will make a lovely Forge profile. If you haven't, look up how to use the installer and the new 1.6.x launcher if you are confused!
2. Download the latest version of BloodMagic from [Curseforge](http://minecraft.curseforge.com/mc-mods/224791-blood-magic).
2. Download the latest version of BloodMagic from [Curseforge](https://minecraft.curseforge.com/projects/blood-magic).
3. Place the mod in the **mods** folder of your .minecraft. If you are unsure of where that is located, it is here: `../Users/you/AppData/roaming/.minecraft`.
## FAQ
## Development Setup
**Q**: My weak blood orb doesn't show my current LP! Fix it please.
First, clone this repository to your local file system, then follow the steps outlined on the [Minecraft Forge documentation site](https://mcforge.readthedocs.io/en/latest/gettingstarted/#from-zero-to-modding).
**A**: The mechanic for viewing the player's essence has changed due to some issues with mechanics. You now need a Divination Sigil to view a player's essence. It does other things, too, so it is worth it!
## Adding Compatibility
**Q**: Why am I dying so much?
Add to your build.gradle:
**A**: It might be a good idea to make sure that you have enough essence to do a task. If you don't have enough essence for, say, an imperfect ritual, it will take it out of your health. If your health reaches 0... Well, you don't have to be a genius to see what would happen.
```groovy
repositories {
maven { url "https://tehnut.info/maven/" }
}
```
**Q**: Waffles?
```groovy
dependencies {
deobfCompile "com.wayoftime.bloodmagic:BloodMagic:${BLOODMAGIC_VERSION}:api"
}
```
**A**: Waffles!
**Q**: Where is x? When I watched spotlight "w," it had an item called x. Don't you need x to make y, before you can create z?
**A**: It might be wise to look at an updated spotlight, or check the changelogs. I'm not evil, so I do document everything that I can. There was most likely some issues with balance with the item, so it may have been removed for those reasons. Or you just grabbed the item from NEI without seeing it was a test item, in which case: shame on you!
**Q**: Isn't that armour ...
**A**: Yes, the armour texture is from the mod EE2. Pahimar and I are good friends, and I decided to use it for the armour and tools. He has given me his express permission for it, so need not worry!
[Proof](https://twitter.com/Pahimar/status/453590600689139712).
**Q**: My game is crashing with the latest TC4!
**A**: To help stop this, remove the TC4 API from my Blood Magic zip file (if it is there). It should solve things.
**Q**: But, my Thaumcraft aspects are messed up!
**A**: Once again, remove the TC4 API from the Blood Magic zip file to solve this. Azanor changed some aspect combinations.
**Q**: When will 1.7.2 be released?
**A**: It's out! Go get it!
**Q**: Way, I've just had an amazing idea! Why not add an in-game book just like the Thaumonomicon?
**A**: This has been suggested several times. It I being worked on, and is proceeding quite well. Some framework needs to be completed, but it isn't a priority - ALL of the information you need is on this post, or online.
**Q**: Why do I not have a Sacrificial Orb? It's only showing up as a knife!
**A**: This is a config option. The person you saw with an orb had a config that changed the knife to an orb. The orb and knife function exactly the same way, but you can change it in the configs by looking for the "Idontlikefun" option.
**Q**: When I respawn, I appear to only come back with 3 hearts. What's happening?
**A**: This is due to another config option in the "WhimpySettings," which is due to my attempt to combat Zerg Rushing. You can disable this if you really want to, but it shouldn't hurt unduly.
`${BLOODMAGIC_VERSION}` can be found on CurseForge (or via the Maven itself), check the file name of the version you want. If making a full addon, remove the `:api` modifier to get the full project.

View file

@ -15,13 +15,18 @@ plugins {
id 'maven-publish'
}
def build_number = 'CUSTOM'
if (System.getenv('BUILD_NUMBER') != null)
build_number = System.getenv('BUILD_NUMBER')
sourceSets {
compat {
compileClasspath += sourceSets.main.runtimeClasspath + sourceSets.main.output
}
def username = "${mod_name}"
if (project.hasProperty('dev_username'))
username = "${dev_username}"
main {
runtimeClasspath += sourceSets.compat.runtimeClasspath
}
}
def build_number = System.getenv('BUILD_NUMBER') != null ? System.getenv('BUILD_NUMBER') : 'CUSTOM'
def username = project.hasProperty('dev_username') ? "${dev_username}" : "${mod_name}"
group = package_group
archivesBaseName = mod_name
@ -33,16 +38,17 @@ repositories {
}
dependencies {
deobfCompile "mezz.jei:jei_${mc_version}:${jei_version}"
deobfCompile "mcp.mobius.waila:Hwyla:${waila_version}"
deobfCompile "info.amerifrance.guideapi:Guide-API:${guideapi_version}"
deobfCompile "mcp.mobius.waila:Hwyla:${hwyla_version}:api"
runtime "mcp.mobius.waila:Hwyla:${hwyla_version}"
deobfCompile "mezz.jei:jei_${mc_version}:${jei_version}:api"
runtime "mezz.jei:jei_${mc_version}:${jei_version}"
}
minecraft {
version = "${mc_version}-${forge_version}"
runDir = "run"
replace "@VERSION@", project.version
replace '${VERSION}', project.version
replaceIn "BloodMagic.java"
clientRunArgs += "--username=${username}"
@ -68,16 +74,11 @@ processResources {
}
}
allprojects {
tasks.withType(Javadoc) {
options.addStringOption('Xdoclint:none', '-quiet')
}
}
jar {
classifier = ''
from sourceSets.main.output
from sourceSets.api.output
from sourceSets.compat.output
manifest.mainAttributes(
"Built-By": System.getProperty('user.name'),
"Created-By": "${System.getProperty('java.vm.version')} + (${System.getProperty('java.vm.vendor')})",
@ -97,18 +98,14 @@ task apiJar(type: Jar) {
from sourceSets.api.allJava
}
task javadocJar(type: Jar, dependsOn: javadoc) {
from javadoc.destinationDir
classifier = 'javadoc'
}
task sourcesJar(type: Jar) {
classifier = 'sources'
from sourceSets.main.allJava
from sourceSets.api.allJava
from sourceSets.compat.allJava
}
tasks.build.dependsOn javadoc, javadocJar, apiJar, sourcesJar
tasks.build.dependsOn apiJar, sourcesJar
tasks.withType(JavaCompile) { task ->
task.options.encoding = 'UTF-8'
@ -119,7 +116,6 @@ publishing {
publications {
mavenJava(MavenPublication) {
artifact jar
artifact javadocJar
artifact sourcesJar
artifact apiJar
}
@ -175,7 +171,6 @@ curseforge {
relations curseRelations
addArtifact javadocJar
addArtifact sourcesJar
addArtifact apiJar
}

View file

@ -1,12 +1,13 @@
mod_name=BloodMagic
package_group=com.wayoftime.bloodmagic
mod_version=2.3.1
mod_version=3.0.0
mc_version=1.12.2
forge_version=14.23.2.2611
curse_id=224791
forge_version=14.23.4.2759
mappings_version=stable_39
mappings_version=snapshot_20180201
jei_version=4.11.0.206
hwyla_version=1.8.26-B41_1.12.2
guideapi_version=1.12-2.1.4-57
jei_version=4.8.5.147
waila_version=1.8.23-B38_1.12
guideapi_version=1.12-2.1.4-57
curse_id=224791

View file

@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-4.6-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-4.9-bin.zip

View file

@ -1,4 +1,4 @@
package WayofTime.bloodmagic.api;
package com.wayoftime.bloodmagic.api;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
@ -16,9 +16,9 @@ public @interface BloodMagicPlugin {
/**
* This annotation will inject the active {@link IBloodMagicAPI} into a {@code static} field of the same
* type. Fields with invalid types will be ignored and an error will be logged.
*
* <p>
* These fields are populated during {@link net.minecraftforge.fml.common.event.FMLPreInitializationEvent}.
*
* <p>
* {@code public static @BloodMagicPlugin.Inject IBloodMagicAPI API_INSTANCE = null;}
*/
@Retention(RetentionPolicy.RUNTIME)

View file

@ -1,4 +1,4 @@
package WayofTime.bloodmagic.api;
package com.wayoftime.bloodmagic.api;
import net.minecraft.block.state.IBlockState;
@ -6,9 +6,9 @@ import javax.annotation.Nonnull;
/**
* The main interface between a plugin and Blood Magic's internals.
*
* <p>
* This API is intended for <i>compatibility</i> between other mods and Blood Magic. More advanced integration is out of the scope of this API and are considered "addons".
*
* <p>
* To get an instance of this without actually creating an {@link IBloodMagicPlugin}, use {@link BloodMagicPlugin.Inject}.
*/
public interface IBloodMagicAPI {

View file

@ -1,4 +1,4 @@
package WayofTime.bloodmagic.api;
package com.wayoftime.bloodmagic.api;
import net.minecraft.block.state.IBlockState;
import net.minecraft.util.ResourceLocation;

View file

@ -1,4 +1,4 @@
package WayofTime.bloodmagic.api;
package com.wayoftime.bloodmagic.api;
/**
* The main class to implement to create a Blood Magic plugin. Everything communicated between a mod and Blood Magic is through this class.

View file

@ -1,4 +1,4 @@
package WayofTime.bloodmagic.api;
package com.wayoftime.bloodmagic.api;
import net.minecraft.item.ItemStack;
import net.minecraft.item.crafting.Ingredient;
@ -11,8 +11,7 @@ import javax.annotation.Nullable;
/**
* Allows recipe addition and removal.
*/
public interface IBloodMagicRecipeRegistrar
{
public interface IBloodMagicRecipeRegistrar {
/**
* Adds a new recipe to the Blood Altar.
@ -55,7 +54,7 @@ public interface IBloodMagicRecipeRegistrar
/**
* Adds a new recipe to the Soul/Tartaric Forge.
*
*
* @param output An output {@link ItemStack}.
* @param minimumSouls The minimum number of souls that must be contained in the Soul Gem.
* @param soulDrain The number of souls to drain from the Soul Gem.
@ -66,8 +65,8 @@ public interface IBloodMagicRecipeRegistrar
/**
* Removes a Soul/Tartaric Forge recipe based on an input {@link ItemStack} array.
*
* @param input The input items to remove the recipe of.
* @return Whether or not a recipe was removed.
* @param input The input items to remove the recipe of.
* @return Whether or not a recipe was removed.
*/
boolean removeTartaricForge(@Nonnull ItemStack... input);

View file

@ -1,4 +1,4 @@
package WayofTime.bloodmagic.api;
package com.wayoftime.bloodmagic.api;
import net.minecraft.block.state.IBlockState;
import net.minecraft.util.ResourceLocation;

View file

@ -1,4 +1,4 @@
package WayofTime.bloodmagic.api.event;
package com.wayoftime.bloodmagic.api.event;
import net.minecraft.item.ItemStack;
import net.minecraftforge.fml.common.eventhandler.Event;
@ -34,19 +34,19 @@ public class BloodMagicCraftedEvent extends Event {
/**
* Fired whenever a craft is completed in a Blood Altar.
*
* <p>
* It is not cancelable, however you can modify the output stack.
*/
public static class Altar extends BloodMagicCraftedEvent {
public Altar(ItemStack output, ItemStack input) {
super(output, new ItemStack[] { input }, true);
super(output, new ItemStack[]{input}, true);
}
}
/**
* Fired whenever a craft is completed in a Soul Forge.
*
* <p>
* It is not cancelable, however you can modify the output stack.
*/
public static class SoulForge extends BloodMagicCraftedEvent {
@ -58,7 +58,7 @@ public class BloodMagicCraftedEvent extends Event {
/**
* Fired whenever a craft is completed in an Alchemy Table.
*
* <p>
* It is not cancelable, however you can modify the output stack.
*/
public static class AlchemyTable extends BloodMagicCraftedEvent {

View file

@ -1,4 +1,4 @@
@API(owner = "bloodmagic", provides = "bloodmagic-api", apiVersion = "2.0.0")
package WayofTime.bloodmagic.api;
package com.wayoftime.bloodmagic.api;
import net.minecraftforge.fml.common.API;

View file

@ -0,0 +1,35 @@
package com.wayoftime.bloodmagic.compat.jei;
import com.wayoftime.bloodmagic.api.impl.BloodMagicAPI;
import com.wayoftime.bloodmagic.api.impl.recipe.RecipeBloodAltar;
import com.wayoftime.bloodmagic.compat.jei.altar.RecipeCategoryAltar;
import com.wayoftime.bloodmagic.compat.jei.altar.RecipeWrapperAltar;
import com.wayoftime.bloodmagic.core.RegistrarBloodMagicBlocks;
import mezz.jei.api.IJeiHelpers;
import mezz.jei.api.IModPlugin;
import mezz.jei.api.IModRegistry;
import mezz.jei.api.JEIPlugin;
import mezz.jei.api.recipe.IRecipeCategoryRegistration;
import net.minecraft.item.ItemStack;
@JEIPlugin
public class BloodMagicJEIPlugin implements IModPlugin {
public static IJeiHelpers helper;
@Override
public void registerCategories(IRecipeCategoryRegistration registry) {
helper = registry.getJeiHelpers();
registry.addRecipeCategories(
new RecipeCategoryAltar()
);
}
@Override
public void register(IModRegistry registry) {
registry.addRecipes(BloodMagicAPI.INSTANCE.getRecipeRegistrar().getAltarRecipes(), RecipeCategoryAltar.CATEGORY_ID);
registry.handleRecipes(RecipeBloodAltar.class, RecipeWrapperAltar::new, RecipeCategoryAltar.CATEGORY_ID);
registry.addRecipeCatalyst(new ItemStack(RegistrarBloodMagicBlocks.BLOOD_ALTAR), RecipeCategoryAltar.CATEGORY_ID);
}
}

View file

@ -1,37 +1,37 @@
package WayofTime.bloodmagic.compat.jei.altar;
package com.wayoftime.bloodmagic.compat.jei.altar;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.util.Constants;
import WayofTime.bloodmagic.compat.jei.BloodMagicJEIPlugin;
import WayofTime.bloodmagic.util.helper.TextHelper;
import com.wayoftime.bloodmagic.BloodMagic;
import com.wayoftime.bloodmagic.compat.jei.BloodMagicJEIPlugin;
import mezz.jei.api.gui.IDrawable;
import mezz.jei.api.gui.IRecipeLayout;
import mezz.jei.api.ingredients.IIngredients;
import mezz.jei.api.recipe.IRecipeCategory;
import net.minecraft.client.Minecraft;
import net.minecraft.client.resources.I18n;
import net.minecraft.item.ItemStack;
import net.minecraft.util.ResourceLocation;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
public class AltarRecipeCategory implements IRecipeCategory<AltarRecipeJEI> {
public class RecipeCategoryAltar implements IRecipeCategory<RecipeWrapperAltar> {
public static final String CATEGORY_ID = "bloodmagic:blood_altar";
private static final int INPUT_SLOT = 0;
private static final int OUTPUT_SLOT = 1;
@Nonnull
private final IDrawable background = BloodMagicJEIPlugin.jeiHelper.getGuiHelper().createDrawable(new ResourceLocation(Constants.Mod.DOMAIN + "gui/jei/altar.png"), 3, 4, 155, 65);
private final IDrawable background = BloodMagicJEIPlugin.helper.getGuiHelper().createDrawable(new ResourceLocation(BloodMagic.MODID, "textures/gui/jei/blood_altar.png"), 3, 4, 155, 65);
@Nonnull
@Override
public String getUid() {
return Constants.Compat.JEI_CATEGORY_ALTAR;
return CATEGORY_ID;
}
@Nonnull
@Override
public String getTitle() {
return TextHelper.localize("jei.bloodmagic.recipe.altar");
return I18n.format("jei.bloodmagic:blood_altar");
}
@Nonnull
@ -40,11 +40,6 @@ public class AltarRecipeCategory implements IRecipeCategory<AltarRecipeJEI> {
return background;
}
@Override
public void drawExtras(Minecraft minecraft) {
}
@Nullable
@Override
public IDrawable getIcon() {
@ -52,7 +47,7 @@ public class AltarRecipeCategory implements IRecipeCategory<AltarRecipeJEI> {
}
@Override
public void setRecipe(@Nonnull IRecipeLayout recipeLayout, @Nonnull AltarRecipeJEI recipeWrapper, @Nonnull IIngredients ingredients) {
public void setRecipe(@Nonnull IRecipeLayout recipeLayout, @Nonnull RecipeWrapperAltar recipeWrapper, @Nonnull IIngredients ingredients) {
recipeLayout.getItemStacks().init(INPUT_SLOT, true, 31, 0);
recipeLayout.getItemStacks().init(OUTPUT_SLOT, false, 125, 30);
@ -65,4 +60,4 @@ public class AltarRecipeCategory implements IRecipeCategory<AltarRecipeJEI> {
public String getModName() {
return BloodMagic.NAME;
}
}
}

View file

@ -0,0 +1,49 @@
package com.wayoftime.bloodmagic.compat.jei.altar;
import com.google.common.collect.Lists;
import com.wayoftime.bloodmagic.api.impl.recipe.RecipeBloodAltar;
import mezz.jei.api.ingredients.IIngredients;
import mezz.jei.api.recipe.IRecipeWrapper;
import net.minecraft.client.Minecraft;
import net.minecraft.client.resources.I18n;
import net.minecraft.item.ItemStack;
import net.minecraft.util.NonNullList;
import javax.annotation.Nonnull;
import java.awt.Color;
import java.util.List;
public class RecipeWrapperAltar implements IRecipeWrapper {
private final RecipeBloodAltar recipe;
public RecipeWrapperAltar(RecipeBloodAltar recipe) {
this.recipe = recipe;
}
@Override
public void getIngredients(@Nonnull IIngredients ingredients) {
ingredients.setInputs(ItemStack.class, NonNullList.from(ItemStack.EMPTY, recipe.getInput().getMatchingStacks()));
ingredients.setOutput(ItemStack.class, recipe.getOutput());
}
@Nonnull
@Override
public List<String> getTooltipStrings(int mouseX, int mouseY) {
List<String> tooltip = Lists.newArrayList();
if (mouseX >= 13 && mouseX <= 64 && mouseY >= 27 && mouseY <= 58) {
tooltip.add(I18n.format("jei.bloodmagic:consumption_rate", recipe.getConsumeRate()));
tooltip.add(I18n.format("jei.bloodmagic:drain_rate", recipe.getDrainRate()));
}
return tooltip;
}
@Override
public void drawInfo(@Nonnull Minecraft minecraft, int recipeWidth, int recipeHeight, int mouseX, int mouseY) {
String line1 = I18n.format("jei.bloodmagic:required_tier", I18n.format("enchantment.level." + (recipe.getMinimumTier().ordinal() + 1)));
minecraft.fontRenderer.drawString(line1, 90 - minecraft.fontRenderer.getStringWidth(line1) / 2, 0, Color.GRAY.getRGB());
String line2 = I18n.format("jei.bloodmagic:required_lp", recipe.getSyphon());
minecraft.fontRenderer.drawString(line2, 90 - minecraft.fontRenderer.getStringWidth(line2) / 2, 10, Color.GRAY.getRGB());
}
}

View file

@ -0,0 +1,15 @@
package com.wayoftime.bloodmagic.compat.waila;
import com.wayoftime.bloodmagic.tile.TileBloodAltar;
import mcp.mobius.waila.api.IWailaPlugin;
import mcp.mobius.waila.api.IWailaRegistrar;
import mcp.mobius.waila.api.WailaPlugin;
@WailaPlugin
public class BloodMagicHwylaPlugin implements IWailaPlugin {
@Override
public void register(IWailaRegistrar registrar) {
registrar.registerBodyProvider(DataProviderBloodAltar.INSTANCE, TileBloodAltar.class);
registrar.registerNBTProvider(DataProviderBloodAltar.INSTANCE, TileBloodAltar.class);
}
}

View file

@ -0,0 +1,40 @@
package com.wayoftime.bloodmagic.compat.waila;
import com.wayoftime.bloodmagic.tile.TileBloodAltar;
import mcp.mobius.waila.api.IWailaConfigHandler;
import mcp.mobius.waila.api.IWailaDataAccessor;
import mcp.mobius.waila.api.IWailaDataProvider;
import net.minecraft.client.resources.I18n;
import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import javax.annotation.Nonnull;
import java.util.List;
public class DataProviderBloodAltar implements IWailaDataProvider {
static final IWailaDataProvider INSTANCE = new DataProviderBloodAltar();
@Nonnull
@Override
public List<String> getWailaBody(ItemStack itemStack, List<String> tooltip, IWailaDataAccessor accessor, IWailaConfigHandler config) {
tooltip.add(I18n.format("tooltip.bloodmagic:tier", I18n.format("enchantment.level." + (accessor.getNBTData().getInteger("tier") + 1))));
if (accessor.getNBTData().hasKey("progress"))
tooltip.add(I18n.format("tooltip.bloodmagic:progress", String.valueOf(accessor.getNBTData().getFloat("progress") * 100)));
return tooltip;
}
@Nonnull
@Override
public NBTTagCompound getNBTData(EntityPlayerMP player, TileEntity te, NBTTagCompound tag, World world, BlockPos pos) {
TileBloodAltar altar = (TileBloodAltar) te;
tag.setInteger("tier", altar.getCurrentTier().ordinal());
if (altar.isCrafting())
tag.setFloat("progress", altar.getProgress());
return tag;
}
}

View file

@ -1,123 +0,0 @@
package WayofTime.bloodmagic;
import WayofTime.bloodmagic.api.BloodMagicPlugin;
import WayofTime.bloodmagic.api.IBloodMagicPlugin;
import WayofTime.bloodmagic.core.registry.OrbRegistry;
import WayofTime.bloodmagic.ritual.RitualManager;
import WayofTime.bloodmagic.client.gui.GuiHandler;
import WayofTime.bloodmagic.command.CommandBloodMagic;
import WayofTime.bloodmagic.core.RegistrarBloodMagic;
import WayofTime.bloodmagic.core.RegistrarBloodMagicItems;
import WayofTime.bloodmagic.meteor.MeteorConfigHandler;
import WayofTime.bloodmagic.network.BloodMagicPacketHandler;
import WayofTime.bloodmagic.proxy.CommonProxy;
import WayofTime.bloodmagic.registry.*;
import WayofTime.bloodmagic.structures.ModDungeons;
import WayofTime.bloodmagic.util.PluginUtil;
import WayofTime.bloodmagic.util.handler.IMCHandler;
import com.google.common.collect.Lists;
import net.minecraft.creativetab.CreativeTabs;
import net.minecraft.item.ItemStack;
import net.minecraft.launchwrapper.Launch;
import net.minecraftforge.common.config.Configuration;
import net.minecraftforge.fluids.FluidRegistry;
import net.minecraftforge.fml.common.Loader;
import net.minecraftforge.fml.common.Mod;
import net.minecraftforge.fml.common.SidedProxy;
import net.minecraftforge.fml.common.event.*;
import net.minecraftforge.fml.common.network.NetworkRegistry;
import org.apache.commons.lang3.tuple.Pair;
import java.io.File;
import java.util.List;
@Mod(modid = BloodMagic.MODID, name = BloodMagic.NAME, version = BloodMagic.VERSION, dependencies = BloodMagic.DEPEND, guiFactory = "WayofTime.bloodmagic.client.gui.GuiBloodMagicConfig$Factory")
public class BloodMagic {
public static final String MODID = "bloodmagic";
public static final String NAME = "Blood Magic: Alchemical Wizardry";
public static final String VERSION = "@VERSION@";
public static final String DEPEND = "required-after:guideapi;";
public static final boolean IS_DEV = (Boolean) Launch.blackboard.get("fml.deobfuscatedEnvironment");
public static final List<Pair<IBloodMagicPlugin, BloodMagicPlugin>> PLUGINS = Lists.newArrayList();
public static final RitualManager RITUAL_MANAGER = new RitualManager(new Configuration(new File(Loader.instance().getConfigDir(), MODID + "/" + "rituals.cfg")));
public static final CreativeTabs TAB_BM = new CreativeTabs(MODID + ".creativeTab") {
@Override
public ItemStack getTabIconItem() {
return OrbRegistry.getOrbStack(RegistrarBloodMagic.ORB_WEAK);
}
};
public static CreativeTabs TAB_TOMES = new CreativeTabs(MODID + ".creativeTabTome") {
@Override
public ItemStack getTabIconItem() {
return new ItemStack(RegistrarBloodMagicItems.UPGRADE_TOME);
}
@Override
public boolean hasSearchBar() {
return true;
}
}.setNoTitle().setBackgroundImageName("item_search.png");
@SidedProxy(serverSide = "WayofTime.bloodmagic.proxy.CommonProxy", clientSide = "WayofTime.bloodmagic.proxy.ClientProxy")
public static CommonProxy proxy;
@Mod.Instance(BloodMagic.MODID)
public static BloodMagic instance;
static {
FluidRegistry.enableUniversalBucket();
}
private File configDir;
@Mod.EventHandler
public void preInit(FMLPreInitializationEvent event) {
configDir = new File(event.getModConfigurationDirectory(), "bloodmagic");
PLUGINS.addAll(PluginUtil.gatherPlugins(event.getAsmData()));
PluginUtil.injectAPIInstances(PluginUtil.gatherInjections(event.getAsmData()));
ModTranquilityHandlers.init();
ModDungeons.init();
RITUAL_MANAGER.discover(event.getAsmData());
proxy.preInit();
}
@Mod.EventHandler
public void init(FMLInitializationEvent event) {
BloodMagicPacketHandler.init();
PluginUtil.handlePluginStep(PluginUtil.RegistrationStep.PLUGIN_REGISTER);
ModRecipes.init();
ModRituals.initHarvestHandlers();
MeteorConfigHandler.init(new File(configDir, "meteors"));
ModArmourTrackers.init();
NetworkRegistry.INSTANCE.registerGuiHandler(BloodMagic.instance, new GuiHandler());
ModCorruptionBlocks.init();
proxy.init();
}
@Mod.EventHandler
public void postInit(FMLPostInitializationEvent event) {
ModRecipes.addCompressionHandlers();
proxy.postInit();
}
@Mod.EventHandler
public void modMapping(FMLModIdMappingEvent event) {
}
@Mod.EventHandler
public void serverStarting(FMLServerStartingEvent event) {
event.registerServerCommand(new CommandBloodMagic());
}
@Mod.EventHandler
public void onIMCRecieved(FMLInterModComms.IMCEvent event) {
IMCHandler.handleIMC(event);
}
}

View file

@ -1,93 +0,0 @@
package WayofTime.bloodmagic;
import WayofTime.bloodmagic.meteor.MeteorConfigHandler;
import net.minecraftforge.common.config.Config;
import net.minecraftforge.common.config.ConfigManager;
import net.minecraftforge.fml.client.event.ConfigChangedEvent;
import net.minecraftforge.fml.common.Mod;
import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
@Config(modid = BloodMagic.MODID, name = BloodMagic.MODID + "/" + BloodMagic.MODID, category = "")
@Mod.EventBusSubscriber(modid = BloodMagic.MODID)
public class ConfigHandler
{
@Config.Comment({ "General settings" })
public static ConfigGeneral general = new ConfigGeneral();
@Config.Comment({ "Blacklist options for various features" })
public static ConfigBlacklist blacklist = new ConfigBlacklist();
@Config.Comment({ "Value modifiers for various features" })
public static ConfigValues values = new ConfigValues();
@Config.Comment({ "Settings that only pertain to the client" })
public static ConfigClient client = new ConfigClient();
@Config.Comment({ "Compatibility settings" })
public static ConfigCompat compat = new ConfigCompat();
@SubscribeEvent
public static void onConfigChanged(ConfigChangedEvent.OnConfigChangedEvent event)
{
if (event.getModID().equals(BloodMagic.MODID))
{
ConfigManager.sync(event.getModID(), Config.Type.INSTANCE); // Sync config values
BloodMagic.RITUAL_MANAGER.syncConfig();
MeteorConfigHandler.handleMeteors(false); // Reload meteors
}
}
public static class ConfigGeneral
{
@Config.Comment({ "Enables extra information to be printed to the log.", "Warning: May drastically increase log size." })
public boolean enableDebugLogging = false;
@Config.Comment({ "Enables extra information to be printed to the log." })
public boolean enableAPILogging = false;
@Config.Comment({ "Enables extra information to be printed to the log.", "Warning: May drastically increase log size." })
public boolean enableVerboseAPILogging = false;
}
public static class ConfigBlacklist
{
@Config.Comment({ "Stops listed blocks and entities from being teleposed.", "Use the registry name of the block or entity. Vanilla objects do not require the modid.", "If a block is specified, you can list the variants to only blacklist a given state." })
public String[] teleposer = { "bedrock", "mob_spawner" };
@Config.Comment({ "Stops listed blocks from being transposed.", "Use the registry name of the block. Vanilla blocks do not require the modid." })
public String[] transposer = { "bedrock", "mob_spawner" };
@Config.Comment({ "Stops the listed entities from being used in the Well of Suffering.", "Use the registry name of the entity. Vanilla entities do not require the modid." })
public String[] wellOfSuffering = {};
}
public static class ConfigValues
{
@Config.Comment({ "Declares the amount of LP gained per HP sacrificed for the given entity.", "Setting the value to 0 will blacklist it.", "Use the registry name of the entity followed by a ';' and then the value you want.", "Vanilla entities do not require the modid." })
public String[] sacrificialValues = { "villager;100", "slime;15", "enderman;10", "cow;100", "chicken;100", "horse;100", "sheep;100", "wolf;100", "ocelot;100", "pig;100", "rabbit;100" };
@Config.Comment({ "Amount of LP the Coat of Arms should provide for each damage dealt." })
@Config.RangeInt(min = 0, max = 100)
public int coatOfArmsConversion = 20;
@Config.Comment({ "Amount of LP the Sacrificial Dagger should provide for each damage dealt." })
@Config.RangeInt(min = 0, max = 10000)
public int sacrificialDaggerConversion = 100;
@Config.Comment({ "Will rewrite any default meteor types with new versions.", "Disable this if you want any of your changes to stay, or do not want default meteor types regenerated." })
public boolean shouldResyncMeteors = true;
}
public static class ConfigClient
{
@Config.Comment({ "Always render the beams between routing nodes.", "If disabled, the beams will only render while the Node Router is held." })
public boolean alwaysRenderRoutingLines = false;
@Config.Comment({ "Completely hide spectral blocks from view.", "If disabled, a transparent block will be displayed." })
public boolean invisibleSpectralBlocks = true;
@Config.Comment({ "When cycling through slots, the Sigil of Holding will skip over empty slots and move to the next occupied one.", "If disabled, it will behave identically to the default hotbar." })
public boolean sigilHoldingSkipsEmptySlots = false;
}
public static class ConfigCompat
{
@Config.Comment({ "The display mode to use when looking at a Blood Altar.", "ALWAYS - Always display information.", "SIGIL_HELD - Only display information when a Divination or Seers sigil is held in either hand.", "SIGIL_CONTAINED - Only display information when a Divination or Seers sigil is somewhere in the inventory." })
public AltarDisplayMode wailaAltarDisplayMode = AltarDisplayMode.SIGIL_HELD;
public enum AltarDisplayMode
{
ALWAYS,
SIGIL_HELD,
SIGIL_CONTAINED, ;
}
}
}

View file

@ -1,33 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.iface.IAlchemyArray;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
public abstract class AlchemyArrayEffect {
public final String key;
public AlchemyArrayEffect(String key) {
this.key = key;
}
public abstract boolean update(TileEntity tile, int ticksActive);
public abstract void writeToNBT(NBTTagCompound tag);
public abstract void readFromNBT(NBTTagCompound tag);
public abstract AlchemyArrayEffect getNewCopy();
public void onEntityCollidedWithBlock(IAlchemyArray array, World world, BlockPos pos, IBlockState state, Entity entity) {
}
public String getKey() {
return key;
}
}

View file

@ -1,243 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import java.util.List;
import javax.vecmath.Vector2d;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.monster.EntityMob;
import net.minecraft.entity.projectile.EntityTippedArrow;
import net.minecraft.init.Items;
import net.minecraft.item.ItemArrow;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.MathHelper;
import net.minecraft.util.math.Vec3d;
import net.minecraft.world.World;
import net.minecraftforge.items.IItemHandler;
import WayofTime.bloodmagic.util.Utils;
public class AlchemyArrayEffectArrowTurret extends AlchemyArrayEffect
{
public EntityLiving target;
public int arrowTimer;
public static final int ARROW_WINDUP = 50;
private int lastChestSlot = -1;
private double pitch = 0;
private double lastPitch = 0;
private double yaw = 0;
private double lastYaw = 0;
public AlchemyArrayEffectArrowTurret(String key)
{
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive)
{
BlockPos pos = tile.getPos();
World world = tile.getWorld();
BlockPos chestPos = pos.down();
TileEntity chestTile = world.getTileEntity(chestPos);
if (chestTile == null)
{
return false;
}
IItemHandler itemHandler = Utils.getInventory(chestTile, EnumFacing.UP);
if (itemHandler == null)
{
return false;
}
ItemStack arrowStack = new ItemStack(Items.AIR);
if (lastChestSlot >= 0 && lastChestSlot < itemHandler.getSlots())
{
ItemStack testStack = itemHandler.extractItem(lastChestSlot, 1, true);
if (testStack.isEmpty() || !(testStack.getItem() instanceof ItemArrow))
{
lastChestSlot = -1;
} else
{
arrowStack = testStack;
}
}
if (lastChestSlot < 0)
{
for (int i = 0; i < itemHandler.getSlots(); i++)
{
ItemStack testStack = itemHandler.extractItem(i, 1, true);
if (!testStack.isEmpty() && testStack.getItem() instanceof ItemArrow)
{
arrowStack = testStack;
lastChestSlot = i;
break;
}
}
}
if (lastChestSlot < 0)
{
return false; //No arrows in the chest. Welp!
}
if (canFireOnMob(world, pos, target))
{
Vector2d pitchYaw = getPitchYaw(pos, target);
lastPitch = pitch;
lastYaw = yaw;
pitch = pitchYaw.x;
yaw = pitchYaw.y;
arrowTimer++;
if (arrowTimer >= ARROW_WINDUP)
{
// ItemStack arrowStack = new ItemStack(Items.ARROW);
fireOnTarget(world, pos, arrowStack, target);
if (!world.isRemote)
{
itemHandler.extractItem(lastChestSlot, 1, false);
}
arrowTimer = 0;
}
return false;
} else
{
target = null;
arrowTimer = -1;
}
List<EntityMob> mobsInRange = world.getEntitiesWithinAABB(EntityMob.class, getBounds(pos));
for (EntityMob entity : mobsInRange)
{
if (canFireOnMob(world, pos, entity))// && isMobInFilter(ent))
{
target = entity;
arrowTimer = 0;
return false;
}
}
arrowTimer = -1;
target = null;
return false;
}
public double getPitch()
{
return pitch;
}
public double getLastPitch()
{
return lastPitch;
}
public double getYaw()
{
return yaw;
}
public double getLastYaw()
{
return lastYaw;
}
public void fireOnTarget(World world, BlockPos pos, ItemStack arrowStack, EntityLiving targetMob)
{
float vel = 3f;
double damage = 2;
if (!world.isRemote)
{
if (arrowStack.getItem() instanceof ItemArrow)
{
// ItemArrow arrow = (ItemArrow) arrowStack.getItem();
// EntityArrow entityarrow = arrow.createArrow(world, arrowStack, targetMob);
EntityTippedArrow entityarrow = new EntityTippedArrow(world);
entityarrow.setPotionEffect(arrowStack);
entityarrow.posX = pos.getX() + 0.5;
entityarrow.posY = pos.getY() + 0.5;
entityarrow.posZ = pos.getZ() + 0.5;
double d0 = targetMob.posX - (pos.getX() + 0.5);
double d1 = targetMob.posY + targetMob.height - (pos.getY() + 0.5);
double d2 = targetMob.posZ - (pos.getZ() + 0.5);
double d3 = (double) MathHelper.sqrt(d0 * d0 + d2 * d2);
entityarrow.setDamage(damage);
entityarrow.shoot(d0, d1 + d3 * 0.05, d2, vel, 0);
world.spawnEntity(entityarrow);
}
}
}
public static Vector2d getPitchYaw(BlockPos pos, Entity entityIn)
{
if (entityIn == null)
{
return new Vector2d(0, 0);
}
double distanceX = entityIn.posX - (pos.getX() + 0.5);
double distanceY = entityIn.posY + (double) entityIn.getEyeHeight() - (pos.getY() + 0.5);
double distanceZ = entityIn.posZ - (pos.getZ() + 0.5);
double radialDistance = Math.sqrt(distanceX * distanceX + distanceZ * distanceZ);
double yaw = Math.atan2(-distanceX, distanceZ) * 180 / Math.PI;
double pitch = -Math.atan2(distanceY, radialDistance) * 180 / Math.PI;
return new Vector2d(pitch, yaw);
}
public boolean canEntityBeSeen(World world, BlockPos pos, Entity entityIn)
{
return world.rayTraceBlocks(new Vec3d(pos.getX() + 0.5, pos.getY() + 0.5, pos.getZ() + 0.5), new Vec3d(entityIn.posX, entityIn.posY + (double) entityIn.getEyeHeight(), entityIn.posZ), false, true, false) == null;
}
public boolean canFireOnMob(World world, BlockPos pos, Entity entityIn)
{
return entityIn != null && !entityIn.isDead && entityIn.getDistanceSqToCenter(pos) <= getRange() * getRange() && entityIn.getDistanceSqToCenter(pos) >= getMinRange() * getMinRange() && canEntityBeSeen(world, pos, entityIn);
}
public AxisAlignedBB getBounds(BlockPos pos)
{
return new AxisAlignedBB(pos).grow(getRange(), getRange(), getRange());
}
public float getRange()
{
return 32;
}
public float getMinRange()
{
return 3;
}
@Override
public void writeToNBT(NBTTagCompound tag)
{
}
@Override
public void readFromNBT(NBTTagCompound tag)
{
}
@Override
public AlchemyArrayEffect getNewCopy()
{
return new AlchemyArrayEffectArrowTurret(key);
}
}

View file

@ -1,393 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.fakePlayer.FakePlayerBM;
import WayofTime.bloodmagic.tile.TileAlchemyArray;
import com.mojang.authlib.GameProfile;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.ai.EntityAIBase;
import net.minecraft.entity.ai.EntityAITasks;
import net.minecraft.entity.ai.EntityAITasks.EntityAITaskEntry;
import net.minecraft.entity.monster.*;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.pathfinding.Path;
import net.minecraft.pathfinding.PathFinder;
import net.minecraft.pathfinding.WalkNodeProcessor;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.MathHelper;
import net.minecraft.world.World;
import net.minecraftforge.common.util.FakePlayer;
import java.util.*;
/**
* Credits for the initial code go to Crazy Pants of EIO.
*/
public class AlchemyArrayEffectAttractor extends AlchemyArrayEffect {
private FakePlayer target;
private Set<EntityLiving> tracking = new HashSet<>();
private int counter = 0;
private int maxMobsAttracted = 10000;
private int cooldown = 50;
public AlchemyArrayEffectAttractor(String key) {
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
if (tile.getWorld().isRemote) {
return false;
}
BlockPos pos = tile.getPos();
counter++;
if (counter < 10) {
for (EntityLiving ent : tracking) {
onEntityTick(pos, ent);
}
return false;
}
counter = 0;
World world = tile.getWorld();
Set<EntityLiving> trackingThisTick = new HashSet<>();
List<EntityLiving> entsInBounds = world.getEntitiesWithinAABB(EntityLiving.class, getBounds(pos));
for (EntityLiving ent : entsInBounds) {
if (!ent.isDead)// && isMobInFilter(ent))
{
double x = (pos.getX() + 0.5D - ent.posX);
double y = (pos.getY() + 1D - ent.posY);
double z = (pos.getZ() + 0.5D - ent.posZ);
double distance = Math.sqrt(x * x + y * y + z * z);
if (distance < 2 && tracking.contains(ent)) {
setEntityCooldown(pos, ent, cooldown);
removeAssignedAITask(pos, ent);
continue;
}
if (!canEntityBeTracked(pos, ent)) {
// System.out.println("Cooldown: " + getEntityCooldown(pos, ent));
decrementEntityCooldown(pos, ent);
continue;
}
if (tracking.contains(ent)) {
trackingThisTick.add(ent);
onEntityTick(pos, ent);
} else if (tracking.size() < maxMobsAttracted && trackMob(pos, ent)) {
trackingThisTick.add(ent);
onTracked(ent);
}
}
}
for (EntityLiving e : tracking) {
if (!trackingThisTick.contains(e)) {
onUntracked(e);
}
}
tracking.clear();
tracking = trackingThisTick;
return false;
}
public boolean canEntityBeTracked(BlockPos pos, EntityLiving entity) {
return getEntityCooldown(pos, entity) <= 0;
}
private String getPosKey(BlockPos pos) {
return "BMAttractor:" + pos;
}
public int getEntityCooldown(BlockPos pos, EntityLiving entity) {
return entity.getEntityData().getInteger(getPosKey(pos));
}
public void setEntityCooldown(BlockPos pos, EntityLiving entity, int cooldown) {
entity.getEntityData().setInteger(getPosKey(pos), cooldown);
}
public void decrementEntityCooldown(BlockPos pos, EntityLiving entity) {
int cooldown = getEntityCooldown(pos, entity);
if (cooldown > 0) {
setEntityCooldown(pos, entity, cooldown - 1);
}
}
public AxisAlignedBB getBounds(BlockPos pos) {
return new AxisAlignedBB(pos).expand(getRange(), getRange(), getRange());
}
public float getRange() {
return 10;
}
private void onUntracked(EntityLiving e) {
if (e instanceof EntityEnderman) {
e.getEntityData().setBoolean("BM:tracked", false);
}
}
private void onTracked(EntityLiving e) {
if (e instanceof EntityEnderman) {
e.getEntityData().setBoolean("BM:tracked", true);
}
}
private void onEntityTick(BlockPos pos, EntityLiving ent) {
if (ent instanceof EntitySlime) {
ent.faceEntity(getTarget(ent.getEntityWorld(), pos), 10.0F, 20.0F);
} else if (ent instanceof EntitySilverfish) {
if (counter < 10) {
return;
}
EntitySilverfish sf = (EntitySilverfish) ent;
Path pathentity = getPathEntityToEntity(ent, getTarget(ent.getEntityWorld(), pos), getRange());
sf.getNavigator().setPath(pathentity, sf.getAIMoveSpeed());
} else if (ent instanceof EntityBlaze) {
double x = (pos.getX() + 0.5D - ent.posX);
double y = (pos.getY() + 1D - ent.posY);
double z = (pos.getZ() + 0.5D - ent.posZ);
double distance = Math.sqrt(x * x + y * y + z * z);
if (distance > 1.25) {
double speed = 0.01;
ent.motionX += x / distance * speed;
if (y > 0) {
ent.motionY += (0.3 - ent.motionY) * 0.3;
}
ent.motionZ += z / distance * speed;
}
} else if (ent instanceof EntityPigZombie || ent instanceof EntitySpider) {
forceMove(pos, ent);
// ent.setAttackTarget(target);
} else if (ent instanceof EntityEnderman) {
ent.setAttackTarget(getTarget(ent.getEntityWorld(), pos));
}
}
private void forceMove(BlockPos pos, EntityLiving ent) {
double x = (pos.getX() + 0.5D - ent.posX);
double y = (pos.getY() + 1D - ent.posY);
double z = (pos.getZ() + 0.5D - ent.posZ);
double distance = Math.sqrt(x * x + y * y + z * z);
if (distance > 2) {
EntityMob mod = (EntityMob) ent;
mod.faceEntity(getTarget(ent.getEntityWorld(), pos), 180, 0);
mod.getMoveHelper().strafe(0, 0.3f);
if (mod.posY < pos.getY()) {
mod.setJumping(true);
} else {
mod.setJumping(false);
}
}
}
public Path getPathEntityToEntity(Entity entity, Entity targetEntity, float range) {
int targX = MathHelper.floor(targetEntity.posX);
int targY = MathHelper.floor(targetEntity.posY + 1.0D);
int targZ = MathHelper.floor(targetEntity.posZ);
PathFinder pf = new PathFinder(new WalkNodeProcessor());
return pf.findPath(targetEntity.getEntityWorld(), (EntityLiving) entity, new BlockPos(targX, targY, targZ), range);
}
private boolean trackMob(BlockPos pos, EntityLiving ent) {
//TODO: Figure out if this crud is needed
if (useSetTarget(ent)) {
ent.setAttackTarget(getTarget(ent.getEntityWorld(), pos));
return true;
} else if (useSpecialCase(ent)) {
return applySpecialCase(pos, ent);
} else {
return attractUsingAITask(pos, ent);
}
}
private boolean useSetTarget(EntityLiving ent) {
return ent instanceof EntityPigZombie || ent instanceof EntitySpider || ent instanceof EntitySilverfish;
}
public void removeAssignedAITask(BlockPos pos, EntityLiving ent) {
Set<EntityAITaskEntry> entries = ent.tasks.taskEntries;
EntityAIBase remove = null;
for (EntityAITaskEntry entry : entries) {
if (entry.action instanceof AttractTask) {
AttractTask at = (AttractTask) entry.action;
if (at.coord.equals(pos)) {
remove = entry.action;
} else {
continue;
}
}
}
if (remove != null) {
ent.tasks.removeTask(remove);
}
}
private boolean attractUsingAITask(BlockPos pos, EntityLiving ent) {
tracking.add(ent);
Set<EntityAITaskEntry> entries = ent.tasks.taskEntries;
// boolean hasTask = false;
EntityAIBase remove = null;
// boolean isTracked;
for (EntityAITaskEntry entry : entries) {
if (entry.action instanceof AttractTask) {
AttractTask at = (AttractTask) entry.action;
if (at.coord.equals(pos) || !at.shouldExecute()) {
remove = entry.action;
} else {
return false;
}
}
}
if (remove != null) {
ent.tasks.removeTask(remove);
}
cancelCurrentTasks(ent);
ent.tasks.addTask(0, new AttractTask(ent, getTarget(ent.getEntityWorld(), pos), pos));
return true;
}
private void cancelCurrentTasks(EntityLiving ent) {
Iterator<EntityAITaskEntry> iterator = ent.tasks.taskEntries.iterator();
List<EntityAITasks.EntityAITaskEntry> currentTasks = new ArrayList<>();
while (iterator.hasNext()) {
EntityAITaskEntry entityaitaskentry = iterator.next();
if (entityaitaskentry != null) {
if (entityaitaskentry.action instanceof AttractTask) {
continue;
}
currentTasks.add(entityaitaskentry);
}
}
// Only available way to stop current execution is to remove all current
// tasks, then re-add them
for (EntityAITaskEntry task : currentTasks) {
ent.tasks.removeTask(task.action);
ent.tasks.addTask(task.priority, task.action);
}
}
private boolean applySpecialCase(BlockPos pos, EntityLiving ent) {
if (ent instanceof EntitySlime) {
ent.faceEntity(getTarget(ent.getEntityWorld(), pos), 10.0F, 20.0F);
// ent.setAttackTarget(getTarget(ent.worldObj, pos));
return true;
} else if (ent instanceof EntitySilverfish) {
EntitySilverfish es = (EntitySilverfish) ent;
Path pathentity = getPathEntityToEntity(ent, getTarget(ent.getEntityWorld(), pos), getRange());
es.getNavigator().setPath(pathentity, es.getAIMoveSpeed());
return true;
} else if (ent instanceof EntityBlaze) {
return true;
}
return false;
}
private boolean useSpecialCase(EntityLiving ent) {
return ent instanceof EntitySlime || ent instanceof EntitySilverfish || ent instanceof EntityBlaze;
}
public FakePlayer getTarget(World world, BlockPos pos) {
if (target == null) {
// System.out.println("...Hi? " + pos);
target = new Target(world, pos);
}
return target;
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectAttractor(key);
}
private static class AttractTask extends EntityAIBase {
private EntityLiving mob;
private BlockPos coord;
private FakePlayer target;
private int updatesSincePathing;
private boolean started = false;
private AttractTask(EntityLiving mob, FakePlayer target, BlockPos coord) {
this.mob = mob;
this.coord = coord;
this.target = target;
}
@Override
public boolean shouldExecute() {
boolean res = false;
//TODO:
TileEntity te = mob.getEntityWorld().getTileEntity(coord);
if (te instanceof TileAlchemyArray) {
res = true;
}
return res;
}
@Override
public void resetTask() {
started = false;
updatesSincePathing = 0;
}
@Override
public boolean isInterruptible() {
return true;
}
@Override
public void updateTask() {
if (!started || updatesSincePathing > 20) {
started = true;
int speed = 1;
// mob.getNavigator().setAvoidsWater(false);
boolean res = mob.getNavigator().tryMoveToEntityLiving(target, speed);
if (!res) {
mob.getNavigator().tryMoveToXYZ(target.posX, target.posY + 1, target.posZ, speed);
}
updatesSincePathing = 0;
} else {
updatesSincePathing++;
}
}
}
private class Target extends FakePlayerBM {
public Target(World world, BlockPos pos) {
super(world, pos, new GameProfile(null, BloodMagic.MODID + "ArrayAttractor" + ":" + pos));
posY += 1;
}
}
}

View file

@ -1,71 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.client.render.alchemyArray.BindingAlchemyCircleRenderer;
import net.minecraft.entity.effect.EntityLightningBolt;
import net.minecraft.entity.item.EntityItem;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
public class AlchemyArrayEffectBinding extends AlchemyArrayEffectCrafting {
public AlchemyArrayEffectBinding(String key, ItemStack outputStack) {
super(key, outputStack, 200);
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
if (ticksActive >= 50 && ticksActive <= 250) {
// TODO: Find a way to spawn lightning from only the server side -
// does not render when just spawned on server, not client.
this.spawnLightningOnCircle(tile.getWorld(), tile.getPos(), ticksActive);
}
if (tile.getWorld().isRemote) {
return false;
}
if (ticksActive >= 300) {
BlockPos pos = tile.getPos();
ItemStack output = outputStack.copy();
EntityItem outputEntity = new EntityItem(tile.getWorld(), pos.getX() + 0.5, pos.getY() + 0.5, pos.getZ() + 0.5, output);
tile.getWorld().spawnEntity(outputEntity);
return true;
}
return false;
}
public void spawnLightningOnCircle(World world, BlockPos pos, int ticksActive) {
if (ticksActive % 50 == 0) {
int circle = ticksActive / 50 - 1;
float distance = BindingAlchemyCircleRenderer.getDistanceOfCircle(circle, ticksActive);
float angle = BindingAlchemyCircleRenderer.getAngleOfCircle(circle, ticksActive);
double dispX = distance * Math.sin(angle);
double dispZ = -distance * Math.cos(angle);
EntityLightningBolt lightning = new EntityLightningBolt(world, pos.getX() + dispX, pos.getY(), pos.getZ() + dispZ, true);
world.spawnEntity(lightning);
}
}
@Override
public void writeToNBT(NBTTagCompound tag) {
//EMPTY
}
@Override
public void readFromNBT(NBTTagCompound tag) {
//EMPTY
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectBinding(key, outputStack);
}
}

View file

@ -1,51 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.iface.IAlchemyArray;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
public class AlchemyArrayEffectBounce extends AlchemyArrayEffect {
public AlchemyArrayEffectBounce(String key) {
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
return false;
}
@Override
public void onEntityCollidedWithBlock(IAlchemyArray array, World world, BlockPos pos, IBlockState state, Entity entity) {
if (entity.isSneaking()) {
entity.fallDistance = 0;
} else if (entity.motionY < 0.0D) {
entity.motionY = -entity.motionY;
if (!(entity instanceof EntityLivingBase)) {
entity.motionY *= 0.8D;
}
entity.fallDistance = 0;
}
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectBounce(key);
}
}

View file

@ -1,63 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import net.minecraft.entity.item.EntityItem;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
public class AlchemyArrayEffectCrafting extends AlchemyArrayEffect {
public final ItemStack outputStack;
public int tickLimit;
public AlchemyArrayEffectCrafting(ItemStack outputStack) {
this(outputStack, 200);
}
public AlchemyArrayEffectCrafting(ItemStack outputStack, int tickLimit) {
this(outputStack.toString() + tickLimit, outputStack, tickLimit);
}
public AlchemyArrayEffectCrafting(String key, ItemStack outputStack, int tickLimit) {
super(key);
this.outputStack = outputStack;
this.tickLimit = tickLimit;
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
// TODO: Add recipe rechecking to verify nothing screwy is going on.
if (tile.getWorld().isRemote) {
return false;
}
if (ticksActive >= tickLimit) {
BlockPos pos = tile.getPos();
ItemStack output = outputStack.copy();
EntityItem outputEntity = new EntityItem(tile.getWorld(), pos.getX() + 0.5, pos.getY() + 0.5, pos.getZ() + 0.5, output);
tile.getWorld().spawnEntity(outputEntity);
return true;
}
return false;
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectCrafting(key, outputStack, tickLimit);
}
}

View file

@ -1,58 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.api.impl.recipe.RecipeAlchemyArray;
import net.minecraft.entity.item.EntityItem;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
public class AlchemyArrayEffectCraftingNew extends AlchemyArrayEffect {
private final RecipeAlchemyArray recipe;
public AlchemyArrayEffectCraftingNew(RecipeAlchemyArray recipe) {
this(recipe.getOutput().toString() + 200, recipe);
}
public AlchemyArrayEffectCraftingNew(String key, RecipeAlchemyArray recipeAlchemyArray) {
super(key);
this.recipe = recipeAlchemyArray;
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
if (tile.getWorld().isRemote)
return false;
if (ticksActive >= 200) {
BlockPos pos = tile.getPos();
ItemStack output = recipe.getOutput().copy();
EntityItem outputEntity = new EntityItem(tile.getWorld(), pos.getX() + 0.5, pos.getY() + 0.5, pos.getZ() + 0.5, output);
tile.getWorld().spawnEntity(outputEntity);
return true;
}
return false;
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectCraftingNew(key, recipe);
}
}

View file

@ -1,143 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import java.util.List;
import WayofTime.bloodmagic.util.DamageSourceBloodMagic;
import net.minecraft.block.Block;
import net.minecraft.block.BlockFurnace;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.init.Blocks;
import net.minecraft.item.ItemStack;
import net.minecraft.item.crafting.FurnaceRecipes;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.tileentity.TileEntityFurnace;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
public class AlchemyArrayEffectFurnaceFuel extends AlchemyArrayEffect
{
static double radius = 10;
static int burnTicksAdded = 401; //Set to +1 more than it needs to be due to a hacky method - basically done so that the array doesn't double dip your health if you only add one item.
public AlchemyArrayEffectFurnaceFuel(String key)
{
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive)
{
BlockPos pos = tile.getPos();
World world = tile.getWorld();
EntityPlayer sacrifice = null;
for (EnumFacing face : EnumFacing.VALUES)
{
BlockPos furnacePos = pos.offset(face);
Block block = world.getBlockState(furnacePos).getBlock();
if (block != Blocks.FURNACE) //This will only work vanilla furnaces. No others!
{
continue;
}
TileEntity bottomTile = world.getTileEntity(furnacePos);
if (bottomTile instanceof TileEntityFurnace)
{
TileEntityFurnace furnaceTile = (TileEntityFurnace) bottomTile;
if (canFurnaceSmelt(furnaceTile) && !furnaceTile.isBurning())
{
if (sacrifice == null || sacrifice.isDead)
{
AxisAlignedBB bb = new AxisAlignedBB(pos).grow(radius);
List<EntityPlayer> playerList = world.getEntitiesWithinAABB(EntityPlayer.class, bb);
for (EntityPlayer player : playerList)
{
if (!player.isDead)
{
sacrifice = player;
}
}
}
if (sacrifice == null || sacrifice.isDead)
{
return false;
}
if (addFuelTime(furnaceTile, world, furnacePos, burnTicksAdded))
{
if (!sacrifice.capabilities.isCreativeMode)
{
sacrifice.hurtResistantTime = 0;
sacrifice.attackEntityFrom(DamageSourceBloodMagic.INSTANCE, 1.0F); //No.
}
}
}
}
}
return false;
}
public static boolean addFuelTime(TileEntityFurnace furnaceTile, World world, BlockPos furnacePos, int cookTime)
{
furnaceTile.setField(0, cookTime);
BlockFurnace.setState(true, world, furnacePos);
return true;
}
public static boolean canFurnaceSmelt(TileEntityFurnace furnaceTile)
{
ItemStack burnStack = furnaceTile.getStackInSlot(0);
if (burnStack.isEmpty())
{
return false;
} else
{
ItemStack resultStack = FurnaceRecipes.instance().getSmeltingResult(burnStack);
if (resultStack.isEmpty())
{
return false;
} else
{
ItemStack finishStack = furnaceTile.getStackInSlot(2);
if (finishStack.isEmpty())
{
return true;
} else if (!finishStack.isItemEqual(resultStack))
{
return false;
} else if (finishStack.getCount() + resultStack.getCount() <= furnaceTile.getInventoryStackLimit() && finishStack.getCount() + resultStack.getCount() <= finishStack.getMaxStackSize()) // Forge fix: make furnace respect stack sizes in furnace recipes
{
return true;
} else
{
return finishStack.getCount() + resultStack.getCount() <= resultStack.getMaxStackSize(); // Forge fix: make furnace respect stack sizes in furnace recipes
}
}
}
}
@Override
public void writeToNBT(NBTTagCompound tag)
{
}
@Override
public void readFromNBT(NBTTagCompound tag)
{
}
@Override
public AlchemyArrayEffect getNewCopy()
{
return new AlchemyArrayEffectFurnaceFuel(key);
}
}

View file

@ -1,154 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import java.util.Random;
import net.minecraft.block.state.IBlockState;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import net.minecraftforge.common.MinecraftForge;
import WayofTime.bloodmagic.event.TeleposeEvent;
import WayofTime.bloodmagic.tile.TileAlchemyArray;
import WayofTime.bloodmagic.util.Constants;
import WayofTime.bloodmagic.util.Utils;
public class AlchemyArrayEffectLaputa extends AlchemyArrayEffect
{
public static final int TELEPOSE_DELAY = 4;
private BlockPos currentPos = BlockPos.ORIGIN;
private int radius = -1;
private int teleportHeightOffset = 5;
public AlchemyArrayEffectLaputa(String key)
{
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive)
{
if (ticksActive >= 100)
{
World world = tile.getWorld();
if (radius == -1)
{
((TileAlchemyArray) tile).setItemDrop(false);
radius = getRandomRadius(world.rand);
teleportHeightOffset = getRandomHeightOffset(world.rand);
currentPos = new BlockPos(-radius, -radius, -radius);
}
BlockPos pos = tile.getPos();
if (world.isRemote)
{
return false;
}
int j = -radius;
int i = -radius;
int k = -radius;
if (currentPos != null)
{
j = currentPos.getY();
i = currentPos.getX();
k = currentPos.getZ();
}
int checks = 0;
int maxChecks = 100;
while (j <= radius)
{
while (i <= radius)
{
while (k <= radius)
{
if (i == 0 && j == 0 && k == 0)
{
k++;
continue;
}
checks++;
if (checks >= maxChecks)
{
this.currentPos = new BlockPos(i, j, k);
return false;
}
if (checkIfSphere(radius, i, j, k))
{
BlockPos newPos = pos.add(i, j, k);
BlockPos offsetPos = newPos.up(teleportHeightOffset);
IBlockState state = world.getBlockState(newPos);
TeleposeEvent event = new TeleposeEvent(world, newPos, world, offsetPos);
if (state.getBlockHardness(world, newPos) > 0 && !MinecraftForge.EVENT_BUS.post(event) && Utils.swapLocations(event.initalWorld, event.initialBlockPos, event.finalWorld, event.finalBlockPos))
{
k++;
this.currentPos = new BlockPos(i, j, k);
return false;
}
}
k++;
}
i++;
k = -radius;
}
j++;
i = -radius;
this.currentPos = new BlockPos(i, j, k);
return false;
}
return true;
}
return false;
}
public boolean checkIfSphere(float radius, float xOff, float yOff, float zOff)
{
float possOffset = 0.5f;
return xOff * xOff + yOff * yOff + zOff * zOff <= ((radius + possOffset) * (radius + possOffset));
}
public int getRandomRadius(Random rand)
{
return rand.nextInt(5) + 4;
}
public int getRandomHeightOffset(Random rand)
{
return radius * 2 + 1 + rand.nextInt(5);
}
@Override
public void writeToNBT(NBTTagCompound tag)
{
tag.setInteger("radius", radius);
tag.setInteger("teleportHeightOffset", teleportHeightOffset);
tag.setInteger(Constants.NBT.X_COORD, currentPos.getX());
tag.setInteger(Constants.NBT.Y_COORD, currentPos.getY());
tag.setInteger(Constants.NBT.Z_COORD, currentPos.getZ());
}
@Override
public void readFromNBT(NBTTagCompound tag)
{
radius = tag.getInteger("radius");
teleportHeightOffset = tag.getInteger("teleportHeightOffset");
currentPos = new BlockPos(tag.getInteger(Constants.NBT.X_COORD), tag.getInteger(Constants.NBT.Y_COORD), tag.getInteger(Constants.NBT.Z_COORD));
}
@Override
public AlchemyArrayEffect getNewCopy()
{
return new AlchemyArrayEffectLaputa(key);
}
}

View file

@ -1,233 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.item.EntityItem;
import net.minecraft.entity.monster.IMob;
import net.minecraft.entity.passive.EntityAnimal;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.init.SoundEvents;
import net.minecraft.item.Item;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumParticleTypes;
import net.minecraft.util.SoundCategory;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Vec3d;
import net.minecraft.world.World;
import net.minecraft.world.WorldServer;
import net.minecraftforge.fml.common.registry.EntityEntry;
import net.minecraftforge.fml.common.registry.EntityRegistry;
import WayofTime.bloodmagic.api.impl.BloodMagicAPI;
import WayofTime.bloodmagic.api.impl.recipe.RecipeSacrificeCraft;
import WayofTime.bloodmagic.ritual.AreaDescriptor;
import WayofTime.bloodmagic.util.DamageSourceBloodMagic;
import WayofTime.bloodmagic.util.helper.PurificationHelper;
public class AlchemyArrayEffectMobSacrifice extends AlchemyArrayEffect
{
public static final AreaDescriptor itemDescriptor = new AreaDescriptor.Rectangle(new BlockPos(-5, -5, -5), 11);
public static final AreaDescriptor mobDescriptor = new AreaDescriptor.Rectangle(new BlockPos(-5, -5, -5), 11);
public int craftTime = 0;
public static final int REQUIRED_CRAFT_TIME = 200;
public AlchemyArrayEffectMobSacrifice(String key)
{
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive)
{
World world = tile.getWorld();
if (world.isRemote && ticksActive < 200 && ticksActive > 40)
{
BlockPos pos = tile.getPos();
Random rand = world.rand;
for (int i = 0; i < 2; i++)
{
double d0 = (double) pos.getX() + 0.5D + (rand.nextDouble() - 0.5D) * 2.5D;
double d1 = (double) pos.getY() + 0.2D + (rand.nextDouble() - 0.5D) * 0.2D;
double d2 = (double) pos.getZ() + 0.5D + (rand.nextDouble() - 0.5D) * 2.5D;
world.spawnParticle(EnumParticleTypes.SPELL_MOB, d0, d1, d2, 1D, 0.0D, 0.0D);
}
}
//We need to do the check on both sides to correctly do particles.
if (ticksActive >= 200)
{
BlockPos pos = tile.getPos();
List<EntityItem> itemList = world.getEntitiesWithinAABB(EntityItem.class, itemDescriptor.getAABB(pos));
List<ItemStack> inputList = new ArrayList<ItemStack>();
for (EntityItem entityItem : itemList)
{
if (entityItem.isDead || entityItem.getItem().isEmpty())
{
continue;
}
inputList.add(entityItem.getItem().copy());
}
if (inputList.isEmpty())
{
return false;
}
if (inputList.size() == 1) //TODO: Test if it is a something that can be filled with Soul Breath
{
}
RecipeSacrificeCraft recipe = BloodMagicAPI.INSTANCE.getRecipeRegistrar().getSacrificeCraft(inputList);
if (recipe != null)
{
double healthRequired = recipe.getHealthRequired();
double healthAvailable = 0;
List<EntityLivingBase> livingEntities = world.getEntitiesWithinAABB(EntityLivingBase.class, mobDescriptor.getAABB(pos));
for (EntityLivingBase living : livingEntities)
{
double health = getEffectiveHealth(living);
if (health > 0)
{
healthAvailable += health;
}
}
if (healthAvailable < healthRequired)
{
craftTime = 0;
return false;
}
craftTime++;
if (craftTime >= REQUIRED_CRAFT_TIME)
{
if (!world.isRemote)
{
for (EntityLivingBase living : livingEntities)
{
double health = getEffectiveHealth(living);
if (healthAvailable > 0 && health > 0)
{
healthAvailable -= health;
living.getEntityWorld().playSound(null, living.posX, living.posY, living.posZ, SoundEvents.BLOCK_FIRE_EXTINGUISH, SoundCategory.BLOCKS, 0.5F, 2.6F + (living.getEntityWorld().rand.nextFloat() - living.getEntityWorld().rand.nextFloat()) * 0.8F);
living.setHealth(-1);
living.onDeath(DamageSourceBloodMagic.INSTANCE);
}
if (healthAvailable <= 0)
{
break;
}
}
for (EntityItem itemEntity : itemList)
{
itemEntity.getItem().setCount(itemEntity.getItem().getCount() - 1);
if (itemEntity.getItem().isEmpty()) //TODO: Check container
{
itemEntity.setDead();
}
}
world.spawnEntity(new EntityItem(world, pos.getX() + 0.5, pos.getY() + 2.5, pos.getZ() + 0.5, recipe.getOutput()));
craftTime = 0;
}
} else
{
if (world.isRemote)
{
Vec3d spawnPosition = new Vec3d(pos.getX() + 0.5, pos.getY() + 2.5, pos.getZ() + 0.5);
for (EntityItem itemEntity : itemList)
{
ItemStack stack = itemEntity.getItem();
double velocityFactor = 0.1;
Vec3d itemPosition = new Vec3d(itemEntity.posX, itemEntity.posY + 0.5, itemEntity.posZ);
Vec3d velVec1 = new Vec3d((world.rand.nextDouble() - 0.5) * velocityFactor, (world.rand.nextDouble() - 0.5) * velocityFactor, (world.rand.nextDouble() - 0.5) * velocityFactor);
// Vec3d velVec2 = new Vec3d((world.rand.nextDouble() - 0.5) * velocityFactor, (world.rand.nextDouble()) * velocityFactor, (world.rand.nextDouble() - 0.5) * velocityFactor);
// vec3d1 = vec3d1.addVector(this.posX, this.posY + (double)this.getEyeHeight(), this.posZ);
// if (this.world instanceof WorldServer) //Forge: Fix MC-2518 spawnParticle is nooped on server, need to use server specific variant
// ((WorldServer)this.world).spawnParticle(EnumParticleTypes.ITEM_CRACK, vec3d1.x, vec3d1.y, vec3d1.z, 0, vec3d.x, vec3d.y + 0.05D, vec3d.z, 0.0D, Item.getIdFromItem(stack.getItem()), stack.getMetadata());
// else //Fix the fact that spawning ItemCrack uses TWO arguments.
world.spawnParticle(EnumParticleTypes.ITEM_CRACK, itemPosition.x + (spawnPosition.x - itemPosition.x) * craftTime / REQUIRED_CRAFT_TIME, itemPosition.y + (spawnPosition.y - itemPosition.y) * craftTime / REQUIRED_CRAFT_TIME, itemPosition.z + (spawnPosition.z - itemPosition.z) * craftTime / REQUIRED_CRAFT_TIME, velVec1.x, velVec1.y, velVec1.z, Item.getIdFromItem(stack.getItem()), stack.getMetadata());
// world.spawnParticle(EnumParticleTypes.ITEM_CRACK, spawnPosition.x, spawnPosition.y, spawnPosition.z, velVec2.x, velVec2.y, velVec2.z, Item.getIdFromItem(stack.getItem()), stack.getMetadata());
}
for (EntityLivingBase living : livingEntities)
{
double health = getEffectiveHealth(living);
if (health <= 0)
{
continue;
}
double d0 = (double) living.posX + (world.rand.nextDouble() - 0.5D) * 0.5D;
double d1 = (double) living.posY + 0.5D + (world.rand.nextDouble() - 0.5D) * 1D;
double d2 = (double) living.posZ + (world.rand.nextDouble() - 0.5D) * 0.5D;
world.spawnParticle(EnumParticleTypes.SPELL_MOB, d0, d1, d2, 1D, 0.0D, 0.0D);
}
}
}
}
}
return false;
}
//Future-proofing in case I want to make different mobs give different effective health
public double getEffectiveHealth(EntityLivingBase living)
{
if (living == null)
return 0;
if (!living.isNonBoss())
return 0;
if (living instanceof EntityPlayer)
return 0;
if (living.isChild() && !(living instanceof IMob))
return 0;
if (living.isDead || living.getHealth() < 0.5F)
return 0;
EntityEntry entityEntry = EntityRegistry.getEntry(living.getClass());
if (entityEntry == null)
return 0;
return living.getHealth();
}
@Override
public void writeToNBT(NBTTagCompound tag)
{
}
@Override
public void readFromNBT(NBTTagCompound tag)
{
}
@Override
public AlchemyArrayEffect getNewCopy()
{
return new AlchemyArrayEffectMobSacrifice(key);
}
}

View file

@ -1,74 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.iface.IAlchemyArray;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
public class AlchemyArrayEffectMovement extends AlchemyArrayEffect {
public AlchemyArrayEffectMovement(String key) {
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
return false;
}
@Override
public void onEntityCollidedWithBlock(IAlchemyArray array, World world, BlockPos pos, IBlockState state, Entity entity) {
double motionY = 0.5;
double speed = 3;
EnumFacing direction = array.getRotation();
entity.motionY = motionY;
entity.fallDistance = 0;
switch (direction) {
case NORTH:
entity.motionX = 0;
entity.motionY = motionY;
entity.motionZ = -speed;
break;
case SOUTH:
entity.motionX = 0;
entity.motionY = motionY;
entity.motionZ = speed;
break;
case WEST:
entity.motionX = -speed;
entity.motionY = motionY;
entity.motionZ = 0;
break;
case EAST:
entity.motionX = speed;
entity.motionY = motionY;
entity.motionZ = 0;
break;
default:
break;
}
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectMovement(key);
}
}

View file

@ -1,39 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.iface.ISigil;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
public class AlchemyArrayEffectSigil extends AlchemyArrayEffect {
private final ISigil sigil;
public AlchemyArrayEffectSigil(String key, ISigil sigil) {
super(key);
this.sigil = sigil;
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
//TODO: Need particles.
if (sigil.hasArrayEffect()) {
sigil.performArrayEffect(tile.getWorld(), tile.getPos());
}
return false;
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectSigil(key, sigil);
}
}

View file

@ -1,186 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.tile.TileAlchemyArray;
import com.google.common.base.Predicate;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.SharedMonsterAttributes;
import net.minecraft.entity.ai.EntityAIBase;
import net.minecraft.entity.ai.EntityAINearestAttackableTarget;
import net.minecraft.entity.ai.EntityAITasks;
import net.minecraft.entity.ai.EntityAITasks.EntityAITaskEntry;
import net.minecraft.entity.monster.EntityMob;
import net.minecraft.entity.monster.EntitySkeleton;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import net.minecraftforge.common.util.FakePlayer;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
/**
* Credits for the initial code go to Crazy Pants of EIO.
*/
public class AlchemyArrayEffectSkeletonTurret extends AlchemyArrayEffect {
public static Predicate<EntityMob> checkSkeleton = input -> !(input instanceof EntitySkeleton);
private EntitySkeleton turret;
public AlchemyArrayEffectSkeletonTurret(String key) {
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
// if (tile.getWorld().isRemote)
// {
// return false;
// }
BlockPos pos = tile.getPos();
if (turret != null && !turret.isDead) {
double x = (pos.getX() + 0.5D - turret.posX);
double y = (pos.getY() + 1D - turret.posY);
double z = (pos.getZ() + 0.5D - turret.posZ);
double distance = Math.sqrt(x * x + y * y + z * z);
if (distance < 2) {
// turret.addPotionEffect(new PotionEffect(MobEffects.SLOWNESS, 100, 100));
return false;
}
}
World world = tile.getWorld();
List<EntitySkeleton> skeletonsInRange = world.getEntitiesWithinAABB(EntitySkeleton.class, getBounds(pos));
for (EntitySkeleton entity : skeletonsInRange) {
if (!entity.isDead)// && isMobInFilter(ent))
{
modifyAITargetTasks(entity);
turret = entity;
break;
}
}
return false;
}
public AxisAlignedBB getBounds(BlockPos pos) {
return new AxisAlignedBB(pos).expand(getRange(), getRange(), getRange());
}
public float getRange() {
return 0;
}
// private void onUntracked(EntityLiving e)
// {
// e.getEntityData().setBoolean("BM:tracked", false);
// }
//
// private void onTracked(EntityLiving e)
// {
// e.getEntityData().setBoolean("BM:tracked", true);
// }
private boolean modifyAITargetTasks(EntitySkeleton entity) {
cancelCurrentTargetTasks(entity);
// entity.setCombatTask();
entity.targetTasks.addTask(1, new EntityAINearestAttackableTarget(entity, EntityMob.class, 10, true, false, checkSkeleton));
entity.getEntityAttribute(SharedMonsterAttributes.MOVEMENT_SPEED).setBaseValue(0);
entity.getEntityAttribute(SharedMonsterAttributes.KNOCKBACK_RESISTANCE).setBaseValue(1);
return true;
}
private void cancelCurrentTargetTasks(EntityLiving entity) {
Iterator<EntityAITaskEntry> iterator = entity.targetTasks.taskEntries.iterator();
List<EntityAITasks.EntityAITaskEntry> currentTasks = new ArrayList<>();
while (iterator.hasNext()) {
EntityAITaskEntry entityaitaskentry = iterator.next();
if (entityaitaskentry != null)// && entityaitaskentry.action instanceof EntityAITarget)
{
currentTasks.add(entityaitaskentry);
}
}
for (EntityAITaskEntry task : currentTasks) {
entity.targetTasks.removeTask(task.action);
}
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectSkeletonTurret(key);
}
private static class AttractTask extends EntityAIBase {
private EntityLiving mob;
private BlockPos coord;
private FakePlayer target;
private int updatesSincePathing;
private boolean started = false;
private AttractTask(EntityLiving mob, FakePlayer target, BlockPos coord) {
this.mob = mob;
this.coord = coord;
this.target = target;
}
@Override
public boolean shouldExecute() {
boolean res = false;
//TODO:
TileEntity te = mob.getEntityWorld().getTileEntity(coord);
if (te instanceof TileAlchemyArray) {
res = true;
}
return res;
}
@Override
public void resetTask() {
started = false;
updatesSincePathing = 0;
}
@Override
public boolean isInterruptible() {
return true;
}
@Override
public void updateTask() {
if (!started || updatesSincePathing > 20) {
started = true;
int speed = 1;
// mob.getNavigator().setAvoidsWater(false);
boolean res = mob.getNavigator().tryMoveToEntityLiving(target, speed);
if (!res) {
mob.getNavigator().tryMoveToXYZ(target.posX, target.posY + 1, target.posZ, speed);
}
updatesSincePathing = 0;
} else {
updatesSincePathing++;
}
}
}
}

View file

@ -1,52 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.DamageSource;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import WayofTime.bloodmagic.iface.IAlchemyArray;
public class AlchemyArrayEffectSpike extends AlchemyArrayEffect
{
public AlchemyArrayEffectSpike(String key)
{
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive)
{
return false;
}
@Override
public void onEntityCollidedWithBlock(IAlchemyArray array, World world, BlockPos pos, IBlockState state, Entity entity)
{
if (entity instanceof EntityLivingBase)
{
entity.attackEntityFrom(DamageSource.CACTUS, 2);
}
}
@Override
public void writeToNBT(NBTTagCompound tag)
{
}
@Override
public void readFromNBT(NBTTagCompound tag)
{
}
@Override
public AlchemyArrayEffect getNewCopy()
{
return new AlchemyArrayEffectSpike(key);
}
}

View file

@ -1,101 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import net.minecraft.block.Block;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.init.SoundEvents;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.network.play.server.SPacketUpdateHealth;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.SoundCategory;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import net.minecraft.world.WorldServer;
import WayofTime.bloodmagic.core.RegistrarBloodMagicBlocks;
import WayofTime.bloodmagic.iface.IAlchemyArray;
public class AlchemyArrayEffectTeleport extends AlchemyArrayEffect
{
public static final int MAX_SEARCH = 20;
public static final int TELEPORT_DELAY = 40;
public AlchemyArrayEffectTeleport(String key)
{
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive)
{
return false;
}
@Override
public void onEntityCollidedWithBlock(IAlchemyArray array, World world, BlockPos pos, IBlockState state, Entity entity)
{
EnumFacing direction = array.getRotation();
teleportEntityInDirection(world, pos, entity, direction);
}
public void teleportEntityInDirection(World world, BlockPos currentPos, Entity entity, EnumFacing direction)
{
if (entity != null && entity.timeUntilPortal <= 0)
{
for (int i = 1; i <= MAX_SEARCH; i++)
{
BlockPos offsetPos = currentPos.offset(direction, i);
Block testBlock = world.getBlockState(offsetPos).getBlock();
if (testBlock == RegistrarBloodMagicBlocks.ALCHEMY_ARRAY)
{
int x = offsetPos.getX();
int y = offsetPos.getY();
int z = offsetPos.getZ();
entity.getEntityWorld().playSound(x, y, z, SoundEvents.ENTITY_ENDERMEN_TELEPORT, SoundCategory.AMBIENT, 1.0F, 1.0F, false);
entity.timeUntilPortal = TELEPORT_DELAY;
if (!world.isRemote)
{
if (entity instanceof EntityPlayer)
{
EntityPlayerMP player = (EntityPlayerMP) entity;
player.setPositionAndUpdate(x + 0.5, y + 0.5, z + 0.5);
player.getEntityWorld().updateEntityWithOptionalForce(player, false);
player.connection.sendPacket(new SPacketUpdateHealth(player.getHealth(), player.getFoodStats().getFoodLevel(), player.getFoodStats().getSaturationLevel()));
} else
{
WorldServer worldServer = (WorldServer) entity.getEntityWorld();
entity.setPosition(x + 0.5, y + 0.5, z + 0.5);
worldServer.resetUpdateEntityTick();
}
}
return;
}
}
}
}
@Override
public void writeToNBT(NBTTagCompound tag)
{
}
@Override
public void readFromNBT(NBTTagCompound tag)
{
}
@Override
public AlchemyArrayEffect getNewCopy()
{
return new AlchemyArrayEffectTeleport(key);
}
}

View file

@ -1,44 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.iface.IAlchemyArray;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
public class AlchemyArrayEffectUpdraft extends AlchemyArrayEffect {
public AlchemyArrayEffectUpdraft(String key) {
super(key);
}
@Override
public boolean update(TileEntity tile, int ticksActive) {
return false;
}
@Override
public void onEntityCollidedWithBlock(IAlchemyArray array, World world, BlockPos pos, IBlockState state, Entity entity) {
double motionY = 1.5;
entity.fallDistance = 0;
entity.motionY = motionY;
}
@Override
public void writeToNBT(NBTTagCompound tag) {
}
@Override
public void readFromNBT(NBTTagCompound tag) {
}
@Override
public AlchemyArrayEffect getNewCopy() {
return new AlchemyArrayEffectUpdraft(key);
}
}

View file

@ -1,151 +0,0 @@
package WayofTime.bloodmagic.alchemyArray;
import WayofTime.bloodmagic.tile.TileAlchemyArray;
import net.minecraft.client.Minecraft;
import net.minecraft.client.renderer.BufferBuilder;
import net.minecraft.client.renderer.GlStateManager;
import net.minecraft.client.renderer.Tessellator;
import net.minecraft.client.renderer.vertex.DefaultVertexFormats;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.ResourceLocation;
public class AlchemyCircleRenderer {
public final ResourceLocation arrayResource;
public float offsetFromFace = -0.9f;
public AlchemyCircleRenderer() {
this(new ResourceLocation("bloodmagic", "textures/models/AlchemyArrays/SightSigil.png"));
}
public AlchemyCircleRenderer(ResourceLocation arrayResource) {
this.arrayResource = arrayResource;
}
public float getRotation(float craftTime) {
float offset = 2;
if (craftTime >= offset) {
float modifier = (float) Math.pow(craftTime - offset, 1.5);
return modifier * 1f;
}
return 0;
}
public float getSecondaryRotation(float craftTime) {
float offset = 50;
if (craftTime >= offset) {
float modifier = (float) Math.pow(craftTime - offset, 1.7);
return modifier * 0.5f;
}
return 0;
}
public float getSizeModifier(float craftTime) {
if (craftTime >= 150 && craftTime <= 250) {
return (200 - craftTime) / 50f;
}
return 1.0f;
}
public float getVerticalOffset(float craftTime) {
if (craftTime >= 5) {
if (craftTime <= 40) {
return (float) ((-0.4) * Math.pow((craftTime - 5) / 35f, 3));
} else {
return -0.4f;
}
}
return 0;
}
public void renderAt(TileEntity tile, double x, double y, double z, float craftTime) {
if (!(tile instanceof TileAlchemyArray)) {
return;
}
TileAlchemyArray tileArray = (TileAlchemyArray) tile;
Tessellator tessellator = Tessellator.getInstance();
BufferBuilder wr = tessellator.getBuffer();
GlStateManager.pushMatrix();
// float rot = (float)(this.worldObj.provider.getWorldTime() % (360 /
// this.rotationspeed) * this.rotationspeed) + this.rotationspeed * f;
float rot = getRotation(craftTime);
float secondaryRot = getSecondaryRotation(craftTime);
float size = 1.0F * getSizeModifier(craftTime);
// Bind the texture to the circle
Minecraft.getMinecraft().renderEngine.bindTexture(arrayResource);
GlStateManager.disableCull();
GlStateManager.enableBlend();
GlStateManager.blendFunc(770, 1);
GlStateManager.translate(x, y, z);
// Specify which face this "circle" is located on
EnumFacing sideHit = EnumFacing.UP;
EnumFacing rotation = tileArray.getRotation();
GlStateManager.translate(sideHit.getFrontOffsetX() * offsetFromFace, sideHit.getFrontOffsetY() * offsetFromFace, sideHit.getFrontOffsetZ() * offsetFromFace);
switch (sideHit) {
case DOWN:
GlStateManager.translate(0, 0, 1);
GlStateManager.rotate(-90.0f, 1, 0, 0);
break;
case EAST:
GlStateManager.rotate(-90.0f, 0, 1, 0);
GlStateManager.translate(0, 0, -1);
break;
case NORTH:
break;
case SOUTH:
GlStateManager.rotate(180.0f, 0, 1, 0);
GlStateManager.translate(-1, 0, -1);
break;
case UP:
GlStateManager.translate(0, 1, 0);
GlStateManager.rotate(90.0f, 1, 0, 0);
break;
case WEST:
GlStateManager.translate(0, 0, 1);
GlStateManager.rotate(90.0f, 0, 1, 0);
break;
}
GlStateManager.pushMatrix();
GlStateManager.translate(0.5f, 0.5f, getVerticalOffset(craftTime));
GlStateManager.rotate(rotation.getHorizontalAngle() + 180, 0, 0, 1);
GlStateManager.pushMatrix();
GlStateManager.rotate(rot, 0, 0, 1);
GlStateManager.rotate(secondaryRot, 1, 0, 0);
GlStateManager.rotate(secondaryRot * 0.45812f, 0, 0, 1);
double var31 = 0.0D;
double var33 = 1.0D;
double var35 = 0;
double var37 = 1;
GlStateManager.color(1f, 1f, 1f, 1f);
wr.begin(7, DefaultVertexFormats.POSITION_TEX);
// wr.setBrightness(200);
wr.pos(size / 2f, size / 2f, 0.0D).tex(var33, var37).endVertex();
wr.pos(size / 2f, -size / 2f, 0.0D).tex(var33, var35).endVertex();
wr.pos(-size / 2f, -size / 2f, 0.0D).tex(var31, var35).endVertex();
wr.pos(-size / 2f, size / 2f, 0.0D).tex(var31, var37).endVertex();
tessellator.draw();
GlStateManager.popMatrix();
// GlStateManager.depthMask(true);
GlStateManager.disableBlend();
GlStateManager.enableCull();
// GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA);
GlStateManager.popMatrix();
GlStateManager.popMatrix();
}
}

View file

@ -1,55 +0,0 @@
package WayofTime.bloodmagic.altar;
import net.minecraft.util.math.BlockPos;
/**
* Used for building the altar structure.
*/
public class AltarComponent {
private final BlockPos offset;
private final ComponentType component;
private boolean upgradeSlot;
/**
* Sets a component location for the altar.
*
* @param offset - Where the block should be in relation to the Altar
* @param component - The type of Component the location should contain
*/
public AltarComponent(BlockPos offset, ComponentType component) {
this.offset = offset;
this.component = component;
}
/**
* Use for setting a location at which there must be a block, but the type
* of block does not matter.
*
* @param offset - Where the block should be in relation to the Altar
*/
public AltarComponent(BlockPos offset) {
this(offset, ComponentType.NOTAIR);
}
/**
* Sets the location to an upgrade slot.
*
* @return the current instance for further use.
*/
public AltarComponent setUpgradeSlot() {
this.upgradeSlot = true;
return this;
}
public BlockPos getOffset() {
return offset;
}
public boolean isUpgradeSlot() {
return upgradeSlot;
}
public ComponentType getComponent() {
return component;
}
}

View file

@ -1,24 +0,0 @@
package WayofTime.bloodmagic.altar;
import WayofTime.bloodmagic.block.enums.BloodRuneType;
import com.google.common.collect.Maps;
import java.util.EnumMap;
public class AltarUpgrade {
private final EnumMap<BloodRuneType, Integer> upgradeLevels;
public AltarUpgrade() {
this.upgradeLevels = Maps.newEnumMap(BloodRuneType.class);
}
public AltarUpgrade upgrade(BloodRuneType rune) {
upgradeLevels.compute(rune, (r, l) -> l == null ? 1 : l + 1);
return this;
}
public int getLevel(BloodRuneType rune) {
return upgradeLevels.getOrDefault(rune, 0);
}
}

View file

@ -1,86 +0,0 @@
package WayofTime.bloodmagic.altar;
import WayofTime.bloodmagic.api.impl.BloodMagicAPI;
import WayofTime.bloodmagic.block.BlockBloodRune;
import WayofTime.bloodmagic.tile.TileAltar;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import org.apache.commons.lang3.tuple.Pair;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import java.util.List;
public class AltarUtil {
@Nonnull
public static AltarTier getTier(World world, BlockPos pos) {
TileEntity tile = world.getTileEntity(pos);
if (!(tile instanceof TileAltar))
return AltarTier.ONE;
AltarTier lastCheck = AltarTier.ONE;
for (AltarTier tier : AltarTier.values()) {
for (AltarComponent component : tier.getAltarComponents()) {
BlockPos componentPos = pos.add(component.getOffset());
IBlockState worldState = world.getBlockState(componentPos);
if (worldState.getBlock() instanceof IAltarComponent)
if (((IAltarComponent) worldState.getBlock()).getType(world, worldState, componentPos) == component.getComponent())
continue;
if (component.getComponent() == ComponentType.NOTAIR && worldState.getMaterial() != Material.AIR && !worldState.getMaterial().isLiquid())
continue;
List<IBlockState> validStates = BloodMagicAPI.INSTANCE.getComponentStates(component.getComponent());
if (!validStates.contains(worldState))
return lastCheck;
}
lastCheck = tier;
}
return lastCheck;
}
@Nonnull
public static AltarUpgrade getUpgrades(World world, BlockPos pos, AltarTier currentTier) {
AltarUpgrade upgrades = new AltarUpgrade();
for (AltarComponent component : currentTier.getAltarComponents()) {
if (!component.isUpgradeSlot() || component.getComponent() != ComponentType.BLOODRUNE)
continue;
BlockPos componentPos = pos.add(component.getOffset());
IBlockState state = world.getBlockState(componentPos);
if (state.getBlock() instanceof BlockBloodRune)
upgrades.upgrade(((BlockBloodRune) state.getBlock()).getBloodRune(world, componentPos, state));
}
return upgrades;
}
@Nullable
public static Pair<BlockPos, ComponentType> getFirstMissingComponent(World world, BlockPos pos, int altarTier) {
if (altarTier >= AltarTier.MAXTIERS)
return null;
for (AltarTier tier : AltarTier.values()) {
for (AltarComponent component : tier.getAltarComponents()) {
BlockPos componentPos = pos.add(component.getOffset());
IBlockState worldState = world.getBlockState(componentPos);
if (component.getComponent() == ComponentType.NOTAIR && worldState.getMaterial() != Material.AIR && !worldState.getMaterial().isLiquid())
continue;
List<IBlockState> validStates = BloodMagicAPI.INSTANCE.getComponentStates(component.getComponent());
if (!validStates.contains(worldState))
return Pair.of(componentPos, component.getComponent());
}
}
return null;
}
}

View file

@ -1,711 +0,0 @@
package WayofTime.bloodmagic.altar;
import WayofTime.bloodmagic.api.event.BloodMagicCraftedEvent;
import WayofTime.bloodmagic.api.impl.BloodMagicAPI;
import WayofTime.bloodmagic.api.impl.recipe.RecipeBloodAltar;
import WayofTime.bloodmagic.block.enums.BloodRuneType;
import WayofTime.bloodmagic.core.data.Binding;
import WayofTime.bloodmagic.core.data.SoulTicket;
import WayofTime.bloodmagic.iface.IBindable;
import WayofTime.bloodmagic.util.Constants;
import WayofTime.bloodmagic.orb.BloodOrb;
import WayofTime.bloodmagic.orb.IBloodOrb;
import WayofTime.bloodmagic.util.helper.NetworkHelper;
import WayofTime.bloodmagic.block.BlockLifeEssence;
import WayofTime.bloodmagic.tile.TileAltar;
import com.google.common.base.Enums;
import net.minecraft.block.state.IBlockState;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumParticleTypes;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import net.minecraft.world.WorldServer;
import net.minecraftforge.common.MinecraftForge;
import net.minecraftforge.fluids.Fluid;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fluids.FluidTank;
import net.minecraftforge.fluids.capability.FluidTankPropertiesWrapper;
import net.minecraftforge.fluids.capability.IFluidHandler;
import net.minecraftforge.fluids.capability.IFluidTankProperties;
import net.minecraftforge.items.ItemHandlerHelper;
public class BloodAltar implements IFluidHandler
{
public boolean isActive;
protected FluidStack fluidOutput = new FluidStack(BlockLifeEssence.getLifeEssence(), 0);
protected FluidStack fluidInput = new FluidStack(BlockLifeEssence.getLifeEssence(), 0);
private TileAltar tileAltar;
private int internalCounter = 0;
private AltarTier altarTier = AltarTier.ONE;
private AltarUpgrade upgrade;
private int capacity = Fluid.BUCKET_VOLUME * 10;
private FluidStack fluid = new FluidStack(BlockLifeEssence.getLifeEssence(), 0);
private int liquidRequired; // mB
private boolean canBeFilled;
private int consumptionRate;
private int drainRate;
private float consumptionMultiplier;
private float efficiencyMultiplier;
private float sacrificeEfficiencyMultiplier;
private float selfSacrificeEfficiencyMultiplier;
private float capacityMultiplier = 1;
private float orbCapacityMultiplier;
private float dislocationMultiplier;
private int accelerationUpgrades;
private boolean isUpgraded;
private boolean isResultBlock;
private int bufferCapacity = Fluid.BUCKET_VOLUME;
private int progress;
private int lockdownDuration;
private int demonBloodDuration;
private int totalCharge = 0; //TODO save
private int chargingRate = 0;
private int chargingFrequency = 0;
private int maxCharge = 0;
private int cooldownAfterCrafting = 60;
private RecipeBloodAltar recipe;
private AltarTier currentTierDisplayed = AltarTier.ONE;
public BloodAltar(TileAltar tileAltar)
{
this.tileAltar = tileAltar;
}
public void readFromNBT(NBTTagCompound tagCompound)
{
if (!tagCompound.hasKey(Constants.NBT.EMPTY))
{
FluidStack fluid = FluidStack.loadFluidStackFromNBT(tagCompound);
if (fluid != null)
setMainFluid(fluid);
FluidStack fluidOut = new FluidStack(BlockLifeEssence.getLifeEssence(), tagCompound.getInteger(Constants.NBT.OUTPUT_AMOUNT));
setOutputFluid(fluidOut);
FluidStack fluidIn = new FluidStack(BlockLifeEssence.getLifeEssence(), tagCompound.getInteger(Constants.NBT.INPUT_AMOUNT));
setInputFluid(fluidIn);
}
internalCounter = tagCompound.getInteger("internalCounter");
altarTier = Enums.getIfPresent(AltarTier.class, tagCompound.getString(Constants.NBT.ALTAR_TIER)).or(AltarTier.ONE);
isActive = tagCompound.getBoolean(Constants.NBT.ALTAR_ACTIVE);
liquidRequired = tagCompound.getInteger(Constants.NBT.ALTAR_LIQUID_REQ);
canBeFilled = tagCompound.getBoolean(Constants.NBT.ALTAR_FILLABLE);
isUpgraded = tagCompound.getBoolean(Constants.NBT.ALTAR_UPGRADED);
consumptionRate = tagCompound.getInteger(Constants.NBT.ALTAR_CONSUMPTION_RATE);
drainRate = tagCompound.getInteger(Constants.NBT.ALTAR_DRAIN_RATE);
consumptionMultiplier = tagCompound.getFloat(Constants.NBT.ALTAR_CONSUMPTION_MULTIPLIER);
efficiencyMultiplier = tagCompound.getFloat(Constants.NBT.ALTAR_EFFICIENCY_MULTIPLIER);
selfSacrificeEfficiencyMultiplier = tagCompound.getFloat(Constants.NBT.ALTAR_SELF_SACRIFICE_MULTIPLIER);
sacrificeEfficiencyMultiplier = tagCompound.getFloat(Constants.NBT.ALTAR_SACRIFICE_MULTIPLIER);
capacityMultiplier = tagCompound.getFloat(Constants.NBT.ALTAR_CAPACITY_MULTIPLIER);
orbCapacityMultiplier = tagCompound.getFloat(Constants.NBT.ALTAR_ORB_CAPACITY_MULTIPLIER);
dislocationMultiplier = tagCompound.getFloat(Constants.NBT.ALTAR_DISLOCATION_MULTIPLIER);
capacity = tagCompound.getInteger(Constants.NBT.ALTAR_CAPACITY);
bufferCapacity = tagCompound.getInteger(Constants.NBT.ALTAR_BUFFER_CAPACITY);
progress = tagCompound.getInteger(Constants.NBT.ALTAR_PROGRESS);
isResultBlock = tagCompound.getBoolean(Constants.NBT.ALTAR_IS_RESULT_BLOCK);
lockdownDuration = tagCompound.getInteger(Constants.NBT.ALTAR_LOCKDOWN_DURATION);
accelerationUpgrades = tagCompound.getInteger(Constants.NBT.ALTAR_ACCELERATION_UPGRADES);
demonBloodDuration = tagCompound.getInteger(Constants.NBT.ALTAR_DEMON_BLOOD_DURATION);
cooldownAfterCrafting = tagCompound.getInteger(Constants.NBT.ALTAR_COOLDOWN_AFTER_CRAFTING);
chargingRate = tagCompound.getInteger(Constants.NBT.ALTAR_CHARGE_RATE);
chargingFrequency = tagCompound.getInteger(Constants.NBT.ALTAR_CHARGE_FREQUENCY);
totalCharge = tagCompound.getInteger(Constants.NBT.ALTAR_TOTAL_CHARGE);
maxCharge = tagCompound.getInteger(Constants.NBT.ALTAR_MAX_CHARGE);
currentTierDisplayed = Enums.getIfPresent(AltarTier.class, tagCompound.getString(Constants.NBT.ALTAR_CURRENT_TIER_DISPLAYED)).or(AltarTier.ONE);
}
public void writeToNBT(NBTTagCompound tagCompound)
{
if (fluid != null)
fluid.writeToNBT(tagCompound);
else
tagCompound.setString(Constants.NBT.EMPTY, "");
if (fluidOutput != null)
tagCompound.setInteger(Constants.NBT.OUTPUT_AMOUNT, fluidOutput.amount);
if (fluidInput != null)
tagCompound.setInteger(Constants.NBT.INPUT_AMOUNT, fluidInput.amount);
tagCompound.setInteger("internalCounter", internalCounter);
tagCompound.setString(Constants.NBT.ALTAR_TIER, altarTier.name());
tagCompound.setBoolean(Constants.NBT.ALTAR_ACTIVE, isActive);
tagCompound.setInteger(Constants.NBT.ALTAR_LIQUID_REQ, liquidRequired);
tagCompound.setBoolean(Constants.NBT.ALTAR_FILLABLE, canBeFilled);
tagCompound.setBoolean(Constants.NBT.ALTAR_UPGRADED, isUpgraded);
tagCompound.setInteger(Constants.NBT.ALTAR_CONSUMPTION_RATE, consumptionRate);
tagCompound.setInteger(Constants.NBT.ALTAR_DRAIN_RATE, drainRate);
tagCompound.setFloat(Constants.NBT.ALTAR_CONSUMPTION_MULTIPLIER, consumptionMultiplier);
tagCompound.setFloat(Constants.NBT.ALTAR_EFFICIENCY_MULTIPLIER, efficiencyMultiplier);
tagCompound.setFloat(Constants.NBT.ALTAR_SACRIFICE_MULTIPLIER, sacrificeEfficiencyMultiplier);
tagCompound.setFloat(Constants.NBT.ALTAR_SELF_SACRIFICE_MULTIPLIER, selfSacrificeEfficiencyMultiplier);
tagCompound.setBoolean(Constants.NBT.ALTAR_IS_RESULT_BLOCK, isResultBlock);
tagCompound.setFloat(Constants.NBT.ALTAR_CAPACITY_MULTIPLIER, capacityMultiplier);
tagCompound.setFloat(Constants.NBT.ALTAR_ORB_CAPACITY_MULTIPLIER, orbCapacityMultiplier);
tagCompound.setFloat(Constants.NBT.ALTAR_DISLOCATION_MULTIPLIER, dislocationMultiplier);
tagCompound.setInteger(Constants.NBT.ALTAR_CAPACITY, capacity);
tagCompound.setInteger(Constants.NBT.ALTAR_PROGRESS, progress);
tagCompound.setInteger(Constants.NBT.ALTAR_BUFFER_CAPACITY, bufferCapacity);
tagCompound.setInteger(Constants.NBT.ALTAR_LOCKDOWN_DURATION, lockdownDuration);
tagCompound.setInteger(Constants.NBT.ALTAR_ACCELERATION_UPGRADES, accelerationUpgrades);
tagCompound.setInteger(Constants.NBT.ALTAR_DEMON_BLOOD_DURATION, demonBloodDuration);
tagCompound.setInteger(Constants.NBT.ALTAR_COOLDOWN_AFTER_CRAFTING, cooldownAfterCrafting);
tagCompound.setInteger(Constants.NBT.ALTAR_CHARGE_RATE, chargingRate);
tagCompound.setInteger(Constants.NBT.ALTAR_CHARGE_FREQUENCY, chargingFrequency);
tagCompound.setInteger(Constants.NBT.ALTAR_TOTAL_CHARGE, totalCharge);
tagCompound.setInteger(Constants.NBT.ALTAR_MAX_CHARGE, maxCharge);
tagCompound.setString(Constants.NBT.ALTAR_CURRENT_TIER_DISPLAYED, currentTierDisplayed.name());
}
public void startCycle()
{
if (tileAltar.getWorld() != null)
tileAltar.getWorld().notifyBlockUpdate(tileAltar.getPos(), tileAltar.getWorld().getBlockState(tileAltar.getPos()), tileAltar.getWorld().getBlockState(tileAltar.getPos()), 3);
checkTier();
if ((fluid == null || fluid.amount <= 0) && totalCharge <= 0)
return;
if (!isActive)
progress = 0;
ItemStack input = tileAltar.getStackInSlot(0);
if (!input.isEmpty())
{
// Do recipes
RecipeBloodAltar recipe = BloodMagicAPI.INSTANCE.getRecipeRegistrar().getBloodAltar(input);
if (recipe != null)
{
if (recipe.getMinimumTier().ordinal() <= altarTier.ordinal())
{
this.isActive = true;
this.recipe = recipe;
this.liquidRequired = recipe.getSyphon();
this.consumptionRate = recipe.getConsumeRate();
this.drainRate = recipe.getDrainRate();
this.canBeFilled = false;
return;
}
} else if (input.getItem() instanceof IBloodOrb)
{
this.isActive = true;
this.canBeFilled = true;
return;
}
}
isActive = false;
}
public void update()
{
World world = tileAltar.getWorld();
BlockPos pos = tileAltar.getPos();
if (world.isRemote)
return;
// Used instead of the world time for checks that do not happen every tick
internalCounter++;
if (lockdownDuration > 0)
lockdownDuration--;
if (internalCounter % 20 == 0)
{
for (EnumFacing facing : EnumFacing.VALUES)
{
BlockPos newPos = pos.offset(facing);
IBlockState block = world.getBlockState(newPos);
block.getBlock().onNeighborChange(world, newPos, pos);
}
}
if (internalCounter % (Math.max(20 - this.accelerationUpgrades, 1)) == 0)
{
int syphonMax = (int) (20 * this.dislocationMultiplier);
int fluidInputted;
int fluidOutputted;
fluidInputted = Math.min(syphonMax, -this.fluid.amount + capacity);
fluidInputted = Math.min(this.fluidInput.amount, fluidInputted);
this.fluid.amount += fluidInputted;
this.fluidInput.amount -= fluidInputted;
fluidOutputted = Math.min(syphonMax, this.bufferCapacity - this.fluidOutput.amount);
fluidOutputted = Math.min(this.fluid.amount, fluidOutputted);
this.fluidOutput.amount += fluidOutputted;
this.fluid.amount -= fluidOutputted;
tileAltar.getWorld().notifyBlockUpdate(tileAltar.getPos(), tileAltar.getWorld().getBlockState(tileAltar.getPos()), tileAltar.getWorld().getBlockState(tileAltar.getPos()), 3);
}
if (internalCounter % this.getChargingFrequency() == 0 && !this.isActive)
{
int chargeInputted = Math.min(chargingRate, this.fluid.amount);
chargeInputted = Math.min(chargeInputted, maxCharge - totalCharge);
totalCharge += chargeInputted;
this.fluid.amount -= chargeInputted;
tileAltar.getWorld().notifyBlockUpdate(tileAltar.getPos(), tileAltar.getWorld().getBlockState(tileAltar.getPos()), tileAltar.getWorld().getBlockState(tileAltar.getPos()), 3);
}
if (internalCounter % 100 == 0 && (this.isActive || this.cooldownAfterCrafting <= 0))
startCycle();
updateAltar();
}
private void updateAltar()
{
if (!isActive)
{
if (cooldownAfterCrafting > 0)
cooldownAfterCrafting--;
return;
}
if (!canBeFilled && recipe == null)
{
startCycle();
return;
}
ItemStack input = tileAltar.getStackInSlot(0);
if (input.isEmpty())
return;
World world = tileAltar.getWorld();
BlockPos pos = tileAltar.getPos();
if (world.isRemote)
return;
if (!canBeFilled)
{
boolean hasOperated = false;
int stackSize = input.getCount();
if (totalCharge > 0)
{
int chargeDrained = Math.min(liquidRequired * stackSize - progress, totalCharge);
totalCharge -= chargeDrained;
progress += chargeDrained;
hasOperated = true;
}
if (fluid != null && fluid.amount >= 1)
{
int liquidDrained = Math.min((int) (altarTier.ordinal() >= 2 ? consumptionRate * (1 + consumptionMultiplier) : consumptionRate), fluid.amount);
if (liquidDrained > (liquidRequired * stackSize - progress))
liquidDrained = liquidRequired * stackSize - progress;
fluid.amount = fluid.amount - liquidDrained;
progress += liquidDrained;
hasOperated = true;
if (internalCounter % 4 == 0 && world instanceof WorldServer)
{
WorldServer server = (WorldServer) world;
server.spawnParticle(EnumParticleTypes.REDSTONE, pos.getX() + 0.5, pos.getY() + 1, pos.getZ() + 0.5, 1, 0.2, 0, 0.2, 0);
}
} else if (!hasOperated && progress > 0)
{
progress -= (int) (efficiencyMultiplier * drainRate);
if (internalCounter % 2 == 0 && world instanceof WorldServer)
{
WorldServer server = (WorldServer) world;
server.spawnParticle(EnumParticleTypes.SMOKE_NORMAL, pos.getX() + 0.5, pos.getY() + 1, pos.getZ() + 0.5, 1, 0.1, 0, 0.1, 0);
}
}
if (hasOperated)
{
if (progress >= liquidRequired * stackSize)
{
ItemStack result = ItemHandlerHelper.copyStackWithSize(recipe.getOutput(), stackSize);
BloodMagicCraftedEvent.Altar event = new BloodMagicCraftedEvent.Altar(result, input.copy());
MinecraftForge.EVENT_BUS.post(event);
tileAltar.setInventorySlotContents(0, event.getOutput());
progress = 0;
if (world instanceof WorldServer)
{
WorldServer server = (WorldServer) world;
server.spawnParticle(EnumParticleTypes.REDSTONE, pos.getX() + 0.5, pos.getY() + 1, pos.getZ() + 0.5, 40, 0.3, 0, 0.3, 0);
}
this.cooldownAfterCrafting = 30;
this.isActive = false;
}
}
} else
{
ItemStack contained = tileAltar.getStackInSlot(0);
if (contained.isEmpty() || !(contained.getItem() instanceof IBloodOrb) || !(contained.getItem() instanceof IBindable))
return;
BloodOrb orb = ((IBloodOrb) contained.getItem()).getOrb(contained);
Binding binding = ((IBindable) contained.getItem()).getBinding(contained);
if (binding == null || orb == null)
return;
if (fluid != null && fluid.amount >= 1)
{
int liquidDrained = Math.min((int) (altarTier.ordinal() >= 2 ? orb.getFillRate() * (1 + consumptionMultiplier) : orb.getFillRate()), fluid.amount);
int drain = NetworkHelper.getSoulNetwork(binding).add(SoulTicket.block(world, pos, liquidDrained), (int) (orb.getCapacity() * this.orbCapacityMultiplier));
fluid.amount = fluid.amount - drain;
if (drain > 0 && internalCounter % 4 == 0 && world instanceof WorldServer)
{
WorldServer server = (WorldServer) world;
server.spawnParticle(EnumParticleTypes.SPELL_WITCH, pos.getX() + 0.5, pos.getY() + 1, pos.getZ() + 0.5, 1, 0, 0, 0, 0.001);
}
}
}
tileAltar.getWorld().notifyBlockUpdate(tileAltar.getPos(), tileAltar.getWorld().getBlockState(tileAltar.getPos()), tileAltar.getWorld().getBlockState(tileAltar.getPos()), 3);
}
public void checkTier()
{
AltarTier tier = AltarUtil.getTier(tileAltar.getWorld(), tileAltar.getPos());
this.altarTier = tier;
upgrade = AltarUtil.getUpgrades(tileAltar.getWorld(), tileAltar.getPos(), tier);
if (tier.equals(currentTierDisplayed))
currentTierDisplayed = AltarTier.ONE;
if (tier.equals(AltarTier.ONE))
{
upgrade = null;
isUpgraded = false;
this.consumptionMultiplier = 0;
this.efficiencyMultiplier = 1;
this.sacrificeEfficiencyMultiplier = 0;
this.selfSacrificeEfficiencyMultiplier = 0;
this.capacityMultiplier = 1;
this.orbCapacityMultiplier = 1;
this.dislocationMultiplier = 1;
this.accelerationUpgrades = 0;
this.chargingFrequency = 20;
this.chargingRate = 0;
this.maxCharge = 0;
this.totalCharge = 0;
return;
} else if (!tier.equals(AltarTier.ONE))
{
this.isUpgraded = true;
this.accelerationUpgrades = upgrade.getLevel(BloodRuneType.ACCELERATION);
this.consumptionMultiplier = (float) (0.20 * upgrade.getLevel(BloodRuneType.SPEED));
this.efficiencyMultiplier = (float) Math.pow(0.85, upgrade.getLevel(BloodRuneType.EFFICIENCY));
this.sacrificeEfficiencyMultiplier = (float) (0.10 * upgrade.getLevel(BloodRuneType.SACRIFICE));
this.selfSacrificeEfficiencyMultiplier = (float) (0.10 * upgrade.getLevel(BloodRuneType.SELF_SACRIFICE));
this.capacityMultiplier = (float) ((1 * Math.pow(1.10, upgrade.getLevel(BloodRuneType.AUGMENTED_CAPACITY))) + 0.20 * upgrade.getLevel(BloodRuneType.CAPACITY));
this.dislocationMultiplier = (float) (Math.pow(1.2, upgrade.getLevel(BloodRuneType.DISPLACEMENT)));
this.orbCapacityMultiplier = (float) (1 + 0.02 * upgrade.getLevel(BloodRuneType.ORB));
this.chargingFrequency = Math.max(20 - accelerationUpgrades, 1);
this.chargingRate = (int) (10 * upgrade.getLevel(BloodRuneType.CHARGING) * (1 + consumptionMultiplier / 2));
this.maxCharge = (int) (Fluid.BUCKET_VOLUME * Math.max(0.5 * capacityMultiplier, 1) * upgrade.getLevel(BloodRuneType.CHARGING));
}
this.capacity = (int) (Fluid.BUCKET_VOLUME * 10 * capacityMultiplier);
this.bufferCapacity = (int) (Fluid.BUCKET_VOLUME * 1 * capacityMultiplier);
if (this.fluid.amount > this.capacity)
this.fluid.amount = this.capacity;
if (this.fluidOutput.amount > this.bufferCapacity)
this.fluidOutput.amount = this.bufferCapacity;
if (this.fluidInput.amount > this.bufferCapacity)
this.fluidInput.amount = this.bufferCapacity;
if (this.totalCharge > this.maxCharge)
this.totalCharge = this.maxCharge;
tileAltar.getWorld().notifyBlockUpdate(tileAltar.getPos(), tileAltar.getWorld().getBlockState(tileAltar.getPos()), tileAltar.getWorld().getBlockState(tileAltar.getPos()), 3);
}
public int fillMainTank(int amount)
{
int filledAmount = Math.min(capacity - fluid.amount, amount);
fluid.amount += filledAmount;
return filledAmount;
}
public void sacrificialDaggerCall(int amount, boolean isSacrifice)
{
if (this.lockdownDuration > 0)
{
int amt = (int) Math.min(bufferCapacity - fluidInput.amount, (isSacrifice ? 1 + sacrificeEfficiencyMultiplier : 1 + selfSacrificeEfficiencyMultiplier) * amount);
fluidInput.amount += amt;
} else
{
fluid.amount += Math.min(capacity - fluid.amount, (isSacrifice ? 1 + sacrificeEfficiencyMultiplier : 1 + selfSacrificeEfficiencyMultiplier) * amount);
}
}
public void setMainFluid(FluidStack fluid)
{
this.fluid = fluid;
}
public void setOutputFluid(FluidStack fluid)
{
this.fluidOutput = fluid;
}
public void setInputFluid(FluidStack fluid)
{
this.fluidInput = fluid;
}
public AltarUpgrade getUpgrade()
{
return upgrade;
}
public void setUpgrade(AltarUpgrade upgrade)
{
this.upgrade = upgrade;
}
public int getCapacity()
{
return capacity;
}
public FluidStack getFluid()
{
return fluid;
}
public int getFluidAmount()
{
return fluid.amount;
}
public int getCurrentBlood()
{
return getFluidAmount();
}
public AltarTier getTier()
{
return altarTier;
}
public void setTier(AltarTier tier)
{
this.altarTier = tier;
}
public int getProgress()
{
return progress;
}
public float getSacrificeMultiplier()
{
return sacrificeEfficiencyMultiplier;
}
public float getSelfSacrificeMultiplier()
{
return selfSacrificeEfficiencyMultiplier;
}
public float getOrbMultiplier()
{
return orbCapacityMultiplier;
}
public float getDislocationMultiplier()
{
return dislocationMultiplier;
}
public float getConsumptionMultiplier()
{
return consumptionMultiplier;
}
public float getConsumptionRate()
{
return consumptionRate;
}
public int getLiquidRequired()
{
return liquidRequired;
}
public int getBufferCapacity()
{
return bufferCapacity;
}
public boolean setCurrentTierDisplayed(AltarTier altarTier)
{
if (currentTierDisplayed == altarTier)
return false;
else
currentTierDisplayed = altarTier;
return true;
}
public void addToDemonBloodDuration(int dur)
{
this.demonBloodDuration += dur;
}
public boolean hasDemonBlood()
{
return this.demonBloodDuration > 0;
}
public void decrementDemonBlood()
{
this.demonBloodDuration = Math.max(0, this.demonBloodDuration - 1);
}
public void setActive()
{
if (tileAltar.getStackInSlot(0).isEmpty())
{
isActive = false;
}
}
public boolean isActive()
{
return isActive;
}
public void requestPauseAfterCrafting(int amount)
{
if (this.isActive)
{
this.cooldownAfterCrafting = amount;
}
}
public int getChargingRate()
{
return chargingRate;
}
public int getTotalCharge()
{
return totalCharge;
}
public int getChargingFrequency()
{
return chargingFrequency == 0 ? 1 : chargingFrequency;
}
@Override
public int fill(FluidStack resource, boolean doFill)
{
if (resource == null || resource.getFluid() != BlockLifeEssence.getLifeEssence())
{
return 0;
}
if (!doFill)
{
if (fluidInput == null)
{
return Math.min(bufferCapacity, resource.amount);
}
if (!fluidInput.isFluidEqual(resource))
{
return 0;
}
return Math.min(bufferCapacity - fluidInput.amount, resource.amount);
}
if (fluidInput == null)
{
fluidInput = new FluidStack(resource, Math.min(bufferCapacity, resource.amount));
return fluidInput.amount;
}
if (!fluidInput.isFluidEqual(resource))
{
return 0;
}
int filled = bufferCapacity - fluidInput.amount;
if (resource.amount < filled)
{
fluidInput.amount += resource.amount;
filled = resource.amount;
} else
{
fluidInput.amount = bufferCapacity;
}
return filled;
}
@Override
public FluidStack drain(FluidStack resource, boolean doDrain)
{
if (resource == null || !resource.isFluidEqual(fluidOutput))
{
return null;
}
return drain(resource.amount, doDrain);
}
@Override
public FluidStack drain(int maxDrain, boolean doDrain)
{
if (fluidOutput == null)
{
return null;
}
int drained = maxDrain;
if (fluidOutput.amount < drained)
{
drained = fluidOutput.amount;
}
FluidStack stack = new FluidStack(fluidOutput, drained);
if (doDrain)
{
fluidOutput.amount -= drained;
}
return stack;
}
@Override
public IFluidTankProperties[] getTankProperties()
{
return new IFluidTankProperties[] { new FluidTankPropertiesWrapper(new FluidTank(fluid, capacity)) };
}
public AltarTier getCurrentTierDisplayed()
{
return currentTierDisplayed;
}
}

View file

@ -1,27 +0,0 @@
package WayofTime.bloodmagic.altar;
import java.util.Locale;
/**
* List of different components used to construct different tiers of altars.
*/
public enum ComponentType {
GLOWSTONE,
BLOODSTONE,
BEACON,
BLOODRUNE,
CRYSTAL,
NOTAIR;
public static final ComponentType[] VALUES = values();
private static final String BASE = "chat.bloodmagic.altar.comp.";
private String key;
ComponentType() {
this.key = BASE + name().toLowerCase(Locale.ENGLISH);
}
public String getKey() {
return key;
}
}

View file

@ -1,12 +0,0 @@
package WayofTime.bloodmagic.altar;
import net.minecraft.block.state.IBlockState;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public interface IAltarComponent {
@Nullable
ComponentType getType(World world, IBlockState state, BlockPos pos);
}

View file

@ -1,8 +0,0 @@
package WayofTime.bloodmagic.altar;
/**
* Any item that implements this interface will not be pulled into the Altar on
* right click.
*/
public interface IAltarManipulator {
}

View file

@ -1,54 +0,0 @@
package WayofTime.bloodmagic.altar;
public interface IBloodAltar {
int getCapacity();
int getCurrentBlood();
AltarTier getTier();
int getProgress();
float getSacrificeMultiplier();
float getSelfSacrificeMultiplier();
float getOrbMultiplier();
float getDislocationMultiplier();
float getConsumptionMultiplier();
float getConsumptionRate();
int getChargingRate();
int getChargingFrequency();
int getTotalCharge();
int getLiquidRequired();
int getBufferCapacity();
void sacrificialDaggerCall(int amount, boolean isSacrifice);
void startCycle();
void checkTier();
boolean isActive();
void setActive();
int fillMainTank(int amount);
/**
* Will set the altar to initiate a cooldown cycle after it crafts before
* starting to craft again, giving the user time to interact with the altar.
* This can only be set while the altar is not active.
*
* @param cooldown - How long the cooldown should last
*/
void requestPauseAfterCrafting(int cooldown);
}

View file

@ -1,156 +0,0 @@
package WayofTime.bloodmagic.api.impl;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.ConfigHandler;
import WayofTime.bloodmagic.api.BloodMagicPlugin;
import WayofTime.bloodmagic.api.IBloodMagicAPI;
import WayofTime.bloodmagic.api.IBloodMagicPlugin;
import WayofTime.bloodmagic.altar.ComponentType;
import WayofTime.bloodmagic.api.IBloodMagicRecipeRegistrar;
import WayofTime.bloodmagic.block.BlockBloodRune;
import WayofTime.bloodmagic.block.BlockDecorative;
import WayofTime.bloodmagic.block.enums.BloodRuneType;
import WayofTime.bloodmagic.block.enums.EnumDecorative;
import WayofTime.bloodmagic.core.RegistrarBloodMagicBlocks;
import WayofTime.bloodmagic.core.RegistrarBloodMagicRecipes;
import WayofTime.bloodmagic.incense.EnumTranquilityType;
import WayofTime.bloodmagic.incense.TranquilityStack;
import WayofTime.bloodmagic.util.StateUtil;
import net.minecraft.block.Block;
import net.minecraft.block.properties.IProperty;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.init.Blocks;
import net.minecraft.util.ResourceLocation;
import net.minecraftforge.fml.common.registry.EntityEntry;
import net.minecraftforge.fml.common.registry.ForgeRegistries;
@BloodMagicPlugin
public class BloodMagicCorePlugin implements IBloodMagicPlugin
{
@Override
public void register(IBloodMagicAPI apiInterface)
{
BloodMagicAPI api = (BloodMagicAPI) apiInterface;
// Add forced blacklistings
api.getBlacklist().addTeleposer(RegistrarBloodMagicBlocks.INPUT_ROUTING_NODE);
api.getBlacklist().addTransposition(RegistrarBloodMagicBlocks.INPUT_ROUTING_NODE);
api.getBlacklist().addTeleposer(RegistrarBloodMagicBlocks.OUTPUT_ROUTING_NODE);
api.getBlacklist().addTransposition(RegistrarBloodMagicBlocks.OUTPUT_ROUTING_NODE);
api.getBlacklist().addTeleposer(RegistrarBloodMagicBlocks.ITEM_ROUTING_NODE);
api.getBlacklist().addTransposition(RegistrarBloodMagicBlocks.ITEM_ROUTING_NODE);
api.getBlacklist().addTeleposer(RegistrarBloodMagicBlocks.MASTER_ROUTING_NODE);
api.getBlacklist().addTransposition(RegistrarBloodMagicBlocks.MASTER_ROUTING_NODE);
api.getBlacklist().addTeleposer(RegistrarBloodMagicBlocks.DEMON_CRYSTAL);
api.getBlacklist().addTransposition(RegistrarBloodMagicBlocks.DEMON_CRYSTAL);
api.getBlacklist().addTeleposer(RegistrarBloodMagicBlocks.INVERSION_PILLAR);
api.getBlacklist().addTransposition(RegistrarBloodMagicBlocks.INVERSION_PILLAR);
api.getBlacklist().addWellOfSuffering(new ResourceLocation("armor_stand"));
api.getBlacklist().addWellOfSuffering(new ResourceLocation(BloodMagic.MODID, "sentient_specter"));
api.getValueManager().setSacrificialValue(new ResourceLocation("armor_stand"), 0);
api.getValueManager().setSacrificialValue(new ResourceLocation(BloodMagic.MODID, "sentient_specter"), 0);
api.getValueManager().setTranquility(Blocks.LAVA, new TranquilityStack(EnumTranquilityType.LAVA, 1.2D));
api.getValueManager().setTranquility(Blocks.FLOWING_LAVA, new TranquilityStack(EnumTranquilityType.LAVA, 1.2D));
api.getValueManager().setTranquility(Blocks.WATER, new TranquilityStack(EnumTranquilityType.WATER, 1.0D));
api.getValueManager().setTranquility(Blocks.FLOWING_WATER, new TranquilityStack(EnumTranquilityType.WATER, 1.0D));
api.getValueManager().setTranquility(RegistrarBloodMagicBlocks.LIFE_ESSENCE, new TranquilityStack(EnumTranquilityType.WATER, 1.5D));
api.getValueManager().setTranquility(Blocks.NETHERRACK, new TranquilityStack(EnumTranquilityType.FIRE, 0.5D));
api.getValueManager().setTranquility(Blocks.DIRT, new TranquilityStack(EnumTranquilityType.EARTHEN, 0.25D));
api.getValueManager().setTranquility(Blocks.FARMLAND, new TranquilityStack(EnumTranquilityType.EARTHEN, 1.0D));
api.getValueManager().setTranquility(Blocks.POTATOES, new TranquilityStack(EnumTranquilityType.CROP, 1.0D));
api.getValueManager().setTranquility(Blocks.CARROTS, new TranquilityStack(EnumTranquilityType.CROP, 1.0D));
api.getValueManager().setTranquility(Blocks.WHEAT, new TranquilityStack(EnumTranquilityType.CROP, 1.0D));
api.getValueManager().setTranquility(Blocks.NETHER_WART, new TranquilityStack(EnumTranquilityType.CROP, 1.0D));
api.getValueManager().setTranquility(Blocks.BEETROOTS, new TranquilityStack(EnumTranquilityType.CROP, 1.0D));
handleConfigValues(api);
// Add standard blocks for altar components
api.registerAltarComponent(Blocks.GLOWSTONE.getDefaultState(), ComponentType.GLOWSTONE.name());
api.registerAltarComponent(Blocks.SEA_LANTERN.getDefaultState(), ComponentType.GLOWSTONE.name());
api.registerAltarComponent(Blocks.BEACON.getDefaultState(), ComponentType.BEACON.name());
BlockDecorative decorative = (BlockDecorative) RegistrarBloodMagicBlocks.DECORATIVE_BRICK;
api.registerAltarComponent(decorative.getDefaultState().withProperty(decorative.getProperty(), EnumDecorative.BLOODSTONE_BRICK), ComponentType.BLOODSTONE.name());
api.registerAltarComponent(decorative.getDefaultState().withProperty(decorative.getProperty(), EnumDecorative.BLOODSTONE_TILE), ComponentType.BLOODSTONE.name());
api.registerAltarComponent(decorative.getDefaultState().withProperty(decorative.getProperty(), EnumDecorative.CRYSTAL_BRICK), ComponentType.CRYSTAL.name());
api.registerAltarComponent(decorative.getDefaultState().withProperty(decorative.getProperty(), EnumDecorative.CRYSTAL_TILE), ComponentType.CRYSTAL.name());
BlockBloodRune bloodRune = (BlockBloodRune) RegistrarBloodMagicBlocks.BLOOD_RUNE;
for (BloodRuneType runeType : BloodRuneType.values())
api.registerAltarComponent(bloodRune.getDefaultState().withProperty(bloodRune.getProperty(), runeType), ComponentType.BLOODRUNE.name());
}
@Override
public void registerRecipes(IBloodMagicRecipeRegistrar recipeRegistrar)
{
RegistrarBloodMagicRecipes.registerAltarRecipes((BloodMagicRecipeRegistrar) recipeRegistrar);
RegistrarBloodMagicRecipes.registerAlchemyTableRecipes((BloodMagicRecipeRegistrar) recipeRegistrar);
RegistrarBloodMagicRecipes.registerTartaricForgeRecipes((BloodMagicRecipeRegistrar) recipeRegistrar);
RegistrarBloodMagicRecipes.registerAlchemyArrayRecipes((BloodMagicRecipeRegistrar) recipeRegistrar);
RegistrarBloodMagicRecipes.registerSacrificeCraftRecipes((BloodMagicRecipeRegistrar) recipeRegistrar);
}
private static void handleConfigValues(BloodMagicAPI api)
{
for (String value : ConfigHandler.values.sacrificialValues)
{
String[] split = value.split(";");
if (split.length != 2) // Not valid format
continue;
api.getValueManager().setSacrificialValue(new ResourceLocation(split[0]), Integer.parseInt(split[1]));
}
for (String value : ConfigHandler.blacklist.teleposer)
{
EntityEntry entityEntry = ForgeRegistries.ENTITIES.getValue(new ResourceLocation(value));
if (entityEntry == null)
{ // It's not an entity (or at least not a valid one), so let's try a block.
String[] blockData = value.split("\\[");
Block block = ForgeRegistries.BLOCKS.getValue(new ResourceLocation(blockData[0]));
if (block == Blocks.AIR || block == null) // Not a valid block either
continue;
if (blockData.length > 1)
{ // We have properties listed, so let's build a state.
api.getBlacklist().addTeleposer(StateUtil.parseState(value));
continue;
}
api.getBlacklist().addTeleposer(block);
continue;
}
api.getBlacklist().addTeleposer(entityEntry.getRegistryName());
}
for (String value : ConfigHandler.blacklist.transposer)
{
String[] blockData = value.split("\\[");
Block block = ForgeRegistries.BLOCKS.getValue(new ResourceLocation(blockData[0]));
if (block == Blocks.AIR || block == null) // Not a valid block
continue;
if (blockData.length > 1)
{ // We have properties listed, so let's build a state.
api.getBlacklist().addTeleposer(StateUtil.parseState(value));
continue;
}
api.getBlacklist().addTeleposer(block);
}
for (String value : ConfigHandler.blacklist.wellOfSuffering)
{
EntityEntry entityEntry = ForgeRegistries.ENTITIES.getValue(new ResourceLocation(value));
if (entityEntry == null) // Not a valid entity
continue;
api.getBlacklist().addWellOfSuffering(entityEntry.getRegistryName());
}
}
}

View file

@ -1,62 +0,0 @@
package WayofTime.bloodmagic.api.impl;
import WayofTime.bloodmagic.api.IBloodMagicValueManager;
import WayofTime.bloodmagic.incense.EnumTranquilityType;
import WayofTime.bloodmagic.incense.TranquilityStack;
import WayofTime.bloodmagic.util.BMLog;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Maps;
import net.minecraft.block.Block;
import net.minecraft.block.state.IBlockState;
import net.minecraft.util.ResourceLocation;
import javax.annotation.Nonnull;
import java.util.Map;
public class BloodMagicValueManager implements IBloodMagicValueManager {
private final Map<ResourceLocation, Integer> sacrificial;
private final Map<IBlockState, TranquilityStack> tranquility;
public BloodMagicValueManager() {
this.sacrificial = Maps.newHashMap();
this.tranquility = Maps.newHashMap();
}
@Override
public void setSacrificialValue(@Nonnull ResourceLocation entityId, int value) {
BMLog.API_VERBOSE.info("Value Manager: Set sacrificial value of {} to {}.", entityId, value);
sacrificial.put(entityId, value);
}
@Override
public void setTranquility(@Nonnull IBlockState state, @Nonnull String tranquilityType, double value) {
EnumTranquilityType tranquility = null;
for (EnumTranquilityType type : EnumTranquilityType.values()) {
if (type.name().equalsIgnoreCase(tranquilityType)) {
tranquility = type;
break;
}
}
if (tranquility != null) {
BMLog.API_VERBOSE.info("Value Manager: Set tranquility value of {} to {} @ {}", state, tranquilityType, value);
this.tranquility.put(state, new TranquilityStack(tranquility, value));
} else BMLog.API.warn("Invalid tranquility type: {}.", tranquilityType);
}
public void setTranquility(Block block, TranquilityStack tranquilityStack) {
for (IBlockState state : block.getBlockState().getValidStates()) {
BMLog.API_VERBOSE.info("Value Manager: Set tranquility value of {} to {} @ {}", state, tranquilityStack.type, tranquilityStack.value);
tranquility.put(state, tranquilityStack);
}
}
public Map<ResourceLocation, Integer> getSacrificial() {
return ImmutableMap.copyOf(sacrificial);
}
public Map<IBlockState, TranquilityStack> getTranquility() {
return ImmutableMap.copyOf(tranquility);
}
}

View file

@ -1,143 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.core.RegistrarBloodMagicItems;
import WayofTime.bloodmagic.tile.TileAlchemyArray;
import WayofTime.bloodmagic.util.Utils;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.RayTraceResult;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import javax.annotation.Nullable;
import java.util.List;
import java.util.Random;
public class BlockAlchemyArray extends Block {
protected static final AxisAlignedBB ARRAY_AABB = new AxisAlignedBB(0, 0, 0, 1, 0.1, 1);
public BlockAlchemyArray() {
super(Material.CLOTH);
setUnlocalizedName(BloodMagic.MODID + ".alchemyArray");
setHardness(0.1f);
}
@Override
public void addCollisionBoxToList(IBlockState state, World worldIn, BlockPos pos, AxisAlignedBB entityBox, List<AxisAlignedBB> collidingBoxes, @Nullable Entity entityIn, boolean p_185477_7_) {
// No-op
}
@Override
public void onEntityCollidedWithBlock(World world, BlockPos pos, IBlockState state, Entity entity) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileAlchemyArray) {
((TileAlchemyArray) tile).onEntityCollidedWithBlock(state, entity);
}
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
return ARRAY_AABB;
}
@Override
@SideOnly(Side.CLIENT)
public BlockRenderLayer getBlockLayer() {
return BlockRenderLayer.CUTOUT;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.INVISIBLE;
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
//TODO: Right click should rotate it
TileAlchemyArray array = (TileAlchemyArray) world.getTileEntity(pos);
if (array == null || player.isSneaking())
return false;
ItemStack playerItem = player.getHeldItem(hand);
if (!playerItem.isEmpty()) {
if (array.getStackInSlot(0).isEmpty()) {
Utils.insertItemToTile(array, player, 0);
} else if (!array.getStackInSlot(0).isEmpty()) {
Utils.insertItemToTile(array, player, 1);
array.attemptCraft();
} else {
return true;
}
}
world.notifyBlockUpdate(pos, state, state, 3);
return true;
}
@Override
public ItemStack getPickBlock(IBlockState state, RayTraceResult target, World world, BlockPos pos, EntityPlayer player) {
return new ItemStack(RegistrarBloodMagicItems.ARCANE_ASHES);
}
@Override
public int quantityDropped(Random random) {
return 0;
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileAlchemyArray alchemyArray = (TileAlchemyArray) world.getTileEntity(blockPos);
if (alchemyArray != null)
alchemyArray.dropItems();
super.breakBlock(world, blockPos, blockState);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileAlchemyArray();
}
}

View file

@ -1,158 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.util.Constants;
import WayofTime.bloodmagic.item.block.ItemBlockAlchemyTable;
import WayofTime.bloodmagic.tile.TileAlchemyTable;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyBool;
import net.minecraft.block.properties.PropertyEnum;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemBlock;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockAlchemyTable extends Block implements IBMBlock {
public static final PropertyBool INVISIBLE = PropertyBool.create("invisible");
public static final PropertyEnum<EnumFacing> DIRECTION = PropertyEnum.create("direction", EnumFacing.class);
public BlockAlchemyTable() {
super(Material.ROCK);
// this.setDefaultState(this.blockState.getBaseState().withProperty(DIRECTION, EnumFacing.DOWN).withProperty(INVISIBLE, false));
setUnlocalizedName(BloodMagic.MODID + ".alchemyTable");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 0);
// setBlockBounds(0.3F, 0F, 0.3F, 0.72F, 1F, 0.72F);
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public boolean canRenderInLayer(IBlockState state, BlockRenderLayer layer) {
return layer == BlockRenderLayer.CUTOUT_MIPPED || layer == BlockRenderLayer.TRANSLUCENT;
}
@Override
public IBlockState getStateFromMeta(int meta) {
return this.getDefaultState();
}
/**
* Convert the BlockState into the correct metadata value
*/
@Override
public int getMetaFromState(IBlockState state) {
return 0;
}
@Override
public IBlockState getActualState(IBlockState state, IBlockAccess world, BlockPos pos) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileAlchemyTable) {
return state.withProperty(INVISIBLE, ((TileAlchemyTable) tile).isInvisible()).withProperty(DIRECTION, ((TileAlchemyTable) tile).getDirection());
}
return state.withProperty(INVISIBLE, false);
}
@Override
protected BlockStateContainer createBlockState() {
return new BlockStateContainer(this, DIRECTION, INVISIBLE);
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
BlockPos position = pos;
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileAlchemyTable) {
if (((TileAlchemyTable) tile).isSlave()) {
position = ((TileAlchemyTable) tile).getConnectedPos();
tile = world.getTileEntity(position);
if (!(tile instanceof TileAlchemyTable)) {
return false;
}
}
}
player.openGui(BloodMagic.instance, Constants.Gui.ALCHEMY_TABLE_GUI, world, position.getX(), position.getY(), position.getZ());
return true;
}
@Override
public void breakBlock(World world, BlockPos pos, IBlockState blockState) {
TileAlchemyTable tile = (TileAlchemyTable) world.getTileEntity(pos);
if (tile != null && !tile.isSlave()) {
tile.dropItems();
}
super.breakBlock(world, pos, blockState);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileAlchemyTable();
}
@Override
public void neighborChanged(IBlockState state, World world, BlockPos pos, Block blockIn, BlockPos fromPos) {
TileAlchemyTable tile = (TileAlchemyTable) world.getTileEntity(pos);
if (tile != null) {
BlockPos connectedPos = tile.getConnectedPos();
TileEntity connectedTile = world.getTileEntity(connectedPos);
if (!(connectedTile instanceof TileAlchemyTable && ((TileAlchemyTable) connectedTile).getConnectedPos().equals(pos))) {
this.breakBlock(world, pos, state);
world.setBlockToAir(pos);
}
}
}
@Override
public ItemBlock getItem() {
return new ItemBlockAlchemyTable(this);
}
}

View file

@ -1,173 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.altar.*;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.core.data.Binding;
import WayofTime.bloodmagic.core.data.SoulNetwork;
import WayofTime.bloodmagic.iface.IAltarReader;
import WayofTime.bloodmagic.iface.IBindable;
import WayofTime.bloodmagic.iface.IDocumentedBlock;
import WayofTime.bloodmagic.orb.BloodOrb;
import WayofTime.bloodmagic.orb.IBloodOrb;
import WayofTime.bloodmagic.tile.TileAltar;
import WayofTime.bloodmagic.util.Utils;
import WayofTime.bloodmagic.util.helper.NetworkHelper;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemBlock;
import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.text.ITextComponent;
import net.minecraft.util.text.TextComponentTranslation;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import org.apache.commons.lang3.tuple.Pair;
import javax.annotation.Nullable;
import java.util.ArrayList;
import java.util.List;
public class BlockAltar extends Block implements IVariantProvider, IDocumentedBlock, IBMBlock {
public BlockAltar() {
super(Material.ROCK);
setUnlocalizedName(BloodMagic.MODID + ".altar");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 1);
}
@Override
public boolean hasComparatorInputOverride(IBlockState state) {
return true;
}
@Override
public int getComparatorInputOverride(IBlockState state, World world, BlockPos pos) {
if (world.isRemote)
return 0;
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileAltar) {
TileAltar altar = (TileAltar) tile;
ItemStack orbStack = altar.getStackInSlot(0);
if (world.getBlockState(pos.down()).getBlock() instanceof BlockDecorative) {
if (orbStack.getItem() instanceof IBloodOrb && orbStack.getItem() instanceof IBindable) {
BloodOrb orb = ((IBloodOrb) orbStack.getItem()).getOrb(orbStack);
Binding binding = ((IBindable) orbStack.getItem()).getBinding(orbStack);
if (orb != null && binding != null) {
SoulNetwork soulNetwork = NetworkHelper.getSoulNetwork(binding);
int maxEssence = orb.getCapacity();
int currentEssence = soulNetwork.getCurrentEssence();
int level = currentEssence * 15 / maxEssence;
return Math.min(15, level) % 16;
}
}
} else {
int maxEssence = altar.getCapacity();
int currentEssence = altar.getCurrentBlood();
int level = currentEssence * 15 / maxEssence;
return Math.min(15, level) % 16;
}
}
return 0;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return true;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
TileAltar altar = (TileAltar) world.getTileEntity(pos);
if (altar == null || player.isSneaking())
return false;
ItemStack playerItem = player.getHeldItem(hand);
if (playerItem.getItem() instanceof IAltarReader || playerItem.getItem() instanceof IAltarManipulator) {
playerItem.getItem().onItemRightClick(world, player, hand);
return true;
}
if (Utils.insertItemToTile(altar, player))
altar.startCycle();
else
altar.setActive();
world.notifyBlockUpdate(pos, state, state, 3);
return true;
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileEntity tile = world.getTileEntity(blockPos);
if (tile instanceof TileAltar)
((TileAltar) tile).dropItems();
super.breakBlock(world, blockPos, blockState);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileAltar();
}
// IDocumentedBlock
@Override
public List<ITextComponent> getDocumentation(EntityPlayer player, World world, BlockPos pos, IBlockState state) {
List<ITextComponent> docs = new ArrayList<>();
IBloodAltar altar = ((IBloodAltar) world.getTileEntity(pos));
Pair<BlockPos, ComponentType> missingBlock = AltarUtil.getFirstMissingComponent(world, pos, altar.getTier().toInt());
if (missingBlock != null)
docs.add(new TextComponentTranslation("chat.bloodmagic.altar.nextTier", new TextComponentTranslation(missingBlock.getRight().getKey()), Utils.prettifyBlockPosString(missingBlock.getLeft())));
return docs;
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
}

View file

@ -1,112 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.core.RegistrarBloodMagicItems;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.client.Minecraft;
import net.minecraft.client.entity.EntityPlayerSP;
import net.minecraft.client.particle.ParticleManager;
import net.minecraft.item.ItemStack;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumHand;
import net.minecraft.util.EnumParticleTypes;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import javax.annotation.Nullable;
import java.util.Random;
public class BlockBloodLight extends Block {
protected static final AxisAlignedBB AABB = new AxisAlignedBB(0.4, 0.4, 0.4, 0.6, 0.6, 0.6);
public BlockBloodLight() {
super(Material.CLOTH);
setUnlocalizedName(BloodMagic.MODID + ".bloodLight");
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
return AABB;
}
@Nullable
@Override
public AxisAlignedBB getCollisionBoundingBox(IBlockState blockState, IBlockAccess worldIn, BlockPos pos) {
return NULL_AABB;
}
@Override
public boolean isReplaceable(IBlockAccess world, BlockPos pos) {
return true;
}
@Override
@SideOnly(Side.CLIENT)
public BlockRenderLayer getBlockLayer() {
return BlockRenderLayer.CUTOUT;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public int getLightValue(IBlockState state) {
return 15;
}
@Override
@SideOnly(Side.CLIENT)
public boolean addDestroyEffects(World world, BlockPos pos, ParticleManager particleManager) {
if (world.getBlockState(pos).getBlock() == this) {
Random random = new Random();
particleManager.spawnEffectParticle(EnumParticleTypes.REDSTONE.getParticleID(), pos.getX() + 0.5D + random.nextGaussian() / 8, pos.getY() + 0.5D, pos.getZ() + 0.5D + random.nextGaussian() / 8, 0, 0, 0);
}
return true;
}
@Override
@SideOnly(Side.CLIENT)
public void randomDisplayTick(IBlockState state, World world, BlockPos pos, Random rand) {
EntityPlayerSP player = Minecraft.getMinecraft().player;
if (rand.nextInt(3) != 0) {
world.spawnParticle(EnumParticleTypes.REDSTONE, pos.getX() + 0.5D + rand.nextGaussian() / 8, pos.getY() + 0.5D, pos.getZ() + 0.5D + rand.nextGaussian() / 8, 0, 0, 0, 0);
ItemStack heldItem = player.getHeldItem(EnumHand.MAIN_HAND);
if (heldItem.isEmpty() || heldItem.getItem() != RegistrarBloodMagicItems.SIGIL_BLOOD_LIGHT)
return;
for (int i = 0; i < 8; i++)
world.spawnParticle(EnumParticleTypes.REDSTONE, pos.getX() + 0.5D + rand.nextGaussian() / 8, pos.getY() + 0.5D, pos.getZ() + 0.5D + rand.nextGaussian() / 8, 0, 0, 0, 0);
}
}
@Override
public int quantityDropped(Random par1Random) {
return 0;
}
}

View file

@ -1,44 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.BloodRuneType;
import WayofTime.bloodmagic.iface.IBloodRune;
import WayofTime.bloodmagic.util.helper.TextHelper;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.client.util.ITooltipFlag;
import net.minecraft.item.ItemStack;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nullable;
import java.util.List;
public class BlockBloodRune extends BlockEnum<BloodRuneType> implements IBloodRune {
public BlockBloodRune() {
super(Material.ROCK, BloodRuneType.class);
setUnlocalizedName(BloodMagic.MODID + ".rune.");
setCreativeTab(BloodMagic.TAB_BM);
setSoundType(SoundType.STONE);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 2);
}
@Nullable
@Override
public BloodRuneType getBloodRune(IBlockAccess world, BlockPos pos, IBlockState state) {
return state.getValue(getProperty());
}
@Override
public void addInformation(ItemStack stack, World world, List<String> tooltip, ITooltipFlag tooltipFlag) {
tooltip.add(TextHelper.localizeEffect("tooltip.bloodmagic.decoration.safe"));
super.addInformation(stack, world, tooltip, tooltipFlag);
}
}

View file

@ -1,195 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockInteger;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.item.block.ItemBlockBloodTank;
import WayofTime.bloodmagic.tile.TileBloodTank;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemBlock;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.NonNullList;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.RayTraceResult;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fluids.FluidUtil;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
public class BlockBloodTank extends BlockInteger implements IVariantProvider, IBMBlock {
public static final AxisAlignedBB BOX = new AxisAlignedBB(0.25, 0, 0.25, 0.75, 0.8, 0.75);
public BlockBloodTank() {
super(Material.IRON, TileBloodTank.CAPACITIES.length - 1, "tier");
setUnlocalizedName(BloodMagic.MODID + ".bloodTank");
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.GLASS);
setHarvestLevel("pickaxe", 1);
setCreativeTab(BloodMagic.TAB_BM);
setLightOpacity(0);
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
return BOX;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
@SideOnly(Side.CLIENT)
public BlockRenderLayer getBlockLayer() {
return BlockRenderLayer.CUTOUT_MIPPED;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public void harvestBlock(World world, EntityPlayer player, BlockPos pos, IBlockState state, @Nullable TileEntity tile, ItemStack stack) {
super.harvestBlock(world, player, pos, state, tile, stack);
world.setBlockToAir(pos);
}
@Override
public boolean removedByPlayer(IBlockState state, World world, BlockPos pos, EntityPlayer player, boolean willHarvest) {
return willHarvest || super.removedByPlayer(state, world, pos, player, willHarvest);
}
@Override
public boolean onBlockActivated(World world, BlockPos blockPos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
boolean success = FluidUtil.interactWithFluidHandler(player, hand, world, blockPos, side);
if (success) {
world.checkLight(blockPos);
world.updateComparatorOutputLevel(blockPos, this);
world.markAndNotifyBlock(blockPos, world.getChunkFromBlockCoords(blockPos), state, state, 3);
return true;
}
return true;
}
@Override
public void onBlockHarvested(World worldIn, BlockPos pos, IBlockState state, EntityPlayer player) {
if (!player.capabilities.isCreativeMode)
this.dropBlockAsItem(worldIn, pos, state, 0);
super.onBlockHarvested(worldIn, pos, state, player);
}
@Override
public void getDrops(NonNullList<ItemStack> drops, IBlockAccess world, BlockPos pos, IBlockState blockState, int fortune) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileBloodTank) {
TileBloodTank bloodTank = (TileBloodTank) tile;
ItemStack drop = new ItemStack(this, 1, bloodTank.getBlockMetadata());
NBTTagCompound fluidTag = new NBTTagCompound();
if (bloodTank.getTank().getFluid() != null) {
bloodTank.getTank().getFluid().writeToNBT(fluidTag);
NBTTagCompound dropTag = new NBTTagCompound();
dropTag.setTag("Fluid", fluidTag);
drop.setTagCompound(dropTag);
}
drops.add(drop);
}
}
@Override
public void onBlockPlacedBy(World world, BlockPos pos, IBlockState blockState, EntityLivingBase placer, ItemStack stack) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileBloodTank) {
TileBloodTank bloodTank = (TileBloodTank) tile;
NBTTagCompound tag = stack.getTagCompound();
if (stack.hasTagCompound() && stack.getTagCompound().hasKey("Fluid")) {
FluidStack fluidStack = FluidStack.loadFluidStackFromNBT(tag.getCompoundTag("Fluid"));
bloodTank.getTank().setFluid(fluidStack);
}
}
world.checkLight(pos);
world.updateComparatorOutputLevel(pos, this);
world.markAndNotifyBlock(pos, world.getChunkFromBlockCoords(pos), blockState, blockState, 3);
}
@Override
public int getLightValue(IBlockState state, IBlockAccess world, BlockPos pos) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileBloodTank) {
FluidStack fluidStack = ((TileBloodTank) tile).getTank().getFluid();
return fluidStack == null || fluidStack.amount <= 0 ? 0 : fluidStack.getFluid().getLuminosity(fluidStack);
}
return super.getLightValue(state, world, pos);
}
@Override
public ItemStack getPickBlock(IBlockState state, RayTraceResult target, World world, BlockPos pos, EntityPlayer player) {
return new ItemStack(this, 1, getMetaFromState(state));
}
@Override
public boolean hasComparatorInputOverride(IBlockState state) {
return true;
}
@Override
public int getComparatorInputOverride(IBlockState state, World world, BlockPos pos) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileBloodTank)
return ((TileBloodTank) tile).getComparatorOutput();
return 0;
}
@Override
public TileEntity createTileEntity(World worldIn, IBlockState blockState) {
return new TileBloodTank(getMetaFromState(blockState));
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Override
public ItemBlock getItem() {
return new ItemBlockBloodTank(this);
}
// IVariantProvider
@Override
public void gatherVariants(@Nonnull Int2ObjectMap<String> variants) {
for (int i = 0; i < TileBloodTank.CAPACITIES.length; i++)
variants.put(i, "inventory");
}
}

View file

@ -1,20 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.EnumDecorative;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
public class BlockDecorative extends BlockEnum<EnumDecorative> {
public BlockDecorative() {
super(Material.ROCK, EnumDecorative.class);
setUnlocalizedName(BloodMagic.MODID + ".");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
}

View file

@ -1,21 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.client.IVariantProvider;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.util.IStringSerializable;
public class BlockDemonBase<E extends Enum<E> & IStringSerializable> extends BlockEnum<E> implements IVariantProvider {
public BlockDemonBase(String baseName, Class<E> enumClass) {
super(Material.ROCK, enumClass);
setUnlocalizedName(BloodMagic.MODID + "." + baseName + ".");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
}

View file

@ -1,102 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.soul.IDemonWillGem;
import WayofTime.bloodmagic.soul.IDiscreteDemonWill;
import WayofTime.bloodmagic.tile.TileDemonCrucible;
import WayofTime.bloodmagic.util.Utils;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemBlock;
import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockDemonCrucible extends Block implements IVariantProvider, IBMBlock {
public BlockDemonCrucible() {
super(Material.ROCK);
setUnlocalizedName(BloodMagic.MODID + ".demonCrucible");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 0);
// setBlockBounds(0.3F, 0F, 0.3F, 0.72F, 1F, 0.72F);
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
ItemStack heldItem = player.getHeldItem(hand);
TileDemonCrucible crucible = (TileDemonCrucible) world.getTileEntity(pos);
if (crucible == null || player.isSneaking())
return false;
if (!heldItem.isEmpty()) {
if (!(heldItem.getItem() instanceof IDiscreteDemonWill) && !(heldItem.getItem() instanceof IDemonWillGem)) {
return true;
}
}
Utils.insertItemToTile(crucible, player);
world.notifyBlockUpdate(pos, state, state, 3);
return true;
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileDemonCrucible tile = (TileDemonCrucible) world.getTileEntity(blockPos);
if (tile != null)
tile.dropItems();
super.breakBlock(world, blockPos, blockState);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileDemonCrucible();
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
}

View file

@ -1,223 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.item.ItemDemonCrystal;
import WayofTime.bloodmagic.item.block.ItemBlockDemonCrystal;
import WayofTime.bloodmagic.soul.EnumDemonWillType;
import WayofTime.bloodmagic.soul.PlayerDemonWillHandler;
import WayofTime.bloodmagic.tile.TileDemonCrystal;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyEnum;
import net.minecraft.block.properties.PropertyInteger;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.creativetab.CreativeTabs;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemBlock;
import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.NonNullList;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
public class BlockDemonCrystal extends Block implements IBMBlock, IVariantProvider {
public static final PropertyInteger AGE = PropertyInteger.create("age", 0, 6);
public static final PropertyEnum<EnumDemonWillType> TYPE = PropertyEnum.create("type", EnumDemonWillType.class);
public static final PropertyEnum<EnumFacing> ATTACHED = PropertyEnum.create("attached", EnumFacing.class);
public BlockDemonCrystal() {
super(Material.ROCK);
this.setDefaultState(this.blockState.getBaseState().withProperty(TYPE, EnumDemonWillType.DEFAULT).withProperty(ATTACHED, EnumFacing.UP));
setUnlocalizedName(BloodMagic.MODID + ".demonCrystal.");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 2);
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
if (!world.isRemote) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileDemonCrystal) {
TileDemonCrystal crystal = (TileDemonCrystal) tile;
boolean isCreative = player.capabilities.isCreativeMode;
boolean holdsCrystal = player.getHeldItem(hand).getItem() instanceof ItemDemonCrystal;
if (PlayerDemonWillHandler.getTotalDemonWill(EnumDemonWillType.DEFAULT, player) > 1024 && !(holdsCrystal && isCreative)) {
crystal.dropSingleCrystal();
}
if (!crystal.getWorld().isRemote && isCreative && holdsCrystal) {
if (crystal.crystalCount < 7) {
crystal.internalCounter = 0;
if(crystal.progressToNextCrystal > 0)
crystal.progressToNextCrystal--;
crystal.crystalCount++;
crystal.markDirty();
crystal.notifyUpdate();
}
}
}
}
return true;
}
@Override
public void getDrops(NonNullList<ItemStack> drops, IBlockAccess world, BlockPos pos, IBlockState state, int fortune) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileDemonCrystal) {
EnumDemonWillType type = state.getValue(TYPE);
int number = ((TileDemonCrystal) tile).getCrystalCount();
drops.add(getItemStackDropped(type, number));
}
}
@Override
public IBlockState getActualState(IBlockState state, IBlockAccess world, BlockPos pos) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileDemonCrystal) {
TileDemonCrystal crystal = (TileDemonCrystal) tile;
state = state.withProperty(AGE, crystal.getCrystalCountForRender());
state = state.withProperty(ATTACHED, crystal.getPlacement());
}
return state;
}
@Override
public void neighborChanged(IBlockState state, World world, BlockPos pos, Block blockIn, BlockPos fromPos) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileDemonCrystal) {
TileDemonCrystal crystal = (TileDemonCrystal) tile;
EnumFacing placement = crystal.getPlacement();
BlockPos offsetPos = pos.offset(placement.getOpposite());
IBlockState offsetState = world.getBlockState(offsetPos);
if (!offsetState.isSideSolid(world, offsetPos, placement))
world.destroyBlock(pos, true);
}
}
@Override
public boolean canPlaceBlockOnSide(World world, BlockPos pos, EnumFacing side) {
BlockPos offsetPos = pos.offset(side.getOpposite());
IBlockState offsetState = world.getBlockState(offsetPos);
return offsetState.isSideSolid(world, offsetPos, side) && this.canPlaceBlockAt(world, pos);
}
@Override
public void getSubBlocks(CreativeTabs creativeTabs, NonNullList<ItemStack> list) {
for (EnumDemonWillType willType : EnumDemonWillType.values())
list.add(new ItemStack(this, 1, willType.ordinal()));
}
@Override
public void harvestBlock(World world, EntityPlayer player, BlockPos pos, IBlockState state, @Nullable TileEntity tile, ItemStack stack) {
super.harvestBlock(world, player, pos, state, tile, stack);
world.setBlockToAir(pos);
}
@Override
public boolean removedByPlayer(IBlockState state, World world, BlockPos pos, EntityPlayer player, boolean willHarvest) {
return willHarvest || super.removedByPlayer(state, world, pos, player, false);
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public IBlockState getStateFromMeta(int meta) {
return this.getDefaultState().withProperty(TYPE, EnumDemonWillType.values()[meta]);
}
@Override
public int getMetaFromState(IBlockState state) {
return state.getValue(TYPE).ordinal();
}
@Override
protected BlockStateContainer createBlockState() {
return new BlockStateContainer(this, TYPE, AGE, ATTACHED);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileDemonCrystal();
}
public static ItemStack getItemStackDropped(EnumDemonWillType type, int crystalNumber) {
ItemStack stack = ItemStack.EMPTY;
switch (type) {
case CORROSIVE:
stack = EnumDemonWillType.CORROSIVE.getStack();
break;
case DEFAULT:
stack = EnumDemonWillType.DEFAULT.getStack();
break;
case DESTRUCTIVE:
stack = EnumDemonWillType.DESTRUCTIVE.getStack();
break;
case STEADFAST:
stack = EnumDemonWillType.STEADFAST.getStack();
break;
case VENGEFUL:
stack = EnumDemonWillType.VENGEFUL.getStack();
break;
}
stack.setCount(crystalNumber);
return stack;
}
@Override
public ItemBlock getItem() {
return new ItemBlockDemonCrystal(this);
}
@Override
public void gatherVariants(@Nonnull Int2ObjectMap<String> variants) {
for (EnumDemonWillType willType : EnumDemonWillType.values())
variants.put(willType.ordinal(), "age=3,attached=up,type=" + willType.getName());
}
}

View file

@ -1,77 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.tile.TileDemonCrystallizer;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.BlockContainer;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.item.ItemBlock;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nonnull;
public class BlockDemonCrystallizer extends BlockContainer implements IVariantProvider, IBMBlock {
public BlockDemonCrystallizer() {
super(Material.ROCK);
setUnlocalizedName(BloodMagic.MODID + ".demonCrystallizer");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 0);
// setBlockBounds(0.3F, 0F, 0.3F, 0.72F, 1F, 0.72F);
}
@Override
public boolean isSideSolid(IBlockState state, IBlockAccess world, BlockPos pos, EnumFacing side) {
return side == EnumFacing.UP;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public TileEntity createNewTileEntity(World world, int meta) {
return new TileDemonCrystallizer();
}
@Override
public void gatherVariants(@Nonnull Int2ObjectMap<String> variants) {
variants.put(0, "normal");
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
}

View file

@ -1,21 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.EnumSubWillType;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
public class BlockDemonLight extends BlockEnum<EnumSubWillType> {
public BlockDemonLight() {
super(Material.ROCK, EnumSubWillType.class);
setUnlocalizedName(BloodMagic.MODID + ".demonlight.");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
setLightLevel(1);
}
}

View file

@ -1,33 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnumPillar;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.IStringSerializable;
import javax.annotation.Nonnull;
public class BlockDemonPillarBase<E extends Enum<E> & IStringSerializable> extends BlockEnumPillar<E> {
public BlockDemonPillarBase(String baseName, Material materialIn, Class<E> enumClass) {
super(materialIn, enumClass);
setUnlocalizedName(BloodMagic.MODID + "." + baseName + ".");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
@Override
public void gatherVariants(@Nonnull Int2ObjectMap<String> variants) {
EnumFacing.Axis[] axis = new EnumFacing.Axis[]{EnumFacing.Axis.Y, EnumFacing.Axis.X, EnumFacing.Axis.Z};
for (int i = 0; i < 3; i++)
for (int j = 0; j < this.getTypes().length; j++)
variants.put(i * 5 + j, "axis=" + axis[i] + ",type=" + this.getTypes()[j]);
}
}

View file

@ -1,31 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnumPillarCap;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.IStringSerializable;
import javax.annotation.Nonnull;
public class BlockDemonPillarCapBase<E extends Enum<E> & IStringSerializable> extends BlockEnumPillarCap<E> {
public BlockDemonPillarCapBase(String baseName, Material materialIn, Class<E> enumClass) {
super(materialIn, enumClass);
setUnlocalizedName(BloodMagic.MODID + "." + baseName + ".");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
@Override
public void gatherVariants(@Nonnull Int2ObjectMap<String> variants) {
for (int i = 0; i < EnumFacing.values().length; i++)
for (int j = 0; j < this.getTypes().length; j++)
variants.put(i * 2 + j, "facing=" + EnumFacing.values()[i] + ",type=" + this.getTypes()[j]);
}
}

View file

@ -1,63 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.tile.TileDemonPylon;
import net.minecraft.block.BlockContainer;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.item.ItemBlock;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
public class BlockDemonPylon extends BlockContainer implements IBMBlock, IVariantProvider {
public BlockDemonPylon() {
super(Material.ROCK);
setUnlocalizedName(BloodMagic.MODID + ".demonPylon");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 0);
// setBlockBounds(0.3F, 0F, 0.3F, 0.72F, 1F, 0.72F);
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public TileEntity createNewTileEntity(World world, int meta) {
return new TileDemonPylon();
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
}

View file

@ -1,27 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnumStairs;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.util.IStringSerializable;
public class BlockDemonStairsBase<E extends Enum<E> & IStringSerializable> extends BlockEnumStairs<E> {
public BlockDemonStairsBase(String baseName, Material materialIn, Class<E> enumClass) {
super(materialIn, enumClass);
setUnlocalizedName(BloodMagic.MODID + "." + baseName + ".");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
@Override
public void gatherVariants(Int2ObjectMap<String> variants) {
for (int i = 0; i < this.getTypes().length; i++)
variants.put(i, "facing=south,half=bottom,shape=straight,type=" + this.getTypes()[i]);
}
}

View file

@ -1,27 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnumWall;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.util.IStringSerializable;
public class BlockDemonWallBase<E extends Enum<E> & IStringSerializable> extends BlockEnumWall<E> {
public BlockDemonWallBase(String baseName, Material materialIn, Class<E> enumClass) {
super(materialIn, enumClass);
setUnlocalizedName(BloodMagic.MODID + "." + baseName + ".");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
@Override
public void gatherVariants(Int2ObjectMap<String> variants) {
for (int i = 0; i < this.getTypes().length; i++)
variants.put(i, "east=true,north=false,south=false,type=" + this.getTypes()[i] + ",up=true,west=true");
}
}

View file

@ -1,183 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.ritual.IMasterRitualStone;
import WayofTime.bloodmagic.teleport.PortalLocation;
import WayofTime.bloodmagic.teleport.TeleportQueue;
import WayofTime.bloodmagic.block.base.BlockInteger;
import WayofTime.bloodmagic.ritual.portal.LocationsHandler;
import WayofTime.bloodmagic.ritual.portal.Teleports;
import WayofTime.bloodmagic.tile.TileDimensionalPortal;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumParticleTypes;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import javax.annotation.Nullable;
import java.util.ArrayList;
import java.util.Random;
public class BlockDimensionalPortal extends BlockInteger {
protected static final AxisAlignedBB AABB_0 = new AxisAlignedBB(0.0D, 0.0D, 0.375D, 1.0D, 1.0D, 0.625D);
protected static final AxisAlignedBB AABB_1 = new AxisAlignedBB(0.375D, 0.0D, 0.0D, 0.625D, 1.0D, 1.0D);
protected static final AxisAlignedBB AABB_DEFAULT = new AxisAlignedBB(0.375D, 0.0D, 0.375D, 0.625D, 1.0D, 0.625D);
public BlockDimensionalPortal() {
super(Material.PORTAL, 2);
setUnlocalizedName(BloodMagic.MODID + ".dimensionalPortal");
setBlockUnbreakable();
setResistance(2000);
setLightOpacity(0);
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public AxisAlignedBB getCollisionBoundingBox(IBlockState state, IBlockAccess world, BlockPos pos) {
return null;
}
public boolean isOpaqueCube() {
return false;
}
public boolean isFullCube() {
return false;
}
@Override
public int getLightValue(IBlockState state, IBlockAccess world, BlockPos pos) {
return 12;
}
@Override
public void onEntityCollidedWithBlock(World world, BlockPos pos, IBlockState blockState, Entity entity) {
if (!world.isRemote && world.getTileEntity(pos) instanceof TileDimensionalPortal) {
TileDimensionalPortal tile = (TileDimensionalPortal) world.getTileEntity(pos);
if (LocationsHandler.getLocationsHandler() != null) {
ArrayList<PortalLocation> linkedLocations = LocationsHandler.getLocationsHandler().getLinkedLocations(tile.portalID);
if (linkedLocations != null && !linkedLocations.isEmpty() && linkedLocations.size() > 1) {
if (world.getTileEntity(tile.getMasterStonePos()) != null && world.getTileEntity(tile.getMasterStonePos()) instanceof IMasterRitualStone) {
IMasterRitualStone masterRitualStone = (IMasterRitualStone) world.getTileEntity(tile.getMasterStonePos());
if (linkedLocations.get(0).equals(new PortalLocation(masterRitualStone.getBlockPos().up(), world.provider.getDimension()))) {
PortalLocation portal = linkedLocations.get(1);
if (portal.getDimension() == world.provider.getDimension()) {
TeleportQueue.getInstance().addITeleport(new Teleports.TeleportSameDim(portal.getX(), portal.getY(), portal.getZ(), entity, masterRitualStone.getOwner(), false));
} else {
TeleportQueue.getInstance().addITeleport(new Teleports.TeleportToDim(portal.getX(), portal.getY(), portal.getZ(), entity, masterRitualStone.getOwner(), world, portal.getDimension(), false));
}
} else if (linkedLocations.get(1).equals(new PortalLocation(masterRitualStone.getBlockPos().up(), world.provider.getDimension()))) {
PortalLocation portal = linkedLocations.get(0);
if (portal.getDimension() == world.provider.getDimension()) {
TeleportQueue.getInstance().addITeleport(new Teleports.TeleportSameDim(portal.getX(), portal.getY(), portal.getZ(), entity, masterRitualStone.getOwner(), false));
} else {
TeleportQueue.getInstance().addITeleport(new Teleports.TeleportToDim(portal.getX(), portal.getY(), portal.getZ(), entity, masterRitualStone.getOwner(), world, portal.getDimension(), false));
}
}
}
}
}
}
}
@Override
public int quantityDropped(Random par1Random) {
return 0;
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess world, BlockPos pos) {
int meta = state.getBlock().getMetaFromState(state);
if (meta == 0) {
return AABB_0;
} else if (meta == 1) {
return AABB_1;
} else {
return AABB_DEFAULT;
}
}
//
// @Override
// public void setBlockBoundsForItemRender()
// {
// setBlockBounds(0f, 0f, 0.375f, 1f, 1f, 0.625f);
// }
@Override
@SideOnly(Side.CLIENT)
public BlockRenderLayer getBlockLayer() {
return BlockRenderLayer.TRANSLUCENT;
}
@Override
@SideOnly(Side.CLIENT)
public void randomDisplayTick(IBlockState state, World world, BlockPos pos, Random rand) {
this.spawnParticles(world, pos.getX(), pos.getY(), pos.getZ());
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileDimensionalPortal();
}
private void spawnParticles(World world, int x, int y, int z) {
Random random = world.rand;
double d0 = 0.0625D;
for (int i = 0; i < 6; ++i) {
double particleX = (double) ((float) x + random.nextFloat());
double particleY = (double) ((float) y + random.nextFloat());
double particleZ = (double) ((float) z + random.nextFloat());
if (i == 0 && !world.getBlockState(new BlockPos(x, y + 1, z)).isOpaqueCube()) {
particleY = (double) (y + 1) + d0;
}
if (i == 1 && !world.getBlockState(new BlockPos(x, y - 1, z)).isOpaqueCube()) {
particleY = (double) y - d0;
}
if (i == 2 && !world.getBlockState(new BlockPos(x, y, z + 1)).isOpaqueCube()) {
particleZ = (double) (z + 1) + d0;
}
if (i == 3 && !world.getBlockState(new BlockPos(x, y, z - 1)).isOpaqueCube()) {
particleZ = (double) z - d0;
}
if (i == 4 && !world.getBlockState(new BlockPos(x + 1, y, z)).isOpaqueCube()) {
particleX = (double) (x + 1) + d0;
}
if (i == 5 && !world.getBlockState(new BlockPos(x - 1, y, z)).isOpaqueCube()) {
particleX = (double) x - d0;
}
if (particleX < (double) x || particleX > (double) (x + 1) || particleY < 0.0D || particleY > (double) (y + 1) || particleZ < (double) z || particleZ > (double) (z + 1)) {
world.spawnParticle(EnumParticleTypes.REDSTONE, particleX, particleY, particleZ, 0.0D, 0.0D, 0.0D);
}
}
}
}

View file

@ -1,86 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.tile.TileIncenseAltar;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.item.ItemBlock;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockIncenseAltar extends Block implements IVariantProvider, IBMBlock {
protected static final AxisAlignedBB AABB = new AxisAlignedBB(0.3F, 0F, 0.3F, 0.72F, 1F, 0.72F);
public BlockIncenseAltar() {
super(Material.ROCK);
setUnlocalizedName(BloodMagic.MODID + ".incenseAltar");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 0);
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
return AABB;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileIncenseAltar TileIncenseAltar = (TileIncenseAltar) world.getTileEntity(blockPos);
if (TileIncenseAltar != null)
TileIncenseAltar.dropItems();
super.breakBlock(world, blockPos, blockState);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileIncenseAltar();
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
}

View file

@ -1,53 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.util.Constants;
import WayofTime.bloodmagic.tile.routing.TileInputRoutingNode;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockInputRoutingNode extends BlockRoutingNode {
public BlockInputRoutingNode() {
super();
setUnlocalizedName(BloodMagic.MODID + ".inputRouting");
}
@Override
//TODO: Combine BlockInputRoutingNode and BlockInputRoutingNode so they have the same superclass
public void breakBlock(World world, BlockPos pos, IBlockState state) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileInputRoutingNode) {
((TileInputRoutingNode) tile).removeAllConnections();
((TileInputRoutingNode) tile).dropItems();
}
super.breakBlock(world, pos, state);
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
if (world.getTileEntity(pos) instanceof TileInputRoutingNode) {
player.openGui(BloodMagic.instance, Constants.Gui.ROUTING_NODE_GUI, world, pos.getX(), pos.getY(), pos.getZ());
}
return true;
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileInputRoutingNode();
}
}

View file

@ -1,91 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.EnumSubWillType;
import WayofTime.bloodmagic.tile.TileInversionPillar;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.common.property.Properties;
public class BlockInversionPillar extends BlockEnum<EnumSubWillType> {
public BlockInversionPillar() {
super(Material.ROCK, EnumSubWillType.class);
setUnlocalizedName(BloodMagic.MODID + ".inversionpillar.");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileEntity tile = world.getTileEntity(blockPos);
if (tile instanceof TileInversionPillar) {
TileInversionPillar tilePillar = (TileInversionPillar) world.getTileEntity(blockPos);
tilePillar.removePillarFromMap();
}
super.breakBlock(world, blockPos, blockState);
}
@Override
public IBlockState getActualState(IBlockState state, IBlockAccess world, BlockPos pos) {
return super.getActualState(state, world, pos).withProperty(Properties.StaticProperty, true);
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public void gatherVariants(Int2ObjectMap<String> variants) {
for (int i = 0; i < this.getTypes().length; i++)
variants.put(i, "static=false,type=" + this.getTypes()[i]);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileInversionPillar(state.getValue(getProperty()).getType());
}
protected BlockStateContainer createStateContainer() {
return new BlockStateContainer.Builder(this).add(getProperty(), Properties.StaticProperty).add(Properties.AnimationProperty).build();
}
}

View file

@ -1,57 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.EnumInversionCap;
import WayofTime.bloodmagic.client.IVariantProvider;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
public class BlockInversionPillarEnd extends BlockEnum<EnumInversionCap> implements IVariantProvider {
public BlockInversionPillarEnd() {
super(Material.ROCK, EnumInversionCap.class);
setUnlocalizedName(BloodMagic.MODID + ".inversionpillarend.");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 2);
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public void gatherVariants(Int2ObjectMap<String> variants) {
for (int i = 0; i < this.getTypes().length; i++)
variants.put(i, "type=" + this.getTypes()[i]);
}
}

View file

@ -1,39 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.tile.routing.TileItemRoutingNode;
import WayofTime.bloodmagic.tile.routing.TileRoutingNode;
import net.minecraft.block.state.IBlockState;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockItemRoutingNode extends BlockRoutingNode {
public BlockItemRoutingNode() {
super();
setUnlocalizedName(BloodMagic.MODID + ".itemRouting");
}
@Override
public void breakBlock(World world, BlockPos pos, IBlockState state) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileRoutingNode) {
((TileRoutingNode) tile).removeAllConnections();
}
super.breakBlock(world, pos, state);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileItemRoutingNode();
}
}

View file

@ -1,66 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.util.Constants;
import WayofTime.bloodmagic.util.helper.TextHelper;
import net.minecraft.block.material.Material;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.ResourceLocation;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fluids.BlockFluidClassic;
import net.minecraftforge.fluids.Fluid;
import net.minecraftforge.fluids.FluidStack;
import java.awt.Color;
public class BlockLifeEssence extends BlockFluidClassic {
private static final Fluid LIFE_ESSENCE = new FluidLifeEssence();
public BlockLifeEssence() {
super(LIFE_ESSENCE, Material.WATER);
setUnlocalizedName(BloodMagic.MODID + ".fluid.lifeEssence");
getLifeEssence().setBlock(this);
}
@Override
public boolean canDisplace(IBlockAccess world, BlockPos blockPos) {
return !world.getBlockState(blockPos).getBlock().getMaterial(world.getBlockState(blockPos)).isLiquid() && super.canDisplace(world, blockPos);
}
@Override
public boolean displaceIfPossible(World world, BlockPos blockPos) {
return !world.getBlockState(blockPos).getBlock().getMaterial(world.getBlockState(blockPos)).isLiquid() && super.displaceIfPossible(world, blockPos);
}
@Override
public BlockRenderLayer getBlockLayer() {
return BlockRenderLayer.SOLID;
}
public static Fluid getLifeEssence() {
return LIFE_ESSENCE;
}
public static class FluidLifeEssence extends Fluid {
public FluidLifeEssence() {
super("lifeEssence", new ResourceLocation(Constants.Mod.DOMAIN + "blocks/lifeEssenceStill"), new ResourceLocation(Constants.Mod.DOMAIN + "blocks/lifeEssenceFlowing"));
setDensity(2000);
setViscosity(2000);
}
@Override
public int getColor() {
return Color.RED.getRGB();
}
@Override
public String getLocalizedName(FluidStack fluidStack) {
return TextHelper.localize("tile.bloodmagic.fluid.lifeEssence.name");
}
}
}

View file

@ -1,43 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.tile.routing.TileMasterRoutingNode;
import net.minecraft.block.state.IBlockState;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockMasterRoutingNode extends BlockRoutingNode {
public BlockMasterRoutingNode() {
super();
setUnlocalizedName(BloodMagic.MODID + ".masterRouting");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 2);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileMasterRoutingNode();
}
// @Override
// public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, ItemStack heldItem, EnumFacing side, float hitX, float hitY, float hitZ)
// {
// if (world.getTileEntity(pos) instanceof TileMasterRoutingNode)
// {
// player.openGui(BloodMagic.instance, Constants.Gui.MASTER_ROUTING_NODE_GUI, world, pos.getX(), pos.getY(), pos.getZ());
// }
//
// return true;
// }
}

View file

@ -1,228 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.altar.ComponentType;
import WayofTime.bloodmagic.altar.IAltarComponent;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.EnumMimic;
import WayofTime.bloodmagic.core.RegistrarBloodMagicBlocks;
import WayofTime.bloodmagic.tile.TileMimic;
import WayofTime.bloodmagic.util.Utils;
import WayofTime.bloodmagic.item.block.ItemBlockMimic;
import net.minecraft.block.Block;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.init.Blocks;
import net.minecraft.item.ItemBlock;
import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import javax.annotation.Nullable;
public class BlockMimic extends BlockEnum<EnumMimic> implements IAltarComponent {
public static final int sentientMimicMeta = 4;
public BlockMimic() {
super(Material.ROCK, EnumMimic.class);
setUnlocalizedName(BloodMagic.MODID + ".mimic.");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("pickaxe", 0);
setLightOpacity(15);
}
@Nullable
@Override
public AxisAlignedBB getCollisionBoundingBox(IBlockState state, IBlockAccess world, BlockPos pos) {
switch (this.getMetaFromState(state)) {
case 1:
case 2:
case 3:
case 4:
TileMimic tileMimic = (TileMimic) world.getTileEntity(pos);
if (tileMimic != null && !tileMimic.getStackInSlot(0).isEmpty()) {
Block mimicBlock = Block.getBlockFromItem(tileMimic.getStackInSlot(0).getItem());
if (mimicBlock == Blocks.AIR) {
return FULL_BLOCK_AABB;
}
IBlockState mimicState = tileMimic.getReplacedState();
if (mimicBlock != this) {
return mimicState.getCollisionBoundingBox(world, pos);
}
} else {
return FULL_BLOCK_AABB;
}
case 0:
default:
return NULL_AABB;
}
}
@Override
@SideOnly(Side.CLIENT)
public AxisAlignedBB getSelectedBoundingBox(IBlockState state, World world, BlockPos pos) {
TileMimic tileMimic = (TileMimic) world.getTileEntity(pos);
if (tileMimic != null && !tileMimic.getStackInSlot(0).isEmpty()) {
Block mimicBlock = Block.getBlockFromItem(tileMimic.getStackInSlot(0).getItem());
if (mimicBlock == Blocks.AIR) {
return FULL_BLOCK_AABB;
}
IBlockState mimicState = tileMimic.getReplacedState();
if (mimicBlock != this) {
return mimicState.getSelectedBoundingBox(world, pos);
}
}
return FULL_BLOCK_AABB;
}
@Override
public int getLightOpacity(IBlockState state) {
switch (this.getMetaFromState(state)) {
case 2:
case 4:
return 0;
default:
return this.lightOpacity;
}
}
@Override
public int getLightValue(IBlockState state) {
switch (this.getMetaFromState(state)) {
case 3:
return 15;
default:
return this.lightValue;
}
}
@Override
public int getMetaFromState(IBlockState state) {
if (state.getBlock() == this) {
return super.getMetaFromState(state);
}
return state.getBlock().getMetaFromState(state);
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
TileMimic mimic = (TileMimic) world.getTileEntity(pos);
return mimic != null && mimic.onBlockActivated(world, pos, state, player, hand, player.getHeldItem(hand), side);
}
@Override
public IBlockState getActualState(IBlockState state, IBlockAccess world, BlockPos pos) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileMimic) {
TileMimic mimic = (TileMimic) tile;
ItemStack stack = mimic.getStackInSlot(0);
if (stack.getItem() instanceof ItemBlock) {
Block block = ((ItemBlock) stack.getItem()).getBlock();
IBlockState mimicState = mimic.getReplacedState();
if (block != this) {
if (block.getRenderType(mimicState) == EnumBlockRenderType.ENTITYBLOCK_ANIMATED) {
return RegistrarBloodMagicBlocks.BLOOD_LIGHT.getDefaultState(); //Small and invisible-ish, basically this is returned in order to not render over the animated block (TESR)
}
return block.getActualState(mimicState, world, pos);
}
}
}
return state;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean canRenderInLayer(IBlockState state, BlockRenderLayer layer) {
return layer == BlockRenderLayer.CUTOUT_MIPPED || layer == BlockRenderLayer.CUTOUT;
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileEntity tile = world.getTileEntity(blockPos);
if (tile instanceof TileMimic) {
TileMimic TileMimic = (TileMimic) world.getTileEntity(blockPos);
if (TileMimic != null)
TileMimic.dropItems();
}
super.breakBlock(world, blockPos, blockState);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileMimic();
}
// IAltarComponent
@Nullable
@Override
public ComponentType getType(World world, IBlockState state, BlockPos pos) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileMimic) {
TileMimic mimic = (TileMimic) tile;
ItemStack stack = mimic.getStackInSlot(0);
if (stack.getItem() instanceof ItemBlock) {
Block block = ((ItemBlock) stack.getItem()).getBlock();
if (block instanceof IAltarComponent) {
return ((IAltarComponent) block).getType(world, mimic.getReplacedState(), pos);
} else {
for (ComponentType altarComponent : ComponentType.values())
if (block == Utils.getBlockForComponent(altarComponent))
return altarComponent;
}
}
}
return null;
}
@Override
public ItemBlock getItem() {
return new ItemBlockMimic(this);
}
}

View file

@ -1,53 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.util.Constants;
import WayofTime.bloodmagic.tile.routing.TileOutputRoutingNode;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockOutputRoutingNode extends BlockRoutingNode {
public BlockOutputRoutingNode() {
super();
setUnlocalizedName(BloodMagic.MODID + ".outputRouting");
}
@Override
//TODO: Combine BlockOutputRoutingNode and BlockInputRoutingNode so they have the same superclass
public void breakBlock(World world, BlockPos pos, IBlockState state) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileOutputRoutingNode) {
((TileOutputRoutingNode) tile).removeAllConnections();
((TileOutputRoutingNode) tile).dropItems();
}
super.breakBlock(world, pos, state);
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
if (world.getTileEntity(pos) instanceof TileOutputRoutingNode) {
player.openGui(BloodMagic.instance, Constants.Gui.ROUTING_NODE_GUI, world, pos.getX(), pos.getY(), pos.getZ());
}
return true;
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileOutputRoutingNode();
}
}

View file

@ -1,64 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.EnumPath;
import WayofTime.bloodmagic.incense.IIncensePath;
import WayofTime.bloodmagic.util.helper.TextHelper;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.client.util.ITooltipFlag;
import net.minecraft.item.ItemStack;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import java.util.List;
public class BlockPath extends BlockEnum<EnumPath> implements IIncensePath {
public BlockPath() {
super(Material.ROCK, EnumPath.class);
setUnlocalizedName(BloodMagic.MODID + ".path.");
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.STONE);
setHarvestLevel("axe", 0, getStateFromMeta(0));
setHarvestLevel("axe", 0, getStateFromMeta(1));
setHarvestLevel("pickaxe", 0, getStateFromMeta(2));
setHarvestLevel("pickaxe", 0, getStateFromMeta(3));
setHarvestLevel("pickaxe", 0, getStateFromMeta(4));
setHarvestLevel("pickaxe", 0, getStateFromMeta(5));
setHarvestLevel("pickaxe", 3, getStateFromMeta(6));
setHarvestLevel("pickaxe", 3, getStateFromMeta(7));
}
@Override
public void addInformation(ItemStack stack, World world, List<String> tooltip, ITooltipFlag tooltipFlag) {
tooltip.add(TextHelper.localizeEffect("tooltip.bloodmagic.decoration.safe"));
super.addInformation(stack, world, tooltip, tooltipFlag);
}
@Override
public int getLevelOfPath(World world, BlockPos pos, IBlockState state) {
switch (this.getMetaFromState(state)) {
case 0:
case 1:
return 2;
case 2:
case 3:
return 4;
case 4:
case 5:
return 6;
case 6:
case 7:
return 8;
default:
return 0;
}
}
}

View file

@ -1,82 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.tile.TilePhantomBlock;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import javax.annotation.Nullable;
import java.util.Random;
public class BlockPhantom extends Block implements IVariantProvider {
public BlockPhantom() {
super(Material.CLOTH);
setUnlocalizedName(BloodMagic.MODID + ".phantom");
setCreativeTab(BloodMagic.TAB_BM);
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
@SideOnly(Side.CLIENT)
public BlockRenderLayer getBlockLayer() {
return BlockRenderLayer.TRANSLUCENT;
}
@Override
@SideOnly(Side.CLIENT)
public boolean shouldSideBeRendered(IBlockState state, IBlockAccess world, BlockPos pos, EnumFacing side) {
return world.getBlockState(pos.offset(side)) != state || state.getBlock() != this && super.shouldSideBeRendered(state, world, pos, side);
}
@Override
public int quantityDropped(Random par1Random) {
return 0;
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TilePhantomBlock(100);
}
}

View file

@ -1,136 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.event.RitualEvent;
import WayofTime.bloodmagic.iface.IBindable;
import WayofTime.bloodmagic.ritual.imperfect.IImperfectRitualStone;
import WayofTime.bloodmagic.ritual.Ritual;
import WayofTime.bloodmagic.ritual.imperfect.ImperfectRitual;
import WayofTime.bloodmagic.util.helper.RitualHelper;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.block.enums.EnumRitualController;
import WayofTime.bloodmagic.core.RegistrarBloodMagicItems;
import WayofTime.bloodmagic.tile.TileImperfectRitualStone;
import WayofTime.bloodmagic.tile.TileMasterRitualStone;
import amerifrance.guideapi.api.IGuideLinked;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.ResourceLocation;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.text.TextComponentTranslation;
import net.minecraft.world.Explosion;
import net.minecraft.world.World;
import net.minecraftforge.common.MinecraftForge;
import javax.annotation.Nullable;
public class BlockRitualController extends BlockEnum<EnumRitualController> implements IGuideLinked {
public BlockRitualController() {
super(Material.ROCK, EnumRitualController.class);
setUnlocalizedName(BloodMagic.MODID + ".stone.ritual.");
setCreativeTab(BloodMagic.TAB_BM);
setSoundType(SoundType.STONE);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 2);
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
ItemStack heldItem = player.getHeldItem(hand);
TileEntity tile = world.getTileEntity(pos);
if (state.getValue(getProperty()) != EnumRitualController.IMPERFECT && tile instanceof TileMasterRitualStone) {
if (heldItem.getItem() == RegistrarBloodMagicItems.ACTIVATION_CRYSTAL) {
if (((IBindable) heldItem.getItem()).getBinding(heldItem) == null)
return false;
String key = RitualHelper.getValidRitual(world, pos);
if (!key.isEmpty()) {
Ritual ritual = BloodMagic.RITUAL_MANAGER.getRitual(key);
if (ritual != null) {
EnumFacing direction = RitualHelper.getDirectionOfRitual(world, pos, ritual);
// TODO: Give a message stating that this ritual is not a valid ritual.
if (direction != null && RitualHelper.checkValidRitual(world, pos, ritual, direction)) {
if (((TileMasterRitualStone) tile).activateRitual(heldItem, player, BloodMagic.RITUAL_MANAGER.getRitual(key))) {
((TileMasterRitualStone) tile).setDirection(direction);
if (state.getValue(getProperty()) == EnumRitualController.INVERTED)
((TileMasterRitualStone) tile).setInverted(true);
}
} else {
player.sendStatusMessage(new TextComponentTranslation("chat.bloodmagic.ritual.notValid"), true);
}
} else {
player.sendStatusMessage(new TextComponentTranslation("chat.bloodmagic.ritual.notValid"), true);
}
} else {
player.sendStatusMessage(new TextComponentTranslation("chat.bloodmagic.ritual.notValid"), true);
}
}
} else if (state.getValue(getProperty()) == EnumRitualController.IMPERFECT && tile instanceof TileImperfectRitualStone) {
IBlockState ritualBlock = world.getBlockState(pos.up());
ImperfectRitual ritual = BloodMagic.RITUAL_MANAGER.getImperfectRitual(ritualBlock);
if (ritual == null)
return false;
RitualEvent.ImperfectRitualActivatedEvent event = new RitualEvent.ImperfectRitualActivatedEvent((IImperfectRitualStone) tile, player, ritual);
return !MinecraftForge.EVENT_BUS.post(event) && ((TileImperfectRitualStone) tile).performRitual(world, pos, ritual, player);
}
return false;
}
@Override
public void onBlockHarvested(World world, BlockPos pos, IBlockState state, EntityPlayer player) {
TileEntity tile = world.getTileEntity(pos);
if (getMetaFromState(state) == 0 && tile instanceof TileMasterRitualStone)
((TileMasterRitualStone) tile).stopRitual(Ritual.BreakType.BREAK_MRS);
}
@Override
public void onBlockDestroyedByExplosion(World world, BlockPos pos, Explosion explosion) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileMasterRitualStone)
((TileMasterRitualStone) tile).stopRitual(Ritual.BreakType.EXPLOSION);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return state.getValue(getProperty()) != EnumRitualController.IMPERFECT ? new TileMasterRitualStone() : new TileImperfectRitualStone();
}
// IGuideLinked
@Override
@Nullable
public ResourceLocation getLinkedEntry(World world, BlockPos pos, EntityPlayer player, ItemStack stack) {
IBlockState state = world.getBlockState(pos);
if (state.getValue(getProperty()).equals(EnumRitualController.MASTER)) {
TileMasterRitualStone mrs = (TileMasterRitualStone) world.getTileEntity(pos);
if (mrs == null || mrs.getCurrentRitual() == null)
return null;
else
return new ResourceLocation("bloodmagic", "ritual_" + mrs.getCurrentRitual().getName());
} else if (state.getValue(getProperty()).equals(EnumRitualController.IMPERFECT)) {
ImperfectRitual imperfectRitual = BloodMagic.RITUAL_MANAGER.getImperfectRitual(world.getBlockState(pos.up()));
if (imperfectRitual != null)
return new ResourceLocation("bloodmagic", "ritual_" + imperfectRitual.getName());
}
return null;
}
}

View file

@ -1,62 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.ritual.EnumRuneType;
import WayofTime.bloodmagic.ritual.IRitualStone;
import WayofTime.bloodmagic.block.base.BlockEnum;
import WayofTime.bloodmagic.core.RegistrarBloodMagicBlocks;
import WayofTime.bloodmagic.util.helper.TextHelper;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.client.util.ITooltipFlag;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import java.util.List;
public class BlockRitualStone extends BlockEnum<EnumRuneType> implements IRitualStone {
public BlockRitualStone() {
super(Material.IRON, EnumRuneType.class);
setUnlocalizedName(BloodMagic.MODID + ".ritualStone.");
setCreativeTab(BloodMagic.TAB_BM);
setSoundType(SoundType.STONE);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 2);
}
@SideOnly(Side.CLIENT)
@Override
public void addInformation(ItemStack stack, World world, List<String> tooltip, ITooltipFlag tooltipFlag) {
tooltip.add(TextHelper.localizeEffect("tooltip.bloodmagic.decoration.safe"));
super.addInformation(stack, world, tooltip, tooltipFlag);
}
@Override
public int damageDropped(IBlockState state) {
return 0;
}
@Override
public boolean canSilkHarvest(World world, BlockPos pos, IBlockState state, EntityPlayer player) {
return false;
}
@Override
public boolean isRuneType(World world, BlockPos pos, EnumRuneType runeType) {
return runeType == this.getTypes()[getMetaFromState(world.getBlockState(pos))];
}
@Override
public void setRuneType(World world, BlockPos pos, EnumRuneType runeType) {
int meta = runeType.ordinal();
IBlockState newState = RegistrarBloodMagicBlocks.RITUAL_STONE.getStateFromMeta(meta);
world.setBlockState(pos, newState);
}
}

View file

@ -1,137 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.tile.routing.TileMasterRoutingNode;
import WayofTime.bloodmagic.tile.routing.TileRoutingNode;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyBool;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.item.ItemBlock;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nonnull;
public class BlockRoutingNode extends Block implements IBMBlock, IVariantProvider {
public static final PropertyBool UP = PropertyBool.create("up");
public static final PropertyBool DOWN = PropertyBool.create("down");
public static final PropertyBool NORTH = PropertyBool.create("north");
public static final PropertyBool EAST = PropertyBool.create("east");
public static final PropertyBool SOUTH = PropertyBool.create("south");
public static final PropertyBool WEST = PropertyBool.create("west");
protected static final AxisAlignedBB AABB = new AxisAlignedBB(0.378F, 0.378F, 0.378F, 0.625F, 0.625F, 0.625F);
public BlockRoutingNode() {
super(Material.ROCK);
setCreativeTab(BloodMagic.TAB_BM);
setHardness(2.0F);
setResistance(5.0F);
setHarvestLevel("pickaxe", 2);
this.setDefaultState(this.blockState.getBaseState().withProperty(DOWN, false).withProperty(UP, false).withProperty(NORTH, false).withProperty(EAST, false).withProperty(SOUTH, false).withProperty(WEST, false));
}
@Override
public boolean canConnectRedstone(IBlockState state, IBlockAccess world, BlockPos pos, EnumFacing side) {
return true;
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
return AABB;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public boolean canRenderInLayer(IBlockState state, BlockRenderLayer layer) {
return layer == BlockRenderLayer.CUTOUT_MIPPED || layer == BlockRenderLayer.TRANSLUCENT;
}
@Override
public IBlockState getStateFromMeta(int meta) {
return this.getDefaultState();
}
/**
* Convert the BlockState into the correct metadata value
*/
@Override
public int getMetaFromState(IBlockState state) {
return 0;
}
@Override
public IBlockState getActualState(IBlockState state, IBlockAccess worldIn, BlockPos pos) {
return state.withProperty(UP, this.shouldConnect(state, worldIn, pos.up(), EnumFacing.DOWN)).withProperty(DOWN, this.shouldConnect(state, worldIn, pos.down(), EnumFacing.UP)).withProperty(NORTH, this.shouldConnect(state, worldIn, pos.north(), EnumFacing.SOUTH)).withProperty(EAST, this.shouldConnect(state, worldIn, pos.east(), EnumFacing.WEST)).withProperty(SOUTH, this.shouldConnect(state, worldIn, pos.south(), EnumFacing.NORTH)).withProperty(WEST, this.shouldConnect(state, worldIn, pos.west(), EnumFacing.EAST));
}
@Override
protected BlockStateContainer createBlockState() {
return new BlockStateContainer(this, UP, DOWN, NORTH, EAST, WEST, SOUTH);
}
public boolean shouldConnect(IBlockState state, IBlockAccess world, BlockPos pos, EnumFacing attachedSide) {
IBlockState blockState = world.getBlockState(pos);
Block block = blockState.getBlock();
return block.getMaterial(blockState).isOpaque() && blockState.isFullCube();
}
@Override
public void breakBlock(World world, BlockPos pos, IBlockState blockState) {
if (!world.isRemote) {
TileEntity tile = world.getTileEntity(pos);
if (tile instanceof TileRoutingNode) {
((TileRoutingNode) tile).removeAllConnections();
} else if (tile instanceof TileMasterRoutingNode) {
((TileMasterRoutingNode) tile).removeAllConnections();
}
}
super.breakBlock(world, pos, blockState);
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
@Override
public void gatherVariants(@Nonnull Int2ObjectMap<String> variants) {
variants.put(0, "inventory");
}
}

View file

@ -1,100 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.tile.TileSoulForge;
import WayofTime.bloodmagic.util.Constants;
import net.minecraft.block.Block;
import net.minecraft.block.SoundType;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemBlock;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import javax.annotation.Nullable;
public class BlockSoulForge extends Block implements IVariantProvider, IBMBlock {
protected static final AxisAlignedBB AABB = new AxisAlignedBB(0.06F, 0.0F, 0.06F, 0.94F, 0.75F, 0.94F);
public BlockSoulForge() {
super(Material.IRON);
setUnlocalizedName(BloodMagic.MODID + ".soulForge");
setHardness(2.0F);
setResistance(5.0F);
setSoundType(SoundType.METAL);
setHarvestLevel("pickaxe", 1);
setCreativeTab(BloodMagic.TAB_BM);
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
return AABB;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
if (world.getTileEntity(pos) instanceof TileSoulForge)
player.openGui(BloodMagic.instance, Constants.Gui.SOUL_FORGE_GUI, world, pos.getX(), pos.getY(), pos.getZ());
return true;
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileSoulForge tileSoulForge = (TileSoulForge) world.getTileEntity(blockPos);
if (tileSoulForge != null)
tileSoulForge.dropItems();
super.breakBlock(world, blockPos, blockState);
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileSoulForge();
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
}

View file

@ -1,105 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.ConfigHandler;
import WayofTime.bloodmagic.tile.TileSpectralBlock;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
import javax.annotation.Nullable;
import java.util.List;
import java.util.Random;
public class BlockSpectral extends Block {
protected static final AxisAlignedBB AABB = new AxisAlignedBB(0, 0, 0, 0, 0, 0);
public BlockSpectral() {
super(Material.CLOTH);
setUnlocalizedName(BloodMagic.MODID + ".spectral");
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
return AABB;
}
@Override
public boolean isNormalCube(IBlockState state, IBlockAccess world, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public boolean causesSuffocation(IBlockState state) {
return false;
}
@SideOnly(Side.CLIENT)
@Override
public BlockRenderLayer getBlockLayer() {
return BlockRenderLayer.TRANSLUCENT;
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return ConfigHandler.client.invisibleSpectralBlocks ? EnumBlockRenderType.INVISIBLE : EnumBlockRenderType.MODEL;
}
@Override
@SideOnly(Side.CLIENT)
public boolean shouldSideBeRendered(IBlockState state, IBlockAccess world, BlockPos pos, EnumFacing side) {
return world.getBlockState(pos.offset(side)) != state || state.getBlock() != this && super.shouldSideBeRendered(state, world, pos, side);
}
@Override
public void addCollisionBoxToList(IBlockState state, World worldIn, BlockPos pos, AxisAlignedBB mask, List<AxisAlignedBB> list, Entity collidingEntity, boolean bool) {
}
@Override
public int quantityDropped(Random par1Random) {
return 0;
}
@Override
public boolean isReplaceable(IBlockAccess worldIn, BlockPos pos) {
return true;
}
@Override
public boolean isAir(IBlockState state, IBlockAccess world, BlockPos blockPos) {
return true;
}
@Override
public boolean hasTileEntity(IBlockState state) {
return true;
}
@Nullable
@Override
public TileEntity createTileEntity(World world, IBlockState state) {
return new TileSpectralBlock();
}
}

View file

@ -1,66 +0,0 @@
package WayofTime.bloodmagic.block;
import WayofTime.bloodmagic.BloodMagic;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.item.ItemTelepositionFocus;
import WayofTime.bloodmagic.tile.TileTeleposer;
import WayofTime.bloodmagic.util.Constants;
import net.minecraft.block.BlockContainer;
import net.minecraft.block.material.Material;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemBlock;
import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumBlockRenderType;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
public class BlockTeleposer extends BlockContainer implements IVariantProvider, IBMBlock {
public BlockTeleposer() {
super(Material.ROCK);
setCreativeTab(BloodMagic.TAB_BM);
setUnlocalizedName(BloodMagic.MODID + ".teleposer");
setHardness(2.0F);
setResistance(5.0F);
}
@Override
public EnumBlockRenderType getRenderType(IBlockState state) {
return EnumBlockRenderType.MODEL;
}
@Override
public boolean onBlockActivated(World world, BlockPos pos, IBlockState state, EntityPlayer player, EnumHand hand, EnumFacing side, float hitX, float hitY, float hitZ) {
ItemStack playerItem = player.getHeldItem(hand);
if (playerItem.getItem() instanceof ItemTelepositionFocus)
((ItemTelepositionFocus) playerItem.getItem()).setBlockPos(playerItem, world, pos);
else if (world.getTileEntity(pos) instanceof TileTeleposer)
player.openGui(BloodMagic.instance, Constants.Gui.TELEPOSER_GUI, world, pos.getX(), pos.getY(), pos.getZ());
return true;
}
@Override
public void breakBlock(World world, BlockPos blockPos, IBlockState blockState) {
TileTeleposer tileTeleposer = (TileTeleposer) world.getTileEntity(blockPos);
if (tileTeleposer != null)
tileTeleposer.dropItems();
super.breakBlock(world, blockPos, blockState);
}
@Override
public TileEntity createNewTileEntity(World worldIn, int meta) {
return new TileTeleposer();
}
@Override
public ItemBlock getItem() {
return new ItemBlock(this);
}
}

View file

@ -1,8 +0,0 @@
package WayofTime.bloodmagic.block;
import net.minecraft.item.ItemBlock;
public interface IBMBlock {
ItemBlock getItem();
}

View file

@ -1,98 +0,0 @@
package WayofTime.bloodmagic.block.base;
import WayofTime.bloodmagic.block.IBMBlock;
import WayofTime.bloodmagic.client.IVariantProvider;
import WayofTime.bloodmagic.item.block.base.ItemBlockEnum;
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyEnum;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.creativetab.CreativeTabs;
import net.minecraft.item.ItemBlock;
import net.minecraft.item.ItemStack;
import net.minecraft.util.IStringSerializable;
import net.minecraft.util.NonNullList;
import javax.annotation.Nonnull;
public class BlockEnum<E extends Enum<E> & IStringSerializable> extends Block implements IBMBlock, IVariantProvider {
private final E[] types;
private final PropertyEnum<E> property;
private final BlockStateContainer realStateContainer;
public BlockEnum(Material material, Class<E> enumClass, String propName) {
super(material);
this.types = enumClass.getEnumConstants();
this.property = PropertyEnum.create(propName, enumClass);
this.realStateContainer = createStateContainer();
setDefaultState(getBlockState().getBaseState());
}
public BlockEnum(Material material, Class<E> enumClass) {
this(material, enumClass, "type");
}
@Override
protected final BlockStateContainer createBlockState() {
return new BlockStateContainer.Builder(this).build(); // Blank to avoid crashes
}
@Override
public final BlockStateContainer getBlockState() {
return realStateContainer;
}
@Override
public IBlockState getStateFromMeta(int meta) {
return getDefaultState().withProperty(property, types[meta]);
}
@Override
public int getMetaFromState(IBlockState state) {
return state.getValue(property).ordinal();
}
@Override
public int damageDropped(IBlockState state) {
return getMetaFromState(state);
}
@Override
public void getSubBlocks(CreativeTabs tab, NonNullList<ItemStack> subBlocks) {
for (E type : types)
subBlocks.add(new ItemStack(this, 1, type.ordinal()));
}
protected BlockStateContainer createStateContainer() {
return new BlockStateContainer.Builder(this).add(property).build();
}
@Override
public ItemBlock getItem() {
return new ItemBlockEnum<>(this);
}
@Override
public void gatherVariants(@Nonnull Int2ObjectMap<String> variants) {
if (getItem() == null)
return;
for (int i = 0; i < types.length; i++)
variants.put(i, getProperty().getName() + "=" + types[i].name());
}
public E[] getTypes() {
return types;
}
public PropertyEnum<E> getProperty() {
return property;
}
public BlockStateContainer getRealStateContainer() {
return realStateContainer;
}
}

View file

@ -1,124 +0,0 @@
package WayofTime.bloodmagic.block.base;
import net.minecraft.block.BlockRotatedPillar;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.IProperty;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.EnumHand;
import net.minecraft.util.IStringSerializable;
import net.minecraft.util.Rotation;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.RayTraceResult;
import net.minecraft.world.World;
import org.apache.commons.lang3.ArrayUtils;
public class BlockEnumPillar<E extends Enum<E> & IStringSerializable> extends BlockEnum<E> {
public BlockEnumPillar(Material material, Class<E> enumClass, String propName) {
super(material, enumClass, propName);
}
public BlockEnumPillar(Material material, Class<E> enumClass) {
this(material, enumClass, "type");
}
@Override
protected BlockStateContainer createStateContainer() {
return new BlockStateContainer.Builder(this).add(getProperty(), BlockRotatedPillar.AXIS).build();
}
@Override
public IBlockState getStateFromMeta(int meta) {
IBlockState state = getBlockState().getBaseState().withProperty(this.getProperty(), getTypes()[meta % 5]);
switch (meta / 5) {
case 0:
state = state.withProperty(BlockRotatedPillar.AXIS, EnumFacing.Axis.Y);
break;
case 1:
state = state.withProperty(BlockRotatedPillar.AXIS, EnumFacing.Axis.X);
break;
case 2:
state = state.withProperty(BlockRotatedPillar.AXIS, EnumFacing.Axis.Z);
break;
default:
state.withProperty(BlockRotatedPillar.AXIS, EnumFacing.Axis.Y);
break;
}
return state;
}
@Override
public ItemStack getPickBlock(IBlockState state, RayTraceResult target, World world, BlockPos pos, EntityPlayer player) {
return new ItemStack(this, 1, damageDropped(state));
}
@SuppressWarnings("incomplete-switch")
@Override
public int getMetaFromState(IBlockState state) {
int i = ArrayUtils.indexOf(getTypes(), state.getValue(getProperty()));
switch (state.getValue(BlockRotatedPillar.AXIS)) {
case X:
i = i + 5;
break;
case Z:
i = i + 10;
break;
}
return i;
}
@Override
public boolean rotateBlock(World world, BlockPos pos, EnumFacing axis) {
IBlockState state = world.getBlockState(pos);
for (IProperty<?> prop : state.getProperties().keySet()) {
if (prop == BlockRotatedPillar.AXIS) {
world.setBlockState(pos, state.cycleProperty(prop));
return true;
}
}
return false;
}
@Override
public IBlockState withRotation(IBlockState state, Rotation rot) {
switch (rot) {
case COUNTERCLOCKWISE_90:
case CLOCKWISE_90:
switch (state.getValue(BlockRotatedPillar.AXIS)) {
case X:
return state.withProperty(BlockRotatedPillar.AXIS, EnumFacing.Axis.Z);
case Z:
return state.withProperty(BlockRotatedPillar.AXIS, EnumFacing.Axis.X);
default:
return state;
}
default:
return state;
}
}
@Override
protected ItemStack getSilkTouchDrop(IBlockState state) {
return new ItemStack(this, 1, damageDropped(state));
}
@Override
public IBlockState getStateForPlacement(World world, BlockPos pos, EnumFacing facing, float hitX, float hitY, float hitZ, int meta, EntityLivingBase placer, EnumHand hand) {
return super.getStateForPlacement(world, pos, facing, hitX, hitY, hitZ, meta, placer, hand).withProperty(BlockRotatedPillar.AXIS, facing.getAxis());
}
@Override
public int damageDropped(IBlockState state) {
return super.getMetaFromState(state);
}
}

View file

@ -1,73 +0,0 @@
package WayofTime.bloodmagic.block.base;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyDirection;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.util.*;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.RayTraceResult;
import net.minecraft.world.World;
import org.apache.commons.lang3.ArrayUtils;
public class BlockEnumPillarCap<E extends Enum<E> & IStringSerializable> extends BlockEnum<E> {
public static final PropertyDirection FACING = PropertyDirection.create("facing");
public BlockEnumPillarCap(Material material, Class<E> enumClass, String propName) {
super(material, enumClass, propName);
}
public BlockEnumPillarCap(Material material, Class<E> enumClass) {
this(material, enumClass, "type");
}
@Override
protected BlockStateContainer createStateContainer() {
return new BlockStateContainer.Builder(this).add(getProperty(), FACING).build();
}
@Override
public IBlockState getStateFromMeta(int meta) {
IBlockState state = getBlockState().getBaseState().withProperty(this.getProperty(), getTypes()[meta % 2]);
return state.withProperty(FACING, EnumFacing.getFront(meta / 2));
}
@Override
public int getMetaFromState(IBlockState state) {
int i = ArrayUtils.indexOf(getTypes(), state.getValue(getProperty()));
return i + 2 * state.getValue(FACING).getIndex();
}
@Override
public ItemStack getPickBlock(IBlockState state, RayTraceResult target, World world, BlockPos pos, EntityPlayer player) {
return new ItemStack(this, 1, damageDropped(state));
}
@Override
public IBlockState withRotation(IBlockState state, Rotation rot) {
return state.withProperty(FACING, rot.rotate(state.getValue(FACING)));
}
@Override
public IBlockState withMirror(IBlockState state, Mirror mirrorIn) {
return state.withRotation(mirrorIn.toRotation(state.getValue(FACING)));
}
@Override
protected ItemStack getSilkTouchDrop(IBlockState state) {
return new ItemStack(this, 1, damageDropped(state));
}
@Override
public IBlockState getStateForPlacement(World world, BlockPos pos, EnumFacing facing, float hitX, float hitY, float hitZ, int meta, EntityLivingBase placer, EnumHand hand) {
return super.getStateForPlacement(world, pos, facing, hitX, hitY, hitZ, meta, placer, hand).withProperty(FACING, facing);
}
@Override
public int damageDropped(IBlockState state) {
return super.getMetaFromState(state);
}
}

View file

@ -1,343 +0,0 @@
package WayofTime.bloodmagic.block.base;
import com.google.common.collect.Lists;
import net.minecraft.block.BlockHorizontal;
import net.minecraft.block.BlockStairs;
import net.minecraft.block.BlockStairs.EnumHalf;
import net.minecraft.block.BlockStairs.EnumShape;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyDirection;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.util.*;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.RayTraceResult;
import net.minecraft.util.math.Vec3d;
import net.minecraft.world.IBlockAccess;
import net.minecraft.world.World;
import net.minecraftforge.common.ForgeModContainer;
import org.apache.commons.lang3.ArrayUtils;
import javax.annotation.Nullable;
import java.util.List;
public class BlockEnumStairs<E extends Enum<E> & IStringSerializable> extends BlockEnum<E> {
public static final PropertyDirection FACING = BlockHorizontal.FACING;
protected static final AxisAlignedBB AABB_SLAB_TOP = new AxisAlignedBB(0.0D, 0.5D, 0.0D, 1.0D, 1.0D, 1.0D);
protected static final AxisAlignedBB AABB_QTR_TOP_WEST = new AxisAlignedBB(0.0D, 0.5D, 0.0D, 0.5D, 1.0D, 1.0D);
protected static final AxisAlignedBB AABB_QTR_TOP_EAST = new AxisAlignedBB(0.5D, 0.5D, 0.0D, 1.0D, 1.0D, 1.0D);
protected static final AxisAlignedBB AABB_QTR_TOP_NORTH = new AxisAlignedBB(0.0D, 0.5D, 0.0D, 1.0D, 1.0D, 0.5D);
protected static final AxisAlignedBB AABB_QTR_TOP_SOUTH = new AxisAlignedBB(0.0D, 0.5D, 0.5D, 1.0D, 1.0D, 1.0D);
protected static final AxisAlignedBB AABB_OCT_TOP_NW = new AxisAlignedBB(0.0D, 0.5D, 0.0D, 0.5D, 1.0D, 0.5D);
protected static final AxisAlignedBB AABB_OCT_TOP_NE = new AxisAlignedBB(0.5D, 0.5D, 0.0D, 1.0D, 1.0D, 0.5D);
protected static final AxisAlignedBB AABB_OCT_TOP_SW = new AxisAlignedBB(0.0D, 0.5D, 0.5D, 0.5D, 1.0D, 1.0D);
protected static final AxisAlignedBB AABB_OCT_TOP_SE = new AxisAlignedBB(0.5D, 0.5D, 0.5D, 1.0D, 1.0D, 1.0D);
protected static final AxisAlignedBB AABB_SLAB_BOTTOM = new AxisAlignedBB(0.0D, 0.0D, 0.0D, 1.0D, 0.5D, 1.0D);
protected static final AxisAlignedBB AABB_QTR_BOT_WEST = new AxisAlignedBB(0.0D, 0.0D, 0.0D, 0.5D, 0.5D, 1.0D);
protected static final AxisAlignedBB AABB_QTR_BOT_EAST = new AxisAlignedBB(0.5D, 0.0D, 0.0D, 1.0D, 0.5D, 1.0D);
protected static final AxisAlignedBB AABB_QTR_BOT_NORTH = new AxisAlignedBB(0.0D, 0.0D, 0.0D, 1.0D, 0.5D, 0.5D);
protected static final AxisAlignedBB AABB_QTR_BOT_SOUTH = new AxisAlignedBB(0.0D, 0.0D, 0.5D, 1.0D, 0.5D, 1.0D);
protected static final AxisAlignedBB AABB_OCT_BOT_NW = new AxisAlignedBB(0.0D, 0.0D, 0.0D, 0.5D, 0.5D, 0.5D);
protected static final AxisAlignedBB AABB_OCT_BOT_NE = new AxisAlignedBB(0.5D, 0.0D, 0.0D, 1.0D, 0.5D, 0.5D);
protected static final AxisAlignedBB AABB_OCT_BOT_SW = new AxisAlignedBB(0.0D, 0.0D, 0.5D, 0.5D, 0.5D, 1.0D);
protected static final AxisAlignedBB AABB_OCT_BOT_SE = new AxisAlignedBB(0.5D, 0.0D, 0.5D, 1.0D, 0.5D, 1.0D);
public BlockEnumStairs(Material material, Class<E> enumClass, String propName) {
super(material, enumClass, propName);
}
public BlockEnumStairs(Material material, Class<E> enumClass) {
this(material, enumClass, "type");
}
@Override
protected BlockStateContainer createStateContainer() {
return new BlockStateContainer.Builder(this).add(getProperty(), FACING, BlockStairs.HALF, BlockStairs.SHAPE).build();
}
@Override
public void addCollisionBoxToList(IBlockState state, World worldIn, BlockPos pos, AxisAlignedBB entityBox, List<AxisAlignedBB> collidingBoxes, @Nullable Entity entityIn, boolean bool) {
state = this.getActualState(state, worldIn, pos);
for (AxisAlignedBB axisalignedbb : getCollisionBoxList(state)) {
addCollisionBoxToList(pos, entityBox, collidingBoxes, axisalignedbb);
}
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
@Override
public boolean isFullCube(IBlockState state) {
return false;
}
@Override
public IBlockState getStateForPlacement(World world, BlockPos pos, EnumFacing facing, float hitX, float hitY, float hitZ, int meta, EntityLivingBase placer, EnumHand hand) {
IBlockState state = super.getStateForPlacement(world, pos, facing, hitX, hitY, hitZ, meta, placer, hand);
state = state.withProperty(FACING, placer.getHorizontalFacing()).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.STRAIGHT);
return facing != EnumFacing.DOWN && (facing == EnumFacing.UP || (double) hitY <= 0.5D) ? state.withProperty(BlockStairs.HALF, BlockStairs.EnumHalf.BOTTOM) : state.withProperty(BlockStairs.HALF, BlockStairs.EnumHalf.TOP);
}
@Override
public RayTraceResult collisionRayTrace(IBlockState blockState, World worldIn, BlockPos pos, Vec3d start, Vec3d end) {
List<RayTraceResult> list = Lists.newArrayList();
for (AxisAlignedBB axisalignedbb : getCollisionBoxList(this.getActualState(blockState, worldIn, pos))) {
list.add(this.rayTrace(pos, start, end, axisalignedbb));
}
RayTraceResult rayTrace = null;
double d1 = 0.0D;
for (RayTraceResult raytraceresult : list) {
if (raytraceresult != null) {
double d0 = raytraceresult.hitVec.squareDistanceTo(end);
if (d0 > d1) {
rayTrace = raytraceresult;
d1 = d0;
}
}
}
return rayTrace;
}
// Meta looks like: {1|11|1} = {HALF|FACING|TYPE}
@Override
public IBlockState getStateFromMeta(int meta) {
IBlockState state = getBlockState().getBaseState().withProperty(BlockStairs.HALF, (meta & 8) > 0 ? BlockStairs.EnumHalf.TOP : BlockStairs.EnumHalf.BOTTOM);
state = state.withProperty(FACING, EnumFacing.getFront(5 - (meta & 6) / 2)).withProperty(this.getProperty(), getTypes()[meta % 2]);
return state;
}
// Meta looks like: {1|11|1} = {HALF|FACING|TYPE}
@Override
public int getMetaFromState(IBlockState state) {
int i = 0;
if (state.getValue(BlockStairs.HALF) == BlockStairs.EnumHalf.TOP) {
i |= 4;
}
i = i | 5 - state.getValue(FACING).getIndex();
return i * 2 + ArrayUtils.indexOf(getTypes(), state.getValue(getProperty()));
}
@Override
public IBlockState getActualState(IBlockState state, IBlockAccess worldIn, BlockPos pos) {
return state.withProperty(BlockStairs.SHAPE, getStairsShape(state, worldIn, pos));
}
@Override
public IBlockState withRotation(IBlockState state, Rotation rot) {
return state.withProperty(FACING, rot.rotate(state.getValue(FACING)));
}
@SuppressWarnings("incomplete-switch")
@Override
public IBlockState withMirror(IBlockState state, Mirror mirrorIn) {
EnumFacing facing = state.getValue(FACING);
BlockStairs.EnumShape stairShape = state.getValue(BlockStairs.SHAPE);
switch (mirrorIn) {
case LEFT_RIGHT:
if (facing.getAxis() == EnumFacing.Axis.Z) {
switch (stairShape) {
case OUTER_LEFT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.OUTER_RIGHT);
case OUTER_RIGHT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.OUTER_LEFT);
case INNER_RIGHT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.INNER_LEFT);
case INNER_LEFT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.INNER_RIGHT);
default:
return state.withRotation(Rotation.CLOCKWISE_180);
}
}
break;
case FRONT_BACK:
if (facing.getAxis() == EnumFacing.Axis.X) {
switch (stairShape) {
case OUTER_LEFT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.OUTER_RIGHT);
case OUTER_RIGHT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.OUTER_LEFT);
case INNER_RIGHT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.INNER_RIGHT);
case INNER_LEFT:
return state.withRotation(Rotation.CLOCKWISE_180).withProperty(BlockStairs.SHAPE, BlockStairs.EnumShape.INNER_LEFT);
case STRAIGHT:
return state.withRotation(Rotation.CLOCKWISE_180);
}
}
}
return super.withMirror(state, mirrorIn);
}
@Override
protected ItemStack getSilkTouchDrop(IBlockState state) {
return new ItemStack(this, 1, damageDropped(state));
}
@Override
public int damageDropped(IBlockState state) {
return super.getMetaFromState(state);
}
@Override
public ItemStack getPickBlock(IBlockState state, RayTraceResult target, World world, BlockPos pos, EntityPlayer player) {
return new ItemStack(this, 1, damageDropped(state));
}
@Override
public boolean doesSideBlockRendering(IBlockState state, IBlockAccess world, BlockPos pos, EnumFacing face) {
if (ForgeModContainer.disableStairSlabCulling)
return super.doesSideBlockRendering(state, world, pos, face);
if (state.isOpaqueCube())
return true;
state = this.getActualState(state, world, pos);
EnumHalf half = state.getValue(BlockStairs.HALF);
EnumFacing side = state.getValue(FACING);
EnumShape shape = state.getValue(BlockStairs.SHAPE);
if (face == EnumFacing.UP)
return half == EnumHalf.TOP;
if (face == EnumFacing.DOWN)
return half == EnumHalf.BOTTOM;
if (shape == EnumShape.OUTER_LEFT || shape == EnumShape.OUTER_RIGHT)
return false;
if (face == side)
return true;
if (shape == EnumShape.INNER_LEFT && face.rotateY() == side)
return true;
if (shape == EnumShape.INNER_RIGHT && face.rotateYCCW() == side)
return true;
return false;
}
private static List<AxisAlignedBB> getCollisionBoxList(IBlockState state) {
List<AxisAlignedBB> list = Lists.newArrayList();
boolean flag = state.getValue(BlockStairs.HALF) == BlockStairs.EnumHalf.TOP;
list.add(flag ? AABB_SLAB_TOP : AABB_SLAB_BOTTOM);
BlockStairs.EnumShape stairShape = state.getValue(BlockStairs.SHAPE);
if (stairShape == BlockStairs.EnumShape.STRAIGHT || stairShape == BlockStairs.EnumShape.INNER_LEFT || stairShape == BlockStairs.EnumShape.INNER_RIGHT) {
list.add(getCollQuarterBlock(state));
}
if (stairShape != BlockStairs.EnumShape.STRAIGHT) {
list.add(getCollEighthBlock(state));
}
return list;
}
private static AxisAlignedBB getCollQuarterBlock(IBlockState state) {
boolean flag = state.getValue(BlockStairs.HALF) == BlockStairs.EnumHalf.TOP;
switch (state.getValue(FACING)) {
case NORTH:
default:
return flag ? AABB_QTR_BOT_NORTH : AABB_QTR_TOP_NORTH;
case SOUTH:
return flag ? AABB_QTR_BOT_SOUTH : AABB_QTR_TOP_SOUTH;
case WEST:
return flag ? AABB_QTR_BOT_WEST : AABB_QTR_TOP_WEST;
case EAST:
return flag ? AABB_QTR_BOT_EAST : AABB_QTR_TOP_EAST;
}
}
private static AxisAlignedBB getCollEighthBlock(IBlockState state) {
EnumFacing facing = state.getValue(FACING);
EnumFacing newFacing;
switch (state.getValue(BlockStairs.SHAPE)) {
case OUTER_LEFT:
default:
newFacing = facing;
break;
case OUTER_RIGHT:
newFacing = facing.rotateY();
break;
case INNER_RIGHT:
newFacing = facing.getOpposite();
break;
case INNER_LEFT:
newFacing = facing.rotateYCCW();
}
boolean isTop = state.getValue(BlockStairs.HALF) == BlockStairs.EnumHalf.TOP;
switch (newFacing) {
case NORTH:
default:
return isTop ? AABB_OCT_BOT_NW : AABB_OCT_TOP_NW;
case SOUTH:
return isTop ? AABB_OCT_BOT_SE : AABB_OCT_TOP_SE;
case WEST:
return isTop ? AABB_OCT_BOT_SW : AABB_OCT_TOP_SW;
case EAST:
return isTop ? AABB_OCT_BOT_NE : AABB_OCT_TOP_NE;
}
}
private static BlockStairs.EnumShape getStairsShape(IBlockState state, IBlockAccess world, BlockPos pos) {
EnumFacing facing = state.getValue(FACING);
IBlockState offsetState = world.getBlockState(pos.offset(facing));
if (isBlockStairs(offsetState) && state.getValue(BlockStairs.HALF) == offsetState.getValue(BlockStairs.HALF)) {
EnumFacing offsetFacing = offsetState.getValue(FACING);
if (offsetFacing.getAxis() != state.getValue(FACING).getAxis() && isDifferentStairs(state, world, pos, offsetFacing.getOpposite())) {
if (offsetFacing == facing.rotateYCCW()) {
return BlockStairs.EnumShape.OUTER_LEFT;
}
return BlockStairs.EnumShape.OUTER_RIGHT;
}
}
IBlockState oppositeOffsetState = world.getBlockState(pos.offset(facing.getOpposite()));
if (isBlockStairs(oppositeOffsetState) && state.getValue(BlockStairs.HALF) == oppositeOffsetState.getValue(BlockStairs.HALF)) {
EnumFacing oppositeOffsetFacing = oppositeOffsetState.getValue(FACING);
if (oppositeOffsetFacing.getAxis() != (state.getValue(FACING)).getAxis() && isDifferentStairs(state, world, pos, oppositeOffsetFacing)) {
if (oppositeOffsetFacing == facing.rotateYCCW()) {
return BlockStairs.EnumShape.INNER_LEFT;
}
return BlockStairs.EnumShape.INNER_RIGHT;
}
}
return BlockStairs.EnumShape.STRAIGHT;
}
private static boolean isDifferentStairs(IBlockState state, IBlockAccess world, BlockPos pos, EnumFacing facing) {
IBlockState offsetState = world.getBlockState(pos.offset(facing));
return !isBlockStairs(offsetState) || offsetState.getValue(FACING) != state.getValue(FACING) || offsetState.getValue(BlockStairs.HALF) != state.getValue(BlockStairs.HALF);
}
public static boolean isBlockStairs(IBlockState state) {
return state.getBlock() instanceof BlockStairs || state.getBlock() instanceof BlockEnumStairs;
}
}

View file

@ -1,122 +0,0 @@
package WayofTime.bloodmagic.block.base;
import net.minecraft.block.Block;
import net.minecraft.block.BlockFenceGate;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyBool;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.init.Blocks;
import net.minecraft.item.ItemStack;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.IStringSerializable;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IBlockAccess;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly;
public class BlockEnumWall<E extends Enum<E> & IStringSerializable> extends BlockEnum<E> {
public static final PropertyBool UP = PropertyBool.create("up");
public static final PropertyBool NORTH = PropertyBool.create("north");
public static final PropertyBool EAST = PropertyBool.create("east");
public static final PropertyBool SOUTH = PropertyBool.create("south");
public static final PropertyBool WEST = PropertyBool.create("west");
protected static final AxisAlignedBB[] AABB_BY_INDEX = new AxisAlignedBB[]{new AxisAlignedBB(0.25D, 0.0D, 0.25D, 0.75D, 1.0D, 0.75D), new AxisAlignedBB(0.25D, 0.0D, 0.25D, 0.75D, 1.0D, 1.0D), new AxisAlignedBB(0.0D, 0.0D, 0.25D, 0.75D, 1.0D, 0.75D), new AxisAlignedBB(0.0D, 0.0D, 0.25D, 0.75D, 1.0D, 1.0D), new AxisAlignedBB(0.25D, 0.0D, 0.0D, 0.75D, 1.0D, 0.75D), new AxisAlignedBB(0.3125D, 0.0D, 0.0D, 0.6875D, 0.875D, 1.0D), new AxisAlignedBB(0.0D, 0.0D, 0.0D, 0.75D, 1.0D, 0.75D), new AxisAlignedBB(0.0D, 0.0D, 0.0D, 0.75D, 1.0D, 1.0D),
new AxisAlignedBB(0.25D, 0.0D, 0.25D, 1.0D, 1.0D, 0.75D), new AxisAlignedBB(0.25D, 0.0D, 0.25D, 1.0D, 1.0D, 1.0D), new AxisAlignedBB(0.0D, 0.0D, 0.3125D, 1.0D, 0.875D, 0.6875D), new AxisAlignedBB(0.0D, 0.0D, 0.25D, 1.0D, 1.0D, 1.0D), new AxisAlignedBB(0.25D, 0.0D, 0.0D, 1.0D, 1.0D, 0.75D), new AxisAlignedBB(0.25D, 0.0D, 0.0D, 1.0D, 1.0D, 1.0D), new AxisAlignedBB(0.0D, 0.0D, 0.0D, 1.0D, 1.0D, 0.75D), new AxisAlignedBB(0.0D, 0.0D, 0.0D, 1.0D, 1.0D, 1.0D)};
protected static final AxisAlignedBB[] CLIP_AABB_BY_INDEX = new AxisAlignedBB[]{AABB_BY_INDEX[0].setMaxY(1.5D), AABB_BY_INDEX[1].setMaxY(1.5D), AABB_BY_INDEX[2].setMaxY(1.5D), AABB_BY_INDEX[3].setMaxY(1.5D), AABB_BY_INDEX[4].setMaxY(1.5D), AABB_BY_INDEX[5].setMaxY(1.5D), AABB_BY_INDEX[6].setMaxY(1.5D), AABB_BY_INDEX[7].setMaxY(1.5D), AABB_BY_INDEX[8].setMaxY(1.5D), AABB_BY_INDEX[9].setMaxY(1.5D), AABB_BY_INDEX[10].setMaxY(1.5D), AABB_BY_INDEX[11].setMaxY(1.5D), AABB_BY_INDEX[12].setMaxY(1.5D), AABB_BY_INDEX[13].setMaxY(1.5D), AABB_BY_INDEX[14].setMaxY(1.5D),
AABB_BY_INDEX[15].setMaxY(1.5D)};
// Most of this is copied from BlockWall - if there is an issue when porting, look there first.
public BlockEnumWall(Material material, Class<E> enumClass, String propName) {
super(material, enumClass, propName);
}
public BlockEnumWall(Material material, Class<E> enumClass) {
this(material, enumClass, "type");
}
@Override
protected BlockStateContainer createStateContainer() {
return new BlockStateContainer.Builder(this).add(getProperty(), UP, NORTH, EAST, SOUTH, WEST).build();
}
@Override
public AxisAlignedBB getBoundingBox(IBlockState state, IBlockAccess source, BlockPos pos) {
state = state.getActualState(source, pos);
return AABB_BY_INDEX[getAABBIndex(state)];
}
@Override
public AxisAlignedBB getCollisionBoundingBox(IBlockState blockState, IBlockAccess worldIn, BlockPos pos) {
blockState = blockState.getActualState(worldIn, pos);
return CLIP_AABB_BY_INDEX[getAABBIndex(blockState)];
}
public boolean isFullCube(IBlockState state) {
return false;
}
public boolean isPassable(IBlockAccess worldIn, BlockPos pos) {
return false;
}
@Override
public boolean isOpaqueCube(IBlockState state) {
return false;
}
private boolean canConnectTo(IBlockAccess worldIn, BlockPos pos) {
IBlockState worldState = worldIn.getBlockState(pos);
Block block = worldState.getBlock();
return block != Blocks.BARRIER && (!(block != this && !(block instanceof BlockFenceGate)) || ((worldState.getMaterial().isOpaque() && worldState.isFullCube()) && worldState.getMaterial() != Material.GOURD));
}
@SideOnly(Side.CLIENT)
@Override
public boolean shouldSideBeRendered(IBlockState blockState, IBlockAccess blockAccess, BlockPos pos, EnumFacing side) {
return side != EnumFacing.DOWN || super.shouldSideBeRendered(blockState, blockAccess, pos, side);
}
@Override
public IBlockState getActualState(IBlockState state, IBlockAccess worldIn, BlockPos pos) {
boolean canNorth = this.canConnectTo(worldIn, pos.north());
boolean canEast = this.canConnectTo(worldIn, pos.east());
boolean canSouth = this.canConnectTo(worldIn, pos.south());
boolean canWest = this.canConnectTo(worldIn, pos.west());
boolean flag4 = canNorth && !canEast && canSouth && !canWest || !canNorth && canEast && !canSouth && canWest;
return state.withProperty(UP, !flag4 || !worldIn.isAirBlock(pos.up())).withProperty(NORTH, canNorth).withProperty(EAST, canEast).withProperty(SOUTH, canSouth).withProperty(WEST, canWest);
}
@Override
protected ItemStack getSilkTouchDrop(IBlockState state) {
return new ItemStack(this, 1, damageDropped(state));
}
@Override
public int damageDropped(IBlockState state) {
return super.getMetaFromState(state);
}
private static int getAABBIndex(IBlockState state) {
int i = 0;
if (state.getValue(NORTH)) {
i |= 1 << EnumFacing.NORTH.getHorizontalIndex();
}
if (state.getValue(EAST)) {
i |= 1 << EnumFacing.EAST.getHorizontalIndex();
}
if (state.getValue(SOUTH)) {
i |= 1 << EnumFacing.SOUTH.getHorizontalIndex();
}
if (state.getValue(WEST)) {
i |= 1 << EnumFacing.WEST.getHorizontalIndex();
}
return i;
}
}

View file

@ -1,81 +0,0 @@
package WayofTime.bloodmagic.block.base;
import net.minecraft.block.Block;
import net.minecraft.block.material.Material;
import net.minecraft.block.properties.PropertyInteger;
import net.minecraft.block.state.BlockStateContainer;
import net.minecraft.block.state.IBlockState;
import net.minecraft.creativetab.CreativeTabs;
import net.minecraft.item.ItemStack;
import net.minecraft.util.NonNullList;
/**
* Creates a block that has multiple meta-based states.
* <p>
* These states will be numbered 0 through {@code maxMeta}.
*/
public class BlockInteger extends Block {
private final int maxMeta;
private final PropertyInteger property;
private final BlockStateContainer realStateContainer;
public BlockInteger(Material material, int maxMeta, String propName) {
super(material);
this.maxMeta = maxMeta;
this.property = PropertyInteger.create(propName, 0, maxMeta);
this.realStateContainer = createStateContainer();
setDefaultState(getBlockState().getBaseState());
}
public BlockInteger(Material material, int maxMeta) {
this(material, maxMeta, "meta");
}
@Override
protected final BlockStateContainer createBlockState() {
return new BlockStateContainer.Builder(this).build(); // Blank to avoid crashes
}
@Override
public final BlockStateContainer getBlockState() {
return realStateContainer;
}
@Override
public IBlockState getStateFromMeta(int meta) {
return getDefaultState().withProperty(property, meta);
}
@Override
public int getMetaFromState(IBlockState state) {
return state.getValue(property);
}
@Override
public int damageDropped(IBlockState state) {
return getMetaFromState(state);
}
@Override
public void getSubBlocks(CreativeTabs tab, NonNullList<ItemStack> subBlocks) {
for (int i = 0; i < maxMeta; i++)
subBlocks.add(new ItemStack(this, 1, i));
}
protected BlockStateContainer createStateContainer() {
return new BlockStateContainer.Builder(this).add(property).build();
}
public int getMaxMeta() {
return maxMeta;
}
public PropertyInteger getProperty() {
return property;
}
public BlockStateContainer getRealStateContainer() {
return realStateContainer;
}
}

View file

@ -1,22 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumDecorative implements IStringSerializable {
BLOODSTONE_TILE,
BLOODSTONE_BRICK,
CRYSTAL_TILE,
CRYSTAL_BRICK,;
@Override
public String toString() {
return name().toLowerCase(Locale.ROOT);
}
@Override
public String getName() {
return toString();
}
}

View file

@ -1,23 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumDemonBlock1 implements IStringSerializable {
BRICK1_RAW,
BRICK1_CORROSIVE,
BRICK1_DESTRUCTIVE,
BRICK1_VENGEFUL,
BRICK1_STEADFAST;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,33 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumDemonBlock2 implements IStringSerializable {
SMALLBRICK_RAW,
SMALLBRICK_CORROSIVE,
SMALLBRICK_DESTRUCTIVE,
SMALLBRICK_VENGEFUL,
SMALLBRICK_STEADFAST,
TILE_RAW,
TILE_CORROSIVE,
TILE_DESTRUCTIVE,
TILE_VENGEFUL,
TILE_STEADFAST,
TILESPECIAL_RAW,
TILESPECIAL_CORROSIVE,
TILESPECIAL_DESTRUCTIVE,
TILESPECIAL_VENGEFUL,
TILESPECIAL_STEADFAST;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,33 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumDemonBlock3 implements IStringSerializable {
STONE_RAW,
STONE_CORROSIVE,
STONE_DESTRUCTIVE,
STONE_VENGEFUL,
STONE_STEADFAST,
POLISHED_RAW,
POLISHED_CORROSIVE,
POLISHED_DESTRUCTIVE,
POLISHED_VENGEFUL,
POLISHED_STEADFAST,
METAL_RAW,
METAL_CORROSIVE,
METAL_DESTRUCTIVE,
METAL_VENGEFUL,
METAL_STEADFAST;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,28 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumInversionCap implements IStringSerializable {
RAW_BOTTOM,
RAW_TOP,
CORROSIVE_BOTTOM,
CORROSIVE_TOP,
DESTRUCTIVE_BOTTOM,
DESTRUCTIVE_TOP,
VENGEFUL_BOTTOM,
VENGEFUL_TOP,
STEADFAST_BOTTOM,
STEADFAST_TOP;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,23 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumMimic implements IStringSerializable {
NOHITBOX,
SOLIDOPAQUE,
SOLIDCLEAR,
SOLIDLIGHT,
SENTIENT;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,26 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumPath implements IStringSerializable {
WOOD,
WOODTILE,
STONE,
STONETILE,
WORNSTONE,
WORNSTONETILE,
OBSIDIAN,
OBSIDIANTILE;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,21 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumRitualController implements IStringSerializable {
MASTER,
IMPERFECT,
INVERTED,;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,33 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import WayofTime.bloodmagic.soul.EnumDemonWillType;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumSubWillType implements IStringSerializable {
RAW,
CORROSIVE,
DESTRUCTIVE,
VENGEFUL,
STEADFAST;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
public EnumDemonWillType getType() {
String name = name();
if (this == RAW)
name = EnumDemonWillType.DEFAULT.name();
return EnumDemonWillType.valueOf(name);
}
}

View file

@ -1,20 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumSubWillType1 implements IStringSerializable {
RAW,
CORROSIVE;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

View file

@ -1,20 +0,0 @@
package WayofTime.bloodmagic.block.enums;
import net.minecraft.util.IStringSerializable;
import java.util.Locale;
public enum EnumSubWillType2 implements IStringSerializable {
DESTRUCTIVE,
VENGEFUL;
@Override
public String toString() {
return name().toLowerCase(Locale.ENGLISH);
}
@Override
public String getName() {
return this.toString();
}
}

Some files were not shown because too many files have changed in this diff Show more